動画やTwitter, Facebook投稿などを埋め込む、HTMLのiframeタグの遅延読み込みがWP5.7でデフォルトになりました。画像はすでにデフォルトになっているので、WordPressは遅延読み込みをコンプリートすることになります。
Lazy-Loadingとは?
最近のWebサイトでは動画などがスクロールで表示されてはじめて読み込みが行われます。これをLazy Loadingと言います。
これまではJavaScriptで処理を行なっていましたが、2020年、HTML5の標準仕様になりました。くわしくはこちらをどうぞ。
動画をサイトページの下の方に埋め込んだとき自動再生がオンになっていて、いきなり音声だけが流れてびっくりすることがあります。
Lazy-loadingでは、動画を埋め込んだところにスクロールしたときに読み込みが始まるので、自動再生でもびっくりするようなことはありません。
会社のPCでエロいサイトに行ってしまって、いきなりイヤラシイ音声が流れるような恥ずかしいことも回避... とはいきませんが。
(喘ぎ声が流れるタイミングが後ろにずれるだけ。というか他人が作ってるのでコントロールできない。)
ブラウザの対応状況に注意が必要
Lazy-loadingはHTML5の標準仕様になりましたが、まだまだブラウザの対応状況はいいとは言えません。
2021年3月30日現在、全体の進捗で完全対応済が70%に届いてませんが、未対応ブラウザでおかしな挙動をするわけではなく、たんに遅延読み込みをしないだけなので、実装しない理由にはならないでしょう。
また、画像に比べて動画の対応状況はさらに悪いです。Google派、Apple派というものがあるのか分かりませんが、あるとすれば対応しているのはGoogle派。
AppleのOperaは対応していません。これは画像も同じ。
(ブラウザの設定で対応可能。)
そして動画特有のものとしてFirefoxは未対応です。
WordPress5.7はiframe遅延読み込みがデフォルト
WP5.5での画像遅延読み込みに続き、WP5.7ではiframeの遅延読み込みがデフォルトになりました。
ユーザーはとくに何もする必要はありません。次の機能を使って<iframe>をHTMLに出力しているものはloading="lazy"が自動追加されます。
(過去記事も追加される。更新しなくていい。)
the_content() get_the_content() | 記事コンテンツ内のiframe |
the_excerpt() get_the_excerpt() | 記事の抜粋内のiframe |
widget_text_content フック | テキストウィジェット内のiframe |
imgとiframeの挙動のちがい
ただしひとつだけ画像と違う点が。
画像ではwidth, height属性もデフォルトで付けます。ブロックのオプションでサイズ変更ができますよね? この機能のおかげで、WordPressでは<img>にwidth, height属性を付けることになっています。
しかし、動画、TwitterやFacebookなどのSNS投稿などで使うiframeにはサイズ指定がありません。
ここがポイントで、WordPressのLazy-Loadingの自動付加はHTMLのwidth, height属性が両方ともあるものだけに追加されます。
画像はwidth, height属性も付けるので気づかなかった仕様。
WordPress Codex 日本語版
WordPress.orgリファレンス
テンプレートに直接書いたものは未対応
テンプレートに直接書いたHTML、また、カスタムで作ったPHPプログラムが出力するHTMLには自動追加されません。
当たり前っちゃ当たり前ですが、そこまでWordPressは見れません。
自分で書いたものは自分の責任でloading属性を追加しましょう。
カスタムのPHPプログラムでも、WPの関数を使ってiframeのHTMLを作成すれば自動追加もできなくはないですが、WPのソース解析が必要なのであまりこれをする人はいなんじゃないでしょうか?
(チャレンジするのはあり。)
Twitter, Facebook投稿埋め込みブロックは未対応
WordPressでは、TwitterやFacebookなどの投稿埋め込みをURLの指定だけでできる便利なブロックがあります。
oEmbedを使った各種サービスの埋め込み用ブロック。oEmbedはURLから各サービスの埋め込みHTMLを作成するプロトコル(ここではプログラムのパッケージのような意味)です。
わざわざ自分で各サービスから埋め込み用HTMLをコピペしなくていい。
iframeのHTMLを作成するのはoEmed
このoEmbedを使ったブロックではoEmbedのプログラムがHTMLを作成するため、iframeにwidth, height属性を付けるかどうかをWordPressは関知しません。
WordPressのドキュメントでも『oEmbedがwidth, height属性を付けたら遅延読み込みの自動付加をします』と言っています。
ちなみに、Twitter, Facebookはコンテンツのサイズをstyle属性を使ったCSSのwidth, heightプロパティで行っているので遅延読み込みはしません。
適当にTwitterとFacebookの投稿を埋め込みブロックを使って貼り付けます。HTMLを確認してみてください。
WordPress.orgサポート
Twitterブロックを使った投稿の埋め込み
Facebookブロックを使った投稿の埋め込み
iframeにwidth, height属性がついてないのは2021年3月30日現在の話で、oEmbedの今後の仕様で変わる可能性があります。
今後、ボクが言ってることと結果がちがっても『間違ってるじゃないか!』と言わないでね?
Youtube埋め込みブロック。ナゾの未対応
もうひとつ、Youtubeブロックでの埋め込みをしてみましたが、ここではちょっと違う結果が。
YoutubeではoEmbedが作るHTMLのiframeにwidth, height属性をつけます。でも loading="lazy" 属性がつかない。
Youtubeブロックを使った動画埋め込み
(余談)かっこいい。何年経っても聞いてそう。
カスタムHTMLブロックを使って各サービスから取得した埋め込みHTMLを使えば遅延読み込みができます。
カスタムHTMLブロックを使ったYoutubeの埋め込み
(余談)ハードロック愛はないけど、なんかいい。はるか彼方の昔のこわ~い高校生を思い出す。いやホントに恐かった。リアル『クローズ』だったもん。マジで。
もちろんですが、iframeタグのwidth, height属性は指定しないといけません。
iframe遅延読み込みのカスタマイズ
『自動追加されると困るんだけど?』という人のためにカスタマイズ用のフィルターが用意されています。
フィルターでごちょごちょするのは、WordPressのカスタマイズでは毎度おなじみなのでかんたん。
サイト全体を変更することもできるし関数ごとにもできます。
Lazy-Loadingの有効/無効
まずは、自動追加されるLazy-Loadingを無効化する方法です。
ぜんぶ無効化することもできるし関数ごとに設定できます。'wp_lazy_loading_enabled' フックを使います。
このフックはWP5.5の画像遅延読み込み処理のときに追加されたもので、画像の遅延読み込みと共同で利用します。
WP5.7での修正はかんたんで対応するタグ名に 'iframe' を追加しただけ。使い方も画像のときと同じです。
add_filter( 'wp_lazy_loading_enabled', '__return_false' );
全無効化は用意されている __return_false() を使うだけなのでかんたん。次は、投稿・固定ページなどの本文で使うiframeタグだけを無効化したサンプルです。
add_filter( 'wp_lazy_loading_enabled', function( $default, $tag_name, $context ) {
if ( 'iframe' === $tag_name && 'the_content' === $context ) {
return false;
}
return $default;
}, 10, 3 );
パラメータ | 内容 |
---|---|
default | 有効/無効。 初期値: true |
tag_name | HTMLタグ名 'img' 'iframe': WP5.7で追加 |
context | Lazy-Loadingを使う関数名。 関数ごとに制御するのに使う。 'the_content' 'the_excerpt' 'widget_text_content' |
関数戻り値 | true: Lazy-Loading有効 false: Lazy-Loading無効 $default: 変更なし |
<iframe>のloading属性値の変更
WP5.7で自動追加する<iframe>のloading属性値は 'lazy' です。これは画像でも同じ。
画像では 'wp_img_tag_add_loading_attr' フックを使います。ただ名称を見てもわかるように、iframeでは使えません。
WP5.7では、新たなフック 'wp_iframe_tag_add_loading_attr' が追加され、名称の 'img' が 'iframe' に変わっただけ。フィルターで引き取るパラメータも同じで使い方も同じ。
画像で使ったことがある人は感覚的に分かるでしょう。
サンプルでは、投稿ページ・固定ページなどで埋め込んだYoutubeだけを無効化しています。
(さっきのフィルタではできなかったコンテンツごとの無効化もできる。)
add_filter( 'wp_iframe_tag_add_loading_attr', function( $value, $iframe, $context ) {
if ( 'the_content' === $context && false !== strpos( $iframe, 'youtube.com' ) ) {
return false;
}
return $value;
}, 10, 3 );
パラメータ | 内容 |
---|---|
value | loading属性値。 デフォルト: 'lazy' 'eager' : 通常読み込み。 false: 無効 |
iframe | <iframe>のHTML全体。 属性も含む。 |
context | Lazy-Loadingを使う関数名。 さっきと同じ。 'the_content' 'the_excerpt' 'widget_text_content' |
関数戻り値 | 'lazy' : Lazy-Loading 'eager' : 通常読み込み false: 無効 $value: 変更なし |