inc ffx single descriptor 1/

This commit is contained in:
2024-10-17 15:58:22 +02:00
parent 30d22892f8
commit ee31634b0b
6 changed files with 203 additions and 344 deletions

View File

@@ -40,8 +40,8 @@ class FfxController():
def __init__(self,
context : dict,
sourceMediaDescriptor : MediaDescriptor,
targetMediaDescriptor : MediaDescriptor):
targetMediaDescriptor : MediaDescriptor,
sourceMediaDescriptor : MediaDescriptor = None):
self.__context = context
self.__sourceMediaDescriptor = sourceMediaDescriptor
@@ -90,7 +90,12 @@ class FfxController():
'-lag-in-frames', '25']
def generateCropTokens(self, start, length):
@staticmethod
def generateCropTokens(cropStart : int = -1, cropLength : int = -1):
start = int(cropStart if cropStart > -1 else FfxController.DEFAULT_CROP_START)
length = int(cropLength if cropLength > -1 else FfxController.DEFAULT_CROP_LENGTH)
return ['-ss', str(start), '-t', str(length)]
@@ -171,27 +176,29 @@ class FfxController():
def generateDispositionTokens(self):
"""-disposition:s:X default+forced"""
sourceTrackDescriptors = self.__sourceMediaDescriptor.getAllTrackDescriptors()
sourceTrackDescriptors = [] if self.__sourceMediaDescriptor is None else self.__sourceMediaDescriptor.getAllTrackDescriptors()
targetTrackDescriptors = self.__targetMediaDescriptor.getReorderedTrackDescriptors()
dispositionTokens = []
# for subStreamIndex in range(len(subDescriptor)):
for trackDescriptor in targetTrackDescriptors:
# Calculate source sub index
changedTargetTrackDescriptor : TrackDescriptor = targetTrackDescriptors[trackDescriptor.getIndex()]
changedTargetTrackSourceIndex = changedTargetTrackDescriptor.getSourceIndex()
sourceSubIndex = sourceTrackDescriptors[changedTargetTrackSourceIndex].getSubIndex()
# Calculate source sub index. This applies only if a source media descriptor is defined.
if sourceTrackDescriptors:
changedTargetTrackDescriptor : TrackDescriptor = targetTrackDescriptors[trackDescriptor.getIndex()]
changedTargetTrackSourceIndex = changedTargetTrackDescriptor.getSourceIndex()
subIndex = sourceTrackDescriptors[changedTargetTrackSourceIndex].getSubIndex()
else:
subIndex = trackDescriptor.getSubIndex()
streamIndicator = trackDescriptor.getType().indicator()
dispositionSet = trackDescriptor.getDispositionSet()
if dispositionSet:
dispositionTokens += [f"-disposition:{streamIndicator}:{sourceSubIndex}", '+'.join([d.label() for d in dispositionSet])]
dispositionTokens += [f"-disposition:{streamIndicator}:{subIndex}", '+'.join([d.label() for d in dispositionSet])]
else:
dispositionTokens += [f"-disposition:{streamIndicator}:{sourceSubIndex}", '0']
dispositionTokens += [f"-disposition:{streamIndicator}:{subIndex}", '0']
return dispositionTokens

View File

@@ -67,24 +67,25 @@ class FileProperties():
#
# print(f"season={season} episode={episode} file={file_index}")
#
#
# # Assemble target filename tokens
# targetFilenameTokens = []
def assembleTargetFilename(self):
targetFilenameTokens = []
# targetFilenameExtension = DEFAULT_FILE_EXTENSION
#
# if label:
# targetFilenameTokens = [label]
#
# if season > -1 and episode > -1:
# targetFilenameTokens += [f"S{season:0{season_digits}d}E{episode:0{episode_digits}d}"]
# elif episode > -1:
# targetFilenameTokens += [f"E{episode:0{episode_digits}d}"]
# if self.__season > -1 and self.__episode > -1:
# targetFilenameTokens += [f"S{self.__season:0{season_digits}d}E{self.__episode:0{episode_digits}d}"]
# elif self.__episode > -1:
# targetFilenameTokens += [f"E{self.__episode:0{episode_digits}d}"]
# else:
# targetFilenameTokens += [f"{file_index:0{index_digits}d}"]
#
# else:
# targetFilenameTokens = [sourceFileBasename]
#
# targetFilenameTokens = [self.__sourceFileBasename]
def searchSubtitleFiles(dir, prefix):

