-
Notifications
You must be signed in to change notification settings - Fork 8
Expand file tree
/
Copy pathvace_batch_context.py
More file actions
116 lines (101 loc) · 4.82 KB
/
vace_batch_context.py
File metadata and controls
116 lines (101 loc) · 4.82 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
import os
class WanVACEBatchContext:
@classmethod
def INPUT_TYPES(cls):
return {
"required": {
"input_list": ("STRING", {"forceInput": True}),
"input_dir": ("STRING", {
"default": "",
"tooltip": "Directory containing input videos"
}),
"project_name": ("STRING", {
"default": "",
"tooltip": "Project name - workflow files will be created under ComfyUI/output/project_name."
}),
"index": ("INT", {
"default": 0,
"min": 0,
"tooltip": "Current iteration index (0 based)"
}),
"debug": ("BOOLEAN", {
"default": False,
"tooltip": "Log some details to the console"
}),
"make_loop": ("BOOLEAN", {
"default": False,
"tooltip": "Generate an extra loop-closing transition between the last and first video"
}),
}
}
RETURN_TYPES = ("STRING", "STRING", "STRING", "STRING", "BOOLEAN", "BOOLEAN", "BOOLEAN")
RETURN_NAMES = ("work_dir", "workfile_prefix", "video_1_filename", "video_2_filename", "is_first", "is_last", "assemble_video")
FUNCTION = "setup_context"
CATEGORY = "video/VACE"
DESCRIPTION = """
Establishes iteration context for batch video join processing.
"""
INPUT_IS_LIST = True
def setup_context(self, **kwargs):
# INPUT_IS_LIST=True makes ComfyUI deliver every input as a list.
# The **kwargs signature is required because list-mode inputs can't
# be declared as positional parameters — ComfyUI wraps each value
# in a list, including scalars, so we unwrap with [0] here.
input_dir = kwargs.get('input_dir', [""])[0]
input_list = kwargs.get('input_list', [])
project_name = kwargs.get('project_name', [""])[0].strip()
index = kwargs.get('index', [0])[0]
debug = kwargs.get('debug', [False])[0]
make_loop = kwargs.get('make_loop', [False])[0]
# Validate input list
list_length = len(input_list)
if list_length < 2:
raise ValueError(
f"Need at least 2 videos to create transitions, found {list_length}"
)
# Validate index bounds
max_index = list_length - 1 if make_loop else list_length - 2
if index < 0 or index > max_index:
raise ValueError(
f"Index {index} out of range (valid: 0-{max_index} for {list_length} videos)"
)
# Construct paths — uses forward slashes intentionally; these are
# relative paths for ComfyUI's output system, not OS filesystem paths.
if project_name:
work_dir = f"{project_name}/vace-work"
else:
work_dir = "vace-work"
padded_index = f"{index:03d}"
workfile_prefix = f"{work_dir}/index{padded_index}"
# Set iteration flags
if make_loop:
is_first = False
is_last = False
else:
is_first = (index == 0)
is_last = (index == max_index)
# Extract filenames
if make_loop and index == list_length - 1:
# Loop-closing iteration: last video → first video
v1 = input_list[-1]
v2 = input_list[0]
else:
v1 = input_list[index]
v2 = input_list[index + 1]
video_1_filename = os.path.join(input_dir, v1) if input_dir else v1
video_2_filename = os.path.join(input_dir, v2) if input_dir else v2
assemble_video = (not make_loop and index == list_length - 2) or (make_loop and index == list_length - 1)
if make_loop and index == list_length - 2:
print(f"[VACE Batch Context] Loop enabled: run once more at index {list_length - 1} to generate loop transition.")
if debug:
is_loop_iter = make_loop and index == list_length - 1
print(f"\n[VACE Batch Context] === Start ===")
print(f"[VACE Batch Context] Index: {index} (videos {index+1}-{index+2 if not is_loop_iter else 1} of {list_length}){' [LOOP TRANSITION]' if is_loop_iter else ''}")
if not make_loop:
print(f"[VACE Batch Context] {'[FIRST]' if is_first else ''} {'[LAST]' if is_last else ''}")
print(f"[VACE Batch Context] Input directory: {input_dir}")
print(f"[VACE Batch Context] Video 1: {v1}")
print(f"[VACE Batch Context] Video 2: {v2}")
print(f"[VACE Batch Context] Work prefix: {workfile_prefix}")
print(f"[VACE Batch Context] === End ===")
return (work_dir, workfile_prefix, video_1_filename, video_2_filename, is_first, is_last, assemble_video)