ssboost commited on
Commit
4641ccb
ยท
verified ยท
1 Parent(s): f89dffd

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +168 -379
app.py CHANGED
@@ -10,9 +10,8 @@ import numpy as np
10
  from io import BytesIO
11
  from datetime import datetime, timedelta
12
  import random
13
- import requests
14
- import base64
15
  from dotenv import load_dotenv
 
16
 
17
  load_dotenv()
18
 
@@ -20,316 +19,177 @@ load_dotenv()
20
  logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
21
  logger = logging.getLogger(__name__)
22
 
23
- # ------------------- API ์—”๋“œํฌ์ธํŠธ ์„ค์ • -------------------
24
- def get_api_endpoint():
25
- """ํ™˜๊ฒฝ๋ณ€์ˆ˜์—์„œ API ์—”๋“œํฌ์ธํŠธ๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ํ•จ์ˆ˜"""
26
- endpoint = os.getenv('API_ENDPOINT')
27
-
28
- # ํ™˜๊ฒฝ๋ณ€์ˆ˜๊ฐ€ ์—†์œผ๋ฉด None ๋ฐ˜ํ™˜
29
- if not endpoint:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
30
  return None
31
-
32
- # ํ—ˆ๊น…ํŽ˜์ด์Šค ์ŠคํŽ˜์ด์Šค ํ˜•์‹ ์ฒ˜๋ฆฌ
33
- if "/" in endpoint and not endpoint.startswith("http"):
34
- # "username/spacename" ํ˜•์‹์„ ์ „์ฒด URL๋กœ ๋ณ€ํ™˜
35
- endpoint = f"https://{endpoint.replace('/', '-')}.hf.space"
36
- elif not endpoint.startswith("http"):
37
- # ๋‹จ์ˆœ ๋„๋ฉ”์ธ์ธ ๊ฒฝ์šฐ https ์ถ”๊ฐ€
38
- endpoint = f"https://{endpoint}"
39
-
40
- return endpoint
41
 
42
- def encode_image_to_base64(image):
43
- """PIL ์ด๋ฏธ์ง€๋ฅผ base64๋กœ ์ธ์ฝ”๋”ฉ"""
44
  if image is None:
45
  return None
46
 
47
- buffered = BytesIO()
48
- image.save(buffered, format="PNG")
49
- img_str = base64.b64encode(buffered.getvalue()).decode()
50
- return img_str
51
-
52
- def decode_base64_to_image(base64_str):
53
- """base64 ๋ฌธ์ž์—ด์„ PIL ์ด๋ฏธ์ง€๋กœ ๋””์ฝ”๋”ฉ"""
54
- if not base64_str:
55
- return None
56
-
57
- image_data = base64.b64decode(base64_str)
58
- image = Image.open(BytesIO(image_data))
59
- return image
60
-
61
- def call_api_endpoint(endpoint_url, data):
62
- """API ์—”๋“œํฌ์ธํŠธ ํ˜ธ์ถœ ํ•จ์ˆ˜"""
63
  try:
64
- response = requests.post(endpoint_url, json=data, timeout=300)
65
- response.raise_for_status()
66
- return response.json()
67
- except requests.exceptions.RequestException as e:
68
- logger.error(f"API ํ˜ธ์ถœ ์ค‘ ์˜ค๋ฅ˜ ๋ฐœ์ƒ: {str(e)}")
69
- return {"error": f"API ํ˜ธ์ถœ ์‹คํŒจ: {str(e)}"}
70
-
71
- # ========== ์ด๋ฏธ์ง€ ์ƒ์„ฑ๊ธฐ ๊ด€๋ จ ํ•จ์ˆ˜ ==========
72
- def get_api_endpoint():
73
- """ํ™˜๊ฒฝ๋ณ€์ˆ˜์—์„œ API ์—”๋“œํฌ์ธํŠธ๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ํ•จ์ˆ˜"""
74
- endpoint = os.getenv('API_ENDPOINT')
75
-
76
- # ํ™˜๊ฒฝ๋ณ€์ˆ˜๊ฐ€ ์—†์œผ๋ฉด ๊ธฐ๋ณธ๊ฐ’ ์‚ฌ์šฉ (ํ…Œ์ŠคํŠธ์šฉ)
77
- if not endpoint:
78
- endpoint = "https://happydoggg-03hd74jd.hf.space"
79
- logger.info("ํ™˜๊ฒฝ๋ณ€์ˆ˜๊ฐ€ ์„ค์ •๋˜์ง€ ์•Š์•„ ๊ธฐ๋ณธ ์—”๋“œํฌ์ธํŠธ๋ฅผ ์‚ฌ์šฉํ•ฉ๋‹ˆ๋‹ค.")
80
-
81
- # ํ—ˆ๊น…ํŽ˜์ด์Šค ์ŠคํŽ˜์ด์Šค ํ˜•์‹ ์ฒ˜๋ฆฌ
82
- if "/" in endpoint and not endpoint.startswith("http"):
83
- # "username/spacename" ํ˜•์‹์„ ์ „์ฒด URL๋กœ ๋ณ€ํ™˜
84
- endpoint = f"https://{endpoint.replace('/', '-')}.hf.space"
85
- elif not endpoint.startswith("http"):
86
- # ๋‹จ์ˆœ ๋„๋ฉ”์ธ์ธ ๊ฒฝ์šฐ https ์ถ”๊ฐ€
87
- endpoint = f"https://{endpoint}"
88
-
89
- return endpoint
90
 
91
- def call_api_endpoint(endpoint_url, data):
92
- """API ์—”๋“œํฌ์ธํŠธ ํ˜ธ์ถœ ํ•จ์ˆ˜"""
93
- try:
94
- response = requests.post(endpoint_url, json=data, timeout=300)
95
- response.raise_for_status()
96
- return response.json()
97
- except requests.exceptions.RequestException as e:
98
- # ์—”๋“œํฌ์ธํŠธ ์ •๋ณด๋ฅผ ์ˆจ๊ธฐ๊ณ  ์ผ๋ฐ˜์ ์ธ ์˜ค๋ฅ˜ ๋ฉ”์‹œ์ง€๋งŒ ํ‘œ์‹œ
99
- logger.error("API ํ˜ธ์ถœ ์ค‘ ์˜ค๋ฅ˜ ๋ฐœ์ƒ")
100
- return {"error": "API ํ˜ธ์ถœ ์‹คํŒจ"}
101
-
102
- def translate_prompt_to_english(prompt):
103
- """ํ”„๋กฌํ”„ํŠธ ๋ฒˆ์—ญ - API ์—”๋“œํฌ์ธํŠธ๋กœ ์ „๋‹ฌ"""
104
- endpoint_url = get_api_endpoint()
105
- if not endpoint_url:
106
- return prompt
107
-
108
- data = {
109
- "function": "translate_prompt",
110
- "prompt": prompt
111
- }
112
-
113
  try:
