root / snf-cyclades-app / synnefo / ui / new_ui / ui / javascripts / jquery.scrollintoview.js @ 812b1e8d
History | View | Annotate | Download (6.6 kB)
1 | 96d15954 | Olga Brani | /*!
|
---|---|---|---|
2 | 96d15954 | Olga Brani | * jQuery scrollintoview() plugin and :scrollable selector filter
|
3 | 96d15954 | Olga Brani | *
|
4 | 96d15954 | Olga Brani | * Version 1.8 (14 Jul 2011)
|
5 | 96d15954 | Olga Brani | * Requires jQuery 1.4 or newer
|
6 | 96d15954 | Olga Brani | *
|
7 | 96d15954 | Olga Brani | * Copyright (c) 2011 Robert Koritnik
|
8 | 96d15954 | Olga Brani | * Licensed under the terms of the MIT license
|
9 | 96d15954 | Olga Brani | * http://www.opensource.org/licenses/mit-license.php
|
10 | 96d15954 | Olga Brani | */
|
11 | 96d15954 | Olga Brani | |
12 | 96d15954 | Olga Brani | (function ($) { |
13 | 96d15954 | Olga Brani | var converter = {
|
14 | 96d15954 | Olga Brani | vertical: { x: false, y: true }, |
15 | 96d15954 | Olga Brani | horizontal: { x: true, y: false }, |
16 | 96d15954 | Olga Brani | both: { x: true, y: true }, |
17 | 96d15954 | Olga Brani | x: { x: true, y: false }, |
18 | 96d15954 | Olga Brani | y: { x: false, y: true } |
19 | 96d15954 | Olga Brani | }; |
20 | 96d15954 | Olga Brani | |
21 | 96d15954 | Olga Brani | var settings = {
|
22 | 96d15954 | Olga Brani | duration: "fast", |
23 | 96d15954 | Olga Brani | direction: "both" |
24 | 96d15954 | Olga Brani | }; |
25 | 96d15954 | Olga Brani | |
26 | 96d15954 | Olga Brani | var rootrx = /^(?:html)$/i; |
27 | 96d15954 | Olga Brani | |
28 | 96d15954 | Olga Brani | // gets border dimensions
|
29 | 96d15954 | Olga Brani | var borders = function (domElement, styles) { |
30 | 96d15954 | Olga Brani | styles = styles || (document.defaultView && document.defaultView.getComputedStyle ? document.defaultView.getComputedStyle(domElement, null) : domElement.currentStyle);
|
31 | 96d15954 | Olga Brani | var px = document.defaultView && document.defaultView.getComputedStyle ? true : false; |
32 | 96d15954 | Olga Brani | var b = {
|
33 | 96d15954 | Olga Brani | top: (parseFloat(px ? styles.borderTopWidth : $.css(domElement, "borderTopWidth")) || 0), |
34 | 96d15954 | Olga Brani | left: (parseFloat(px ? styles.borderLeftWidth : $.css(domElement, "borderLeftWidth")) || 0), |
35 | 96d15954 | Olga Brani | bottom: (parseFloat(px ? styles.borderBottomWidth : $.css(domElement, "borderBottomWidth")) || 0), |
36 | 96d15954 | Olga Brani | right: (parseFloat(px ? styles.borderRightWidth : $.css(domElement, "borderRightWidth")) || 0) |
37 | 96d15954 | Olga Brani | }; |
38 | 96d15954 | Olga Brani | return {
|
39 | 96d15954 | Olga Brani | top: b.top,
|
40 | 96d15954 | Olga Brani | left: b.left,
|
41 | 96d15954 | Olga Brani | bottom: b.bottom,
|
42 | 96d15954 | Olga Brani | right: b.right,
|
43 | 96d15954 | Olga Brani | vertical: b.top + b.bottom,
|
44 | 96d15954 | Olga Brani | horizontal: b.left + b.right
|
45 | 96d15954 | Olga Brani | }; |
46 | 96d15954 | Olga Brani | }; |
47 | 96d15954 | Olga Brani | |
48 | 96d15954 | Olga Brani | var dimensions = function ($element) { |
49 | 96d15954 | Olga Brani | var win = $(window); |
50 | 96d15954 | Olga Brani | var isRoot = rootrx.test($element[0].nodeName); |
51 | 96d15954 | Olga Brani | return {
|
52 | 96d15954 | Olga Brani | border: isRoot ? { top: 0, left: 0, bottom: 0, right: 0} : borders($element[0]), |
53 | 96d15954 | Olga Brani | scroll: {
|
54 | 96d15954 | Olga Brani | top: (isRoot ? win : $element).scrollTop(), |
55 | 96d15954 | Olga Brani | left: (isRoot ? win : $element).scrollLeft() |
56 | 96d15954 | Olga Brani | }, |
57 | 96d15954 | Olga Brani | scrollbar: {
|
58 | 96d15954 | Olga Brani | right: isRoot ? 0 : $element.innerWidth() - $element[0].clientWidth, |
59 | 96d15954 | Olga Brani | bottom: isRoot ? 0 : $element.innerHeight() - $element[0].clientHeight |
60 | 96d15954 | Olga Brani | }, |
61 | 96d15954 | Olga Brani | rect: (function () { |
62 | 96d15954 | Olga Brani | var r = $element[0].getBoundingClientRect(); |
63 | 96d15954 | Olga Brani | return {
|
64 | 96d15954 | Olga Brani | top: isRoot ? 0 : r.top, |
65 | 96d15954 | Olga Brani | left: isRoot ? 0 : r.left, |
66 | 96d15954 | Olga Brani | bottom: isRoot ? $element[0].clientHeight : r.bottom, |
67 | 96d15954 | Olga Brani | right: isRoot ? $element[0].clientWidth : r.right |
68 | 96d15954 | Olga Brani | }; |
69 | 96d15954 | Olga Brani | })() |
70 | 96d15954 | Olga Brani | }; |
71 | 96d15954 | Olga Brani | }; |
72 | 96d15954 | Olga Brani | |
73 | 96d15954 | Olga Brani | $.fn.extend({
|
74 | 96d15954 | Olga Brani | scrollintoview: function (options) { |
75 | 96d15954 | Olga Brani | /// <summary>Scrolls the first element in the set into view by scrolling its closest scrollable parent.</summary>
|
76 | 96d15954 | Olga Brani | /// <param name="options" type="Object">Additional options that can configure scrolling:
|
77 | 96d15954 | Olga Brani | /// duration (default: "fast") - jQuery animation speed (can be a duration string or number of milliseconds)
|
78 | 96d15954 | Olga Brani | /// direction (default: "both") - select possible scrollings ("vertical" or "y", "horizontal" or "x", "both")
|
79 | 96d15954 | Olga Brani | /// complete (default: none) - a function to call when scrolling completes (called in context of the DOM element being scrolled)
|
80 | 96d15954 | Olga Brani | /// </param>
|
81 | 96d15954 | Olga Brani | /// <return type="jQuery">Returns the same jQuery set that this function was run on.</return>
|
82 | 96d15954 | Olga Brani | |
83 | 96d15954 | Olga Brani | options = $.extend({}, settings, options);
|
84 | 96d15954 | Olga Brani | options.direction = converter[typeof (options.direction) === "string" && options.direction.toLowerCase()] || converter.both; |
85 | 96d15954 | Olga Brani | |
86 | 96d15954 | Olga Brani | var dirStr = ""; |
87 | 96d15954 | Olga Brani | if (options.direction.x === true) dirStr = "horizontal"; |
88 | 96d15954 | Olga Brani | if (options.direction.y === true) dirStr = dirStr ? "both" : "vertical"; |
89 | 96d15954 | Olga Brani | |
90 | 96d15954 | Olga Brani | var el = this.eq(0); |
91 | 96d15954 | Olga Brani | var scroller = el.closest(":scrollable(" + dirStr + ")"); |
92 | 96d15954 | Olga Brani | |
93 | 96d15954 | Olga Brani | // check if there's anything to scroll in the first place
|
94 | 96d15954 | Olga Brani | if (scroller.length > 0) |
95 | 96d15954 | Olga Brani | { |
96 | 96d15954 | Olga Brani | scroller = scroller.eq(0);
|
97 | 96d15954 | Olga Brani | |
98 | 96d15954 | Olga Brani | var dim = {
|
99 | 96d15954 | Olga Brani | e: dimensions(el),
|
100 | 96d15954 | Olga Brani | s: dimensions(scroller)
|
101 | 96d15954 | Olga Brani | }; |
102 | 96d15954 | Olga Brani | |
103 | 96d15954 | Olga Brani | var rel = {
|
104 | 96d15954 | Olga Brani | top: dim.e.rect.top - (dim.s.rect.top + dim.s.border.top),
|
105 | 96d15954 | Olga Brani | bottom: dim.s.rect.bottom - dim.s.border.bottom - dim.s.scrollbar.bottom - dim.e.rect.bottom,
|
106 | 96d15954 | Olga Brani | left: dim.e.rect.left - (dim.s.rect.left + dim.s.border.left),
|
107 | 96d15954 | Olga Brani | right: dim.s.rect.right - dim.s.border.right - dim.s.scrollbar.right - dim.e.rect.right
|
108 | 96d15954 | Olga Brani | }; |
109 | 96d15954 | Olga Brani | |
110 | 96d15954 | Olga Brani | var animOptions = {};
|
111 | 96d15954 | Olga Brani | |
112 | 96d15954 | Olga Brani | // vertical scroll
|
113 | 96d15954 | Olga Brani | if (options.direction.y === true) |
114 | 96d15954 | Olga Brani | { |
115 | 96d15954 | Olga Brani | if (rel.top < 0) |
116 | 96d15954 | Olga Brani | { |
117 | 96d15954 | Olga Brani | animOptions.scrollTop = dim.s.scroll.top + rel.top; |
118 | 96d15954 | Olga Brani | } |
119 | 96d15954 | Olga Brani | else if (rel.top > 0 && rel.bottom < 0) |
120 | 96d15954 | Olga Brani | { |
121 | 96d15954 | Olga Brani | animOptions.scrollTop = dim.s.scroll.top + Math.min(rel.top, -rel.bottom); |
122 | 96d15954 | Olga Brani | } |
123 | 96d15954 | Olga Brani | } |
124 | 96d15954 | Olga Brani | |
125 | 96d15954 | Olga Brani | // horizontal scroll
|
126 | 96d15954 | Olga Brani | if (options.direction.x === true) |
127 | 96d15954 | Olga Brani | { |
128 | 96d15954 | Olga Brani | if (rel.left < 0) |
129 | 96d15954 | Olga Brani | { |
130 | 96d15954 | Olga Brani | animOptions.scrollLeft = dim.s.scroll.left + rel.left; |
131 | 96d15954 | Olga Brani | } |
132 | 96d15954 | Olga Brani | else if (rel.left > 0 && rel.right < 0) |
133 | 96d15954 | Olga Brani | { |
134 | 96d15954 | Olga Brani | animOptions.scrollLeft = dim.s.scroll.left + Math.min(rel.left, -rel.right); |
135 | 96d15954 | Olga Brani | } |
136 | 96d15954 | Olga Brani | } |
137 | 96d15954 | Olga Brani | |
138 | 96d15954 | Olga Brani | // scroll if needed
|
139 | 96d15954 | Olga Brani | if (!$.isEmptyObject(animOptions)) |
140 | 96d15954 | Olga Brani | { |
141 | 96d15954 | Olga Brani | if (rootrx.test(scroller[0].nodeName)) |
142 | 96d15954 | Olga Brani | { |
143 | 96d15954 | Olga Brani | scroller = $("html,body"); |
144 | 96d15954 | Olga Brani | } |
145 | 96d15954 | Olga Brani | scroller |
146 | 96d15954 | Olga Brani | .animate(animOptions, options.duration) |
147 | 96d15954 | Olga Brani | .eq(0) // we want function to be called just once (ref. "html,body") |
148 | 96d15954 | Olga Brani | .queue(function (next) {
|
149 | 96d15954 | Olga Brani | $.isFunction(options.complete) && options.complete.call(scroller[0]); |
150 | 96d15954 | Olga Brani | next(); |
151 | 96d15954 | Olga Brani | }); |
152 | 96d15954 | Olga Brani | } |
153 | 96d15954 | Olga Brani | else
|
154 | 96d15954 | Olga Brani | { |
155 | 96d15954 | Olga Brani | // when there's nothing to scroll, just call the "complete" function
|
156 | 96d15954 | Olga Brani | $.isFunction(options.complete) && options.complete.call(scroller[0]); |
157 | 96d15954 | Olga Brani | } |
158 | 96d15954 | Olga Brani | } |
159 | 96d15954 | Olga Brani | |
160 | 96d15954 | Olga Brani | // return set back
|
161 | 96d15954 | Olga Brani | return this; |
162 | 96d15954 | Olga Brani | } |
163 | 96d15954 | Olga Brani | }); |
164 | 96d15954 | Olga Brani | |
165 | 96d15954 | Olga Brani | var scrollValue = {
|
166 | 96d15954 | Olga Brani | auto: true, |
167 | 96d15954 | Olga Brani | scroll: true, |
168 | 96d15954 | Olga Brani | visible: false, |
169 | 96d15954 | Olga Brani | hidden: false |
170 | 96d15954 | Olga Brani | }; |
171 | 96d15954 | Olga Brani | |
172 | 96d15954 | Olga Brani | $.extend($.expr[":"], { |
173 | 96d15954 | Olga Brani | scrollable: function (element, index, meta, stack) { |
174 | 96d15954 | Olga Brani | var direction = converter[typeof (meta[3]) === "string" && meta[3].toLowerCase()] || converter.both; |
175 | 96d15954 | Olga Brani | var styles = (document.defaultView && document.defaultView.getComputedStyle ? document.defaultView.getComputedStyle(element, null) : element.currentStyle); |
176 | 96d15954 | Olga Brani | var overflow = {
|
177 | 96d15954 | Olga Brani | x: scrollValue[styles.overflowX.toLowerCase()] || false, |
178 | 96d15954 | Olga Brani | y: scrollValue[styles.overflowY.toLowerCase()] || false, |
179 | 96d15954 | Olga Brani | isRoot: rootrx.test(element.nodeName)
|
180 | 96d15954 | Olga Brani | }; |
181 | 96d15954 | Olga Brani | |
182 | 96d15954 | Olga Brani | // check if completely unscrollable (exclude HTML element because it's special)
|
183 | 96d15954 | Olga Brani | if (!overflow.x && !overflow.y && !overflow.isRoot)
|
184 | 96d15954 | Olga Brani | { |
185 | 96d15954 | Olga Brani | return false; |
186 | 96d15954 | Olga Brani | } |
187 | 96d15954 | Olga Brani | |
188 | 96d15954 | Olga Brani | var size = {
|
189 | 96d15954 | Olga Brani | height: {
|
190 | 96d15954 | Olga Brani | scroll: element.scrollHeight,
|
191 | 96d15954 | Olga Brani | client: element.clientHeight
|
192 | 96d15954 | Olga Brani | }, |
193 | 96d15954 | Olga Brani | width: {
|
194 | 96d15954 | Olga Brani | scroll: element.scrollWidth,
|
195 | 96d15954 | Olga Brani | client: element.clientWidth
|
196 | 96d15954 | Olga Brani | }, |
197 | 96d15954 | Olga Brani | // check overflow.x/y because iPad (and possibly other tablets) don't dislay scrollbars
|
198 | 96d15954 | Olga Brani | scrollableX: function () { |
199 | 96d15954 | Olga Brani | return (overflow.x || overflow.isRoot) && this.width.scroll > this.width.client; |
200 | 96d15954 | Olga Brani | }, |
201 | 96d15954 | Olga Brani | scrollableY: function () { |
202 | 96d15954 | Olga Brani | return (overflow.y || overflow.isRoot) && this.height.scroll > this.height.client; |
203 | 96d15954 | Olga Brani | } |
204 | 96d15954 | Olga Brani | }; |
205 | 96d15954 | Olga Brani | return direction.y && size.scrollableY() || direction.x && size.scrollableX();
|
206 | 96d15954 | Olga Brani | } |
207 | 96d15954 | Olga Brani | }); |
208 | 96d15954 | Olga Brani | })(jQuery); |