web-dev-qa-db-ja.com

Lazyloadプラグインの画像属性を置換する(data-src)

Jquery lazyloadプラグインを適用したいです。これが機能するためには、data-srcという新しい属性を作成し、そこにsrc値を配置してから、そのsrc値を特定の値'...nothing.gif'に置き換える必要があります。 wordpress.orgのサポートに 解決策が見つかりました

これは私の改作コードです -

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');

このコードの問題は、alt image属性だけでなく、すべてのalt文字列(例えば段落内)を.../library/images/nothing.gifに置き換えることです。

誰もがこれを解決する方法を知っていますか?

4
Alvaro

altタグを置き換える代わりに、 タグに属性を追加する

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;
}

注:私はこのコードを十分にテストしていないので、注意してください:)

7
pcarvalho

私はpeteroakの優れた解決策をutf-8に変換するように修正し、doctype、html、bodyを出力から取り除きました。

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');
7
Shieeet

私はShieeetsソリューションにいくつかの機能を追加しました:

  • srcsetのサポート(srcsetをdata-srcsetに変更)
  • noscriptの代替(元の画像を表示)
  • ビデオ/埋め込み/ iframeのサポート(YouTubeと共同)
  • (投稿画像に加えて)サムネイルに影響を与えるための追加のフック
  • "lazy"および "lazy-hidden"クラスは自動的に追加されます

これがPHPコードです。

// 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');
1