I need to change src
to data-src
for iframes inside Wordpress content and add class lazy
. I was trying this:
function iframe_image_lazy_load($the_content) {
$thecontent = get_the_content();
if(!empty($thecontent)) {
libxml_use_internal_errors(true);
$post = new DOMDocument();
$post->loadHTML(mb_convert_encoding($the_content, 'HTML-ENTITIES', 'UTF-8'));
$iframes = $post->getElementsByTagName('iframe');
foreach( $iframes as $iframe ) {
if( $iframe->hasAttribute('data-src') ) continue;
$clone = $iframe->cloneNode();
$src = $iframe->getAttribute('src');
$iframe->removeAttribute('src');
$iframe->setAttribute('data-src', $src);
$srcset = $iframe->getAttribute('srcset');
$iframe->removeAttribute('srcset');
if( ! empty($srcset)) {
$iframe->setAttribute('data-srcset', $srcset);
}
$iframeClass = $iframe->getAttribute('class');
$iframe->setAttribute('class', $iframeClass . ' lazy');
};
return $post->saveHTML();
}
}
add_filter('the_content', 'iframe_image_lazy_load', 15);
It's based on other working snippet, but for images. Should this be working?
I need to change src
to data-src
for iframes inside Wordpress content and add class lazy
. I was trying this:
function iframe_image_lazy_load($the_content) {
$thecontent = get_the_content();
if(!empty($thecontent)) {
libxml_use_internal_errors(true);
$post = new DOMDocument();
$post->loadHTML(mb_convert_encoding($the_content, 'HTML-ENTITIES', 'UTF-8'));
$iframes = $post->getElementsByTagName('iframe');
foreach( $iframes as $iframe ) {
if( $iframe->hasAttribute('data-src') ) continue;
$clone = $iframe->cloneNode();
$src = $iframe->getAttribute('src');
$iframe->removeAttribute('src');
$iframe->setAttribute('data-src', $src);
$srcset = $iframe->getAttribute('srcset');
$iframe->removeAttribute('srcset');
if( ! empty($srcset)) {
$iframe->setAttribute('data-srcset', $srcset);
}
$iframeClass = $iframe->getAttribute('class');
$iframe->setAttribute('class', $iframeClass . ' lazy');
};
return $post->saveHTML();
}
}
add_filter('the_content', 'iframe_image_lazy_load', 15);
It's based on other working snippet, but for images. Should this be working?
Share Improve this question asked Feb 2, 2020 at 16:33 D_PD_P 1531 gold badge3 silver badges12 bronze badges 3 |1 Answer
Reset to default 0The code snippet in your question is a filter, but it isn't built properly:
- A filter needs a function that takes in the thing to be filtered as the first parameter, and returns the new version
- Your function ignores the first parameter, breaking any changes that have already been made
- Your function doesn't always return a value
So, lets start with the function:
function iframe_image_lazy_load($the_content) {
$thecontent = get_the_content();
if(!empty($thecontent)) {
... do modifications to iframes
return $post->saveHTML();
}
}
add_filter('the_content', 'iframe_image_lazy_load', 15);
First, there are no iframes to modify, those happened on the_content
filter, and got passed in as the parameter, but you ignored that and got the original.
As a result, the string you're working with just contains OEmbed URLs, no iframes. Lets fix that:
function iframe_image_lazy_load($content) {
if(!empty($content)) {
... do modifications to iframes
return $post->saveHTML();
}
}
add_filter('the_content', 'iframe_image_lazy_load', 15);
Notice I used variable passed to the function, instead of ignoring it and retrieving the original content. I also fixed the indentation levels, bad indentation is a great way to get bugs.
Next, the if statement is unnecessary, lets turn it into a guard and exit early:
function iframe_image_lazy_load($content) {
if(empty($content)) {
return $content;
}
... do modifications to iframes
return $post->saveHTML();
}
add_filter('the_content', 'iframe_image_lazy_load', 15);
OEmbed Filters
Thinking about these things in terms of HTML strings with iframes in them is a limiting and narrow way to view things. These are OEmbeds! So why not filter OEmbeds
get_the_content
anyway? There's also noreturn
value at the end, filters must always return but this filter only returns if$thecontent
is not empty – Tom J Nowell ♦ Commented Feb 2, 2020 at 16:53