PluginProbe ʕ •ᴥ•ʔ
Jetpack – WP Security, Backup, Speed, & Growth / 6.5.4
Jetpack – WP Security, Backup, Speed, & Growth v6.5.4
15.9-a.7 15.9-a.5 15.9-a.3 15.9-a.1 15.8 15.8-beta 15.8-a.7 15.8-a.5 5.2.5 5.3.4 5.4.4 5.5.5 5.6.5 5.7.5 5.8.4 5.9.4 6.0.4 6.1 6.1.1 6.1.2 6.1.3 6.1.4 6.1.5 6.2 6.2.1 6.2.2 6.2.3 6.2.4 6.2.5 6.3 6.3.1 6.3.2 6.3.3 6.3.4 6.3.5 6.3.6 6.3.7 6.4 6.4.1 6.4.2 6.4.3 6.4.4 6.4.5 6.4.6 6.5 6.5.1 6.5.2 6.5.3 6.5.4 6.6 6.6.1 6.6.2 6.6.3 6.6.4 6.6.5 6.7 6.7.1 6.7.2 6.7.3 6.7.4 6.8 6.8.1 6.8.2 6.8.3 6.8.4 6.8.5 6.9 6.9.1 6.9.2 6.9.3 6.9.4 7.0 7.0.1 7.0.2 7.0.3 7.0.4 7.0.5 7.1 7.1.1 7.1.2 7.1.3 7.1.4 7.1.5 7.2 7.2.1 7.2.1.1 7.2.2 7.2.3 7.2.4 7.2.5 7.3 7.3.0.1 7.3.1 7.3.1.1 7.3.2 7.3.3 7.3.4 7.3.5 7.4 7.4.1 7.4.2 7.4.3 7.4.4 7.4.5 7.5 7.5.0.1 7.5.1 7.5.2 7.5.3 7.5.4 7.5.5 7.5.6 7.5.7 7.6 7.6.1 7.6.2 7.6.3 7.6.4 7.7 7.7.1 7.7.2 7.7.3 7.7.4 7.7.5 7.7.6 7.8 7.8.1 7.8.2 7.8.3 7.8.4 7.9 7.9.1 7.9.2 7.9.3 7.9.4 8.0 8.0.1 8.0.2 8.0.3 8.1 8.1.1 8.1.2 8.1.3 8.1.4 8.2 8.2.0.1 8.2.1 8.2.2 8.2.3 8.2.4 8.2.5 8.2.6 8.3 8.3.1 8.3.2 8.3.3 8.4 8.4.1 8.4.2 8.4.3 8.4.4 8.4.5 8.5 8.5.1 8.5.2 8.5.3 8.6 8.6.1 8.6.2 8.6.3 8.6.4 8.7 8.7.0.1 8.7.1 8.7.2 8.7.3 8.7.4 8.8 8.8.1 8.8.2 8.8.3 8.8.4 8.8.5 8.9 8.9.1 8.9.2 8.9.3 8.9.4 9.0 9.0.1 9.0.2 9.0.3 9.0.4 9.0.5 9.1 9.1.1 9.1.2 9.1.3 9.2 9.2.1 9.2.2 9.2.3 9.2.4 9.3 9.3.1 9.3.2 9.3.3 9.3.4 9.3.5 9.4 9.4.1 9.4.2 9.4.3 9.4.4 9.5 9.5.1 9.5.2 9.5.3 9.5.4 9.5.5 9.6 9.6.1 9.6.2 9.6.3 9.6.4 9.7 9.7.1 9.7.2 15.7-beta.2 9.7.3 15.7.1 9.8 15.8-a.1 9.8.1 15.8-a.3 9.8.2 2.0.9 9.8.3 2.1.7 9.9 2.2.10 9.9.1 2.3.10 9.9.2 2.4.7 9.9.3 2.5.5 2.6.6 2.7.5 2.8.5 2.9.6 3.0.6 3.1.5 3.2.5 3.3.6 3.4.6 3.5.6 3.6.4 3.7.5 3.8.5 3.9.10 4.0.7 4.1.4 4.2.5 4.3.5 4.4.5 4.5.3 4.6.3 4.7.4 4.8.5 4.9.3 5.0.3 5.1.4 trunk 10.0 10.0.1 10.0.2 10.1 10.1.1 10.1.2 10.2 10.2.1 10.2.2 10.2.3 10.3 10.3.1 10.3.2 10.4 10.4.1 10.4.2 10.5 10.5.1 10.5.2 10.5.3 10.6 10.6.1 10.6.2 10.7 10.7.1 10.7.2 10.8 10.8.1 10.8.2 10.9 10.9.1 10.9.2 10.9.3 11.0 11.0.1 11.0.2 11.1 11.1.1 11.1.2 11.1.3 11.1.4 11.2 11.2.1 11.2.2 11.3 11.3.1 11.3.2 11.3.3 11.3.4 11.4 11.4.1 11.4.2 11.5 11.5.1 11.5.2 11.5.3 11.6 11.6.1 11.6.2 11.7 11.7.1 11.7.2 11.7.3 11.8 11.8.3 11.8.4 11.8.5 11.8.6 11.9 11.9.1 11.9.2 11.9.3 12.0 12.0.1 12.0.2 12.1 12.1.1 12.1.2 12.2 12.2.1 12.2.2 12.3 12.3.1 12.4 12.4.1 12.5 12.5.1 12.6 12.6.1 12.6.2 12.6.3 12.7 12.7.1 12.7.2 12.8 12.8.1 12.8.2 12.9 12.9.1 12.9.2 12.9.3 12.9.4 13.0 13.0.1 13.1 13.1.1 13.1.2 13.1.3 13.1.4 13.2 13.2.1 13.2.2 13.2.3 13.3 13.3.1 13.3.2 13.4 13.4.1 13.4.2 13.4.3 13.4.4 13.5 13.5.1 13.6 13.6.1 13.7 13.7.1 13.8 13.8.1 13.8.2 13.9 13.9.1 14.0 14.1 14.2 14.2.1 14.3 14.4 14.4.1 14.5 14.6 14.7 14.8 14.9 14.9.1 15.0 15.0.1 15.0.2 15.1 15.1.1 15.2 15.3 15.3.1 15.4 15.5 15.6 15.7 15.7-a.1 15.7-a.3 15.7-a.5 15.7-a.7 15.7-beta
jetpack / class.jetpack-post-images.php
jetpack Last commit date
3rd-party 7 years ago _inc 1 year ago bin 7 years ago css 7 years ago images 1 year ago json-endpoints 3 years ago languages 7 years ago modules 1 year ago sal 7 years ago scss 7 years ago sync 7 years ago views 8 years ago .svnignore 12 years ago CODE-OF-CONDUCT.md 9 years ago changelog.txt 7 years ago class.frame-nonce-preview.php 9 years ago class.jetpack-admin.php 8 years ago class.jetpack-autoupdate.php 8 years ago class.jetpack-bbpress-json-api-compat.php 9 years ago class.jetpack-cli.php 7 years ago class.jetpack-client-server.php 8 years ago class.jetpack-client.php 7 years ago class.jetpack-connection-banner.php 7 years ago class.jetpack-constants.php 8 years ago class.jetpack-data.php 7 years ago class.jetpack-debugger.php 8 years ago class.jetpack-error.php 10 years ago class.jetpack-heartbeat.php 7 years ago class.jetpack-idc.php 8 years ago class.jetpack-ixr-client.php 10 years ago class.jetpack-jitm.php 8 years ago class.jetpack-modules-list-table.php 8 years ago class.jetpack-network-sites-list-table.php 9 years ago class.jetpack-network.php 8 years ago class.jetpack-options.php 7 years ago class.jetpack-post-images.php 7 years ago class.jetpack-signature.php 7 years ago class.jetpack-tracks.php 8 years ago class.jetpack-twitter-cards.php 7 years ago class.jetpack-user-agent.php 8 years ago class.jetpack-xmlrpc-server.php 7 years ago class.jetpack.php 7 years ago class.json-api-endpoints.php 3 years ago class.json-api.php 7 years ago class.photon.php 7 years ago composer.json 7 years ago functions.compat.php 7 years ago functions.gallery.php 8 years ago functions.global.php 7 years ago functions.opengraph.php 8 years ago functions.photon.php 8 years ago jetpack.php 1 year ago json-api-config.php 10 years ago json-endpoints.php 8 years ago locales.php 9 years ago phpcs.xml 7 years ago readme.txt 1 year ago require-lib.php 8 years ago uninstall.php 8 years ago wpml-config.xml 10 years ago
class.jetpack-post-images.php
657 lines
1 <?php
2
3 /**
4 * Useful for finding an image to display alongside/in representation of a specific post.
5 *
6 * Includes a few different methods, all of which return a similar-format array containing
7 * details of any images found. Everything can (should) be called statically, it's just a
8 * function-bucket. You can also call Jetpack_PostImages::get_image() to cycle through all of the methods until
9 * one of them finds something useful.
10 *
11 * This file is included verbatim in Jetpack
12 */
13 class Jetpack_PostImages {
14 /**
15 * If a slideshow is embedded within a post, then parse out the images involved and return them
16 */
17 static function from_slideshow( $post_id, $width = 200, $height = 200 ) {
18 $images = array();
19
20 $post = get_post( $post_id );
21
22 if ( ! $post ) {
23 return $images;
24 }
25
26 if ( ! empty( $post->post_password ) ) {
27 return $images;
28 }
29
30 if ( false === has_shortcode( $post->post_content, 'slideshow' ) ) {
31 return $images; // no slideshow - bail
32 }
33
34 $permalink = get_permalink( $post->ID );
35
36 // Mechanic: Somebody set us up the bomb
37 $old_post = $GLOBALS['post'];
38 $GLOBALS['post'] = $post;
39 $old_shortcodes = $GLOBALS['shortcode_tags'];
40 $GLOBALS['shortcode_tags'] = array( 'slideshow' => $old_shortcodes['slideshow'] );
41
42 // Find all the slideshows
43 preg_match_all( '/' . get_shortcode_regex() . '/sx', $post->post_content, $slideshow_matches, PREG_SET_ORDER );
44
45 ob_start(); // The slideshow shortcode handler calls wp_print_scripts and wp_print_styles... not too happy about that
46
47 foreach ( $slideshow_matches as $slideshow_match ) {
48 $slideshow = do_shortcode_tag( $slideshow_match );
49 if ( false === $pos = stripos( $slideshow, 'jetpack-slideshow' ) ) // must be something wrong - or we changed the output format in which case none of the following will work
50 continue;
51 $start = strpos( $slideshow, '[', $pos );
52 $end = strpos( $slideshow, ']', $start );
53 $post_images = json_decode( wp_specialchars_decode( str_replace( "'", '"', substr( $slideshow, $start, $end - $start + 1 ) ), ENT_QUOTES ) ); // parse via JSON
54 // If the JSON didn't decode don't try and act on it.
55 if ( is_array( $post_images ) ) {
56 foreach ( $post_images as $post_image ) {
57 if ( !$post_image_id = absint( $post_image->id ) )
58 continue;
59
60 $meta = wp_get_attachment_metadata( $post_image_id );
61
62 // Must be larger than 200x200 (or user-specified)
63 if ( !isset( $meta['width'] ) || $meta['width'] < $width )
64 continue;
65 if ( !isset( $meta['height'] ) || $meta['height'] < $height )
66 continue;
67
68 $url = wp_get_attachment_url( $post_image_id );
69
70 $images[] = array(
71 'type' => 'image',
72 'from' => 'slideshow',
73 'src' => $url,
74 'src_width' => $meta['width'],
75 'src_height' => $meta['height'],
76 'href' => $permalink,
77 );
78 }
79 }
80 }
81 ob_end_clean();
82
83 // Operator: Main screen turn on
84 $GLOBALS['shortcode_tags'] = $old_shortcodes;
85 $GLOBALS['post'] = $old_post;
86
87 return $images;
88 }
89
90 /**
91 * If a gallery is detected, then get all the images from it.
92 */
93 static function from_gallery( $post_id ) {
94 $images = array();
95
96 $post = get_post( $post_id );
97
98 if ( ! $post ) {
99 return $images;
100 }
101
102 if ( ! empty( $post->post_password ) ) {
103 return $images;
104 }
105
106 $permalink = get_permalink( $post->ID );
107
108 /**
109 * Juggle global post object because the gallery shortcode uses the
110 * global object.
111 *
112 * See core ticket:
113 * https://core.trac.wordpress.org/ticket/39304
114 */
115 if ( isset( $GLOBALS['post'] ) ) {
116 $juggle_post = $GLOBALS['post'];
117 $GLOBALS['post'] = $post;
118 $galleries = get_post_galleries( $post->ID, false );
119 $GLOBALS['post'] = $juggle_post;
120 } else {
121 $GLOBALS['post'] = $post;
122 $galleries = get_post_galleries( $post->ID, false );
123 unset( $GLOBALS['post'] );
124 }
125
126 foreach ( $galleries as $gallery ) {
127 if ( isset( $gallery['type'] ) && 'slideshow' === $gallery['type'] && ! empty( $gallery['ids'] ) ) {
128 $image_ids = explode( ',', $gallery['ids'] );
129 $image_size = isset( $gallery['size'] ) ? $gallery['size'] : 'thumbnail';
130 foreach ( $image_ids as $image_id ) {
131 $image = wp_get_attachment_image_src( $image_id, $image_size );
132 if ( ! empty( $image[0] ) ) {
133 list( $raw_src ) = explode( '?', $image[0] ); // pull off any Query string (?w=250)
134 $raw_src = wp_specialchars_decode( $raw_src ); // rawify it
135 $raw_src = esc_url_raw( $raw_src ); // clean it
136 $images[] = array(
137 'type' => 'image',
138 'from' => 'gallery',
139 'src' => $raw_src,
140 'href' => $permalink,
141 );
142 }
143 }
144 } elseif ( ! empty( $gallery['src'] ) ) {
145 foreach ( $gallery['src'] as $src ) {
146 list( $raw_src ) = explode( '?', $src ); // pull off any Query string (?w=250)
147 $raw_src = wp_specialchars_decode( $raw_src ); // rawify it
148 $raw_src = esc_url_raw( $raw_src ); // clean it
149 $images[] = array(
150 'type' => 'image',
151 'from' => 'gallery',
152 'src' => $raw_src,
153 'href' => $permalink,
154 );
155 }
156 }
157 }
158
159 return $images;
160 }
161
162 /**
163 * Get attachment images for a specified post and return them. Also make sure
164 * their dimensions are at or above a required minimum.
165 */
166 static function from_attachment( $post_id, $width = 200, $height = 200 ) {
167 $images = array();
168
169 $post = get_post( $post_id );
170
171 if ( ! empty( $post->post_password ) ) {
172 return $images;
173 }
174
175 $post_images = get_posts( array(
176 'post_parent' => $post_id, // Must be children of post
177 'numberposts' => 5, // No more than 5
178 'post_type' => 'attachment', // Must be attachments
179 'post_mime_type' => 'image', // Must be images
180 'suppress_filters' => false,
181 ) );
182
183 if ( ! $post_images ) {
184 return $images;
185 }
186
187 $permalink = get_permalink( $post_id );
188
189 foreach ( $post_images as $post_image ) {
190 $meta = wp_get_attachment_metadata( $post_image->ID );
191 // Must be larger than 200x200
192 if ( !isset( $meta['width'] ) || $meta['width'] < $width )
193 continue;
194 if ( !isset( $meta['height'] ) || $meta['height'] < $height )
195 continue;
196
197 $url = wp_get_attachment_url( $post_image->ID );
198
199 $images[] = array(
200 'type' => 'image',
201 'from' => 'attachment',
202 'src' => $url,
203 'src_width' => $meta['width'],
204 'src_height' => $meta['height'],
205 'href' => $permalink,
206 );
207 }
208
209 /*
210 * We only want to pass back attached images that were actually inserted.
211 * We can load up all the images found in the HTML source and then
212 * compare URLs to see if an image is attached AND inserted.
213 */
214 $html_images = self::from_html( $post_id );
215 $inserted_images = array();
216
217 foreach( $html_images as $html_image ) {
218 $src = parse_url( $html_image['src'] );
219 // strip off any query strings from src
220 if( ! empty( $src['scheme'] ) && ! empty( $src['host'] ) ) {
221 $inserted_images[] = $src['scheme'] . '://' . $src['host'] . $src['path'];
222 } elseif( ! empty( $src['host'] ) ) {
223 $inserted_images[] = set_url_scheme( 'http://' . $src['host'] . $src['path'] );
224 } else {
225 $inserted_images[] = site_url( '/' ) . $src['path'];
226 }
227 }
228 foreach( $images as $i => $image ) {
229 if ( !in_array( $image['src'], $inserted_images ) )
230 unset( $images[$i] );
231 }
232
233 return $images;
234 }
235
236 /**
237 * Check if a Featured Image is set for this post, and return it in a similar
238 * format to the other images?_from_*() methods.
239 * @param int $post_id The post ID to check
240 * @return Array containing details of the Featured Image, or empty array if none.
241 */
242 static function from_thumbnail( $post_id, $width = 200, $height = 200 ) {
243 $images = array();
244
245 $post = get_post( $post_id );
246
247 if ( ! empty( $post->post_password ) ) {
248 return $images;
249 }
250
251 if ( ! function_exists( 'get_post_thumbnail_id' ) ) {
252 return $images;
253 }
254
255 $thumb = get_post_thumbnail_id( $post_id );
256
257 if ( $thumb ) {
258 $meta = wp_get_attachment_metadata( $thumb );
259 // Must be larger than requested minimums
260 if ( !isset( $meta['width'] ) || $meta['width'] < $width )
261 return $images;
262 if ( !isset( $meta['height'] ) || $meta['height'] < $height )
263 return $images;
264
265 $too_big = ( ( ! empty( $meta['width'] ) && $meta['width'] > 1200 ) || ( ! empty( $meta['height'] ) && $meta['height'] > 1200 ) );
266
267 if (
268 $too_big &&
269 (
270 ( method_exists( 'Jetpack', 'is_module_active' ) && Jetpack::is_module_active( 'photon' ) ) ||
271 ( defined( 'IS_WPCOM' ) && IS_WPCOM )
272 )
273 ) {
274 $img_src = wp_get_attachment_image_src( $thumb, array( 1200, 1200 ) );
275 } else {
276 $img_src = wp_get_attachment_image_src( $thumb, 'full' );
277 }
278 if ( ! is_array( $img_src ) ) {
279 // If wp_get_attachment_image_src returns false but we know that there should be an image that could be used.
280 // we try a bit harder and user the data that we have.
281 $thumb_post_data = get_post( $thumb );
282 $img_src = array( $thumb_post_data->guid, $meta['width'], $meta['height'] );
283 }
284
285 $url = $img_src[0];
286 $images = array( array( // Other methods below all return an array of arrays
287 'type' => 'image',
288 'from' => 'thumbnail',
289 'src' => $url,
290 'src_width' => $img_src[1],
291 'src_height' => $img_src[2],
292 'href' => get_permalink( $thumb ),
293 ) );
294
295 }
296
297 if ( empty( $images ) && ( defined( 'IS_WPCOM' ) && IS_WPCOM ) ) {
298 $meta_thumbnail = get_post_meta( $post_id, '_jetpack_post_thumbnail', true );
299 if ( ! empty( $meta_thumbnail ) ) {
300 if ( ! isset( $meta_thumbnail['width'] ) || $meta_thumbnail['width'] < $width ) {
301 return $images;
302 }
303
304 if ( ! isset( $meta_thumbnail['height'] ) || $meta_thumbnail['height'] < $height ) {
305 return $images;
306 }
307
308 $images = array( array( // Other methods below all return an array of arrays
309 'type' => 'image',
310 'from' => 'thumbnail',
311 'src' => $meta_thumbnail['URL'],
312 'src_width' => $meta_thumbnail['width'],
313 'src_height' => $meta_thumbnail['height'],
314 'href' => $meta_thumbnail['URL'],
315 ) );
316 }
317 }
318
319 return $images;
320 }
321
322 /**
323 * Very raw -- just parse the HTML and pull out any/all img tags and return their src
324 *
325 * @param mixed $html_or_id The HTML string to parse for images, or a post id.
326 * @param int $width Minimum Image width.
327 * @param int $height Minimum Image height.
328 *
329 * @uses DOMDocument
330 *
331 * @return Array containing images
332 */
333 static function from_html( $html_or_id, $width = 200, $height = 200 ) {
334 $images = array();
335
336 if ( is_numeric( $html_or_id ) ) {
337 $post = get_post( $html_or_id );
338
339 if ( empty( $post ) || ! empty( $post->post_password ) ) {
340 return $images;
341 }
342
343 $html = $post->post_content; // DO NOT apply the_content filters here, it will cause loops.
344 } else {
345 $html = $html_or_id;
346 }
347
348 if ( ! $html ) {
349 return $images;
350 }
351
352 // Do not go any further if DOMDocument is disabled on the server.
353 if ( ! class_exists( 'DOMDocument' ) ) {
354 return $images;
355 }
356
357 // Let's grab all image tags from the HTML.
358 $dom_doc = new DOMDocument;
359
360 // The @ is not enough to suppress errors when dealing with libxml,
361 // we have to tell it directly how we want to handle errors.
362 libxml_use_internal_errors( true );
363 @$dom_doc->loadHTML( $html );
364 libxml_use_internal_errors( false );
365
366 $image_tags = $dom_doc->getElementsByTagName( 'img' );
367
368 // For each image Tag, make sure it can be added to the $images array, and add it.
369 foreach ( $image_tags as $image_tag ) {
370 $img_src = $image_tag->getAttribute( 'src' );
371
372 if ( empty( $img_src ) ) {
373 continue;
374 }
375
376 // Do not grab smiley images that were automatically created by WP when entering text smilies.
377 if ( stripos( $img_src, '/smilies/' ) ) {
378 continue;
379 }
380
381 $meta = array(
382 'width' => (int) $image_tag->getAttribute( 'width' ),
383 'height' => (int) $image_tag->getAttribute( 'height' ),
384 );
385
386 /**
387 * Filters the switch to ignore minimum image size requirements. Can be used
388 * to add custom logic to image dimensions, like only enforcing one of the dimensions,
389 * or disabling it entirely.
390 *
391 * @since 6.4.0
392 *
393 * @param bool $ignore Should the image dimensions be ignored?
394 * @param array $meta Array containing image dimensions parsed from the markup.
395 */
396 $ignore_dimensions = apply_filters( 'jetpack_postimages_ignore_minimum_dimensions', false, $meta );
397
398 // Must be larger than 200x200 (or user-specified).
399 if (
400 ! $ignore_dimensions
401 && (
402 empty( $meta['width'] )
403 || empty( $meta['height'] )
404 || $meta['width'] < $width
405 || $meta['height'] < $height
406 )
407 ) {
408 continue;
409 }
410
411 $images[] = array(
412 'type' => 'image',
413 'from' => 'html',
414 'src' => $img_src,
415 'src_width' => $meta['width'],
416 'src_height' => $meta['height'],
417 'href' => '', // No link to apply to these. Might potentially parse for that as well, but not for now.
418 );
419 }
420 return $images;
421 }
422
423 /**
424 * @param int $post_id The post ID to check
425 * @param int $size
426 * @return Array containing details of the image, or empty array if none.
427 */
428 static function from_blavatar( $post_id, $size = 96 ) {
429
430 $permalink = get_permalink( $post_id );
431
432 if ( function_exists( 'blavatar_domain' ) && function_exists( 'blavatar_exists' ) && function_exists( 'blavatar_url' ) ) {
433 $domain = blavatar_domain( $permalink );
434
435 if ( ! blavatar_exists( $domain ) ) {
436 return array();
437 }
438
439 $url = blavatar_url( $domain, 'img', $size );
440 } elseif ( function_exists( 'has_site_icon' ) && has_site_icon() ) {
441 $url = get_site_icon_url( $size );
442 } else {
443 return array();
444 }
445
446 return array( array(
447 'type' => 'image',
448 'from' => 'blavatar',
449 'src' => $url,
450 'src_width' => $size,
451 'src_height' => $size,
452 'href' => $permalink,
453 ) );
454 }
455
456 /**
457 * Gets a post image from the author avatar.
458 *
459 * @param int $post_id The post ID to check.
460 * @param int $size The size of the avatar to get.
461 * @param string $default The default image to use.
462 * @return Array containing details of the image, or empty array if none.
463 */
464 static function from_gravatar( $post_id, $size = 96, $default = false ) {
465 $post = get_post( $post_id );
466 $permalink = get_permalink( $post_id );
467
468 if ( function_exists( 'wpcom_get_avatar_url' ) ) {
469 $url = wpcom_get_avatar_url( $post->post_author, $size, $default, true );
470 if ( $url && is_array( $url ) ) {
471 $url = $url[0];
472 }
473 } else {
474 $url = get_avatar_url( $post->post_author, array(
475 'size' => $size,
476 'default' => $default,
477 ) );
478 }
479
480 return array(
481 array(
482 'type' => 'image',
483 'from' => 'gravatar',
484 'src' => $url,
485 'src_width' => $size,
486 'src_height' => $size,
487 'href' => $permalink,
488 ),
489 );
490 }
491
492 /**
493 * Run through the different methods that we have available to try to find a single good
494 * display image for this post.
495 * @param int $post_id
496 * @param array $args Other arguments (currently width and height required for images where possible to determine)
497 * @return Array containing details of the best image to be used
498 */
499 static function get_image( $post_id, $args = array() ) {
500 $image = '';
501
502 /**
503 * Fires before we find a single good image for a specific post.
504 *
505 * @since 2.2.0
506 *
507 * @param int $post_id Post ID.
508 */
509 do_action( 'jetpack_postimages_pre_get_image', $post_id );
510 $media = self::get_images( $post_id, $args );
511
512
513 if ( is_array( $media ) ) {
514 foreach ( $media as $item ) {
515 if ( 'image' == $item['type'] ) {
516 $image = $item;
517 break;
518 }
519 }
520 }
521
522 /**
523 * Fires after we find a single good image for a specific post.
524 *
525 * @since 2.2.0
526 *
527 * @param int $post_id Post ID.
528 */
529 do_action( 'jetpack_postimages_post_get_image', $post_id );
530
531 return $image;
532 }
533
534 /**
535 * Get an array containing a collection of possible images for this post, stopping once we hit a method
536 * that returns something useful.
537 * @param int $post_id
538 * @param array $args Optional args, see defaults list for details
539 * @return Array containing images that would be good for representing this post
540 */
541 static function get_images( $post_id, $args = array() ) {
542 // Figure out which image to attach to this post.
543 $media = false;
544
545 /**
546 * Filters the array of images that would be good for a specific post.
547 * This filter is applied before options ($args) filter the original array.
548 *
549 * @since 2.0.0
550 *
551 * @param array $media Array of images that would be good for a specific post.
552 * @param int $post_id Post ID.
553 * @param array $args Array of options to get images.
554 */
555 $media = apply_filters( 'jetpack_images_pre_get_images', $media, $post_id, $args );
556 if ( $media )
557 return $media;
558
559 $defaults = array(
560 'width' => 200, // Required minimum width (if possible to determine)
561 'height' => 200, // Required minimum height (if possible to determine)
562
563 'fallback_to_avatars' => false, // Optionally include Blavatar and Gravatar (in that order) in the image stack
564 'avatar_size' => 96, // Used for both Grav and Blav
565 'gravatar_default' => false, // Default image to use if we end up with no Gravatar
566
567 'from_thumbnail' => true, // Use these flags to specify which methods to use to find an image
568 'from_slideshow' => true,
569 'from_gallery' => true,
570 'from_attachment' => true,
571 'from_html' => true,
572
573 'html_content' => '' // HTML string to pass to from_html()
574 );
575 $args = wp_parse_args( $args, $defaults );
576
577 $media = false;
578 if ( $args['from_thumbnail'] )
579 $media = self::from_thumbnail( $post_id, $args['width'], $args['height'] );
580 if ( !$media && $args['from_slideshow'] )
581 $media = self::from_slideshow( $post_id, $args['width'], $args['height'] );
582 if ( !$media && $args['from_gallery'] )
583 $media = self::from_gallery( $post_id );
584 if ( !$media && $args['from_attachment'] )
585 $media = self::from_attachment( $post_id, $args['width'], $args['height'] );
586 if ( !$media && $args['from_html'] ) {
587 if ( empty( $args['html_content'] ) )
588 $media = self::from_html( $post_id, $args['width'], $args['height'] ); // Use the post_id, which will load the content
589 else
590 $media = self::from_html( $args['html_content'], $args['width'], $args['height'] ); // If html_content is provided, use that
591 }
592
593 if ( !$media && $args['fallback_to_avatars'] ) {
594 $media = self::from_blavatar( $post_id, $args['avatar_size'] );
595 if ( !$media )
596 $media = self::from_gravatar( $post_id, $args['avatar_size'], $args['gravatar_default'] );
597 }
598
599 /**
600 * Filters the array of images that would be good for a specific post.
601 * This filter is applied after options ($args) filter the original array.
602 *
603 * @since 2.0.0
604 *
605 * @param array $media Array of images that would be good for a specific post.
606 * @param int $post_id Post ID.
607 * @param array $args Array of options to get images.
608 */
609 return apply_filters( 'jetpack_images_get_images', $media, $post_id, $args );
610 }
611
612 /**
613 * Takes an image URL and pixel dimensions then returns a URL for the
614 * resized and cropped image.
615 *
616 * @param string $src
617 * @param int $dimension
618 * @return string Transformed image URL
619 */
620 static function fit_image_url( $src, $width, $height ) {
621 $width = (int) $width;
622 $height = (int) $height;
623
624 if ( $width < 1 || $height < 1 ) {
625 return $src;
626 }
627
628 // See if we should bypass WordPress.com SaaS resizing
629 if ( has_filter( 'jetpack_images_fit_image_url_override' ) ) {
630 /**
631 * Filters the image URL used after dimensions are set by Photon.
632 *
633 * @since 3.3.0
634 *
635 * @param string $src Image URL.
636 * @param int $width Image width.
637 * @param int $width Image height.
638 */
639 return apply_filters( 'jetpack_images_fit_image_url_override', $src, $width, $height );
640 }
641
642 // If WPCOM hosted image use native transformations
643 $img_host = parse_url( $src, PHP_URL_HOST );
644 if ( '.files.wordpress.com' == substr( $img_host, -20 ) ) {
645 return add_query_arg( array( 'w' => $width, 'h' => $height, 'crop' => 1 ), set_url_scheme( $src ) );
646 }
647
648 // Use Photon magic
649 if( function_exists( 'jetpack_photon_url' ) ) {
650 return jetpack_photon_url( $src, array( 'resize' => "$width,$height" ) );
651 }
652
653 // Arg... no way to resize image using WordPress.com infrastructure!
654 return $src;
655 }
656 }
657