Skip to content

Commit fc021ee

Browse files
committed
wip parser.py
1 parent 278111f commit fc021ee

2 files changed

Lines changed: 22 additions & 9 deletions

File tree

src/ffmpegio/utils/parser.py

Lines changed: 16 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
from collections import abc
33

44
from ..filtergraph import Graph, Chain, Filter
5+
from ..filtergraph.abc import FilterGraphObject
56
from .. import devices
67

78
__all__ = ["parse", "compose", "FLAG"]
@@ -84,7 +85,11 @@ def parse(cmdline):
8485
elif all_gopts[k] is FLAG:
8586
gopts[k] = FLAG
8687
else:
87-
gopts[k] = args[i + 1]
88+
if k == "filter_complex" and isinstance(gopts.get(k, None), str):
89+
# if more than 1 filter_complex, return a list instead
90+
gopts[k] = [gopts[k], args[i + 1]]
91+
else:
92+
gopts[k] = args[i + 1]
8893
is_lopt[i + 1] = False
8994

9095
args = [s for s, tf in zip(args, is_lopt) if tf]
@@ -137,20 +142,20 @@ def compose(args, command="", shell_command=False):
137142
138143
If global_options is None and only 1 output file given, FFmpeg global options
139144
may be specified as additional output options.
145+
140146
"""
141147

142148
def finalize_global(key, val):
149+
if key == "filter_complex" and not isinstance(val, (str, FilterGraphObject, list)):
150+
val = list(val)
143151
return key, val
144152

145153
def finalize_output(key, val):
146154
if re.match(r"s(?:\:|$)", key) and not isinstance(val, str):
147155
val = "x".join((str(v) for v in val))
148-
elif key == "map" and not isinstance(val, str):
149-
# if an entry is a seq, join with ':'
150-
val = [
151-
v if isinstance(v, str) else ":".join((str(vi) for vi in v))
152-
for v in val
153-
]
156+
elif key == "map" and not isinstance(val, str, int, list):
157+
# multiple stream mapping, must be a list
158+
val = list(val)
154159
return key, val
155160

156161
def finalize_input(key, val):
@@ -166,6 +171,8 @@ def opts2args(opts, finalize):
166171
opts_parsed = {}
167172
for itm in opts.items():
168173
k, v = finalize(*itm)
174+
# if isinstance(v,list):
175+
# # multiple option values
169176
oname, *sspec = k.split(":", 1)
170177
o = opts_parsed.get(oname, None)
171178
if o is None:
@@ -194,7 +201,7 @@ def set_arg(karg, val):
194201

195202
return args
196203

197-
def inputs2args(inputs):
204+
def inputs2args(inputs)->list[str]:
198205
args = []
199206
for url, opts in inputs:
200207
# resolve url enumeration if it's a device
@@ -210,7 +217,7 @@ def inputs2args(inputs):
210217
)
211218
return args
212219

213-
def outputs2args(outputs):
220+
def outputs2args(outputs)->list[str]:
214221
args = []
215222
for url, opts in outputs:
216223
# resolve url enumeration if it's a device

tests/test_utils_parser.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,3 +100,9 @@ def test_compose():
100100
)
101101
== "ffmpeg -i /tmp/a.wav -map 0:a -b:a 64k '/tmp/a test.mp2' -map 0:a -b:a 128k /tmp/b.mp2"
102102
)
103+
104+
def test_ffmpeg7():
105+
ffmpeg7_example = "ffmpeg -i input.mkv -filter_complex '[0:v]scale=size=hd1080,split=outputs=2[for_enc][orig_scaled]' -filter_complex '[dec:0][orig_scaled]hstack[stacked]' -c:v libx264 -map '[for_enc]' output.mkv -dec 0:0 -map '[stacked]' -c:v ffv1 comparison.mkv"
106+
107+
ffargs = parser.parse(ffmpeg7_example)
108+
assert len(ffargs['global_options']['filter_complex'])==2

0 commit comments

Comments
 (0)