114
- result = call_api_endpoint(f"{endpoint_url}/translate", data)
115
- if "error" in result:
116
- logger.warning("๋ฒˆ์—ญ API ์˜ค๋ฅ˜ ๋ฐœ์ƒ")
117
- return prompt
118
- return result.get("translated_prompt", prompt)
119
- except Exception as e:
120
- logger.warning("๋ฒˆ์—ญ ์ค‘ ์˜ค๋ฅ˜ ๋ฐœ์ƒ")
121
- return prompt
122
-
123
- def generate_with_images(prompt, images, variation_index=0):
124
- """API ์—”๋“œํฌ์ธํŠธ๋กœ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์š”์ฒญ"""
125
- endpoint_url = get_api_endpoint()
126
- if not endpoint_url:
127
- return None, "API ์—”๋“œํฌ์ธํŠธ๊ฐ€ ์„ค์ •๋˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค."
128
-
129
- # ์ด๋ฏธ์ง€๋“ค์„ base64๋กœ ์ธ์ฝ”๋”ฉ
130
- encoded_images = []
131
- for img in images:
132
- if img is not None:
133
- encoded_img = encode_image_to_base64(img)
134
- encoded_images.append(encoded_img)
135
  else:
136
- encoded_images.append(None)
137
-
138
- data = {
139
- "function": "generate_with_images",
140
- "prompt": prompt,
141
- "images": encoded_images,
142
- "variation_index": variation_index
143
- }
144
-
145
  try:
146
- result = call_api_endpoint(f"{endpoint_url}/generate", data)
147
- if "error" in result:
148
- return None, "์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค‘ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค."
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
149
 
150
- # base64 ์ด๋ฏธ์ง€๋ฅผ PIL ์ด๋ฏธ์ง€๋กœ ๋ณ€ํ™˜
151
- if "image" in result:
152
- generated_image = decode_base64_to_image(result["image"])
153
- return generated_image, result.get("status", "์ด๋ฏธ์ง€๊ฐ€ ์„ฑ๊ณต์ ์œผ๋กœ ์ƒ์„ฑ๋˜์—ˆ์Šต๋‹ˆ๋‹ค.")
154
  else:
155
- return None, "API์—์„œ ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค."
 
156
  except Exception as e:
157
- logger.error("์ด๋ฏธ์ง€ ์ƒ์„ฑ API ํ˜ธ์ถœ ์ค‘ ์˜ค๋ฅ˜")
158
- return None, "์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค‘ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค."
159
- """ํ”„๋กฌํ”„ํŠธ ์ „์ฒ˜๋ฆฌ - ๊ธฐ์กด ๋กœ์ง ์œ ์ง€"""
160
- has_img1 = image1 is not None
161
- has_img2 = image2 is not None
162
- has_img3 = image3 is not None
163
-
164
- if "#1" in prompt and not has_img1:
165
- prompt = prompt.replace("#1", "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€(์—†์Œ)")
166
- else:
167
- prompt = prompt.replace("#1", "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€")
168
-
169
- if "#2" in prompt and not has_img2:
170
- prompt = prompt.replace("#2", "๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€(์—†์Œ)")
171
- else:
172
- prompt = prompt.replace("#2", "๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€")
173
-
174
- if "#3" in prompt and not has_img3:
175
- prompt = prompt.replace("#3", "์„ธ ๋ฒˆ์งธ ์ด๋ฏธ์ง€(์—†์Œ)")
176
- else:
177
- prompt = prompt.replace("#3", "์„ธ ๋ฒˆ์งธ ์ด๋ฏธ์ง€")
178
-
179
- if "1. ์ด๋ฏธ์ง€ ๋ณ€๊ฒฝ" in prompt:
180
- desc_match = re.search(r'#1์„ "(.*?)"์œผ๋กœ ๋ฐ”๊ฟ”๋ผ', prompt)
181
- if desc_match:
182
- description = desc_match.group(1)
183
- prompt = f"์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋ฅผ {description}์œผ๋กœ ๋ณ€๊ฒฝํ•ด์ฃผ์„ธ์š”. ์›๋ณธ ์ด๋ฏธ์ง€์˜ ์ฃผ์š” ๋‚ด์šฉ์€ ์œ ์ง€ํ•˜๋˜ ์ƒˆ๋กœ์šด ์Šคํƒ€์ผ๊ณผ ๋ถ„์œ„๊ธฐ๋กœ ์žฌํ•ด์„ํ•ด์ฃผ์„ธ์š”."
184
- else:
185
- prompt = "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋ฅผ ์ฐฝ์˜์ ์œผ๋กœ ๋ณ€ํ˜•ํ•ด์ฃผ์„ธ์š”. ๋” ์ƒ์ƒํ•˜๊ณ  ์˜ˆ์ˆ ์ ์ธ ๋ฒ„์ „์œผ๋กœ ๋งŒ๋“ค์–ด์ฃผ์„ธ์š”."
186
 
187
- elif "2. ๊ธ€์ž์ง€์šฐ๊ธฐ" in prompt:
188
- text_match = re.search(r'#1์—์„œ "(.*?)"๋ฅผ ์ง€์›Œ๋ผ', prompt)
189
- if text_match:
190
- text_to_remove = text_match.group(1)
191
- prompt = f"์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์—์„œ '{text_to_remove}' ํ…์ŠคํŠธ๋ฅผ ์ฐพ์•„ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์ œ๊ฑฐํ•ด์ฃผ์„ธ์š”. ํ…์ŠคํŠธ๊ฐ€ ์žˆ๋˜ ๋ถ€๋ถ„์„ ๋ฐฐ๊ฒฝ๊ณผ ์กฐํ™”๋กญ๊ฒŒ ์ฑ„์›Œ์ฃผ์„ธ์š”."
192
- else:
193
- prompt = "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์—์„œ ๋ชจ๋“  ํ…์ŠคํŠธ๋ฅผ ์ฐพ์•„ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์ œ๊ฑฐํ•ด์ฃผ์„ธ์š”. ๊น”๋”ํ•œ ์ด๋ฏธ์ง€๋กœ ๋งŒ๋“ค์–ด์ฃผ์„ธ์š”."
194
 
