Android WebView で明朝体フォントをアプリ内アセットから読み込む方法

これまでのあらすじ

Q. じゃあどうすればいいのか?

解決方法

A. WebViewClientshouldInterceptRequest メソッドを実装しましょう。

override fun shouldInterceptRequest(view: WebView?, request: WebResourceRequest?): WebResourceResponse? {
  return if (request.url.toString() == "https://0.0.0.0/NotoSerifJP-Regular.woff2")) {
    WebResourceResponse(
      "application/font-woff2",
      "UTF-8",
      200,
      "OK",
      mapOf(HEADER_ACCESS_CONTROL_ALLOW_ORIGIN to "*"),
      context.assets.open("NotoSerifJP-Regular.woff2")
    )
  } else {
    super.shouldInterceptRequest(view, request)
  }
}

そして、 NotoSerifJP-Regular.woff2 を呼び出すように CSS を書き換える。

@font-face {
  font-family: "NotoSerifJP";
  src: url("https://0.0.0.0/NotoSerifJP-Regular.woff2");
}

うっかりこの仕組みが動かなくなった後に HTTP Request が漏れないようダミー URL として 0.0.0.0 を指定しているけど、自分が管理しているウェブサーバでウェブフォントを配信しているならそこに向けても良いかもしれない。

ただし GoogleFonts にするのはダメで、それはグリフごとに別々の woff ファイルを作って配信効率を良くしようとしているので、今回のような単一の woff ファイルでの置き換えが出来ないからである。

所感

解決してみれば、そういうものだなって感じがするけど、ググっても出てこないので非常にめんどくさい。

Android WebView で明朝体を表示したいが、ウェブフォントを直接指定するのでは困る人は結構いそうなものだけど…。

追記