PluginProbe
Jetpack – WP Security, Backup, Speed, & Growth / 16.3
Jetpack – WP Security, Backup, Speed, & Growth v16.3
16.3 16.3-beta 16.3-a.5 16.3-a.7 16.3-a.3 16.3-a.1 16.2 16.2-beta 12.0.3 12.1.3 12.2.3 12.3.2 12.4.2 12.5.2 12.6.4 12.7.3 12.8.3 12.9.5 13.0.2 13.1.5 13.2.4 13.3.3 13.4.5 13.5.2 13.6.2 All 508 releases
jetpack / modules / shortcodes / js / slideshow-shortcode.js

slideshow-shortcode.js in Jetpack – WP Security, Backup, Speed, & Growth 16.3, at modules/shortcodes/js/slideshow-shortcode.js

246 lines 7.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 /* global jetpackSlideshowSettings */
2
3 /**
4 * Turn a gallery caption into the plain text it is meant to be.
5 *
6 * A caption is meant to read as text, but wptexturize() leaves HTML entities behind, so it needs
7 * decoding before it can be set as one.
8 *
9 * @param {*} caption - Caption value from the gallery data.
10 * @return {string} The decoded caption, as text.
11 */
12 function jetpackSlideshowCaptionText( caption ) {
13 if ( typeof caption !== 'string' || '' === caption ) {
14 return '';
15 }
16
17 var parsed = new DOMParser().parseFromString( caption, 'text/html' );
18
19 // These land in the body when they appear mid-caption, and their source is not caption text.
20 parsed.body
21 .querySelectorAll( 'script, style, noscript, template' )
22 .forEach( function ( element ) {
23 element.remove();
24 } );
25
26 // Without a space in its place, a caption broken over two lines reads as "Ada LovelaceLondon".
27 parsed.body.querySelectorAll( 'br' ).forEach( function ( element ) {
28 element.replaceWith( ' ' );
29 } );
30
31 return parsed.body.textContent;
32 }
33
34 function JetpackSlideshow( element, transition, autostart ) {
35 this.element = element;
36 this.images = [];
37 this.controls = {};
38 this.transition = transition || 'fade';
39 this.autostart = autostart;
40 }
41
42 JetpackSlideshow.prototype.showLoadingImage = function ( toggle ) {
43 if ( toggle ) {
44 this.loadingImage_ = document.createElement( 'div' );
45 this.loadingImage_.className = 'jetpack-slideshow-loading';
46 var img = document.createElement( 'img' );
47 img.src = jetpackSlideshowSettings.spinner;
48 this.loadingImage_.appendChild( img );
49 this.loadingImage_.appendChild( this.makeZeroWidthSpan() );
50 this.element.append( this.loadingImage_ );
51 } else if ( this.loadingImage_ ) {
52 this.loadingImage_.parentNode.removeChild( this.loadingImage_ );
53 this.loadingImage_ = null;
54 }
55 };
56
57 JetpackSlideshow.prototype.init = function () {
58 this.showLoadingImage( true );
59
60 var self = this;
61 // Set up DOM.
62 for ( var i = 0; i < this.images.length; i++ ) {
63 var imageInfo = this.images[ i ];
64 var img = document.createElement( 'img' );
65 img.src = imageInfo.src;
66 img.title = typeof imageInfo.title !== 'undefined' ? imageInfo.title : '';
67 img.alt = typeof imageInfo.alt !== 'undefined' ? imageInfo.alt : '';
68 img.setAttribute( 'itemprop', 'image' );
69 img.nopin = 'nopin';
70 var caption = document.createElement( 'div' );
71 caption.className = 'jetpack-slideshow-slide-caption';
72 caption.setAttribute( 'itemprop', 'caption description' );
73 caption.textContent = jetpackSlideshowCaptionText( imageInfo.caption );
74 var container = document.createElement( 'div' );
75 container.className = 'jetpack-slideshow-slide';
76 container.setAttribute( 'itemprop', 'associatedMedia' );
77 container.setAttribute( 'itemscope', '' );
78 container.setAttribute( 'itemtype', 'https://schema.org/ImageObject' );
79
80 // Hide loading image once first image has loaded.
81 if ( i === 0 ) {
82 if ( img.complete ) {
83 // IE, image in cache
84 setTimeout( function () {
85 self.finishInit_();
86 }, 1 );
87 } else {
88 img.addEventListener( 'load', function () {
89 self.finishInit_();
90 } );
91 }
92 }
93 container.appendChild( img );
94 // I'm not sure where these were coming from, but IE adds
95 // bad values for width/height for portrait-mode images
96 img.removeAttribute( 'width' );
97 img.removeAttribute( 'height' );
98 container.appendChild( this.makeZeroWidthSpan() );
99 container.appendChild( caption );
100 this.element.append( container );
101 }
102 };
103
104 JetpackSlideshow.prototype.makeZeroWidthSpan = function () {
105 var emptySpan = document.createElement( 'span' );
106 emptySpan.className = 'jetpack-slideshow-line-height-hack';
107 // Having a NBSP makes IE act weird during transitions, but other
108 // browsers ignore a text node with a space in it as whitespace.
109 if ( -1 !== window.navigator.userAgent.indexOf( 'MSIE ' ) ) {
110 emptySpan.appendChild( document.createTextNode( ' ' ) );
111 } else {
112 emptySpan.innerHTML = '&nbsp;';
113 }
114 return emptySpan;
115 };
116
117 JetpackSlideshow.prototype.finishInit_ = function () {
118 this.showLoadingImage( false );
119
120 var self = this;
121 if ( this.images.length > 1 ) {
122 this.renderControls_();
123
124 // Initialize Cycle instance.
125 jQuery( this.element ).cycle( {
126 fx: this.transition,
127 prev: this.controls.prev,
128 next: this.controls.next,
129 timeout: jetpackSlideshowSettings.speed,
130 slideExpr: '.jetpack-slideshow-slide',
131 onPrevNextEvent: function () {
132 return self.onCyclePrevNextClick_.apply( self, arguments );
133 },
134 } );
135
136 var slideshow = this.element;
137
138 if ( ! this.autostart ) {
139 jQuery( slideshow ).cycle( 'pause' );
140 this.controls.stop.classList.remove( 'running' );
141 this.controls.stop.classList.add( 'paused' );
142 }
143
144 this.controls.stop.addEventListener( 'click', function ( event ) {
145 var button = event.currentTarget;
146
147 if ( button === event.target ) {
148 event.preventDefault();
149
150 if ( ! button.classList.contains( 'paused' ) ) {
151 jQuery( slideshow ).cycle( 'pause' );
152 button.classList.remove( 'running' );
153 button.classList.add( 'paused' );
154 } else {
155 button.classList.add( 'running' );
156 button.classList.remove( 'paused' );
157 jQuery( slideshow ).cycle( 'resume', true );
158 }
159 }
160 } );
161 } else if ( this.element.children.length ) {
162 this.element.children[ 0 ].style.display = 'block';
163 this.element.style.position = 'relative';
164 }
165 this.initialized_ = true;
166 };
167
168 JetpackSlideshow.prototype.renderControls_ = function () {
169 if ( this.controlsDiv_ ) {
170 return;
171 }
172
173 var controlsDiv = document.createElement( 'div' );
174 controlsDiv.className = 'jetpack-slideshow-controls';
175
176 var controls = [ 'prev', 'stop', 'next' ];
177 for ( var i = 0; i < controls.length; i++ ) {
178 var controlName = controls[ i ];
179 var label_name = 'label_' + controlName;
180 var a = document.createElement( 'a' );
181
182 a.href = '#';
183 a.className = 'button-' + controlName;
184 a.setAttribute( 'aria-label', jetpackSlideshowSettings[ label_name ] );
185 a.setAttribute( 'role', 'button' );
186
187 controlsDiv.appendChild( a );
188 this.controls[ controlName ] = a;
189 }
190 this.element.append( controlsDiv );
191 this.controlsDiv_ = controlsDiv;
192 };
193
194 JetpackSlideshow.prototype.onCyclePrevNextClick_ = function ( isNext, i /*, slideElement*/ ) {
195 // If blog_id not present don't track page views
196 if ( ! jetpackSlideshowSettings.blog_id ) {
197 return;
198 }
199
200 var postid = this.images[ i ].id;
201 var stats = new Image();
202 stats.src =
203 document.location.protocol +
204 '//pixel.wp.com/g.gif?host=' +
205 encodeURIComponent( document.location.host ) +
206 '&rand=' +
207 Math.random() +
208 '&blog=' +
209 jetpackSlideshowSettings.blog_id +
210 '&subd=' +
211 jetpackSlideshowSettings.blog_subdomain +
212 '&user_id=' +
213 jetpackSlideshowSettings.user_id +
214 '&post=' +
215 postid +
216 '&ref=' +
217 encodeURIComponent( document.location );
218 };
219
220 ( function () {
221 function jetpack_slideshow_init() {
222 document.querySelectorAll( '.jetpack-slideshow-noscript' ).forEach( function ( element ) {
223 element.remove();
224 } );
225 document.querySelectorAll( '.jetpack-slideshow' ).forEach( function ( container ) {
226 if ( container.dataset.processed === 'true' ) {
227 return;
228 }
229
230 // Extract data attributes manually
231 var transition = container.dataset.trans;
232 var autostart = container.dataset.autostart === 'true';
233 var gallery = JSON.parse( container.dataset.gallery || '[]' );
234
235 var slideshow = new JetpackSlideshow( container, transition, autostart );
236 slideshow.images = gallery;
237 slideshow.init();
238
239 container.dataset.processed = 'true';
240 } );
241 }
242
243 document.addEventListener( 'DOMContentLoaded', jetpack_slideshow_init );
244 document.body.addEventListener( 'post-load', jetpack_slideshow_init );
245 } )();
246