195
- elif "4. ์˜ท๋ฐ”๊พธ๊ธฐ" in prompt:
196
- prompt = "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ์ธ๋ฌผ ์˜์ƒ์„ ๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ์˜์ƒ์œผ๋กœ ๋ณ€๊ฒฝํ•ด์ฃผ์„ธ์š”. ์˜์ƒ์˜ ์Šคํƒ€์ผ๊ณผ ์ƒ‰์ƒ์€ ๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋ฅผ ๋”ฐ๋ฅด๋˜, ์‹ ์ฒด ๋น„์œจ๊ณผ ํฌ์ฆˆ๋Š” ์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€๋ฅผ ์œ ์ง€ํ•ด์ฃผ์„ธ์š”."
 
197
 
198
- elif "5. ๋ฐฐ๊ฒฝ๋ฐ”๊พธ๊ธฐ" in prompt:
199
- prompt = "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ๋ฐฐ๊ฒฝ์„ ๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ๋ฐฐ๊ฒฝ์œผ๋กœ ๋ณ€๊ฒฝํ•ด์ฃผ์„ธ์š”. ์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ์ฃผ์š” ํ”ผ์‚ฌ์ฒด๋Š” ์œ ์ง€ํ•˜๊ณ , ๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์˜ ๋ฐฐ๊ฒฝ๊ณผ ์กฐํ™”๋กญ๊ฒŒ ํ•ฉ์„ฑํ•ด์ฃผ์„ธ์š”."
 
200
 
201
- elif "6. ์ด๋ฏธ์ง€ ํ•ฉ์„ฑ(์ƒํ’ˆํฌํ•จ)" in prompt:
202
- prompt = "์ฒซ ๋ฒˆ์งธ ์ด๋ฏธ์ง€์™€ ๋‘ ๋ฒˆ์งธ ์ด๋ฏธ์ง€(๋˜๋Š” ์„ธ ๋ฒˆ์งธ ์ด๋ฏธ์ง€)๋ฅผ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ํ•ฉ์„ฑํ•ด์ฃผ์„ธ์š”. ๋ชจ๋“  ์ด๋ฏธ์ง€์˜ ์ฃผ์š” ์š”์†Œ๋ฅผ ํฌํ•จํ•˜๊ณ , ํŠนํžˆ ์ƒํ’ˆ์ด ๋‹๋ณด์ด๋„๋ก ์กฐํ™”๋กญ๊ฒŒ ํ†ตํ•ฉํ•ด์ฃผ์„ธ์š”."
 
203
 
204
- prompt += " ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•ด์ฃผ์„ธ์š”. ์ด๋ฏธ์ง€์— ํ…์ŠคํŠธ๋‚˜ ๊ธ€์ž๋ฅผ ํฌํ•จํ•˜์ง€ ๋งˆ์„ธ์š”."
205
- return prompt
 
206
 
207
- def generate_with_images(prompt, images, variation_index=0):
208
- """API ์—”๋“œํฌ์ธํŠธ๋กœ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์š”์ฒญ"""
209
- endpoint_url = get_api_endpoint()
210
- if not endpoint_url:
211
- return None, "API ์—”๋“œํฌ์ธํŠธ๊ฐ€ ์„ค์ •๋˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค."
212
-
213
- # ์ด๋ฏธ์ง€๋“ค์„ base64๋กœ ์ธ์ฝ”๋”ฉ
214
- encoded_images = []
215
- for img in images:
216
- if img is not None:
217
- encoded_img = encode_image_to_base64(img)
218
- encoded_images.append(encoded_img)
219
- else:
220
- encoded_images.append(None)
221
-
222
- data = {
223
- "function": "generate_with_images",
224
- "prompt": prompt,
225
- "images": encoded_images,
226
- "variation_index": variation_index
227
- }
228
-
229
- try:
230
- result = call_api_endpoint(f"{endpoint_url}/generate", data)
231
- if "error" in result:
232
- return None, result["error"]
233
-
234
- # base64 ์ด๋ฏธ์ง€๋ฅผ PIL ์ด๋ฏธ์ง€๋กœ ๋ณ€ํ™˜
235
- if "image" in result:
236
- generated_image = decode_base64_to_image(result["image"])
237
- return generated_image, result.get("status", "์ด๋ฏธ์ง€๊ฐ€ ์„ฑ๊ณต์ ์œผ๋กœ ์ƒ์„ฑ๋˜์—ˆ์Šต๋‹ˆ๋‹ค.")
238
- else:
239
- return None, "API์—์„œ ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค."
240
- except Exception as e:
241
- logger.error(f"์ด๋ฏธ์ง€ ์ƒ์„ฑ API ํ˜ธ์ถœ ์ค‘ ์˜ค๋ฅ˜: {str(e)}")
242
- return None, f"์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค‘ ์˜ค๋ฅ˜ ๋ฐœ์ƒ: {str(e)}"
243
 
244
- def process_images_with_prompt(image1, image2, image3, prompt, variation_index=0, max_retries=3):
245
- """์ด๋ฏธ์ง€ ์ฒ˜๋ฆฌ ๋ฉ”์ธ ํ•จ์ˆ˜"""
246
- retry_count = 0
247
- last_error = None
248
-
249
- while retry_count < max_retries:
250
- try:
251
- images = [image1, image2, image3]
252
- valid_images = [img for img in images if img is not None]
253
-
254
- if not valid_images:
255
- if prompt and prompt.strip():
256
- logger.info("ํ…์ŠคํŠธ ํ”„๋กฌํ”„ํŠธ๋งŒ์œผ๋กœ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์‹œ๋„")
257
- try:
258
- result_img, status = generate_with_images(prompt, [], variation_index)
259
- if result_img is not None:
260
- return result_img, status, prompt
261
- except:
262
- pass
263
- return None, "์ด๋ฏธ์ง€๋ฅผ ์—…๋กœ๋“œํ•˜๊ฑฐ๋‚˜ ํ…์ŠคํŠธ ํ”„๋กฌํ”„ํŠธ๋ฅผ ์ž…๋ ฅํ•ด์ฃผ์„ธ์š”.", ""
264
-
265
- if prompt and prompt.strip():
266
- processed_prompt = preprocess_prompt(prompt, image1, image2, image3)
267
- if re.search("[๊ฐ€-ํžฃ]", processed_prompt):
268
- final_prompt = translate_prompt_to_english(processed_prompt)
269
- else:
270
- final_prompt = processed_prompt
271
- else:
272
- if len(valid_images) == 1:
273
- final_prompt = "Please creatively transform this image into a more vivid and artistic version. Do not include any text or watermarks in the generated image."
274
- logger.info("Default prompt generated for single image")
275
- elif len(valid_images) == 2:
276
- final_prompt = "Please seamlessly composite these two images, integrating their key elements harmoniously into a single image. Do not include any text or watermarks in the generated image."
277
- logger.info("Default prompt generated for two images")
278
- else:
279
- final_prompt = "Please creatively composite these three images, combining their main elements into a cohesive and natural scene. Do not include any text or watermarks in the generated image."
280
- logger.info("Default prompt generated for three images")
281
-
282
- result_img, status = generate_with_images(final_prompt, valid_images, variation_index)
283
- if result_img is not None:
284
- return result_img, status, final_prompt
285
- else:
286
- last_error = status
287
- retry_count += 1
288
- logger.warning(f"์ด๋ฏธ์ง€ ์ƒ์„ฑ ์‹คํŒจ, ์žฌ์‹œ๋„ {retry_count}/{max_retries}")
289
- time.sleep(1)
290
- except Exception as e:
291
- last_error = "์ฒ˜๋ฆฌ ์ค‘ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค."
292
- retry_count += 1
293
- logger.exception(f"์ด๋ฏธ์ง€ ์ฒ˜๋ฆฌ ์ค‘ ์˜ค๋ฅ˜ ๋ฐœ์ƒ, ์žฌ์‹œ๋„ {retry_count}/{max_retries}")
294
- time.sleep(1)
295
-
296
- return None, f"์ตœ๋Œ€ ์žฌ์‹œ๋„ ํšŸ์ˆ˜({max_retries}ํšŒ) ์ดˆ๊ณผ ํ›„ ์‹คํŒจ: {last_error}", prompt
297
 
