Webpの向き不向き

Webpの向き不向き

WebpにはLosslessとLossyの2つのオプションがある。常識的に考えて、Losslessはファイル容量がデカくなりがちで、ファイル容量を小さくしたければLossyを使えばいいと思うが、意外とそんなことないので、用途を考えて使い分けましょうという話。

ウェブ用の画像形式 | WebP | Google for Developers
ウェブ用により小さい画像を作成するこの画像形式の詳細や、G4 Converter のダウンロードやサポートのためのリンクを確認できます。

最近、ScanSnapのix1300で本をスキャンするようになった。白黒の最高解像度でスキャンをする場合、PDFで画像が出力される。PDFよりも汎用的な画像ファイルのほうが都合がいいので、pdfimagesで画像を抜き出している。

PDFから画像をTiffで抜き出す

PDFが一個だけ

$base = (Get-Item *.pdf).BaseName; pdfimages -tiff *.pdf temp; Get-ChildItem temp-*.tif | ForEach-Object { Rename-Item $_ ($_.Name -replace '^temp-',"$base-") }

複数PDF

Get-ChildItem *.pdf | ForEach-Object { $base = $_.BaseName; pdfimages -tiff $_.Name temp; Get-ChildItem temp-*.tif | ForEach-Object { Rename-Item $_ "$base-$($_.Name -replace 'temp-','')" } }

Lossy Webpに変換

そのまま出力してもあまり使いやすくないので、TIFFに出力し、それをcweb.exeでWebpに変換している。

Get-ChildItem *.tif | ForEach-Object { cwebp -q 82 -m 6 -af -mt "$_" -o "$($_.BaseName).webp"; if($LASTEXITCODE -eq 0) { Remove-Item $_ } }

深く考えずに、Lossy Webpに変換していたのだが、なんとTIFFファイルよりもファイル容量が大きくなったので、びっくり。

Lossless Webpに変換

ダメ元でLossless Webpに変換したら非常に小さなファイル容量になった。

Get-ChildItem *.tif | ForEach-Object { cwebp -lossless -z 9 "$_" -o "$($_.BaseName).webp"; if($LASTEXITCODE -eq 0) { Remove-Item $_ } }

Losslessの方が小さい?なんで?

Lossless WebPは、PNGと同様に画像の冗長性やパターンを利用して圧縮しする。つまり、単純な画像(白黒スキャン、図表、ロゴ、アイコンなど)では圧縮率が非常に高くなる。色の繰り返し、エッジの鮮明さ、パターンが多いほど効率的。

Lossy WebPは、写真のような複雑な画像向けに設計されていて、複雑なグラデーションや自然な質感を効率的に圧縮する。単純な画像だと、そのアルゴリズムが逆に非効率になることも

白黒スキャン画像は色数が少なく繰り返しパターンが多いので、Losslessが大活躍するわけ。

逆に、カラースキャンのように、輪郭に中間色が入ってくるようになると、効率はガクッと下がる。

📄
スキャン文書・図表・ロゴ → Lossless
  • 文字がぼやけない
  • ファイルサイズも小さい
🖼️
写真・複雑なグラフィック → Lossy
  • 圧縮率が高い
  • 視覚的な劣化が少ない

じゃあ何を使えばいいのよ?

基本的にはLossy Webpを使っていればいい。白黒スキャンしたドキュメントなど、TIFFやPNGでも小さい画像はLossless Webpを検討してもいいかなという感じ。

Read more

Boids

群れに指揮者はいない 鳥の群れは、誰かが指示を出しているわけではない。魚の群れも同じ。それぞれが周囲を見て、少しだけ動く。その繰り返しが、全体として秩序ある動きを生む。 これを1986年にCraig Reynoldsがコードで再現した。名前は Boids(bird + oid)。個体に与えるルールは3つだけ。 1. Separation ── 近すぎたら離れる 2. Alignment ── 周囲と同じ方向を向く 3. Cohesion ── 群れの中心に寄る これだけで、群れは群れらしく動く。 なぜ作ったか 群れの動きは、見ていて飽きない。 * 単純なルールから複雑な動きが生まれる ── 創発(emergence)の典型例。設計していないのに、設計したかのように見える。 * 自分のブログに置きたかった ── 静的なページに、動くものがあると空気が変わる。 * Web Components で作りたかった ── どこにでも持っていける部品として。 設計の話 見えないときは止める 画面外でアニメーションを回し続けるのは無駄。Inte

By Sakashita Yasunobu

Days Elapsed

一年を「面」で見る 一年は365日。数字で見ると多いけど、並べてみると案外少ない。 12ヶ月を並べて、過去を塗りつぶして、今日を光らせる。それだけのカレンダーを作った。進捗バーが「一次元」なら、これは「二次元」の進捗表示。 Year Progress一年は50週ちょっとしかない 2026年を週で数えると、52週とちょっと。 カレンダーで見ると長そうなのに、週で数えると急に短くなる。そんな感覚を形にしたくて、このページの上の方に進捗バーを置いた。 やっていることは単純で、「今年が何%進んだか」をリアルタイムで表示しているだけ。 なぜ作ったか 理由は3つある。 1. 時間を「量」として見たかった ── イベントや予定ではなく、単純に「どれだけ経ったか」を数値で見たかった。 2. 目に見える形にしたかった ── 抽象的な「一年」を、動く数字に落とすとどう感じるか試したかった。 3. 自分の場所に置きたかった ── 誰かのツールを借りるのではなく、自分のブログに自分で作ったものを置きたかった。 実装の話 せっかく作るなら、

By Sakashita Yasunobu

Year Progress

一年は50週ちょっとしかない 一年を週で数えると、52週とちょっと。 カレンダーで見ると長そうなのに、週で数えると急に短くなる。そんな感覚を形にしたくて、このページの上の方に進捗バーを置いた。 やっていることは単純で、「今年が何%進んだか」をリアルタイムで表示しているだけ。 なぜ作ったか 理由は3つある。 1. 時間を「量」として見たかった ── イベントや予定ではなく、単純に「どれだけ経ったか」を数値で見たかった。 2. 目に見える形にしたかった ── 抽象的な「一年」を、動く数字に落とすとどう感じるか試したかった。 3. 自分の場所に置きたかった ── 誰かのツールを借りるのではなく、自分のブログに自分で作ったものを置きたかった。 実装の話 せっかく作るなら、それなりに丁寧にやりたかった。 * Web Components で実装。ブログのCSSやDOMを汚さず、どこにでも持っていける。 * requestAnimationFrame で描画。固定間隔のタイマーではなく、画面更新に同期させることで滑らかさとリソース効率を両立。 *

By Sakashita Yasunobu