I want to apply jquery lazyload plugin. For this to work I have to create a new attribute which is data-src place there the src value and then replace the src value with a specific value '...nothing.gif'
.
I found a solution on wordpress support
This is my adapted code -
function add_lazyload($content)
{
global $post;
$search = '/src\=\"([^\s]+(?=\.(bmp|gif|jpeg|jpg|png))\.\2)\"/';
$content = replacer($content, $search, '/src/', 'data-original');
$search = '/img\ class\=\"/';
$content = replacer($content, $search, '/class\=\"/', 'class="lazy ');
$search = '/alt/';
$content = replacer($content, $search, '/alt/', 'src="'.get_template_directory_uri().'/library/images/nothing.gif"');
return $content;
}
function replacer($src, $search, $find, $replace)
{
preg_match_all($search, $src, $result, PREG_OFFSET_CAPTURE);
foreach($result[0] as $entry)
{
$org = $entry[0];
$rep = preg_replace($find, $replace, $entry[0]);
$org = "/" .str_replace(array("=",":","/",".","-","_",'"',"'"," "), array("\=","\:","\/","\.","\-","\_",'\"',"\'","\ "), $org). "/";
$src = preg_replace($org, $rep, $src);
}
return $src;
}
add_filter('the_content', 'add_lazyload');
The problem with this code is that it replaces every alt
string (for example in a paragraph) with .../library/images/nothing.gif
, not just the alt image attribute.
Does anyone know how to solve this?
I want to apply jquery lazyload plugin. For this to work I have to create a new attribute which is data-src place there the src value and then replace the src value with a specific value '...nothing.gif'
.
I found a solution on wordpress support
This is my adapted code -
function add_lazyload($content)
{
global $post;
$search = '/src\=\"([^\s]+(?=\.(bmp|gif|jpeg|jpg|png))\.\2)\"/';
$content = replacer($content, $search, '/src/', 'data-original');
$search = '/img\ class\=\"/';
$content = replacer($content, $search, '/class\=\"/', 'class="lazy ');
$search = '/alt/';
$content = replacer($content, $search, '/alt/', 'src="'.get_template_directory_uri().'/library/images/nothing.gif"');
return $content;
}
function replacer($src, $search, $find, $replace)
{
preg_match_all($search, $src, $result, PREG_OFFSET_CAPTURE);
foreach($result[0] as $entry)
{
$org = $entry[0];
$rep = preg_replace($find, $replace, $entry[0]);
$org = "/" .str_replace(array("=",":","/",".","-","_",'"',"'"," "), array("\=","\:","\/","\.","\-","\_",'\"',"\'","\ "), $org). "/";
$src = preg_replace($org, $rep, $src);
}
return $src;
}
add_filter('the_content', 'add_lazyload');
The problem with this code is that it replaces every alt
string (for example in a paragraph) with .../library/images/nothing.gif
, not just the alt image attribute.
Does anyone know how to solve this?
Share Improve this question edited Jun 15, 2020 at 8:21 CommunityBot 1 asked Aug 4, 2012 at 10:21 AlvaroAlvaro 2,5932 gold badges28 silver badges29 bronze badges3 Answers
Reset to default 7instead of replacing the alt tag you could add-an-attribute-to-a-tag
function add_lazyload($content) {
$dom = new DOMDocument();
@$dom->loadHTML($content);
foreach ($dom->getElementsByTagName('img') as $node) {
$oldsrc = $node->getAttribute('src');
$node->setAttribute("data-original", $oldsrc );
$newsrc = ''.get_template_directory_uri().'/library/images/nothing.gif';
$node->setAttribute("src", $newsrc);
}
$newHtml = $dom->saveHtml();
return $newHtml;
}
note: i didn't quite tested this code, so be careful :)
I modified peteroak's excellent solution to convert to utf-8 and stripped the doctype, html, and body from the ouput.
function add_lazyload($content) {
$content = mb_convert_encoding($content, 'HTML-ENTITIES', "UTF-8");
$dom = new DOMDocument();
@$dom->loadHTML($content);
foreach ($dom->getElementsByTagName('img') as $node) {
$oldsrc = $node->getAttribute('src');
$node->setAttribute("data-original", $oldsrc );
$newsrc = ''.get_template_directory_uri().'/images/nothing.gif';
$node->setAttribute("src", $newsrc);
}
$newHtml = preg_replace('/^<!DOCTYPE.+?>/', '', str_replace( array('<html>', '</html>', '<body>', '</body>'), array('', '', '', ''), $dom->saveHTML()));
return $newHtml;
}
add_filter('the_content', 'add_lazyload');
I added some features to Shieeets solution:
- srcset support (changes srcset to data-srcset)
- noscript fallback (displays original image)
- video/embed/iframe support (Youtube and co)
- additional hook to affect thumbnails (in addition to post images)
- classes "lazy" and "lazy-hidden" are added automatically
Here is the PHP code:
// Lazyload Converter
function add_lazyload($content) {
$content = mb_convert_encoding($content, 'HTML-ENTITIES', "UTF-8");
$dom = new DOMDocument();
@$dom->loadHTML($content);
// Convert Images
$images = [];
foreach ($dom->getElementsByTagName('img') as $node) {
$images[] = $node;
}
foreach ($images as $node) {
$fallback = $node->cloneNode(true);
$oldsrc = $node->getAttribute('src');
$node->setAttribute('data-src', $oldsrc );
$newsrc = get_template_directory_uri() . '/images/placeholder.gif';
$node->setAttribute('src', $newsrc);
$oldsrcset = $node->getAttribute('srcset');
$node->setAttribute('data-srcset', $oldsrcset );
$newsrcset = '';
$node->setAttribute('srcset', $newsrcset);
$classes = $node->getAttribute('class');
$newclasses = $classes . ' lazy lazy-hidden';
$node->setAttribute('class', $newclasses);
$noscript = $dom->createElement('noscript', '');
$node->parentNode->insertBefore($noscript, $node);
$noscript->appendChild($fallback);
}
// Convert Videos
$videos = [];
foreach ($dom->getElementsByTagName('iframe') as $node) {
$videos[] = $node;
}
foreach ($videos as $node) {
$fallback = $node->cloneNode(true);
$oldsrc = $node->getAttribute('src');
$node->setAttribute('data-src', $oldsrc );
$newsrc = '';
$node->setAttribute('src', $newsrc);
$classes = $node->getAttribute('class');
$newclasses = $classes . ' lazy lazy-hidden';
$node->setAttribute('class', $newclasses);
$noscript = $dom->createElement('noscript', '');
$node->parentNode->insertBefore($noscript, $node);
$noscript->appendChild($fallback);
}
$newHtml = preg_replace('/^<!DOCTYPE.+?>/', '', str_replace( array('<html>', '</html>', '<body>', '</body>'), array('', '', '', ''), $dom->saveHTML()));
return $newHtml;
}
add_filter('the_content', 'add_lazyload');
add_filter('post_thumbnail_html', 'add_lazyload');