rails-active-ui 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/Rakefile +6 -0
- data/app/assets/stylesheets.css +73555 -0
- data/app/components/accordion_component.rb +34 -0
- data/app/components/ad_component.rb +28 -0
- data/app/components/api_component.rb +24 -0
- data/app/components/breadcrumb_component.rb +26 -0
- data/app/components/button_component.rb +49 -0
- data/app/components/calendar_component.rb +34 -0
- data/app/components/card_component.rb +56 -0
- data/app/components/checkbox_component.rb +41 -0
- data/app/components/column_component.rb +62 -0
- data/app/components/comment_component.rb +45 -0
- data/app/components/concerns/alignable.rb +21 -0
- data/app/components/concerns/attachable.rb +16 -0
- data/app/components/concerns/orientable.rb +21 -0
- data/app/components/concerns/positionable.rb +21 -0
- data/app/components/concerns/sizeable.rb +18 -0
- data/app/components/container_component.rb +23 -0
- data/app/components/dimmer_component.rb +30 -0
- data/app/components/divider_component.rb +30 -0
- data/app/components/dropdown_component.rb +63 -0
- data/app/components/embed_component.rb +32 -0
- data/app/components/emoji_component.rb +15 -0
- data/app/components/feed_component.rb +22 -0
- data/app/components/flag_component.rb +15 -0
- data/app/components/flyout_component.rb +41 -0
- data/app/components/form_component.rb +39 -0
- data/app/components/grid_component.rb +85 -0
- data/app/components/h_stack_component.rb +67 -0
- data/app/components/header_component.rb +60 -0
- data/app/components/icon_component.rb +41 -0
- data/app/components/image_component.rb +46 -0
- data/app/components/input_component.rb +52 -0
- data/app/components/item_component.rb +39 -0
- data/app/components/item_group_component.rb +30 -0
- data/app/components/label_component.rb +49 -0
- data/app/components/link_component.rb +23 -0
- data/app/components/list_component.rb +39 -0
- data/app/components/loader_component.rb +33 -0
- data/app/components/menu_component.rb +64 -0
- data/app/components/menu_item_component.rb +52 -0
- data/app/components/message_component.rb +54 -0
- data/app/components/modal_component.rb +50 -0
- data/app/components/nag_component.rb +25 -0
- data/app/components/overlay_component.rb +16 -0
- data/app/components/placeholder_component.rb +39 -0
- data/app/components/popup_component.rb +31 -0
- data/app/components/progress_component.rb +48 -0
- data/app/components/pusher_component.rb +18 -0
- data/app/components/rail_component.rb +31 -0
- data/app/components/rating_component.rb +41 -0
- data/app/components/reset_component.rb +12 -0
- data/app/components/reveal_component.rb +39 -0
- data/app/components/row_component.rb +39 -0
- data/app/components/search_component.rb +44 -0
- data/app/components/segment_component.rb +57 -0
- data/app/components/segment_group_component.rb +36 -0
- data/app/components/shape_component.rb +25 -0
- data/app/components/sidebar_component.rb +33 -0
- data/app/components/site_component.rb +12 -0
- data/app/components/slider_component.rb +46 -0
- data/app/components/state_component.rb +25 -0
- data/app/components/statistic_component.rb +43 -0
- data/app/components/step_component.rb +56 -0
- data/app/components/step_group_component.rb +38 -0
- data/app/components/sticky_component.rb +22 -0
- data/app/components/sub_header_component.rb +15 -0
- data/app/components/sub_menu_component.rb +24 -0
- data/app/components/tab_component.rb +24 -0
- data/app/components/table_cell_component.rb +60 -0
- data/app/components/table_component.rb +160 -0
- data/app/components/table_row_component.rb +43 -0
- data/app/components/text_component.rb +73 -0
- data/app/components/toast_component.rb +36 -0
- data/app/components/transition_component.rb +32 -0
- data/app/components/v_stack_component.rb +31 -0
- data/app/components/visibility_component.rb +22 -0
- data/app/helpers/component_helper.rb +109 -0
- data/app/helpers/fui_helper.rb +53 -0
- data/app/javascript/accordion.js +547 -0
- data/app/javascript/accordion.min.js +11 -0
- data/app/javascript/api.js +1112 -0
- data/app/javascript/api.min.js +11 -0
- data/app/javascript/calendar.js +1960 -0
- data/app/javascript/calendar.min.js +11 -0
- data/app/javascript/checkbox.js +819 -0
- data/app/javascript/checkbox.min.js +11 -0
- data/app/javascript/dimmer.js +686 -0
- data/app/javascript/dimmer.min.js +11 -0
- data/app/javascript/dropdown.js +4019 -0
- data/app/javascript/dropdown.min.js +11 -0
- data/app/javascript/embed.js +646 -0
- data/app/javascript/embed.min.js +11 -0
- data/app/javascript/flyout.js +1405 -0
- data/app/javascript/flyout.min.js +11 -0
- data/app/javascript/form.js +2070 -0
- data/app/javascript/form.min.js +11 -0
- data/app/javascript/jquery.js +10716 -0
- data/app/javascript/jquery.min.js +2 -0
- data/app/javascript/modal.js +1507 -0
- data/app/javascript/modal.min.js +11 -0
- data/app/javascript/nag.js +522 -0
- data/app/javascript/nag.min.js +11 -0
- data/app/javascript/popup.js +1457 -0
- data/app/javascript/popup.min.js +11 -0
- data/app/javascript/progress.js +922 -0
- data/app/javascript/progress.min.js +11 -0
- data/app/javascript/rating.js +496 -0
- data/app/javascript/rating.min.js +11 -0
- data/app/javascript/search.js +1519 -0
- data/app/javascript/search.min.js +11 -0
- data/app/javascript/shape.js +721 -0
- data/app/javascript/shape.min.js +11 -0
- data/app/javascript/sidebar.js +952 -0
- data/app/javascript/sidebar.min.js +11 -0
- data/app/javascript/site.js +415 -0
- data/app/javascript/site.min.js +11 -0
- data/app/javascript/slider.js +1449 -0
- data/app/javascript/slider.min.js +11 -0
- data/app/javascript/state.js +653 -0
- data/app/javascript/state.min.js +11 -0
- data/app/javascript/sticky.js +852 -0
- data/app/javascript/sticky.min.js +11 -0
- data/app/javascript/tab.js +867 -0
- data/app/javascript/tab.min.js +11 -0
- data/app/javascript/toast.js +916 -0
- data/app/javascript/toast.min.js +11 -0
- data/app/javascript/transition.js +955 -0
- data/app/javascript/transition.min.js +11 -0
- data/app/javascript/ui/controllers/fui_accordion_controller.js +45 -0
- data/app/javascript/ui/controllers/fui_api_controller.js +80 -0
- data/app/javascript/ui/controllers/fui_calendar_controller.js +66 -0
- data/app/javascript/ui/controllers/fui_checkbox_controller.js +48 -0
- data/app/javascript/ui/controllers/fui_dimmer_controller.js +45 -0
- data/app/javascript/ui/controllers/fui_dropdown_controller.js +68 -0
- data/app/javascript/ui/controllers/fui_embed_controller.js +49 -0
- data/app/javascript/ui/controllers/fui_flyout_controller.js +49 -0
- data/app/javascript/ui/controllers/fui_form_controller.js +62 -0
- data/app/javascript/ui/controllers/fui_modal_controller.js +61 -0
- data/app/javascript/ui/controllers/fui_nag_controller.js +52 -0
- data/app/javascript/ui/controllers/fui_popup_controller.js +58 -0
- data/app/javascript/ui/controllers/fui_progress_controller.js +60 -0
- data/app/javascript/ui/controllers/fui_rating_controller.js +49 -0
- data/app/javascript/ui/controllers/fui_search_controller.js +76 -0
- data/app/javascript/ui/controllers/fui_shape_controller.js +45 -0
- data/app/javascript/ui/controllers/fui_sidebar_controller.js +48 -0
- data/app/javascript/ui/controllers/fui_site_controller.js +29 -0
- data/app/javascript/ui/controllers/fui_slider_controller.js +53 -0
- data/app/javascript/ui/controllers/fui_state_controller.js +63 -0
- data/app/javascript/ui/controllers/fui_sticky_controller.js +50 -0
- data/app/javascript/ui/controllers/fui_tab_controller.js +57 -0
- data/app/javascript/ui/controllers/fui_toast_controller.js +60 -0
- data/app/javascript/ui/controllers/fui_transition_controller.js +60 -0
- data/app/javascript/ui/controllers/fui_visibility_controller.js +55 -0
- data/app/javascript/ui/index.js +114 -0
- data/app/javascript/visibility.js +1196 -0
- data/app/javascript/visibility.min.js +11 -0
- data/app/lib/component.rb +63 -0
- data/config/importmap.rb +27 -0
- data/config/initializers/ruby_template_handler.rb +31 -0
- data/config/routes.rb +2 -0
- data/lib/tasks/ui_tasks.rake +4 -0
- data/lib/ui/engine.rb +27 -0
- data/lib/ui/version.rb +3 -0
- data/lib/ui.rb +6 -0
- metadata +220 -0
|
@@ -0,0 +1,852 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* # Fomantic-UI 2.9.4 - Sticky
|
|
3
|
+
* https://github.com/fomantic/Fomantic-UI/
|
|
4
|
+
*
|
|
5
|
+
*
|
|
6
|
+
* Released under the MIT license
|
|
7
|
+
* https://opensource.org/licenses/MIT
|
|
8
|
+
*
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
(function ($, window, document) {
|
|
12
|
+
'use strict';
|
|
13
|
+
|
|
14
|
+
function isFunction(obj) {
|
|
15
|
+
return typeof obj === 'function' && typeof obj.nodeType !== 'number';
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
window = window !== undefined && window.Math === Math
|
|
19
|
+
? window
|
|
20
|
+
: globalThis;
|
|
21
|
+
|
|
22
|
+
$.fn.sticky = function (...args) {
|
|
23
|
+
const $allModules = $(this);
|
|
24
|
+
const $document = $(document);
|
|
25
|
+
|
|
26
|
+
let time = Date.now();
|
|
27
|
+
let performance = [];
|
|
28
|
+
|
|
29
|
+
const parameters = args[0];
|
|
30
|
+
const methodInvoked = typeof parameters === 'string';
|
|
31
|
+
const queryArguments = args.slice(1);
|
|
32
|
+
const contextCheck = function (context, win) {
|
|
33
|
+
let $context;
|
|
34
|
+
if ([window, document].includes(context)) {
|
|
35
|
+
$context = $(context);
|
|
36
|
+
} else {
|
|
37
|
+
$context = $(win.document).find(context);
|
|
38
|
+
if ($context.length === 0) {
|
|
39
|
+
$context = win.frameElement ? contextCheck(context, win.parent) : window;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
return $context;
|
|
44
|
+
};
|
|
45
|
+
let returnedValue;
|
|
46
|
+
|
|
47
|
+
$allModules.each(function () {
|
|
48
|
+
const settings = $.isPlainObject(parameters)
|
|
49
|
+
? $.extend(true, {}, $.fn.sticky.settings, parameters)
|
|
50
|
+
: $.extend({}, $.fn.sticky.settings);
|
|
51
|
+
|
|
52
|
+
const className = settings.className;
|
|
53
|
+
const namespace = settings.namespace;
|
|
54
|
+
const error = settings.error;
|
|
55
|
+
|
|
56
|
+
const eventNamespace = '.' + namespace;
|
|
57
|
+
const moduleNamespace = 'module-' + namespace;
|
|
58
|
+
|
|
59
|
+
const $module = $(this);
|
|
60
|
+
const $window = $(window);
|
|
61
|
+
const $scroll = contextCheck(settings.scrollContext, window);
|
|
62
|
+
let $container;
|
|
63
|
+
let $context;
|
|
64
|
+
|
|
65
|
+
let instance = $module.data(moduleNamespace);
|
|
66
|
+
|
|
67
|
+
const element = this;
|
|
68
|
+
|
|
69
|
+
let documentObserver;
|
|
70
|
+
let observer;
|
|
71
|
+
|
|
72
|
+
const module = {
|
|
73
|
+
|
|
74
|
+
initialize: function () {
|
|
75
|
+
module.determineContainer();
|
|
76
|
+
module.determineContext();
|
|
77
|
+
module.verbose('Initializing sticky', settings, $container);
|
|
78
|
+
|
|
79
|
+
module.save.positions();
|
|
80
|
+
module.checkErrors();
|
|
81
|
+
module.bind.events();
|
|
82
|
+
|
|
83
|
+
if (settings.observeChanges) {
|
|
84
|
+
module.observeChanges();
|
|
85
|
+
}
|
|
86
|
+
module.instantiate();
|
|
87
|
+
},
|
|
88
|
+
|
|
89
|
+
instantiate: function () {
|
|
90
|
+
module.verbose('Storing instance of module', module);
|
|
91
|
+
instance = module;
|
|
92
|
+
$module
|
|
93
|
+
.data(moduleNamespace, module);
|
|
94
|
+
},
|
|
95
|
+
|
|
96
|
+
destroy: function () {
|
|
97
|
+
module.verbose('Destroying previous instance');
|
|
98
|
+
module.reset();
|
|
99
|
+
if (documentObserver) {
|
|
100
|
+
documentObserver.disconnect();
|
|
101
|
+
}
|
|
102
|
+
if (observer) {
|
|
103
|
+
observer.disconnect();
|
|
104
|
+
}
|
|
105
|
+
$window
|
|
106
|
+
.off('load' + eventNamespace, module.event.load)
|
|
107
|
+
.off('resize' + eventNamespace, module.event.resize);
|
|
108
|
+
$scroll
|
|
109
|
+
.off('scrollchange' + eventNamespace, module.event.scrollchange);
|
|
110
|
+
$module.removeData(moduleNamespace);
|
|
111
|
+
},
|
|
112
|
+
|
|
113
|
+
observeChanges: function () {
|
|
114
|
+
documentObserver = new MutationObserver(module.event.documentChanged);
|
|
115
|
+
observer = new MutationObserver(module.event.changed);
|
|
116
|
+
documentObserver.observe(document, {
|
|
117
|
+
childList: true,
|
|
118
|
+
subtree: true,
|
|
119
|
+
});
|
|
120
|
+
observer.observe(element, {
|
|
121
|
+
childList: true,
|
|
122
|
+
subtree: true,
|
|
123
|
+
});
|
|
124
|
+
observer.observe($context[0], {
|
|
125
|
+
childList: true,
|
|
126
|
+
subtree: true,
|
|
127
|
+
});
|
|
128
|
+
module.debug('Setting up mutation observer', observer);
|
|
129
|
+
},
|
|
130
|
+
|
|
131
|
+
determineContainer: function () {
|
|
132
|
+
$container = settings.container ? contextCheck(settings.container, window) : $module.offsetParent();
|
|
133
|
+
},
|
|
134
|
+
|
|
135
|
+
determineContext: function () {
|
|
136
|
+
$context = settings.context ? contextCheck(settings.context, window) : $container;
|
|
137
|
+
if ($context.length === 0) {
|
|
138
|
+
module.error(error.invalidContext, settings.context, $module);
|
|
139
|
+
}
|
|
140
|
+
},
|
|
141
|
+
|
|
142
|
+
checkErrors: function () {
|
|
143
|
+
if (module.is.hidden()) {
|
|
144
|
+
module.error(error.visible, $module);
|
|
145
|
+
}
|
|
146
|
+
if (module.cache.element.height > module.cache.context.height) {
|
|
147
|
+
module.reset();
|
|
148
|
+
module.error(error.elementSize, $module);
|
|
149
|
+
}
|
|
150
|
+
},
|
|
151
|
+
|
|
152
|
+
bind: {
|
|
153
|
+
events: function () {
|
|
154
|
+
$window
|
|
155
|
+
.on('load' + eventNamespace, module.event.load)
|
|
156
|
+
.on('resize' + eventNamespace, module.event.resize);
|
|
157
|
+
// pub/sub pattern
|
|
158
|
+
$scroll
|
|
159
|
+
.off('scroll' + eventNamespace)
|
|
160
|
+
.on('scroll' + eventNamespace, module.event.scroll)
|
|
161
|
+
.on('scrollchange' + eventNamespace, module.event.scrollchange);
|
|
162
|
+
},
|
|
163
|
+
},
|
|
164
|
+
|
|
165
|
+
event: {
|
|
166
|
+
changed: function (mutations) {
|
|
167
|
+
clearTimeout(module.timer);
|
|
168
|
+
module.timer = setTimeout(function () {
|
|
169
|
+
module.verbose('DOM tree modified, updating sticky menu', mutations);
|
|
170
|
+
module.refresh();
|
|
171
|
+
}, 100);
|
|
172
|
+
},
|
|
173
|
+
documentChanged: function (mutations) {
|
|
174
|
+
for (const mutation of mutations) {
|
|
175
|
+
for (const node of mutation.removedNodes) {
|
|
176
|
+
if (node === element || $(node).find(element).length > 0) {
|
|
177
|
+
module.debug('Element removed from DOM, tearing down events');
|
|
178
|
+
module.destroy();
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
}
|
|
182
|
+
},
|
|
183
|
+
load: function () {
|
|
184
|
+
module.verbose('Page contents finished loading');
|
|
185
|
+
requestAnimationFrame(module.refresh);
|
|
186
|
+
},
|
|
187
|
+
resize: function () {
|
|
188
|
+
module.verbose('Window resized');
|
|
189
|
+
requestAnimationFrame(module.refresh);
|
|
190
|
+
},
|
|
191
|
+
scroll: function () {
|
|
192
|
+
requestAnimationFrame(function () {
|
|
193
|
+
$scroll.triggerHandler('scrollchange' + eventNamespace, $scroll.scrollTop());
|
|
194
|
+
});
|
|
195
|
+
},
|
|
196
|
+
scrollchange: function (event, scrollPosition) {
|
|
197
|
+
module.stick(scrollPosition);
|
|
198
|
+
settings.onScroll.call(element);
|
|
199
|
+
},
|
|
200
|
+
},
|
|
201
|
+
|
|
202
|
+
refresh: function (hardRefresh) {
|
|
203
|
+
module.reset();
|
|
204
|
+
if (!settings.context) {
|
|
205
|
+
module.determineContext();
|
|
206
|
+
}
|
|
207
|
+
if (hardRefresh) {
|
|
208
|
+
module.determineContainer();
|
|
209
|
+
}
|
|
210
|
+
module.save.positions();
|
|
211
|
+
module.stick();
|
|
212
|
+
settings.onReposition.call(element);
|
|
213
|
+
},
|
|
214
|
+
|
|
215
|
+
supports: {
|
|
216
|
+
sticky: function () {
|
|
217
|
+
const $element = $('<div/>');
|
|
218
|
+
$element.addClass(className.supported);
|
|
219
|
+
|
|
220
|
+
return $element.css('position').match('sticky');
|
|
221
|
+
},
|
|
222
|
+
},
|
|
223
|
+
|
|
224
|
+
save: {
|
|
225
|
+
lastScroll: function (scroll) {
|
|
226
|
+
module.lastScroll = scroll;
|
|
227
|
+
},
|
|
228
|
+
elementScroll: function (scroll) {
|
|
229
|
+
module.elementScroll = scroll;
|
|
230
|
+
},
|
|
231
|
+
positions: function () {
|
|
232
|
+
const scrollContext = {
|
|
233
|
+
height: $scroll.height(),
|
|
234
|
+
};
|
|
235
|
+
const element = {
|
|
236
|
+
margin: {
|
|
237
|
+
top: Number.parseInt($module.css('margin-top'), 10),
|
|
238
|
+
bottom: Number.parseInt($module.css('margin-bottom'), 10),
|
|
239
|
+
},
|
|
240
|
+
offset: $module.offset(),
|
|
241
|
+
width: $module.outerWidth(),
|
|
242
|
+
height: $module.outerHeight(),
|
|
243
|
+
};
|
|
244
|
+
const context = {
|
|
245
|
+
offset: $context.offset(),
|
|
246
|
+
height: $context.outerHeight(),
|
|
247
|
+
};
|
|
248
|
+
if (!module.is.standardScroll()) {
|
|
249
|
+
module.debug('Non-standard scroll. Removing scroll offset from element offset');
|
|
250
|
+
|
|
251
|
+
scrollContext.top = $scroll.scrollTop();
|
|
252
|
+
scrollContext.left = $scroll.scrollLeft();
|
|
253
|
+
|
|
254
|
+
element.offset.top += scrollContext.top;
|
|
255
|
+
context.offset.top += scrollContext.top;
|
|
256
|
+
element.offset.left += scrollContext.left;
|
|
257
|
+
context.offset.left += scrollContext.left;
|
|
258
|
+
}
|
|
259
|
+
module.cache = {
|
|
260
|
+
fits: (element.height + settings.offset) <= scrollContext.height,
|
|
261
|
+
sameHeight: element.height === context.height,
|
|
262
|
+
scrollContext: {
|
|
263
|
+
height: scrollContext.height,
|
|
264
|
+
},
|
|
265
|
+
element: {
|
|
266
|
+
margin: element.margin,
|
|
267
|
+
top: element.offset.top - element.margin.top,
|
|
268
|
+
left: element.offset.left,
|
|
269
|
+
width: element.width,
|
|
270
|
+
height: element.height,
|
|
271
|
+
bottom: element.offset.top + element.height,
|
|
272
|
+
},
|
|
273
|
+
context: {
|
|
274
|
+
top: context.offset.top,
|
|
275
|
+
height: context.height,
|
|
276
|
+
bottom: context.offset.top + context.height,
|
|
277
|
+
},
|
|
278
|
+
};
|
|
279
|
+
module.set.containerSize();
|
|
280
|
+
|
|
281
|
+
module.stick();
|
|
282
|
+
module.debug('Caching element positions', module.cache);
|
|
283
|
+
},
|
|
284
|
+
},
|
|
285
|
+
|
|
286
|
+
get: {
|
|
287
|
+
direction: function (scroll = $scroll.scrollTop()) {
|
|
288
|
+
let direction = 'down';
|
|
289
|
+
if (module.lastScroll && module.lastScroll > scroll) {
|
|
290
|
+
direction = 'up';
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
return direction;
|
|
294
|
+
},
|
|
295
|
+
scrollChange: function (scroll = $scroll.scrollTop()) {
|
|
296
|
+
return module.lastScroll
|
|
297
|
+
? scroll - module.lastScroll
|
|
298
|
+
: 0;
|
|
299
|
+
},
|
|
300
|
+
currentElementScroll: function () {
|
|
301
|
+
if (module.elementScroll) {
|
|
302
|
+
return module.elementScroll;
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
return module.is.top()
|
|
306
|
+
? Math.abs(Number.parseInt($module.css('top'), 10)) || 0
|
|
307
|
+
: Math.abs(Number.parseInt($module.css('bottom'), 10)) || 0;
|
|
308
|
+
},
|
|
309
|
+
|
|
310
|
+
elementScroll: function (scroll = $scroll.scrollTop()) {
|
|
311
|
+
const element = module.cache.element;
|
|
312
|
+
const scrollContext = module.cache.scrollContext;
|
|
313
|
+
const delta = module.get.scrollChange(scroll);
|
|
314
|
+
const maxScroll = element.height - scrollContext.height + settings.offset;
|
|
315
|
+
let elementScroll = module.get.currentElementScroll();
|
|
316
|
+
const possibleScroll = elementScroll + delta;
|
|
317
|
+
if (module.cache.fits || possibleScroll < 0) {
|
|
318
|
+
elementScroll = 0;
|
|
319
|
+
} else if (possibleScroll > maxScroll) {
|
|
320
|
+
elementScroll = maxScroll;
|
|
321
|
+
} else {
|
|
322
|
+
elementScroll = possibleScroll;
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
return elementScroll;
|
|
326
|
+
},
|
|
327
|
+
},
|
|
328
|
+
|
|
329
|
+
remove: {
|
|
330
|
+
lastScroll: function () {
|
|
331
|
+
delete module.lastScroll;
|
|
332
|
+
},
|
|
333
|
+
elementScroll: function () {
|
|
334
|
+
delete module.elementScroll;
|
|
335
|
+
},
|
|
336
|
+
minimumSize: function () {
|
|
337
|
+
$container
|
|
338
|
+
.css('min-height', '');
|
|
339
|
+
},
|
|
340
|
+
offset: function () {
|
|
341
|
+
$module.css('margin-top', '');
|
|
342
|
+
},
|
|
343
|
+
},
|
|
344
|
+
|
|
345
|
+
set: {
|
|
346
|
+
offset: function () {
|
|
347
|
+
module.verbose('Setting offset on element', settings.offset);
|
|
348
|
+
$module
|
|
349
|
+
.css('margin-top', settings.offset);
|
|
350
|
+
},
|
|
351
|
+
containerSize: function () {
|
|
352
|
+
const tagName = $container[0].tagName;
|
|
353
|
+
if (tagName === 'HTML' || tagName === 'body') {
|
|
354
|
+
module.determineContainer();
|
|
355
|
+
} else {
|
|
356
|
+
const tallestHeight = Math.max(module.cache.context.height, module.cache.element.height);
|
|
357
|
+
if (tallestHeight - $container.outerHeight() > settings.jitter) {
|
|
358
|
+
module.debug('Context is taller than container. Specifying exact height for container', module.cache.context.height);
|
|
359
|
+
$container.css({
|
|
360
|
+
height: tallestHeight,
|
|
361
|
+
});
|
|
362
|
+
} else {
|
|
363
|
+
$container.css({
|
|
364
|
+
height: '',
|
|
365
|
+
});
|
|
366
|
+
}
|
|
367
|
+
if (Math.abs($container.outerHeight() - module.cache.context.height) > settings.jitter) {
|
|
368
|
+
module.debug('Context has padding, specifying exact height for container', module.cache.context.height);
|
|
369
|
+
$container.css({
|
|
370
|
+
height: module.cache.context.height,
|
|
371
|
+
});
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
},
|
|
375
|
+
minimumSize: function () {
|
|
376
|
+
const element = module.cache.element;
|
|
377
|
+
$container
|
|
378
|
+
.css('min-height', element.height);
|
|
379
|
+
},
|
|
380
|
+
scroll: function (scroll) {
|
|
381
|
+
module.debug('Setting scroll on element', scroll);
|
|
382
|
+
if (module.elementScroll === scroll) {
|
|
383
|
+
return;
|
|
384
|
+
}
|
|
385
|
+
if (module.is.top()) {
|
|
386
|
+
$module
|
|
387
|
+
.css('bottom', '')
|
|
388
|
+
.css('top', -scroll + 'px');
|
|
389
|
+
}
|
|
390
|
+
if (module.is.bottom()) {
|
|
391
|
+
$module
|
|
392
|
+
.css('top', '')
|
|
393
|
+
.css('bottom', scroll + 'px');
|
|
394
|
+
}
|
|
395
|
+
},
|
|
396
|
+
size: function () {
|
|
397
|
+
if (module.cache.element.height !== 0 && module.cache.element.width !== 0) {
|
|
398
|
+
element.style.setProperty('width', module.cache.element.width + 'px', 'important');
|
|
399
|
+
element.style.setProperty('height', module.cache.element.height + 'px', 'important');
|
|
400
|
+
}
|
|
401
|
+
},
|
|
402
|
+
},
|
|
403
|
+
|
|
404
|
+
is: {
|
|
405
|
+
standardScroll: function () {
|
|
406
|
+
return $scroll[0] === window;
|
|
407
|
+
},
|
|
408
|
+
top: function () {
|
|
409
|
+
return $module.hasClass(className.top);
|
|
410
|
+
},
|
|
411
|
+
bottom: function () {
|
|
412
|
+
return $module.hasClass(className.bottom);
|
|
413
|
+
},
|
|
414
|
+
initialPosition: function () {
|
|
415
|
+
return !module.is.fixed() && !module.is.bound();
|
|
416
|
+
},
|
|
417
|
+
hidden: function () {
|
|
418
|
+
return !$module.is(':visible');
|
|
419
|
+
},
|
|
420
|
+
bound: function () {
|
|
421
|
+
return $module.hasClass(className.bound);
|
|
422
|
+
},
|
|
423
|
+
fixed: function () {
|
|
424
|
+
return $module.hasClass(className.fixed);
|
|
425
|
+
},
|
|
426
|
+
},
|
|
427
|
+
|
|
428
|
+
stick: function (scrollPosition = $scroll.scrollTop()) {
|
|
429
|
+
const cache = module.cache;
|
|
430
|
+
const fits = cache.fits;
|
|
431
|
+
const sameHeight = cache.sameHeight;
|
|
432
|
+
const element = cache.element;
|
|
433
|
+
const scrollContext = cache.scrollContext;
|
|
434
|
+
const context = cache.context;
|
|
435
|
+
const offset = module.is.bottom() && settings.pushing
|
|
436
|
+
? settings.bottomOffset
|
|
437
|
+
: settings.offset;
|
|
438
|
+
const scroll = {
|
|
439
|
+
top: scrollPosition + offset,
|
|
440
|
+
bottom: scrollPosition + offset + scrollContext.height,
|
|
441
|
+
};
|
|
442
|
+
const elementScroll = fits
|
|
443
|
+
? 0
|
|
444
|
+
: module.get.elementScroll(scroll.top);
|
|
445
|
+
|
|
446
|
+
// shorthand
|
|
447
|
+
const doesntFit = !fits;
|
|
448
|
+
const elementVisible = element.height !== 0;
|
|
449
|
+
if (elementVisible && !sameHeight) {
|
|
450
|
+
if (module.is.initialPosition()) {
|
|
451
|
+
if (scroll.top >= context.bottom) {
|
|
452
|
+
module.debug('Initial element position is bottom of container');
|
|
453
|
+
module.bindBottom();
|
|
454
|
+
} else if (scroll.top > element.top) {
|
|
455
|
+
if ((element.height + scroll.top - elementScroll) >= context.bottom && element.height < context.height) {
|
|
456
|
+
module.debug('Initial element position is bottom of container');
|
|
457
|
+
module.bindBottom();
|
|
458
|
+
} else {
|
|
459
|
+
module.debug('Initial element position is fixed');
|
|
460
|
+
module.fixTop();
|
|
461
|
+
}
|
|
462
|
+
}
|
|
463
|
+
} else if (module.is.fixed()) {
|
|
464
|
+
if (module.is.top()) {
|
|
465
|
+
if (scroll.top <= element.top) {
|
|
466
|
+
module.debug('Fixed element reached top of container');
|
|
467
|
+
module.setInitialPosition();
|
|
468
|
+
} else if ((element.height + scroll.top - elementScroll) >= context.bottom) {
|
|
469
|
+
module.debug('Fixed element reached bottom of container');
|
|
470
|
+
module.bindBottom();
|
|
471
|
+
} else if (doesntFit) { // scroll element if larger than screen
|
|
472
|
+
module.set.scroll(elementScroll);
|
|
473
|
+
module.save.lastScroll(scroll.top);
|
|
474
|
+
module.save.elementScroll(elementScroll);
|
|
475
|
+
}
|
|
476
|
+
} else if (module.is.bottom()) {
|
|
477
|
+
if ((scroll.bottom - element.height) <= element.top) { // top edge
|
|
478
|
+
module.debug('Bottom fixed rail has reached top of container');
|
|
479
|
+
module.setInitialPosition();
|
|
480
|
+
} else if (scroll.bottom >= context.bottom) { // bottom edge
|
|
481
|
+
module.debug('Bottom fixed rail has reached bottom of container');
|
|
482
|
+
module.bindBottom();
|
|
483
|
+
} else if (doesntFit) { // scroll element if larger than screen
|
|
484
|
+
module.set.scroll(elementScroll);
|
|
485
|
+
module.save.lastScroll(scroll.top);
|
|
486
|
+
module.save.elementScroll(elementScroll);
|
|
487
|
+
}
|
|
488
|
+
}
|
|
489
|
+
} else if (module.is.bottom()) {
|
|
490
|
+
if (scroll.top <= element.top) {
|
|
491
|
+
module.debug('Jumped from bottom fixed to top fixed, most likely used home/end button');
|
|
492
|
+
module.setInitialPosition();
|
|
493
|
+
} else if (settings.pushing) {
|
|
494
|
+
if (module.is.bound() && scroll.bottom <= context.bottom) {
|
|
495
|
+
module.debug('Fixing bottom attached element to bottom of browser.');
|
|
496
|
+
module.fixBottom();
|
|
497
|
+
}
|
|
498
|
+
} else if (module.is.bound() && (scroll.top <= context.bottom - element.height)) {
|
|
499
|
+
module.debug('Fixing bottom attached element to top of browser.');
|
|
500
|
+
module.fixTop();
|
|
501
|
+
}
|
|
502
|
+
}
|
|
503
|
+
}
|
|
504
|
+
},
|
|
505
|
+
|
|
506
|
+
bindTop: function () {
|
|
507
|
+
module.debug('Binding element to top of parent container');
|
|
508
|
+
module.remove.offset();
|
|
509
|
+
if (settings.setSize) {
|
|
510
|
+
module.set.size();
|
|
511
|
+
}
|
|
512
|
+
$module
|
|
513
|
+
.css({
|
|
514
|
+
left: '',
|
|
515
|
+
top: '',
|
|
516
|
+
marginBottom: '',
|
|
517
|
+
})
|
|
518
|
+
.removeClass(className.fixed)
|
|
519
|
+
.removeClass(className.bottom)
|
|
520
|
+
.addClass(className.bound)
|
|
521
|
+
.addClass(className.top);
|
|
522
|
+
settings.onTop.call(element);
|
|
523
|
+
settings.onUnstick.call(element);
|
|
524
|
+
},
|
|
525
|
+
bindBottom: function () {
|
|
526
|
+
module.debug('Binding element to bottom of parent container');
|
|
527
|
+
module.remove.offset();
|
|
528
|
+
if (settings.setSize) {
|
|
529
|
+
module.set.size();
|
|
530
|
+
}
|
|
531
|
+
$module
|
|
532
|
+
.css({
|
|
533
|
+
left: '',
|
|
534
|
+
top: '',
|
|
535
|
+
})
|
|
536
|
+
.removeClass(className.fixed)
|
|
537
|
+
.removeClass(className.top)
|
|
538
|
+
.addClass(className.bound)
|
|
539
|
+
.addClass(className.bottom);
|
|
540
|
+
settings.onBottom.call(element);
|
|
541
|
+
settings.onUnstick.call(element);
|
|
542
|
+
},
|
|
543
|
+
|
|
544
|
+
setInitialPosition: function () {
|
|
545
|
+
module.debug('Returning to initial position');
|
|
546
|
+
module.unfix();
|
|
547
|
+
module.unbind();
|
|
548
|
+
},
|
|
549
|
+
|
|
550
|
+
fixTop: function () {
|
|
551
|
+
module.debug('Fixing element to top of page');
|
|
552
|
+
if (settings.setSize) {
|
|
553
|
+
module.set.size();
|
|
554
|
+
}
|
|
555
|
+
module.set.minimumSize();
|
|
556
|
+
module.set.offset();
|
|
557
|
+
$module
|
|
558
|
+
.css({
|
|
559
|
+
left: module.cache.element.left,
|
|
560
|
+
bottom: '',
|
|
561
|
+
marginBottom: '',
|
|
562
|
+
})
|
|
563
|
+
.removeClass(className.bound)
|
|
564
|
+
.removeClass(className.bottom)
|
|
565
|
+
.addClass(className.fixed)
|
|
566
|
+
.addClass(className.top);
|
|
567
|
+
settings.onStick.call(element);
|
|
568
|
+
},
|
|
569
|
+
|
|
570
|
+
fixBottom: function () {
|
|
571
|
+
module.debug('Sticking element to bottom of page');
|
|
572
|
+
if (settings.setSize) {
|
|
573
|
+
module.set.size();
|
|
574
|
+
}
|
|
575
|
+
module.set.minimumSize();
|
|
576
|
+
module.set.offset();
|
|
577
|
+
$module
|
|
578
|
+
.css({
|
|
579
|
+
left: module.cache.element.left,
|
|
580
|
+
bottom: '',
|
|
581
|
+
marginBottom: '',
|
|
582
|
+
})
|
|
583
|
+
.removeClass(className.bound)
|
|
584
|
+
.removeClass(className.top)
|
|
585
|
+
.addClass(className.fixed)
|
|
586
|
+
.addClass(className.bottom);
|
|
587
|
+
settings.onStick.call(element);
|
|
588
|
+
},
|
|
589
|
+
|
|
590
|
+
unbind: function () {
|
|
591
|
+
if (module.is.bound()) {
|
|
592
|
+
module.debug('Removing container bound position on element');
|
|
593
|
+
module.remove.offset();
|
|
594
|
+
$module
|
|
595
|
+
.removeClass(className.bound)
|
|
596
|
+
.removeClass(className.top)
|
|
597
|
+
.removeClass(className.bottom);
|
|
598
|
+
}
|
|
599
|
+
},
|
|
600
|
+
|
|
601
|
+
unfix: function () {
|
|
602
|
+
if (module.is.fixed()) {
|
|
603
|
+
module.debug('Removing fixed position on element');
|
|
604
|
+
module.remove.minimumSize();
|
|
605
|
+
module.remove.offset();
|
|
606
|
+
$module
|
|
607
|
+
.removeClass(className.fixed)
|
|
608
|
+
.removeClass(className.top)
|
|
609
|
+
.removeClass(className.bottom);
|
|
610
|
+
settings.onUnstick.call(element);
|
|
611
|
+
}
|
|
612
|
+
},
|
|
613
|
+
|
|
614
|
+
reset: function () {
|
|
615
|
+
module.debug('Resetting elements position');
|
|
616
|
+
module.unbind();
|
|
617
|
+
module.unfix();
|
|
618
|
+
module.resetCSS();
|
|
619
|
+
module.remove.offset();
|
|
620
|
+
module.remove.lastScroll();
|
|
621
|
+
},
|
|
622
|
+
|
|
623
|
+
resetCSS: function () {
|
|
624
|
+
$module
|
|
625
|
+
.css({
|
|
626
|
+
width: '',
|
|
627
|
+
height: '',
|
|
628
|
+
});
|
|
629
|
+
$container
|
|
630
|
+
.css({
|
|
631
|
+
height: '',
|
|
632
|
+
});
|
|
633
|
+
},
|
|
634
|
+
|
|
635
|
+
setting: function (name, value) {
|
|
636
|
+
if ($.isPlainObject(name)) {
|
|
637
|
+
$.extend(true, settings, name);
|
|
638
|
+
} else if (value !== undefined) {
|
|
639
|
+
settings[name] = value;
|
|
640
|
+
} else {
|
|
641
|
+
return settings[name];
|
|
642
|
+
}
|
|
643
|
+
},
|
|
644
|
+
internal: function (name, value) {
|
|
645
|
+
if ($.isPlainObject(name)) {
|
|
646
|
+
$.extend(true, module, name);
|
|
647
|
+
} else if (value !== undefined) {
|
|
648
|
+
module[name] = value;
|
|
649
|
+
} else {
|
|
650
|
+
return module[name];
|
|
651
|
+
}
|
|
652
|
+
},
|
|
653
|
+
debug: function (...args) {
|
|
654
|
+
if (!settings.silent && settings.debug) {
|
|
655
|
+
if (settings.performance) {
|
|
656
|
+
module.performance.log(args);
|
|
657
|
+
} else {
|
|
658
|
+
module.debug = Function.prototype.bind.call(console.info, console, settings.name + ':');
|
|
659
|
+
module.debug.apply(console, args);
|
|
660
|
+
}
|
|
661
|
+
}
|
|
662
|
+
},
|
|
663
|
+
verbose: function (...args) {
|
|
664
|
+
if (!settings.silent && settings.verbose && settings.debug) {
|
|
665
|
+
if (settings.performance) {
|
|
666
|
+
module.performance.log(args);
|
|
667
|
+
} else {
|
|
668
|
+
module.verbose = Function.prototype.bind.call(console.info, console, settings.name + ':');
|
|
669
|
+
module.verbose.apply(console, args);
|
|
670
|
+
}
|
|
671
|
+
}
|
|
672
|
+
},
|
|
673
|
+
error: function (...args) {
|
|
674
|
+
if (!settings.silent) {
|
|
675
|
+
module.error = Function.prototype.bind.call(console.error, console, settings.name + ':');
|
|
676
|
+
module.error.apply(console, args);
|
|
677
|
+
}
|
|
678
|
+
},
|
|
679
|
+
performance: {
|
|
680
|
+
log: function (message) {
|
|
681
|
+
let currentTime;
|
|
682
|
+
let executionTime;
|
|
683
|
+
let previousTime;
|
|
684
|
+
if (settings.performance) {
|
|
685
|
+
currentTime = Date.now();
|
|
686
|
+
previousTime = time || currentTime;
|
|
687
|
+
executionTime = currentTime - previousTime;
|
|
688
|
+
time = currentTime;
|
|
689
|
+
performance.push({
|
|
690
|
+
Name: message[0],
|
|
691
|
+
Arguments: message.slice(1),
|
|
692
|
+
Element: element,
|
|
693
|
+
'Execution Time': executionTime,
|
|
694
|
+
});
|
|
695
|
+
}
|
|
696
|
+
clearTimeout(module.performance.timer);
|
|
697
|
+
module.performance.timer = setTimeout(function () {
|
|
698
|
+
module.performance.display();
|
|
699
|
+
}, 0);
|
|
700
|
+
},
|
|
701
|
+
display: function () {
|
|
702
|
+
let title = settings.name + ':';
|
|
703
|
+
let totalTime = 0;
|
|
704
|
+
time = false;
|
|
705
|
+
clearTimeout(module.performance.timer);
|
|
706
|
+
$.each(performance, function (index, data) {
|
|
707
|
+
totalTime += data['Execution Time'];
|
|
708
|
+
});
|
|
709
|
+
title += ' ' + totalTime + 'ms';
|
|
710
|
+
if (performance.length > 0) {
|
|
711
|
+
console.groupCollapsed(title);
|
|
712
|
+
console.table(performance);
|
|
713
|
+
console.groupEnd();
|
|
714
|
+
}
|
|
715
|
+
performance = [];
|
|
716
|
+
},
|
|
717
|
+
},
|
|
718
|
+
invoke: function (query, passedArguments = queryArguments, context = element) {
|
|
719
|
+
let object = instance;
|
|
720
|
+
let maxDepth;
|
|
721
|
+
let found;
|
|
722
|
+
let response;
|
|
723
|
+
if (typeof query === 'string' && object !== undefined) {
|
|
724
|
+
query = query.split(/[ .]/);
|
|
725
|
+
maxDepth = query.length - 1;
|
|
726
|
+
$.each(query, function (depth, value) {
|
|
727
|
+
const camelCaseValue = depth !== maxDepth
|
|
728
|
+
? value + query[depth + 1].charAt(0).toUpperCase() + query[depth + 1].slice(1)
|
|
729
|
+
: query;
|
|
730
|
+
if ($.isPlainObject(object[camelCaseValue]) && (depth !== maxDepth)) {
|
|
731
|
+
object = object[camelCaseValue];
|
|
732
|
+
} else if (object[camelCaseValue] !== undefined) {
|
|
733
|
+
found = object[camelCaseValue];
|
|
734
|
+
|
|
735
|
+
return false;
|
|
736
|
+
} else if ($.isPlainObject(object[value]) && (depth !== maxDepth)) {
|
|
737
|
+
object = object[value];
|
|
738
|
+
} else if (object[value] !== undefined) {
|
|
739
|
+
found = object[value];
|
|
740
|
+
|
|
741
|
+
return false;
|
|
742
|
+
} else {
|
|
743
|
+
module.error(error.method, query);
|
|
744
|
+
|
|
745
|
+
return false;
|
|
746
|
+
}
|
|
747
|
+
});
|
|
748
|
+
}
|
|
749
|
+
if (isFunction(found)) {
|
|
750
|
+
response = found.apply(context, passedArguments);
|
|
751
|
+
} else if (found !== undefined) {
|
|
752
|
+
response = found;
|
|
753
|
+
}
|
|
754
|
+
if (Array.isArray(returnedValue)) {
|
|
755
|
+
returnedValue.push(response);
|
|
756
|
+
} else if (returnedValue !== undefined) {
|
|
757
|
+
returnedValue = [returnedValue, response];
|
|
758
|
+
} else if (response !== undefined) {
|
|
759
|
+
returnedValue = response;
|
|
760
|
+
}
|
|
761
|
+
|
|
762
|
+
return found;
|
|
763
|
+
},
|
|
764
|
+
};
|
|
765
|
+
|
|
766
|
+
if (methodInvoked) {
|
|
767
|
+
if (instance === undefined) {
|
|
768
|
+
module.initialize();
|
|
769
|
+
}
|
|
770
|
+
module.invoke(parameters);
|
|
771
|
+
} else {
|
|
772
|
+
if (instance !== undefined) {
|
|
773
|
+
instance.invoke('destroy');
|
|
774
|
+
}
|
|
775
|
+
module.initialize();
|
|
776
|
+
}
|
|
777
|
+
});
|
|
778
|
+
|
|
779
|
+
return returnedValue !== undefined
|
|
780
|
+
? returnedValue
|
|
781
|
+
: this;
|
|
782
|
+
};
|
|
783
|
+
|
|
784
|
+
$.fn.sticky.settings = {
|
|
785
|
+
|
|
786
|
+
name: 'Sticky',
|
|
787
|
+
namespace: 'sticky',
|
|
788
|
+
|
|
789
|
+
silent: false,
|
|
790
|
+
debug: false,
|
|
791
|
+
verbose: true,
|
|
792
|
+
performance: true,
|
|
793
|
+
|
|
794
|
+
// whether to stick in the opposite direction on scroll up
|
|
795
|
+
pushing: false,
|
|
796
|
+
|
|
797
|
+
context: false,
|
|
798
|
+
container: false,
|
|
799
|
+
|
|
800
|
+
// Context to watch scroll events
|
|
801
|
+
scrollContext: window,
|
|
802
|
+
|
|
803
|
+
// Offset to adjust scroll
|
|
804
|
+
offset: 0,
|
|
805
|
+
|
|
806
|
+
// Offset to adjust scroll when attached to bottom of screen
|
|
807
|
+
bottomOffset: 0,
|
|
808
|
+
|
|
809
|
+
// will only set container height if the difference between context and container is larger than this number
|
|
810
|
+
jitter: 5,
|
|
811
|
+
|
|
812
|
+
// set width of the sticky element when it is fixed to page (used to make sure 100% width is maintained if no fixed size set)
|
|
813
|
+
setSize: true,
|
|
814
|
+
|
|
815
|
+
// Whether to automatically observe changes with Mutation Observers
|
|
816
|
+
observeChanges: false,
|
|
817
|
+
|
|
818
|
+
// Called when position is recalculated
|
|
819
|
+
onReposition: function () {},
|
|
820
|
+
|
|
821
|
+
// Called on each scroll
|
|
822
|
+
onScroll: function () {},
|
|
823
|
+
|
|
824
|
+
// Called when the element is stuck to viewport
|
|
825
|
+
onStick: function () {},
|
|
826
|
+
|
|
827
|
+
// Called when the element is unstuck from viewport
|
|
828
|
+
onUnstick: function () {},
|
|
829
|
+
|
|
830
|
+
// Called when element reaches top of context
|
|
831
|
+
onTop: function () {},
|
|
832
|
+
|
|
833
|
+
// Called when element reaches bottom of context
|
|
834
|
+
onBottom: function () {},
|
|
835
|
+
|
|
836
|
+
error: {
|
|
837
|
+
visible: 'Element is hidden, you must call refresh after element becomes visible. Use silent setting to suppress this warning in production.',
|
|
838
|
+
method: 'The method you called is not defined.',
|
|
839
|
+
invalidContext: 'Context specified does not exist',
|
|
840
|
+
elementSize: 'Sticky element is larger than its container, cannot create sticky.',
|
|
841
|
+
},
|
|
842
|
+
|
|
843
|
+
className: {
|
|
844
|
+
bound: 'bound',
|
|
845
|
+
fixed: 'fixed',
|
|
846
|
+
supported: 'native',
|
|
847
|
+
top: 'top',
|
|
848
|
+
bottom: 'bottom',
|
|
849
|
+
},
|
|
850
|
+
|
|
851
|
+
};
|
|
852
|
+
})(jQuery, window, document);
|