PluginProbe ʕ •ᴥ•ʔ
Image Widget / 4.4.6
Image Widget v4.4.6
trunk 1.0 2.0 2.1 2.2 2.2.1 2.2.2 3.0 3.0.1 3.0.2 3.0.3 3.0.4 3.0.5 3.0.6 3.0.7 3.0.8 3.0.9 3.1 3.1.1 3.1.2 3.1.3 3.1.4 3.1.5 3.1.6 3.2 3.2.1 3.2.10 3.2.11 3.2.2 3.2.3 3.2.4 3.2.5 3.2.7 3.2.8 3.2.9 3.3 3.3.1 3.3.2 3.3.3 3.3.4 3.3.5 3.3.6 3.3.7 4.0 4.0.1 4.0.2 4.0.3 4.0.4 4.0.5 4.0.6 4.0.7 4.0.8 4.0.9 4.1 4.1.1 4.1.2 4.2 4.2.1 4.2.2 4.3 4.3.1 4.4 4.4.1 4.4.11 4.4.12 4.4.2 4.4.3 4.4.4 4.4.5 4.4.6 4.4.7 4.4.8 4.4.9
image-widget / image-widget.php
image-widget Last commit date
lang 8 years ago lib 8 years ago resources 8 years ago views 8 years ago image-widget.php 8 years ago index.php 8 years ago readme.txt 8 years ago
image-widget.php
610 lines
1 <?php
2 /*
3 Plugin Name: Image Widget
4 Plugin URI: http://wordpress.org/plugins/image-widget/
5 Description: A simple image widget that uses the native WordPress media manager to add image widgets to your site. <strong><a href="http://m.tri.be/19my">Image Widget Plus</a> - Multiple images, slider and more.</strong>
6 Author: Modern Tribe, Inc.
7 Version: 4.4.6
8 Author URI: http://m.tri.be/iwpdoc
9 Text Domain: image-widget
10 Domain Path: /lang
11 */
12
13 // Block direct requests
14 if ( ! defined( 'ABSPATH' ) ) {
15 die( '-1' );
16 }
17
18 // Load the widget on widgets_init
19 function tribe_load_image_widget() {
20 register_widget( 'Tribe_Image_Widget' );
21 }
22 add_action( 'widgets_init', 'tribe_load_image_widget' );
23
24 class Tribe_Image_Widget extends WP_Widget {
25
26 const VERSION = '4.4.6';
27
28 const CUSTOM_IMAGE_SIZE_SLUG = 'tribe_image_widget_custom';
29
30 const VERSION_KEY = '_image_widget_version';
31
32 /**
33 * Tribe Image Widget constructor
34 */
35 public function __construct() {
36 load_plugin_textdomain( 'image-widget', false, trailingslashit( basename( dirname( __FILE__ ) ) ) . 'lang/' );
37
38 $widget_ops = array( 'classname' => 'widget_sp_image', 'description' => __( 'Showcase a single image with a Title, URL, and a Description', 'image-widget' ) );
39 $control_ops = array( 'id_base' => 'widget_sp_image' );
40
41 parent::__construct( 'widget_sp_image', __( 'Image Widget', 'image-widget' ), $widget_ops, $control_ops );
42
43 if ( $this->use_old_uploader() ) {
44 require_once( 'lib/ImageWidgetDeprecated.php' );
45 new ImageWidgetDeprecated( $this );
46 } else {
47 add_action( 'sidebar_admin_setup', array( $this, 'admin_setup' ) );
48 }
49
50 // fire admin_setup if we are in the customizer
51 add_action( 'admin_enqueue_scripts', array( $this, 'maybe_admin_setup' ) );
52
53 add_action( 'plugin_row_meta', array( $this, 'plugin_row_meta' ), 10, 2 );
54
55 if ( ! defined( 'I_HAVE_SUPPORTED_THE_IMAGE_WIDGET' ) )
56 add_action( 'admin_notices', array( $this, 'post_upgrade_nag' ) );
57
58 add_action( 'network_admin_notices', array( $this, 'post_upgrade_nag' ) );
59 add_action( 'wp_ajax_dismissed_image_widget_notice_handler', array( $this, 'ajax_notice_handler' ) );
60 }
61
62 /**
63 * Test to see if this version of WordPress supports the new image manager.
64 *
65 * @return bool True if the current version of WordPress does NOT support the current image management tech.
66 */
67 private function use_old_uploader() {
68 if ( defined( 'IMAGE_WIDGET_COMPATIBILITY_TEST' ) ) {
69 return true;
70 }
71
72 return ! function_exists( 'wp_enqueue_media' );
73 }
74
75 /**
76 * Enqueue all the javascript and CSS.
77 */
78 public function admin_setup() {
79 wp_enqueue_media();
80
81 wp_enqueue_style( 'tribe-image-widget', plugins_url( 'resources/css/admin.css', __FILE__ ), array(), self::VERSION );
82 wp_enqueue_script( 'tribe-image-widget', plugins_url( 'resources/js/image-widget.js', __FILE__ ), array( 'jquery', 'media-upload', 'media-views' ), self::VERSION );
83
84 wp_localize_script( 'tribe-image-widget', 'TribeImageWidget', array(
85 'frame_title' => __( 'Select an Image', 'image-widget' ),
86 'button_title' => __( 'Insert Into Widget', 'image-widget' ),
87 ) );
88 }
89
90 /**
91 * Trigger the enqueueing of admin scripts and styles on widget admin page and in the "Customizer" view.
92 */
93 public function maybe_admin_setup() {
94 $screen = get_current_screen();
95
96 if ( 'customize' !== $screen->base ) {
97 return;
98 }
99
100 $this->admin_setup();
101 }
102
103 /**
104 * Widget frontend output
105 *
106 * @param array $args
107 * @param array $instance
108 */
109 public function widget( $args, $instance ) {
110 extract( $args );
111
112 $instance = wp_parse_args( (array) $instance, self::get_defaults() );
113
114 if ( ! empty( $instance['imageurl'] ) || ! empty( $instance['attachment_id'] ) ) {
115
116 $instance['title'] = apply_filters( 'widget_title', empty( $instance['title'] ) ? '' : $instance['title'] );
117 $instance['description'] = apply_filters( 'widget_text', $instance['description'], $args, $instance );
118 $instance['link'] = apply_filters( 'image_widget_image_link', esc_url( $instance['link'] ), $args, $instance );
119 $instance['linkid'] = apply_filters( 'image_widget_image_link_id', esc_attr( $instance['linkid'] ), $args, $instance );
120 $instance['linktarget'] = apply_filters( 'image_widget_image_link_target', esc_attr( $instance['linktarget'] ), $args, $instance );
121 $instance['width'] = apply_filters( 'image_widget_image_width', abs( $instance['width'] ), $args, $instance );
122 $instance['height'] = apply_filters( 'image_widget_image_height', abs( $instance['height'] ), $args, $instance );
123 $instance['maxwidth'] = apply_filters( 'image_widget_image_maxwidth', esc_attr( $instance['maxwidth'] ), $args, $instance );
124 $instance['maxheight'] = apply_filters( 'image_widget_image_maxheight', esc_attr( $instance['maxheight'] ), $args, $instance );
125 $instance['align'] = apply_filters( 'image_widget_image_align', esc_attr( $instance['align'] ), $args, $instance );
126 $instance['alt'] = apply_filters( 'image_widget_image_alt', esc_attr( $instance['alt'] ), $args, $instance );
127 $instance['rel'] = apply_filters( 'image_widget_image_rel', esc_attr( $instance['rel'] ), $args, $instance );
128
129 if ( ! defined( 'IMAGE_WIDGET_COMPATIBILITY_TEST' ) ) {
130 $instance['attachment_id'] = ( $instance['attachment_id'] > 0 ) ? $instance['attachment_id'] : $instance['image'];
131 $instance['attachment_id'] = apply_filters( 'image_widget_image_attachment_id', abs( $instance['attachment_id'] ), $args, $instance );
132 $instance['size'] = apply_filters( 'image_widget_image_size', esc_attr( $instance['size'] ), $args, $instance );
133 }
134
135 $instance['imageurl'] = apply_filters( 'image_widget_image_url', esc_url( $instance['imageurl'] ), $args, $instance );
136
137 // No longer using extracted vars. This is here for backwards compatibility.
138 extract( $instance );
139
140 include( $this->getTemplateHierarchy( 'widget' ) );
141 }
142 }
143
144 /**
145 * Update widget options
146 *
147 * @param object $new_instance Widget Instance
148 * @param object $old_instance Widget Instance
149 * @return object
150 */
151 public function update( $new_instance, $old_instance ) {
152
153 $instance = $old_instance;
154 $new_instance = wp_parse_args( (array) $new_instance, self::get_defaults() );
155
156 $instance['title'] = strip_tags( $new_instance['title'] );
157
158 if ( current_user_can( 'unfiltered_html' ) ) {
159 $instance['description'] = $new_instance['description'];
160 } else {
161 $instance['description'] = wp_kses_post( $new_instance['description'] );
162 }
163
164 /**
165 * Make the description filterable; especially useful for working with allowing/disallowing HTML and other content.
166 *
167 * @since 4.4.6
168 *
169 * @param $description The current value of $instance['description'].
170 * @param $new_instance The new instance of the widget, i.e. the new values being saved for it.
171 * @param $old_instance The pre-existing instance of the widget, i.e. the values that are potentially being updated.
172 */
173 $instance['description'] = apply_filters( 'tribe_image_widget_instance_description', $instance['description'], $new_instance, $old_instance );
174
175 $instance['link'] = $new_instance['link'];
176 $instance['linkid'] = $new_instance['linkid'];
177 $instance['linktarget'] = $new_instance['linktarget'];
178 $instance['width'] = abs( $new_instance['width'] );
179 $instance['height'] = abs( $new_instance['height'] );
180
181 if ( ! defined( 'IMAGE_WIDGET_COMPATIBILITY_TEST' ) ) {
182 $instance['size'] = $new_instance['size'];
183 }
184
185 $instance['align'] = $new_instance['align'];
186 $instance['alt'] = $new_instance['alt'];
187 $instance['rel'] = $new_instance['rel'];
188
189 // Reverse compatibility with $image, now called $attachement_id
190 if ( ! defined( 'IMAGE_WIDGET_COMPATIBILITY_TEST' ) && $new_instance['attachment_id'] > 0 ) {
191 $instance['attachment_id'] = abs( $new_instance['attachment_id'] );
192 } elseif ( $new_instance['image'] > 0 ) {
193 $instance['attachment_id'] = $instance['image'] = abs( $new_instance['image'] );
194 if ( class_exists( 'ImageWidgetDeprecated' ) ) {
195 $instance['imageurl'] = ImageWidgetDeprecated::get_image_url( $instance['image'], $instance['width'], $instance['height'] ); // image resizing not working right now
196 }
197 }
198
199 $instance['imageurl'] = $new_instance['imageurl']; // deprecated
200 $instance['aspect_ratio'] = $this->get_image_aspect_ratio( $instance );
201
202 return $instance;
203 }
204
205 /**
206 * Form UI
207 *
208 * @param object $instance Widget Instance
209 */
210 public function form( $instance ) {
211 $instance = wp_parse_args( (array) $instance, self::get_defaults() );
212 if ( $this->use_old_uploader() ) {
213 include( $this->getTemplateHierarchy( 'widget-admin.deprecated' ) );
214 } else {
215 include( $this->getTemplateHierarchy( 'widget-admin' ) );
216 }
217 }
218
219 /**
220 * Render an array of default values.
221 *
222 * @return array default values
223 */
224 private static function get_defaults() {
225
226 $defaults = array(
227 'title' => '',
228 'description' => '',
229 'link' => '',
230 'linkid' => '',
231 'linktarget' => '',
232 'width' => 0,
233 'height' => 0,
234 'maxwidth' => '100%',
235 'maxheight' => '',
236 'image' => 0, // reverse compatible - now attachement_id
237 'imageurl' => '', // reverse compatible.
238 'align' => 'none',
239 'alt' => '',
240 'rel' => '',
241 );
242
243 if ( ! defined( 'IMAGE_WIDGET_COMPATIBILITY_TEST' ) ) {
244 $defaults['size'] = self::CUSTOM_IMAGE_SIZE_SLUG;
245 $defaults['attachment_id'] = 0;
246 }
247
248 return $defaults;
249 }
250
251 /**
252 * Render the image html output.
253 *
254 * @param array $instance
255 * @param bool $include_link will only render the link if this is set to true. Otherwise link is ignored.
256 * @return string image html
257 */
258 private function get_image_html( $instance, $include_link = true ) {
259
260 // Backwards compatible image display.
261 if ( $instance['attachment_id'] == 0 && $instance['image'] > 0 ) {
262 $instance['attachment_id'] = $instance['image'];
263 }
264
265 $output = '';
266
267 if ( $include_link && ! empty( $instance['link'] ) ) {
268
269 $attr = array(
270 'href' => $instance['link'],
271 'id' => $instance['linkid'],
272 'target' => $instance['linktarget'],
273 'class' => $this->widget_options['classname'] . '-image-link',
274 'title' => ( ! empty( $instance['alt'] ) ) ? $instance['alt'] : $instance['title'],
275 'rel' => $instance['rel'],
276 );
277
278 $attr = apply_filters( 'image_widget_link_attributes', $attr, $instance );
279 $attr = array_map( 'esc_attr', $attr );
280
281 $output = '<a';
282
283 foreach ( $attr as $name => $value ) {
284 if ( ! empty( $value ) ) {
285 $output .= sprintf( ' %s="%s"', $name, $value );
286 }
287 }
288 $output .= '>';
289 }
290
291 $size = $this->get_image_size( $instance );
292
293 if ( is_array( $size ) ) {
294 $instance['width'] = $size[0];
295 $instance['height'] = $size[1];
296 } elseif ( ! empty( $instance['attachment_id'] ) ) {
297 //$instance['width'] = $instance['height'] = 0;
298 $image_details = wp_get_attachment_image_src( $instance['attachment_id'], $size );
299 if ( $image_details ) {
300 $instance['imageurl'] = $image_details[0];
301 $instance['width'] = $image_details[1];
302 $instance['height'] = $image_details[2];
303 }
304
305 $image_srcset = function_exists( 'wp_get_attachment_image_srcset' )
306 ? wp_get_attachment_image_srcset( $instance['attachment_id'], $size )
307 : false;
308 if ( $image_srcset ) {
309 $instance['srcset'] = $image_srcset;
310
311 $image_sizes = function_exists( 'wp_get_attachment_image_sizes' )
312 ? wp_get_attachment_image_sizes( $instance['attachment_id'], $size )
313 : false;
314 if ( $image_sizes ) {
315 $instance['sizes'] = $image_sizes;
316 }
317 }
318 }
319
320 $instance['width'] = abs( $instance['width'] );
321 $instance['height'] = abs( $instance['height'] );
322
323 $attr = array();
324
325 if ( ! empty( $instance['alt'] ) ) {
326 $attr['alt'] = $instance['alt'];
327 } elseif ( ! empty( $instance['title'] ) ) {
328 $attr['alt'] = $instance['title'];
329 }
330
331 if ( is_array( $size ) ) {
332 $attr['class'] = 'attachment-' . join( 'x', $size );
333 } else {
334 $attr['class'] = 'attachment-' . $size;
335 }
336
337 $attr['style'] = '';
338 if ( ! empty( $instance['maxwidth'] ) ) {
339 $attr['style'] .= "max-width: {$instance['maxwidth']};";
340 }
341
342 if ( ! empty( $instance['maxheight'] ) ) {
343 $attr['style'] .= "max-height: {$instance['maxheight']};";
344 }
345
346 if ( ! empty( $instance['align'] ) && $instance['align'] != 'none' ) {
347 $attr['class'] .= " align{$instance['align']}";
348 }
349
350 if ( ! empty( $instance['srcset'] ) ) {
351 $attr['srcset'] = $instance['srcset'];
352 }
353
354 if ( ! empty( $instance['sizes'] ) ) {
355 $attr['sizes'] = $instance['sizes'];
356 }
357
358 /**
359 * Allow filtering of the image attributes used on the front-end.
360 *
361 * @param array $attr Image attributes to be filtered.
362 * @param array $instance The current widget instance.
363 */
364 $attr = apply_filters( 'image_widget_image_attributes', $attr, $instance );
365
366 // If there is an imageurl, use it to render the image. Eventually we should kill this and simply rely on attachment_ids.
367 if ( ! empty( $instance['imageurl'] ) ) {
368 // If all we have is an image src url we can still render an image.
369 $attr['src'] = $instance['imageurl'];
370 $attr = array_map( 'esc_attr', $attr );
371 $hwstring = image_hwstring( $instance['width'], $instance['height'] );
372
373 $output .= rtrim( "<img $hwstring" );
374
375 foreach ( $attr as $name => $value ) {
376 $output .= sprintf( ' %s="%s"', $name, $value );
377 }
378
379 $output .= ' />';
380
381 } elseif ( abs( $instance['attachment_id'] ) > 0 ) {
382 $output .= wp_get_attachment_image( $instance['attachment_id'], $size, false, $attr );
383 }
384
385 if ( $include_link && ! empty( $instance['link'] ) ) {
386 $output .= '</a>';
387 }
388
389 return $output;
390 }
391
392 /**
393 * Get all possible image sizes to choose from
394 *
395 * @return array
396 */
397 private function possible_image_sizes() {
398 $registered = get_intermediate_image_sizes();
399 // label other sizes with their image size "ID"
400 $registered = array_combine( $registered, $registered );
401
402 $possible_sizes = array_merge( $registered, array(
403 'full' => __( 'Full Size', 'image-widget' ),
404 'thumbnail' => __( 'Thumbnail', 'image-widget' ),
405 'medium' => __( 'Medium', 'image-widget' ),
406 'large' => __( 'Large', 'image-widget' ),
407 self::CUSTOM_IMAGE_SIZE_SLUG => __( 'Custom', 'image-widget' ),
408 ) );
409
410 /**
411 * Allow filtering the image sizes available for use in the Image Widget dropdown
412 *
413 * @param array $possible_sizes The array of available sizes.
414 */
415 return (array) apply_filters( 'image_size_names_choose', $possible_sizes );
416 }
417
418 /**
419 * Assesses the image size in case it has not been set or in case there is a mismatch.
420 *
421 * @param $instance
422 * @return array|string
423 */
424 private function get_image_size( $instance ) {
425 if ( ! empty( $instance['size'] ) && $instance['size'] != self::CUSTOM_IMAGE_SIZE_SLUG ) {
426 $size = $instance['size'];
427 } elseif ( isset( $instance['width'] ) && is_numeric( $instance['width'] ) && isset( $instance['height'] ) && is_numeric( $instance['height'] ) ) {
428 //$size = array(abs($instance['width']),abs($instance['height']));
429 $size = array( $instance['width'], $instance['height'] );
430 } else {
431 $size = 'full';
432 }
433
434 return $size;
435 }
436
437 /**
438 * Establish the aspect ratio of the image.
439 *
440 * @param $instance
441 * @return float|number
442 */
443 private function get_image_aspect_ratio( $instance ) {
444 if ( ! empty( $instance['aspect_ratio'] ) ) {
445 return abs( $instance['aspect_ratio'] );
446 } else {
447 $attachment_id = ( ! empty( $instance['attachment_id'] ) ) ? $instance['attachment_id'] : $instance['image'];
448 if ( ! empty( $attachment_id ) ) {
449 $image_details = wp_get_attachment_image_src( $attachment_id, 'full' );
450 if ( $image_details ) {
451 return ( $image_details[1] / $image_details[2] );
452 }
453 }
454 }
455 }
456
457 /**
458 * Loads theme files in appropriate hierarchy: 1) child theme,
459 * 2) parent template, 3) plugin resources. will look in the image-widget/
460 * directory in a theme and the views/ directory in the plugin
461 *
462 * @param string $template template file to search for
463 * @return template path
464 */
465
466 public function getTemplateHierarchy( $template ) {
467 // whether or not .php was added
468 $template_slug = rtrim( $template, '.php' );
469 $template = $template_slug . '.php';
470
471 if ( $theme_file = locate_template( array( 'image-widget/' . $template ) ) ) {
472 $file = $theme_file;
473 } else {
474 $file = 'views/' . $template;
475 }
476
477 /**
478 * Allow filtering of currently-retrieved Image Widget template file's path.
479 *
480 * @param string $file The retrieved template file's path.
481 */
482 return apply_filters( 'sp_template_image-widget_' . $template, $file );
483 }
484
485 /**
486 * Display a thank you nag when the plugin has been upgraded.
487 */
488 public function post_upgrade_nag() {
489
490 if (
491 ! current_user_can( 'install_plugins' )
492 || class_exists( 'Tribe__Image__Plus__Main' )
493 ) {
494 return;
495 }
496
497 global $pagenow;
498 $msg = false;
499 switch ( $pagenow ) {
500 case 'plugins.php' :
501 $msg = $this->upgrade_nag_plugins_admin_msg();
502 break;
503 case 'widgets.php' :
504 $msg = $this->upgrade_nag_widget_admin_msg();
505 break;
506 }
507
508 if ( ! $msg ) return;
509
510 echo $msg;
511 ?><script>
512 jQuery(document).ready(function($){
513 // Dismiss our admin notice
514 $( document ).on( 'click', '.image-widget-notice .notice-dismiss', function () {
515 var key = $( this ).closest( '.image-widget-notice' ).data( 'key' );
516 $.ajax( ajaxurl,
517 {
518 type: 'POST',
519 data: {
520 action: 'dismissed_image_widget_notice_handler',
521 key: key
522 }
523 } );
524 } );
525 } );
526 </script><?php
527 }
528
529 /**
530 * AJAX handler to store the state of dismissible notices.
531 */
532 public function ajax_notice_handler() {
533 if ( empty( $_POST['key'] ) ) {
534 return;
535 }
536
537 $key = $this->generate_key( sanitize_text_field( $_POST['key'] ) );
538
539 update_site_option( $key, self::VERSION );
540 }
541
542 /**
543 * Generate version key for admin notice options
544 *
545 * @param string $key
546 * @return string option key
547 */
548 private function generate_key( $key ) {
549 return join( '_', array( self::VERSION_KEY, $key, ) );
550 }
551
552 /**
553 * Upgrade nag: Plugins Admin
554 *
555 * @return string alert message.
556 */
557 private function upgrade_nag_plugins_admin_msg() {
558 $key = 'plugin';
559 $option_key = $this->generate_key( $key );
560
561 if ( get_site_option( $option_key ) == self::VERSION ) {
562 return;
563 }
564
565 $msg = sprintf(
566 __( '<p class="dashicons-before dashicons-format-gallery"><strong>Image Widget Plus</strong> - Add lightbox, slideshow, and random image widgets. <strong><a href="%s" target="_blank">Find out how!</a></strong></p>', 'image-widget' ),
567 'http://m.tri.be/19my',
568 'http://m.tri.be/19my'
569 );
570
571 return "<div class='notice notice-info is-dismissible image-widget-notice' data-key='$key'>$msg</div>";
572 }
573
574 /**
575 * Upgrade nag: Widget Admin
576 *
577 * @return string alert message.
578 */
579 private function upgrade_nag_widget_admin_msg() {
580 $key = 'widget';
581 $option_key = $this->generate_key( $key );
582
583 if ( get_site_option( $option_key ) == self::VERSION ) {
584 return;
585 }
586
587 $msg = sprintf(
588 __( '<p class="dashicons-before dashicons-star-filled"><strong>Image Widget Plus</strong> - Add lightbox, slideshow, and random image widgets. <strong><a href="%s" target="_blank">Find out how!</a></strong></p>', 'image-widget' ),
589 'http://m.tri.be/19mx'
590 );
591
592 return "<div class='notice notice-info is-dismissible image-widget-notice' data-key='$key'>$msg</div>";
593 }
594
595 /**
596 * Display an informational section in the plugin admin ui.
597 *
598 * @param $meta
599 * @param $file
600 * @return array
601 */
602 public function plugin_row_meta( $meta, $file ) {
603 if ( $file == plugin_basename( dirname( __FILE__ ) . '/image-widget.php' ) ) {
604 $meta[] = '<strong><a href="http://m.tri.be/19ma" target="_blank">' . esc_html__( 'Image Widget Plus', 'image-widget' ) . '</a></strong>';
605 }
606
607 return $meta;
608 }
609 }
610