Add buttons for random and reuse seed.
Random button sets seed to -1, reuse copies the seed from the last generated image.
This commit is contained in:
parent
7476593014
commit
a96076f49c
|
@ -11,6 +11,8 @@ titles = {
|
||||||
"Batch size": "How many image to create in a single batch",
|
"Batch size": "How many image to create in a single batch",
|
||||||
"CFG Scale": "Classifier Free Guidance Scale - how strongly the image should conform to prompt - lower values produce more creative results",
|
"CFG Scale": "Classifier Free Guidance Scale - how strongly the image should conform to prompt - lower values produce more creative results",
|
||||||
"Seed": "A value that determines the output of random number generator - if you create an image with same parameters and seed as another image, you'll get the same result",
|
"Seed": "A value that determines the output of random number generator - if you create an image with same parameters and seed as another image, you'll get the same result",
|
||||||
|
"\u{1f3b2}\ufe0f": "Set seed to -1, which will cause a new random number to be used every time",
|
||||||
|
"\u267b\ufe0f": "Reuse seed from last generation, mostly useful if it was randomed",
|
||||||
|
|
||||||
"Inpaint a part of image": "Draw a mask over an image, and the script will regenerate the masked area with content according to prompt",
|
"Inpaint a part of image": "Draw a mask over an image, and the script will regenerate the masked area with content according to prompt",
|
||||||
"SD upscale": "Upscale image normally, split result into tiles, improve each tile using img2img, merge whole image back",
|
"SD upscale": "Upscale image normally, split result into tiles, improve each tile using img2img, merge whole image back",
|
||||||
|
|
|
@ -83,11 +83,13 @@ class StableDiffusionProcessing:
|
||||||
|
|
||||||
|
|
||||||
class Processed:
|
class Processed:
|
||||||
def __init__(self, p: StableDiffusionProcessing, images_list, seed, info):
|
def __init__(self, p: StableDiffusionProcessing, images_list, seed, subseed, info):
|
||||||
self.images = images_list
|
self.images = images_list
|
||||||
self.prompt = p.prompt
|
self.prompt = p.prompt
|
||||||
self.negative_prompt = p.negative_prompt
|
self.negative_prompt = p.negative_prompt
|
||||||
self.seed = seed
|
self.seed = seed
|
||||||
|
self.subseed = subseed
|
||||||
|
self.subseed_strength = p.subseed_strength
|
||||||
self.info = info
|
self.info = info
|
||||||
self.width = p.width
|
self.width = p.width
|
||||||
self.height = p.height
|
self.height = p.height
|
||||||
|
@ -100,6 +102,8 @@ class Processed:
|
||||||
"prompt": self.prompt if type(self.prompt) != list else self.prompt[0],
|
"prompt": self.prompt if type(self.prompt) != list else self.prompt[0],
|
||||||
"negative_prompt": self.negative_prompt if type(self.negative_prompt) != list else self.negative_prompt[0],
|
"negative_prompt": self.negative_prompt if type(self.negative_prompt) != list else self.negative_prompt[0],
|
||||||
"seed": int(self.seed if type(self.seed) != list else self.seed[0]),
|
"seed": int(self.seed if type(self.seed) != list else self.seed[0]),
|
||||||
|
"subseed": int(self.subseed if type(self.subseed) != list else self.subseed[0]),
|
||||||
|
"subseed_strength": self.subseed_strength,
|
||||||
"width": self.width,
|
"width": self.width,
|
||||||
"height": self.height,
|
"height": self.height,
|
||||||
"sampler": self.sampler,
|
"sampler": self.sampler,
|
||||||
|
@ -352,7 +356,7 @@ def process_images(p: StableDiffusionProcessing) -> Processed:
|
||||||
images.save_image(grid, p.outpath_grids, "grid", all_seeds[0], all_prompts[0], opts.grid_format, info=infotext(), short_filename=not opts.grid_extended_filename, p=p)
|
images.save_image(grid, p.outpath_grids, "grid", all_seeds[0], all_prompts[0], opts.grid_format, info=infotext(), short_filename=not opts.grid_extended_filename, p=p)
|
||||||
|
|
||||||
devices.torch_gc()
|
devices.torch_gc()
|
||||||
return Processed(p, output_images, all_seeds[0], infotext())
|
return Processed(p, output_images, all_seeds[0], all_subseeds[0], infotext())
|
||||||
|
|
||||||
|
|
||||||
class StableDiffusionProcessingTxt2Img(StableDiffusionProcessing):
|
class StableDiffusionProcessingTxt2Img(StableDiffusionProcessing):
|
||||||
|
|
138
modules/ui.py
138
modules/ui.py
|
@ -53,6 +53,12 @@ css_hide_progressbar = """
|
||||||
.meta-text { display:none!important; }
|
.meta-text { display:none!important; }
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
# Using constants for these since the variation selector isn't visible.
|
||||||
|
# Important that they exactly match script.js for tooltip to work.
|
||||||
|
random_symbol = '\U0001f3b2\ufe0f' # 🎲️
|
||||||
|
reuse_symbol = '\u267b\ufe0f' # ♻️
|
||||||
|
|
||||||
|
|
||||||
def plaintext_to_html(text):
|
def plaintext_to_html(text):
|
||||||
text = "<p>" + "<br>\n".join([f"{html.escape(x)}" for x in text.split('\n')]) + "</p>"
|
text = "<p>" + "<br>\n".join([f"{html.escape(x)}" for x in text.split('\n')]) + "</p>"
|
||||||
return text
|
return text
|
||||||
|
@ -221,40 +227,6 @@ def visit(x, func, path=""):
|
||||||
func(path + "/" + str(x.label), x)
|
func(path + "/" + str(x.label), x)
|
||||||
|
|
||||||
|
|
||||||
def create_seed_inputs():
|
|
||||||
with gr.Row():
|
|
||||||
seed = gr.Number(label='Seed', value=-1)
|
|
||||||
subseed = gr.Number(label='Variation seed', value=-1, visible=False)
|
|
||||||
seed_checkbox = gr.Checkbox(label="Extra", elem_id="subseed_show", value=False)
|
|
||||||
|
|
||||||
with gr.Row():
|
|
||||||
subseed_strength = gr.Slider(label='Variation strength', value=0.0, minimum=0, maximum=1, step=0.01, visible=False)
|
|
||||||
seed_resize_from_w = gr.Slider(minimum=0, maximum=2048, step=64, label="Resize seed from width", value=0, visible=False)
|
|
||||||
seed_resize_from_h = gr.Slider(minimum=0, maximum=2048, step=64, label="Resize seed from height", value=0, visible=False)
|
|
||||||
|
|
||||||
def change_visiblity(show):
|
|
||||||
|
|
||||||
return {
|
|
||||||
subseed: gr_show(show),
|
|
||||||
subseed_strength: gr_show(show),
|
|
||||||
seed_resize_from_h: gr_show(show),
|
|
||||||
seed_resize_from_w: gr_show(show),
|
|
||||||
}
|
|
||||||
|
|
||||||
seed_checkbox.change(
|
|
||||||
change_visiblity,
|
|
||||||
inputs=[seed_checkbox],
|
|
||||||
outputs=[
|
|
||||||
subseed,
|
|
||||||
subseed_strength,
|
|
||||||
seed_resize_from_h,
|
|
||||||
seed_resize_from_w
|
|
||||||
]
|
|
||||||
)
|
|
||||||
|
|
||||||
return seed, subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w
|
|
||||||
|
|
||||||
|
|
||||||
def add_style(name: str, prompt: str, negative_prompt: str):
|
def add_style(name: str, prompt: str, negative_prompt: str):
|
||||||
if name is None:
|
if name is None:
|
||||||
return [gr_show(), gr_show()]
|
return [gr_show(), gr_show()]
|
||||||
|
@ -282,6 +254,94 @@ def interrogate(image):
|
||||||
return gr_show(True) if prompt is None else prompt
|
return gr_show(True) if prompt is None else prompt
|
||||||
|
|
||||||
|
|
||||||
|
def create_seed_inputs():
|
||||||
|
with gr.Row():
|
||||||
|
with gr.Box():
|
||||||
|
with gr.Row(elem_id='seed_row'):
|
||||||
|
seed = gr.Number(label='Seed', value=-1)
|
||||||
|
seed.style(container=False)
|
||||||
|
random_seed = gr.Button('🎲', elem_id='random_seed')
|
||||||
|
reuse_seed = gr.Button('♻️', elem_id='reuse_seed')
|
||||||
|
|
||||||
|
with gr.Box(elem_id='subseed_show_box'):
|
||||||
|
seed_checkbox = gr.Checkbox(label='Extra', elem_id='subseed_show', value=False)
|
||||||
|
|
||||||
|
# Components to show/hide based on the 'Extra' checkbox
|
||||||
|
seed_extras = []
|
||||||
|
|
||||||
|
with gr.Row(visible=False) as seed_extra_row_1:
|
||||||
|
seed_extras.append(seed_extra_row_1)
|
||||||
|
with gr.Box():
|
||||||
|
with gr.Row(elem_id='subseed_row'):
|
||||||
|
subseed = gr.Number(label='Variation seed', value=-1)
|
||||||
|
subseed.style(container=False)
|
||||||
|
random_subseed = gr.Button(random_symbol, elem_id='random_subseed')
|
||||||
|
reuse_subseed = gr.Button(reuse_symbol, elem_id='reuse_subseed')
|
||||||
|
subseed_strength = gr.Slider(label='Variation strength', value=0.0, minimum=0, maximum=1, step=0.01)
|
||||||
|
|
||||||
|
with gr.Row(visible=False) as seed_extra_row_2:
|
||||||
|
seed_extras.append(seed_extra_row_2)
|
||||||
|
seed_resize_from_w = gr.Slider(minimum=0, maximum=2048, step=64, label="Resize seed from width", value=0)
|
||||||
|
seed_resize_from_h = gr.Slider(minimum=0, maximum=2048, step=64, label="Resize seed from height", value=0)
|
||||||
|
|
||||||
|
random_seed.click(fn=lambda: -1, show_progress=False, inputs=[], outputs=[seed])
|
||||||
|
random_subseed.click(fn=lambda: -1, show_progress=False, inputs=[], outputs=[subseed])
|
||||||
|
|
||||||
|
def change_visibility(show):
|
||||||
|
return {comp: gr_show(show) for comp in seed_extras}
|
||||||
|
|
||||||
|
seed_checkbox.change(change_visibility, show_progress=False, inputs=[seed_checkbox], outputs=seed_extras)
|
||||||
|
|
||||||
|
return seed, reuse_seed, subseed, reuse_subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w
|
||||||
|
|
||||||
|
|
||||||
|
def connect_reuse_seed(seed: gr.Number, reuse_seed: gr.Button, generation_info: gr.Textbox):
|
||||||
|
""" Connects a 'reuse seed' button's click event so that it copies last used
|
||||||
|
seed value from generation info the to the seed."""
|
||||||
|
def copy_seed(gen_info_string: str):
|
||||||
|
try:
|
||||||
|
gen_info = json.loads(gen_info_string)
|
||||||
|
return gen_info.get('seed', -1)
|
||||||
|
except json.decoder.JSONDecodeError as e:
|
||||||
|
if gen_info_string != '':
|
||||||
|
print("Error parsing JSON generation info:", file=sys.stderr)
|
||||||
|
print(gen_info_string, file=sys.stderr)
|
||||||
|
return -1
|
||||||
|
|
||||||
|
reuse_seed.click(
|
||||||
|
fn=copy_seed,
|
||||||
|
show_progress=False,
|
||||||
|
inputs=[generation_info],
|
||||||
|
outputs=[seed]
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def connect_reuse_subseed(seed: gr.Number, reuse_seed: gr.Button, generation_info: gr.Textbox):
|
||||||
|
""" Connects a 'reuse subseed' button's click event so that it copies last used
|
||||||
|
subseed value from generation info the to the subseed. If subseed strength
|
||||||
|
was 0, i.e. no variation seed was used, it copies the normal seed value instead."""
|
||||||
|
def copy_seed(gen_info_string: str):
|
||||||
|
try:
|
||||||
|
gen_info = json.loads(gen_info_string)
|
||||||
|
subseed_strength = gen_info.get('subseed_strength', 0)
|
||||||
|
if subseed_strength > 0:
|
||||||
|
return gen_info.get('subseed', -1)
|
||||||
|
else:
|
||||||
|
return gen_info.get('seed', -1)
|
||||||
|
except json.decoder.JSONDecodeError as e:
|
||||||
|
if gen_info_string != '':
|
||||||
|
print("Error parsing JSON generation info:", file=sys.stderr)
|
||||||
|
print(gen_info_string, file=sys.stderr)
|
||||||
|
return -1
|
||||||
|
|
||||||
|
reuse_seed.click(
|
||||||
|
fn=copy_seed,
|
||||||
|
show_progress=False,
|
||||||
|
inputs=[generation_info],
|
||||||
|
outputs=[seed]
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
def create_toprow(is_img2img):
|
def create_toprow(is_img2img):
|
||||||
with gr.Row(elem_id="toprow"):
|
with gr.Row(elem_id="toprow"):
|
||||||
with gr.Column(scale=4):
|
with gr.Column(scale=4):
|
||||||
|
@ -357,7 +417,7 @@ def create_ui(txt2img, img2img, run_extras, run_pnginfo):
|
||||||
width = gr.Slider(minimum=64, maximum=2048, step=64, label="Width", value=512)
|
width = gr.Slider(minimum=64, maximum=2048, step=64, label="Width", value=512)
|
||||||
height = gr.Slider(minimum=64, maximum=2048, step=64, label="Height", value=512)
|
height = gr.Slider(minimum=64, maximum=2048, step=64, label="Height", value=512)
|
||||||
|
|
||||||
seed, subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w = create_seed_inputs()
|
seed, reuse_seed, subseed, reuse_subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w = create_seed_inputs()
|
||||||
|
|
||||||
with gr.Group():
|
with gr.Group():
|
||||||
custom_inputs = modules.scripts.scripts_txt2img.setup_ui(is_img2img=False)
|
custom_inputs = modules.scripts.scripts_txt2img.setup_ui(is_img2img=False)
|
||||||
|
@ -383,6 +443,9 @@ def create_ui(txt2img, img2img, run_extras, run_pnginfo):
|
||||||
html_info = gr.HTML()
|
html_info = gr.HTML()
|
||||||
generation_info = gr.Textbox(visible=False)
|
generation_info = gr.Textbox(visible=False)
|
||||||
|
|
||||||
|
connect_reuse_seed(seed, reuse_seed, generation_info)
|
||||||
|
connect_reuse_subseed(subseed, reuse_subseed, generation_info)
|
||||||
|
|
||||||
txt2img_args = dict(
|
txt2img_args = dict(
|
||||||
fn=txt2img,
|
fn=txt2img,
|
||||||
_js="submit",
|
_js="submit",
|
||||||
|
@ -490,7 +553,7 @@ def create_ui(txt2img, img2img, run_extras, run_pnginfo):
|
||||||
width = gr.Slider(minimum=64, maximum=2048, step=64, label="Width", value=512)
|
width = gr.Slider(minimum=64, maximum=2048, step=64, label="Width", value=512)
|
||||||
height = gr.Slider(minimum=64, maximum=2048, step=64, label="Height", value=512)
|
height = gr.Slider(minimum=64, maximum=2048, step=64, label="Height", value=512)
|
||||||
|
|
||||||
seed, subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w = create_seed_inputs()
|
seed, reuse_seed, subseed, reuse_subseed, subseed_strength, seed_resize_from_h, seed_resize_from_w = create_seed_inputs()
|
||||||
|
|
||||||
with gr.Group():
|
with gr.Group():
|
||||||
custom_inputs = modules.scripts.scripts_img2img.setup_ui(is_img2img=True)
|
custom_inputs = modules.scripts.scripts_img2img.setup_ui(is_img2img=True)
|
||||||
|
@ -518,6 +581,9 @@ def create_ui(txt2img, img2img, run_extras, run_pnginfo):
|
||||||
html_info = gr.HTML()
|
html_info = gr.HTML()
|
||||||
generation_info = gr.Textbox(visible=False)
|
generation_info = gr.Textbox(visible=False)
|
||||||
|
|
||||||
|
connect_reuse_seed(seed, reuse_seed, generation_info)
|
||||||
|
connect_reuse_subseed(subseed, reuse_subseed, generation_info)
|
||||||
|
|
||||||
def apply_mode(mode, uploadmask):
|
def apply_mode(mode, uploadmask):
|
||||||
is_classic = mode == 0
|
is_classic = mode == 0
|
||||||
is_inpaint = mode == 1
|
is_inpaint = mode == 1
|
||||||
|
|
|
@ -2,7 +2,7 @@ transformers==4.19.2
|
||||||
diffusers==0.2.4
|
diffusers==0.2.4
|
||||||
basicsr==1.3.5
|
basicsr==1.3.5
|
||||||
gfpgan
|
gfpgan
|
||||||
gradio==3.3
|
gradio==3.3.1
|
||||||
numpy==1.23.3
|
numpy==1.23.3
|
||||||
Pillow==9.2.0
|
Pillow==9.2.0
|
||||||
realesrgan==0.2.5.0
|
realesrgan==0.2.5.0
|
||||||
|
|
26
style.css
26
style.css
|
@ -43,9 +43,31 @@
|
||||||
margin-right: auto;
|
margin-right: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#random_seed, #random_subseed, #reuse_seed, #reuse_subseed{
|
||||||
|
min-width: auto;
|
||||||
|
flex-grow: 0;
|
||||||
|
padding-left: 0.25em;
|
||||||
|
padding-right: 0.25em;
|
||||||
|
}
|
||||||
|
|
||||||
|
#seed_row, #subseed_row{
|
||||||
|
gap: 0.5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
#subseed_show_box{
|
||||||
|
min-width: auto;
|
||||||
|
flex-grow: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#subseed_show_box > div{
|
||||||
|
border: 0;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
#subseed_show{
|
#subseed_show{
|
||||||
min-width: 6em;
|
min-width: auto;
|
||||||
max-width: 6em;
|
flex-grow: 0;
|
||||||
|
padding: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#subseed_show label{
|
#subseed_show label{
|
||||||
|
|
Loading…
Reference in New Issue