| from __future__ import annotations |
|
|
|
|
| CONDITION_PIPELINE_MODES = frozenset({"FLF2V", "KEYFRAME", "KEYFRAME_FLF2V"}) |
| INVALID_CONDITION_MODE = "INVALID_CONDITION_WITHOUT_START" |
|
|
|
|
| def mode_from_condition_images(start_image_path, middle_image_path, end_image_path) -> str: |
| """Resolve the product conditioning mode without touching media bytes.""" |
| if (middle_image_path or end_image_path) and not start_image_path: |
| return INVALID_CONDITION_MODE |
| if start_image_path and middle_image_path and end_image_path: |
| return "KEYFRAME_FLF2V" |
| if start_image_path and middle_image_path: |
| return "KEYFRAME" |
| if start_image_path and end_image_path: |
| return "FLF2V" |
| if start_image_path: |
| return "I2V" |
| return "T2V" |
|
|
|
|
| def conditioning_mode_status_markdown(start_image_path, middle_image_path, end_image_path) -> str: |
| """Human-readable live summary of the mode inferred from conditioning inputs.""" |
| mode = mode_from_condition_images(start_image_path, middle_image_path, end_image_path) |
| labels = { |
| "T2V": "T2V · text only", |
| "I2V": "I2V · Start frame", |
| "FLF2V": "FLF2V · Start + End frames", |
| "KEYFRAME": "Keyframe · Start + Middle frames", |
| "KEYFRAME_FLF2V": "Keyframe + FLF2V · Start + Middle + End frames", |
| INVALID_CONDITION_MODE: "Invalid · Middle/End requires a Start frame", |
| } |
| return f"**Detected mode:** {labels[mode]}" |
|
|
|
|
| def uses_condition_pipeline(mode: str) -> bool: |
| return str(mode) in CONDITION_PIPELINE_MODES |
|
|
|
|
| def middle_keyframe_latent_index(num_frames: int, temporal_ratio: int = 8) -> int: |
| """Nearest non-zero latent index to the pixel-space timeline midpoint.""" |
| frames = int(num_frames) |
| ratio = int(temporal_ratio) |
| if frames < 3 or ratio < 1: |
| raise ValueError("middle keyframe requires a positive temporal grid") |
| latent_num_frames = (frames - 1) // ratio + 1 |
| if latent_num_frames < 3: |
| raise ValueError("video is too short to place a distinct middle keyframe") |
| target_pixel_frame = (frames - 1) // 2 |
| |
| nearest = ((max(0, target_pixel_frame - 1) + ratio // 2) // ratio) + 1 |
| return max(1, min(latent_num_frames - 2, int(nearest))) |
|
|
|
|
| def keyframe_pixel_frame_index(latent_index: int, temporal_ratio: int = 8) -> int: |
| idx = int(latent_index) |
| ratio = int(temporal_ratio) |
| if idx <= 0: |
| return 0 |
| return (idx - 1) * ratio + 1 |
|
|