dikdimon's picture
Upload extensions using SD-Hub extension
3dabe4a verified
from PIL import Image, ImageDraw
import gradio as gr
def parse_mapping(data: list) -> list:
mapping = []
for [X, Y, W] in data:
if not X.strip():
continue
mapping.append(
(
(float(X.split(":")[0]), float(X.split(":")[1])),
(float(Y.split(":")[0]), float(Y.split(":")[1])),
float(W),
)
)
return mapping
def validata_mapping(data: list) -> bool:
try:
for [X, Y, W] in data:
if not X.strip():
continue
float(X.split(":")[0])
float(X.split(":")[1])
float(Y.split(":")[0])
float(Y.split(":")[1])
float(W)
return True
except AssertionError:
print("\n\n[Couple] Incorrect number of : in Mapping...\n\n")
return False
except ValueError:
print("\n\n[Couple] Non-Number in Mapping...\n\n")
return False
def visualize_mapping(p_WIDTH: int, p_HEIGHT: int, data: list) -> Image:
if not (validata_mapping(data)):
return None
COLORS = ("red", "orange", "yellow", "green", "blue", "violet", "purple", "white")
matt = Image.new("RGB", (p_WIDTH, p_HEIGHT), "black")
draw = ImageDraw.Draw(matt)
mapping = parse_mapping(data)
print("\nAdv. Preview:")
for tile_index in range(len(mapping)):
color_index = tile_index % len(COLORS)
(X, Y, W) = mapping[tile_index]
x_from = int(p_WIDTH * X[0])
x_to = int(p_WIDTH * X[1])
y_from = int(p_HEIGHT * Y[0])
y_to = int(p_HEIGHT * Y[1])
weight = W
print(f" [{y_from:4d}:{y_to:4d}, {x_from:4d}:{x_to:4d}] = {weight:.2f}")
draw.rectangle(
[(x_from, y_from), (x_to, y_to)], outline=COLORS[color_index], width=2
)
return matt
def couple_UI(script, title: str):
with gr.Accordion(label=title, open=False):
with gr.Row():
enable = gr.Checkbox(label="Enable", elem_id="fc_enable")
mode = gr.Radio(
["Basic", "Advanced"],
label="Region Assignment",
value="Basic",
)
separator = gr.Textbox(
label="Couple Separator",
lines=1,
max_lines=1,
placeholder="Leave empty to use newline",
)
with gr.Group() as basic_settings:
with gr.Row():
direction = gr.Radio(
["Horizontal", "Vertical"],
label="Tile Direction",
value="Horizontal",
)
background = gr.Radio(
["None", "First Line", "Last Line"],
label="Global Effect",
value="None",
)
with gr.Group(visible=False, elem_id="fc_adv") as adv_settings:
mapping = gr.Dataframe(
label="Mapping",
headers=["x", "y", "weight"],
datatype="str",
row_count=(2, "dynamic"),
col_count=(3, "fixed"),
interactive=True,
type="array",
value=[["0:0.5", "0.0:1.0", "1.0"], ["0.5:1.0", "0.0:1.0", "1.0"]],
)
preview_img = gr.Image(
image_mode="RGB",
label="Mapping Preview",
type="pil",
interactive=False,
height=512,
)
with gr.Row():
preview_width = gr.Number(value=1024, label="Width", precision=0)
preview_height = gr.Number(value=1024, label="Height", precision=0)
preview_btn = gr.Button("Preview Mapping", elem_id="fc_preview")
preview_btn.click(
visualize_mapping,
[preview_width, preview_height, mapping],
preview_img,
)
def on_radio_change(choice):
if choice == "Basic":
return [
gr.Group.update(visible=True),
gr.Group.update(visible=False),
]
else:
return [
gr.Group.update(visible=False),
gr.Group.update(visible=True),
]
mode.change(on_radio_change, mode, [basic_settings, adv_settings])
script.paste_field_names = []
script.infotext_fields = [
(enable, "forge_couple"),
(direction, "forge_couple_direction"),
(background, "forge_couple_background"),
(separator, "forge_couple_separator"),
(mode, "forge_couple_mode"),
(mapping, "forge_couple_mapping"),
]
for comp, name in script.infotext_fields:
comp.do_not_save_to_config = True
script.paste_field_names.append(name)
return [enable, direction, background, separator, mode, mapping]