Spaces:
Running
on
Zero
Running
on
Zero
Update app.py
Browse files
app.py
CHANGED
@@ -653,31 +653,52 @@ with gr.Blocks(title="Self-Forcing Streaming Demo") as demo:
|
|
653 |
label="Generation Status"
|
654 |
)
|
655 |
|
656 |
-
# Add download button and output
|
657 |
-
download_btn = gr.Button("💾 Download Video", variant="secondary")
|
658 |
-
download_output = gr.File(label="Download")
|
659 |
-
|
660 |
# Define a wrapper function to ensure proper handling of outputs
|
661 |
def safe_frame_generator(p, s, f):
|
662 |
# Clear frames from previous generation
|
663 |
-
APP_STATE
|
664 |
|
665 |
# Reset the final video display
|
666 |
yield None, None, gr.update(visible=False)
|
667 |
|
|
|
|
|
|
|
668 |
# Call the generator function and yield frames, status, and video updates
|
669 |
try:
|
670 |
-
|
671 |
-
|
672 |
-
|
673 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
674 |
|
675 |
-
yield frame, status_html, video_update[0]
|
676 |
except Exception as e:
|
677 |
import traceback
|
678 |
-
print(f"Error in generator: {e}")
|
679 |
traceback.print_exc()
|
680 |
-
error_html = f"<div style='color: red; padding: 10px; border: 1px solid #ffcccc; border-radius: 5px;'>Error: {e}</div>"
|
681 |
yield None, error_html, gr.update(visible=False)
|
682 |
|
683 |
# Connect the generator to the streaming video
|
@@ -687,23 +708,7 @@ with gr.Blocks(title="Self-Forcing Streaming Demo") as demo:
|
|
687 |
outputs=[streaming_video, status_display, final_video]
|
688 |
)
|
689 |
|
690 |
-
#
|
691 |
-
def download_video(fps):
|
692 |
-
if not APP_STATE.get("current_frames"):
|
693 |
-
return None
|
694 |
-
video_path = save_frames_as_video(APP_STATE["current_frames"], fps)
|
695 |
-
return video_path
|
696 |
-
|
697 |
-
# Connect download button
|
698 |
-
download_btn.click(
|
699 |
-
fn=download_video,
|
700 |
-
inputs=[fps],
|
701 |
-
outputs=[download_output],
|
702 |
-
show_progress=True,
|
703 |
-
api_name="download_video" # Make it accessible via API
|
704 |
-
)
|
705 |
-
|
706 |
-
# Make the FPS slider visible for download quality control
|
707 |
fps.visible = True
|
708 |
|
709 |
enhance_button.click(
|
|
|
653 |
label="Generation Status"
|
654 |
)
|
655 |
|
|
|
|
|
|
|
|
|
656 |
# Define a wrapper function to ensure proper handling of outputs
|
657 |
def safe_frame_generator(p, s, f):
|
658 |
# Clear frames from previous generation
|
659 |
+
APP_STATE["current_frames"] = []
|
660 |
|
661 |
# Reset the final video display
|
662 |
yield None, None, gr.update(visible=False)
|
663 |
|
664 |
+
# Collect all frames from this generation
|
665 |
+
collected_frames = []
|
666 |
+
|
667 |
# Call the generator function and yield frames, status, and video updates
|
668 |
try:
|
669 |
+
# Set save_frames=True to explicitly ensure frames are collected
|
670 |
+
for frame, status_html in video_generation_handler_streaming(p, s, f, save_frames=True):
|
671 |
+
# Track frames for this specific session
|
672 |
+
if frame is not None and isinstance(frame, np.ndarray):
|
673 |
+
collected_frames.append(frame.copy())
|
674 |
+
|
675 |
+
# Show status update during generation
|
676 |
+
yield frame, status_html, gr.update(visible=False)
|
677 |
+
|
678 |
+
# Check if this is the final frame
|
679 |
+
if "Complete" in str(status_html) or "100%" in str(status_html):
|
680 |
+
# Create the final video
|
681 |
+
if collected_frames:
|
682 |
+
print(f"Creating final video from {len(collected_frames)} frames at {f} FPS")
|
683 |
+
temp_file = save_frames_as_video(collected_frames, f)
|
684 |
+
if temp_file:
|
685 |
+
# Save these frames as the current set
|
686 |
+
APP_STATE["current_frames"] = collected_frames
|
687 |
+
yield frame, status_html, gr.update(visible=True, value=temp_file)
|
688 |
+
else:
|
689 |
+
yield frame, status_html, gr.update(visible=False)
|
690 |
+
|
691 |
+
# Ensure final frame is properly handled
|
692 |
+
if collected_frames and "Complete" not in str(status_html) and "100%" not in str(status_html):
|
693 |
+
print(f"Generation complete, creating final video from {len(collected_frames)} frames")
|
694 |
+
temp_file = save_frames_as_video(collected_frames, f)
|
695 |
+
if temp_file:
|
696 |
+
yield frame, status_html, gr.update(visible=True, value=temp_file)
|
697 |
|
|
|
698 |
except Exception as e:
|
699 |
import traceback
|
|
|
700 |
traceback.print_exc()
|
701 |
+
error_html = f"<div style='color: red; padding: 10px; border: 1px solid #ffcccc; border-radius: 5px;'>Error: {str(e)}</div>"
|
702 |
yield None, error_html, gr.update(visible=False)
|
703 |
|
704 |
# Connect the generator to the streaming video
|
|
|
708 |
outputs=[streaming_video, status_display, final_video]
|
709 |
)
|
710 |
|
711 |
+
# Make the FPS slider visible for video quality control
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
712 |
fps.visible = True
|
713 |
|
714 |
enhance_button.click(
|