View File

@@ -65,39 +65,74 @@ class MediaDescriptor():
self.__jellyfinOrder = False
def getDefaultVideoTrack(self):
videoDefaultTracks = [v for v in self.getVideoTracks() if TrackDisposition.DEFAULT in v.getDispositionSet()]
if len(videoDefaultTracks) > 1:
raise ValueError('MediaDescriptor.getDefaultVideoTrack(): More than one default video track is not supported')
return videoDefaultTracks[0] if videoDefaultTracks else None
def getForcedVideoTrack(self):
videoForcedTracks = [v for v in self.getVideoTracks() if TrackDisposition.FORCED in v.getDispositionSet()]
if len(videoForcedTracks) > 1:
raise ValueError('MediaDescriptor.getForcedVideoTrack(): More than one forced video track is not supported')
return videoForcedTracks[0] if videoForcedTracks else None
def getDefaultAudioTrack(self):
audioDefaultTracks = [a for a in self.getAudioTracks() if TrackDisposition.DEFAULT in a.getDispositionSet()]
if len(audioDefaultTracks) > 1:
raise ValueError('MediaDescriptor.getDefaultAudioTrack(): More than one default audio track is not supported')
return audioDefaultTracks[0] if audioDefaultTracks else None
def getForcedAudioTrack(self):
audioForcedTracks = [a for a in self.getAudioTracks() if TrackDisposition.FORCED in a.getDispositionSet()]
if len(audioForcedTracks) > 1:
raise ValueError('MediaDescriptor.getForcedAudioTrack(): More than one forced audio track is not supported')
return audioForcedTracks[0] if audioForcedTracks else None
def getDefaultSubtitleTrack(self):
subtitleDefaultTracks = [s for s in self.getSubtitleTracks() if TrackDisposition.DEFAULT in s.getDispositionSet()]
if len(subtitleDefaultTracks) > 1:
raise ValueError('MediaDescriptor.getDefaultSubtitleTrack(): More than one default subtitle track is not supported')
return subtitleDefaultTracks[0] if subtitleDefaultTracks else None
def getForcedSubtitleTrack(self):
subtitleForcedTracks = [s for s in self.getSubtitleTracks() if TrackDisposition.FORCED in s.getDispositionSet()]
if len(subtitleForcedTracks) > 1:
raise ValueError('MediaDescriptor.getForcedSubtitleTrack(): More than one forced subtitle track is not supported')
return subtitleForcedTracks[0] if subtitleForcedTracks else None
def setDefaultSubTrack(self, trackType : TrackType, subIndex : int):
for t in self.getAllTrackDescriptors():
if t.getType() == trackType:
t.setDispositionFlag(TrackDisposition.DEFAULT, t.getSubIndex() == int(subIndex))
def setForcedSubTrack(self, trackType : TrackType, subIndex : int):
for t in self.getAllTrackDescriptors():
if t.getType() == trackType:
t.setDispositionFlag(TrackDisposition.FORCED, t.getSubIndex() == int(subIndex))
def getReorderedTrackDescriptors(self):
videoTracks = self.getVideoTracks()
audioTracks = self.getAudioTracks()
subtitleTracks = self.getSubtitleTracks()
videoTracks = self.sortSubIndices(self.getVideoTracks())
audioTracks = self.sortSubIndices(self.getAudioTracks())
subtitleTracks = self.sortSubIndices(self.getSubtitleTracks())
videoDefaultTracks = [v for v in videoTracks if TrackDisposition.DEFAULT in v.getDispositionSet()]
videoForcedTracks = [v for v in videoTracks if TrackDisposition.FORCED in v.getDispositionSet()]
audioDefaultTracks = [a for a in audioTracks if TrackDisposition.DEFAULT in a.getDispositionSet()]
audioForcedTracks = [a for a in audioTracks if TrackDisposition.FORCED in a.getDispositionSet()]
subtitleDefaultTracks = [s for s in subtitleTracks if TrackDisposition.DEFAULT in s.getDispositionSet()]
subtitleForcedTracks = [s for s in subtitleTracks if TrackDisposition.FORCED in s.getDispositionSet()]
videoDefaultTrack = self.getDefaultVideoTrack()
self.getForcedVideoTrack()
audioDefaultTrack = self.getDefaultAudioTrack()
self.getForcedAudioTrack()
subtitleDefaultTrack = self.getDefaultSubtitleTrack()
self.getForcedSubtitleTrack()
if len(videoDefaultTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one default video track is not supported')
if len(videoForcedTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one forced video track is not supported')
if len(audioDefaultTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one default audio track is not supported')
if len(audioForcedTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one forced audio track is not supported')
if len(subtitleDefaultTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one default subtitle track is not supported')
if len(subtitleForcedTracks) > 1:
raise ValueError('MediaDescriptor.__getSourceIndexOrder(): More than one forced subtitle track is not supported')
if self.__jellyfinOrder:
if videoDefaultTracks:
videoTracks.append(videoTracks.pop(videoTracks.index(videoDefaultTracks[0])))
if audioDefaultTracks:
audioTracks.append(audioTracks.pop(audioTracks.index(audioDefaultTracks[0])))
if subtitleDefaultTracks:
subtitleTracks.append(subtitleTracks.pop(subtitleTracks.index(subtitleDefaultTracks[0])))
if not videoDefaultTrack is None:
videoTracks.append(videoTracks.pop(videoTracks.index(videoDefaultTrack)))
if not audioDefaultTrack is None:
audioTracks.append(audioTracks.pop(audioTracks.index(audioDefaultTrack)))
if not subtitleDefaultTrack is None:
subtitleTracks.append(subtitleTracks.pop(subtitleTracks.index(subtitleDefaultTrack)))
reorderedTrackDescriptors = videoTracks + audioTracks + subtitleTracks
orderedSourceTrackSequence = [t.getSourceIndex() for t in reorderedTrackDescriptors]
@@ -143,32 +178,26 @@ class MediaDescriptor():
return self.__mediaTags
def sortSubIndices(self, descriptors : List[TrackDescriptor]) -> List[TrackDescriptor]:
subIndex = 0
for t in descriptors:
t.setSubIndex(subIndex)
subIndex += 1
return descriptors
def getAllTrackDescriptors(self) -> List[TrackDescriptor]:
return self.getVideoTracks() + self.getAudioTracks() + self.getSubtitleTracks()
def getVideoTracks(self) -> List[TrackDescriptor]:
videoTracks = [v for v in self.__trackDescriptors.copy() if v.getType() == TrackType.VIDEO]
subIndex = 0
for v in videoTracks:
v.setSubIndex(subIndex)
subIndex += 1
return videoTracks
return [v for v in self.__trackDescriptors.copy() if v.getType() == TrackType.VIDEO]
def getAudioTracks(self) -> List[TrackDescriptor]:
audioTracks = [a for a in self.__trackDescriptors.copy() if a.getType() == TrackType.AUDIO]
subIndex = 0
for a in audioTracks:
a.setSubIndex(subIndex)
subIndex += 1
return audioTracks
return [a for a in self.__trackDescriptors.copy() if a.getType() == TrackType.AUDIO]
def getSubtitleTracks(self) -> List[TrackDescriptor]:
subtitleTracks = [s for s in self.__trackDescriptors.copy() if s.getType() == TrackType.SUBTITLE]
subIndex = 0
for s in subtitleTracks:
s.setSubIndex(subIndex)
subIndex += 1
return subtitleTracks
return [s for s in self.__trackDescriptors.copy() if s.getType() == TrackType.SUBTITLE]
def getJellyfin(self):
return self.__jellyfinOrder

View File

@@ -229,3 +229,10 @@ class TrackController():
raise click.ClickException(f"TrackController.deleteTrack(): {repr(ex)}")
finally:
s.close()
def setDefaultSubTrack(self, trackType, subIndex):
pass
def setForcedSubTrack(self, trackType, subIndex):
pass

View File

@@ -204,6 +204,16 @@ class TrackDescriptor():
return self.__dispositionSet
def getDispositionFlag(self, disposition : TrackDisposition) -> bool:
return bool(disposition in self.__dispositionSet)
def setDispositionFlag(self, disposition : TrackDisposition, state : bool):
if state:
self.__dispositionSet.add(disposition)
else:
self.__dispositionSet.discard(disposition)
def compare(self, vsTrackDescriptor):
compareResult = {}