【Stable Diffusion】Diffusersを使ってColab無料枠でAIイラストを生成する方法【2023年】

こんにちは!悠です!

 

2023年5月23日時点で、無料版のGoogle Colaboratoryでは「Stable Diffusion WebUI」を使おうとすると警告文が表示されます。

この件に関しては下記の記事に詳しくまとめていますので、参考にしてください。

【Stable Diffusion】Google Colaboratory版終了のお知らせ?無料版ではWebUIの利用に制限がかかるように!
2023年4月21日以降、Google Colaboratoryで「Stable Diffusion WebUI」を使おうとすると表示される制限メッセージについて解説した記事です。

 

この警告文なんですが、禁止されているのは「Stable Diffusionを使ってAIイラストを生成すること」ではなく、「Stable Diffusion WebUIをリモート起動すること」です。

※remote UIsという部分なんですが、日本から閲覧できる規約にはまだ反映されていないのかも。Reddit等では追加された画像が上がっています。

出典:https://research.google.com/colaboratory/faq.html#limitations-and-restrictions

 

そのため、publicURLを生成するWebUIを使用せずに、「Stable Diffusion」でAIイラストを作成することは無料版でもOKなわけですね。

 

そこで今回は、Diffusersというライブラリ使って、「Stable Diffusion」をGoogle Colaboratory無料枠で利用する方法について紹介していきます。

なお予め言っておくと、WebUIで利用できた拡張機能を使うことは(おそらく)できません。私が方法を知らないだけの可能性もあるので、ご存知でしたらコメント欄で教えてください!

 

アイキャッチ画像はモデルに「AbyssOrangeMix3」、LoRAに「flat2」を使用しています。
スポンサーリンク
スポンサーリンク

「Diffusers」とは?

Diffusers」とは、画像や音楽さらには分子の3D構造を生成するための、最先端の事前トレーニング済みDiffusionモデルのライブラリです。以下原文です。

Diffusers is the go-to library for state-of-the-art pretrained diffusion models for generating images, audio, and even 3D structures of molecules.

出典:https://huggingface.co/docs/diffusers/index

 

Diffusers
We’re on a journey to advance and democratize artificial intelligence through open source and open science.

 

凄まじいほどたくさんの機能を備えたライブラリなんですが、この中の「Stable diffusion pipelines」というモジュールを使ってAIイラストを生成することができます。

Stable diffusion pipelines
We’re on a journey to advance and democratize artificial intelligence through open source and open science.

 

「Diffusers」を使ってColabでAIイラストを生成する方法

それでは早速、Google Colaboratory内でDiffusersを使ってAIイラストを生成する方法を紹介していきます。

記事の通りにコードをコピペしていくだけでいいので、全く難しくはありませんよ!

 

なおローカル環境導入済みの方やColab有料版の方は、絶対にWebUIを使いましょう。圧倒的にできることの量が違いますからね。

ただColabにおいて、DiffusersはWebUIと違い起動までにかかる時間が3分程度と非常に短いです。WebUIは10分近くかかるので、ここは嬉しいポイントですね。

 

【追記】下の記事で紹介したLoRAをDiffusersで使う方法に関しても、このページ内のコードに反映させています。

【Stable Diffusion】DiffusersでLoRAを使ってAIイラストを生成するやり方を紹介!【Colab無料枠】
「Diffusers」でLoRAを使ってAIイラストを生成する方法についてまとめています。Google Colaboratory無料枠の方でも制限がかかることなく試すことができますよ!

 

新しくノートブックを準備しよう

まず下記のリンクからGoogle Colaboratoryにアクセスしてください。

Google Colaboratory

 

左上にある「ファイル」→「ノートブックを新規作成」とクリックします。

 

「編集」→「ノートブックの設定」を選択し、ハードウェアアクセラレーターをGPUにして保存をクリックします。

 

 

「+コード」をクリックします。

 

これから5つのセルを作成し、コードを入力していきます。

6つ目のセル以降はオプションです。お好みで利用してください。

 

なお読者の方から「Seed値をif文で分岐させる方法」、「LoRAの有効化無効化をチェックボックスで設定する方法」、「各パラメータをUIに表示させて簡単に入力できるようにする方法」を教えていただきました。

このおかげでDiffusersがめちゃくちゃ使いやすくなりました!本当にありがとうございます!!

 

1つ目のセル

最初のセルに下記のコードをコピペしてください。

#stable diffusionのインストール
!pip install --upgrade diffusers[torch] transformers

 

2つ目のセル

2つ目のセルに下記のコードを入力してください。

from google.colab import drive
drive.mount('/content/drive')

 

これはGoogle Driveをマウントするためのコードです。

Drive内に保存したLoRAやモデルデータをDiffusersで利用できるようにします。なお、モデルデータの方は後述するスクリプトを使用してDiffusersの形式に変換する必要があります。

 

3つ目のセル

3つ目のセルに次のコードを入力してください。なおこの部分に関しては下記の記事を参考にさせていただきました。

diffusers で Lora (safetensors) を読み込んで生成する方法 - Qiita
はじめにこれはhuggingface/diffusersモジュールを利用して画像生成する際に、safetensors の lora を読み込む方法です。Civitai 等で公開されている Lora は safetensors フ...

 

ここでは、LoRAを読み込む際に使用する「load_safetensors_lora」という関数を定義してます。

この部分は参考文献として紹介した記事の内容を、100%そのまま使わせていただきました。リンク先の「モジュール」という部分です。

これを私のブログに載せるわけにはいかないので、実際にリンク先に飛んでコピペしてください。

 

ただ、一番最初に!pip install safetensorsを付ける必要があるので、ここだけ注意してください。

!pip install safetensors

import torch
from safetensors.torch import load_file

def load_safetensors_lora(pipeline, checkpoint_path, LORA_PREFIX_UNET="lora_unet", LORA_PREFIX_TEXT_ENCODER="lora_te", alpha=0.75):

#########################################################
この先は参考文献のモジュールの欄をそのままコピペしてください。
#########################################################

 

4つ目のセル(使用するモデルやLoRAの準備)

4つ目のセルに下記のコードを入力してください。

from diffusers import StableDiffusionPipeline, EulerDiscreteScheduler
from diffusers.models import AutoencoderKL
import torch

#画像生成に使うモデルデータ
model_id = "AIARTCHAN/AbyssHellVer3"#@param {type:"string"}
#画像生成に使うVAE
vae = "stabilityai/sd-vae-ft-ema"#@param {type:"string"}
vae = AutoencoderKL.from_pretrained(vae)

#画像生成に使うスケジューラー
scheduler = EulerDiscreteScheduler.from_pretrained(model_id, subfolder="scheduler")

#パイプラインの作成
pipe = StableDiffusionPipeline.from_pretrained(model_id, scheduler=scheduler, vae=vae, custom_pipeline="lpw_stable_diffusion")

#LoRAを読み込む
LoRA_USE = True #@param {type:"boolean"}
if LoRA_USE == True:
  LoRA="/content/drive/MyDrive/StableDiffusion/Lora/flat2.safetensors"#@param {type:"string"}
  LoRA_alpha = -1#@param {type:"number"}
  pipe = load_safetensors_lora(pipe, LoRA, alpha=LoRA_alpha) 

pipe = pipe.to("cuda")

#NSFW規制を無効化する
if pipe.safety_checker is not None:
  pipe.safety_checker = lambda images, **kwargs: (images, False)

 

このコードをコピペすると右側に下の画像のようなUIが表示されます。各UIの使い方については次の通りです。

 

model_id

画像生成に使用するモデルデータのパスを入力します。

なお、初期状態ではHugging Faceからダウンロードできるものしか使うことができません。

ただ後述する変換スクリプトを使うことで、Google Driveに保存したCivitaiのモデルデータを利用することもできるようになります。

 

今回はアニメイラスト系のモデルデータ「AbyssHellVer3」を使用します。下記のURLにアクセスして、モデル名の右にあるボタンを押してクリップボードにコピーし、model_idの欄に貼り付けてください。

AIARTCHAN/AbyssHellVer3 · Hugging Face
We’re on a journey to advance and democratize artificial intelligence through open source and open science.

 

 

vae

