luh1124 commited on
Commit
71ce4de
Β·
1 Parent(s): a2f3bcf

ui: remove PBR GLB export from online demo

Browse files

- Remove generate_glb callback, btn_glb, glb_view, simplify/tex_size sliders.
- Move vid_hdri into the top row next to mesh_view.
- Add note: PBR GLB export is disabled on the online demo; use local
inference (example.py) for full material export.
- Pipeline code under trellis/ is untouched.

Files changed (1) hide show
  1. app.py +8 -97
app.py CHANGED
@@ -599,90 +599,6 @@ def generate_videos(
599
  return str(p_cam), str(p_hdri), str(p_roll), msg
600
 
601
 
602
- @GPU
603
- def generate_glb(
604
- asset_state: Dict[str, Any],
605
- hdri_file_obj: Any,
606
- hdri_rot: float,
607
- simplify: float,
608
- texture_size: int,
609
- req: gr.Request,
610
- progress: gr.Progress = gr.Progress(track_tqdm=True),
611
- ) -> tuple[str, str]:
612
- """β‘£ Export PBR GLB (baked texture + simplified mesh).
613
-
614
- Separate @GPU callback so the heavy mesh simplification does not
615
- blow the 120 s budget shared with video rendering.
616
- Returns: (pbr_glb, status_msg)
617
- """
618
- slat_path = _require_slat(asset_state)
619
- hdri_path = _require_hdri(hdri_file_obj)
620
- session_dir = CACHE_DIR / str(req.session_hash)
621
-
622
- progress(0.05, desc="Loading NeAR on GPU")
623
- pipe = _ensure_near_on_cuda()
624
-
625
- progress(0.15, desc="Loading SLaT / HDRI / mesh")
626
- slat = pipe.load_slat(slat_path)
627
- hdri_np = _load_hdri_resized(pipe, hdri_path)
628
-
629
- mesh_path = asset_state.get("mesh_path")
630
- base_mesh: Optional[trimesh.Trimesh] = None
631
- if mesh_path and os.path.isfile(mesh_path):
632
- print(f"[NeAR] loading Hunyuan mesh from {mesh_path}…", flush=True)
633
- raw = trimesh.load(mesh_path, force="mesh")
634
- print(f"[NeAR] raw mesh bounds: {raw.bounds[0].round(3)} β†’ {raw.bounds[1].round(3)}", flush=True)
635
- base_mesh = _hunyuan_mesh_to_renderer_space(raw)
636
- del raw
637
- else:
638
- print("[NeAR] no mesh_path β€” will use SLaT decoder mesh for GLB", flush=True)
639
-
640
- progress(0.30, desc="Baking PBR GLB…")
641
- glb = pipe.export_glb_from_slat(
642
- slat, hdri_np,
643
- hdri_rot_deg=float(hdri_rot),
644
- base_mesh=base_mesh,
645
- simplify=float(simplify),
646
- texture_size=int(texture_size),
647
- fill_holes=True,
648
- )
649
- del slat, hdri_np, base_mesh
650
- _free_cuda()
651
-
652
- out_path = session_dir / "near_pbr.glb"
653
- glb.export(out_path)
654
- del glb
655
-
656
- _teardown_near()
657
-
658
- msg = f"**β‘£ PBR GLB ready** β†’ `{Path(out_path).name}`"
659
- return str(out_path), msg
660
-
661
-
662
- def _hunyuan_mesh_to_renderer_space(mesh: trimesh.Trimesh) -> trimesh.Trimesh:
663
- """Transform a Hunyuan3D output mesh into the coordinate space expected by
664
- NeAR's renderer / shape_to_coords: Y-up β†’ Z-up, scale to [-0.5, 0.5]Β³.
665
-
666
- Hunyuan outputs: Y-up, vertices in ~[-1.01, 1.01]Β³.
667
- NeAR renderer: Z-up, vertices in [-0.5, 0.5]Β³.
668
- """
669
- mesh = mesh.copy()
670
- # Y-up β†’ Z-up
671
- R = trimesh.transformations.rotation_matrix(np.pi / 2, [1, 0, 0])
672
- mesh.apply_transform(R)
673
- # [-1.01,1.01] β†’ [-0.5,0.5] (multiply by 0.5, same as shape_to_coords)
674
- mesh.vertices = mesh.vertices * 0.5
675
-
676
- bounds = mesh.bounds # [[xmin,ymin,zmin],[xmax,ymax,zmax]]
677
- print(
678
- f"[NeAR] base_mesh after transform: "
679
- f"bounds={bounds[0].round(3)} β†’ {bounds[1].round(3)}, "
680
- f"vertices={len(mesh.vertices)}, faces={len(mesh.faces)}",
681
- flush=True,
682
- )
683
- return mesh
684
-
685
-
686
  def clear_cache(req: gr.Request) -> str:
687
  """Clear session cache and free GPU memory."""
688
  session_dir = CACHE_DIR / str(req.session_hash)
@@ -794,10 +710,12 @@ def build_app() -> gr.Blocks:
794
 
795
  gr.Markdown(
796
  "## NeAR β€” Image-to-Relightable 3D Gaussian Splatting\n"
797
- "**β‘  Geometry** β†’ **β‘‘ SLaT** β†’ **β‘’ Videos** β†’ **β‘£ PBR GLB**\n\n"
798
- "Upload an image and walk through the four steps. "
799
  "Geometry and appearance are decoupled β€” after step β‘  you can swap the input image "
800
- "before step β‘‘ to retexture the same mesh with a different style."
 
 
801
  )
802
 
803
  with gr.Row(equal_height=False):
@@ -837,8 +755,7 @@ def build_app() -> gr.Blocks:
837
 
838
  gr.HTML('<p class="section-kicker" style="margin:2px 0 2px;padding:0">Actions</p>')
839
  btn_videos = gr.Button("β‘’ Generate Videos", variant="primary")
840
- btn_glb = gr.Button("β‘£ Export PBR GLB", variant="primary")
841
- with gr.Accordion("Video / export settings", open=False):
842
  fps = gr.Slider(8, 48, value=24, step=1, label="FPS")
843
  num_cam = gr.Slider(8, 96, value=48, step=2, label="Camera-orbit frames")
844
  num_hdri = gr.Slider(8, 96, value=48, step=2, label="HDRI-rotation frames")
@@ -848,8 +765,6 @@ def build_app() -> gr.Blocks:
848
  with gr.Row():
849
  fov = gr.Slider(10, 70, value=40, step=1, label="FoV")
850
  radius = gr.Slider(1.0, 4.0, value=2.0, step=0.05, label="Radius")
851
- simplify = gr.Slider(0.80, 0.99, value=0.85, step=0.01, label="GLB simplify ratio")
852
- tex_size = gr.Slider(512, 2048, value=1024, step=512, label="Texture resolution")
853
  btn_clear = gr.Button("Clear session cache", variant="secondary")
854
 
855
  # ── CENTER: linear output area ────────────────────────────────────
@@ -861,12 +776,11 @@ def build_app() -> gr.Blocks:
861
 
862
  with gr.Row():
863
  mesh_view = gr.Model3D(label="β‘  Geometry", height=250)
864
- glb_view = gr.Model3D(label="β‘£ PBR GLB (download)", height=250)
 
865
 
866
  vid_cam = gr.Video(label="β‘’ Camera orbit",
867
  autoplay=True, loop=True, height=250)
868
- vid_hdri = gr.Video(label="β‘’ HDRI rotation",
869
- autoplay=True, loop=True, height=250)
870
 
871
  with gr.Accordion("HDRI env roll", open=False):
872
  vid_roll = gr.Video(label="β‘’ HDRI env roll",
@@ -906,9 +820,6 @@ def build_app() -> gr.Blocks:
906
  btn_videos.click(generate_videos,
907
  [asset_state, hdri_file, hdri_rot, fps, num_cam, num_hdri, yaw, pitch, fov, radius],
908
  [vid_cam, vid_hdri, vid_roll, status])
909
- btn_glb.click(generate_glb,
910
- [asset_state, hdri_file, hdri_rot, simplify, tex_size],
911
- [glb_view, status])
912
  btn_clear.click(clear_cache, [], [status])
913
 
914
  return demo
 
599
  return str(p_cam), str(p_hdri), str(p_roll), msg
600
 
601
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
602
  def clear_cache(req: gr.Request) -> str:
603
  """Clear session cache and free GPU memory."""
604
  session_dir = CACHE_DIR / str(req.session_hash)
 
710
 
711
  gr.Markdown(
712
  "## NeAR β€” Image-to-Relightable 3D Gaussian Splatting\n"
713
+ "**β‘  Geometry** β†’ **β‘‘ SLaT** β†’ **β‘’ Videos**\n\n"
714
+ "Upload an image and walk through the three steps. "
715
  "Geometry and appearance are decoupled β€” after step β‘  you can swap the input image "
716
+ "before step β‘‘ to retexture the same mesh with a different style.\n\n"
717
+ "> πŸ’‘ **PBR GLB export** is disabled on this online demo due to bake-time limits. "
718
+ "Run the local inference script (`example.py`) for full PBR material export."
719
  )
720
 
721
  with gr.Row(equal_height=False):
 
755
 
756
  gr.HTML('<p class="section-kicker" style="margin:2px 0 2px;padding:0">Actions</p>')
757
  btn_videos = gr.Button("β‘’ Generate Videos", variant="primary")
758
+ with gr.Accordion("Video settings", open=False):
 
759
  fps = gr.Slider(8, 48, value=24, step=1, label="FPS")
760
  num_cam = gr.Slider(8, 96, value=48, step=2, label="Camera-orbit frames")
761
  num_hdri = gr.Slider(8, 96, value=48, step=2, label="HDRI-rotation frames")
 
765
  with gr.Row():
766
  fov = gr.Slider(10, 70, value=40, step=1, label="FoV")
767
  radius = gr.Slider(1.0, 4.0, value=2.0, step=0.05, label="Radius")
 
 
768
  btn_clear = gr.Button("Clear session cache", variant="secondary")
769
 
770
  # ── CENTER: linear output area ────────────────────────────────────
 
776
 
777
  with gr.Row():
778
  mesh_view = gr.Model3D(label="β‘  Geometry", height=250)
779
+ vid_hdri = gr.Video(label="β‘’ HDRI rotation",
780
+ autoplay=True, loop=True, height=250)
781
 
782
  vid_cam = gr.Video(label="β‘’ Camera orbit",
783
  autoplay=True, loop=True, height=250)
 
 
784
 
785
  with gr.Accordion("HDRI env roll", open=False):
786
  vid_roll = gr.Video(label="β‘’ HDRI env roll",
 
820
  btn_videos.click(generate_videos,
821
  [asset_state, hdri_file, hdri_rot, fps, num_cam, num_hdri, yaw, pitch, fov, radius],
822
  [vid_cam, vid_hdri, vid_roll, status])
 
 
 
823
  btn_clear.click(clear_cache, [], [status])
824
 
825
  return demo