298
- def generate_multiple_images(image1, image2, image3, prompt, progress=gr.Progress()):
299
- """๋‹ค์ค‘ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ํ•จ์ˆ˜"""
300
- results = []
301
- statuses = []
302
- prompts = []
303
-
304
- num_images = 2
305
- max_retries = 3
306
-
307
- progress(0, desc="์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค€๋น„ ์ค‘...")
308
-
309
- for i in range(num_images):
310
- progress((i / num_images), desc=f"{i+1}/{num_images} ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค‘...")
311
- result_img, status, final_prompt = process_images_with_prompt(image1, image2, image3, prompt, i, max_retries)
312
-
313
- if result_img is not None:
314
- results.append(result_img)
315
- statuses.append(f"์ด๋ฏธ์ง€ #{i+1}: {status}")
316
- prompts.append(f"์ด๋ฏธ์ง€ #{i+1}: {final_prompt}")
317
- else:
318
- results.append(None)
319
- statuses.append(f"์ด๋ฏธ์ง€ #{i+1} ์ƒ์„ฑ ์‹คํŒจ: {status}")
320
- prompts.append(f"์ด๋ฏธ์ง€ #{i+1}: {final_prompt}")
321
-
322
- time.sleep(1)
323
-
324
- progress(1.0, desc="์ด๋ฏธ์ง€ ์ƒ์„ฑ ์™„๋ฃŒ!")
325
-
326
- while len(results) < 2:
327
- results.append(None)
328
-
329
- combined_status = "\n".join(statuses)
330
- combined_prompts = "\n".join(prompts)
331
-
332
- return results[0], results[1], combined_status, combined_prompts
333
 
334
  # ๋‹คํฌ๋ชจ๋“œ ์ž๋™ ์ ์šฉ ์ปค์Šคํ…€ CSS ์Šคํƒ€์ผ
