2023/03/16:軽量化モデルのリンクを追記。binary
のモデルを追記しscribble
系を調査して加筆。T2i Adapter
の項を追加。その他細かい記事修正。
2023/03/04:古い情報を修正。推定モデルにDepth_leres
,pidinet
を追加。Allow detectmap auto saving
の設定を追加。Guidance Start(End)
を追加。
この記事はStable Diffusion
のExtensionであるControlNet
のより深い解説を目指す。
更新がとても頻繁に行われており、まだエクステンションの機能は網羅できていない。
逐一更新する予定。
例で見たほうが早いので紹介する。
まず先日自作したウマ娘の洋服を着せたCGモデルの画像を用意する。
※これは自作画像なのでAIは一切通していない(モデル素体はMD付属)
img2img
でDenoising strength
を0.1
に設定すると元のイメージを維持した絵が出てくる。
実際に作成したのが次。
確かに維持したまま絵が書かれたが、ほとんど同じものになるので手書き風エフェクトを加えた程度の変化といっても良い。
前回の作例ではむしろそれを狙って使用した。
つまり色を塗り替えたり、洋服のデザインを変更したりはできない。
もっとポーズを一致させた他のキャラにしたい場合や、線画だけの絵に色を付けたいなどのコントロールをしたい。
そこで登場するのがControlNet
。
私が試した例だと、次のような出力ができた。
ポーズを維持したまま赤髪+赤い洋服になっている。いちばんよく出来た例。
全く同じ設定で、茶色系が出力された。
表情がイマイチだが、背景に逆光が追加された。
制服が黄色になった。服のディティールがよく出ている。
部屋のような背景が浮き出した例。こちらもキャラクターのシルエットは高品質で維持されたままだ。
このように、もとのイラストのポーズや線画を維持したまま新しいイラストを生成できる。
つまりアウトプットされるイラストを思い通りにコントロールできる可能性が増えたといえる。
以前は白黒の線画を維持したまま色を付けるなどは難しかった。
このアルゴリズムを考えた大元は次のモデル。
GitHub - lllyasviel/ControlNet: Let us control diffusion models
そしてこれを使いやすくautomatic1111氏のweb UIに対応させたのが今回利用させていただいたもの。
GitHub - Mikubill/sd-webui-controlnet: WebUI extension for ControlNet
この場を借りて公開に感謝いたします。
恐らくここ以降の記事を読むユーザーはStable Diffusion
のweb UIには詳しい人が多いだろうという想定なので冗長になりそうな箇所を省略している。
Web-UIのExtension
で導入する。
リポジトリのURLを貼り付けるだけでインストールできる。
URL: https://github.com/Mikubill/sd-webui-controlnet.git
2023/03/04時点ではExtension
のリストから検索してもインストールが出来る模様。
Web-UIからインストールするとエラーになる場合がある。
その場合は次のようにextensions
フォルダ下でgit clone
してやれば完了。
opencv-python
も別途必要らしく念のため入れている。
%cd stable-diffusion-webui/extensions/
!pip install opencv-python
!git clone https://github.com/Mikubill/sd-webui-controlnet.git
ControlNet
はインストールしただけでは動作しない。
輪郭やポーズを抽出するモデルを別途入れる必要がある。
次のサイトに抽出する手法別にデータが分かれているので欲しい物をDLする。
上記モデルはフルサイズのようなので、サイズが大きいと思ったら軽量化の次でもよい。
この追加のモデルに関しては次の項で解説する。
上で説明した推定するモデルについて、それぞれがどういうものかを一覧にしておく。
ファイル名:control_sd15_canny.pth
canny
はイラストから輪郭を抽出して、それを線画として絵を書いていくモデル。今回利用したのはこれ。
線画に色を付けたい、元のイラストイメージをほとんど壊さず別の絵にしたい場合はこれかと思った。
内部では上のようなラインを抽出し線画として処理しているようだ。
ファイル名:control_sd15_hed.pth
上のcanny
に似ているが、グレースケール全範囲を利用することによって線の強弱まで取っている?
このモデルは元の画像の細かい書き込みを変化させること無く新しい画像にしたい場合に有用そうに思う。
推定画像
出力画像
Denoising=0.75
にも関わらずディティールを維持したかなり美しい画像となった。
今回は最初からこれを使うべきだったかもしれない。
リペイント目的なら個人的おすすめ。
ファイル名:control_sd15_openpose.pth
openpose
はAIによるモーションキャプチャなどの類だと思われる。人物の四肢の位置を推定しCGのボーンのような棒人間のデータを出力する。
それをもとにイラストを書いていくのでポーズは維持して全く別のキャラクターを作りたい場合に有用。
入力画像から人のポーズを取り出し、それに沿って画像を生成するので
このように全く別キャラだがポーズを維持した画像となる。
2023/03/16:現在、推定モデルがうまく機能していない模様。大きな手を使ってテストしたがうまく指が拾えなかった。
hand専用のモデルが出てくるまでは使用不可能?
次は実際に試してうまくいかなかったものをそのまま掲載。
上の棒人間方式に「手」を加えたもの。
次のような画像が生成される。
よく見ると手が追加されているのが分かる。
手をより正確に出したい場合に有用だとおもわれる。
テストで出力したところ、残念ながら手はそこまで正確ではなかった。
ファイル名:control_sd15_depth
画像の「奥行き」を推定するモデル。
これは3DCGで利用されるDepth Map
と概念的には同じ画像が利用されていると思われる(黒いほうが奥、白が手前)
奥行きなので、キャラが斜めになっていたり、背景と共存している画像に最も強い?
またcanny
やhed
の場合は洋服のシワなどの細かい線も再現されるが、こちらはキャラのシルエットは残して内側は書き換えてしまう、といった場合に有用ではないだろうか。
テストで行った生成では次のようになった。
輪郭がはっきりと維持されている。
Depth
と同じマップだが内部アルゴリズムが違うようだ。
基本的にこれは使わないようにして、通常のDepth
で生成したほうがおおよそ良いものが出来る模様。
ただ、こちらのメリットはより細かい設定が詰めれるようになっているので上級者向け。
次のフォーラムが参考になる。
"Depth_lres" ControlNet options : StableDiffusion
ファイル名:control_sd15_mlsd.pth
こちらは建物や家具といった「直線」を抽出するモデル。
従ってキャラクターには全く無意味となるので注意。
3DCG的には「ハードサーフェス」に適用するとよさそうだ。
ファイル名:control_sd15_normal.pth
ノーマルマップ(法線マップ)を生成し、それを元にするモード。
ノーマルマップは3DCGで使われる概念なので、簡易的に解説すると面の方向が入っている画像データ。
CGでは凹凸がないところ(ローポリな箇所)でライティングや影をコントロールするような使い方をするので恐らくこちらも同じだろう。
自作のノーマルマップを使う方法は後の項目に記載。
ファイル名:control_sd15_scribble.pth
手書きで白黒画像を作り、それをベースに画像を作るモード。
デジタルで書いたラフ画(白黒画像でなくてもよい)を使う場合は最適そうだ。
アナログで書いたラフをスキャンして入れると、線が薄いためうまく拾えない模様。
この場合はbinary
を使うと良さそう(後述)
アウトプットの画像をより元絵に忠実にしたい場合(ざっくり書いたラフではなく、本気で書かれてる線の場合)はhed
推定のほうが良いと思う。
モデルと動作は上とほぼ同じ。
こちらは手書きではない「画像」を一旦手書き風に変換して使う用途。
元画像から線だけ抽出して再描画させるイメージだと思う。
hed
やcanny
と思うと線が太いものになるのでより曖昧な絵になるのではないだろうか。
こちらもscribble
と基本は同じだが、色に対して線の抽出され方が若干違う。
画像データの数値から直接しきい値的に取っている?ようでscribble
と違ってBinary Threshold
というスライダを上下させて線の判定を変化させられる。
詳しくは分かっていないがscribble
でうまく線が拾えない場合はこちらで微調整するのが良いかもしれない。
つまり、アナログ線画のスキャン(線が薄い)や、白黒だけど濃淡がついているラフ絵を使うには効果的そうだ。
scribble
などのpreprocessor
を通して白黒画像化した参考例一覧。
ファイル名:control_sd15_seg.pth
画像を色でわけると、色分けされた箇所で別々のものが描画されるので、独自の構図を作ることができる。
txt2img
で1分で作った適当な画像を入れて実験。
上の画像で想定した通りの構図で部屋が現れる。
「この平面は窓や、この箱はテーブルやな」のような推理を自動でやってくれている感じがすばらしい。
hed
に似た推定画像が出る。hed
よりも輪郭がハッキリしている。
ギターをもったキャラクターから推定する例が次。
ただし、これに対応した公式の推定モデルが存在しない模様。
一応hed
のモデルを使えば生成はできるらしい...のだが全く良いものが作れなかった。
使っているユーザーも少なそうなので今現在はマニア向け。
次のフォーラムが参考になるので貼り付けておく(英語)
"Pidinet" ControlNet preprocessor options : StableDiffusion
上のモデル(pth
)をDLしたらextension
のmodel
フォルダに保存する。
ここはStable Diffusion
本体のmodel
フォルダではないので注意。
従って次のようになるかと思う。
stable-diffusion-webui/extensions/sd-webui-controlnet/models/~~~~.pth
また、これ以外にも推定用のモデルがあれば使える模様。
起動する時にCOMMANDLINE_ARGS
に--xformers
を指定することが求められている。
ローカルPCのCPUオンリーで動かした場合だけこのオプション無しでも動いた。CPUならいらないかもしれない。
Google Colab
を使う場合はこれがなければそもそも起動しないケースを確認。参考まで。
左下にツールが折りたたまれているのでそこからControlNet
をオンにする。
txt2img
だけでなくimg2img
でも使用可能。
Preprocessor
とModel
に先程DLしたポーズ等を抽出するアルゴリズムを指定する必要が有る。基本はどちらも同じもので揃える必要がある。
Preprocessor
とはControlNet
に放り込んだ画像から線などを抽出してくる処理を指している。
例えば、ここにdepth
を指定するということは「元画像自体は何の処理もされていない生の画像」
であり、これのdepth
画像を抽出して、ソレを元にAI絵を書いてね、ということ。
Preprocessor
をnone
にする場合は、自前で(別ソフトで)depth
などの推定画像を自作している場合に利用する。
つまりmodel
は基本的に何か指定しないといけないがPreprosessor
は自前で推定画像を用意したときのみnone
でも良いことになる。
線を抽出する時にコンピュータは「白を線、黒を背景」として認識しているようなので、人間が手書きでよく使う「黒を線、白を背景」とした画像を入力したときに反転してしまう。
こういうときのための反転オプションだと思われる。
手書き画像(黒線、白背景)を入れる時以外は基本はオフで。
Blender
のcomposite
からDepthを出力すると白と黒が逆になるのでこのオプションをチェックすると良い。
オリジナルの解説によるとプロンプトに何も入れないで、推定モデルをいくつか比較する時に使うらしい。
別名ノンプロンプトモードとも。
Sampling steps = 50
, CFG Scale 3 ~ 5
で使うことを推奨。
元画像(segment用)
Guess Mode
なし、Sampling steps = 50
, CFG Scale = 4
、Preprocessor = none
よくある画像が出力。よくも悪くもない。
同じ条件でGuess Mode
をオン
背景が消えてキャラクターがスッキリした。
なんというか曖昧な箇所を自動でハッキリする効果?
同様の設定のままPreprocessor = depth
でdepth
モードでテスト(Guess Mode
オフ)
塗りが甘く、シミが出ている。
同じ条件でGuess Mode
をオン
線がハッキリして、塗りも美しくなった。
とりあえず楽してきれいな画像を作りたい時にプロンプト無しでGuess Modeを使うと良い結果が得られる可能性がある。
とりあえず実験的に生成を試すときはコレを使う価値がありそうだ。
どれぐらいControlNet
側の画像を優先するかの値。
入力サンプル(Depth
)
出力結果とWeight
の値
Weight
は大きく上げると線は再現されるかもしれないが、絵としての質が落ちる印象。上の結果からもそれが分かる。
ControlNet
を使っている限り、あえてこの数値を下げるということも珍しいと思うので基本は1
で良い。
ControlNetの適用を途中から注入(Start)/途中で適用をやめる(End)オプションだと思われる。
例えば次の画像をControlNet
に入れて
デフォルトのStart=0,End=1
だと
こちらはコレまで解説した通り、元映像のリペイント的な使い方。
これをStart=0.1
にすることで、画像生成直後はControlNet
を適用しない状態で開始して、少し遅らせてからControlNet
が入るようになる。
するとどうなるかというと
背景の書き込みが増えたのがわかるだろうか。
つまり、はじめはプロンプト通りの画像(背景的な何か)が生成されながらも後からControlNet
が適用されて真ん中のキャラクターとなっているわけである。
End
はこれの逆で、1より低くすることで画像生成の途中でControlNet
の画像が適用されなくなるのだと思われる。
画像生成順のレイヤー分けのようなイメージで画像を作る場合に役立つかもしれない。
上の画像がなんか好みだったのでアップスケールしてみた。
ちなみにアップスケール(画像を拡大して、細かいところをより書き込む)方法はi2i
で画像をいれた後、画面下部のScript
からSD upscale
を設定する。
自前ノーマルマップを使う場合にオンにする。後ほど解説。
normalやopenposeなどなど殆どの推定画像は別ソフトと互換性がある形式なので自前で用意できる。
ただし設定を理解しないまま各データを入れても、そこからさらに再生性されてしまうので意味がない。
normalを利用する例でメモを残しておく。
まずは自前のノーマルマップをCGソフトで生成。
次にPreprocessor
をNone
にしてModel
をノーマルに設定する(重要)
Normal
の場合はRGB to BGR
をチェック。
OpenGL形式とDirectX形式でノーマルマップの一部出力が逆になることへの対応?
これに関しては自信がないので、出力結果が変になる場合は切り替えて試したほうが良いかも。
txt2img
なら後は通常の流れで生成できる。
img2img
の場合は上記設定のままControlNet
の画像に何も入れないようにしてimg2img
側の画像にノーマルマップを入れても動作するようだ。
githubの議論をざっくり見ていた感じだと、バッチ処理で動画化する時用の措置だと思われる(ControlNet
のUIだけだとバッチができないため)
従って、ノーマル画像を大量に用意しておいてこの方法でバッチにかけることができる。
このときノーマルマップはControlNet
のみならずi2i
用の参照としても使われるので、虹色の出力結果になってしまうことがある。
この解決は下の項で解説
こんどは自前ノーマルマップ+自前画像でリペイントのようなことを行うケース。
つまり1回の生成で2枚の入力画像を使うケース。
この場合はimg2img
側に通常の画像を入れてControlNet
側に自前のノーマルマップを入れれば良い。
この場合は現時点ではバッチ処理は不可能だと思われる。
issue
に要望が上がっていたのは確認したので需要はありそうだ。
i2i
+自作ノーマルを使うと、かなり元画像に近い構造を維持しながらもリペイントできる。
実際にやってみる。
img2img
に入れる元画像
ノーマルマップは上で貼っているものを利用。これをControlNet
の画像に入れる。
この時Denoising strength
は0.3
より小さいぐらいが良いかと思う。
ここを大きくすると出力画像が擦れてしまうような結果となった。
これで生成した画像が次
ノーマルマップを使わずにDenoising strength
を下げただけで出力すると次。
顔の構造に大きく差が出ている。あきらかに上の方が良い。
何度か試したが、ノーマルを使ったほうが顔の構造が正確に表現される。
髪の塗りや、尾ひれの陰影のクオリティも上が高い。
ただ、ノーマルを使った場合でも手は崩れやすいようなので研究が必要。
あまりこだわりがない人にとっては微細な変化かもしれないが、個人的にはかなりの進化。
こだわったリペイントをしたい場合に有効かもしれない。
ControlNet
側の画像は空白でi2i
側にマップ画像を入れることによりバッチ処理が可能になるが、その画像自体もi2i
の参照として使われるのでマップの色が出力に反映されてしまう。
例えば次のようなSegment
用の画像をi2i
に入れ、ControlNet
側に画像をいれない方法で処理してみる。
(Denoising strength = 0.1
)
この場合、ほぼそのままの色で出力されて次の画像となってしまう。
そこでSettings
タブにあるSkip img2img processing when using img2img initial image
オンにすることそれが回避できる模様。
この設定をオンにしてDenoising
を0.1
(かなり元に近い画像になる)
同様のsegment
画像で再出力すると
構図を維持しながらも全く新しい色で画像が生成された。
上の画像を見ると分かるが、この方法を使うと黒背景の入力画像でも出力に背景が挿入される。
現時点でどうしても背景を切り抜いて生成したい場合には使えない。
Settings
タブ > ControlNet
の設定にあるMulti ControlNet
の数値を上げると、上げた数値だけControlNet
のUIが増えて、複数適用できる。
つまりDepth+Segmenetのような同時に複数のマップを利用して画像が生成できる。
設定をApply
した後、UIの再読み込みではなくAutomatic1111
本体から再起動する必要あり。
次のツイートよりtoyxyzさんが面白い使い方を提唱している。
By separately rendering the hand mesh depth and open pose bones and inputting them to Multi-ControlNet, various poses and character images can be generated while controlling the fingers more precisely. pic.twitter.com/Y4B3hYa9jd
— toyxyz (@toyxyz3) February 25, 2023
手とポーズを別々のControlNet
で分けてやることで、今までAIが苦手だった手を正確に表現できることが発見されている。
toyxyzさんがBlenderにて画像生成用プロジェクトを配布してくれている。
Character bones that look like Openpose for blender _ Ver_4 Depth+Canny
こちらを使用して次の画像を用意した(Canny
+ Pose
)
このツールで生成した画像の場合Canny
のときだけpreprocessor
をCanny
に合わせる。それ以外はnone
とのこと。
結果
確かに指と足のラインが出ている。
が、今回ちょっとアグレッシヴな格好にしすぎたかもしれない。ポーズが学習になさそう。
ControlNet
を使用すると推定に使用する画像が自動生成され、それと一緒に出力されるため画像は2枚になる。
これが邪魔な時にオフにできる。
上部のSettingタブ
=> 左側のタブからControlNet
=> Do not append detectmap to output
をチェック
最後に上部のApply settings
を押して保存。
これで生成された画像1枚だけの出力になる。
以前はこれをオンにしないとバッチ処理した時に落ちていたが、現在は落ちなくなっている?
もしバッチでトラブルがあるようならこの設定をオンにしてみると良いかもしれない。
デフォルトでマップ画像(Depth
などのグレースケール画像)は生成はされるが保存されない。
これを保存したい場合はSettings
よりAllow detectmap auto saving
をオンにする。
いくつかエラーがあったのでメモしておく
Google Colab
を使う時グラボではなくメインメモリがオーバーしてしまって落ちるという現象が多々あった。
またローカルで起動しても落ちることがよくある。
かなりメモリを消費している模様。
Stable Diffusion
本体のモデルを変更しようとするとメモリがオーバーしてしまいよく落ちるので、こちらはUI起動後変更しないほうがよろしいかと思う。
Generate
ボタンを押した跡にコンソールにpythonのエラーが出ることがある。
これは殆どの場合Google Drive
からpth
ファイルが正しくコピーされてなかったことが原因だった。
手動でドライブにファイルを格納して、同期完了となっていてもGoogle Colab
からアクセスした場合に不完全なファイルとしてコピーされているのではないかと思われる。
ドライブにpth
ファイルを入れた場合は同期完了後5分ほど待ってから実行すると問題なかった。
他にもこのエクステンションに限ったことではないが画像サイズを大きくしていると止まってしまうことがある。
まずは512*512
で試してみよう。
ControlNet
とは似て非なる技術にT2I adapter
というものがある。
現時点でなんとT2I adapter
のモデルを読み込んで使用できる...のだが、画像が崩れてしまい殆ど実用には至らなかったので、メモ程度の情報。
通常の推定モデルと同じく、次からDLしたモデルをsd-webui-controlnet/models/
に入れて利用する。
TencentARC/T2I-Adapter at main
2023/03/16:現在現在できるのは次の2つ。
t2iadapter_style_sd14v1.pth
と合わせて使用できた。
元絵の画風を反映させるもの?
試した限り画像が乱れるだけでうまく利用できなかった。
Guidance Start
を少し上げてGuidance End
を少し下げた状態で使うのがコツとの情報あり。
t2iadapter_color_sd14v1.pth
で利用する。
入力された絵からカラー入りのモザイク画像を作成し、出力に反映させる。
モザイクの色のみならずピクセルの位置も反映されるようなので、元絵を一旦モザイク画像にしてi2iに通したような効果が得られるようだ。
ControlNet
のTips的な使い方を書いておく。
img2img
に光の元となる画像を入れて、ControlNet
にメインのキャラクタのような画像を入れると
img2img
側の色味や光源が反映されるので光のイメージをコントロールできそうだ。
こちらはDepth
推定をつかった動画制作のテスト。
映像後半は使用したDepth
の画像。
恐らくだがDepth
は奥行きだけでなくシルエットを維持しやすいという特徴があるようで、活用方法がありそうだ。
こちらは蝶の作例。そもそもCGで私が自作アニメーションした蝶をベースにしているのでプロンプトの魔術は少なめでもいける。
こちらもDepth
を使うことにより羽のシルエットを正確に捉え、アニメーションとして成立させるテスト。
背景を別で合成したほうが良いという知見や、撮影の角度によってはDepth
であっても蝶の羽が消えてしまうなどの課題も見つかった。
Depth
がシルエットを維持しやすいということは、模様を描かせるのが得意なのではという実験。
相変わらず背景のチラツキ課題はあるが、模様が入ったキューブが回転していることがハッキリと分かる。
後ろにも別の模様をいれているが、キューブ側の模様と後ろの模様が同一化するコマも多い。それもまた味とも捉えられる。
この場合はアナログノイズのような雰囲気も合わせてMVの1カットに十分使えそうに思える。
細かくスライスした3DCGをDepth
にかけることで一貫性のあるアブストラクト動画にする例。
こちらもかなりMV風味。
CGで普通にレンダリングした人魚の画像をi2i
側に入れて、自前で用意したSegment画像をControlNet
側に入れて生成した動画例。
2枚の元画像を使った生成は現時点でバッチに対応していないので1コマずつ手作業で出力した。かなり大変。
上でも少し触れているが、この手法に限り指の再現度が極めて高い。
i2i
1枚だけで処理した場合、Denoising=0.1
にしても指の描画が壊れることを確認済み。
このCGモデルに関してはむしろ表情のほうが課題。この手法はいずれバッチに対応したものが出てくると思う。
この記事は暫く更新を続ける予定。
ControlNet
の登場でクリエーター側の意図をAIに伝えるすごいツールになりそう。
イラストが書けるユーザーであれば、線画だけ書いて色塗りを自動化できるのでかなり強力かも。
また、クリスタの3Dデッサン人形でポーズだけ作ってイラストを書かせるという手法を使っているユーザーもいて面白い。
今後は動画化などでも役に立ちそうなので暫く研究したい。