Skip to content

Commit 09429e3

Browse files
committed
logic modules split
1 parent 564c03b commit 09429e3

File tree

8 files changed

+1152
-0
lines changed

8 files changed

+1152
-0
lines changed

src/modules/jqlite-extras-register.js

Lines changed: 253 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,253 @@
1+
export default function jqLiteExtrasRegister(element) {
2+
var convertToPx, css, getStyle, isWindow;
3+
// angular implementation blows up if elem is the window
4+
css = angular.element.prototype.css;
5+
6+
element.prototype.css = function (name, value) {
7+
let self = this;
8+
let elem = self[0];
9+
if (!(!elem || elem.nodeType === 3 || elem.nodeType === 8 || !elem.style)) {
10+
return css.call(self, name, value);
11+
}
12+
};
13+
14+
// as defined in angularjs v1.0.5
15+
isWindow = (obj) => obj && obj.document && obj.location && obj.alert && obj.setInterval;
16+
17+
function scrollTo(self, direction, value) {
18+
let elem = self[0];
19+
let [method, prop, preserve] = {
20+
top: [
21+
'scrollTop',
22+
'pageYOffset',
23+
'scrollLeft'
24+
],
25+
left: [
26+
'scrollLeft',
27+
'pageXOffset',
28+
'scrollTop'
29+
]
30+
}[direction];
31+
32+
if (isWindow(elem)) {
33+
if (angular.isDefined(value)) {
34+
return elem.scrollTo(self[preserve].call(self), value);
35+
}
36+
37+
return (prop in elem) ? elem[prop] : elem.document.documentElement[method];
38+
} else {
39+
if (angular.isDefined(value)) {
40+
elem[method] = value;
41+
}
42+
43+
return elem[method];
44+
}
45+
}
46+
47+
if (window.getComputedStyle) {
48+
getStyle = (elem) => window.getComputedStyle(elem, null);
49+
convertToPx = (elem, value) => parseFloat(value);
50+
} else {
51+
getStyle = (elem) => elem.currentStyle;
52+
convertToPx = (elem, value) => {
53+
let left, result, rs, rsLeft, style;
54+
let core_pnum = /[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source;
55+
let rnumnonpx = new RegExp('^(' + core_pnum + ')(?!px)[a-z%]+$', 'i');
56+
57+
if (!rnumnonpx.test(value)) {
58+
return parseFloat(value);
59+
}
60+
61+
// ported from JQuery
62+
style = elem.style;
63+
left = style.left;
64+
rs = elem.runtimeStyle;
65+
rsLeft = rs && rs.left;
66+
if (rs) {
67+
rs.left = style.left;
68+
}
69+
// put in the new values to get a computed style out
70+
style.left = value;
71+
result = style.pixelLeft;
72+
style.left = left;
73+
if (rsLeft) {
74+
rs.left = rsLeft;
75+
}
76+
return result;
77+
};
78+
}
79+
80+
function getMeasurements(elem, measure) {
81+
let base, borderA, borderB, computedMarginA, computedMarginB, computedStyle, dirA, dirB, marginA, marginB, paddingA, paddingB;
82+
83+
if (isWindow(elem)) {
84+
base = document.documentElement[{height: 'clientHeight', width: 'clientWidth'}[measure]];
85+
86+
return {
87+
base: base,
88+
padding: 0,
89+
border: 0,
90+
margin: 0
91+
};
92+
}
93+
94+
// Start with offset property
95+
[
96+
base,
97+
dirA,
98+
dirB
99+
] = {
100+
width: [
101+
elem.offsetWidth,
102+
'Left',
103+
'Right'
104+
],
105+
height: [
106+
elem.offsetHeight,
107+
'Top',
108+
'Bottom'
109+
]
110+
}[measure];
111+
112+
computedStyle = getStyle(elem);
113+
paddingA = convertToPx(elem, computedStyle['padding' + dirA]) || 0;
114+
paddingB = convertToPx(elem, computedStyle['padding' + dirB]) || 0;
115+
borderA = convertToPx(elem, computedStyle['border' + dirA + 'Width']) || 0;
116+
borderB = convertToPx(elem, computedStyle['border' + dirB + 'Width']) || 0;
117+
computedMarginA = computedStyle['margin' + dirA];
118+
computedMarginB = computedStyle['margin' + dirB];
119+
120+
// I do not care for width for now, so this hack is irrelevant
121+
// if ( !supportsPercentMargin )
122+
// computedMarginA = hackPercentMargin( elem, computedStyle, computedMarginA )
123+
// computedMarginB = hackPercentMargin( elem, computedStyle, computedMarginB )
124+
marginA = convertToPx(elem, computedMarginA) || 0;
125+
marginB = convertToPx(elem, computedMarginB) || 0;
126+
127+
return {
128+
base: base,
129+
padding: paddingA + paddingB,
130+
border: borderA + borderB,
131+
margin: marginA + marginB
132+
};
133+
}
134+
135+
function getWidthHeight(elem, direction, measure) {
136+
let computedStyle, result;
137+
138+
let measurements = getMeasurements(elem, direction);
139+
140+
if (measurements.base > 0) {
141+
return {
142+
base: measurements.base - measurements.padding - measurements.border,
143+
outer: measurements.base,
144+
outerfull: measurements.base + measurements.margin
145+
}[measure];
146+
}
147+
148+
// Fall back to computed then uncomputed css if necessary
149+
computedStyle = getStyle(elem);
150+
result = computedStyle[direction];
151+
152+
if (result < 0 || result === null) {
153+
result = elem.style[direction] || 0;
154+
}
155+
156+
// Normalize "", auto, and prepare for extra
157+
result = parseFloat(result) || 0;
158+
159+
return {
160+
base: result - measurements.padding - measurements.border,
161+
outer: result,
162+
outerfull: result + measurements.padding + measurements.border + measurements.margin
163+
}[measure];
164+
}
165+
166+
// define missing methods
167+
return angular.forEach({
168+
before(newElem) {
169+
var children, elem, i, j, parent, ref, self;
170+
self = this;
171+
elem = self[0];
172+
parent = self.parent();
173+
children = parent.contents();
174+
if (children[0] === elem) {
175+
return parent.prepend(newElem);
176+
} else {
177+
for (i = j = 1, ref = children.length - 1; 1 <= ref ? j <= ref : j >= ref; i = 1 <= ref ? ++j : --j) {
178+
if (children[i] === elem) {
179+
angular.element(children[i - 1]).after(newElem);
180+
return;
181+
}
182+
}
183+
throw new Error('invalid DOM structure ' + elem.outerHTML);
184+
}
185+
},
186+
height (value){
187+
var self;
188+
self = this;
189+
if (angular.isDefined(value)) {
190+
if (angular.isNumber(value)) {
191+
value = value + 'px';
192+
}
193+
return css.call(self, 'height', value);
194+
} else {
195+
return getWidthHeight(this[0], 'height', 'base');
196+
}
197+
},
198+
outerHeight(option) {
199+
return getWidthHeight(this[0], 'height', option ? 'outerfull' : 'outer');
200+
},
201+
202+
/*
203+
The offset setter method is not implemented
204+
*/
205+
offset(value) {
206+
let docElem, win;
207+
let self = this;
208+
let box = {
209+
top: 0,
210+
left: 0
211+
};
212+
let elem = self[0];
213+
let doc = elem && elem.ownerDocument;
214+
215+
if (arguments.length) {
216+
if (value === undefined) {
217+
return self;
218+
}
219+
// TODO: implement setter
220+
throw new Error('offset setter method is not implemented');
221+
}
222+
223+
if (!doc) {
224+
return;
225+
}
226+
227+
docElem = doc.documentElement;
228+
229+
// TODO: Make sure it's not a disconnected DOM node
230+
231+
if (elem.getBoundingClientRect != null) {
232+
box = elem.getBoundingClientRect();
233+
}
234+
235+
win = doc.defaultView || doc.parentWindow;
236+
237+
return {
238+
top: box.top + (win.pageYOffset || docElem.scrollTop) - (docElem.clientTop || 0),
239+
left: box.left + (win.pageXOffset || docElem.scrollLeft) - (docElem.clientLeft || 0)
240+
};
241+
},
242+
scrollTop(value) {
243+
return scrollTo(this, 'top', value);
244+
},
245+
scrollLeft(value) {
246+
return scrollTo(this, 'left', value);
247+
}
248+
}, (value, key) => {
249+
if (!element.prototype[key]) {
250+
return element.prototype[key] = value;
251+
}
252+
});
253+
}

src/modules/misc/adapter.js

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,97 @@
1+
export default function Adapter($parse, $attr, viewport, buffer, adjustBuffer) {
2+
const viewportScope = viewport.scope() || $rootScope;
3+
const setTopVisible = $attr.topVisible ? $parse($attr.topVisible).assign : angular.noop;
4+
const setTopVisibleElement = $attr.topVisibleElement ? $parse($attr.topVisibleElement).assign : angular.noop;
5+
const setTopVisibleScope = $attr.topVisibleScope ? $parse($attr.topVisibleScope).assign : angular.noop;
6+
const setIsLoading = $attr.isLoading ? $parse($attr.isLoading).assign : angular.noop;
7+
8+
this.isLoading = false;
9+
10+
function applyUpdate(wrapper, newItems) {
11+
if (!angular.isArray(newItems)) {
12+
return;
13+
}
14+
15+
let keepIt;
16+
let pos = (buffer.indexOf(wrapper)) + 1;
17+
18+
newItems.reverse().forEach((newItem) => {
19+
if (newItem === wrapper.item) {
20+
keepIt = true;
21+
pos--;
22+
} else {
23+
buffer.insert(pos, newItem);
24+
}
25+
});
26+
27+
if (!keepIt) {
28+
wrapper.op = 'remove';
29+
}
30+
}
31+
32+
this.applyUpdates = (arg1, arg2) => {
33+
if (angular.isFunction(arg1)) {
34+
// arg1 is the updater function, arg2 is ignored
35+
buffer.slice(0).forEach((wrapper) => {
36+
// we need to do it on the buffer clone, because buffer content
37+
// may change as we iterate through
38+
applyUpdate(wrapper, arg1(wrapper.item, wrapper.scope, wrapper.element));
39+
});
40+
} else {
41+
// arg1 is item index, arg2 is the newItems array
42+
if (arg1 % 1 !== 0) {// checking if it is an integer
43+
throw new Error('applyUpdates - ' + arg1 + ' is not a valid index');
44+
}
45+
46+
const index = arg1 - buffer.first;
47+
if ((index >= 0 && index < buffer.length)) {
48+
applyUpdate(buffer[index], arg2);
49+
}
50+
}
51+
52+
adjustBuffer();
53+
};
54+
55+
this.append = (newItems) => {
56+
buffer.append(newItems);
57+
adjustBuffer();
58+
};
59+
60+
this.prepend = (newItems) => {
61+
buffer.prepend(newItems);
62+
adjustBuffer();
63+
};
64+
65+
this.loading = function (value) {
66+
this.isLoading = value;
67+
setIsLoading(viewportScope, value);
68+
};
69+
70+
this.calculateProperties = function () {
71+
let i, item, itemHeight, itemTop, isNewRow, rowTop;
72+
let topHeight = 0;
73+
for (i = 0; i < buffer.length; i++) {
74+
item = buffer[i];
75+
itemTop = item.element.offset().top;
76+
isNewRow = rowTop !== itemTop;
77+
rowTop = itemTop;
78+
if (isNewRow) {
79+
itemHeight = item.element.outerHeight(true);
80+
}
81+
if (isNewRow && (viewport.topDataPos() + topHeight + itemHeight <= viewport.topVisiblePos())) {
82+
topHeight += itemHeight;
83+
} else {
84+
if (isNewRow) {
85+
this.topVisible = item.item;
86+
this.topVisibleElement = item.element;
87+
this.topVisibleScope = item.scope;
88+
setTopVisible(viewportScope, item.item);
89+
setTopVisibleElement(viewportScope, item.element);
90+
setTopVisibleScope(viewportScope, item.scope);
91+
}
92+
break;
93+
94+
}
95+
}
96+
};
97+
}

0 commit comments

Comments
 (0)