예제 #1
0
        internal CodecStream(IDataReader dataReader, IDataBlockBuilder dataBlockBuilder, QtAtom root)
        {
            if (dataReader == null)
            {
                throw new ArgumentNullException("dataReader");
            }
            if (dataBlockBuilder == null)
            {
                throw new ArgumentNullException("dataBlockBuilder");
            }
            if (root == null)
            {
                throw new ArgumentNullException("root");
            }

            _dataReader       = dataReader;
            _dataBlockBuilder = dataBlockBuilder;
            _root             = root;
            _moov             = _root.FindChild(AtomName.Movie);
            _mdat             = _root.FindChild(AtomName.MediaData);
            _fileOffset       = _root.FirstChild.Offset;

            if (_mdat == null)
            {
                _mdatChunk = new Chunk(((QtAtom)_root.GetLastDescendant()).Offset - _fileOffset, 0);
            }
            else
            {
                _mdatChunk = new Chunk(_mdat.Offset - _fileOffset + 8, (_mdat.Length - 8));
            }

            _mdatMaxUnparsedBytes = (uint)QtDetector.Configurable[QtDetector.ConfigurationKey.MediaDateMaxUnparsedBytes];
        }
예제 #2
0
        private static string GetExtraDataCodecStreamName(IResultNode headerDataAtom)
        {
            QtAtom track             = FindParentAtom(headerDataAtom, AtomName.Track);
            QtAtom sampleDescription = FindParentAtom(headerDataAtom, AtomName.SampleDescription);

            return(GetCodecStreamName(track, sampleDescription, true));
        }
예제 #3
0
            private T GetRequiredAtom <T>(QtAtom parent, AtomName atomName, bool recursive) where T : QtAtom
            {
                T atom = (parent == null) ? null : parent.FindChild(atomName, recursive) as T;

                if (atom == null)
                {
                    _requiredAtomsMissing = true;
                }
                return(atom);
            }
        /// <summary>
        /// Locates the handler reference and verifies that the given
        /// <paramref name="componentSubType"/> is correct for this
        /// sample description.
        /// </summary>
        /// <param name="componentSubType">the component sub-type</param>
        /// <returns>true if the component sub-type is valid, false otherwise</returns>
        protected bool CheckComponentSubType(ComponentSubType componentSubType)
        {
            QtAtom media = FindParent(AtomName.Media);

            if (media != null)
            {
                HandlerReference handlerReference = media.FindChild(AtomName.HandlerReference) as HandlerReference;
                if (handlerReference != null && handlerReference.ComponentSubType != componentSubType)
                {
                    return(false);
                }
            }
            return(true);
        }
예제 #5
0
        private static string GetCodecStreamName(QtAtom track, QtAtom sampleDescription, bool isPartial)
        {
            var sb = new StringBuilder();

            if (track != null)
            {
                // Report the track ID
                var trackHeader = track.FindChild(AtomName.TrackHeader) as TrackHeader;
                if (trackHeader != null)
                {
                    sb.AppendFormat(CultureInfo.CurrentCulture, "Track {0}", trackHeader.TrackID);
                }
                if (isPartial)
                {
                    sb.Append(" [Partial]");
                }

                // Report the handler type (audio/video) and the handler component name
                var handlerReference = track.FindChild(AtomName.HandlerReference, true) as HandlerReference;
                if (handlerReference != null)
                {
                    sb.AppendFormat(CultureInfo.CurrentCulture, ", {0}", handlerReference.ComponentSubType);
                    if (!string.IsNullOrEmpty(handlerReference.ComponentName))
                    {
                        sb.AppendFormat(CultureInfo.CurrentCulture, ", {0}", handlerReference.ComponentName);
                    }
                }
            }
            else if (isPartial)
            {
                sb.Append("[Partial]");
            }

            // Report the codec name + description
            if ((sampleDescription != null) && sampleDescription.HasChildren())
            {
                string typeName   = Enum.GetName(typeof(QtAtom.Attribute), QtAtom.Attribute.Type);
                string dataFormat = sampleDescription.Children[0].FindAttributeByName(typeName).ValueAsString;

                if (!string.IsNullOrEmpty(dataFormat))
                {
                    sb.AppendFormat(CultureInfo.CurrentCulture, ", {0}", dataFormat);
                    sb.AppendDescriptiveCodecName(dataFormat);
                }
            }
            return(sb.ToString());
        }
