この記事は最後に更新してから1年以上経過しています。

4.2で始まるiOSの絵文字ケア

説明

WordPress 4.2のベータ1、ベータ2が立て続けにリリースされ、4.2の正式版リリースが近づいています。4.2のポイントの1つは絵文字のクロスブラウザ対応です。ここでの絵文字とは、UTF-8で4バイトのコードが割り当てられている(基本的にはiOSの)絵文字を指します。この絵文字を含んだ投稿が正しく保存できなかったり、iOS以外の環境で意図した通りに表示できないといった問題があり、4.2ではそのような問題を対処をコードが組み込まれています。

今回の絵文字対応について紹介する前に、ここで記載する内容はWordPress 4.2ベータ2のソースコードをもとにしていることをあらかじめお伝えいたします。そのため正式版では内容が変更される可能性がありますので、ご了承ください。

投稿情報の保存

絵文字の問題の1つは、絵文字を含んだデータを標準設定(テーブルのcharsetが'utf8')のMySQLが正常に保存できないこと。この問題の解決策として、MySQL 5.5では'utf8mb4'というcharsetが追加されていますが、サーバー環境によってはこの対処方法を利用できません。

この問題の本質は、標準設定でiOSの絵文字(UTF-8で4バイト)のようなテキストを保存すると、その文字以降が欠落して保存されるところ。その部分をUTF-8で3バイト以内の文字で表現できるテキストに置き換えてあげれば問題は発生しません。そこでWordPress 4.2では、 wp_insert_post関数内で投稿情報をデータベースへ保存する前段階で、「投稿タイトル」「内容」「抜粋」に含まれる絵文字を数値表現のHTMLエンティティに置き換えるようになっています。このアプローチは私自身が公開しているプラグイン「emojin」に似ています。4.2が正式リリースされれば、このプラグインはお役御免になりますね。

iOS以外の環境におけるRSS

もう1つの問題は、iOSの絵文字はフォントに依存しているため、絵文字を含んだフォントがインストールされていない環境では意図した絵文字が表示されないこと。これってガラケー時代にキャリアや機種間で絵文字のイメージが異なる問題に通じるものがありますね。

4.2では、絵文字をimg要素に置き換えるwp_staticize_emoji関数が用意されており、この関数をRSSやメール出力時のフィルターの1つとして登録することで環境依存を回避するようです。絵文字をimg要素に置き換えは単純に行われるわけではなく、code要素やscript要素などの内容はこの置き換えが行われないようになっています。

またimg要素で指定される画像ファイルは、標準では「s0.wp.com」内のpngファイルを参照しています。このサーバーのURLと画像ファイルの拡張子はそれぞれフィルターで変更できるようになっており、テーマやプラグインでオリジナルの画像ファイルを指定できるようになっています。

さてベータ版を告知している公式ブログでは「絵文字関連の問題があったら報告してね」的な記述があります。これまで運用・開発しているサイトで絵文字に関連する問題があった方はその内容を報告しておくといいかもしれませんね。


最終更新 : 2018年05月27日 10:46

お勧め

convert_invalid_entities(2018年5月27日 更新)

string convert_invalid_entities( string $content )
コンテントに含まれる無効なHTMLエンティティを変換する。

wp_die(2019年5月10日 更新)

void wp_die( string | WP_Error $message [ , string | int $title = '' [ , mixed $args = array() ] ] )
エラーメッセージ(ページ)を表示する。

remove_meta_box(2011年8月25日 更新)

void remove_meta_box( string $id, string $page, string $context )
投稿ページのメタボックスを削除(非表示)する。

get_header_image_tag(2018年5月27日 更新)

string get_header_image_tag( array $attr = array() )
カスタムヘッダーのimg要素を取得する。

wp_schedule_single_event(2019年3月20日 更新)

void bool wp_schedule_single_event( int $timestamp, string $hook [ , array $args = array() ] )
一度だけ実行するアクションをスケジュールに登録する。