File size: 15,591 Bytes
3c3804b
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
# encoding=utf8


import os
import cv2
import gradio as gr
import numpy as np
import re
import json

from huggingface_hub import login
from functions import *
from gradio.components import Component

login(token=os.getenv('LOGIN_TOKEN'))
css = './css/style.css'

# Initial a Gradio Block with specific theme
block = gr.Blocks(
    theme=gr.themes.Base(),
    css=css
).queue()

# Load javascript plugin
with open('javascript/bboxHint.js', 'r', encoding="utf-8") as file:
    value = file.read()
escaped_value = json.dumps(value)

with block:
    block.load(
        fn=None,
        _js=f"""() => {{
                const script = document.createElement("script");
                const text =  document.createTextNode({escaped_value});
                script.appendChild(text);
                document.head.appendChild(script);
            }}"""
    )
    gr.HTML(
        '<div style="text-align: center; margin: 20px auto;"> \
        <h1 style="font-size:5em">JoyType</h1> \
        <h1 style="font-size:2.5em">A Robust Design for Multilingual Visual Text Creation</h1> \
        </div>'
    )
    with gr.Row():
        with gr.Column(scale=3):
            with gr.Accordion('Basic Settings(基础设置)', open=True):
                with gr.Row(variant='compact'):
                    usr_prompt = gr.Textbox(label='Prompt(提示词)', elem_id='usr_prompt')
                with gr.Row(variant='compact'):
                    base_model = gr.Dropdown(
                        value='JoyType.v1.0', choices=model_list,
                        label='Base Model(基模型)', elem_id='base_model', allow_custom_value=False
                    )

            with gr.Accordion('Advanced Settings(高级设置)', open=False):
                with gr.Row(variant='compact'):
                    image_width = gr.Slider(label='Image Width(宽度)', minimum=256, maximum=768, value=512, step=32)
                    image_height = gr.Slider(label='Image Height(高度)', minimum=256, maximum=768, value=512, step=32)
                with gr.Row(variant='compact'):
                    num_samples = gr.Slider(label='Samples(生成数量)', minimum=1, maximum=4, value=2, step=1)
                    inference_steps = gr.Slider(label='Steps(推理步数)', minimum=10, maximum=50, value=20, step=1)
                with gr.Row(variant='compact'):
                    conditioning_scale = gr.Slider(label='Text Strength(文字强度)', minimum=0.1, maximum=2., value=1., step=0.1)
                    cfg_scale = gr.Slider(label='CFG Scale(CFG制强度)', minimum=1, maximum=20, value=7.5, step=0.5)
                with gr.Row(variant='compact'):
                    seed = gr.Slider(label='Seed(随机种子)', minimum=-1, maximum=2147483647, value=-1, step=1)
                    scheduler_name = gr.Dropdown(
                        value='PNDM', choices=[
                            'PNDM', 'LMS', 'Euler', 'DPM', 'DDIM', 'Heun', 'Euler-Ancestral'
                        ],
                        label='Scheduler(采样器)', allow_custom_value=False
                    )
                with gr.Row(variant='compact'):
                    a_prompt = gr.Textbox(
                        label='Added Prompt(附加提示词)', max_lines=2,
                        value='best quality, extremely detailed, supper legible text, '
                              'clear text edges, clear strokes, neat writing, no watermarks'
                    )
                with gr.Row(variant='compact'):
                    n_prompt = gr.Textbox(
                        label='Negative Prompt(负向提示词)', max_lines=2,
                        value='low-res, bad anatomy, extra digit, fewer digits, cropped, worst quality, '
                              'low quality, watermark, unreadable text, messy words, distorted text, '
                              'disorganized writing, advertising picture'
                    )

                base_model.change(
                    fn=change_settings,
                    inputs=base_model,
                    outputs=[inference_steps, cfg_scale, scheduler_name]
                )

            with gr.Row():
                with gr.Tab('Text Editing(文字编辑)', elem_id='MD-tab-t2i'):
                    with gr.Row(variant='compact'):
                        choice = gr.Slider(
                            label=f'Text Boxes(可编辑文字框)',
                            minimum=0, maximum=8, step=1, value=BBOX_INI_NUM
                        )

                    with gr.Row():
                        with gr.Column(scale=2):
                            rect_img = gr.Image(
                                value=create_canvas(), label='Rect Position',
                                elem_id='MD-bbox-rect-t2i', show_label=False, visible=True,
                                height=300
                            )
                        with gr.Column(scale=3):
                            rect_cb_list: list[Component] = []
                            rect_box_list: list[Component] = []
                            rect_font_name_list: list[Component] = []
                            rect_usr_text_list: list[Component] = []

                            with gr.Column():
                                with gr.Row(elem_id='row_show'):
                                    with gr.Column(scale=1, min_width=20):
                                        gr.Markdown('<p align="center">Font(字体)</p>', elem_id='markdown_1')
                                    with gr.Column(scale=2, min_width=20):
                                        gr.Markdown('<p align="center">Text(文字内容)</p>', elem_id='markdown_2')

                                row_layout = [gr.Row() for _ in range(BBOX_MAX_NUM)]
                                for i in range(BBOX_MAX_NUM):
                                    visible = True if i < BBOX_INI_NUM else False
                                    with row_layout[i]:
                                        fn = gr.Dropdown(
                                            choices=font_list,
                                            label='Font(字体)', value='CHN-华文行楷', visible=visible,
                                            show_label=False, scale=1, allow_custom_value=False,
                                            min_width=90, elem_id=f'font_input_{i}', container=False
                                        )
                                        ut = gr.Textbox(
                                            label='Text(文字内容)', visible=visible, scale=2,
                                            show_label=False, elem_id=f'text_input_{i}', container=False, max_lines=1
                                        )
                                    e = gr.Checkbox(label=f'{i}', value=visible, visible=False, min_width=10)

                                    x = gr.Slider(label='x', value=0.4, minimum=0.0, maximum=1.0, step=0.0001,
                                                  elem_id=f'MD-t2i-{i}-x',
                                                  visible=False)
                                    y = gr.Slider(label='y', value=0.4, minimum=0.0, maximum=1.0, step=0.0001,
                                                  elem_id=f'MD-t2i-{i}-y',
                                                  visible=False)
                                    w = gr.Slider(label='w', value=0.2, minimum=0.0, maximum=1.0, step=0.0001,
                                                  elem_id=f'MD-t2i-{i}-w',
                                                  visible=False)
                                    h = gr.Slider(label='h', value=0.2, minimum=0.0, maximum=1.0, step=0.0001,
                                                  elem_id=f'MD-t2i-{i}-h',
                                                  visible=False)
                                    x.change(fn=None, inputs=x, outputs=x, _js=f'v => onBoxChange({i}, "x", v)',
                                             show_progress=False, queue=False)
                                    y.change(fn=None, inputs=y, outputs=y, _js=f'v => onBoxChange({i}, "y", v)',
                                             show_progress=False, queue=False)
                                    w.change(fn=None, inputs=w, outputs=w, _js=f'v => onBoxChange({i}, "w", v)',
                                             show_progress=False, queue=False)
                                    h.change(fn=None, inputs=h, outputs=h, _js=f'v => onBoxChange({i}, "h", v)',
                                             show_progress=False, queue=False)
                                    e.change(fn=None, inputs=e, outputs=e, _js=f'e => onBoxEnableClick({i}, e)',
                                             queue=False)

                                    rect_cb_list.extend([e])
                                    rect_box_list.extend([x, y, w, h])
                                    rect_font_name_list.extend([fn])
                                    rect_usr_text_list.extend([ut])

                            choice.change(
                                fn=update_box_num,
                                inputs=[choice],
                                outputs=[
                                    *rect_cb_list, *rect_font_name_list, *rect_usr_text_list, *rect_box_list
                                ]
                            )
                    with gr.Row():
                        gr.Markdown('')
                        run_edit = gr.Button(value='Run(运行)', elem_classes='run', elem_id='run_edit')
                        gr.Markdown('')
                    with gr.Row():
                        with gr.Accordion(label='Examples(示例)', open=True):
                            img_container = gr.Image(visible=False, label='Text Layout(文字布局)')
                            example_id = gr.Textbox(value=-1, visible=False, label='ID(编号)')
                            gen_examples = gr.Examples(
                                [
                                    [1, 'templates/1.png', 'landscape, Chinese style, ink peaks, poster', model_list[0], 1648703813, 3, 1],
                                    [2, 'templates/2.png', 'a clock and medicine bottle has texts and "time"', model_list[0], 1654615998, 2, 1],
                                    [3, 'templates/3.png', '漂亮的风景照,很多山峰,清澈的湖水', model_list[3], 2078698098, 3, 1],
                                    [4, 'templates/4.png', 'a vodka, on the bar, dim background', model_list[2], 443791646, 3, 1],
                                    [5, 'templates/5.png', '画有玫瑰的卡片,明亮的背景', model_list[4], 516210890, 2, 1],
                                    [6, 'templates/6.png', 'posters on the table, with pens, clear background, starry sky, moon', model_list[1], 228167646, 4, 1],
                                    [7, 'templates/7.png', 'snowy landscape, domed cabin, winter scene, cozy atmosphere, soft lighting', model_list[5], 695897181, 3, 1],
                                    [8, 'templates/8.png', '一张关于健康教育的卡片,上面有一些文字,有一些食物图标,背景里有一些水果喝饮料的图标,且背景是模糊的', model_list[1], 936188591, 6, 1],
                                ],
                                [example_id, img_container, usr_prompt, base_model, seed, choice, num_samples],
                                examples_per_page=5,
                                label=''
                            )

                        example_id.change(
                            fn=load_box_list,
                            inputs=[example_id, choice],
                            outputs=[
                                *rect_cb_list, *rect_font_name_list, *rect_usr_text_list, *rect_box_list, example_id
                            ]
                        )

                    rect_img.clear(re_edit, None, [*rect_box_list, rect_img, image_width, image_height])
                    image_width.release(resize_w, [image_width, rect_img], rect_img)
                    image_height.release(resize_h, [image_height, rect_img], rect_img)
                    
        with gr.Column(scale=2):
            with gr.Row():
                result_gallery = gr.Gallery(
                    label='Result(结果)', show_label=True, preview=True, columns=8,
                    allow_preview=True, elem_id='gallery'
                )
            with gr.Row():
                with gr.Tab("Introduction"):
                    gr.Markdown('<span style="color:#3B5998;font-size:20px">What we can do</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">Generating images with accurately represented text in multi-language.</span>')
                    gr.Markdown('<span style="color:#3B5998;font-size:20px">How to use</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">Enter a description of the image you want to generate in the "Prompt" text box.</span>')
                    gr.Markdown('<span style="color:#3B5998;font-size:18px">Text Editing</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">You can drag the "Text Boxes" slider to set the number of text to be laid out, '
                        'and set the corresponding font and text content respectively, Note that there must be no overlap between the text boxes, '
                        'or the model will not generate an image.</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">Finally, click the Run button to generate a picture!</span>')
                with gr.Tab("说明"):
                    gr.Markdown('<span style="color:#3B5998;font-size:20px">我们能做什么</span>')
                    gr.Markdown('<span style="color:black;font-size:15px">在多种语言上生成具有准确文本的图像</span>')
                    gr.Markdown('<span style="color:#3B5998;font-size:20px">如何使用</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">在“提示词”文本框中输入你想要生成的图片所对应的文字描述。</span>')
                    gr.Markdown('<span style="color:#3B5998;font-size:18px">文本编辑</span>')
                    gr.Markdown(
                        '<span style="color:black;font-size:15px">你可以拖动“可编辑文字框”滑块来设置需要布局的文字数量,并分别设置对应的字体和文字内容;'
                        '请注意,文本框之间不能有重叠,否则模型将不会生成图片。</span>')
                    gr.Markdown('<span style="color:black;font-size:15px">最后点击运行按钮,即可生成图片!</span>')
            with gr.Row():
                result_info = gr.Markdown('debug', visible=False)

    args = [
        num_samples, a_prompt, n_prompt,
        conditioning_scale, cfg_scale, inference_steps, seed, usr_prompt, 
        rect_img, base_model, scheduler_name, gr.State(BBOX_MAX_NUM),
        *(rect_cb_list + rect_box_list + rect_font_name_list + rect_usr_text_list)
    ]
    run_edit.click(
        fn=process,
        inputs=args,
        outputs=[result_gallery, result_info]
    )


if __name__ == "__main__":
    block.launch(
        server_name='0.0.0.0',
        share=True,
    )