WordPressの投稿でSVG画像を使えるようにしても、OGPやTwitter Cardsで対応してなかった件

Advertisement

svg-on-wordpress-and-sns

イメージオプティム でPNG画像を最適化すると、やたらと時間がかかるなぁと思ってTwitterでつぶやいたら「さっさとSVGに行けと言う啓示なのでは?笑」というコメントをいただきました(笑)。最近このブログに使う画像はSVGに最適なイラストが多いですし、ファイルサイズを小さくできて高解像度のディスプレーにも対応できるので確かにメリットがありそうです。

そこで早速WordPressの投稿にSVG画像をアップしようと思ったんですが。。。メディアアップローダーでは以下のようなメッセージが出てきてアップさせてもらえませんでした。デフォルトではサポートされてないんですね。ちょっと驚きました。

svg-not-supported-on-wordpress

ということで、今回はWordPressの投稿でSVGを使うために必要なカスタマイズや関連する設定をまとめてみます。WordPressでSVGを使いたい!という方の参考になれば幸いです。

目次

WordPressの投稿でSVG画像を扱えるようにする方法

プラグインをインストールする方法

プラグインを入れた方が簡単なので、SVG Support というのを入れました。このプラグインをインストールすると、メディアアップローダーでSVGをアップロードできるようになり、画像一覧でもSVGの内容が表示されるようになります。

svg-supported-on-wordpress

プラグインを入れたくない場合は、以下の方法もあります。

functions.phpにフィルターを追加する方法

functions.phpにフィルターを追加して、WordPressのメディアアップローダーでSVGを扱えるようにする方法 で、以下をfunctions.phpに追加します。

function custom_mime_types($mimes){
  $mimes['svg'] = 'image/svg+xml';
  return $mimes;
}
add_filter('upload_mimes', 'custom_mime_types');

ただ、この方法だと下のキャプチャ画像のようにメディア一覧でSVG画像の内容が表示されません。ファイル名は表示されるんですけどね。

media-library-showing-svg-file-names

この問題をfunctions.phpのカスタマイズだけでどうにか対応できないか探してみたんですが、最終的には先ほどのプラグインのソースコードを見て、結構手間がかかりそうだったので諦めました。

アイキャッチ画像でSVG画像を表示させる

先ほどのプラグインを入れても、functions.phpに上記のフィルターを追加しても、SVG画像をアイキャッチ画像に設定した場合、サムネイルが表示されません。

eye-catch-image-not-showing

これを修正するには、以下のフィルターをfunctions.phpに追加します。

function fix_svg_thumb_display() {
  echo '';
}
add_action('admin_head', 'fix_svg_thumb_display');

これで、とりあえずWordPressの投稿にSVG画像を使えるようになります。あ、あとSVGの表示に対応するために、サーバ側の設定をお忘れなく。

次に、このブログ特有のものでSVG関連のカスタマイズをした部分をまとめておきます。このブログでは、以下の対応をしました。

Facebook OGPやTwitter Cardsへの対応

さて、これでWordPressの投稿でSVG画像を使えるようになったわけですが、Facebookの投稿やTwitter CardsではSVGがサポートされていなくて、メタにSVGが指定してあると無視されてしまいます。SNSの影響が大きくなっている昨今、ブラウザのサポート状況だけでなく、SNSで共有された際の表示の確認もウェブサイト運営の必須条件になっています。

functions.phpのカスタマイズで対応する方法

このブログでは投稿で最初に使われている画像を自動でFacebook投稿用のOGPとTwitter Cards用のメタに入れるようにしています。そのため、以下をfunctions.phpに追加しました。

// Function to get the first image in a post
function catch_that_image() {
  global $post, $posts;
  $first_img = '';
  ob_start();
  ob_end_clean();
  $output = preg_match_all('//i', $post->post_content, $matches);
  $first_img = $matches [1] [0];

  if(empty($first_img)){ //Defines a default image
    $first_img = get_bloginfo('template_url') . "/img/rriver-default.png";
  }
  return $first_img;
}

上記の関数で投稿で使われている最初の画像のURLを引っ張ってきます。そして、以下の関数でTwitter CardsとOGPを設定します。

// Add Twitter cards meta
function twitter_cards_for_posts() {
  if ( is_singular() ) {
    global $post;
    setup_postdata( $post );
    $tw_type = '' . "\n";
    $tw_site = '' . "\n";
    $tw_creator = '' . "\n";
    $tw_title = '' . "\n";
    $tw_desc = '' . "\n";
    $tw_image = '' . "\n";
    echo $tw_type . $tw_site . $tw_creator . $tw_title . $tw_desc . $tw_image;
  }
}
add_action( 'wp_head', 'twitter_cards_for_posts' );


// Add OGP meta
function ogp_for_posts() {
  if ( is_singular() ) {
    global $post;
    setup_postdata( $post );
    $og_title = '' . "\n";
    $og_type = '' . "\n";
    $og_url = '' . "\n";
    $og_image = '' . "\n";
    $og_desc = '' . "\n";
    echo $og_title . $og_type . $og_url . $og_image . $og_desc;
  }
}
add_action( 'wp_head', 'ogp_for_posts' );

