-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathprogress-buttons.js
205 lines (142 loc) · 5.2 KB
/
progress-buttons.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
// http://tutorialzine.com/2013/10/buttons-built-in-progress-meters/
// The progress meter functionality is available as a series of plugins.
// You can put this code in a separate file if you wish to keep things tidy.
(function($) {
// Creating a number of jQuery plugins that you can use to
// initialize and control the progress meters.
$.fn.progressInitialize = function() {
// This function creates the necessary markup for the progress meter
// and sets up a few event listeners.
// Loop through all the buttons:
return this.each(function() {
var button = $(this),
progress = 0;
// Extract the data attributes into the options object.
// If they are missing, they will receive default values.
var options = $.extend({
type: 'background-horizontal',
loading: 'Loading..',
finished: 'Done!'
}, button.data());
// Add the data attributes if they are missing from the element.
// They are used by our CSS code to show the messages
button.attr({
'data-loading': options.loading,
'data-finished': options.finished
});
// Add the needed markup for the progress bar to the button
var bar = $('<span class="tz-bar ' + options.type + '">').appendTo(button);
// The progress event tells the button to update the progress bar
button.on('progress', function(e, val, absolute, finish, error) {
if (!button.hasClass('in-progress')) {
// This is the first progress event for the button (or the
// first after it has finished in a previous run). Re-initialize
// the progress and remove some classes that may be left.
bar.show();
progress = 0;
button.removeClass('finished').addClass('in-progress');
}
// val, absolute and finish are event data passed by the progressIncrement
// and progressSet methods that you can see near the end of this file.
if (absolute) {
progress = val;
} else {
progress += val;
}
if (progress >= 100) {
progress = 100;
}
if (finish) {
button.removeClass('in-progress').addClass('finished');
bar.delay(500).fadeOut(function() {
// Trigger the custom progress-finish event
button.trigger('progress-finish');
setProgress(0);
});
}
if (error) {
button.removeClass('in-progress').addClass('error');
bar.delay(500).fadeOut(function() {
button.trigger('progress-error');
setProgress(0);
});
}
setProgress(progress);
});
function setProgress(percentage) {
bar.filter('.background-horizontal,.background-bar').width(percentage + '%');
bar.filter('.background-vertical').height(percentage + '%');
}
});
};
// progressStart simulates activity on the progress meter. Call it first,
// if the progress is going to take a long time to finish.
$.fn.progressStart = function() {
var button = this.first(),
last_progress = new Date().getTime();
if (button.hasClass('in-progress')) {
// Don't start it a second time!
return this;
}
button.on('progress', function() {
last_progress = new Date().getTime();
});
// Every half a second check whether the progress
// has been incremented in the last two seconds
var interval = window.setInterval(function() {
if (new Date().getTime() > 2000 + last_progress) {
// There has been no activity for two seconds. Increment the progress
// bar a little bit to show that something is happening
button.progressIncrement(5);
}
}, 500);
button.on('progress-finish', function() {
window.clearInterval(interval);
});
button.on('progress-error', function() {
window.clearInterval(interval);
});
return button.progressIncrement(10);
};
$.fn.progressFinish = function() {
return this.first().progressSet(100);
};
$.fn.progressError = function() {
return this.first().progressSet(100, true);
};
$.fn.progressIncrement = function(val) {
val = val || 10;
var button = this.first();
button.trigger('progress', [val]);
return this;
};
$.fn.progressSet = function(val, error) {
val = val || 10;
error = error || false;
var finish = false;
if (val >= 100 && !error) {
finish = true;
}
return this.first().trigger('progress', [val, true, finish, error]);
};
// This function creates a progress meter that
// finishes in a specified amount of time.
$.fn.progressTimed = function(seconds, cb) {
var button = this.first(),
bar = button.find('.tz-bar');
if (button.is('.in-progress')) {
return this;
}
// Set a transition declaration for the duration of the meter.
// CSS will do the job of animating the progress bar for us.
bar.css('transition', seconds + 's linear');
button.progressSet(99);
window.setTimeout(function() {
bar.css('transition', '');
button.progressFinish();
if ($.isFunction(cb)) {
cb();
}
}, seconds * 1000);
};
})(jQuery);