Proyectos de Subversion Moodle

Rev

| Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
// This file is part of Moodle - http://moodle.org/
2
//
3
// Moodle is free software: you can redistribute it and/or modify
4
// it under the terms of the GNU General Public License as published by
5
// the Free Software Foundation, either version 3 of the License, or
6
// (at your option) any later version.
7
//
8
// Moodle is distributed in the hope that it will be useful,
9
// but WITHOUT ANY WARRANTY; without even the implied warranty of
10
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11
// GNU General Public License for more details.
12
//
13
// You should have received a copy of the GNU General Public License
14
// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
15
 
16
/*
17
 * JavaScript to provide automatic scrolling, e.g. during a drag operation.
18
 *
19
 * Note: this module is defined statically. It is a singleton. You
20
 * can only have one use of it active at any time. However, since this
21
 * is usually used in relation to drag-drop, and since you only ever
22
 * drag one thing at a time, this is not a problem in practice.
23
 *
24
 * @module     core/autoscroll
25
 * @copyright  2016 The Open University
26
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
27
 * @since      3.6
28
 */
29
define(['jquery'], function($) {
30
    /**
31
     * @alias module:core/autoscroll
32
     */
33
    var autoscroll = {
34
        /**
35
         * Size of area near edge of screen that triggers scrolling.
36
         * @private
37
         */
38
        SCROLL_THRESHOLD: 30,
39
 
40
        /**
41
         * How frequently to scroll window.
42
         * @private
43
         */
44
        SCROLL_FREQUENCY: 1000 / 60,
45
 
46
        /**
47
         * How many pixels to scroll per unit (1 = max scroll 30).
48
         * @private
49
         */
50
        SCROLL_SPEED: 0.5,
51
 
52
        /**
53
         * Set if currently scrolling up/down.
54
         * @private
55
         */
56
        scrollingId: null,
57
 
58
        /**
59
         * Speed we are supposed to scroll (range 1 to SCROLL_THRESHOLD).
60
         * @private
61
         */
62
        scrollAmount: 0,
63
 
64
        /**
65
         * Optional callback called when it scrolls
66
         * @private
67
         */
68
        callback: null,
69
 
70
        /**
71
         * Starts automatically scrolling if user moves near edge of window.
72
         * This should be called in response to mouse down or touch start.
73
         *
74
         * @public
75
         * @param {Function} callback Optional callback that is called every time it scrolls
76
         */
77
        start: function(callback) {
78
            $(window).on('mousemove', autoscroll.mouseMove);
79
            $(window).on('touchmove', autoscroll.touchMove);
80
            autoscroll.callback = callback;
81
        },
82
 
83
        /**
84
         * Stops automatically scrolling. This should be called in response to mouse up or touch end.
85
         *
86
         * @public
87
         */
88
        stop: function() {
89
            $(window).off('mousemove', autoscroll.mouseMove);
90
            $(window).off('touchmove', autoscroll.touchMove);
91
            if (autoscroll.scrollingId !== null) {
92
                autoscroll.stopScrolling();
93
            }
94
        },
95
 
96
        /**
97
         * Event handler for touch move.
98
         *
99
         * @private
100
         * @param {Object} e Event
101
         */
102
        touchMove: function(e) {
103
            for (var i = 0; i < e.changedTouches.length; i++) {
104
                autoscroll.handleMove(e.changedTouches[i].clientX, e.changedTouches[i].clientY);
105
            }
106
        },
107
 
108
        /**
109
         * Event handler for mouse move.
110
         *
111
         * @private
112
         * @param {Object} e Event
113
         */
114
        mouseMove: function(e) {
115
            autoscroll.handleMove(e.clientX, e.clientY);
116
        },
117
 
118
        /**
119
         * Handles user moving.
120
         *
121
         * @private
122
         * @param {number} clientX X
123
         * @param {number} clientY Y
124
         */
125
        handleMove: function(clientX, clientY) {
126
            // If near the bottom or top, start auto-scrolling.
127
            if (clientY < autoscroll.SCROLL_THRESHOLD) {
128
                autoscroll.scrollAmount = -Math.min(autoscroll.SCROLL_THRESHOLD - clientY, autoscroll.SCROLL_THRESHOLD);
129
            } else if (clientY > $(window).height() - autoscroll.SCROLL_THRESHOLD) {
130
                autoscroll.scrollAmount = Math.min(clientY - ($(window).height() - autoscroll.SCROLL_THRESHOLD),
131
                    autoscroll.SCROLL_THRESHOLD);
132
            } else {
133
                autoscroll.scrollAmount = 0;
134
            }
135
            if (autoscroll.scrollAmount && autoscroll.scrollingId === null) {
136
                autoscroll.startScrolling();
137
            } else if (!autoscroll.scrollAmount && autoscroll.scrollingId !== null) {
138
                autoscroll.stopScrolling();
139
            }
140
        },
141
 
142
        /**
143
         * Starts automatic scrolling.
144
         *
145
         * @private
146
         */
147
        startScrolling: function() {
148
            var maxScroll = $(document).height() - $(window).height();
149
            autoscroll.scrollingId = window.setInterval(function() {
150
                // Work out how much to scroll.
151
                var y = $(window).scrollTop();
152
                var offset = Math.round(autoscroll.scrollAmount * autoscroll.SCROLL_SPEED);
153
                if (y + offset < 0) {
154
                    offset = -y;
155
                }
156
                if (y + offset > maxScroll) {
157
                    offset = maxScroll - y;
158
                }
159
                if (offset === 0) {
160
                    return;
161
                }
162
 
163
                // Scroll.
164
                $(window).scrollTop(y + offset);
165
                var realOffset = $(window).scrollTop() - y;
166
                if (realOffset === 0) {
167
                    return;
168
                }
169
 
170
                // Inform callback
171
                if (autoscroll.callback) {
172
                    autoscroll.callback(realOffset);
173
                }
174
 
175
            }, autoscroll.SCROLL_FREQUENCY);
176
        },
177
 
178
        /**
179
         * Stops the automatic scrolling.
180
         *
181
         * @private
182
         */
183
        stopScrolling: function() {
184
            window.clearInterval(autoscroll.scrollingId);
185
            autoscroll.scrollingId = null;
186
        }
187
    };
188
 
189
    return {
190
        /**
191
         * Starts automatic scrolling if user moves near edge of window.
192
         * This should be called in response to mouse down or touch start.
193
         *
194
         * @public
195
         * @param {Function} callback Optional callback that is called every time it scrolls
196
         */
197
        start: autoscroll.start,
198
 
199
        /**
200
         * Stops automatic scrolling. This should be called in response to mouse up or touch end.
201
         *
202
         * @public
203
         */
204
        stop: autoscroll.stop
205
    };
206
 
207
});