VAEも同じ要領で貼り付けます。ただVAEの場合は、ダウンロードページ内にconfig.jsonがないものは利用できません。

 

なので「vae-ft-mse-840000-ema-pruned」や「kl-f8-anime」は無理です。おすすめなのは下記の「sd-vae-ft-ema」です。

stabilityai/sd-vae-ft-ema at main
We’re on a journey to advance and democratize artificial intelligence through open source and open science.

 

【追記】

ckpt形式のVAEをDiffusersで利用できるようにする方法に関して、コメント欄で教えていただきました!

下記の記事にまとめていますのでぜひ参考にしてください!

【Stable Diffusion】ckpt形式のVAEを変換してDiffusersで使えるようにする方法を紹介!
「vae-ft-mse-840000-ema-pruned」や「kl-f8-anime」等のckpt形式のVAEを、Diffusersで利用できるように変換するやり方に関してまとめた記事です。

 

LoRA_USE

LoRAを使う際はここにチェックを入れてください。

チェックを入れなければLoRAなしの状態で出力されます。

 

LoRA

Google Driveに保存したLoRAのパスを入力します。

なおおそらくLyCORIS(LoCon、LoHa)に関しては使用できないと思いますので、注意してください。

【Stable Diffusion】LyCORIS(LoHa・LoCon)をWebUIで使用する方法を紹介!【LoRA亜種】
「Stable Diffusion」で使用できるLoRAの亜種、「LyCORIS(LoHa・LoCon)」をWebUIで使う方法についてまとめた記事です。

 

LoRA_alpha

使用するLoRAの比重を入力してください。

WebUIでいう、<lora:lora_name:1.0>の1.0の部分です。

 

それ以外の補足

スケジューラーは恐らくですがWebUIでいうSampling methodのことだと思います。

ここは下記のページを参考にして変更可能です。ただ2M-Karrasとかはない気がします。

Schedulers
We’re on a journey to advance and democratize artificial intelligence through open source and open science.

 

Colab内にUIを作る方法に関して

パラメータが文字列なら#@param {type:”string”}、数字なら#@param {type:”number”}を付けるだけで、Colab内で簡単にUI化できるようです。

読者の方に教えていただくまで全く知りませんでした…

 

【参考記事】

ColabにUIをつける小技集 - Qiita
ColabにUIをつけるGoogle Colabratory NoteBook で UIを表示できます。入力フォームやボタンなど、他の人に使ってもらうときに便利です。フォームの値は、セルの値に反映されます。実際のCola...

 

5つ目のセル(画像の生成)

【2023年5月10日追記】

出力画像の名前を「(生成時した際の日本時間)+(Seed値)」にするコードをコメント欄で教えていただいたので、反映しております!

 

5つ目のセルに下記のコードを入力してください。

import datetime
import os
import random

#txt2img出力画像の保存先
!mkdir -p /content/txt2img_output

# ファイル名に使う日付と時刻のフォーマットを定義する
file_format = "%Y%m%d_%H%M%S"
i=0

#ポジティブプロンプト
prompt = "masterpiece,1girl,portrait,school uniform,blonde hair,smile"#@param {type:"string"} 
#ネガティブプロンプト
n_prompt = "(worst quality,low quality:1.4),(monochrome,greyscale:1.4),nude,nsfw"#@param {type:"string"} 
#CFG Scale
CFG_scale = 7#@param {type:"number"}
#ステップ数
Steps = 20#@param {type:"number"}
#seed値
seed=-1#@param {type:"number"}
if seed is None or seed == -1:
  inputSeed = random.randint(0, 2147483647)
else:
  valueSeed = seed

#生成枚数
num_images = 1#@param {type:"number"}
#出力画像の横幅
width = 768#@param {type:"number"}
#出力画像の高さ
height = 512#@param {type:"number"}
#出力画像を保存するフォルダ
save_path = "/content/txt2img_output"#@param {type:"string"}

while i < int(num_images):
  #generator
  if seed is None or seed == -1:valueSeed = inputSeed + i
  generator = torch.Generator(device="cuda").manual_seed(valueSeed)
  
  #画像を生成
  image = pipe(prompt, negative_prompt=n_prompt, width=width, height=height, generator=generator, guidance_scale=CFG_scale, num_inference_steps=Steps).images[0]

  # 現在の日本時間を取得
  jst_now = datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9)))
  #出力する画像の名前を生成する
  file_name = (jst_now.strftime(file_format)+ "_" + str(valueSeed))
  image_name = file_name + f".png"

  #画像を保存する
  save_location = os.path.join(save_path, image_name)
  image.save(save_location)
  i = i + 1

 

if文やwhile文の後の行は、最初にタブキーでスペースを空けるのを忘れずに。

 

下記のようなUIが表示されます。

 

promptにはポジティブプロンプトを、n_promptにはネガティブプロンプトを入力してください。

seedは-1だとランダム、自分で任意の数字を入力すると固定されます。

num_imagesには生成したい画像の枚数を入力してください。

 

これで準備完了なので、上から順にセルを実行していってください。

 

左側のtxt2img_outputフォルダに、生成した画像が保存されます。ダブルクリックすると画像を表示できます。

 

参考までにモデル「AbyssHellVer3」を使って生成した画像を紹介いたします。

【Positive】
masterpiece,1girl,school uniform,long skirt

【Negative】
(worst quality,low quality:1.4),(monochrome,greyscale:1.4),nude,nsfw

 

 

6つ目のセル(画像の保存)

Colab環境内で生成した画像をZIPファイルに圧縮して、「ローカル環境(自分のPC)」に保存するコードをコメント欄で教えていただきました!

6つ目のセルに下記のコードを入力してください。

# ファイルをDL
from google.colab import files
import shutil
# フォルダをzip圧縮
shutil.make_archive("txt2img_output", "zip", "/content/txt2img_output")
# 圧縮ファイルをダウンロード
files.download("txt2img_output.zip")

 

このセルを実行することで、「txt2img_output」フォルダに生成した画像を、ZIPファイル形式で自分の使っているPC内に保存することができます。

 

7つ目のセル(outputフォルダ内の画像を消去)

こちらもコメント欄で教えていただきました。

6つ目のセルで生成した画像をダウンロードした後、不要になったtxt2img_outputフォルダ内の画像を消去することができます。

 

7つ目のセルに下のコードを入力してください。

# /content/txt2img_outputフォルダ内のデータを削除
shutil.rmtree("/content/txt2img_output")

 

75トークン制限を回避する方法

DiffusersによるAIイラストの生成は、WebUIとは違い残念ながら75トークン制限が適用されてしまいます。

75トークン制限に関しては、下の記事で詳しく紹介しているので参考にしてください。

【Stable Diffusion】トークンとは何か?AND構文とBREAK構文の使い方も合わせて紹介!
「Stable Diffusion WebUI」でプロンプトを作成する際に活用することができる、AND構文とBREAK構文の使い方について紹介した記事です。

 

ただこの制限を簡単に回避する方法があります

pipe = StableDiffusionPipeline.from_pretrained(model_id, scheduler=scheduler, vae=vae, custom_pipeline="lpw_stable_diffusion")

 

上記のように使用するモデルやVAEを設定する欄の中に、custom_pipeline=”lpw_stable_diffusion”を入れるだけです。

この記事内で紹介しているコードの中にも盛り込んでおきましたので、コピペするだけでトークン制限のことは気にしなくてよくなりますよ!

 

「Diffusers」でLoRAを使う方法

この部分は上のコードに盛り込んであります。

Google Drive内に保存したLoRAを「Diffusers」で使う方法に関して、下記の記事で詳しくまとめました。

【Stable Diffusion】DiffusersでLoRAを使ってAIイラストを生成するやり方を紹介!【Colab無料枠】
「Diffusers」でLoRAを使ってAIイラストを生成する方法についてまとめています。Google Colaboratory無料枠の方でも制限がかかることなく試すことができますよ!

 

複数のLoRAを使う方法

コメント欄で複数のLoRAを使う方法に関して教えていただきました!

 

4つ目のセルに下記のように追記します。

from diffusers import StableDiffusionPipeline, EulerDiscreteScheduler
from diffusers.models import AutoencoderKL
import torch

