File size: 1,967 Bytes
a740f1b
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
d3530a8
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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
import gradio as gr
from PIL import Image
import numpy as np
from typing import TypedDict


def combine_masks(im_1: np.ndarray, im_2: np.ndarray):
    """
    Layers images on top of each other, with the foreground image overwriting the background.
    params:
        im_1: background image
        im_2: foreground image
    return:
        combined image
    """
    if im_1.shape != im_2.shape:
        raise ValueError("Images must have the same dimensions")

    # replace rgb values of the background with the foreground where foreground is not fully transparent
    foreground_mask = im_2[:, :, 3] > 0
    im_1[foreground_mask] = im_2[foreground_mask]

    return im_1


def make_grey(image: np.ndarray, grey_value: int = 128):
    """
    Converts opaque pixels within an image to a static grey value.
    params:
        image: RGBA image
    return:
        greyscale image
    """
    rgb = image[:, :, :3]
    alpha = image[:, :, 3]

    opaque_mask = alpha == 255

    # arbitrary grey value

    # apply grey values to the opaque pixels
    rgb[opaque_mask] = np.stack((grey_value, grey_value, grey_value), axis=-1)

    # combine channels and return
    return np.dstack((rgb, alpha))
    
class ImageData(TypedDict):
    background: np.ndarray
    layers: list[np.ndarray]


def mask(image: ImageData):
    bg = image.get("background", None)
    layers = image.get("layers", [])

    if bg is None and not layers:
        raise ValueError("No background or layers provided")

    mask = layers[0]
    for layer in layers[1:]:
        mask = combine_masks(mask, layer)

    # save images or use them elsewhere
    # Image.fromarray(mask).save("mask.png")
    # Image.fromarray(bg).save("bg.png")

    mask = make_grey(mask)

    return [bg, mask]


with gr.Blocks() as demo:
    imed = gr.ImageEditor()
    im_1 = gr.Image()
    im_2 = gr.Image()
    imed.apply(mask, inputs=imed, outputs=[im_1, im_2])

if __name__ == "__main__":
    demo.launch()