Spaces:
Sleeping
Sleeping
updates app.py - fix pattern matching
Browse files
app.py
CHANGED
|
@@ -132,25 +132,38 @@ def add_text_to_image(img, pattern, line1, line2, line3, font_size, color, add_o
|
|
| 132 |
|
| 133 |
w, h = image.size
|
| 134 |
print(f"Image dimensions: {w}x{h}")
|
|
|
|
|
|
|
| 135 |
positions = []
|
|
|
|
|
|
|
|
|
|
|
|
|
| 136 |
|
| 137 |
-
|
| 138 |
-
if pattern == "2-lines-top":
|
| 139 |
positions = [(w // 2, int(h * 0.10)), (w // 2, int(h * 0.20))]
|
| 140 |
-
|
|
|
|
| 141 |
positions = [(w // 2, int(h * 0.80)), (w // 2, int(h * 0.90))]
|
| 142 |
-
|
|
|
|
| 143 |
positions = [(w // 2, int(h * 0.45)), (w // 2, int(h * 0.55))]
|
| 144 |
-
|
| 145 |
-
|
| 146 |
-
elif pattern == "3-lines-top":
|
| 147 |
positions = [(w // 2, int(h * 0.10)), (w // 2, int(h * 0.20)), (w // 2, int(h * 0.30))]
|
| 148 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 149 |
positions = [(w // 2, int(h * 0.70)), (w // 2, int(h * 0.80)), (w // 2, int(h * 0.90))]
|
|
|
|
| 150 |
else:
|
| 151 |
-
print(f"WARNING: Unknown pattern '{pattern}', using default")
|
| 152 |
-
positions = [(w // 2, int(h * 0.
|
|
|
|
| 153 |
|
|
|
|
| 154 |
print(f"Text positions calculated: {positions}")
|
| 155 |
|
| 156 |
# FIXED: Parse RGBA string from Gradio ColorPicker
|
|
@@ -224,74 +237,73 @@ def add_text_to_image(img, pattern, line1, line2, line3, font_size, color, add_o
|
|
| 224 |
|
| 225 |
print(f"Final color for drawing: {final_color}")
|
| 226 |
|
| 227 |
-
# Draw text
|
| 228 |
-
lines = [line1, line2, line3]
|
| 229 |
-
print(f"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 230 |
text_drawn = False
|
| 231 |
|
| 232 |
-
for i, ((x, y), txt) in enumerate(
|
| 233 |
-
|
| 234 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 235 |
|
| 236 |
-
#
|
| 237 |
-
|
| 238 |
-
|
| 239 |
-
|
| 240 |
-
|
| 241 |
-
|
| 242 |
-
|
| 243 |
-
for dy in [-stroke_width, 0, stroke_width]:
|
| 244 |
-
if dx != 0 or dy != 0:
|
| 245 |
try:
|
| 246 |
-
draw.
|
| 247 |
-
|
| 248 |
-
|
| 249 |
-
|
| 250 |
-
|
| 251 |
-
|
| 252 |
-
|
| 253 |
-
|
| 254 |
-
|
| 255 |
-
|
| 256 |
-
|
| 257 |
-
|
| 258 |
-
|
| 259 |
-
|
| 260 |
try:
|
| 261 |
-
draw.
|
| 262 |
-
|
| 263 |
-
|
| 264 |
-
|
| 265 |
-
|
| 266 |
-
|
| 267 |
-
|
| 268 |
-
|
| 269 |
-
|
| 270 |
-
|
| 271 |
-
|
| 272 |
-
|
| 273 |
-
|
| 274 |
-
print(f"Fallback failed: {e}, trying basic draw")
|
| 275 |
-
draw.text((x, y), txt, fill=final_color, font=font)
|
| 276 |
-
print(f"SUCCESS: Basic text drawn with color {final_color} at ({x}, {y})")
|
| 277 |
-
except Exception as e:
|
| 278 |
-
print(f"ERROR drawing main text with final_color: {e}")
|
| 279 |
-
# Last resort - try with white
|
| 280 |
-
try:
|
| 281 |
-
draw.text((x, y), txt, fill=(255, 255, 255), font=font, anchor="mm")
|
| 282 |
-
print(f"FALLBACK: Drew text in white")
|
| 283 |
-
except Exception as e2:
|
| 284 |
-
print(f"Even white text failed: {e2}")
|
| 285 |
-
|
| 286 |
-
text_drawn = True
|
| 287 |
-
print(f"Completed drawing line {i+1}")
|
| 288 |
|
| 289 |
if not text_drawn:
|
| 290 |
-
print("No text was drawn")
|
| 291 |
return img, "No text to add (all lines were empty)"
|
| 292 |
|
| 293 |
print("=== Text drawing completed successfully ===")
|
| 294 |
-
return image, f"
|
| 295 |
|
| 296 |
except Exception as e:
|
| 297 |
print(f"CRITICAL ERROR in add_text_to_image: {e}")
|
|
@@ -511,7 +523,7 @@ with gr.Blocks(title="AI Image Generator & Text Overlay") as demo:
|
|
| 511 |
("3-lines-center", "π 3 Lines - Center (Full title)"),
|
| 512 |
("3-lines-bottom", "π 3 Lines - Bottom (Credits style)")
|
| 513 |
],
|
| 514 |
-
value="2-lines-top",
|
| 515 |
label="Layout Pattern"
|
| 516 |
)
|
| 517 |
|
|
|
|
| 132 |
|
| 133 |
w, h = image.size
|
| 134 |
print(f"Image dimensions: {w}x{h}")
|
| 135 |
+
|
| 136 |
+
# ROBUST pattern matching - handle both simple names and descriptive text
|
| 137 |
positions = []
|
| 138 |
+
detected_pattern = "unknown"
|
| 139 |
+
|
| 140 |
+
# Normalize pattern string for matching
|
| 141 |
+
pattern_lower = pattern.lower()
|
| 142 |
|
| 143 |
+
if ("2-lines-top" in pattern_lower) or ("2 lines - top" in pattern_lower):
|
|
|
|
| 144 |
positions = [(w // 2, int(h * 0.10)), (w // 2, int(h * 0.20))]
|
| 145 |
+
detected_pattern = "2-lines-top"
|
| 146 |
+
elif ("2-lines-bottom" in pattern_lower) or ("2 lines - bottom" in pattern_lower):
|
| 147 |
positions = [(w // 2, int(h * 0.80)), (w // 2, int(h * 0.90))]
|
| 148 |
+
detected_pattern = "2-lines-bottom"
|
| 149 |
+
elif ("2-lines-center" in pattern_lower) or ("2 lines - center" in pattern_lower):
|
| 150 |
positions = [(w // 2, int(h * 0.45)), (w // 2, int(h * 0.55))]
|
| 151 |
+
detected_pattern = "2-lines-center"
|
| 152 |
+
elif ("3-lines-top" in pattern_lower) or ("3 lines - top" in pattern_lower):
|
|
|
|
| 153 |
positions = [(w // 2, int(h * 0.10)), (w // 2, int(h * 0.20)), (w // 2, int(h * 0.30))]
|
| 154 |
+
detected_pattern = "3-lines-top"
|
| 155 |
+
elif ("3-lines-center" in pattern_lower) or ("3 lines - center" in pattern_lower):
|
| 156 |
+
positions = [(w // 2, int(h * 0.40)), (w // 2, int(h * 0.50)), (w // 2, int(h * 0.60))]
|
| 157 |
+
detected_pattern = "3-lines-center"
|
| 158 |
+
elif ("3-lines-bottom" in pattern_lower) or ("3 lines - bottom" in pattern_lower):
|
| 159 |
positions = [(w // 2, int(h * 0.70)), (w // 2, int(h * 0.80)), (w // 2, int(h * 0.90))]
|
| 160 |
+
detected_pattern = "3-lines-bottom"
|
| 161 |
else:
|
| 162 |
+
print(f"WARNING: Unknown pattern '{pattern}', using 2-lines-center as default")
|
| 163 |
+
positions = [(w // 2, int(h * 0.45)), (w // 2, int(h * 0.55))]
|
| 164 |
+
detected_pattern = "2-lines-center (default)"
|
| 165 |
|
| 166 |
+
print(f"Detected pattern: {detected_pattern}")
|
| 167 |
print(f"Text positions calculated: {positions}")
|
| 168 |
|
| 169 |
# FIXED: Parse RGBA string from Gradio ColorPicker
|
|
|
|
| 237 |
|
| 238 |
print(f"Final color for drawing: {final_color}")
|
| 239 |
|
| 240 |
+
# Draw text - PROPERLY handle all lines
|
| 241 |
+
lines = [line1, line2, line3]
|
| 242 |
+
print(f"All input lines: {lines}")
|
| 243 |
+
|
| 244 |
+
# Only use as many lines as we have positions, but process non-empty ones
|
| 245 |
+
active_lines = []
|
| 246 |
+
for i in range(len(positions)):
|
| 247 |
+
if i < len(lines) and lines[i] and lines[i].strip():
|
| 248 |
+
active_lines.append((positions[i], lines[i].strip()))
|
| 249 |
+
|
| 250 |
+
print(f"Active lines to draw: {len(active_lines)} out of {len(positions)} positions")
|
| 251 |
+
for i, (pos, text) in enumerate(active_lines):
|
| 252 |
+
print(f" Line {i+1}: '{text}' at {pos}")
|
| 253 |
+
|
| 254 |
text_drawn = False
|
| 255 |
|
| 256 |
+
for i, ((x, y), txt) in enumerate(active_lines):
|
| 257 |
+
print(f"Drawing line {i+1}: '{txt}' at position ({x}, {y})")
|
| 258 |
+
|
| 259 |
+
# Optional outline/stroke
|
| 260 |
+
if add_outline:
|
| 261 |
+
stroke_width = max(1, font_size // 20)
|
| 262 |
+
print(f"Adding outline with stroke width: {stroke_width}")
|
| 263 |
|
| 264 |
+
# Draw text outline (black)
|
| 265 |
+
for dx in [-stroke_width, 0, stroke_width]:
|
| 266 |
+
for dy in [-stroke_width, 0, stroke_width]:
|
| 267 |
+
if dx != 0 or dy != 0:
|
| 268 |
+
try:
|
| 269 |
+
draw.text((x + dx, y + dy), txt, fill=(0, 0, 0), font=font, anchor="mm")
|
| 270 |
+
except TypeError:
|
|
|
|
|
|
|
| 271 |
try:
|
| 272 |
+
bbox = draw.textbbox((0, 0), txt, font=font)
|
| 273 |
+
text_w = bbox[2] - bbox[0]
|
| 274 |
+
text_h = bbox[3] - bbox[1]
|
| 275 |
+
draw.text((x - text_w//2 + dx, y - text_h//2 + dy), txt, fill=(0, 0, 0), font=font)
|
| 276 |
+
except Exception:
|
| 277 |
+
draw.text((x + dx, y + dy), txt, fill=(0, 0, 0), font=font)
|
| 278 |
+
else:
|
| 279 |
+
print("Skipping outline (disabled)")
|
| 280 |
+
|
| 281 |
+
# Draw main text
|
| 282 |
+
try:
|
| 283 |
+
draw.text((x, y), txt, fill=final_color, font=font, anchor="mm")
|
| 284 |
+
print(f"SUCCESS: Main text drawn with color {final_color} at ({x}, {y})")
|
| 285 |
+
except TypeError:
|
| 286 |
try:
|
| 287 |
+
bbox = draw.textbbox((0, 0), txt, font=font)
|
| 288 |
+
text_w = bbox[2] - bbox[0]
|
| 289 |
+
text_h = bbox[3] - bbox[1]
|
| 290 |
+
fallback_x = x - text_w//2
|
| 291 |
+
fallback_y = y - text_h//2
|
| 292 |
+
draw.text((fallback_x, fallback_y), txt, fill=final_color, font=font)
|
| 293 |
+
print(f"SUCCESS: Fallback text drawn with color {final_color} at ({fallback_x}, {fallback_y})")
|
| 294 |
+
except Exception:
|
| 295 |
+
draw.text((x, y), txt, fill=final_color, font=font)
|
| 296 |
+
print(f"SUCCESS: Basic text drawn with color {final_color} at ({x}, {y})")
|
| 297 |
+
|
| 298 |
+
text_drawn = True
|
| 299 |
+
print(f"Completed drawing line {i+1}")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 300 |
|
| 301 |
if not text_drawn:
|
| 302 |
+
print("No text was drawn - all lines were empty")
|
| 303 |
return img, "No text to add (all lines were empty)"
|
| 304 |
|
| 305 |
print("=== Text drawing completed successfully ===")
|
| 306 |
+
return image, f"β
{len(active_lines)} lines added! Pattern: {detected_pattern}"
|
| 307 |
|
| 308 |
except Exception as e:
|
| 309 |
print(f"CRITICAL ERROR in add_text_to_image: {e}")
|
|
|
|
| 523 |
("3-lines-center", "π 3 Lines - Center (Full title)"),
|
| 524 |
("3-lines-bottom", "π 3 Lines - Bottom (Credits style)")
|
| 525 |
],
|
| 526 |
+
value="2-lines-top",
|
| 527 |
label="Layout Pattern"
|
| 528 |
)
|
| 529 |
|