335
  custom_css = """
@@ -765,7 +625,6 @@ with gr.Blocks(css=custom_css, theme=gr.themes.Default(
765
  )) as demo:
766
  gr.HTML(fontawesome_link)
767
 
768
- # ํƒญ ์ œ๊ฑฐํ•˜๊ณ  ์ด๋ฏธ์ง€ ์ƒ์„ฑ๊ธฐ ๋‚ด์šฉ์„ ์ง์ ‘ ๋ฐฐ์น˜
769
  with gr.Row(equal_height=True):
770
  with gr.Column(scale=1):
771
  # ======== ์ด๋ฏธ์ง€ ์—…๋กœ๋“œ ๋ฐ ์„ค์ • ์„น์…˜ ========
@@ -854,85 +713,23 @@ with gr.Blocks(css=custom_css, theme=gr.themes.Default(
854
  )
855
 
856
  # ========== ์ด๋ฏธ์ง€ ์ƒ์„ฑ๊ธฐ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ ==========
857
- # ๋ฒ„ํŠผ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ
858
- image_change_btn1.click(
859
- fn=lambda: "(#1์˜ ์—ฌ์„ฑ)์ด ์‚ด์ง ๋’ค๋กœ ๋Œ์•„๋ณด๋Š” ๋ชจ์Šต์œผ๋กœ ์ตœ๋Œ€ํ•œ ์ด์ „ seed๋ฅผ ์œ ์ง€ํ•œํ…Œ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๋ณ€๊ฒฝํ•˜๋ผ.",
860
- inputs=[],
861
- outputs=prompt_input
862
- )
863
- image_change_btn2.click(
864
- fn=lambda: "(#1 ๋ ˆ๋ชจ๋ชจํ˜•)์—์„œ ์ฒญ์ƒ‰์ƒ์–ด๋ ˆ๊ณ ๋งŒ ๊ฒ€์€์ƒ‰ ๊ณ ๋ž˜๋ ˆ๊ณ ๋กœ ๋ณ€๊ฒฝํ•˜๊ณ  ๋‚˜๋จธ์ง€ ๋ถ€๋ถ„์€ seed๋ฅผ ๋ณ€๊ฒฝ์„ ํ•˜์ง€๋งˆ๋ผ.",
865
- inputs=[],
866
- outputs=prompt_input
867
- )
868
- image_change_btn3.click(
869
- fn=lambda: "(#1 ์—ฌํ–‰์šฉ ์–ผ์Œ๋ฐ•์Šค)์•ž์— ์–ผ์Œ์ด ๋‹ด๊ธด 3์ž”์˜ ์ฝœ๋ผ๊ฐ€ ๋†“์—ฌ์žˆ๋Š” ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ.",
870
- inputs=[],
871
- outputs=prompt_input
872
- )
873
-
874
- text_remove_btn.click(
875
- fn=lambda: "(#1 ์ด๋ฏธ์ง€)์— ์žˆ๋Š” ์ค‘๊ตญ์–ด๋ฅผ ๋ชจ๋‘ ์ œ๊ฑฐํ•˜๋ผ.",
876
- inputs=[],
877
- outputs=prompt_input
878
- )
879
- text_change_btn.click(
880
- fn=lambda: '(#1์˜ ํ…์ŠคํŠธ)๋ฅผ ์Šคํƒ€์ผ์„ ์œ ์ง€ํ•œ์ฒด ํ…์ŠคํŠธ๋งŒ "Hello"๋กœ ๋ฐ”๊ฟ”๋ผ',
881
- inputs=[],
882
- outputs=prompt_input
883
- )
884
- clothes_change_btn1.click(
885
- fn=lambda: "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด ์‹ ์ฒด ๋น„์œจ๊ณผ ํฌ์ฆˆ๋Š” ์œ ์ง€ํ•œ ์ฒด (#2์˜ ์„ ๊ธ€๋ผ์Šค)์™€ (#3์˜ ์ฒญ๋ฐ”์ง€)๋ฅผ ์ง์ ‘ ๋ชจ๋ธ์ด ์ฐฉ์šฉํ•œ๊ฒƒ ์ฒ˜๋Ÿผ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ.",
886
- inputs=[],
887
- outputs=prompt_input
888
- )
889
- clothes_change_btn2.click(
890
- fn=lambda: "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด (#2์˜ ์„ ๊ธ€๋ผ์Šค)์„ ์ฐฉ์šฉํ•˜๊ณ  (#3์˜ ๋’ท๋ฐฐ๊ฒฝ์˜ ์นดํŽ˜์ „์ฒด๊ฐ€ ๋ณด์ด๋ฉฐ) ์˜์ž์— ์•‰์•„ ์žˆ๋Š” ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ.",
891
- inputs=[],
892
- outputs=prompt_input
893
- )
894
- holding_product_btn.click(
895
- fn=lambda: "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด(#2์˜ ์™€์ธ์ž”)์„ ๋“ค๊ณ  ์žˆ๋Š” ์ž์—ฐ์Šค๋Ÿฌ์šด ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ.",
896
- inputs=[],
897
- outputs=prompt_input
898
- )
899
- background_change_btn.click(
900
- fn=lambda: "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด (#2 ์นดํŽ˜)์—์„œ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์žˆ๋Š” ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ.",
901
- inputs=[],
902
- outputs=prompt_input
903
- )
904
- composite_product_btn.click(
905
- fn=lambda: "(#1์˜ ๋ ˆ๊ณ ๋ชจํ˜•)์—์„œ ์ฒญ์ƒ‰์ƒ์–ด๋ ˆ๊ณ ๋ฅผ ์ œ๊ฑฐํ•œ ํ›„, ๊ทธ ์ž๋ฆฌ๋ฅผ ์ฃผ๋ณ€ ๋ฐฐ๊ฒฝ๊ณผ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์–ด์šฐ๋Ÿฌ์ง€๋„๋ก ์ฑ„์›Œ์ฃผ์„ธ์š”. ๋‹จ, ์ด๋ฏธ์ง€์˜ ๋‹ค๋ฅธ ๋ถ€๋ถ„์˜ ์ฃผ์š” ์š”์†Œ๋Š” ๋™์ผํ•˜๊ฒŒ ์œ ์ง€ ํ•ด์•ผํ•œ๋‹ค.",
906
- inputs=[],
907
- outputs=prompt_input
908
- )
909
- outpainting_btn.click(
910
- fn=lambda: "(#1 ์ด๋ฏธ์ง€)๋ฅผ ์›๋ณธ๊ทธ๋Œ€๋กœ ์ค‘์•™์— ๋‘๊ณ  ๋น„์œจ๋กœ ์œ ์ง€ํ•œ ์ฒด ์œ„์•„๋ž˜ ๋ฐ ์ขŒ์šฐ๋กœ ํฌ๊ฒŒ ํ™•์žฅํ•˜๋ผ.",
911
- inputs=[],
912
- outputs=prompt_input
913
-
914
- )
915
- food_btn_1.click(
916
- fn=lambda: "(#1์…€๋Ÿฌ๋“œ)์— ๋‹ด์€ ์šฉ๊ธฐ๋Š” ๋ฒ„๋ฆฌ๊ณ  ๋„“๊ณ  ํฐ ์˜ˆ์œ ์ ‘์‹œ์— (#1์…€๋Ÿฌ๋“œ)์Œ์‹๋งŒ ๊ฐ€๋“ ์ฑ„์›Œ์„œ ์ƒ์—…์ ์ธ ๊ฐ๋„๋กœ ์–ด์šธ๋ฆฌ๋Š” ์†Œํ’ˆ๊ณผ ํ•จ๊ป˜ ํ”Œ๋ ˆ์ดํŒ… ํ•œ ๋ชจ์Šต์„ ์ด๋ฏธ์ง€๋กœ ์ƒ์„ฑํ•˜๋ผ. ",
917
- inputs=[],
918
- outputs=prompt_input
919
- )
920
- food_btn_2.click(
921
- fn=lambda: "(#2 ํ”Œ๋ ˆ์ดํŒ…ํ•œ ์ด๋ฏธ์ง€)์— ๋‹ด๊ธด ์Œ์‹์„ (#1 ์ƒ๋Ÿฌ๋“œ)๋กœ ๋ฐ”๊พธ๊ณ  ๋‚˜๋จธ์ง€๋Š” ์‹œ๋“œ๋ฅผ ์œ ์ง€ํ•œ ์ฒด ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ.",
922
- inputs=[],
923
- outputs=prompt_input
924
- )
925
-
926
- food_btn_3.click(
927
- fn=lambda: "(#1์ปต)์— ๋”ธ๊ธฐ, ๋ฐ”๋‹๋ผ, ์ดˆ์ฝ” ์•„์ด์Šคํฌ๋ฆผ์„ ๋‹ด๊ณ  ๊ทธ ์œ„์— ์ดˆ์ฝ” ์‹œ๋Ÿฝ์ด ํ๋ฅด๊ฒŒ ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ.",
928
- inputs=[],
929
- outputs=prompt_input
930
- )
931
 
932
  # ๋‹จ์ผ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ๋ฒ„ํŠผ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ
933
- def generate_single_image(image1, image2, image3, prompt):
934
- return process_images_with_prompt(image1, image2, image3, prompt, 0, 3)
935
-
936
  submit_single_btn.click(
937
  fn=generate_single_image,
938
  inputs=[image1_input, image2_input, image3_input, prompt_input],
@@ -947,13 +744,5 @@ with gr.Blocks(css=custom_css, theme=gr.themes.Default(
947
  )
948
 
949
  # ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ์‹คํ–‰
950
- if __name__ == "__main__":
951
- # API ์—”๋“œํฌ์ธํŠธ ํ™•์ธ (๋กœ๊ทธ์—๋Š” ๋ฏผ๊ฐ์ •๋ณด ์ถœ๋ ฅํ•˜์ง€ ์•Š์Œ)
952
- endpoint = get_api_endpoint()
953
- if endpoint:
954
- logger.info("์ปจํŠธ๋กค ํƒ€์›Œ๊ฐ€ ์‹œ์ž‘๋˜์—ˆ์Šต๋‹ˆ๋‹ค.")
955
- else:
956
- logger.warning("API ์„ค์ •์„ ํ™•์ธํ•ด์ฃผ์„ธ์š”.")
957
-
958
- demo.queue()
959
- demo.launch(share=False, inbrowser=True, width="100%")
 
10
  from io import BytesIO
11
  from datetime import datetime, timedelta
12
  import random
 
 
13
  from dotenv import load_dotenv
14
+ from gradio_client import Client, handle_file
15
 
16
  load_dotenv()
17
 
 
19
  logging.basicConfig(level=logging.INFO, format='%(asctime)s - %(levelname)s - %(message)s')
20
  logger = logging.getLogger(__name__)
21
 
22
+ # ํด๋ผ์ด์–ธํŠธ ์ •๋ณด ๋กœ๊ทธ์—์„œ ์ˆจ๊ธฐ๊ธฐ
23
+ logging.getLogger('gradio_client').setLevel(logging.WARNING)
24
+
25
+ # API ์—”๋“œํฌ์ธํŠธ ์„ค์ • (ํ™˜๊ฒฝ๋ณ€์ˆ˜์—์„œ๋งŒ ์„ค์ •)
26
+ API_ENDPOINT = os.environ.get("API_ENDPOINT", "")
27
+
28
+ if not API_ENDPOINT:
29
+ raise ValueError("API_ENDPOINT ํ™˜๊ฒฝ๋ณ€์ˆ˜๊ฐ€ ์„ค์ •๋˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.")
30
+
31
+ # ํด๋ผ์ด์–ธํŠธ ์ดˆ๊ธฐํ™”
32
+ try:
33
+ client = Client(API_ENDPOINT)
34
+ logger.info("ํด๋ผ์ด์–ธํŠธ ์ดˆ๊ธฐํ™” ์™„๋ฃŒ")
35
+ except Exception as e:
36
+ logger.error(f"ํด๋ผ์ด์–ธํŠธ ์ดˆ๊ธฐํ™” ์‹คํŒจ: {e}")
37
+ raise
38
+
39
+ def safe_client_call(api_name, **kwargs):
40
+ """์•ˆ์ „ํ•œ ํด๋ผ์ด์–ธํŠธ ํ˜ธ์ถœ ํ•จ์ˆ˜"""
41
+ try:
42
+ return client.predict(api_name=api_name, **kwargs)
43
+ except Exception as e:
44
+ logger.error(f"API ํ˜ธ์ถœ ์‹คํŒจ ({api_name}): {e}")
45
  return None
 
 
 
 
 
 
 
 
 
 
46
 
47
+ def convert_image_to_file(image):
48
+ """PIL Image ๊ฐ์ฒด๋ฅผ ์ž„์‹œ ํŒŒ์ผ๋กœ ๋ณ€ํ™˜"""
49
  if image is None:
50
  return None
51
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
52
  try:
53
+ # PIL Image ๊ฐ์ฒด์ธ ๊ฒฝ์šฐ
54
+ if hasattr(image, 'save'):
55
+ # ์ž„์‹œ ํŒŒ์ผ ์ƒ์„ฑ
56
+ temp_file = tempfile.NamedTemporaryFile(suffix='.png', delete=False)
57
+ image.save(temp_file.name, format='PNG')
58
+ temp_file.close()
59
+ return temp_file.name
60
+ # ์ด๋ฏธ ํŒŒ์ผ ๊ฒฝ๋กœ์ธ ๊ฒฝ์šฐ
61
+ elif isinstance(image, str):
62
+ return image
63
+ # ๊ธฐํƒ€ ๊ฒฝ์šฐ
64
+ else:
65
+ return image
66
+ except Exception as e:
67
+ logger.error(f"์ด๋ฏธ์ง€ ํŒŒ์ผ ๋ณ€ํ™˜ ์‹คํŒจ: {e}")
68
+ return None
 
 
 
 
 
 
 
 
 
 
69
 
70
+ # ========== ์ด๋ฏธ์ง€ ์ƒ์„ฑ๊ธฐ ๊ด€๋ จ ํ•จ์ˆ˜ (ํด๋ผ์ด์–ธํŠธ API ํ™œ์šฉ) ==========
71
+ def generate_single_image(image1, image2, image3, prompt):
72
+ """๋‹จ์ผ ์ด๋ฏธ์ง€ ์ƒ์„ฑ - ์›๋ณธ ํ•จ์ˆ˜๋ช… ์œ ์ง€"""
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
73
  try:
74
+ # ์ด๋ฏธ์ง€ ํŒŒ์ผ ์ฒ˜๋ฆฌ - PIL Image๋ฅผ ์ž„์‹œ ํŒŒ์ผ๋กœ ๋ณ€ํ™˜
75
+ image1_path = convert_image_to_file(image1)
76
+ image2_path = convert_image_to_file(image2)
77
+ image3_path = convert_image_to_file(image3)
78
+
79
+ # handle_file๋กœ ์ฒ˜๋ฆฌ
80
+ image1_file = handle_file(image1_path) if image1_path else None
81
+ image2_file = handle_file(image2_path) if image2_path else None
82
+ image3_file = handle_file(image3_path) if image3_path else None
83
+
84
+ result = safe_client_call(
85
+ "/generate_single_image",
86
+ image1=image1_file,
87
+ image2=image2_file,
88
+ image3=image3_file,
89
+ prompt=prompt
90
+ )
91
+
92
+ if result:
93
+ return result[0], result[1], result[2]
 
94
  else:
95
+ return None, "API ํ˜ธ์ถœ ์‹คํŒจ", ""
96
+
97
+ except Exception as e:
98
+ logger.error(f"๋‹จ์ผ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์‹คํŒจ: {e}")
99
+ return None, f"์˜ค๋ฅ˜ ๋ฐœ์ƒ: {str(e)}", ""
100
+
101
+ def generate_multiple_images(image1, image2, image3, prompt, progress=gr.Progress()):
102
+ """๋‹ค์ค‘ ์ด๋ฏธ์ง€ ์ƒ์„ฑ - ์›๋ณธ ํ•จ์ˆ˜๋ช… ์œ ์ง€"""
 
103
  try:
104
+ progress(0, desc="์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค€๋น„ ์ค‘...")
105
+
106
+ # ์ด๋ฏธ์ง€ ํŒŒ์ผ ์ฒ˜๋ฆฌ - PIL Image๋ฅผ ์ž„์‹œ ํŒŒ์ผ๋กœ ๋ณ€ํ™˜
107
+ image1_path = convert_image_to_file(image1)
108
+ image2_path = convert_image_to_file(image2)
109
+ image3_path = convert_image_to_file(image3)
110
+
111
+ # handle_file๋กœ ์ฒ˜๋ฆฌ
112
+ image1_file = handle_file(image1_path) if image1_path else None
113
+ image2_file = handle_file(image2_path) if image2_path else None
114
+ image3_file = handle_file(image3_path) if image3_path else None
115
+
116
+ progress(0.5, desc="์ด๋ฏธ์ง€ ์ƒ์„ฑ ์ค‘...")
117
+
118
+ result = safe_client_call(
119
+ "/generate_multiple_images",
120
+ image1=image1_file,
121
+ image2=image2_file,
122
+ image3=image3_file,
123
+ prompt=prompt
124
+ )
125
+
126
+ progress(1.0, desc="์ด๋ฏธ์ง€ ์ƒ์„ฑ ์™„๋ฃŒ!")
127
 
128
+ if result:
129
+ return result[0], result[1], result[2], result[3]
 
 
130
  else:
131
+ return None, None, "API ํ˜ธ์ถœ ์‹คํŒจ", ""
132
+
133
  except Exception as e:
134
+ logger.error(f"๋‹ค์ค‘ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ์‹คํŒจ: {e}")
135
+ return None, None, f"์˜ค๋ฅ˜ ๋ฐœ์ƒ: {str(e)}", ""
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
136
 
137
+ # ========== ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ ํ•จ์ˆ˜๋“ค - ํด๋ผ์ด์–ธํŠธ API ํ™œ์šฉ ==========
138
+ def get_prompt_template_1():
139
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 1 - ๋ถ€๋ถ„๋ณ€๊ฒฝ-1"""
140
+ return "(#1์˜ ์—ฌ์„ฑ)์ด ์‚ด์ง ๋’ค๋กœ ๋Œ์•„๋ณด๋Š” ๋ชจ์Šต์œผ๋กœ ์ตœ๋Œ€ํ•œ ์ด์ „ seed๋ฅผ ์œ ์ง€ํ•œํ…Œ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๋ณ€๊ฒฝํ•˜๋ผ."
 
 
 
