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

namespace skyscraper5.Dvb.Descriptors
{
	[SkyscraperPlugin]
	[TsDescriptor(0x5a,"NIT")]
    public class TerristialDeliverySystemDescriptor : TsDescriptor
    {
        public TerristialDeliverySystemDescriptor(byte[] buffer)
        {
            MemoryStream ms = new MemoryStream(buffer, false);
            CentreFrequency = ms.ReadUInt32BE();

            byte readUInt8 = ms.ReadUInt8();
            Bandwidth = 8 - ((readUInt8 & 0xe0) >> 5);
            Priority = (readUInt8 & 0x10) != 0;
            TimeSlicingIndicator = (readUInt8 & 0x80) != 0;
            MpeFecIndicator = (readUInt8 & 0x40) != 0;

            readUInt8 = ms.ReadUInt8();
            Constellation = ((readUInt8 & 0xc0) >> 6);
            HierarchyInformation = (HierarchySignallingFormat)((readUInt8 & 0x38) >> 3);
            CodeRateHpStream = (CodeRate)(readUInt8 & 0x07);

            readUInt8 = ms.ReadUInt8();
            CodeRateLpStream = (CodeRate)((readUInt8 & 0xe0) >> 5);
            GuardInterval = ((readUInt8 & 0x18) >> 3);
            TransmissionMode = (readUInt8 & 0x06) >> 1;
            OtherFrequencyFlag = (readUInt8 & 0x01) != 0;
        }

        public int Constellation { get; set; }

        public bool OtherFrequencyFlag { get; private set; }

        public int TransmissionMode { get; private set; }

        public int GuardInterval { get; private set; }

        public CodeRate CodeRateLpStream { get; private set; }

        public CodeRate CodeRateHpStream { get; private set; }

        public HierarchySignallingFormat HierarchyInformation { get; private set; }
        
        public bool MpeFecIndicator { get; private set; }

        public bool TimeSlicingIndicator { get; private set; }

        public bool Priority { get; private set; }

        public int Bandwidth { get; private set; }

        public uint CentreFrequency { get; private set; }
        
        public enum HierarchySignallingFormat : byte
        {
            NonHierarchialNative = 0,
            Alpha1Native = 1,
            Alpha2Native = 2,
            Alpha4Native = 3,
            NonHierarchialInDepth = 4,
            Alpha1InDepth = 5,
            Alpha2InDepth = 6,
            Alpha4InDepth = 7
        }

        public enum CodeRate : byte
        {
            Half = 0,
            TwoThird = 1,
            ThreeFourth = 2,
            FiveSixth = 3,
            SevenEigth = 4
        }
    }
}
