HongzeFu commited on
Commit
a7b9f8e
·
1 Parent(s): 9aca6ab

text size control

Browse files
gradio-web/config.py CHANGED
@@ -15,6 +15,9 @@ CONTROL_PANEL_SCALE = 2
15
  RIGHT_TOP_ACTION_SCALE = 2
16
  RIGHT_TOP_LOG_SCALE = 1
17
 
 
 
 
18
  # Session超时配置
19
  SESSION_TIMEOUT = 300 # Session超时时间(秒),如果30秒内没有execute_step操作,将自动回收session
20
 
 
15
  RIGHT_TOP_ACTION_SCALE = 2
16
  RIGHT_TOP_LOG_SCALE = 1
17
 
18
+ # 全局界面字号(不作用于页面主标题)
19
+ UI_GLOBAL_FONT_SIZE = "20px"
20
+
21
  # Session超时配置
22
  SESSION_TIMEOUT = 300 # Session超时时间(秒),如果30秒内没有execute_step操作,将自动回收session
23
 
gradio-web/test/test_ui_native_layout_contract.py CHANGED
@@ -23,6 +23,28 @@ def test_native_ui_has_no_legacy_runtime_js_or_card_shell_tokens(reload_module):
23
  assert token not in css
24
 
25
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
26
  def test_extract_last_goal_prefers_last_list_item(reload_module):
27
  ui_layout = reload_module("ui_layout")
28
 
 
23
  assert token not in css
24
 
25
 
26
+ def test_native_ui_css_uses_configured_global_font_size_variables(reload_module):
27
+ config = reload_module("config")
28
+ ui_layout = reload_module("ui_layout")
29
+
30
+ css = ui_layout.CSS
31
+
32
+ assert f"--body-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
33
+ assert f"--prose-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
34
+ assert f"--input-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
35
+ assert f"--block-label-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
36
+ assert f"--button-large-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
37
+ assert f"--section-header-text-size: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
38
+ assert f"--text-md: {config.UI_GLOBAL_FONT_SIZE} !important;" in css
39
+
40
+
41
+ def test_native_ui_css_excludes_header_title_from_global_font_size(reload_module):
42
+ ui_layout = reload_module("ui_layout")
43
+
44
+ assert "#header_title h2" in ui_layout.CSS
45
+ assert "font-size: var(--text-xxl) !important;" in ui_layout.CSS
46
+
47
+
48
  def test_extract_last_goal_prefers_last_list_item(reload_module):
49
  ui_layout = reload_module("ui_layout")
50
 
gradio-web/test/test_ui_phase_machine_runtime_e2e.py CHANGED
@@ -124,6 +124,54 @@ def _read_live_obs_geometry(page) -> dict[str, dict[str, float] | None]:
124
  )
125
 
126
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
127
  @pytest.fixture
128
  def phase_machine_ui_url():
129
  state = {"precheck_calls": 0}
@@ -292,6 +340,41 @@ def phase_machine_ui_url():
292
  demo.close()
293
 
294
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
295
  def test_phase_machine_runtime_flow_and_execute_precheck(phase_machine_ui_url):
296
  root_url, state = phase_machine_ui_url
297
 
 
124
  )
125
 
126
 
127
+ def _read_font_probe_snapshot(page) -> dict[str, str | None]:
128
+ return page.evaluate(
129
+ """() => {
130
+ const heading = document.querySelector('#header_title h2');
131
+ const field = document.querySelector('#font_probe textarea, #font_probe input');
132
+ const prose = document.querySelector('#body_probe p');
133
+ const readSize = (node) => (node ? getComputedStyle(node).fontSize : null);
134
+ return {
135
+ header: readSize(heading),
136
+ field: readSize(field),
137
+ body: readSize(prose),
138
+ };
139
+ }"""
140
+ )
141
+
142
+
143
+ @pytest.fixture
144
+ def font_size_probe_ui_url(monkeypatch):
145
+ config_module = importlib.reload(importlib.import_module("config"))
146
+ monkeypatch.setattr(config_module, "UI_GLOBAL_FONT_SIZE", "32px")
147
+ ui_layout = importlib.reload(importlib.import_module("ui_layout"))
148
+
149
+ with contextlib.closing(socket.socket(socket.AF_INET, socket.SOCK_STREAM)) as sock:
150
+ sock.bind(("127.0.0.1", 0))
151
+ port = int(sock.getsockname()[1])
152
+
153
+ with gr.Blocks(title="Native font size probe test") as demo:
154
+ gr.Markdown("## RoboMME Human Evaluation", elem_id="header_title")
155
+ gr.Textbox(value="font probe", label="Probe", elem_id="font_probe")
156
+ gr.Markdown("Probe body text", elem_id="body_probe")
157
+
158
+ _app, root_url, _share_url = demo.launch(
159
+ server_name="127.0.0.1",
160
+ server_port=port,
161
+ prevent_thread_lock=True,
162
+ quiet=True,
163
+ show_error=True,
164
+ ssr_mode=False,
165
+ css=ui_layout.CSS,
166
+ )
167
+ _wait_http_ready(root_url)
168
+
169
+ try:
170
+ yield root_url
171
+ finally:
172
+ demo.close()
173
+
174
+
175
  @pytest.fixture