예제 #6
0
            internal TrackData(QtAtom track, Chunk mdatChunk, long fileOffset)
            {
                _track             = track;
                _mdatChunk         = mdatChunk;
                _fileOffset        = fileOffset;
                _buffer            = new byte[8];
                _sampleTable       = GetRequiredAtom <QtAtom>(track, AtomName.SampleTable, true);
                _handlerReference  = GetRequiredAtom <HandlerReference>(track, AtomName.HandlerReference, true);
                _sampleDescription = GetRequiredAtom <SampleDescription>(_sampleTable, AtomName.SampleDescription);
                _chunkOffset       = GetRequiredAtom <ChunkOffset>(_sampleTable, AtomName.ChunkOffset);
                _sampleSize        = GetRequiredAtom <SampleSize>(_sampleTable, AtomName.SampleSize);
                _sampleToChunk     = GetRequiredAtom <SampleToChunk>(_sampleTable, AtomName.SampleToChunk);
                _chunks            = new List <Chunk>();

                _validators = new List <VideoSampleValidator> {
                    IsValidH264Sample, IsValidMpeg4Sample, IsValidH263Sample
                };
                _validatorsToRemove = new List <VideoSampleValidator>();

                FirstSampleOffset   = long.MaxValue;
                LastSampleEndOffset = long.MinValue;
            }
예제 #7
0
 public ElementaryStreamDescriptor(QtAtom previousHeader)
     : base(previousHeader, AtomName.ElementaryStreamDescriptor)
 {
 }
예제 #8
0
 public ClippingRegion(QtAtom previousHeader)
     : base(previousHeader, AtomName.ClippingRegion)
 {
 }
예제 #9
0
 public override bool IsSuitableParent(QtAtom parent)
 {
     // File type should always be the first atom
     return(parent.IsRoot && !parent.HasChildren());
 }
예제 #10
0
 public FileType(QtAtom previousHeader)
     : base(previousHeader, AtomName.FileType)
 {
 }
예제 #11
0
 public DataReferenceEntry(QtAtom previousHeader)
     : base(previousHeader, AtomName.DataReferenceEntry)
 {
 }
예제 #12
0
 public MetaData(QtAtom previousHeader)
     : base(previousHeader, AtomName.MetaData)
 {
 }
 protected SampleEntry(QtAtom previousHeader, AtomName atomName)
     : base(previousHeader, atomName)
 {
 }
 public QtSampleDescriptionAtom(QtAtom previousHeader, AtomName atomName)
     : base(previousHeader, atomName)
 {
     Debug.Assert(atomName.IsFlagSet(AtomFlags.SizeAndType) && !atomName.IsFlagSet(AtomFlags.VersionAndFlags));
 }
예제 #15
0
 public TimeCodeSampleDescription(QtAtom previousHeader)
     : base(previousHeader, AtomName.TimeCodeSampleDescription)
 {
 }
예제 #16
0
 public ColorParameter(QtAtom previousHeader)
     : base(previousHeader, AtomName.ColorParameter)
 {
 }
예제 #17
0
 public AvcConfigurationBox(QtAtom previousHeader)
     : base(previousHeader, AtomName.AvcConfigurationBox)
 {
 }
예제 #18
0
 public override bool IsSuitableParent(QtAtom parent)
 {
     return(!parent.HasChildren() || parent.LastChild.HeaderName != AtomName.Wide);
 }
예제 #19
0
 /// <summary>
 /// Creates a new wide atom.
 /// </summary>
 /// <param name="previousHeader">the header that directly precedes the wide atom</param>
 public Wide(QtAtom previousHeader)
     : base(previousHeader, AtomName.Wide)
 {
 }
 public Profile(QtAtom previousHeader)
     : base(previousHeader, AtomName.Profile)
 {
 }
예제 #21
0
 public AvcLayerEntry(QtAtom previousHeader)
     : base(previousHeader, AtomName.AvcLayerEntry)
 {
 }
 public TimeToSample(QtAtom previousHeader)
     : base(previousHeader, AtomName.TimeToSample)
 {
 }
예제 #23
0
 protected SampleGroupDescriptionEntry(QtAtom previousHeader, AtomName atomName)
     : base(previousHeader, atomName)
 {
 }
 public SampleSize(QtAtom previousHeader)
     : base(previousHeader, AtomName.SampleSize)
 {
 }
예제 #25
0
 public SyncSample(QtAtom previousHeader)
     : base(previousHeader, AtomName.SyncSample)
 {
 }
 public ChunkOffset(QtAtom previousHeader, AtomType atomType)
     : base(previousHeader, AtomName.ChunkOffset)
 {
     _atomType = atomType;
 }
 public EditList(QtAtom previousHeader)
     : base(previousHeader, AtomName.EditList)
 {
 }
예제 #28
0
 public SampleToGroupBox(QtAtom previousHeader)
     : base(previousHeader, AtomName.SampleToGroupBox)
 {
 }
 public AvcSubSequenceEntry(QtAtom previousHeader)
     : base(previousHeader, AtomName.AvcSubSequenceEntry)
 {
 }
 public TrackHeader(QtAtom previousHeader)
     : base(previousHeader, AtomName.TrackHeader)
 {
 }