#画像生成に使うモデルデータ
model_id = "AIARTCHAN/AbyssHellVer3"#@param {type:"string"}
#画像生成に使うVAE
vae = "stabilityai/sd-vae-ft-ema"#@param {type:"string"}
vae = AutoencoderKL.from_pretrained(vae)

#画像生成に使うスケジューラー
scheduler = EulerDiscreteScheduler.from_pretrained(model_id, subfolder="scheduler")

#パイプラインの作成
pipe = StableDiffusionPipeline.from_pretrained(model_id, scheduler=scheduler, vae=vae, custom_pipeline="lpw_stable_diffusion")

#LoRAを読み込む
LoRA_USE = True #@param {type:"boolean"}
if LoRA_USE == True:
  LoRA="/content/drive/MyDrive/StableDiffusion/Lora/flat2.safetensors"#@param {type:"string"}
  LoRA_alpha = -1#@param {type:"number"}
  pipe = load_safetensors_lora(pipe, LoRA, alpha=LoRA_alpha) 

#LoRA_2を読み込む
LoRA_USE_2= False #@param {type:"boolean"}
  if LoRA_USE_2== True:
  LoRA_2="/content/drive/MyDrive/StableDiffusion/Lora/Nahida3.safetensors"#@param {type:"string"}
  LoRA_alpha_2 = 1#@param {type:"number"}
  pipe = load_safetensors_lora(pipe, LoRA_2, alpha=LoRA_alpha_2)

pipe = pipe.to("cuda")

#NSFW規制を無効化する
if pipe.safety_checker is not None:
  pipe.safety_checker = lambda images, **kwargs: (images, False)

 

これで、LoRA_USEとLoRA_USE_2に反映したLoRAを使って画像を生成できます。

 

「Diffusers」でCivitaiのモデルデータを使う方法

変換スクリプトを使って、Civitaiでダウンロードしたモデルデータを「Diffusers」で利用する方法について下の記事で詳しくまとめています!

【Stable Diffusion】DiffusersでCivitaiのモデルデータを変換して使う方法を紹介!
「Diffusers」を使って、Google Drive上にアップロードしたCivitaiのモデルデータを利用する方法についてまとめています。

 

ckpt形式のVAEを「Diffusers」で使う方法

ckpt形式のVAE(例えば「vae-ft-mse-840000-ema-pruned」や「kl-f8-anime」)を、Diffusersで利用する方法に関してコメント欄で教えていただきました!

下の記事で詳しく紹介しています。

【Stable Diffusion】ckpt形式のVAEを変換してDiffusersで使えるようにする方法を紹介!
「vae-ft-mse-840000-ema-pruned」や「kl-f8-anime」等のckpt形式のVAEを、Diffusersで利用できるように変換するやり方に関してまとめた記事です。

 

NSFW規制の無効化について

下記の記事を参考にいたしました。

DiffusersでNSFW警告からの黒画像を無効にする方法 [Potential NSFW content was detected in one or more images. A black image will be returned instead. Try again with a different prompt and/or seed.] - Qiita
はじめにdiffusersを使って画像を生成しようとするとモデルによってはNSFW検出されてしまい黒く塗りつぶされてしまう。今回はそれの回避方法探してみると、モジュールのPythonを書き換える方法が見当たるが、pipが使えな...

 

Diffusersでは、初期設定でNSFW規制がオンになっているため、そういう画像を生成することはできません。

ですが、下記のコードをモデルデータやVAEを読み込むセルに挿入することで、制限を回避することができます。

#NSFW規制を無効化する
if pipe.safety_checker is not None:
  pipe.safety_checker = lambda images, **kwargs: (images, False)

 

そもそもColabでNSFW画像を作ることはリスクが高いのでおすすめしませんが、明らかに違うのにNSFW判定をされて画像が出力できないこともあるそうなので、とりあえず上のコードで無効化した後にネガティブプロンプトにnsfwを入れておけばいいと思います。



Seed値を固定するやり方について

下記の動画を参考にさせていただきました。

 

Seed値を固定する場合は、下記のコードを画像を生成するセルの中に盛り込めばOKです。

#seed値
seed=1234

#seed固定 
generator = torch.Generator(device='cuda').manual_seed(seed)
image = pipe(prompt, negative_prompt=n_prompt, width=768, height=512, generator=generator, guidance_scale=7, num_inference_steps=20).images[0]

 

seed=-1にするとランダムシードで画像が生成されます。

 

「Diffusers」で生成した画像を高画質化する方法

「Diffusers」を使って生成したAIイラストを、「Real-ESRGAN」というアップスケーラーで高画質化する方法に関して下の記事で詳しく紹介しています。

こちらも無料版のColabで制限なく使用することができます。

【Diffusers】「Real-ESRGAN」を使って生成したAIイラストを高画質化する方法【Colab無料枠】
「Diffusers」で生成したAIイラストを、「Real-ESRGAN」というアップスケーラーを使って高画質化する方法について紹介した記事です。

 

「Diffusers」でControlNetを使える可能性

下記のGitHubのページを偶然発見したので紹介いたします。DiffusersでもControlNetを使えるかもしれません。

GitHub - haofanwang/ControlNet-for-Diffusers: Transfer the ControlNet with any basemodel in diffusers🔥
Transfer the ControlNet with any basemodel in diffusers🔥 - GitHub - haofanwang/ControlNet-for-Diffusers: Transfer the ControlNet with any basemodel in diffusers...

 

ちょっと難しそうな印象を受けたので、まだ試せていません(涙)

もしいつか試してみて、実際に使えそうなら記事にまとめていきたいと思います。

 

「Diffusers」の情報を是非コメント欄で教えてください!

「Diffusers」の情報をご存知でしたら、ぜひコメント欄で教えてください!

例えばですが、

  • WebUIの拡張機能を導入する方法
  • hires.fixを使う方法
  • embeddingsを使う方法

 

などをDiffusersに盛り込めたら、Colab無料ユーザーの方にかなりおすすめできるようになります。

img2imgはどうやらできるようなので、これは後日別記事にまとめます。

 

なお私はプログラマーでも何でもないので、コードに不備がある場合や、改善案をもしご存知でしたらぜひコメント欄までお願いいたします!



まとめ

以上が無料版のGoogle Colaboratoryでも、規約違反することなく「Stable Diffusion」でAIイラストを生成できる「Diffusers」の使い方でした。

WebUIと比べてできることは限られますが、BANリスクはないのでぜひ皆さんも試してみてくださいね!

 

では、ここまで読んでいただきありがとうございました。

