-
-
Save sophy/9c7043e86324fda0b3ee4b01c23da6d3 to your computer and use it in GitHub Desktop.
A PHP class used to generate an <img> tag, specifically for use within WordPress sites (uploaded images, theme images, and external images) and the awesome lazysizes script (but not necessary).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| // !!! ALPHA VERSION !!! | |
| // !!! ALPHA VERSION !!! | |
| // !!! ALPHA VERSION !!! | |
| // !!! NOT FOR PRODUCTION USE !!! | |
| // !!! USE LATEST STABLE v0.0.3.1: | |
| // https://gist.github.com/crstauf/030df6bd6c436620e96cb92a44c9772f/e671037f46d8262357bbcef53581ac8235044e56 | |
| // https://gist.github.com/crstauf/030df6bd6c436620e96cb92a44c9772f | |
| if (!defined('ABSPATH') || !function_exists('add_filter')) { | |
| header( 'Status: 403 Forbidden' ); | |
| header( 'HTTP/1.1 403 Forbidden' ); | |
| exit(); | |
| } | |
| class image_tag { | |
| const VERSION = '0.0.4-alpha'; | |
| const DATAURI = 'data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7'; | |
| protected $args = array(); | |
| var $attributes = array( | |
| 'id' => '', | |
| 'alt' => '', | |
| 'src' => '', | |
| 'sizes' => '', | |
| 'title' => '', | |
| 'width' => 0, | |
| 'height' => 0, | |
| 'srcset' => array(), | |
| 'class' => array(), | |
| ), | |
| $echo = true, | |
| $noscript = true, | |
| $lazyload = true, | |
| $lazypreload = false, | |
| $noscript_sizes = array(); | |
| protected $files = array( | |
| '__smallest' => array( | |
| 'width' => 9999999, | |
| 'height' => 9999999, | |
| 'url' => '' | |
| ), | |
| '__largest' => array( | |
| 'width' => 0, | |
| 'height' => 0, | |
| 'url' => '', | |
| ), | |
| ); | |
| protected $orientation = ''; // portrait|landscape | |
| function __construct() { | |
| if ( !is_subclass_of( $this, 'image_tag' ) ) { | |
| $args = func_get_arg( 0 ); | |
| if ( array_key_exists( 'attachment_id', $args ) ) | |
| $source = $args['attachment_id']; | |
| else if ( array_key_exists( 'source', $args ) ) | |
| $source = $args['source']; | |
| else if ( array_key_exists( 'theme_image', $args ) ) | |
| $source = $args['theme_image']; | |
| else | |
| return false; | |
| $args['attributes']['class']['old-generated'] = 'old-generated-image-tag'; | |
| unset( | |
| $args['attachment_id'], | |
| $args['source'], | |
| $args['theme_image'] | |
| ); | |
| if ( | |
| array_key_exists( 'echo', $args ) | |
| && false === $args['echo'] | |
| ) | |
| return image_tag( $source, $args ); | |
| else | |
| echo image_tag( $source, $args ); | |
| } | |
| add_filter( 'image-tag/noscript/attributes/glue', array( &$this, 'filter_image_tag_noscript_attributes_glue' ) ); | |
| if ( is_array( $this->args ) && count( $this->args ) ) | |
| foreach ( $this->args as $key => $value ) | |
| if ( isset( $this->$key ) ) | |
| $this->$key = $value; | |
| $this->attributes['class']['generated'] = 'generated-image-tag'; | |
| $this->gather_files(); | |
| $this->determine_orientation(); | |
| $this->being_lazy(); | |
| } | |
| function __toString() { | |
| if ( !$this->echo ) | |
| return ''; | |
| ksort( $this->attributes ); | |
| $image_output = $this->image_output(); | |
| if ( !$this->noscript ) | |
| return implode( "\n", $image_output ); | |
| $this->noscript_prep(); | |
| return implode( "\n", array_filter( $image_output ) ) . implode( "\n", array_filter( $this->noscript_image_output() ) ); | |
| } | |
| function image_output() { | |
| $output = array( 'open' => "\n<img " ); | |
| foreach ( $this->attributes as $attr_name => $attr_value ) { | |
| $attr_value = apply_filters( 'image-tag/attributes/value', $attr_value, $attr_name, $this ); | |
| $attr_value = apply_filters( 'image-tag/attributes/' . $attr_name . '/value', $attr_value, $this ); | |
| $output[$attr_name] = $this->construct_attribute( $attr_name, $attr_value ); | |
| if ( '' === trim( $output[$attr_name] ) ) | |
| unset( $output[$attr_name] ); | |
| } | |
| $output['close'] = "/>\n"; | |
| return array_filter( $output ); | |
| } | |
| function noscript_prep() { | |
| $this->attributes['class']['noscript'] = 'noscript'; | |
| $this->attributes['class']['post-noscript'] = $this->attributes['class']['post'] . '-noscript'; | |
| if ( !empty( $this->attributes['id'] ) ) | |
| $this->attributes['id'] .= '-noscript'; | |
| if ( array_key_exists( 'data-sizes', $this->attributes ) ) | |
| $this->attributes['sizes'] = $this->attributes['data-sizes']; | |
| if ( array_key_exists( 'data-src', $this->attributes ) && self::DATAURI !== $this->attributes['data-src'] ) | |
| $this->attributes['src'] = $this->attributes['data-src']; | |
| if ( 'auto' === $this->attributes['sizes'] ) { | |
| if ( !empty( $this->noscript_sizes ) && is_array( $this->noscript_sizes ) && count( $this->noscript_sizes ) ) { | |
| $this->attributes['sizes'] = $this->noscript_sizes; | |
| if ( array_key_exists( 'data-srcset', $this->attributes ) ) | |
| $this->attributes['srcset'] = $this->attributes['data-srcset']; | |
| } else { | |
| $this->attributes['src'] = $this->files['__largest']['url']; | |
| unset( $this->attributes['sizes'] ); | |
| } | |
| } | |
| unset( | |
| $this->attributes['class']['lazyload'], | |
| $this->attributes['class']['lazypreload'], | |
| $this->attribtues['data-src'], | |
| $this->attributes['data-sizes'], | |
| $this->attributes['data-srcset'] | |
| ); | |
| } | |
| function noscript_image_output() { | |
| $output = array( | |
| 'open_noscript' => '<noscript>', | |
| 'open_img' => "\t<img", | |
| ); | |
| foreach ( $this->attributes as $attr_name => $attr_value ) { | |
| $attr_value = apply_filters( 'image-tag/noscript/attributes/value', $attr_value, $attr_name, $this ); | |
| $attr_value = apply_filters( 'image-tag/noscript/attributes/' . $attr_name . '/value', $attr_value, $this ); | |
| $output[$attr_name] = "\t" . $this->construct_attribute( $attr_name, $attr_value, true ); | |
| if ( '' === trim( $output[$attr_name] ) ) | |
| unset( $output[$attr_name] ); | |
| } | |
| $output['close_img'] = "\n\t/>"; | |
| $output['close_noscript'] = "</noscript>\n"; | |
| return array_filter( $output ); | |
| } | |
| function construct_attribute( $attr_name, $attr_value, $noscript = false ) { | |
| if ( !is_array( $attr_value ) ) { | |
| if ( !empty( $attr_value ) && ( '' !== trim( $attr_value ) || 'alt' === $attr_name ) ) | |
| return "\t" . $attr_name . '="' . esc_attr( $attr_value ) . '" '; | |
| return false; | |
| } | |
| if ( false !== strpos( $attr_name, 'srcset' ) && count( $attr_value ) ) | |
| foreach ( $attr_value as $w => $url ) | |
| $attr_value[$w] = $url . ' ' . $w; | |
| switch ( $attr_name ) { | |
| case 'sizes': | |
| case 'srcset': | |
| case 'data-srcset': | |
| $glue = ",\n\t\t"; | |
| break; | |
| case 'class': | |
| default: | |
| $glue = ' '; | |
| break; | |
| } | |
| $glue = apply_filters( 'image-tag/' . ( $noscript ? 'noscript/' : '' ) . 'attributes/glue', $glue, $attr_name, $this ); | |
| $glue = apply_filters( 'image-tag/' . ( $noscript ? 'noscript/' : '' ) . 'attributes/' . $attr_name . '/glue', $glue, $this ); | |
| foreach ( $attr_value as $i => $maybe_array ) | |
| if ( is_array( $maybe_array ) ) | |
| $attr_value[$i] = implode( $glue, $maybe_array ); | |
| return "\t" . $attr_name . '="' . implode( $glue, $attr_value ) . '" '; | |
| } | |
| function filter_image_tag_noscript_attributes_glue( $glue ) { | |
| if ( ' ' === $glue ) | |
| return ' '; | |
| return $glue . "\t"; | |
| } | |
| function determine_orientation() { | |
| $largest = &$this->files['__largest']; | |
| if ( $largest['width'] > $largest['height'] ) | |
| $this->orientation = 'landscape'; | |
| else if ( $largest['width'] < $largest['height'] ) | |
| $this->orientation = 'portrait'; | |
| else if ( $largest['width'] === $largest['height'] ) | |
| $this->orientation = 'square'; | |
| else | |
| $this->orientation = false; | |
| $this->attributes['class']['orientation'] = 'orientation-' . | |
| ( false === $this->orientation | |
| ? 'unknown' | |
| : $this->orientation | |
| ); | |
| } | |
| function gather_files() {} | |
| function being_lazy() { | |
| if ( !$this->lazyload && !$this->lazypreload ) | |
| return false; | |
| if ( $this->lazypreload ) | |
| $this->attributes['class']['lazypreload'] = 'lazypreload'; | |
| if ( !$this->lazyload ) | |
| return false; | |
| $this->attributes['data-sizes'] = 'auto'; | |
| $this->attributes['class']['lazyload'] = 'lazyload'; | |
| $this->attributes['src'] = self::DATAURI; | |
| $this->attributes['data-src' . ( count( $this->files ) > 3 ? 'set' : '' )] = $this->attributes['srcset']; | |
| unset( $this->attributes['srcset'] ); | |
| return true; | |
| } | |
| } | |
| /* | |
| ## ## ####### ######## ######## ######## ######## ######## ###### ###### | |
| ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## | |
| ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## | |
| ## ## ## ## ## ######## ## ## ######## ######## ###### ###### ###### | |
| ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## | |
| ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## ## | |
| ### ### ####### ## ## ######## ## ## ## ######## ###### ###### | |
| */ | |
| class image_tag_wp_attachment extends image_tag { | |
| var $id = 0, | |
| $post = null, | |
| $image_sizes = array( 'thumbnail', 'medium', 'medium_large', 'large', 'full' ); | |
| function __construct() { | |
| $this->args = func_get_arg( 0 ); | |
| parent::__construct(); | |
| $this->get_post(); | |
| if ( | |
| false === $this->post | |
| || is_wp_error( $this->post ) | |
| ) | |
| return; | |
| $this->attributes['class']['post'] = 'post-' . $this->id; | |
| } | |
| function noscript_prep() { | |
| parent::noscript_prep(); | |
| if ( !empty( $this->attributes['sizes'] ) || !empty( $this->noscript_sizes ) ) | |
| return; | |
| $largest = $this->files['__largest']; | |
| foreach ( $this->files as $size => $file ) { | |
| if ( in_array( $size, array( '__largest', '__smallest' ) ) ) | |
| continue; | |
| if ( $file['url'] === $largest['url'] ) { | |
| $this->attributes['class']['WP-size'] = 'size-' . $size; | |
| break; | |
| } | |
| } | |
| } | |
| function get_post() { | |
| $this->post = get_post( $this->id ); | |
| if ( '' === $this->attributes['alt'] ) | |
| $this->attributes['alt'] = esc_attr( get_the_title( $this->post ) ); | |
| if ( '' === $this->attributes['title'] ) | |
| $this->attributes['title'] = esc_attr( get_the_title( $this->post ) ); | |
| } | |
| function gather_files() { | |
| foreach ( $this->image_sizes as $i => $image_size ) { | |
| $this->attributes['class']['WP-size'][$image_size] = 'size-' . $image_size; | |
| $img = wp_get_attachment_image_src( $this->id, $image_size ); | |
| if ( 0 === $i ) { | |
| $this->attributes['src'] = $img[0]; | |
| $this->attributes['width'] = $img[1]; | |
| $this->attributes['height'] = $img[2]; | |
| } | |
| $this->files[$image_size] = array( | |
| 'width' => $img[1], | |
| 'height' => $img[2], | |
| 'url' => $img[0], | |
| ); | |
| $this->attributes['srcset'][$img[1] . 'w'] = $img[0]; | |
| if ( $this->files['__largest']['width'] < $img[1] ) | |
| $this->files['__largest'] = &$this->files[$image_size]; | |
| if ( $this->files['__smallest']['width'] > $img[1] ) | |
| $this->files['__smallest'] = &$this->files[$image_size]; | |
| } | |
| $this->files['__largest']['ratio'] = ( $this->files['__largest']['height'] / $this->files['__largest']['width'] ) * 100; | |
| } | |
| } | |
| /* | |
| ## ## ######## ## | |
| ## ## ## ## ## | |
| ## ## ## ## ## | |
| ## ## ######## ## | |
| ## ## ## ## ## | |
| ## ## ## ## ## | |
| ####### ## ## ######## | |
| */ | |
| class image_tag_uri extends image_tag { | |
| function __construct() { | |
| parent::__construct(); | |
| } | |
| function gather_files() { | |
| } | |
| } | |
| function image_tag( $source, $args = false ) { | |
| if ( false === $args ) | |
| $args = array(); | |
| if ( is_int( $source ) ) { | |
| $args['id'] = $source; | |
| return new image_tag_wp_attachment( $args ); | |
| } else if ( | |
| false !== stripos( 'http://', $source ) | |
| || false !== stripos( 'https://', $source ) | |
| ) | |
| $args['source'] = $source; | |
| else if ( apply_filters( 'image-tag/enable-theme-images', defined( 'THEME_IMAGES_URI' ) ) ) | |
| $args['source'] = apply_filters( 'image-tag/theme-images-uri', THEME_IMAGES_URI ) . $source; | |
| return new image_tag_uri( $args ); | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment