琉煌・庵三灯寺

VFX・テクニカルアーティスト

ポートフォリオに戻る

うごくメモ帳シェーダー

個人研究開発

3Dシーンを、ニンテンドーDSi・3DSのアニメーション作成ソフト『うごくメモ帳』で描いたように見せるUnityのポストエフェクト。うごくメモ帳の6色までディザリングで落とし込み、ラフな輪郭線を加えます。テックアートの制作日誌を毎日つけながら16日間ひとりで開発し、HLSLで実装、カラーテーブルはPythonで生成しました。

  • 色:3Dルックアップテクスチャが任意のRGBカラーを231段階のディザ色のうち最も近いものに対応づけ、8×8のベイヤーパターンで画面に描画。
  • 輪郭線:シーンの深度と法線にSobelフィルターをかけ、ノイズで手描きらしい線に。
  • 調整項目:彩度、パレット、輪郭線のディテール。
  • 使い方:.unitypackageを任意のURPカメラにポストエフェクトとして追加するだけ。

UnityHLSLURPC#Python

色

3DS版のうごくメモ帳は、黒、白、赤、青、黄、緑の6色で描きます。DSi版は4色です。Pythonスクリプトで、これらの色から2色ずつ選んだすべての組み合わせを8×8のベイヤー行列で17段階に混ぜて231の色調を作り、ディザパレットとして保存しました。

次に、シェーダーは画面上のあらゆる色について、最も近い色調を見つける必要があります。ピクセルごとにパレットを探索すると遅いため、2つ目のスクリプトでRGBキューブ全体の答えを3Dルックアップテクスチャ(LUT)として事前に計算し、C#のエディタースクリプトでUnityのTexture3Dに変換しました。その赤と緑のチャンネルには、ディザパレット内で対応する色調の位置が入っています。シェーダーはその位置を読み取り、ピクセルのスクリーン座標(8で割った余り)を使ってパターンの正しいテクセルを選びます。

「最も近い」の意味は、距離の測り方しだいです。RGB、HSV、CIELABの距離を比較しました。HSVは結果がちぐはぐで、見せた友人たちはRGBのマップを気に入ったので、シェーダーではRGBを使っています。

6色のパレットでは、くすんだシーンが灰色になってしまいました。そこで、パレット処理の前に小さなシェーダーでシーンの彩度を上げています。

ディザリングした4つのカラーマップ:3DSとDSiのパレットを、それぞれCIELAB距離とRGB距離で対応づけたもの

輪郭線

カラー画像だけでエッジ検出をすると、同じ色の2つのオブジェクトの境目を見逃し、影に輪郭線を引いてしまいます。そこでSobelフィルターは、代わりにデプス・ノーマルテクスチャ(シーンの法線に深度を掛けたもの)にかけています。

フィルターは各カラーチャンネルの変化を測り、最大のものを採用します。輝度だけを使うより少し負荷は上がりますが、明るさの近い色どうしの境目も検出できます。

うごくメモ帳の線はきれいというよりラフなので、疑似乱数のオフセットで輪郭線のサンプルをひとつずつ少しずらしています。輪郭線は、ディザリングした色の上に合成します。

改善したい点

デモ動画を作っている最中に、フレーム落ちに気づきました。各ピクセルはルックアップテクスチャ、次にディザパレットの順にサンプリングしています。この2つを統合すればサンプル呼び出しを1回減らせますし、ノイズ関数ももっと軽くできるはずです。

クレジット

テスト用のシーンは、JustCreate、karboosx、Polygonal MindによるUnity Asset Storeのパックです。うごくメモ帳のカエルのスプライトはthatmusicweeb作。シェーダーの世界への入り口になったのは、Acerola と Freya Holmér の動画、そして Ronja のチュートリアルでした。