public SequenceState(SequenceStateBuilder builder) { Id = builder._id; ByteStreamFormat = builder.ByteStreamFormat; Profile = builder.ProfileIdc; ChromaFormat = builder.SeparateColourPlaneFlag ? ChromaFormat.SeparateColorPlane : ChromaFormats[builder.ChromaFormatIdc]; BitDepthLuma = builder.BitDepthLumaMinus8 + 8; BitDepthChroma = builder.BitDepthChromaMinus8 + 8; Log2MaxFrameNum = builder.Log2MaxFrameNumMinus4 + 4; PictureOrderCountType = builder.PictureOrderCountType; Log2MaxPicOrderCntLsb = builder.Log2MaxPicOrderCntLsbMinus4 + 4; DeltaPicOrderAlwaysZeroFlag = builder.DeltaPicOrderAlwaysZeroFlag; MaxNumRefFrames = builder.MaxNumRefFrames; PicWidthInMbs = builder.PicWidthInMbsMinus1 + 1; PicHeightInMapUnits = builder.PicHeightInMapUnitsMinus1 + 1; FrameMbsOnlyFlag = builder.FrameMbsOnlyFlag; MbAdaptiveFrameFieldFlag = builder.MbAdaptiveFrameFieldFlag; Direct8X8InferenceFlag = builder.Direct8X8InferenceFlag; int qbBdOffsetY = 6 * ((int)BitDepthLuma - 8); MinMbQpDelta = -(26 + qbBdOffsetY / 2); MaxMbQpDelta = (25 + qbBdOffsetY / 2); }
// 7.3.2.1.1 SequenceState parameter set data syntax public void Parse(INalUnitReader reader, IResultNodeState resultState) { // Constraints from 7.4.2.11 resultState.Name = Name; Profile profileIdc = reader.GetBits(8, Attribute.ProfileIdc, _profileValidator); reader.GetBits(6); // constraint_set{0-5}_flag if (reader.GetBits(2) != 0) // reserved_zero_2bits { resultState.Invalidate(); return; } reader.GetByte(false, Attribute.LevelIdc, 59); // level_idc, Table A-1 - Level limits uint sequenceParameterSetId = reader.GetExpGolombCoded(Attribute.SequenceParameterSetId, 31); ISequenceStateBuilder builder = new SequenceStateBuilder(sequenceParameterSetId); builder.ByteStreamFormat = reader.State.ByteStreamFormat; builder.ProfileIdc = profileIdc; if (IsHighProfile(profileIdc)) { uint chromaFormatIdc = reader.GetExpGolombCoded(Attribute.ChromaFormatIdc, 3); // Table 6-1 builder.ChromaFormatIdc = chromaFormatIdc; if (chromaFormatIdc == 3) { builder.SeparateColourPlaneFlag = reader.GetBit(Attribute.SeparateColorPlaneFlag); } builder.BitDepthLumaMinus8 = reader.GetExpGolombCoded(Attribute.BitDepthLumaArraySampleMinus8, 6); builder.BitDepthChromaMinus8 = reader.GetExpGolombCoded(Attribute.BitDepthChromaArraySampleMinus8, 6); reader.GetBit(); // qpprime_y_zero_transform_bypass_flag if (reader.GetBit()) // seq_scaling_matrix_present_flag { for (int i = 0; i < ((chromaFormatIdc != 3) ? 8 : 12); i++) { if (reader.GetBit()) // seq_scaling_list_present_flag[i] { // FIXME: scaling_list() is not implemented!! resultState.Invalidate(); return; } } } } builder.Log2MaxFrameNumMinus4 = reader.GetExpGolombCoded(Attribute.Log2MaxFrameNumMinus4, 28); DecodePictureOrderCount(reader, builder); uint maxDpbFramesUpperLimit = (profileIdc == Profile.MultiviewHigh) ? 160U : 16U; //could use the exact maxDpbFrames, but this is easier builder.MaxNumRefFrames = reader.GetExpGolombCoded(Attribute.MaxNumberReferenceFrames, maxDpbFramesUpperLimit); reader.GetBit(); // gaps_in_frame_num_value_allowed_flag builder.PicWidthInMbsMinus1 = reader.GetExpGolombCoded(Attribute.PictureWidthInMacroBlocksMinus1, 543); builder.PicHeightInMapUnitsMinus1 = reader.GetExpGolombCoded(Attribute.PictureHeightInMapUnitsMinus1, 543); var frameMbsOnlyFlag = reader.GetBit(Attribute.FrameMbsOnlyFlag); builder.FrameMbsOnlyFlag = frameMbsOnlyFlag; if (!frameMbsOnlyFlag) { builder.MbAdaptiveFrameFieldFlag = reader.GetBit(); } bool direct8X8InferenceFlag = reader.GetBit(); builder.Direct8X8InferenceFlag = direct8X8InferenceFlag; if (!frameMbsOnlyFlag && !direct8X8InferenceFlag) { resultState.Invalidate(); return; } if (reader.GetBit()) // frame_cropping_flag { // TODO: Cropping should not exceed the size of a frame! reader.GetExpGolombCoded(Attribute.FrameCropLeftOffset, 8703); reader.GetExpGolombCoded(Attribute.FrameCropRightOffset, 8703); reader.GetExpGolombCoded(Attribute.FrameCropTopOffset, 8703); reader.GetExpGolombCoded(Attribute.FrameCropBottomOffset, 8703); } if (reader.GetBit()) // vui_parameters_present_flag { GetVuiParameters(reader, resultState); } if (reader.ShowBits(1) == 1) { reader.GetBit(); // rbsp_stop_one_bit (equal to 1) // trailing zero bits } if (resultState.Valid) { reader.State.SequenceStates[sequenceParameterSetId] = builder.Build(); } }