MyoLab-infra commited on
Commit
f5d5899
Β·
1 Parent(s): 6438e61

simplified file management and api error handling

Browse files
Files changed (1) hide show
  1. app.py +10 -71
app.py CHANGED
@@ -21,7 +21,6 @@ from metrabs_pytorch.scripts.run_video import run_metrabs_video
21
  from myo_tools.mjs.marker.marker_api import get_marker_names
22
  from myo_tools.utils.file_ops.dataframe_utils import from_array_to_dataframe
23
  from myosdk import Client
24
- import spaces
25
 
26
  PLOT_CONFIG = {
27
  "plot_bgcolor": "#0f172a",
@@ -31,24 +30,6 @@ PLOT_CONFIG = {
31
  "yaxis": {"gridcolor": "#1e293b", "linecolor": "#334155"},
32
  }
33
 
34
- custom_css = """
35
- .upload-box {
36
- border: 2px dashed #ccc;
37
- border-radius: 8px;
38
- padding: 30px;
39
- text-align: center;
40
- cursor: pointer;
41
- }
42
- .upload-box:hover {
43
- border-color: #666;
44
- }
45
- #file-upload {
46
- position: absolute !important;
47
- opacity: 0 !important;
48
- pointer-events: none !important;
49
- height: 0 !important;
50
- }
51
- """
52
 
53
  DEVICE = "cuda" if torch.cuda.is_available() else "cpu"
54
 
@@ -82,34 +63,6 @@ def save_video_with_keypoints(results, output_video):
82
  return output_video
83
 
84
 
85
- def update_display(files, str_msg="πŸ“ Click to select XML files"):
86
- if files is None:
87
- return f'<div class="upload-box" onclick="document.querySelector(\'input[type=file]\').click()">{str_msg}</div>'
88
-
89
- # Handle single file (not a list) or empty list
90
- if not isinstance(files, list):
91
- files = [files]
92
-
93
- if len(files) == 0:
94
- return f'<div class="upload-box" onclick="document.querySelector(\'input[type=file]\').click()">{str_msg}</div>'
95
-
96
- # Handle both file objects (with .name attribute) and strings (file paths)
97
- filenames = []
98
- for f in files:
99
- if isinstance(f, str):
100
- # If it's a string, extract filename from path
101
- filenames.append(f.split("/")[-1])
102
- elif hasattr(f, "name"):
103
- # If it's a file object with .name attribute
104
- filenames.append(f.name.split("/")[-1])
105
- else:
106
- # Fallback: convert to string and extract filename
107
- filenames.append(str(f).split("/")[-1])
108
-
109
- file_list = "<br>".join([f"βœ“ {name}" for name in filenames])
110
- return f'<div class="upload-box" onclick="document.querySelector(\'input[type=file]\').click()">{file_list}<br><br>Click to reselect</div>'
111
-
112
-
113
  def load_all_videos():
114
  video_dir = os.path.join(os.path.dirname(__file__), "./data")
115
  return [
@@ -130,13 +83,15 @@ def run_retargeting_c3d(api_key, c3d_files, markerset_file):
130
  if not api_key:
131
  api_key = os.getenv("MYOSDK_API_KEY")
132
  if not api_key:
 
133
  yield (
134
- "❌ Error: API key missing",
135
  None,
136
  None,
137
  gr.update(value=[], visible=True),
138
  gr.update(visible=False),
139
  )
 
140
 
141
  if markerset_file is None:
142
  yield (
@@ -266,7 +221,7 @@ def run_retargeting_c3d(api_key, c3d_files, markerset_file):
266
  gr.update(visible=False),
267
  )
268
 
269
- @spaces.GPU
270
  def run_retargeting_video(
271
  api_key,
272
  video_file="",
@@ -278,15 +233,16 @@ def run_retargeting_video(
278
  if not api_key:
279
  api_key = os.getenv("MYOSDK_API_KEY")
280
  if not api_key: # covers None, "", or other falsy values
 
281
  yield (
282
  "❌ Error: API key is missing or invalid",
283
  None,
284
  None,
285
  gr.update(visible=False),
286
  gr.update(visible=False),
287
- None,
288
  )
289
- raise ValueError("❌ Error: API key is missing or invalid")
290
 
291
  # Extract path from list if it's a list, otherwise use directly
292
  if isinstance(video_file, list):
@@ -530,20 +486,11 @@ with gr.Blocks(css=custom_css) as app:
530
  </span>
531
  """
532
  )
533
- upload_markerset_display = gr.HTML(
534
- '<div class="upload-box" onclick="document.querySelector(\'input[type=file]\').click()">πŸ“ Click to select XML file</div>'
535
- )
536
 
537
  markerset = gr.File(
538
- label=None,
539
  file_types=[".xml"],
540
- elem_id="file-upload",
541
- )
542
-
543
- markerset.change(
544
- lambda files: update_display(files, "πŸ“ Click to select XML file"),
545
- [markerset],
546
- upload_markerset_display,
547
  )
548
 
549
  with gr.Column(scale=2):
@@ -557,22 +504,14 @@ with gr.Blocks(css=custom_css) as app:
557
  </span>
558
  """
559
  )
560
- upload_c3d_display = gr.HTML(
561
- '<div class="upload-box" onclick="document.querySelector(\'input[type=file]\').click()">πŸ“ Click to select C3D files</div>'
562
- )
563
 
564
  c3d_files = gr.File(
565
  label=None,
566
  file_types=[".c3d"],
567
- elem_id="file-upload",
568
  file_count="multiple",
569
  )
570
 
571
- c3d_files.change(
572
- lambda files: update_display(files, "πŸ“ Click to select C3D files"),
573
- [c3d_files],
574
- upload_c3d_display,
575
- )
576
  run_btn_c3d = gr.Button("3. πŸš€ Run Retargeting", variant="primary")
577
 
578
  with gr.Tab("πŸŽ₯ Video-Based Motion Retargeting"):
 
21
  from myo_tools.mjs.marker.marker_api import get_marker_names
22
  from myo_tools.utils.file_ops.dataframe_utils import from_array_to_dataframe
23
  from myosdk import Client
 
24
 
25
  PLOT_CONFIG = {
26
  "plot_bgcolor": "#0f172a",
 
30
  "yaxis": {"gridcolor": "#1e293b", "linecolor": "#334155"},
31
  }
32
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
33
 
34
  DEVICE = "cuda" if torch.cuda.is_available() else "cpu"
35
 
 
63
  return output_video
64
 
65
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
66
  def load_all_videos():
67
  video_dir = os.path.join(os.path.dirname(__file__), "./data")
68
  return [
 
83
  if not api_key:
84
  api_key = os.getenv("MYOSDK_API_KEY")
85
  if not api_key:
86
+ gr.Warning("❌ Error: API key is missing!", duration=5)
87
  yield (
88
+ "❌ Error: API key is missing or invalid",
89
  None,
90
  None,
91
  gr.update(value=[], visible=True),
92
  gr.update(visible=False),
93
  )
94
+ return
95
 
96
  if markerset_file is None:
97
  yield (
 
221
  gr.update(visible=False),
222
  )
223
 
224
+
225
  def run_retargeting_video(
226
  api_key,
227
  video_file="",
 
233
  if not api_key:
234
  api_key = os.getenv("MYOSDK_API_KEY")
235
  if not api_key: # covers None, "", or other falsy values
236
+ gr.Warning("❌ Error: API key is missing!", duration=5)
237
  yield (
238
  "❌ Error: API key is missing or invalid",
239
  None,
240
  None,
241
  gr.update(visible=False),
242
  gr.update(visible=False),
243
+ video_file,
244
  )
245
+ return
246
 
247
  # Extract path from list if it's a list, otherwise use directly
248
  if isinstance(video_file, list):
 
486
  </span>
487
  """
488
  )
 
 
 
489
 
490
  markerset = gr.File(
491
+ # label=None,
492
  file_types=[".xml"],
493
+ elem_id="file-upload-markerset",
 
 
 
 
 
 
494
  )
495
 
496
  with gr.Column(scale=2):
 
504
  </span>
505
  """
506
  )
 
 
 
507
 
508
  c3d_files = gr.File(
509
  label=None,
510
  file_types=[".c3d"],
511
+ elem_id="file-upload-c3d",
512
  file_count="multiple",
513
  )
514
 
 
 
 
 
 
515
  run_btn_c3d = gr.Button("3. πŸš€ Run Retargeting", variant="primary")
516
 
517
  with gr.Tab("πŸŽ₯ Video-Based Motion Retargeting"):