176
  def phase_machine_ui_url():
177
  state = {"precheck_calls": 0}
 
340
  demo.close()
341
 
342
 
343
+ def test_global_font_size_applies_except_header_title(font_size_probe_ui_url):
344
+ root_url = font_size_probe_ui_url
345
+
346
+ with sync_playwright() as p:
347
+ browser = p.chromium.launch(headless=True)
348
+ page = browser.new_page(viewport={"width": 1280, "height": 900})
349
+ page.goto(root_url, wait_until="domcontentloaded")
350
+
351
+ page.wait_for_selector("#header_title h2", timeout=10000)
352
+ page.wait_for_selector("#font_probe textarea, #font_probe input", timeout=10000)
353
+ page.wait_for_selector("#body_probe p", timeout=10000)
354
+ page.wait_for_function(
355
+ """() => {
356
+ const heading = document.querySelector('#header_title h2');
357
+ const field = document.querySelector('#font_probe textarea, #font_probe input');
358
+ const prose = document.querySelector('#body_probe p');
359
+ if (!heading || !field || !prose) return false;
360
+ return (
361
+ getComputedStyle(heading).fontSize === '26px' &&
362
+ getComputedStyle(field).fontSize === '32px' &&
363
+ getComputedStyle(prose).fontSize === '32px'
364
+ );
365
+ }""",
366
+ timeout=10000,
367
+ )
368
+
369
+ snapshot = _read_font_probe_snapshot(page)
370
+ assert snapshot["header"] == "26px"
371
+ assert snapshot["field"] == "32px"
372
+ assert snapshot["body"] == "32px"
373
+ assert snapshot["header"] != snapshot["field"]
374
+
375
+ browser.close()
376
+
377
+
378
  def test_phase_machine_runtime_flow_and_execute_precheck(phase_machine_ui_url):
379
  root_url, state = phase_machine_ui_url
380
 
gradio-web/ui_layout.py CHANGED
@@ -14,6 +14,7 @@ from config import (
14
  KEYPOINT_SELECTION_SCALE,
15
  RIGHT_TOP_ACTION_SCALE,
16
  RIGHT_TOP_LOG_SCALE,
 
17
  )
