uikit 3.11.2-dev.72dbb9a19 → 3.11.2-dev.76734f785
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.
- package/CHANGELOG.md +39 -19
- package/dist/css/uikit-core-rtl.css +86 -170
- package/dist/css/uikit-core-rtl.min.css +1 -1
- package/dist/css/uikit-core.css +86 -170
- package/dist/css/uikit-core.min.css +1 -1
- package/dist/css/uikit-rtl.css +88 -176
- package/dist/css/uikit-rtl.min.css +1 -1
- package/dist/css/uikit.css +88 -176
- package/dist/css/uikit.min.css +1 -1
- package/dist/js/components/countdown.js +1 -1
- package/dist/js/components/countdown.min.js +1 -1
- package/dist/js/components/filter.js +1 -1
- package/dist/js/components/filter.min.js +1 -1
- package/dist/js/components/lightbox-panel.js +1 -1
- package/dist/js/components/lightbox-panel.min.js +1 -1
- package/dist/js/components/lightbox.js +1 -1
- package/dist/js/components/lightbox.min.js +1 -1
- package/dist/js/components/notification.js +1 -1
- package/dist/js/components/notification.min.js +1 -1
- package/dist/js/components/parallax.js +115 -78
- package/dist/js/components/parallax.min.js +1 -1
- package/dist/js/components/slider-parallax.js +115 -78
- package/dist/js/components/slider-parallax.min.js +1 -1
- package/dist/js/components/slider.js +79 -33
- package/dist/js/components/slider.min.js +1 -1
- package/dist/js/components/slideshow-parallax.js +115 -78
- package/dist/js/components/slideshow-parallax.min.js +1 -1
- package/dist/js/components/slideshow.js +45 -3
- package/dist/js/components/slideshow.min.js +1 -1
- package/dist/js/components/sortable.js +1 -1
- package/dist/js/components/sortable.min.js +1 -1
- package/dist/js/components/tooltip.js +1 -1
- package/dist/js/components/tooltip.min.js +1 -1
- package/dist/js/components/upload.js +1 -1
- package/dist/js/components/upload.min.js +1 -1
- package/dist/js/uikit-core.js +259 -234
- package/dist/js/uikit-core.min.js +1 -1
- package/dist/js/uikit-icons.js +1 -1
- package/dist/js/uikit-icons.min.js +1 -1
- package/dist/js/uikit.js +461 -347
- package/dist/js/uikit.min.js +1 -1
- package/package.json +1 -1
- package/src/js/components/internal/slider-preload.js +37 -0
- package/src/js/components/slider.js +43 -34
- package/src/js/components/slideshow.js +8 -1
- package/src/js/core/height-viewport.js +3 -0
- package/src/js/core/icon.js +13 -6
- package/src/js/core/img.js +131 -114
- package/src/js/core/sticky.js +51 -57
- package/src/js/core/svg.js +10 -6
- package/src/js/core/toggle.js +2 -1
- package/src/js/mixin/parallax.js +116 -79
- package/src/js/util/ajax.js +6 -2
- package/src/js/util/dimensions.js +4 -4
- package/src/js/util/dom.js +37 -31
- package/src/js/util/lang.js +6 -5
- package/src/js/util/player.js +3 -2
- package/src/js/util/style.js +4 -4
- package/src/less/components/base.less +10 -28
- package/src/less/components/form-range.less +48 -95
- package/src/less/components/form.less +0 -1
- package/src/less/components/height.less +3 -0
- package/src/less/components/lightbox.less +0 -1
- package/src/less/components/modal.less +3 -7
- package/src/less/components/progress.less +14 -36
- package/src/less/components/slider.less +0 -3
- package/src/less/components/slideshow.less +0 -3
- package/src/less/components/text.less +16 -32
- package/src/scss/components/base.scss +10 -28
- package/src/scss/components/form-range.scss +48 -95
- package/src/scss/components/form.scss +0 -1
- package/src/scss/components/height.scss +3 -0
- package/src/scss/components/lightbox.scss +0 -1
- package/src/scss/components/modal.scss +3 -7
- package/src/scss/components/progress.scss +14 -36
- package/src/scss/components/slider.scss +0 -3
- package/src/scss/components/slideshow.scss +0 -3
- package/src/scss/components/text.scss +16 -32
- package/src/scss/mixins-theme.scss +1 -1
- package/src/scss/mixins.scss +1 -1
- package/src/scss/variables-theme.scss +3 -3
- package/src/scss/variables.scss +3 -3
- package/tests/align.html +10 -10
- package/tests/animation.html +2 -2
- package/tests/article.html +2 -2
- package/tests/base.html +3 -3
- package/tests/card.html +10 -10
- package/tests/column.html +3 -3
- package/tests/comment.html +9 -9
- package/tests/dotnav.html +3 -3
- package/tests/image.html +296 -64
- package/tests/images/image-type.avif +0 -0
- package/tests/images/image-type.jpeg +0 -0
- package/tests/images/image-type.webp +0 -0
- package/tests/index.html +8 -8
- package/tests/lightbox.html +10 -10
- package/tests/marker.html +2 -2
- package/tests/modal.html +8 -9
- package/tests/navbar.html +2 -2
- package/tests/overlay.html +7 -7
- package/tests/parallax.html +16 -7
- package/tests/position.html +12 -12
- package/tests/slidenav.html +12 -12
- package/tests/slider.html +20 -20
- package/tests/sortable.html +1 -1
- package/tests/sticky-parallax.html +56 -71
- package/tests/svg.html +6 -6
- package/tests/table.html +11 -11
- package/tests/thumbnav.html +12 -12
- package/tests/transition.html +30 -30
- package/tests/utility.html +33 -33
- package/tests/video.html +1 -1
- package/tests/width.html +1 -1
- package/tests/images/animated.gif +0 -0
package/package.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"name": "uikit",
|
|
3
3
|
"title": "UIkit",
|
|
4
4
|
"description": "UIkit is a lightweight and modular front-end framework for developing fast and powerful web interfaces.",
|
|
5
|
-
"version": "3.11.2-dev.
|
|
5
|
+
"version": "3.11.2-dev.76734f785",
|
|
6
6
|
"main": "dist/js/uikit.js",
|
|
7
7
|
"style": "dist/css/uikit.css",
|
|
8
8
|
"sideEffects": [
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { $$, isVisible, removeAttr } from 'uikit-util';
|
|
2
|
+
|
|
3
|
+
export default {
|
|
4
|
+
connected() {
|
|
5
|
+
if (window.IntersectionObserver) {
|
|
6
|
+
this.observer = new IntersectionObserver(
|
|
7
|
+
(entries) => {
|
|
8
|
+
if (entries.some((entry) => entry.isIntersecting)) {
|
|
9
|
+
removeLazyLoad(this.getAdjacentSlides());
|
|
10
|
+
}
|
|
11
|
+
},
|
|
12
|
+
{ rootMargin: '50% 50%' }
|
|
13
|
+
);
|
|
14
|
+
this.observer.observe(this.$el);
|
|
15
|
+
}
|
|
16
|
+
},
|
|
17
|
+
|
|
18
|
+
disconnected() {
|
|
19
|
+
this.observer && this.observer.disconnect();
|
|
20
|
+
},
|
|
21
|
+
|
|
22
|
+
update: {
|
|
23
|
+
read() {
|
|
24
|
+
if (isVisible(this.$el)) {
|
|
25
|
+
removeLazyLoad(this.getAdjacentSlides());
|
|
26
|
+
}
|
|
27
|
+
},
|
|
28
|
+
|
|
29
|
+
events: ['resize'],
|
|
30
|
+
},
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
export function removeLazyLoad(elements = []) {
|
|
34
|
+
for (const el of elements) {
|
|
35
|
+
el && $$('img[loading="lazy"]', el).forEach((el) => removeAttr(el, 'loading'));
|
|
36
|
+
}
|
|
37
|
+
}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import Class from '../mixin/class';
|
|
2
2
|
import Slider, { speedUp } from '../mixin/slider';
|
|
3
3
|
import SliderReactive from '../mixin/slider-reactive';
|
|
4
|
+
import SliderPreload from './internal/slider-preload';
|
|
4
5
|
import Transitioner, { getMax, getWidth } from './internal/slider-transitioner';
|
|
5
6
|
import {
|
|
6
7
|
$,
|
|
@@ -11,16 +12,14 @@ import {
|
|
|
11
12
|
dimensions,
|
|
12
13
|
findIndex,
|
|
13
14
|
includes,
|
|
14
|
-
isEmpty,
|
|
15
15
|
last,
|
|
16
|
-
sortBy,
|
|
17
16
|
toFloat,
|
|
18
17
|
toggleClass,
|
|
19
18
|
toNumber,
|
|
20
19
|
} from 'uikit-util';
|
|
21
20
|
|
|
22
21
|
export default {
|
|
23
|
-
mixins: [Class, Slider, SliderReactive],
|
|
22
|
+
mixins: [Class, Slider, SliderReactive, SliderPreload],
|
|
24
23
|
|
|
25
24
|
props: {
|
|
26
25
|
center: Boolean,
|
|
@@ -72,48 +71,39 @@ export default {
|
|
|
72
71
|
return ~index ? index : this.length - 1;
|
|
73
72
|
},
|
|
74
73
|
|
|
75
|
-
sets({ sets }) {
|
|
76
|
-
if (!
|
|
74
|
+
sets({ sets: enabled }) {
|
|
75
|
+
if (!enabled) {
|
|
77
76
|
return;
|
|
78
77
|
}
|
|
79
78
|
|
|
80
|
-
const width = dimensions(this.list).width / (this.center ? 2 : 1);
|
|
81
|
-
|
|
82
79
|
let left = 0;
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
const slideWidth = dimensions(slide).width;
|
|
88
|
-
const slideRight = slideLeft + slideWidth;
|
|
80
|
+
const sets = [];
|
|
81
|
+
const width = dimensions(this.list).width;
|
|
82
|
+
for (let i in this.slides) {
|
|
83
|
+
const slideWidth = dimensions(this.slides[i]).width;
|
|
89
84
|
|
|
90
|
-
if (
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
}
|
|
85
|
+
if (left + slideWidth > width) {
|
|
86
|
+
left = 0;
|
|
87
|
+
}
|
|
94
88
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
leftCenter -= slideWidth;
|
|
103
|
-
} else {
|
|
104
|
-
leftCenter = width;
|
|
105
|
-
sets.push(i);
|
|
106
|
-
left = slideLeft + width + (this.center ? slideWidth / 2 : 0);
|
|
107
|
-
}
|
|
89
|
+
if (this.center) {
|
|
90
|
+
if (
|
|
91
|
+
left < width / 2 &&
|
|
92
|
+
left + slideWidth + dimensions(this.slides[+i + 1]).width / 2 > width / 2
|
|
93
|
+
) {
|
|
94
|
+
sets.push(+i);
|
|
95
|
+
left = width / 2 - slideWidth / 2;
|
|
108
96
|
}
|
|
97
|
+
} else if (left === 0) {
|
|
98
|
+
sets.push(Math.min(+i, this.maxIndex));
|
|
109
99
|
}
|
|
110
100
|
|
|
111
|
-
|
|
101
|
+
left += slideWidth;
|
|
102
|
+
}
|
|
112
103
|
|
|
104
|
+
if (sets.length) {
|
|
113
105
|
return sets;
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
return !isEmpty(sets) && sets;
|
|
106
|
+
}
|
|
117
107
|
},
|
|
118
108
|
|
|
119
109
|
transitionOptions() {
|
|
@@ -258,6 +248,25 @@ export default {
|
|
|
258
248
|
|
|
259
249
|
return index;
|
|
260
250
|
},
|
|
251
|
+
|
|
252
|
+
getAdjacentSlides() {
|
|
253
|
+
const { width } = dimensions(this.list);
|
|
254
|
+
const left = -width;
|
|
255
|
+
const right = width * 2;
|
|
256
|
+
const slideWidth = dimensions(this.slides[this.index]).width;
|
|
257
|
+
const slideLeft = this.center ? width / 2 - slideWidth / 2 : 0;
|
|
258
|
+
const slides = new Set();
|
|
259
|
+
for (const i of [-1, 1]) {
|
|
260
|
+
let currentLeft = slideLeft + (i > 0 ? slideWidth : 0);
|
|
261
|
+
let j = 0;
|
|
262
|
+
do {
|
|
263
|
+
const slide = this.slides[this.getIndex(this.index + i + j++ * i)];
|
|
264
|
+
currentLeft += dimensions(slide).width * i;
|
|
265
|
+
slides.add(slide);
|
|
266
|
+
} while (this.slides.length > j && currentLeft > left && currentLeft < right);
|
|
267
|
+
}
|
|
268
|
+
return Array.from(slides);
|
|
269
|
+
},
|
|
261
270
|
},
|
|
262
271
|
};
|
|
263
272
|
|
|
@@ -2,10 +2,11 @@ import Class from '../mixin/class';
|
|
|
2
2
|
import Slideshow from '../mixin/slideshow';
|
|
3
3
|
import Animations from './internal/slideshow-animations';
|
|
4
4
|
import SliderReactive from '../mixin/slider-reactive';
|
|
5
|
+
import SliderPreload from './internal/slider-preload';
|
|
5
6
|
import { boxModelAdjust, css } from 'uikit-util';
|
|
6
7
|
|
|
7
8
|
export default {
|
|
8
|
-
mixins: [Class, Slideshow, SliderReactive],
|
|
9
|
+
mixins: [Class, Slideshow, SliderReactive, SliderPreload],
|
|
9
10
|
|
|
10
11
|
props: {
|
|
11
12
|
ratio: String,
|
|
@@ -50,4 +51,10 @@ export default {
|
|
|
50
51
|
|
|
51
52
|
events: ['resize'],
|
|
52
53
|
},
|
|
54
|
+
|
|
55
|
+
methods: {
|
|
56
|
+
getAdjacentSlides() {
|
|
57
|
+
return [1, -1].map((i) => this.slides[this.getIndex(this.index + i)]);
|
|
58
|
+
},
|
|
59
|
+
},
|
|
53
60
|
};
|
package/src/js/core/icon.js
CHANGED
|
@@ -68,14 +68,14 @@ const Icon = {
|
|
|
68
68
|
},
|
|
69
69
|
|
|
70
70
|
methods: {
|
|
71
|
-
getSvg() {
|
|
71
|
+
async getSvg() {
|
|
72
72
|
const icon = getIcon(this.icon);
|
|
73
73
|
|
|
74
74
|
if (!icon) {
|
|
75
|
-
|
|
75
|
+
throw 'Icon not found.';
|
|
76
76
|
}
|
|
77
77
|
|
|
78
|
-
return
|
|
78
|
+
return icon;
|
|
79
79
|
},
|
|
80
80
|
},
|
|
81
81
|
};
|
|
@@ -137,9 +137,16 @@ export const Close = {
|
|
|
137
137
|
export const Spinner = {
|
|
138
138
|
extends: IconComponent,
|
|
139
139
|
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
140
|
+
methods: {
|
|
141
|
+
async getSvg() {
|
|
142
|
+
const icon = await Icon.methods.getSvg.call(this);
|
|
143
|
+
|
|
144
|
+
if (this.ratio !== 1) {
|
|
145
|
+
css($('circle', icon), 'strokeWidth', 1 / this.ratio);
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
return icon;
|
|
149
|
+
},
|
|
143
150
|
},
|
|
144
151
|
};
|
|
145
152
|
|
package/src/js/core/img.js
CHANGED
|
@@ -1,64 +1,52 @@
|
|
|
1
1
|
import {
|
|
2
|
+
append,
|
|
3
|
+
attr,
|
|
4
|
+
children,
|
|
2
5
|
createEvent,
|
|
3
6
|
css,
|
|
4
|
-
|
|
7
|
+
data,
|
|
5
8
|
escape,
|
|
6
|
-
|
|
9
|
+
fragment,
|
|
10
|
+
hasAttr,
|
|
7
11
|
includes,
|
|
8
|
-
|
|
12
|
+
isArray,
|
|
13
|
+
isEmpty,
|
|
14
|
+
isTag,
|
|
15
|
+
parent,
|
|
16
|
+
parseOptions,
|
|
9
17
|
queryAll,
|
|
18
|
+
removeAttr,
|
|
10
19
|
startsWith,
|
|
11
20
|
toFloat,
|
|
12
21
|
toPx,
|
|
13
22
|
trigger,
|
|
14
23
|
} from 'uikit-util';
|
|
15
24
|
|
|
25
|
+
const nativeLazyLoad = 'loading' in HTMLImageElement.prototype;
|
|
26
|
+
const nativeIsIntersecting = 'isIntersecting' in IntersectionObserverEntry.prototype; // Old chromium based browsers (UC Browser) did not implement `isIntersecting`
|
|
27
|
+
|
|
16
28
|
export default {
|
|
17
29
|
args: 'dataSrc',
|
|
18
30
|
|
|
19
31
|
props: {
|
|
20
32
|
dataSrc: String,
|
|
21
|
-
|
|
22
|
-
sizes: String,
|
|
23
|
-
width: Number,
|
|
24
|
-
height: Number,
|
|
33
|
+
sources: String,
|
|
25
34
|
offsetTop: String,
|
|
26
35
|
offsetLeft: String,
|
|
27
36
|
target: String,
|
|
37
|
+
loading: String,
|
|
28
38
|
},
|
|
29
39
|
|
|
30
40
|
data: {
|
|
31
41
|
dataSrc: '',
|
|
32
|
-
|
|
33
|
-
sizes: false,
|
|
34
|
-
width: false,
|
|
35
|
-
height: false,
|
|
42
|
+
sources: false,
|
|
36
43
|
offsetTop: '50vh',
|
|
37
44
|
offsetLeft: '50vw',
|
|
38
45
|
target: false,
|
|
46
|
+
loading: 'lazy',
|
|
39
47
|
},
|
|
40
48
|
|
|
41
49
|
computed: {
|
|
42
|
-
cacheKey({ dataSrc }) {
|
|
43
|
-
return `${this.$name}.${dataSrc}`;
|
|
44
|
-
},
|
|
45
|
-
|
|
46
|
-
width({ width, dataWidth }) {
|
|
47
|
-
return width || dataWidth;
|
|
48
|
-
},
|
|
49
|
-
|
|
50
|
-
height({ height, dataHeight }) {
|
|
51
|
-
return height || dataHeight;
|
|
52
|
-
},
|
|
53
|
-
|
|
54
|
-
sizes({ sizes, dataSizes }) {
|
|
55
|
-
return sizes || dataSizes;
|
|
56
|
-
},
|
|
57
|
-
|
|
58
|
-
isImg(_, $el) {
|
|
59
|
-
return isImg($el);
|
|
60
|
-
},
|
|
61
|
-
|
|
62
50
|
target: {
|
|
63
51
|
get({ target }) {
|
|
64
52
|
return [this.$el, ...queryAll(target, this.$el)];
|
|
@@ -68,65 +56,61 @@ export default {
|
|
|
68
56
|
this.observe();
|
|
69
57
|
},
|
|
70
58
|
},
|
|
71
|
-
|
|
72
|
-
offsetTop({ offsetTop }) {
|
|
73
|
-
return toPx(offsetTop, 'height');
|
|
74
|
-
},
|
|
75
|
-
|
|
76
|
-
offsetLeft({ offsetLeft }) {
|
|
77
|
-
return toPx(offsetLeft, 'width');
|
|
78
|
-
},
|
|
79
59
|
},
|
|
80
60
|
|
|
81
61
|
connected() {
|
|
82
|
-
if (!window.IntersectionObserver) {
|
|
83
|
-
|
|
62
|
+
if (this.loading !== 'lazy' || !window.IntersectionObserver || !nativeIsIntersecting) {
|
|
63
|
+
this.load();
|
|
84
64
|
return;
|
|
85
65
|
}
|
|
86
66
|
|
|
87
|
-
if (
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
setSrcAttrs(this.$el, getPlaceholderImage(this.width, this.height, this.sizes));
|
|
91
|
-
}
|
|
67
|
+
if (nativeLazyLoad && isImg(this.$el)) {
|
|
68
|
+
this.$el.loading = 'lazy';
|
|
69
|
+
setSrcAttrs(this.$el);
|
|
92
70
|
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
71
|
+
if (this.target.length === 1) {
|
|
72
|
+
return;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
96
75
|
|
|
97
|
-
|
|
76
|
+
ensureSrcAttribute(this.$el);
|
|
77
|
+
|
|
78
|
+
const rootMargin = `${toPx(this.offsetTop, 'height')}px ${toPx(
|
|
79
|
+
this.offsetLeft,
|
|
80
|
+
'width'
|
|
81
|
+
)}px`;
|
|
82
|
+
this.observer = new IntersectionObserver(
|
|
83
|
+
(entries) => {
|
|
84
|
+
if (entries.some((entry) => entry.isIntersecting)) {
|
|
85
|
+
this.load();
|
|
86
|
+
this.observer.disconnect();
|
|
87
|
+
}
|
|
88
|
+
},
|
|
89
|
+
{ rootMargin }
|
|
90
|
+
);
|
|
91
|
+
this.observe();
|
|
98
92
|
},
|
|
99
93
|
|
|
100
94
|
disconnected() {
|
|
101
|
-
|
|
95
|
+
if (this._data.image) {
|
|
96
|
+
this._data.image.onload = '';
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
this.observer?.disconnect();
|
|
102
100
|
},
|
|
103
101
|
|
|
104
102
|
update: {
|
|
105
|
-
|
|
106
|
-
if (!this.observer) {
|
|
103
|
+
write(store) {
|
|
104
|
+
if (!this.observer || isImg(this.$el)) {
|
|
107
105
|
return false;
|
|
108
106
|
}
|
|
109
107
|
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
if (this.isImg) {
|
|
115
|
-
return false;
|
|
116
|
-
}
|
|
117
|
-
|
|
118
|
-
image &&
|
|
119
|
-
image.then(
|
|
120
|
-
(img) => img && img.currentSrc !== '' && setSrcAttrs(this.$el, currentSrc(img))
|
|
121
|
-
);
|
|
122
|
-
},
|
|
123
|
-
|
|
124
|
-
write(data) {
|
|
125
|
-
if (this.dataSrcset && window.devicePixelRatio !== 1) {
|
|
108
|
+
const srcset = data(this.$el, 'data-srcset');
|
|
109
|
+
if (srcset && window.devicePixelRatio !== 1) {
|
|
126
110
|
const bgSize = css(this.$el, 'backgroundSize');
|
|
127
|
-
if (bgSize.match(/^(auto\s?)+$/) || toFloat(bgSize) ===
|
|
128
|
-
|
|
129
|
-
css(this.$el, 'backgroundSize', `${
|
|
111
|
+
if (bgSize.match(/^(auto\s?)+$/) || toFloat(bgSize) === store.bgSize) {
|
|
112
|
+
store.bgSize = getSourceSize(srcset, data(this.$el, 'sizes'));
|
|
113
|
+
css(this.$el, 'backgroundSize', `${store.bgSize}px`);
|
|
130
114
|
}
|
|
131
115
|
}
|
|
132
116
|
},
|
|
@@ -135,24 +119,18 @@ export default {
|
|
|
135
119
|
},
|
|
136
120
|
|
|
137
121
|
methods: {
|
|
138
|
-
load(
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
!entries.some((entry) => isUndefined(entry.isIntersecting) || entry.isIntersecting)
|
|
142
|
-
) {
|
|
143
|
-
return;
|
|
122
|
+
load() {
|
|
123
|
+
if (this._data.image) {
|
|
124
|
+
return this._data.image;
|
|
144
125
|
}
|
|
145
126
|
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
storage[this.cacheKey] = currentSrc(img);
|
|
150
|
-
return img;
|
|
151
|
-
},
|
|
152
|
-
(e) => trigger(this.$el, new e.constructor(e.type, e))
|
|
153
|
-
);
|
|
127
|
+
const image = isImg(this.$el)
|
|
128
|
+
? this.$el
|
|
129
|
+
: getImageFromElement(this.$el, this.dataSrc, this.sources);
|
|
154
130
|
|
|
155
|
-
|
|
131
|
+
removeAttr(image, 'loading');
|
|
132
|
+
setSrcAttrs(this.$el, image.currentSrc);
|
|
133
|
+
return (this._data.image = image);
|
|
156
134
|
},
|
|
157
135
|
|
|
158
136
|
observe() {
|
|
@@ -165,12 +143,11 @@ export default {
|
|
|
165
143
|
},
|
|
166
144
|
};
|
|
167
145
|
|
|
168
|
-
function setSrcAttrs(el, src
|
|
146
|
+
function setSrcAttrs(el, src) {
|
|
169
147
|
if (isImg(el)) {
|
|
170
|
-
const
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
set('src', src);
|
|
148
|
+
const parentNode = parent(el);
|
|
149
|
+
const elements = isPicture(parentNode) ? children(parentNode) : [el];
|
|
150
|
+
elements.forEach((el) => setSourceProps(el, el));
|
|
174
151
|
} else if (src) {
|
|
175
152
|
const change = !includes(el.style.backgroundImage, src);
|
|
176
153
|
if (change) {
|
|
@@ -180,16 +157,62 @@ function setSrcAttrs(el, src, srcset, sizes) {
|
|
|
180
157
|
}
|
|
181
158
|
}
|
|
182
159
|
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
160
|
+
const srcProps = ['data-src', 'data-srcset', 'sizes'];
|
|
161
|
+
function setSourceProps(sourceEl, targetEl) {
|
|
162
|
+
srcProps.forEach((prop) => {
|
|
163
|
+
const value = data(sourceEl, prop);
|
|
164
|
+
if (value) {
|
|
165
|
+
attr(targetEl, prop.replace(/^(data-)+/, ''), value);
|
|
166
|
+
}
|
|
167
|
+
});
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
function getImageFromElement(el, src, sources) {
|
|
171
|
+
const img = new Image();
|
|
172
|
+
|
|
173
|
+
wrapInPicture(img, sources);
|
|
174
|
+
setSourceProps(el, img);
|
|
175
|
+
img.onload = () => {
|
|
176
|
+
setSrcAttrs(el, img.currentSrc);
|
|
177
|
+
};
|
|
178
|
+
attr(img, 'src', src);
|
|
179
|
+
return img;
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
function wrapInPicture(img, sources) {
|
|
183
|
+
sources = parseSources(sources);
|
|
184
|
+
|
|
185
|
+
if (sources.length) {
|
|
186
|
+
const picture = fragment('<picture>');
|
|
187
|
+
for (const attrs of sources) {
|
|
188
|
+
const source = fragment('<source>');
|
|
189
|
+
attr(source, attrs);
|
|
190
|
+
append(picture, source);
|
|
191
|
+
}
|
|
192
|
+
append(picture, img);
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
|
|
196
|
+
function parseSources(sources) {
|
|
197
|
+
if (!sources) {
|
|
198
|
+
return [];
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
if (startsWith(sources, '[')) {
|
|
202
|
+
try {
|
|
203
|
+
sources = JSON.parse(sources);
|
|
204
|
+
} catch (e) {
|
|
205
|
+
sources = [];
|
|
206
|
+
}
|
|
207
|
+
} else {
|
|
208
|
+
sources = parseOptions(sources);
|
|
190
209
|
}
|
|
191
210
|
|
|
192
|
-
|
|
211
|
+
if (!isArray(sources)) {
|
|
212
|
+
sources = [sources];
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
return sources.filter((source) => !isEmpty(source));
|
|
193
216
|
}
|
|
194
217
|
|
|
195
218
|
const sizesRe = /\s*(.*?)\s*(\w+|calc\(.*?\))\s*(?:,|$)/g;
|
|
@@ -229,22 +252,16 @@ function getSourceSize(srcset, sizes) {
|
|
|
229
252
|
return descriptors.filter((size) => size >= srcSize)[0] || descriptors.pop() || '';
|
|
230
253
|
}
|
|
231
254
|
|
|
232
|
-
function
|
|
233
|
-
|
|
255
|
+
function ensureSrcAttribute(el) {
|
|
256
|
+
if (isImg(el) && !hasAttr(el, 'src')) {
|
|
257
|
+
attr(el, 'src', 'data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg"></svg>');
|
|
258
|
+
}
|
|
234
259
|
}
|
|
235
260
|
|
|
236
|
-
function
|
|
237
|
-
return el
|
|
261
|
+
function isPicture(el) {
|
|
262
|
+
return isTag(el, 'picture');
|
|
238
263
|
}
|
|
239
264
|
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
// workaround for Safari's private browsing mode and accessing sessionStorage in Blink
|
|
244
|
-
try {
|
|
245
|
-
storage = window.sessionStorage || {};
|
|
246
|
-
storage[key] = 1;
|
|
247
|
-
delete storage[key];
|
|
248
|
-
} catch (e) {
|
|
249
|
-
storage = {};
|
|
265
|
+
function isImg(el) {
|
|
266
|
+
return isTag(el, 'img');
|
|
250
267
|
}
|