using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using skyscraper5.Skyscraper.IO;
using skyscraper5.Skyscraper.Plugins;

namespace skyscraper5.Mpeg2.Descriptors
{
	[SkyscraperPlugin]
	[TsDescriptor(0x24,"PMT")]
    [BannedTable("EIT")] //According to ITU-T Rec. H.222.0 this one may also be included in "tables to describe segments of programs or elementary streams", which would include an EIT, but each time I tried it, nothing sensible came out.
    class ContentLabelingDescriptor
    {
        public ContentLabelingDescriptor(byte[] buffer)
        {
            MemoryStream ms = new MemoryStream(buffer, false);
            MetadataApplicationFormat = ms.ReadUInt16BE();
            if (MetadataApplicationFormat == 0xffff)
            {
                MetadataApplicationFormatIdentifier = ms.ReadUInt32BE();
            }

            byte readUInt8 = ms.ReadUInt8();
            ContentReferenceIdRecordFlag = (readUInt8 & 0x80) != 0;
            ContentTimeBaseIndicator = (readUInt8 & 0x78) >> 3;
            if (ContentReferenceIdRecordFlag)
            {
                byte contentReferenceIdRecordLength = ms.ReadUInt8();
                ContentReferenceId = ms.ReadBytes(contentReferenceIdRecordLength);
            }

            if (ContentTimeBaseIndicator == 1 || ContentTimeBaseIndicator == 2)
            {
                ContentTimeBaseValue = ms.ReadUInt8() & 0x01;
                ContentTimeBaseValue <<= 32;
                ContentTimeBaseValue += ms.ReadUInt32BE();

                MetadataTimeBaseValue = ms.ReadUInt8() & 0x01;
                MetadataTimeBaseValue <<= 32;
                MetadataTimeBaseValue += ms.ReadUInt32BE();
            }

            if (ContentTimeBaseIndicator == 2)
            {
                ContentId = ms.ReadUInt8() & 0x07f;
            }

            if (ContentTimeBaseIndicator >= 3 && ContentTimeBaseIndicator <= 7)
            {
                byte timeBaseAssociationDataLength = ms.ReadUInt8();
                TimeBaseAssociationData = ms.ReadBytes(timeBaseAssociationDataLength);
            }

            PrivateData = ms.ReadBytes(ms.GetAvailableBytes());
        }

        public byte[] PrivateData { get; private set; }

        public byte[] TimeBaseAssociationData { get; private set; }

        public int? ContentId { get; private set; }

        public long? MetadataTimeBaseValue { get; private set; }

        public long? ContentTimeBaseValue { get; private set; }

        public byte[] ContentReferenceId { get; private set; }

        public int ContentTimeBaseIndicator { get; private set; }

        public bool ContentReferenceIdRecordFlag { get; private set; }

        public uint? MetadataApplicationFormatIdentifier { get; private set; }

        public ushort MetadataApplicationFormat { get; private set; }
    }
}