コメント

  1. unreal_chicken より:

    ついにcolabの無料版でWeb UIが使えなくなってしまったようなので、代わりの方法を探していたところこの記事を見つけて読まさせていただきました。とても分かりやすく、実際に画像を生成するところまで出来ました!ありがとうございます。

    Loraとhires.fixについてですが、調べてみたところこのような記事を見つけました。
    https://towardsdatascience.com/improving-diffusers-package-for-high-quality-image-generation-a50fff04bdd4
    まだ私自身この記事をすべて読んだ訳ではないので間違っているかもしれませんが、diffusersでLoraを使う方法や画像をアップスケーリングする方法などについて述べられているようです。参考になれば嬉しいです。

    • 悠 より:

      コメントありがとうございます!!

      大変有益な情報感謝いたします!!これ早速明日拝見させていただきます!
      Colabの無料版だとBANにはならないけれど、10分くらい使うだけでWebUIの接続が切れるという話を聞きました…悲しいですよね…

      Diffusersの方で何とかいろいろなことができるように、今後もこの記事をアップデートしていきたいと思います!

      • unreal_chicken より:

        返信ありがとうございます!

        以前からColab無料版でWeb UIが使えなくなると聞いていたので覚悟はしていましたが、実際に使えなくなったと気づいたときはかなりショックでした…他のサービスへの乗り換えも検討しましたが、やはり天下のGoogle様のサービスが一番安心して使えるので、なるべく今後もColabを使っていきたいです。

        改めて先述の記事を読みましたが、Diffusersで何とかできそうな感じですね!悠さんの記事のアップデートを楽しみにしてます!

  2. honey より:

    こちらにseed値を設定できる方法が記載されてた気がします
    https://m.youtube.com/watch?v=lOjHo0c55wA

    • 悠 より:

      コメントありがとうございます!!

      超有益な情報、感謝いたします!!
      実際に固定できることを確認できましたので、記事内に追記させていただきました!

  3. 初心者 より:

    失礼失礼いたします。
    プロンプト入力時、毎回同じようなエラーとなります。
    特に問題ないように思いますが「構文エラー」のようです
    ご回答をお願い致します。

    prompt = “masterpiece, best quality, ultra high res, Lens Glow , f1.8, 3 girls, fullbody,office ”

    SyntaxError: invalid syntax

    • 悠 より:

      コメントありがとうございます!

      そのプロンプトを試してみたんですが、特にエラーは表示されませんでした。
      どこかのコードをコピペし忘れているとかですかね?

      prompt が含まれているセルの部分のコードを全文貼っていただいてもいいでしょうか?

      • 初心者 より:

        返信が遅くなり申し訳ございません。
        何回かコピペしなおしたら問題ありませんでした。
        ご回答等ありがとうございました。
        お手数をおかけいたしました。

  4. DfsBootTest より:

    以下の条件で動くコードはありませんか?
    ・モデルとvae、Loraは、全てgoogleDriveに格納している
    ・アカウントが違う為に現在のアカウントにはマウントできないが、すべての共有リンクアドレスは判明している

    下記コードは格納までは問題なく出来てます
    ———————————-
    !pip install gdown

    #ディレクトリの作成
    !mkdir -p /mut_models
    !mkdir -p /mut_vae

    #画像生成に使うモデルデータ
    modelIdName = “googleDrive共有リンクアドレス”#@param {type:”string”}
    !gdown –id {modelIdName} -O /mut_models/model.pth
    model_id = “/mut_models/model.pth”

    #画像生成に使うVAE
    vaeName = “googleDrive共有リンクアドレス”#@param {type:”string”}
    !gdown –id {vaeName} -O /mut_vae/model.pth
    vae = “/mut_vae/model.pth”

    ———————————-
    この段階で以下の様なerrが発生(一部のみ記載)
    /usr/local/lib/python3.10/dist-packages/diffusers/configuration_utils.py:409 in load_config │
    │ │
    │ 406 │ │ │
    │ 407 │ │ try: │
    │ 408 │ │ │ # Load config dict │
    │ ❱ 409 │ │ │ config_dict = cls._dict_from_json_file(config_file) │
    │ 410 │ │ │ │
    │ 411 │ │ │ commit_hash = extract_commit_hash(config_file) │
    │ 412 │ │ except (json.JSONDecodeError, UnicodeDecodeError):

  5. DfsBootTest より:

    chatGPTでerr解析をお願いしたところ、以下の原因の様でした

    このエラーは、/mut_vae/model.pth ファイルが JSON フォーマットで書かれていないことが原因のようです。AutoencoderKL.from_pretrained メソッドは、ファインチューニングのための前学習済みの重みを読み込むために、モデルの構成ファイルを読み込みます。エラーメッセージによると、/mut_vae/model.pth ファイルを読み込む際に UnicodeDecodeError が発生しています。このエラーは、ファイルが UTF-8 でエンコードされていないことを示唆しています。

    この問題を解決するには、モデルの構成ファイルを JSON 形式に変換し、UTF-8 でエンコードする必要があります。または、モデルを保存するときに JSON 形式で保存する必要があります。

  6. DfsBootTest より:

    返信ありがとうございます
    ひとまずは、このページのご紹介いただいた方法で遊んでみました

    ちょっと不便だなと感じたので以下の調整を加えてみました
    ・ファイル名を日本時間に変更、末尾にseedを付与
    ———————————-
    while i < int(count_images):
    #画像を生成
    image = pipe(prompt, negative_prompt=n_prompt, width=width, height=height, generator=generator, guidance_scale=CFG_scale, num_inference_steps=Steps).images[0]

    #出力する画像の名前を生成する
    # 現在の日本時間を取得
    jst_now = (datetime.datetime.now(datetime.
    timezone(datetime.timedelta(hours=9))))
    #ファイル名を作成
    seedCount = seed + i
    file_name = (jst_now.strftime(file_format)
    + "_" + str(seedCount))
    image_name = file_name + f".png"

    ———————————-
    変数file_nameは端折れるかもですが、可読性保持で作成してます
    該当の個所に置き換えてみてください

    ※seed付与について、複数枚を生成する場合に+1づつseedが増加される前提で設定してます、間違いがあればまたご連絡いたします

  7. DfsBootTest より:

    こちらは既知の情報かも知れませんが作成しました
    ———————————-
    # ファイルをDL
    from google.colab import files
    import shutil
    # フォルダをzip圧縮
    shutil.make_archive(‘txt2img_output’, ‘zip’, ‘/content/txt2img_output’)
    # 圧縮ファイルをダウンロード
    files.download(‘txt2img_output.zip’)

    ———————————-
    # /content/txt2img_outputフォルダ内のデータを削除
    shutil.rmtree(‘/content/txt2img_output’)

    ———————————-
    ふたつはこのページで言うところの”5つ目のセル”に繋げて記述してもいいですし、
    それぞれ別に作成して都度実行でもいいと思います

    削除が伴いますので、初回は念のため手動で保存してから使ってみてください

    また、zipである必要ないのでchatGPTに聞いてみました
    Q.zipの必要はないのですが、zipでないとDL出来ないのですか?
    A.Google Colabでは、ファイルやフォルダーを直接ダウンロードする機能が提供されていないため、ファイルやフォルダーをダウンロードするためには、zip圧縮をする必要があります。

    以上です

    • 悠 より:

      改善案ありがとうございます!!

      これで保存されるファイル名をwebuiみたいに出来るようになるんですね!!

      すぐに私の方でも試してみて記事内に反映させていただきます!!!

      • 悠 より:

        # 現在の日本時間を取得
        jst_now = (datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9))))
        #出力する画像の名前を生成する
        seedCount = seed + i
        file_name = (jst_now.strftime(file_format)+ “_” + str(seedCount))
        image_name = file_name + f”.png”

        上記の部分、5つ目のセル内のコードに反映させていただきました!

        ああ!しかも2つ目に紹介していただいたコードは、Colab内で生成した画像をzipファイルにまとめてローカル環境に保存できるものなんですね!
        こんな便利なものがあったとは、さっそくこちらも反映させていただきました!

        本当に教えていただきありがとうございます!

  8. DfsBootTest より:

    悠 さま
    (このコメントは本文側に記載不要です)

    >こんな便利なものがあったとは、本当に教えていただきありがとうございます!
    すみません、私が作成しましたのでどこかにあるか否かは不明です
    追加コード書いて触ってたらGPU(ランタイム?)がタイムアウトしてしまったので、あまり検証できてないのです
    不備があるようなら、削除してくださいね

    zipファイルの名称も指定変更することは出来ると思いますが、私的には必要ない気がしたので実装してません

    Samplerまたはschedulerを5つ目のセル内のコード実行前に変更できればいいなあと思って試行錯誤しましたが、私のDiffusers知識では実装できませんでした、またなにか気がついたらご連絡いたします

    ありがとうございました

  9. DfsBootTest より:

    度々すみません
    (このコメントも未検証箇所がありますので、本ページコメント欄には記載不要です)

    恐らくですが、「6つ目のセル(画像の保存)」を実行せず「7つ目のセル(outputフォルダ内の画像を消去)」を実行するとErrになるかと思います

    6つ目のセル(画像の保存)で下記を行っているので「7つ目のセル(outputフォルダ内の画像を消去)」時はその記述を省略しているだけなのです
    >from google.colab import files
    >import shutil

    ざっくり言いますと、shutilは6で既にimport しているので、何度もimport する必要はないのです。逆にimport 出来ていない場合は必要となります

    こちらも未検証な情報で申し訳ないのですが、セッション開始時に1回のみの実行でも問題ないかもしれません。
    余談にもなりますが、余計な処理を複数回行うとメモリ等のリソースの浪費となり、結果的に生成可能枚数や稼働可能時間が減少する可能性があります

    • 悠 より:

      追記ありがとうございます!

      仰っている意味わかります!
      ZIPファイルで保存する前に削除する場合は少ないと思うので、とりあえずこのままで大丈夫だと思います。
      本当に最適化を考えるなら、import系のコードはどこか一か所にまとめて毎回実行しない方が良いのかもしれませんね。

      私は今何とかhires.fixのような機能をdiffusersで使えないか探していますが、なかなかやり方が見つかりません(涙)
      一応img2imgの方も(下記)試しているんですが、こちらもなぜか微妙に上手くいかないんですよね。処理自体は実行されるんですが、画像サイズが変わらない…
      https://huggingface.co/docs/diffusers/api/pipelines/stable_diffusion/img2img

      また何かDiffusersで使える新機能を見つけましたら追記していきます!

  10. DfsBootTest より:

    また発見してしまいました
    (このコメントも本ページコメント欄には記載不要です)

    このページの、5つ目のセル(画像の生成)の部分ですが、変数に格納する内容のコードが横に長すぎたので()で囲んで折り返し(=見た目上の改行)させているのです

    # 現在の日本時間を取得
    jst_now =(datetime.datetime.now(datetime.
          timezone(datetime.timedelta(hours=9))))
    #出力する画像の名前を生成する
    seedCount = seed + i
    file_name = (jst_now.strftime(file_format)
           + “_” + str(seedCount))

    具体的にはjst_nowとfile_name に格納している内容の最両端の()です
    一行で書くのであれば最両端の()は不要、下記記述で問題ありません

    # 現在の日本時間を取得
    jst_now = datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9)))
    #出力する画像の名前を生成する
    seedCount = seed + i
    file_name = jst_now.strftime(file_format) + “_” + str(seedCount)

    補足
    以下URLの”関数呼び出しの改行”の項目に概要が書いてあります
    https://yumarublog.com/python/indention/

    言葉足らずばかりで申し訳ございません

    • 悠 より:

      本当に丁寧にありがとうございます!!

      そういう仕組みなんですね…お恥ずかしい、実際に試してエラーが出ないから大丈夫!とか思ってました…
      また勉強させていただきました!記事内の方にも反映させていただきました!

      あっ!本ページコメント欄には記載不要ってもしかしてここに反映しなくてもいいって意味でした?でも、Dfsさんのコメントで私のように勉強になる方もいらっしゃると思うので、反映しておいても大丈夫でしょうか…?

  11. DfsBootTest より:

    >あっ!本ページコメント欄には記載不要ってもしかしてここに反映しなくてもいいって意味でした?でも、Dfsさんのコメントで私のように勉強になる方もいらっしゃると思うので、反映しておいても大丈夫でしょうか…?

    まさに「ここに反映しなくてもいい」という意図でしたが、そう思って頂けるのであれば反映して頂いて大丈夫です

    私もパイソンは専門言語ではないので、改めて学びながらコードを書いてる部分があって、勉強になります 
    だからこそ私の完璧ではない発言が恥ずかしい訳なのですけどねw
    少しでも皆様のお力になれるのなら嬉しいです

    画像生成のプロンプトを考えて書くのって、ちょっとコードを自分で考えて書くことに似てるなーって思います なかなか敷居が高いかもですがプログラミングも面白いのでいつか是非挑戦してみてください

  12. あいあい より:

    はじめましいつも楽しみに拝見させていただいております。
    下記のようなエラー表示が初めてでまして Running on local URL:http://127.0.0.1:7860まで表示がでるのですが
    それ以降の表記が出現しなくなってしまいました
    note: This error originates from a subprocess, and is likely not a problem with pip.
    ERROR: Failed building wheel for pycairo
    ERROR: Could not build wheels for pycairo, which is required to install pyproject.toml-based projects

    どのようにいじれば今までのように青い3つのリンクが表示されるかアドバイスを頂けるとありがたく思います。
    説明が分かりにくくて申し訳ございません。
    よろしくお願いいたします。

    • 悠 より:

      コメントありがとうございます!

      public urlが表示されないということでしょうか?ということはWebUIの方ですかね?
      今日別の方から同じ症状のコメントをいただいたんですが、どうやら一時的な現象の可能性があるっぽいです。

      少し時間をおいて再度挑戦していただいてもよろしいでしょうか?

      • あいあい より:

        お時間いただきありがとうございます
        解決することが出来ました
        ありがとうございました。
        今後も楽しみに拝見させて頂きます
        また何かございましたらよろしくお願いいたします。

  13. るるるん! より:

    はじめまして!
    こういった形で誰でも使えるようにまとめた記事は本当にありがたいです……!

    Colab上でDiffusersで自作LoRAっぽいことができるみたいな記事を見つけました!
    https://torch.classcat.com/2023/04/12/blog-sd-webui-colab-lora-training-by-diffusers/

    • 悠 より:

      コメントありがとうございます!!
      DiffusersでLoraの学習までできるとは!!

      参考文献、読ませていただきます!

      ちなみにlora作成に関しては、remoteUIを使わないため、kohya guiのcolab版でも規制がかからなかったと思います!
      ただ無料版だと学習途中でランタイムが切れたりするらしいですが(涙)

      下記の記事辺りでご紹介しているので、良かったら参考にしてください!
      https://yuuyuublog.org/sdwebuitraintools/

      • るるるん! より:

        返信ありがとうございます!

        >ちなみにlora作成に関しては、remteUIを使わないため、kohya guiのcolab版でも規制がかからなかったと思います!
        おお!それは盲点でした!!
        ご紹介いただいた記事ありがたく読ませていただきます!

  14. DfsBootTest より:

    プログラミングで内容を改変できる前提ですが、webuiよりも優れた使用方法を構築できるアイデアをいくつか紹介します

    1、プロンプトの多段実装と実行
    これは1回の生成時に、複数のプロンプトの内容を実行できる処理
    単純にプロンプトの入力欄を複数設けて、実行時にloop内で参照する変数を変更させる

    2、乱数処理を入れて生成する画像の出力割合を設定
    こちらは既に作成したい画像プロンプトはあるが、20%でちびキャラが欲しい、20%でスタンプ用のデフォルト画像も欲しい、などというケースを1回の処理で楽しめる
    こちらは処理実行時、確率で分岐した際に基本のプロンプトに一部のプロンプトを追加して出力させるだけ
    プロンプトは文字列変数なので文字列統合すればいいだけなので簡単
    応用した利用なので30%で髪の色を変えた結果が欲しいなども考えかた次第では実装可能

    3、AIイラスト呪文生成器機能の実装
    これはプロンプト入力欄を複数設けてそれぞれに該当の項目のリストボックス機能を持たせて、最終的にプロンプトを文字列統合する
    @paramで表示されるフォーム機能時にリストボックス(select?combo?呼び方不明)を使用するだけ
    超絶多機能なものだと作り上げるのに非常に労力がかかるが、配布目的ならば重宝されるはず

    4、Step数の多段階作成
    (類似の記事を見た気もしますが)こちらは初めて使うモデルなどで便利な機能
    あらかじめ2,5,10,15,20,25,30,35,40といった具合に変数か配列を準備して、1回の処理で複数枚出力させて変化度合いを確認して好みのstepを探り当てる方法
    例でStep数2,5を選択肢に入れているのは時折芸術的な作品が作成されるので私の個人的意見だが、別に80でも120でもいいと思う
    実装には上記等と同じく実行処理のloop内で参照値を変動させるだけ

    上記は思いついた一例だが、例えばプロンプトmasterpieceを入れると画質は格段に良くなるが偏った絵柄になるなどの問題を懸念した場合に、一回の生成で差異を判別できる等の機能も実装可能

    次に機能面の強化として、生成画像の指定サイズが8の倍数意外だとErrが出る場合があるので、実行処理中のサイズを読み込んだ時に8の倍数近似値に書き換える処理を入れるといいかも
    (こちらはwebuiでは勝手に変換される様でした)

    あとは、他類似情報サイトで得た情報なので詳細は省きますが、生成処理後に実行結果として自動で画像を表示させる事は可能です 現在調整中ですが縮小表示も可能なはず

    それとこちらは生成後に他のツールで画像をリサイズすればいいだけの話ですが、手間を省きたいなら生成後の画像サイズを任意に指定することは可能です(なのでi2iでも可能)

    また、おそらく生成後の保存時にプロンプト等のメタデータを画像に付与することも可能かと思います

  15. 悠 より:

    お久しぶりです!

    非常にいいアイデアありがとうございます!Diffusersはまだまだ伸び代がありそうですね…!

    これっておそらくdfsさんも取り組んでいらっしゃいますよね?私の記事の内容はいくらでもそのまま使っていいので(半分は読者の方に教えていただきましたしw)、もしインターネット上にブログか何かで公開した場合はぜひ教えてください!

    この記事内でも紹介させていただきます!!より使いやすいdiffusersの下地が出来れば、colab無料版ユーザーの方が喜んでくれるはず…!

    あ、もちろん紹介っていうのはリンクです!内容をそのまま記事に反映したりはしません!

  16. DfsBootTest より:

    実現できた事柄を中心にご報告します

    生成処理後に実行結果として、自動で欄外に画像縮小表示することは実装出来ました
    画像生成後の保存時にプロンプト等のメタデータを画像に付与することも実現出来ました

    それと有用か否かは別として、生成後に自動でDLして保存フォルダ内を削除すること(一括処理)も理論的に可能です
    手動で行う操作工程が削減できるので、より集中して生成を行えます

    それから残念ながら、私はブログ等で情報の発信は行ってませんし、これらの情報をここで公開しても私にはフィーが発生しません 個人で楽しむ範疇だと思いますので公開は出来ません

    また、便利な要素が増えて利用者が増えれば次の規制の的とも成りかねません それはつまり私自身の首を絞めることになりますのでコードサンプルの提供は申し訳ございませんが控えさせていただきます
    ご自身でお調べいただくか、真似事でも考えてご自身で組んでみることをお勧めいたします

    次に、ある意味訂正となりますが、本記事の保存ファイル名にseed値を付与する件ですが、複数枚の生成を行った場合にwebuiの様にseed値が+1づつ増加するかについてはかなり怪しいです、なぜならwhile内に+1する記載が見当たらないのです(i = i + 1はループカウンタ)
    >image = pipe(prompt, negative_prompt=n_prompt, width=width, height=height, generator=generator, guidance_scale=CFG_scale, num_inference_steps=Steps).images[0]
    >generator = torch.Generator(device=”cuda”).manual_seed(seed)
    >seed = random.randint(0, 2147483647)
    生成を行う処理で参照しているgeneratorではseedを再度乱数で生成しているとしか思えないという見解です

    訂正例としては以下の通りです
    NG:
    seedCount = seed + i
    file_name = (jst_now.strftime(file_format)+ “_” + str(seedCount))
    Ans:
    #seedCount = seed + i ←削除またはコメントアウト
    file_name = (jst_now.strftime(file_format)+ “_” + str(seed))

    前述にて間違った情報の提供、申し訳ございません

    • 悠 より:

      いつもコメントありがとうございます!

      承知しました!いろいろ実現できるということをご報告していただけただけでも、非常に感謝感激です!!
      最近調べていく中でMultiDiffusionっぽいパイプラインがあるかも?とか思っているので、いろいろ試しながらわかった点で改良していこうと思います!

      seed値の付与に関する訂正まで、重ね重ねありがとうございます!
      記事内に反映させていただきます!

      【追記】私も試させていただいたんですが、確かに複数処理するとseed値はその都度ランダムに生成されているみたいですね。
      ただseedで取得できる値は各処理ごとに同じなんですよね。(1枚目がseed=1234なら、2枚目もseed=1234)
      この現象に関しては、解決できたら上に追記させていただきますね!本当にありがとうございました!

  17. DfsBootTest より:

    お酒飲みながら推測で例を書いてしまいました、ごめんなさい

    なぜseed値が変わるのに変数の値が変わらないのか、仕様に疎いため謎です
    ちょっと理解できないので、理解が及ぶように書き換えてみました

    動作試験は行っておりますが、不備があれば教えてください
    書き換え箇所はseedの部分とwhile以下です
    ————————————————
    #seed値
    seed=-1#@param {type:”number”}
    if seed is None or seed == -1:
    inputSeed = random.randint(0, 2147483647)
    else:
    inputSeed = seed

    ————————————————
    while i < int(count_images):
    if seed is None or seed == -1:valueSeed = inputSeed + i
    generator = torch.Generator(device="cuda").manual_seed(valueSeed)

    #画像生成
    image = pipe(prompt,
    negative_prompt=n_prompt,
    width=width,
    height=height,
    generator=generator,
    guidance_scale=CFG_scale,
    num_inference_steps=Steps
    ).images[0]

    #画像名生成
    #| 現在の日本時間を取得
    jst_now = datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9)))
    #| ファイル名を作成
    file_name = (jst_now.strftime(file_format)
    + "_" + str(valueSeed))
    image_name = file_name + f".png"

    #画像保存
    save_location = os.path.join(save_path, image_name)
    image.save(save_location)
    i = i + 1
    print(" ————————- ")

    ————————————————
    seed値指定が-1の場合は、whileでその値をもとにseedを+1・・・してます
    webuiの仕様に近づけたと思いますが、generatorをwhile内で都度指定してるので、もしかしたら現行と何か動きが変わっているかもしれません

    whileのすぐ下のifはelseが不要なので1行に続けて書いてます、間違いではありません
    変数名は本来であればスネークケースで書くべきですが、改変したことがわかるようにあえてキャメルケースで書いてます、気になるようであれば書き換えてください

    動作試験は、-1指定で4枚程度同時生成して、その後生成画像のseed値で同じ画像になるか目視確認されるとよいかと思います

    お手数をお掛けして申し訳ございません、以上です

  18. DfsBootTest より:

    2023/05/15_06:16追記

    ちょっと調べていて、
    generator = torch.Generator(device=”cuda”).manual_seed(inputSeed)
    はgeneratorの初期化なので、while外が良いらしいので、先程の投稿内容は一時保留でお願いします!

    以下、GPT先生のコメント
    ループ内でのGeneratorの初期化:
    現在のコードでは、whileループの中で毎回torch.Generatorが初期化されています。Generatorを初期化するために、毎回計算リソースを使用する必要はありません。初期化はループの外で1回だけ実行することができます。
    この場合、Generatorオブジェクトを初期化しておき、ループ内で必要な場合はそのオブジェクトを使用するように変更することができます。

    寝て起きたら続きやりますね、すみません

  19. DfsBootTest より:

    動作確認終わりました、以下で問題ないと思われます

    ——————————————–
    #seed値
    seed=-1#@param {type:”number”}
    if seed is None or seed == -1:
    inputSeed = random.randint(0, 2147483647)
    else:
    inputSeed = seed

    ——————————————–
    generator = torch.Generator(device=”cuda”)
    if inputSeed is not None:generator.manual_seed(inputSeed)

    i = 0
    while i < int(count_images):
    # 画像生成
    image = pipe(prompt,
    negative_prompt=n_prompt,
    width=width,
    height=height,
    generator=generator,
    guidance_scale=CFG_scale,
    num_inference_steps=Steps
    ).images[0]

    # 画像名作成
    jst_now = datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9)))
    file_name = jst_now.strftime(file_format) + "_" + str(inputSeed)
    image_name = file_name + f".png"

    # 画像をcolab環境に保存
    save_location = os.path.join(save_path, image_name)
    image.save(save_location)

    # inputSeed の更新
    if inputSeed is not None:inputSeed += 1
    i += 1

    ——————————————–
    その他として、chatGPTに嘘をつかれてました!w
    一転二転して申し訳ないですが、試行錯誤してみたらzip形式でなくても問題ない様です

    • 悠 より:

      Dfsさん、本当にありがとうございます!
      こんなに詳しくご説明していただき、感謝しかありません…!!

      1つだけ私が確認できた現象なんですが、例えばseed値を-1、生成枚数を2にして生成された2枚が、
      2023xxx_xxx_1234.png
      2023xxx_xxx_1235.png
      だとします。

      ここでseed値を1234、生成枚数を2にして生成すると、2枚とも完璧に同じ画像が出力されます。

      次にseed値を1234、生成枚数を1にして生成すると、2023xxx_xxx_1234.pngが生成されます。

      ただ、seed値を1235、生成枚数を1にして生成すると、2023xxx_xxx_1235.pngとは別の画像が生成されます。

      これってどう解釈するのが正しいのでしょうか?コードまで教えていただき、更に質問までさせていただく非礼をお許しください。

  20. DfsBootTest より:

    確認しました、たしかに挙動が変ですね

    言い訳となりますが、私のcolabノートブックに、このページで言う”5つ目のセル”が試験用試作用含めて7つ程度置いてありまして、混合しているようです 申し訳ございません
    まとまった時間がとれたら再度確認してみます

    ひとまず、昨晩のはじめの投稿内容であれば動いたはずです
    ——————————————————–
    #seed値
    seed=-1#@param {type:”number”}
    if seed is None or seed == -1:
    inputSeed = random.randint(0, 2147483647)
    else:
    valueSeed = seed            # ←ここだけ変数変えてます     
    ——————————————————–
    while i < int(count_images):
    #generator
    if seed is None or seed == -1:valueSeed = inputSeed + i
    generator = torch.Generator(device="cuda").manual_seed(valueSeed)

    #画像を生成
    image = pipe(prompt,
    negative_prompt=n_prompt,
    width=width,
    height=height,
    generator=generator,
    guidance_scale=CFG_scale,
    num_inference_steps=Steps
    ).images[0]

    #出力する画像の名前を生成する
    # 現在の日本時間を取得
    jst_now = datetime.datetime.now(datetime.timezone(datetime.timedelta(hours=9)))
    #ファイル名を作成
    file_name = (jst_now.strftime(file_format)
    + "_" + str(valueSeed))
    image_name = file_name + f".png"

    #画像を保存する
    save_location = os.path.join(save_path, image_name)
    image.save(save_location)

    print(" ——————————————————– ")
    i = i + 1

    ——————————————————–
    体たらくで申し訳ない、です
    generator の初期化を複数回行う(らしい)仕様のままですが、体感実行時間は大差ないと思います、ご確認ください

    • 悠 より:

      おおおおお!!!
      動作することを確認させていただきました!本当にすごすぎます!!

      早速記事内に追記させていただきますね!私的には十分すぎるように思います!

  21. DfsBootTest より:

    こんばんわ
    サンプラー(スケジューラー)をここの5の実行フェイズで変更する試作版が作成出来ました
    やっぱりモデルによって得意なサンプラあるので、変更できるか否かは結構重要かと思うんですよ

    一部だけ紹介
    #Sampler
    print(“old_oldSampler: ” + oldSampler)
    #oldSampler = “” # 初回実行時の初期値を設定
    useSampler=”DPMSolverMultistepScheduler” #@param[“EulerAncestralDiscreteScheduler”,”EulerDiscreteScheduler”,”LMSDiscreteScheduler”,”PNDMScheduler”,”DDIMScheduler”,”DPMSolverMultistepScheduler”] {allow-input: true}
    if not ‘oldSampler’ or useSampler != oldSampler:
    scheduler_class = xyz

    もうちょっと試してみて、公開可能な要件でしたらサンプルコードをこちらでお知らせしますね、お待ちください

    • 悠 より:

      こんばんは!
      サンプラーまで取り組まれているとは…!凄すぎます!

      私の方はimg2imgの方を取り組んでみているんですが、なぜかさっぱり上手くいきません(涙)
      ただ、Real-ESRGANというアップスケーラーを使って、diffusersで生成した画像を高画質化することはできたので、これを近いうちにまとめようかなって思っています!

      hires.fixと比べると正直物足りないという欠点もあるんですが…

  22. DfsBootTest より:

    私はyoutube表示画像用に640×360ばかり作成しているので、大きな画像はあまり必要ないのですが、hires.fixは組み込めるなら面白そうですね
    ただ設定項目もそれなりにあるようで、Denoising strength(ノイズを除去する強さ?)はどうやっているのか全く意味不明です

    いくつか別サイトを拝見してみましたが、アップスケーラーはLatentを推奨されているところが多いようですね まあ向き不向きもあるとの事ですが

    高画質化するメカニズムは生成後にi2iで更に再加工しているからなのでしょうか、であればまずはi2iの導入が必要ですね

    サンプラー導入につきましては、DPM++ 2S a,DPM++ 2Mなどwebuiで使用できた全てに該当するものがまだ組み込めてないので、そちらを進めたいです

    https://wonderhorn.net/column/sampler.html
    こちらで”拡散モデルにおけるサンプラー/スケジューラーとは何か”を紹介されてました、難しい話なので「そうなのか」程度しか思えませんでしたがより理解が深まるかと思います

  23. DfsBootTest より:

    ご報告

    まずサンプラー選択機能については、モデルにより実装可能だが、起動できないものもあるということが判明しました
    おそらく、Hugging Faceにあるモデル名ページにサンプラー関連ファイルがあるか否かが条件
    Diffusersとしてサンプラーをインポートできているので、モデルに紐づいてはいないのでは?という見解です
    逆に考えると、jsonファイルを偽装すればどのモデルでも対応可能なのでは?と考えますが、手がすすんでません

    更に横展開すればvaeも偽装で何とかなる?・・・と考えますが、こちらも不明
    vaeは明度や輝度関連が多いので画像editerである程度は調整できるので保留です

    次にpngメタデータの件ですが、こちらはmetadata = PngInfo()、metadata.add_text()を追加すれば情報は載せられる(ttps://image-convert.cman.jp/imgInfo/等)のですが、
    ttps://www.aipictors.com/ではなぜかメタデータの反映が出来ない状態です
    恐らくはwebuiでも参照できないはず
    残念ながら原因解析は進んでいなくて、不確定な情報となりますのでご紹介できない範疇かと思います

    あとはclipskip=2も実装したいのですが、こちらは全く進んでいません
    あまり有力な情報は無いものですね

    以上です

    • 悠 より:

      お久しぶりです!ご報告ありがとうございます!

      サンプラーに関しては個体差があるとは…存じ上げておりませんでした…!
      なんとか2M Karrasを全てのモデルで実装できれば便利なんですけどね…
      一番早くて出来がよく万能感があると個人的思っています!

      メタデータの読み込みはサイトによって違うんですかね?majinAIとかだとどうなるんでしょうね…

      clipskipに関しては私も一切見たことがありません…!

      そういえば、最近下記のようなプロジェクトを見かけました。DiffusersベースのWebUI的なものみたいです。
      https://github.com/ddPn08/Radiata

      これをcolabで動かせたらいいんですけどね…おそらくremoteUIになるから規制対象ですよね…

      Diffusersを考えれば考えるほど、如何にwebuiが多機能かを痛感しますよね。あれが無料というのが信じられません

  24. 匿名 より:

    DPM++ 2M Karrasに関してはこちらで有効にできるようです。

    https://github.com/huggingface/diffusers/issues/2905
    https://github.com/huggingface/diffusers/pull/2874

    審美眼もなく、数も試せてませんが、一応有無で差分はありました。

    • 悠 より:

      コメントありがとうございます!!

      またまた非常に有益な情報感謝いたします!!
      早速試させていただきます!

      個人的にDPM++ 2M Karrasが一番好きなサンプラーなので、diffusersで使えるのはありがたいです!

      • 匿名 より:

        追記
        VAEがsd-vae-ft-emaだと発色がおかしくなるかもなので、おかしかったら他の物を試してください。

        • 悠 より:

          試してみたんですが、なぜかEulerDiscreteSchedulerの方がくっきりしていて好みでしたw
          何か私のやり方が間違えている気がします…

          それに仰る通り、sd-vae-ft-emaだと発色が微妙な気がしましたので、もう少し探ってみます!

          本当に情報ありがとうございます!

  25. DfsBootTest より:

    こんばんは、いつも大変お世話になっております

    DPM++ 2M Karrasの導入について私も試そうと思いましたが、そもそもこのサンプラー名の++が何の略か不明で頓挫してしまいました

    で、かわりにdiffusersのページ(https://huggingface.co/docs/diffusers/index)の左カラムの下の方にあるSCHEDULERSを全部試してみました
    ———————————————————
    from diffusers import (
    EulerAncestralDiscreteScheduler as EulerA,
    EulerDiscreteScheduler as Euler,
    LMSDiscreteScheduler as LMS,
    HeunDiscreteScheduler as Heun,
    DPMSolverSinglestepScheduler as DPMSolS,
    DPMSolverMultistepScheduler as DPMSolM,
    KDPM2DiscreteScheduler as KDPM2,
    KDPM2AncestralDiscreteScheduler as KDPM2A,
    DDIMInverseScheduler as DDIMInverse,
    DDIMScheduler as DDIM,
    DDPMScheduler as DDPM,
    DEISMultistepScheduler as DEISM,
    KarrasVeScheduler as KarrasVe,
    PNDMScheduler as PNDM,
    IPNDMScheduler as IPNDM,
    VQDiffusionScheduler as VQDiffusion,
    UniPCMultistepScheduler as UniPCM,
    RePaintScheduler as RePaint
    )
    from diffusers.schedulers import(ScoreSdeVeScheduler as ScoreSdeVe,
    ScoreSdeVpScheduler as ScoreSdeVp)
    ※一部のみそのままではインポートできなかったので別記述
    ※長すぎるので名称を一時変更してますが、webuiと同等の命名規則や省略方法がわからないので独自に変更してます

    ———————————————————
    次にサンプラーの変更はこんな感じのコンボボックスを用意
    useSampler=”” #@param[“EulerA”,”Euler”,”LMS”,”Heun”,”DPMSolS”,”DPMSolM”,”KDPM2″,”KDPM2A”,”DDIMInverse”,”DDIM”,”DDPM”,”DEISM”,”KarrasVe”,”PNDM”,”ScoreSdeVe”,”IPNDM”,”ScoreSdeVp”,”VQDiffusion”,”UniPCM”,”RePaint”] {allow-input: true}
    変更には随時pipeの再構築が必要です

    ———————————————————
    同じ条件下でなければ意味が無いので以下の通りに指定して利用可能可否を確認しました
    Prompt:同じ(内容割愛)
    Negative prompt:同じ(内容割愛)
    Steps:22
    CFG scale:8
    Seed:-1
    Size:512×768
    Model:stablediffusionapi/anythingelse-v4
    vae:stablediffusionapi/anything-v5
    Lora:未使用
    Model hash: 不明(無しまたは未指定)
    Clip skip: 不明(無しまたは未指定)
    Sampler:※変動

    結果はこんな感じで、特記事項が無いものは概ね問題ない様でした
    EulerAncestralDiscreteScheduler EulerA
    EulerDiscreteScheduler Euler
    LMSDiscreteScheduler LMS 眼や顔が崩れる
    HeunDiscreteScheduler Heun
    DPMSolverSinglestepScheduler DPMSolS
    DPMSolverMultistepScheduler DPMSolM
    KDPM2DiscreteScheduler KDPM2
    KDPM2AncestralDiscreteScheduler KDPM2A 顔が崩れる?
    DDIMInverseScheduler DDIMInverse ノイズのまま
    DDIMScheduler DDIM
    DDPMScheduler DDPM
    DEISMultistepScheduler DEISM
    KarrasVeScheduler KarrasVe Errで生成不可
    PNDMScheduler PNDM 眼や顔が崩れる
    schedulers.ScoreSdeVeScheduler ScoreSdeVe Errで生成不可  そもそも方法が違うのかも
    IPNDMScheduler IPNDM ノイズのまま
    schedulers.ScoreSdeVpScheduler ScoreSdeVp Errで生成不可  そもそも方法が違うのかも
    VQDiffusionScheduler VQDiffusion Errで生成不可
    UniPCMultistepScheduler UniPCM
    RePaintScheduler RePaint Errで生成不可

    Tabズレで見づらかったらすみません、画像で用意出来ればよかったのですが
    Stepsが40前後以上からさらに悪くなるものもあるとの情報でしたが、リソースの問題で確認出来てません

    ———————————————————
    vaeについては、やや面倒なのですがconfig.jsonファイルと.binファイルのDLリンクが判れば、
    パイソンcolabに一時的な格納フォルダを作成してそこに格納、パスを指定すれば利用可能な様です
    useVae =”/content/mountVae”
    usedVae = AutoencoderKL.from_pretrained(useVae)

    ———————————————————
    メタデータはmajinAIにて確認しましたが何も表示されませんでした(webuiで作成したものは表示を確認)

    from PIL.PngImagePlugin import PngInfo
    metadata = PngInfo()
    metadata.add_text(“Parameters”, prompt
    + ” .Negative prompt:” + n_prompt
    + ” .Steps:” + str(Steps)
    + ” Sampler:” + useSampler
    + ” CFG scale:” + str(CFG_scale)
    + ” Seed:” + str(valueSeed)
    + ” Size:” + str(width) + “x” + str(height)
    + ” Model hash:” + “”
    + ” Model:” + useModel
    + ” Clip skip:” + “”
    )
    save_location = os.path.join(save_path, image_name)
    image.save(save_location,pnginfo=metadata)

    上記のようにメタデータを作成して一緒に保存すれば情報は乗るのですが、特定のサイトだと反映されません、原因判れば教えてほしいです

    以上です

    • 悠 より:

      お疲れ様です!!

      正直内容はわかっていないんですけど、下の2つの記事
      https://arxiv.org/abs/2211.01095
      https://www.reddit.com/r/StableDiffusion/comments/13nl6pk/dpm_sde2mkarras_is_rejected_by_iclr_what_happened/
      とか見るに、DPM-Solver++っていうのがDPM++ 2M KarrasのDPM++の部分かな?と思っています。

      なので、上で紹介してくださった
      scheduler = DPMSolverMultistepScheduler(use_karras_sigmas=True)
      これがDPM++ 2M Karrasのことかな?とこれを書いている時点では考えています!

      ただ実行しても、EulerDiscreteSchedulerの方が綺麗に感じたので、多分私の実装の仕方が間違えてる気がします(涙)現在試行錯誤中です。

      サンプラーの検証、すごいです!よく見ればDDIMもあるんですね。DDIMは確かステップ数少な目で結果が綺麗なので、DPM++ 2M Karras登場前にはよく使われていたと聞いたことがあります。これも試してみます!

      VAEとメタデータに関しての情報までありがとうございます!!
      メタデータに関してなんですが、webuiの形式とコンマの位置が少しずれるだけで上手く反映できなくなるというようなことを聞いたことがあります。
      何か特定の形式があって、それに従わないと上手く反映できないのかもしれないですよね…

      私も明日試してみます!

  26. ゆきち より:

    この度は素敵な記事を本当にありがとうございます。
    3日ほど使っておりましたが、急に三つ目のコマにエラーが発生するようになり
    unet/diffusinon_pytorch_model.safeteosors not found
    と出てきました。
    またGPUに接続ができなくなっていました。(これが先の原因だと)
    素人質問で申し訳ないのですが、この度この記事で作ったdiffuserの内容でもこちらのGPUの上限は受け入れ、無料でこれ以上作るのは不可という認識で合っておりますでしょうか。

    • 悠 より:

      コメントありがとうございます!

      私も試してみたんですが、特にそのようなエラーは出ず画像生成できました。
      「unet/diffusinon_pytorch_model.safeteosors not found」

      に関してなのですが、safetensorsのスペルが違うので、3つ目のセル内のコードのどこかのスペルが間違っていたするのではないでしょうか?

      Diffusersはcolabの制限がかからないので、これからも無料で作成できますよ!

      • ゆきち より:

        できました!
        本当にありがとうございます!

      • ゆきち より:

        ランタイムが切れた際に再接続をすると、GPUバックエンドに接続できません
        となってしまうのですが、
        →無視するとセル1が実行できなくなる
        →GPUなしで接続するとセル4が実行できなくなる
        状態です。昨日この状態になり、今日ご教示いただいて難なく実行できたのですが、またこの状態になってしまいました。
        対処法などあれば、教えて頂きたいです。
        お忙しい中大変申し訳ございません。

        • 悠 より:

          無料版のColabでは一日に使えるGPUの量に制限があるので、「GPUバックエンドに接続できません」と出たときはその日はもう使えません!

          だいたい半日~1日程度で回復するのでそれを待つか、ColabのPro版に入るかになりますね~