_Al_
28th March 2023, 19:20
Is there a way to abort ModifyFrame function and modify output clip length to when aborted?
This would be for a situation with unknown length of clips if fed from a sort of frame generator. Example below creates an attribute clip for ModifyFrame where its clip length is exaggerated when passed to ModifyFrame. Then if no more sources just black frames are added.
import vapoursynth as vs
from vapoursynth import core
import os
DIRECTORY = r'D:\sources'
def get_clips():
for filename in os.listdir(DIRECTORY):
path = os.path.join(DIRECTORY, filename)
clip = core.lsmas.LibavSMASHSource(path)
yield clip
class Clip_handler:
def __init__(self, get_clips):
self.clip_generator = get_clips()
self.load_new_clip()
self.frame_num = -1
self.total_length = 0
def load_new_clip(self):
try: self.clip = next(self.clip_generator)
except StopIteration: self.clip = None
self.frame_num = 0
def fetch_frame(self, n, f):
self.frame_num += 1
if self.clip is not None and self.frame_num == self.clip.num_frames:
self.load_new_clip()
if self.clip is None:
pass
#need to abort here with total_length
self.total_length += 1
return self.clip.get_frame(self.frame_num) if self.clip is not None else f.copy()
placeholder_clip = core.std.BlankClip(width=1920, height=1080, format=vs.YUV420P8, length=500000)
placeholder_clip = core.std.AssumeFPS(placeholder_clip, fpsnum=60000, fpsden=1001)
clip_handler = Clip_handler(get_clips)
joined_clips = core.std.ModifyFrame(clip=placeholder_clip, clips=placeholder_clip, selector=clip_handler.fetch_frame)
joined_clips.set_output()
So in that concrete example, is it possible to abort ModifyFrame when StopIteration happens and return correct clip length to joined_clips?
Or is there another way how to approach it? All is needed for an encoder is to feed it with frames in linear fashion. No seeking is needed.
This would be for a situation with unknown length of clips if fed from a sort of frame generator. Example below creates an attribute clip for ModifyFrame where its clip length is exaggerated when passed to ModifyFrame. Then if no more sources just black frames are added.
import vapoursynth as vs
from vapoursynth import core
import os
DIRECTORY = r'D:\sources'
def get_clips():
for filename in os.listdir(DIRECTORY):
path = os.path.join(DIRECTORY, filename)
clip = core.lsmas.LibavSMASHSource(path)
yield clip
class Clip_handler:
def __init__(self, get_clips):
self.clip_generator = get_clips()
self.load_new_clip()
self.frame_num = -1
self.total_length = 0
def load_new_clip(self):
try: self.clip = next(self.clip_generator)
except StopIteration: self.clip = None
self.frame_num = 0
def fetch_frame(self, n, f):
self.frame_num += 1
if self.clip is not None and self.frame_num == self.clip.num_frames:
self.load_new_clip()
if self.clip is None:
pass
#need to abort here with total_length
self.total_length += 1
return self.clip.get_frame(self.frame_num) if self.clip is not None else f.copy()
placeholder_clip = core.std.BlankClip(width=1920, height=1080, format=vs.YUV420P8, length=500000)
placeholder_clip = core.std.AssumeFPS(placeholder_clip, fpsnum=60000, fpsden=1001)
clip_handler = Clip_handler(get_clips)
joined_clips = core.std.ModifyFrame(clip=placeholder_clip, clips=placeholder_clip, selector=clip_handler.fetch_frame)
joined_clips.set_output()
So in that concrete example, is it possible to abort ModifyFrame when StopIteration happens and return correct clip length to joined_clips?
Or is there another way how to approach it? All is needed for an encoder is to feed it with frames in linear fashion. No seeking is needed.