예제 #1
0
 def adjustPositions(video_file, hits):
     # used if variable frame rate
     frmcnt = 0
     hitspos = 0
     last = 0
     cap = cv2api_delegate.videoCapture(video_file)
     try:
         while cap.grab() and hitspos < len(hits):
             frmcnt += 1
             aptime = cap.get(cv2api_delegate.prop_pos_msec)
             while hitspos < len(hits) and aptime > hits[hitspos][0]:
                 mask = hits[hitspos][2]
                 element = hits[hitspos][1]
                 error = max(abs(last - hits[hitspos][0]),
                             abs(aptime - hits[hitspos][0]))
                 if element == 'starttime':
                     update_segment(mask,
                                    starttime=last,
                                    startframe=frmcnt,
                                    error=error)
                 else:
                     update_segment(mask,
                                    endtime=last,
                                    endframe=frmcnt,
                                    error=max(
                                        error,
                                        get_error_from_segment(mask)))
                 hitspos += 1
             last = aptime
     finally:
         cap.release()
     return mask
예제 #2
0
 def adjustPositionsFFMPEG(meta, video_frames, hits):
     rate = ffmpeg_api.get_video_frame_rate_from_meta([meta],
                                                      [video_frames])
     aptime = 0
     lasttime = 0
     hitspos = 0
     start_mask = None
     for pos in range(0, len(video_frames)):
         aptime = get_frame_time(video_frames[pos], aptime, rate)
         while hitspos < len(hits) and aptime > hits[hitspos][0]:
             mask = hits[hitspos][2]
             element = hits[hitspos][1]
             error = abs(aptime - hits[hitspos][0])
             if element == 'starttime':
                 update_segment(mask,
                                starttime=lasttime,
                                startframe=pos,
                                error=error +
                                get_error_from_segment(mask))
                 start_mask = mask
             else:
                 # for error, only record the error if not recorded
                 update_segment(
                     mask,
                     endtime=lasttime,
                     endframe=pos,
                     error=(error if start_mask != mask else 0) +
                     get_error_from_segment(mask))
             hitspos += 1
         lasttime = aptime
     return mask
예제 #3
0
    def create_video_for_audio(self, source, masks):
        """
        make a mask in video time for each audio mask in masks.
        in VFR case, uses ffmpeg frames to get nearest frame to timestamp.
        :param source: video file
        :param masks:
        :return: new set of masks
        """
        from math import floor
        from video_tools import get_frame_rate

        def _get_frame_time(frame):
            if 'pkt_pts_time' in frame.keys() and frame['pkt_pts_time'] != 'N/A':
                return float(frame['pkt_pts_time']) * 1000
            else:
                return float(frame['pkt_dts_time']) * 1000

        def _frame_distance(time_a, time_b):
            dist = time_a - time_b
            return abs(dist) if dist <= 0 else float('inf')

        meta_and_frames = self.getVideoMeta(source, show_streams=True, with_frames=False, media_types=['video'])
        hasVideo = ffmpeg_api.get_stream_indices_of_type(meta_and_frames[0], 'video')
        meta = meta_and_frames[0][0]
        isVFR = ffmpeg_api.is_vfr(meta)
        video_masks = [mask for mask in masks if get_type_of_segment(mask)== 'video']
        audio_masks = [mask for mask in masks if get_type_of_segment(mask) == 'audio']
        if len(video_masks) == 0 and hasVideo:
            entire_mask = getMaskSetForEntireVideoForTuples(self.getMetaDataLocator(source), media_types=['video'])[0]
            upper_bounds = (get_end_frame_from_segment(entire_mask), get_end_time_from_segment(entire_mask))
            new_masks = list(audio_masks)
            for mask in audio_masks:
                end_time = min(get_end_time_from_segment(mask), upper_bounds[1])
                new_mask = mask.copy()
                rate = get_frame_rate(self.getMetaDataLocator(source))
                if not isVFR:
                    start_frame = int(get_start_time_from_segment(mask) * rate / 1000.0) + 1
                    end_frame = int(end_time * rate / 1000.0)
                else:
                    video_frames = \
                    self.getVideoMeta(source, show_streams=True, with_frames=True, media_types=['video'])[1][0]
                    start_frame = video_frames.index(
                        min(video_frames, key=lambda x: _frame_distance(_get_frame_time(x), get_start_time_from_segment(mask)))) + 1
                    end_frame = video_frames.index(
                        min(video_frames, key=lambda x: _frame_distance(_get_frame_time(x), end_time))) + 1
                end_frame = min(end_frame, upper_bounds[0])
                update_segment(new_mask,
                               type= 'video-associate',
                               rate=rate,
                               endtime=end_time,
                               startframe=start_frame,
                               endframe=end_frame)
                new_masks.append(new_mask)
            return new_masks
        else:
            return masks
예제 #4
0
    def create_masks(self, mask_set):
        from maskgen import tool_set
        import numpy as np

        for segment in mask_set:
            writer = tool_set.GrayBlockWriter(
                'test_warp', video_tools.get_rate_from_segment(segment))
            for i in range(video_tools.get_frames_from_segment(segment)):
                f = i + video_tools.get_start_frame_from_segment(segment)
                writer.write(
                    np.random.randint(0, 1, (1000, 1000), 'uint8') * 255,
                    (f - 1) * video_tools.get_rate_from_segment(segment),
                    frame_number=f)
            writer.close()
            video_tools.update_segment(segment, videosegment=writer.filename)
            self.addFileToRemove(writer.filename)
예제 #5
0
    def create(self, arguments={}, invert=False):
        from maskgen.tool_set import getMilliSecondsAndFrameCount
        media_types = ['video', 'audio'] if getValue(
            arguments, 'include audio', 'no') == 'yes' else ['video']

        from maskgen.video_tools import FileMetaDataLocator
        end_time_tuple = getMilliSecondsAndFrameCount(
            getValue(arguments, 'End Time', "00:00:00"))
        start_time_tuple = getMilliSecondsAndFrameCount(
            getValue(arguments, 'Start Time', '00:00:00'))
        video_set = FileMetaDataLocator(
            self.startFileName).getMaskSetForEntireVideoForTuples(
                start_time_tuple=start_time_tuple,
                end_time_tuple=end_time_tuple
                if end_time_tuple[1] > start_time_tuple[1] else None,
                media_types=media_types)
        audio_segments = [
            x for x in video_set if get_type_of_segment(x) == 'audio'
        ]
        video_segments = [
            x for x in video_set if get_type_of_segment(x) == 'video'
        ]

        if getValue(arguments, 'include audio', 'no') == 'yes':
            for audio_segment in audio_segments:
                video_segment = video_segments[0] if len(
                    video_segments) > 0 else audio_segment
                update_segment(
                    audio_segment,
                    type='audio',
                    starttime=get_start_time_from_segment(video_segment),
                    endtime=get_end_time_from_segment(video_segment),
                    startframe=int(
                        get_start_time_from_segment(video_segment) *
                        get_rate_from_segment(audio_segment) / 1000.0),
                    endframe=int(
                        get_end_time_from_segment(video_segment) *
                        get_rate_from_segment(audio_segment) / 1000.0) + 1)
        return video_set