141
 
142
+ def get_prompt_template_2():
143
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 2 - ๋ถ€๋ถ„๋ณ€๊ฒฝ-2"""
144
+ return "(#1 ๋ ˆ๋ชจ๋ชจํ˜•)์—์„œ ์ฒญ์ƒ‰์ƒ์–ด๋ ˆ๊ณ ๋งŒ ๊ฒ€์€์ƒ‰ ๊ณ ๋ž˜๋ ˆ๊ณ ๋กœ ๋ณ€๊ฒฝํ•˜๊ณ  ๋‚˜๋จธ์ง€ ๋ถ€๋ถ„์€ seed๋ฅผ ๋ณ€๊ฒฝ์„ ํ•˜์ง€๋งˆ๋ผ."
145
 
146
+ def get_prompt_template_3():
147
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 3 - ๋ถ€๋ถ„๋ณ€๊ฒฝ-3"""
148
+ return "(#1 ์—ฌํ–‰์šฉ ์–ผ์Œ๋ฐ•์Šค)์•ž์— ์–ผ์Œ์ด ๋‹ด๊ธด 3์ž”์˜ ์ฝœ๋ผ๊ฐ€ ๋†“์—ฌ์žˆ๋Š” ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ."
149
 
150
+ def get_prompt_template_4():
151
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 4 - ๊ธ€์ž์ง€์šฐ๊ธฐ"""
152
+ return "(#1 ์ด๋ฏธ์ง€)์— ์žˆ๋Š” ์ค‘๊ตญ์–ด๋ฅผ ๋ชจ๋‘ ์ œ๊ฑฐํ•˜๋ผ."
153
 
154
+ def get_prompt_template_5():
155
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 5 - ๊ธ€์ž๋ณ€๊ฒฝ"""
156
+ return '(#1์˜ ํ…์ŠคํŠธ)๋ฅผ ์Šคํƒ€์ผ์„ ์œ ์ง€ํ•œ์ฒด ํ…์ŠคํŠธ๋งŒ "Hello"๋กœ ๋ฐ”๊ฟ”๋ผ'
157
 
