TIMBOVILL commited on
Commit
188e92b
·
verified ·
1 Parent(s): e7b5496

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +27 -12
app.py CHANGED
@@ -10,39 +10,54 @@ def brightness_to_opacity_overlay(foreground_img, background_img, invert_opacity
10
  bg = background_img.convert("RGBA")
11
  fg = foreground_img.convert("RGB").resize(bg.size)
12
 
13
- # Convert foreground to grayscale (luminance)
14
  fg_array = np.array(fg)
15
  luminance = np.dot(fg_array[...,:3], [0.299, 0.587, 0.114]).astype(np.uint8)
16
 
17
- # Optionally invert the opacity
18
  alpha = 255 - luminance if invert_opacity else luminance
19
 
20
- # Set RGB to white, combine with alpha
21
  white_rgb = np.ones_like(fg_array) * 255
22
  rgba_array = np.dstack((white_rgb, alpha)).astype(np.uint8)
23
- mask_image = Image.fromarray(rgba_array, mode="RGBA")
24
 
25
- # Overlay mask_image on background
26
- combined = Image.alpha_composite(bg, mask_image)
 
27
 
28
- return combined
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
29
 
30
  # Gradio UI
31
  iface = gr.Interface(
32
  fn=brightness_to_opacity_overlay,
33
  inputs=[
34
  gr.Image(type="pil", label="Mask Source (Brightness to Alpha)"),
35
- gr.Image(type="pil", label="Background Image"),
36
  gr.Checkbox(label="Invert Opacity", value=False)
37
  ],
38
  outputs=gr.Image(type="pil", label="Final Composite"),
39
- title="Brightness-to-Alpha Overlay Tool",
40
  description=(
41
- "This tool uses the brightness of the first image as its opacity mask, "
42
- "optionally inverts it, resizes it to match the second image, and overlays the result."
43
  )
44
  )
45
 
46
- # Run the app
47
  if __name__ == "__main__":
48
  iface.launch()
 
10
  bg = background_img.convert("RGBA")
11
  fg = foreground_img.convert("RGB").resize(bg.size)
12
 
13
+ # Convert to luminance (grayscale)
14
  fg_array = np.array(fg)
15
  luminance = np.dot(fg_array[...,:3], [0.299, 0.587, 0.114]).astype(np.uint8)
16
 
17
+ # Invert if requested
18
  alpha = 255 - luminance if invert_opacity else luminance
19
 
20
+ # Create white RGBA image with computed alpha
21
  white_rgb = np.ones_like(fg_array) * 255
22
  rgba_array = np.dstack((white_rgb, alpha)).astype(np.uint8)
23
+ overlay = Image.fromarray(rgba_array, mode="RGBA")
24
 
25
+ # Manual alpha blending
26
+ bg_arr = np.array(bg).astype(np.float32) / 255.0
27
+ ov_arr = np.array(overlay).astype(np.float32) / 255.0
28
 
29
+ # Extract alpha channels
30
+ alpha_bg = bg_arr[..., 3:4]
31
+ alpha_ov = ov_arr[..., 3:4]
32
+
33
+ # Composite alpha and color
34
+ out_alpha = alpha_ov + alpha_bg * (1 - alpha_ov)
35
+ out_rgb = (
36
+ ov_arr[..., :3] * alpha_ov +
37
+ bg_arr[..., :3] * alpha_bg * (1 - alpha_ov)
38
+ ) / np.clip(out_alpha, 1e-6, 1)
39
+
40
+ # Combine and convert to final image
41
+ out_image = np.dstack((out_rgb, out_alpha)).clip(0, 1) * 255
42
+ out_image = Image.fromarray(out_image.astype(np.uint8), mode="RGBA")
43
+
44
+ return out_image
45
 
46
  # Gradio UI
47
  iface = gr.Interface(
48
  fn=brightness_to_opacity_overlay,
49
  inputs=[
50
  gr.Image(type="pil", label="Mask Source (Brightness to Alpha)"),
51
+ gr.Image(type="pil", label="Background Image (with or without transparency)"),
52
  gr.Checkbox(label="Invert Opacity", value=False)
53
  ],
54
  outputs=gr.Image(type="pil", label="Final Composite"),
55
+ title="Brightness-to-Alpha Overlay Tool (with Transparency Fix)",
56
  description=(
57
+ "Uses the brightness of the first image as alpha, resizes to match the second image, "
58
+ "and overlays correctly even when the background has transparency."
59
  )
60
  )
61
 
 
62
  if __name__ == "__main__":
63
  iface.launch()