def _parse_stream(self): while True: strl = self._next_chunk() # search for next LIST/strl chunk if strl.fcc == b"LIST" and strl.sub_fcc == b"strl": break # skip LIST/odml chunks elif strl.fcc == b"LIST" and strl.sub_fcc == b"odml": self._skip_chunk(strl) # back up if anything else is found else: self._put_back(strl) return False self._log.write("Stream definition #{0}".format(len(self._stream_data))) strh = self._require_chunk(b"strh") stream_header = self._read_struct_chunk(strh, StreamHeader) self._log.write("Stream header") self._log.writeobj(stream_header) bitmap_info = None strf = self._require_chunk(b"strf") if stream_header.fccType == b"vids": bitmap_info = self._read_struct_chunk(strf, BitmapInfoHeader) self._log.write("Bitmap info header") self._log.writeobj(bitmap_info) else: self._skip_chunk(strf) codec_data = None c = self._next_chunk() if c.fcc == b"strd": codec_data = self._read_chunk_content(c) self._log.write("Codec data: {0} bytes", len(codec_data)) c = self._next_chunk() stream_name = None if c.fcc == b"strn": stream_name = _from_asciiz(self._read_chunk_content(c)) self._log.write("Stream name: {0!r}", stream_name) else: self._put_back(c) if bitmap_info is not None: vs = InputVideoStream(self) vs.stream_num = len(self._stream_data) vs.width = bitmap_info.Width vs.height = bitmap_info.Height vs.frame_rate = Timecode.interpret_frame_rate( stream_header.Rate / float(stream_header.Scale)) vs.codec = stream_header.fccHandler vs.codec_data = codec_data vs.suggested_buffer_size = stream_header.SuggestedBufferSize vs.bit_depth = bitmap_info.BitCount vs.compression = bitmap_info.Compression vs.size_image = bitmap_info.SizeImage self.video_streams.append(vs) self._stream_data.append(StreamInfo( stream_header, bitmap_info, codec_data, stream_name)) return True
def microseconds_per_frame(self): return round(1e6 / Timecode.interpret_frame_rate(self.frame_rate))