ジャコ Lab

プログラミング関連のメモ帳的ブログです

Prompt Weighting を試してみる!

huggingface.co

以前 (best quality:1.4) みたいなのが使えないらしいとの情報を得ました。
今回は公式ドキュメントに沿って試してみようと思います。

Prompt Weighting

公式では compel という pip モジュールを使って重み付けをするようです。
以下の pip install を忘れないようにしておきます。

!pip install compel

プロンプトは "a red cat playing with a ball" をベースとするようです。
最初は、重み付け無しでただ単に Text-to-Image を実行します。

import torch
from diffusers import StableDiffusionPipeline, UniPCMultistepScheduler

pipe = StableDiffusionPipeline.from_pretrained(
    "CompVis/stable-diffusion-v1-4", 
    use_safetensors=True
)
pipe.scheduler = UniPCMultistepScheduler.from_config(pipe.scheduler.config)
pipe.to("cuda")

prompt = "a red cat playing with a ball"
image = pipe(
    prompt, 
    generator=torch.Generator(device="cpu").manual_seed(33), 
    num_inference_steps=20
).images[0]
image

重み付け無しで生成された画像

プロンプトに重み付けをする

from compel import Compel

compel_proc = Compel(tokenizer=pipe.tokenizer, text_encoder=pipe.text_encoder)

prompt = "a red cat playing with a ball++"
prompt_embeds = compel_proc(prompt)

image = pipe(
    prompt_embeds=prompt_embeds,
    generator=torch.Generator(device="cpu").manual_seed(33),
    num_inference_steps=20
).images[0]
image

ball++ になっているのがポイント なのと、
prompt_embeds 引数を設定しているのがポイント のようです

重み付けをして生成された画像

重みを減らすこともできる

# prompt = "a red------- cat playing with a ball"
prompt = "a red---- cat playing with a ball"
prompt_embeds = compel_proc(prompt)

generator = torch.manual_seed(33)

image = pipe(
    prompt_embeds=prompt_embeds, 
    generator=generator,
    num_inference_steps=20
).images[0]
image

が、、、ヤバい画像が生まれてしまた。。。
ので、重みの量を少し変えておく。。。

ドキュメント通りではなく、少し重みを変更して生成した画像

なお、torch.manual_seed(33)の部分を
touch.Generator(device="cuda").manual_seed(33)にすることで全く同じ絵が出ました!

複数の重みを設定することもできる

# prompt = "a red cat++ playing with a ball----"
prompt = "a red cat+ playing with a ball++++"
prompt_embeds = compel_proc(prompt)

generator = torch.manual_seed(33)

image = pipe(
    prompt_embeds=prompt_embeds, 
    generator=generator,
    num_inference_steps=20
).images[0]
image

※こちらもドキュメントから重みの量は変えました!なんか怖いから!

なお、torch.manual_seed(33)の部分を
touch.Generator(device="cuda").manual_seed(33)にすることで全く同じ絵が出ました!

ちなみに Compel 使わないで -+ を用いると?

a red cat playing with a ball++

ボールは出なかったですね。
ちゃんと重み付けされているっぽいですね!

まとめ

  • diffusers にはデフォルトで重み制御はない
  • Compel モジュールを使うことで重み付けが可能になる

ドキュメント通りの重み付けで、期待通りの絵が生成されなかったのはバージョン違いでしょうか?
バージョンの詳細が載っていないのでわからないですが、、、
ドキュメントの誤りである可能性が高いことがわかりました。
torch.Generator(device="cuda").manual_seed(33) にしたらドキュメント通りでした。

Compel にはブレンド機能やその他の機能もあるようなので、次回は続きを遊んでみようと思います。