HN 日本語サマリー

← 一覧へ戻る
科学・技術

ガウシアンによるペイント

Painting with Gaussians (yogthos.net)

82 pointsby yogthos14 コメント

要約

本記事では、画像のエッジ情報を利用してデジタルペイント風の画像を生成するインタラクティブなツール開発について解説しています。筆者は、ブラシストロークを計算論的に表現するために2次元ガウシアン分布(スプラット)を採用し、構造テンソルを用いて画像のエッジやテクスチャの方向性・密度を抽出してブラシストロークの形状や配置を決定しました。これにより、従来のグラデーション降下法に頼る手法よりも高速かつ直感的なペイント生成を実現しています。

全文翻訳

2026年8月3日ガウシアンによるペイント昨年、私はエッジを意識したピクセル化ツールを作成し、画像をピクセルアートに変換しました。これは、固定グリッドを画像に単純に適用するのではなく、グリッドを変形させてエッジに追従させることで実現しました。色と明るさのピクセルを伝えるために曲げられたエッジアダプターグリッドを使用することは、エッジをシャープに保ち、ディテールを維持するためにうまく機能しました。その後、同じエッジ情報がデジタルペイントのコンテキストにも応用できることに気づきました。ペイントプログラムは、ブラシストロークをどこに配置するか、どのくらいの大きさにするか、どの方向に流すべきかを決定する必要があります。その多くはすでにエッジにエンコードされています。なぜなら、エッジは領域間の境界を示すからです。これらはオブジェクトの領域の周りの輪郭であり、ブラシがたどるであろうものであり、それらの不在は、いくつかの広いストロークで十分な、一般的に平坦な領域を示します。そこで、デジタルペイントのスタイルでペイントするプログラムを作成できるかどうかを試してみることにしました。そこでは、画像構造から派生したマークがブラシストロークに似るようにします。私の目標は、スライダーをドラッグするとペイントが目の前で再形成されるインタラクティブなツールを作成することでした。このプロジェクトは、Joltをテストドライブし、非自明なプロジェクトの構築にどの程度役立つかを確認する絶好の機会でもありました。この記事では、すべてがどのようにまとまったかを順を追って説明します。うまくいったアイデアとそうでないアイデアを見ていきます。最も重要なのは、最終結果が実際にペイントのようなものに見えるかどうかを見つけることです。なぜガウシアンなのか?最初に考慮すべき質問は、計算論的にブラシストロークとは正確には何かということです。油絵の具やアクリル絵の具のストロークは、色の中央がエッジに向かって薄れていく細長いマークであり、その向きはブラシがキャンバス上をドラッグされた結果です。エッジは半透明であり、ストロークは重なり合っているため、画家は最初に色の広いブロックを置き、次に小さい、より半透明なマークでディテールを重ねて、より細かいディテールを追加できます。2次元ガウシアン分布のスプラットがこのアイデアに驚くほどよくマッピングされることがわかりました。それは、ストロークが着地する平均、それが引き伸ばされ回転される方法を表す共分散行列、および色と不透明度を持っています。共分散は、ブラシの方向とその伸長をエンコードするために使用でき、主軸はストロークに沿って、短軸はそれに沿って配置されます。標準的なオーバーコンポジットでスプラットのフィールドをレンダリングすると、各スプラットがアルファによって背後にあるものを遮蔽することで、マークが重なり合い、ブレンドすることを可能にする自然なペイントモデルと同様の効果が得られます。もちろん、実際の絵の具のような忠実度は得られないため、効果はGIMPやKritaのようなツールを使用したデジタルペイントに近くなります。このアイデアにはすでにDrawingWithGaussiansや2d-gaussian-splatting-Artなどの実装があります。しかし、どちらも勾配降下法を使用しており、ランダムなスプラットをシードし、レンダリングされたフィールドがターゲット画像の外観になるまで、位置、形状、色を繰り返し微調整します。これは遅く、不透明なことで知られているアプローチです。最悪の部分は、最終結果が単に入力画像の損失のある再構築になり、どのような種類のペイントにも見えないことです。画像からエッジ情報を抽出するソリューションはすでにあったので、画像を盲目的に進化させる意味はありませんでした。代わりに、抽出されたエッジは、ディテールがどこにあるか、ストロークの向きとともに、ペイントプロセスをガイドするために使用できます。ディテール密度とピクセルの色があれば、勾配降下法に頼ることなく必要なすべての情報が得られます。基本的に既存の画像をトレースするだけで済みます。実際、どれほど難しいでしょうか?そこで、加法混色を使用する参照ラスタライザーに従い始めました。ピクセル = 背景 + Σ(強度 × 色)。このアプローチは、オプティマイザーがオーバーラップを補償する色を学習するため、フィッティングレジームで機能することがわかりました。残念ながら、ピクセル色から直接数千のスプラットをシードして加法的にレンダリングすると、オーバーラップが大幅に増加します。64x64の画像に1,200個のスプラットを使用すると、一部のピクセルで合計が22.06に達し、画像全体に純粋な白い塊が生成されました。幸いなことに、この問題はアルファコンポジットの標準的なオーバー演算子を使用して解決できます。これにより、各スプラットがアルファによって背後にあるものを遮蔽し、合計色が1.0を超えることがなくなります。このアプローチのもう1つの利点は、画像からサンプリングされた色と不透明度がきれいに分離されることです。エッジはどこにペイントするかを教えてくれますこのセクションのすべての画像は、1つのアイデアを一度にオフにして同じパイプラインを通過させた同じ写真です。同じソース、同じストローク予算、同じ基本サイズなので、各ステップは、その1つのアイデアが何をもたらすかを正確に示しています。私は次のソース写真を使用し始め、アプリを改善し続けるにつれて進捗を記録して、各アイデアが何をもたらすかを示しました。新しいトリックが追加されるにつれて、ペイントがどのように進化するかを見てみましょう。初期レンダラーでは、均一なモザイクのように見える、かなり残念な出力が得られました。各スプラットは同じサイズ、アスペクト比、回転を持ち、同じブロブの規則的なグリッドを生成していました。まだペイントのようには見えません。実際のアナログ画家は、空や滑らかな表面のような平坦な領域にはいくつかの広いストロークを使用し、ストロークを変化させます。次に、エッジや目や生地のようなテクスチャ領域では、より小さいブラシを使用して、オブジェクトの輪郭に沿った多数の細かいストロークを作成します。これをエミュレートする1つの方法は、構造テンソルを使用して画像勾配を計算することです。これは、各ピクセルの色の変化の量と方向をエンコードします。勾配の外積から2x2テンソルが形成され、近傍全体にぼかされます。重要なのは、テンソルの固有ベクトルが3つの重要なことを教えてくれることです。主固有ベクトルは輪郭を横切り、最も強い勾配の方向を示します。副固有ベクトルはエッジに沿って、ブラシストロークの方向を示します。そしてコヒーレンス、つまり固有値の比率は、エッジがシャープな輪郭なのか、等方性のマッシュなのかを教えてくれます。各スプラットは、その位置にあるこのテンソルから独自の共分散を取得し、エッジに沿って引き伸ばされ、伸長はコヒーレンスに比例します。平坦な領域は丸いままですが、エッジはシーンのオブジェクトの輪郭をたどる細くて方向性のあるストロークになります。これは、LitwinowiczとHertzmannによる古典的なペイント風レンダリングトリックです。これが実装されると、少し目を細めると、レンダリングはブラシストロークのように見えるものになり始めました。ここでは、毛皮と帽子のつばが方向を拾い、ひげが現れ始めます。しかし、ここで別の問題に直面しました。構造テンソルは輝度勾配を使用しますが、これはグレースケールであり、肌の色の唇や灰色の壁の青い看板のような等輝度色エッジには見えません。幸いなことに、Di Zenzoカラーテンソルを使用して、RGBチャネルごとにSobel勾配を計算できます。それらの外積を1つのテンソルに合計すると、輝度エッジと同じくらい強く方向性を駆動する色度エッジが得られます。エッジだけでは不十分構造テンソルは方向性を把握する問題は解決しますが、領域の密度については何も教えてくれません。そして、それなしでは、その領域にいくつのストロークが必要で、どのくらい小さくする必要があるかを判断することはできません。エッジ強度を使用してそれを把握し、使用するストロークの数を決定できると思うかもしれません。しかし、そうすると、オブジェクトのテクスチャが完全に失われます。たとえば、砂利道は一貫したエッジ構造はほとんどありませんが、独自の細かいマークに値する高周波ディテールがたくさんあります。一方、滑らかな頬は単一の輪郭エッジを持ちますが、その内部は広く保たれるべきです。逆に、かすかだが本物のエッジ、例えば微妙な布の折り目や遠くの木の枝は、絶対勾配の大きさが小さいですが、レンダリングする必要があります。したがって、単独で依存することは