using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Maxim.MAX30101GUI.DeviceDescriptions
{
    /// <summary>
    /// This class holds the properties of the ADC selected
    /// </summary>
    public class AccelDevice
    {
        string name = "MAX11270";
        //public string[] parts = {"MAX11270"};//, "MAX11271", "MAX11280"};
        int resolution = 24;
        bool bipolar = true;
        bool twosComp = true;
        double VREFExternal = 2.5;

        public double gain; //calculated
        public int offset;  //calculated
        //public double CNVSTime = 1000;//us

        //public double[] cont_SINC;// = { 1.9, 3.9, 7.8, 15.6, 31.2, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000, 64000 };
        //public double[] single_cont = { 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 4000, 6400, 12800 };
        //public double[] cont_FIR = { 125, 250, 500, 1000, 2000, 4000, 8000, 16000 };
        public List<double> cont_SINC = new List<double>();
        public List<double> single_cont = new List<double>();
        public List<double> cont_FIR = new List<double>();

        public bool FIRon = false;

        //public string DeviceName;
        public List<RegisterDescription> Registers;
        public int RegisterCount;

        //Registers
        public RegisterDescription STAT;
        public RegisterDescription CTRL1;
        public RegisterDescription CTRL2;
        public RegisterDescription CTRL3;
        public RegisterDescription CTRL4;
        public RegisterDescription CTRL5;
        public RegisterDescription DATA;
        public RegisterDescription SOC_SPI;
        public RegisterDescription SGC_SPI;
        public RegisterDescription SCOC_SPI;
        public RegisterDescription SCGC_SPI;
        public RegisterDescription HPF;
        public RegisterDescription SOC_ADC;
        public RegisterDescription SGC_ADC;
        public RegisterDescription SCOC_ADC;
        public RegisterDescription SCGC_ADC;

        public List<BitInfo> CommandMODE0Bits = new List<BitInfo>();
        public List<BitInfo> CommandMODE1Bits = new List<BitInfo>();

        public AccelDevice()
        {
            GetDefault();
        }

        /// Get the default structure and values of the Register map
        /// 
        public void GetDefault()
        {
            if (name == "MAX11214")
            {
                cont_SINC.AddRange(new double[] { 0.95, 1.9, 3.9, 7.8, 15.6, 31.25, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000 });
                single_cont.AddRange(new double[] { 25, 31.25, 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 6400 });
                cont_FIR.AddRange(new double[] { 62.5, 125, 250, 500, 1000, 2000, 4000, 8000 });
            }
            else//MAX11216, MAX11270
            {
                cont_SINC.AddRange(new double[] { 1.9, 3.9, 7.8, 15.6, 31.2, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000, 64000 });
                single_cont.AddRange(new double[] { 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 4000, 6400, 12800 });
                cont_FIR.AddRange(new double[] { 125, 250, 500, 1000, 2000, 4000, 8000, 16000 });
            }

            //SetFullScaleAndOffset();

            Registers = new List<RegisterDescription>();

            List<BitInfo> R0bits = new List<BitInfo>();
            List<BitInfo> R1bits = new List<BitInfo>();
            List<BitInfo> R2bits = new List<BitInfo>();
            List<BitInfo> R3bits = new List<BitInfo>();
            List<BitInfo> R4bits = new List<BitInfo>();
            List<BitInfo> R5bits = new List<BitInfo>();
            List<BitInfo> R6bits = new List<BitInfo>();
            List<BitInfo> R7bits = new List<BitInfo>();
            List<BitInfo> R8bits = new List<BitInfo>();
            List<BitInfo> R9bits = new List<BitInfo>();
            List<BitInfo> R10bits = new List<BitInfo>();
            List<BitInfo> R11bits = new List<BitInfo>();

            //bit description for STAT
            R0bits.Add(new BitInfo() { bitIndex = "B[0]", name = "RDY", Description = "Ready: 1 = new conversion result is ready" });
            R0bits.Add(new BitInfo() { bitIndex = "B[1]", name = "MSTAT", Description = "Measurement Status: 1 = modulator is busy measuring" });
            R0bits.Add(new BitInfo() { bitIndex = "B[2]", name = "DOR", Description = "Data Overrange: 1 = data out of range" });
            R0bits.Add(new BitInfo() { bitIndex = "B[3]", name = "SYSGOR", Description = "System Gain Overrange: 1 = system gain out of range" });
            R0bits.Add(new BitInfo() { bitIndex = "B[7:4]", name = "RATE[3:0]", Description = "Data Rate: Data rate of previous conversion" });
            R0bits.Add(new BitInfo() { bitIndex = "B[8]", name = "AOR", Description = "Analog Overrange: input voltage > 1.3 x full scale" });
            R0bits.Add(new BitInfo() { bitIndex = "B[9]", name = "RDERR", Description = "Data Read Error: 1 = data read while data written" });
            R0bits.Add(new BitInfo() { bitIndex = "B[11:10]", name = "PSTAT[1:0]", Description = "Power Status\r\n00 = ADC is converting\r\n01 = powered down\r\n10 = standby" });
            R0bits.Add(new BitInfo() { bitIndex = "B[13:12]", name = "Reserved", Description = "-" });
            R0bits.Add(new BitInfo() { bitIndex = "B[14]", name = "ERROR", Description = "Error: 1 = CAL[1:0] set to invalid setting of 11" });
            R0bits.Add(new BitInfo() { bitIndex = "B[15]", name = "INRESET", Description = "In Reset: 1 = part is in reset mode" });

            //bit description for CTRL1
            R1bits.Add(new BitInfo() { bitIndex = "B[0]", name = "CONTSC", Description = "Continuous Single Cycle: 1 = continuous conversion" });
            R1bits.Add(new BitInfo() { bitIndex = "B[1]", name = "SCYCLE", Description = "Single Cycle: 1 = single cycle mode" });
            R1bits.Add(new BitInfo() { bitIndex = "B[2]", name = "FORMAT", Description = "Format: 1 = offset binary, 0 = two's complement" });
            R1bits.Add(new BitInfo() { bitIndex = "B[3]", name = "U/B", Description = "Input Range: 1 = unipolar, 0 = bipolar" });
            R1bits.Add(new BitInfo() { bitIndex = "B[5:4]", name = "PD[1:0]", Description = "Power State\r\n00 = normal\r\n01 = power down\r\n10 = standby\r\n11 = reset registers" });
            R1bits.Add(new BitInfo() { bitIndex = "B[6]", name = "SYNC", Description = "SYNC: 1 = continuous mode, 0 = pulse mode" });
            R1bits.Add(new BitInfo() { bitIndex = "B[7]", name = "EXTCK", Description = "Clock: 1 = external, 0 = internal" });

            //bit description for CTRL2
            R2bits.Add(new BitInfo() { bitIndex = "B[2:0]", name = "PGA[2:0]", Description = "PGA Gain\r\n000 = x1    100 = x16\r\n001 = x2    101 = x32\r\n010 = x4    110 = x64\r\n011 = x8    111 = x128" });
            R2bits.Add(new BitInfo() { bitIndex = "B[3]", name = "PGAEN", Description = "PGA Enable: 1 = enable" });
            R2bits.Add(new BitInfo() { bitIndex = "B[4]", name = "LPMODE", Description = "PGA Low Power: 1 = low power" });
            R2bits.Add(new BitInfo() { bitIndex = "B[5]", name = "BUFEN", Description = "Input Buffer Enable: 1 = enable" });
            R2bits.Add(new BitInfo() { bitIndex = "B[7:6]", name = "DGAIN[1:0]", Description = "Modulator Digital Gain\r\n00 = x1\r\n01 = x2\r\n10 = x4\r\n11 = x8" });

            //bit description for CTRL3
            if (name == "MAX11270")
            {
                R3bits.Add(new BitInfo() { bitIndex = "B[1:0]", name = "Reserved", Description = "-" });
                R3bits.Add(new BitInfo() { bitIndex = "B[2]", name = "Reserved", Description = "-" });
            }
            else
            {
                R3bits.Add(new BitInfo() { bitIndex = "B[1:0]", name = "FILT[1:0]", Description = "Filter Control\r\n0x = SINC\r\n10 = FIR\r\n11 = IIR" });
                R3bits.Add(new BitInfo() { bitIndex = "B[2]", name = "PHASE", Description = "FIR Phase: 1 = minimum, 0 = linear" });
            }

            R3bits.Add(new BitInfo() { bitIndex = "B[3]", name = "DATA32", Description = "32-bit Data: 1 = 32-bit data, 0 = 24-bit data" });
            R3bits.Add(new BitInfo() { bitIndex = "B[4]", name = "MODBITS", Description = "Modulator Output Mode Enable: 1 = enable" });
            R3bits.Add(new BitInfo() { bitIndex = "B[5]", name = "ENMSYNC", Description = "Modulator SYNC Pulse Enable: 1 = enable" });
            R3bits.Add(new BitInfo() { bitIndex = "B[7:6]", name = "Reserved", Description = "-" });


            //bit description for CTRL4
            R4bits.Add(new BitInfo() { bitIndex = "B[0]", name = "DIO1", Description = "GPIO1 Bit Value" });
            R4bits.Add(new BitInfo() { bitIndex = "B[1]", name = "DIO2", Description = "GPIO2 Bit Value" });
            R4bits.Add(new BitInfo() { bitIndex = "B[2]", name = "DIO3", Description = "GPIO3 Bit Value" });
            R4bits.Add(new BitInfo() { bitIndex = "B[3]", name = "Reserved", Description = "-" });
            R4bits.Add(new BitInfo() { bitIndex = "B[4]", name = "DIR1", Description = "GPIO1 Direction: 1 = output, 0 = input" });
            R4bits.Add(new BitInfo() { bitIndex = "B[5]", name = "DIR2", Description = "GPIO2 Direction: 1 = output, 0 = input" });
            R4bits.Add(new BitInfo() { bitIndex = "B[6]", name = "DIR3", Description = "GPIO3 Direction: 1 = output, 0 = input" });
            R4bits.Add(new BitInfo() { bitIndex = "B[7]", name = "Reserved", Description = "-" });

            //bit description for CTRL5
            R5bits.Add(new BitInfo() { bitIndex = "B[0]", name = "NOSCO", Description = "Disable Self Calibration Offset" });
            R5bits.Add(new BitInfo() { bitIndex = "B[1]", name = "NOSCG", Description = "Disable Self Calibration Gain" });
            R5bits.Add(new BitInfo() { bitIndex = "B[2]", name = "NOSYSO", Description = "Disable System Calibration Offset" });
            R5bits.Add(new BitInfo() { bitIndex = "B[3]", name = "NOSYSG", Description = "Disable System Calibration Gain" });
            R5bits.Add(new BitInfo() { bitIndex = "B[5:4]", name = "Reserved", Description = "-" });
            R5bits.Add(new BitInfo() { bitIndex = "B[7:6]", name = "CAL[1:0]", Description = "Calibration\r\n00 = Perform Self Calibration\r\n01 = Perform System Offset Calibration\r\n10 = Perform System Gain Calibration" });

            //bit description for Data
            R6bits.Add(new BitInfo() { bitIndex = "B[31:0]", name = "DATA", Description = "32-Bit Mode: MSB = bit31, LSB = bit0" });
            R6bits.Add(new BitInfo() { bitIndex = "B[31:8]", name = "DATA", Description = "24-Bit Mode: MSB = bit31, LSB = bit8" });

            //bit description for SOC
            R7bits.Add(new BitInfo() { bitIndex = "B[23:0]", name = "SOC[23:0]", Description = "System Offset Calibration: two's complement format" });

            //bit description for SGC
            R8bits.Add(new BitInfo() { bitIndex = "B[23:0]", name = "SGC[23:0]", Description = "System Gain Calibration: two's complement format" });

            //bit description for SCOC
            R9bits.Add(new BitInfo() { bitIndex = "B[23:0]", name = "SCOC[23:0]", Description = "Self Offset Calibration: two's complement format" });

            //bit description for SCGC
            R10bits.Add(new BitInfo() { bitIndex = "B[23:0]", name = "SCGC[23:0]", Description = "Self Gain Calibration: two's complement format" });

            //bit description for HPF
            R11bits.Add(new BitInfo() { bitIndex = "B[16:0]", name = "HPF[16:0]", Description = "High Pass Filter: corner frequency" });

            //add information to registers
            STAT = new RegisterDescription() { Address = 0x00, Name = "STAT", Description = "Status", ReadOnly = true, numBytes = 2, Value = 0x0000, BitInfo = R0bits };
            CTRL1 = new RegisterDescription() { Address = 0x01, Name = "CTRL1", Description = "Control 1", ReadOnly = false, numBytes = 1, Value = 0x02, BitInfo = R1bits };
            CTRL2 = new RegisterDescription() { Address = 0x02, Name = "CTRL2", Description = "Control 2", ReadOnly = false, numBytes = 1, Value = 0x00, BitInfo = R2bits };
            CTRL3 = new RegisterDescription() { Address = 0x03, Name = "CTRL3", Description = "Control 3", ReadOnly = false, numBytes = 1, Value = 0x61, BitInfo = R3bits };
            CTRL4 = new RegisterDescription() { Address = 0x04, Name = "CTRL4", Description = "Control 4", ReadOnly = false, numBytes = 1, Value = 0x08, BitInfo = R4bits };
            CTRL5 = new RegisterDescription() { Address = 0x05, Name = "CTRL5", Description = "Control 5", ReadOnly = false, numBytes = 1, Value = 0x0C, BitInfo = R5bits };
            DATA = new RegisterDescription() { Address = 0x06, Name = "DATA", Description = "Data", ReadOnly = true, numBytes = 4, Value = 0x00000000, BitInfo = R6bits };
            SOC_SPI = new RegisterDescription() { Address = 0x07, Name = "SOC_SPI", Description = "SPI System Offset Calibration", ReadOnly = false, numBytes = 3, Value = 0x000000, BitInfo = R7bits };
            SGC_SPI = new RegisterDescription() { Address = 0x08, Name = "SGC_SPI", Description = "SPI System Gain Calibration", ReadOnly = false, numBytes = 3, Value = 0x7FFFFF, BitInfo = R8bits };
            SCOC_SPI = new RegisterDescription() { Address = 0x09, Name = "SCOC_SPI", Description = "SPI Self Offset Calibration", ReadOnly = false, numBytes = 3, Value = 0x000000, BitInfo = R9bits };
            SCGC_SPI = new RegisterDescription() { Address = 0x0A, Name = "SCGC_SPI", Description = "SPI Self Gain Calibration", ReadOnly = false, numBytes = 3, Value = 0xBF851B, BitInfo = R10bits };
            HPF = new RegisterDescription() { Address = 0x0B, Name = "HPF", Description = "High Pass Filter", ReadOnly = false, numBytes = 2, Value = 0x0000, BitInfo = R11bits };
            SOC_ADC = new RegisterDescription() { Address = 0x15, Name = "SOC_ADC", Description = "ADC System Offset Calibration", ReadOnly = true, numBytes = 3, Value = 0x000000, BitInfo = R7bits };
            SGC_ADC = new RegisterDescription() { Address = 0x16, Name = "SGC_ADC", Description = "ADC System Gain Calibration", ReadOnly = true, numBytes = 3, Value = 0x000000, BitInfo = R8bits };
            SCOC_ADC = new RegisterDescription() { Address = 0x17, Name = "SCOC_ADC", Description = "ADC Self Offset Calibration", ReadOnly = true, numBytes = 3, Value = 0x000000, BitInfo = R9bits };
            SCGC_ADC = new RegisterDescription() { Address = 0x18, Name = "SCGC_ADC", Description = "ADC Self Gain Calibration", ReadOnly = true, numBytes = 3, Value = 0x000000, BitInfo = R10bits };

            //add registers to map
            /*
            Registers.Add(STAT);
            Registers.Add(CTRL1);
            Registers.Add(CTRL2);
            Registers.Add(CTRL3);
            Registers.Add(CTRL4);
            Registers.Add(CTRL5);
            Registers.Add(DATA);
            Registers.Add(SOC_SPI);
            Registers.Add(SGC_SPI);
            Registers.Add(SCOC_SPI);
            Registers.Add(SCGC_SPI);

            if (name != "MAX11270")
                Registers.Add(HPF);

            Registers.Add(SOC_ADC);
            Registers.Add(SGC_ADC);
            Registers.Add(SCOC_ADC);
            Registers.Add(SCGC_ADC);
            */
            //STATUS_REG_AUX
            for (int reg = 0; reg <= 0x3F; reg++)
            {
                Registers.Add(new RegisterDescription() { Address = (byte)reg, Name = RegisterNames[reg], Description = "ADC Self Gain Calibration", ReadOnly = true, numBytes = 1, Value = 0x000000, BitInfo = R10bits });
            }
            RegisterCount = Registers.Count;


            //bit description for command MODE 0 bits
            CommandMODE0Bits.Add(new BitInfo() { bitIndex = "B[3:0]", name = "RATE[3:0]", Description = "Data Rate for conversion" });
            CommandMODE0Bits.Add(new BitInfo() { bitIndex = "B[4]", name = "IMPD", Description = "1 = sleep mode\r\n0 = normal" });
            CommandMODE0Bits.Add(new BitInfo() { bitIndex = "B[5]", name = "CAL", Description = "1 = perform calibration\r\n0 = no calibration" });
            CommandMODE0Bits.Add(new BitInfo() { bitIndex = "B[6]", name = "MODE", Description = "MODE = 0 to start conversion, power down or calibrate" });
            CommandMODE0Bits.Add(new BitInfo() { bitIndex = "B[7]", name = "START", Description = "START = 1" });

            //bit description for command MODE 1 bits
            CommandMODE1Bits.Add(new BitInfo() { bitIndex = "B[0]", name = "R/W", Description = "Read/Write bit:\r\n1 = read, 0 = write" });
            CommandMODE1Bits.Add(new BitInfo() { bitIndex = "B[5:1]", name = "RS[4:0]", Description = "Register address" });
            CommandMODE1Bits.Add(new BitInfo() { bitIndex = "B[6]", name = "MODE", Description = "MODE = 1 for register access mode" });
            CommandMODE1Bits.Add(new BitInfo() { bitIndex = "B[7]", name = "START", Description = "START = 1" });
        }

        public void ResetReigsters()
        {
            CTRL1.Value = 0x02;
            CTRL2.Value = 0x00;
            CTRL3.Value = 0x61;
            CTRL4.Value = 0x08;
            CTRL5.Value = 0x0C;

            HPF.Value = 0;

            SOC_SPI.Value = 0;
            SGC_SPI.Value = 0x7FFFFF;
            SCOC_SPI.Value = 0;
            SCGC_SPI.Value = 0xBF851B;

        }

        String[] RegisterNames = {
        "Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"STATUS_REG_AUX",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"OUT_TEMP_L",
"OUT_TEMP_H",
"INT_COUNTER_REG",
"WHO_AM_I",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"Reserved",
"TEMP_CFG_REG",
"CTRL_REG1",
"CTRL_REG2",
"CTRL_REG3",
"CTRL_REG4",
"CTRL_REG5",
"CTRL_REG6",
"REFERENCE",
"STATUS_REG2",
"OUT_X_L",
"OUT_X_H",
"OUT_Y_L",
"OUT_Y_H",
"OUT_Z_L",
"OUT_Z_H",
"FIFO_CTRL_REG",
"FIFO_SRC_REG",
"INT1_CFG",
"INT1_SOURCE",
"INT1_THS",
"INT1_DURATION",
"INT2_CFG",
"INT2_SOURCE",
"INT2_THS",
"INT2_DURATION",
"CLICK_CFG",
"CLICK_SRC",
"CLICK_THS",
"TIME_LIMIT",
"TIME_LATENCY",
"TIME_WINDOW",
"Act_THS",
"Act_DUR"
    };


        /// When the name property changes the other properties will change based on the name
        public string Name
        {
            get
            {
                return name;
            }
            set
            {
                if (value != name)
                {
                    name = value;

                    //change register map and sampling rates for other devices
                    ChangeADCSetting();
                }

            }
        }

        public void ChangeADCSetting()
        {
            switch (name)
            {
                case "MAX11214":

                    if (cont_SINC[0] != 0.95)
                    {
                        cont_SINC.Clear();
                        single_cont.Clear();
                        cont_FIR.Clear();
                        cont_SINC.AddRange(new double[] { 0.95, 1.9, 3.9, 7.8, 15.6, 31.25, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000 });
                        single_cont.AddRange(new double[] { 25, 31.25, 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 6400 });
                        cont_FIR.AddRange(new double[] { 62.5, 125, 250, 500, 1000, 2000, 4000, 8000 });
                    }

                    if (!Registers.Contains(HPF))
                    {
                        Registers.Insert(11, HPF);
                        RegisterCount = Registers.Count;


                        CTRL3.BitInfo[0].name = "FILT[1:0]";
                        CTRL3.BitInfo[0].Description = "Filter Control\r\n0x = SINC\r\n10 = FIR\r\n11 = IIR";
                        CTRL3.BitInfo[1].name = "PHASE";
                        CTRL3.BitInfo[1].Description = "FIR Phase: 1 = minimum, 0 = linear";
                    }

                    break;
                case "MAX11216":

                    if (cont_SINC[0] != 1.9)
                    {
                        cont_SINC.Clear();
                        single_cont.Clear();
                        cont_FIR.Clear();

                        cont_SINC.AddRange(new double[] { 1.9, 3.9, 7.8, 15.6, 31.2, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000, 64000 });
                        single_cont.AddRange(new double[] { 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 4000, 6400, 12800 });
                        cont_FIR.AddRange(new double[] { 125, 250, 500, 1000, 2000, 4000, 8000, 16000 });
                    }

                    if (!Registers.Contains(HPF))
                    {
                        Registers.Insert(11, HPF);
                        RegisterCount = Registers.Count;


                        CTRL3.BitInfo[0].name = "FILT[1:0]";
                        CTRL3.BitInfo[0].Description = "Filter Control\r\n0x = SINC\r\n10 = FIR\r\n11 = IIR";
                        CTRL3.BitInfo[1].name = "PHASE";
                        CTRL3.BitInfo[1].Description = "FIR Phase: 1 = minimum, 0 = linear";
                    }

                    break;
                case "MAX11270":

                    if (cont_SINC[0] != 1.9)
                    {
                        cont_SINC.Clear();
                        single_cont.Clear();
                        cont_FIR.Clear();

                        cont_SINC.AddRange(new double[] { 1.9, 3.9, 7.8, 15.6, 31.2, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000, 64000 });
                        single_cont.AddRange(new double[] { 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 4000, 6400, 12800 });
                        cont_FIR.AddRange(new double[] { 125, 250, 500, 1000, 2000, 4000, 8000, 16000 });
                    }

                    if (Registers.Contains(HPF))
                    {
                        Registers.Remove(HPF);
                        RegisterCount = Registers.Count;


                        CTRL3.BitInfo[0].name = "Reserved";
                        CTRL3.BitInfo[0].Description = "-";
                        CTRL3.BitInfo[1].name = "Reserved";
                        CTRL3.BitInfo[1].Description = "-";
                    }

                    break;
                case "MAX11271":

                    if (cont_SINC[0] != 1.9)
                    {
                        cont_SINC.Clear();
                        single_cont.Clear();
                        cont_FIR.Clear();

                        cont_SINC.AddRange(new double[] { 1.9, 3.9, 7.8, 15.6, 31.2, 62.5, 125, 250, 500, 1000, 2000, 4000, 8000, 16000, 32000, 64000 });
                        single_cont.AddRange(new double[] { 50, 62.5, 100, 125, 200, 250, 400, 500, 800, 1000, 1600, 2000, 3200, 4000, 6400, 12800 });
                        cont_FIR.AddRange(new double[] { 125, 250, 500, 1000, 2000, 4000, 8000, 16000 });
                    }

                    if (Registers.Contains(HPF))
                    {
                        Registers.Remove(HPF);
                        RegisterCount = Registers.Count;


                        CTRL3.BitInfo[0].name = "Reserved";
                        CTRL3.BitInfo[0].Description = "-";
                        CTRL3.BitInfo[1].name = "Reserved";
                        CTRL3.BitInfo[1].Description = "-";
                    }
                    break;
                case "MAX11280":
                    break;
                case "MAX11281":
                    break;
                case "MAX11282":
                    break;
            }

        }

        public int Resolution
        {
            get
            {
                return resolution;

            }
            set
            {
                if (value != resolution)
                {
                    resolution = value;

                    //SetFullScaleAndOffset();
                }
            }
        }

        public double VREF
        {
            get
            {
                return VREFExternal;

            }
            set
            {
                if (value != VREFExternal)
                {
                    VREFExternal = value;

                    //SetFullScaleAndOffset();
                }
            }
        }

        public bool IsBipolar
        {
            get
            {
                return bipolar;

            }
            set
            {
                if (value != bipolar)
                {
                    bipolar = value;

                    //SetFullScaleAndOffset();
                }
            }
        }

        public bool IsTwosComp
        {
            get
            {
                return twosComp;

            }
            set
            {
                if (value != twosComp)
                {
                    twosComp = value;

                    //SetFullScaleAndOffset();
                }
            }
        }

        /// Calculates the Full scale value and offset of the ADC
        public void SetGainAndOffset(int res)
        {
            double FullScale;

            if (bipolar)
            {
                FullScale = 2 * VREFExternal;

                if (twosComp) //2's compliment
                    offset = 0;
                else          //offset binary
                    offset = 1 << (res - 1); //2^(resolution-1)
            }
            else //unipolar
            {
                FullScale = VREFExternal;
                offset = 0;
            }

            long digitalFullscale = ((long)1 << res) - 1;

            gain = FullScale / digitalFullscale;
        }
    }

    /// <summary>
    /// This class sets up a structure to hold register information
    /// </summary>
    /// @see RegisterMap
    public class RegisterDescription
    {
        public byte Address;
        public string Name;
        public bool ReadOnly;
        public int numBytes;
        public string Description;
        public int Value;
        public List<BitInfo> BitInfo;
    }

    ///<summary>
    /// This class sets up the structure to hold bit information of registers
    /// </summary>
    ///@see RegisterDescription
    public class BitInfo
    {
        public string name;
        public string bitIndex;
        public string Description;
    }
}
