akhaliq HF Staff commited on
Commit
4eac3f3
·
1 Parent(s): 07c98cb

Prefill reference values via node data, wire condition image, handle canvas file URLs in edit_image

Browse files
Files changed (2) hide show
  1. app.py +18 -5
  2. workflow.json +24 -7
app.py CHANGED
@@ -10,7 +10,10 @@ PyTorch runs in CUDA emulation mode, and a real ZeroGPU is attached only while
10
  a decorated function executes.
11
  """
12
 
 
13
  import os
 
 
14
 
15
  import gradio as gr
16
  from gradio_client import utils as client_utils
@@ -39,14 +42,24 @@ pipe.to("cuda")
39
 
40
  def _to_pil(image) -> Image.Image:
41
  """Accept whatever the canvas hands a bound function for an image port:
42
- a PIL image, a file path, or Gradio's {path, url, is_file} file dict."""
 
 
 
 
43
  if isinstance(image, Image.Image):
44
  return image
45
  if isinstance(image, dict):
46
- image = image.get("path") or image.get("url")
47
- if isinstance(image, str):
48
- return Image.open(image)
49
- raise ValueError(f"Unsupported image input: {type(image)!r}")
 
 
 
 
 
 
50
 
51
 
52
  def _save(image: Image.Image) -> dict:
 
10
  a decorated function executes.
11
  """
12
 
13
+ import base64
14
  import os
15
+ import urllib.parse
16
+ import urllib.request
17
 
18
  import gradio as gr
19
  from gradio_client import utils as client_utils
 
42
 
43
  def _to_pil(image) -> Image.Image:
44
  """Accept whatever the canvas hands a bound function for an image port:
45
+ a PIL image, a local path, a /gradio_api/file= reference, an http(s) or
46
+ data: URL, or a file dict carrying any of those. Mirrors _file_ref in
47
+ gradio.workflow — canvas file values carry only `url`, no `path`."""
48
+ import io
49
+
50
  if isinstance(image, Image.Image):
51
  return image
52
  if isinstance(image, dict):
53
+ image = image.get("path") or image.get("url") or ""
54
+ if not isinstance(image, str) or not image:
55
+ raise ValueError(f"Unsupported image input: {type(image)!r}")
56
+ if image.startswith("/gradio_api/file="):
57
+ image = urllib.parse.unquote(image.removeprefix("/gradio_api/file="))
58
+ if image.startswith("data:"):
59
+ return Image.open(io.BytesIO(base64.b64decode(image.split(",", 1)[1])))
60
+ if image.startswith(("http://", "https://")):
61
+ return Image.open(io.BytesIO(urllib.request.urlopen(image).read()))
62
+ return Image.open(image)
63
 
64
 
65
  def _save(image: Image.Image) -> dict:
workflow.json CHANGED
@@ -23,7 +23,10 @@
23
  "type": "text",
24
  "default_value": "A capybara wearing a wizard hat, oil painting"
25
  }
26
- ]
 
 
 
27
  },
28
  {
29
  "id": "ref_image",
@@ -45,7 +48,12 @@
45
  "label": "Image",
46
  "type": "image"
47
  }
48
- ]
 
 
 
 
 
49
  },
50
  {
51
  "id": "ref_instruction",
@@ -68,7 +76,10 @@
68
  "type": "text",
69
  "default_value": "Move it to a snowy mountain top"
70
  }
71
- ]
 
 
 
72
  }
73
  ],
74
  "operators": [
@@ -101,7 +112,10 @@
101
  "type": "image",
102
  "output_index": 0
103
  }
104
- ]
 
 
 
105
  },
106
  {
107
  "id": "op_edit",
@@ -138,7 +152,10 @@
138
  "type": "image",
139
  "output_index": 0
140
  }
141
- ]
 
 
 
142
  }
143
  ],
144
  "subjects": [
@@ -221,8 +238,8 @@
221
  "type": "image"
222
  },
223
  {
224
- "id": "e_chain",
225
- "from_node_id": "sub_generated",
226
  "from_port_id": "out",
227
  "to_node_id": "op_edit",
228
  "to_port_id": "image",
 
23
  "type": "text",
24
  "default_value": "A capybara wearing a wizard hat, oil painting"
25
  }
26
+ ],
27
+ "data": {
28
+ "out": "A capybara wearing a wizard hat, oil painting"
29
+ }
30
  },
31
  {
32
  "id": "ref_image",
 
48
  "label": "Image",
49
  "type": "image"
50
  }
51
+ ],
52
+ "data": {
53
+ "out": {
54
+ "url": "https://huggingface.co/datasets/huggingface/documentation-images/resolve/main/diffusers/input_image_vermeer.png"
55
+ }
56
+ }
57
  },
58
  {
59
  "id": "ref_instruction",
 
76
  "type": "text",
77
  "default_value": "Move it to a snowy mountain top"
78
  }
79
+ ],
80
+ "data": {
81
+ "out": "Move it to a snowy mountain top"
82
+ }
83
  }
84
  ],
85
  "operators": [
 
112
  "type": "image",
113
  "output_index": 0
114
  }
115
+ ],
116
+ "data": {
117
+ "steps": 40
118
+ }
119
  },
120
  {
121
  "id": "op_edit",
 
152
  "type": "image",
153
  "output_index": 0
154
  }
155
+ ],
156
+ "data": {
157
+ "steps": 40
158
+ }
159
  }
160
  ],
161
  "subjects": [
 
238
  "type": "image"
239
  },
240
  {
241
+ "id": "e3",
242
+ "from_node_id": "ref_image",
243
  "from_port_id": "out",
244
  "to_node_id": "op_edit",
245
  "to_port_id": "image",