158
+ def get_prompt_template_6():
159
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 6 - ์ƒํ’ˆ์ฐฉ์šฉ-1"""
160
+ return "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด ์‹ ์ฒด ๋น„์œจ๊ณผ ํฌ์ฆˆ๋Š” ์œ ์ง€ํ•œ ์ฒด (#2์˜ ์„ ๊ธ€๋ผ์Šค)์™€ (#3์˜ ์ฒญ๋ฐ”์ง€)๋ฅผ ์ง์ ‘ ๋ชจ๋ธ์ด ์ฐฉ์šฉํ•œ๊ฒƒ ์ฒ˜๋Ÿผ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ."
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
161
 
162
+ def get_prompt_template_7():
163
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 7 - ์ƒํ’ˆ์ฐฉ์šฉ-2"""
164
+ return "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด (#2์˜ ์„ ๊ธ€๋ผ์Šค)์„ ์ฐฉ์šฉํ•˜๊ณ  (#3์˜ ๋’ท๋ฐฐ๊ฒฝ์˜ ์นดํŽ˜์ „์ฒด๊ฐ€ ๋ณด์ด๋ฉฐ) ์˜์ž์— ์•‰์•„ ์žˆ๋Š” ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ."
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
165
 
166
+ def get_prompt_template_8():
167
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 8 - ์ƒํ’ˆ๋“ค๊ณ """
168
+ return "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด(#2์˜ ์™€์ธ์ž”)์„ ๋“ค๊ณ  ์žˆ๋Š” ์ž์—ฐ์Šค๋Ÿฌ์šด ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ."
169
+
170
+ def get_prompt_template_9():
171
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 9 - ๋ฐฐ๊ฒฝ๋ฐ”๊พธ๊ธฐ"""
172
+ return "(#1์˜ ์—ฌ์„ฑ๋ชจ๋ธ)์ด (#2 ์นดํŽ˜)์—์„œ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์žˆ๋Š” ๋ชจ์Šต์„ ์ƒ์„ฑํ•˜๋ผ."
173
+
174
+ def get_prompt_template_10():
175
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 10 - ๋ถ€๋ถ„์ง€์šฐ๊ธฐ"""
176
+ return "(#1์˜ ๋ ˆ๊ณ ๋ชจํ˜•)์—์„œ ์ฒญ์ƒ‰์ƒ์–ด๋ ˆ๊ณ ๋ฅผ ์ œ๊ฑฐํ•œ ํ›„, ๊ทธ ์ž๋ฆฌ๋ฅผ ์ฃผ๋ณ€ ๋ฐฐ๊ฒฝ๊ณผ ์ž์—ฐ์Šค๋Ÿฝ๊ฒŒ ์–ด์šฐ๏ฟฝ๏ฟฝ๏ฟฝ์ง€๋„๋ก ์ฑ„์›Œ์ฃผ์„ธ์š”. ๋‹จ, ์ด๋ฏธ์ง€์˜ ๋‹ค๋ฅธ ๋ถ€๋ถ„์˜ ์ฃผ์š” ์š”์†Œ๋Š” ๋™์ผํ•˜๊ฒŒ ์œ ์ง€ ํ•ด์•ผํ•œ๋‹ค."
177
+
178
+ def get_prompt_template_11():
179
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 11 - ์ด๋ฏธ์ง€ํ™•์žฅ"""
180
+ return "(#1 ์ด๋ฏธ์ง€)๋ฅผ ์›๋ณธ๊ทธ๋Œ€๋กœ ์ค‘์•™์— ๋‘๊ณ  ๋น„์œจ๋กœ ์œ ์ง€ํ•œ ์ฒด ์œ„์•„๋ž˜ ๋ฐ ์ขŒ์šฐ๋กœ ํฌ๊ฒŒ ํ™•์žฅํ•˜๋ผ."
181
+
182
+ def get_prompt_template_12():
183
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 12 - ํ”Œ๋ ˆ์ดํŒ…-1"""
184
+ return "(#1์…€๋Ÿฌ๋“œ)์— ๋‹ด์€ ์šฉ๊ธฐ๋Š” ๋ฒ„๋ฆฌ๊ณ  ๋„“๊ณ  ํฐ ์˜ˆ์œ ์ ‘์‹œ์— (#1์…€๋Ÿฌ๋“œ)์Œ์‹๋งŒ ๊ฐ€๋“ ์ฑ„์›Œ์„œ ์ƒ์—…์ ์ธ ๊ฐ๋„๋กœ ์–ด์šธ๋ฆฌ๋Š” ์†Œํ’ˆ๊ณผ ํ•จ๊ป˜ ํ”Œ๋ ˆ์ดํŒ… ํ•œ ๋ชจ์Šต์„ ์ด๋ฏธ์ง€๋กœ ์ƒ์„ฑํ•˜๋ผ. "
185
+
186
+ def get_prompt_template_13():
187
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 13 - ํ”Œ๋ ˆ์ดํŒ…-2"""
188
+ return "(#2 ํ”Œ๋ ˆ์ดํŒ…ํ•œ ์ด๋ฏธ์ง€)์— ๋‹ด๊ธด ์Œ์‹์„ (#1 ์ƒ๋Ÿฌ๋“œ)๋กœ ๋ฐ”๊พธ๊ณ  ๋‚˜๋จธ์ง€๋Š” ์‹œ๋“œ๋ฅผ ์œ ์ง€ํ•œ ์ฒด ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ."
189
+
190
+ def get_prompt_template_14():
191
+ """ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ 14 - ํ”Œ๋ ˆ์ดํŒ…-3"""
192
+ return "(#1์ปต)์— ๋”ธ๊ธฐ, ๋ฐ”๋‹๋ผ, ์ดˆ์ฝ” ์•„์ด์Šคํฌ๋ฆผ์„ ๋‹ด๊ณ  ๊ทธ ์œ„์— ์ดˆ์ฝ” ์‹œ๋Ÿฝ์ด ํ๋ฅด๊ฒŒ ์ด๋ฏธ์ง€๋ฅผ ์ƒ์„ฑํ•˜๋ผ."
 
 
 
 
 
 
 
 
193
 