18
  from gradio_callbacks import (
19
  execute_step,
@@ -194,9 +195,28 @@ LIVE_OBS_CLIENT_RESIZE_JS = r"""
194
 
195
 
196
  CSS = f"""
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
197
  .native-card {{
198
  }}
199
 
 
 
 
 
200
  #loading_overlay_group {{
201
  position: fixed !important;
202
  inset: 0 !important;
@@ -289,16 +309,15 @@ def create_ui_blocks():
289
  return last_goal if last_goal else "—"
290
 
291
  with gr.Blocks(title="Oracle Planner Interface") as demo:
292
- demo.theme = gr.themes.Soft()
293
  demo.css = CSS
294
 
295
- gr.Markdown("## RoboMME Human Evaluation", elem_id="header_title")
296
  with gr.Row():
297
  with gr.Column(scale=1):
298
  header_task_box = gr.Dropdown(
299
  choices=list(user_manager.env_choices),
300
  value=render_header_task(""),
301
- label="Current Task",
302
  show_label=True,
303
  interactive=True,
304
  elem_id="header_task",
@@ -306,7 +325,7 @@ def create_ui_blocks():
306
  with gr.Column(scale=2):
307
  header_goal_box = gr.Textbox(
308
  value=render_header_goal(""),
309
- label="Goal",
310
  show_label=True,
311
  interactive=False,
312
  lines=1,
@@ -330,7 +349,7 @@ def create_ui_blocks():
330
  with gr.Column(elem_classes=["native-card"], elem_id="media_card"):
331
  with gr.Column(visible=False, elem_id="video_phase_group") as video_phase_group:
332
  video_display = gr.Video(
333
- label="Demonstration Video",
334
  interactive=False,
335
  elem_id="demo_video",
336
  autoplay=True,
@@ -357,7 +376,7 @@ def create_ui_blocks():
357
  with gr.Column(elem_classes=["native-card"], elem_id="action_selection_card"):
358
  options_radio = gr.Radio(
359
  choices=[],
360
- label=" Action Selection",
361
  type="value",
362
  show_label=True,
363
  elem_id="action_radio",
@@ -380,19 +399,19 @@ def create_ui_blocks():
380
  show_label=True,
381
  interactive=False,
382
  elem_id="log_output",
383
- label="System Log",
384
  )
385
 
386
  with gr.Row(elem_id="action_buttons_row"):
387
  with gr.Column(elem_classes=["native-card", "native-button-card"], elem_id="exec_btn_card"):
388
- exec_btn = gr.Button("EXECUTE", variant="stop", size="lg", elem_id="exec_btn")
389
 
390
  with gr.Column(
391
  elem_classes=["native-card", "native-button-card"],
392
  elem_id="reference_btn_card",
393
  ):
394
  reference_action_btn = gr.Button(
395
- "Ground Truth Action",
396
  variant="secondary",
397
  interactive=False,
398
  elem_id="reference_action_btn",
@@ -403,7 +422,7 @@ def create_ui_blocks():
403
  elem_id="restart_episode_btn_card",
404
  ):
405
  restart_episode_btn = gr.Button(
406
- "restart episode",
407
  variant="secondary",
408
  interactive=False,
409
  elem_id="restart_episode_btn",
@@ -414,7 +433,7 @@ def create_ui_blocks():
414
  elem_id="next_task_btn_card",
415
  ):
416
  next_task_btn = gr.Button(
417
- "change episode",
418
  variant="primary",
419
  interactive=False,
420
  elem_id="next_task_btn",
@@ -426,7 +445,7 @@ def create_ui_blocks():
426
  lines=8,
427
  max_lines=16,
428
  show_label=True,
429
- label="Task Hint",
430
  interactive=True,
431
  elem_id="task_hint_display",
432
  )
 
14
  KEYPOINT_SELECTION_SCALE,
15
  RIGHT_TOP_ACTION_SCALE,
16
  RIGHT_TOP_LOG_SCALE,
17
+ UI_GLOBAL_FONT_SIZE,
18
  )
19
  from gradio_callbacks import (
20
  execute_step,
 
195
 
196
 
197
  CSS = f"""
198
+ :root {{
199
+ --body-text-size: {UI_GLOBAL_FONT_SIZE} !important;
200
+ --prose-text-size: {UI_GLOBAL_FONT_SIZE} !important;
201
+ --input-text-size: {UI_GLOBAL_FONT_SIZE} !important;
202
+ --block-label-text-size: {UI_GLOBAL_FONT_SIZE} !important;
203
+ --block-title-text-size: {UI_GLOBAL_FONT_SIZE} !important;
204
+ --block-info-text-size: {UI_GLOBAL_FONT_SIZE} !important;
205
+ --checkbox-label-text-size: {UI_GLOBAL_FONT_SIZE} !important;
206
+ --button-large-text-size: {UI_GLOBAL_FONT_SIZE} !important;
207
+ --button-medium-text-size: {UI_GLOBAL_FONT_SIZE} !important;
208
+ --button-small-text-size: {UI_GLOBAL_FONT_SIZE} !important;
209
+ --section-header-text-size: {UI_GLOBAL_FONT_SIZE} !important;
210
+ --text-md: {UI_GLOBAL_FONT_SIZE} !important;
211
+ }}
212
+
213
  .native-card {{
214
  }}
215
 
216
+ #header_title h2 {{
217
+ font-size: var(--text-xxl) !important;
218
+ }}
219
+
220
  #loading_overlay_group {{
221
  position: fixed !important;
222
  inset: 0 !important;
 
309
  return last_goal if last_goal else "—"
310
 
311
  with gr.Blocks(title="Oracle Planner Interface") as demo:
 
312
  demo.css = CSS
313
 
314
+ gr.Markdown("## RoboMME Human Evaluation 🚀🚀🚀", elem_id="header_title")
315
  with gr.Row():
316
  with gr.Column(scale=1):
317
  header_task_box = gr.Dropdown(
318
  choices=list(user_manager.env_choices),
319
  value=render_header_task(""),
320
+ label="Current Task 🔥",
321
  show_label=True,
322
  interactive=True,
323
  elem_id="header_task",
 
325
  with gr.Column(scale=2):
326
  header_goal_box = gr.Textbox(
327
  value=render_header_goal(""),
328
+ label="Goal 🎯",
329
  show_label=True,
330
  interactive=False,
331
  lines=1,
 
349
  with gr.Column(elem_classes=["native-card"], elem_id="media_card"):
350
  with gr.Column(visible=False, elem_id="video_phase_group") as video_phase_group:
351
  video_display = gr.Video(
352
+ label="Demonstration Video 🎬",
353
  interactive=False,
354
  elem_id="demo_video",
355
  autoplay=True,
 
376
  with gr.Column(elem_classes=["native-card"], elem_id="action_selection_card"):
377
  options_radio = gr.Radio(
378
  choices=[],
379
+ label="Action Selection 🦾",
380
  type="value",
381
  show_label=True,
382
  elem_id="action_radio",
 
399
  show_label=True,
400
  interactive=False,
401
  elem_id="log_output",
402
+ label="System Log📝",
403
  )
404
 
405
  with gr.Row(elem_id="action_buttons_row"):
406
  with gr.Column(elem_classes=["native-card", "native-button-card"], elem_id="exec_btn_card"):
407
+ exec_btn = gr.Button("EXECUTE 🤖", variant="stop", size="lg", elem_id="exec_btn")
408
 
409
  with gr.Column(
410
  elem_classes=["native-card", "native-button-card"],
411
  elem_id="reference_btn_card",
412
  ):
413
  reference_action_btn = gr.Button(
414
+ "Ground Truth Action 🙋‍♀️",
415
  variant="secondary",
416
  interactive=False,
417
  elem_id="reference_action_btn",
 
422
  elem_id="restart_episode_btn_card",
423
  ):
424
  restart_episode_btn = gr.Button(
425
+ "Restart Episode 🔄",
426
  variant="secondary",
427
  interactive=False,
428
  elem_id="restart_episode_btn",
 
433
  elem_id="next_task_btn_card",
434
  ):
435
  next_task_btn = gr.Button(
436
+ "Change Episode ⏩️",
437
  variant="primary",
438
  interactive=False,
439
  elem_id="next_task_btn",
 
445
  lines=8,
446
  max_lines=16,
447
  show_label=True,
448
+ label="Task Hint💡",
449
  interactive=True,
450
  elem_id="task_hint_display",
451
  )
pyproject.toml CHANGED
@@ -5,15 +5,21 @@ description = "Add your description here"
5
  readme = "README.md"
6
  requires-python = ">=3.11"
7
  dependencies = [
 
 
 
 
8
  "mani-skill",
 
9
  "opencv-python>=4.11.0.86",
 
10
  "setuptools==80.9.0",
11
  "torch==2.9.1",
12
  "torchvision==0.24.1",
13
  ]
14
 
15
  [project.optional-dependencies]
16
- dev = ["opencv-python", "pytest"]
17
 
18
  [tool.uv.sources]
19
  mani-skill = { git = "https://github.com/YinpeiDai/ManiSkill.git", rev = "07be6fbc66350ddca200abfb0a11b692f078f7fd" }
 
5
  readme = "README.md"
6
  requires-python = ">=3.11"
7
  dependencies = [
8
+ "gradio",
9
+ "gymnasium",
10
+ "h5py",
11
+ "imageio",
12
  "mani-skill",
13
+ "numpy",
14
  "opencv-python>=4.11.0.86",
15
+ "Pillow",
16
  "setuptools==80.9.0",
17
  "torch==2.9.1",
18
  "torchvision==0.24.1",
19
  ]
20
 
21
  [project.optional-dependencies]
22
+ dev = ["opencv-python", "playwright", "pytest", "uvicorn"]
23
 
24
  [tool.uv.sources]
25
  mani-skill = { git = "https://github.com/YinpeiDai/ManiSkill.git", rev = "07be6fbc66350ddca200abfb0a11b692f078f7fd" }
uv.lock CHANGED
The diff for this file is too large to render. See raw diff