こういう仕様にしているので、このブログのWordPressではSVGを投稿の最初の画像に使うと、せっかく指定したOGPやTwitter Cardsの画像が無視されてしまいます。そのため、先ほどのcatch_that_image()という関数に、以下のコードを追加して投稿に使われている最初の画像がSVGの場合、メタに指定する画像ファイルの拡張子をPNGに変更するようにしました。

  if(strpos($first_img, 'svg') !== false){
    $first_img = preg_replace('/svg/i', 'png', $first_img);
  }

SVGと同じファイル名のPNG画像を別途アップロードする必要があるので、運用でカバーしないといけませんが、僕にとってはこっちの方が楽なのでこのような対応にしました。

「All in One SEO Pack」プラグインを活用する方法

OGPやTwitter Cardsへの対応は「All in One SEO Pack 」というプラグインでもできます。「All in One SEO Pack」の使い方はバズ部 さんの「All in One SEO Pack の設定方法と使い方 」という記事で詳しく紹介されています。

一般的にはこのプラグインで対応したほうが良さそうですね。

SVG非対応のブラウザ向けの対応

IE8など、SVGをサポートしていないブラウザに対応するために、SVG画像が投稿に挿入される際は以下をimgタグに追加するようにしました。

<img src="path/to/image.svg" onerror="this.src='path/to/fallback-image.png';this.onerror=null;">

このブログでは、functions.phpにカスタマイズを追加してimgタグが挿入される際にwidthheightを削除するようにしているので、同じ関数を使って画像がSVGの場合は上記コードを追加するようにしました。

// Remove img attributes and add svg fallback
function my_remove_img_attr($html, $id, $alt, $title, $align, $size){

  $html = preg_replace('/ width="\d+"/', '', $html);
  $html = preg_replace('/ height="\d+"/', '', $html);
  $html = preg_replace('/(alignnone| size-full )/', '', $html);

  if(strpos($html, 'svg') !== false){
    $output = preg_match('/<img.+src=[\'"]([^\'"]+)[\'"].*>/i', $html, $matches);
    $output = preg_replace('/svg/i', 'png', $matches[1]);
    $add_attr = "onerror=\"this.src='" . $output . "'; this.onerror=null;\" />";
    $html = preg_replace('/\/>/', $add_attr, $html);
  }

return $html;
}
add_action( 'get_image_tag', 'my_remove_img_attr', 1 ,6);

フォールバック用のPNG画像がすでにアップロードされていることを前提としているので、ベストな対応ではないですが、こちらも運用でカバーすることにしました。

SVGのフォールバックの方法はいろいろある んですが、一番手間がかからずシンプルなので、ハック的な対応ですけど、この方法を選びました。

サーバサイドで処理ができたらいいのに

ここで紹介した対応では運用側の手間が増えてしまうだけでなく、WordPress側でエラーチェックをまったくしてないので、クライアントに納品できるような代物ではないことは確かです。SVGをアップロードしたらサーバ上で自動でPNGを生成、最適化、保存して、それをフォールバックに指定するような仕組みが作れたら良いんですが、なかなかハードルが高そうです。ImageMagickとか使ったらできそう だけど。

WordPressのコアでこういった対応がされるとか、お金を持っているFacebookとかTwitterがSVGに対応してくれれば良いんですけどね。タイムラインへの投稿やつぶやきにSVGを使ったら、自動でPNGに変換して保存してくれたら。。。

とりあえず、このブログは自分だけが使うものなので、今のところは上記の対応で良しとしようと思います。

アイキャッチ画像設定のひと手間

もう一つ手間がかかるのが、アイキャッチ画像のために別途SVGを用意する必要があるところです。このブログでは数ヶ月前にトップページでサムネイル画像を表示するようにしたので、Post Thumbnail Editor というプラグインをインストールして使ってたんですけど、これがSVGに対応していません。

そのため、別途サムネイル用にSVGを書き出してアップロードする必要があります。また、このアイキャッチ画像にフォールバックを設定する場合は、先ほどの要領でPNGを指定するなどのカスタマイズが必要になります。ここまでくると、もうPNGでいいか。。。と、なっちゃいそうです。汗

まとめ

今回の設定をしてみて、SNSでシェアする場合にSVGがサポートされていないとか、SVG非対応のブラウザ向けのフォールバックの対応に手間がかかるなど、SVGを気兼ねなく使えるようになるまでには、まだ、いくつか解決すべき課題が存在することを再認識しました。SVGを使おうと思うと、ひと手間もふた手間も増えてしまうので、導入の障壁になってしまいます。簡単じゃないですね。

SVG非対応のブラウザへの対応は、それらブラウザのシェアがなくなるのは時間の問題だと思いますが、SNS対応の方は、どうにか手間のかからない解決策を考えないと、SVG普及の妨げになってしまうような気がしています。

参照・参考サイト

以下のサイトを参考にさせてもらいました。ありがとうございました!

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です