194
  # ๋‹คํฌ๋ชจ๋“œ ์ž๋™ ์ ์šฉ ์ปค์Šคํ…€ CSS ์Šคํƒ€์ผ
195
  custom_css = """
 
625
  )) as demo:
626
  gr.HTML(fontawesome_link)
627
 
 
628
  with gr.Row(equal_height=True):
629
  with gr.Column(scale=1):
630
  # ======== ์ด๋ฏธ์ง€ ์—…๋กœ๋“œ ๋ฐ ์„ค์ • ์„น์…˜ ========
 
713
  )
714
 
715
  # ========== ์ด๋ฏธ์ง€ ์ƒ์„ฑ๊ธฐ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ ==========
716
+ # ๋ฒ„ํŠผ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ - ํ”„๋กฌํ”„ํŠธ ํ…œํ”Œ๋ฆฟ
717
+ image_change_btn1.click(fn=get_prompt_template_1, outputs=prompt_input)
718
+ image_change_btn2.click(fn=get_prompt_template_2, outputs=prompt_input)
719
+ image_change_btn3.click(fn=get_prompt_template_3, outputs=prompt_input)
720
+ text_remove_btn.click(fn=get_prompt_template_4, outputs=prompt_input)
721
+ text_change_btn.click(fn=get_prompt_template_5, outputs=prompt_input)
722
+ clothes_change_btn1.click(fn=get_prompt_template_6, outputs=prompt_input)
723
+ clothes_change_btn2.click(fn=get_prompt_template_7, outputs=prompt_input)
724
+ holding_product_btn.click(fn=get_prompt_template_8, outputs=prompt_input)
725
+ background_change_btn.click(fn=get_prompt_template_9, outputs=prompt_input)
726
+ composite_product_btn.click(fn=get_prompt_template_10, outputs=prompt_input)
727
+ outpainting_btn.click(fn=get_prompt_template_11, outputs=prompt_input)
728
+ food_btn_1.click(fn=get_prompt_template_12, outputs=prompt_input)
729
+ food_btn_2.click(fn=get_prompt_template_13, outputs=prompt_input)
730
+ food_btn_3.click(fn=get_prompt_template_14, outputs=prompt_input)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
731
 
732
  # ๋‹จ์ผ ์ด๋ฏธ์ง€ ์ƒ์„ฑ ๋ฒ„ํŠผ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ
 
 
 
733
  submit_single_btn.click(
734
  fn=generate_single_image,
735
  inputs=[image1_input, image2_input, image3_input, prompt_input],
 
744
  )
745
 
746
  # ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ์‹คํ–‰
747
+ demo.queue()
748
+ demo.launch(share=False, inbrowser=True, width="100%")