示例#1
0
        private static void TestTemperatureHumidityAdjustment(Ccs811Sensor ccs811)
        {
            Console.WriteLine("Drastically change the temperature and humidity to see the impact on the calculation " +
                              "In real life, we'll get normal data and won't change them that often. " +
                              "The system does not react the best way when shake like this");
            // First use with the default ones, no changes should appear
            Temperature temp = Temperature.FromDegreesCelsius(25);
            Ratio       hum  = Ratio.FromPercent(50);

            Console.WriteLine($"Changing temperature and humidity reference to {temp.DegreesCelsius:0.00} C, {hum.Percent:0.0} %, baseline for calculation: {ccs811.BaselineAlgorithmCalculation}");
            ccs811.SetEnvironmentData(temp, hum);
            ReadAndDisplayDetails(ccs811, 100);
            // Changing with very different temperature
            temp = Temperature.FromDegreesCelsius(70);
            hum  = Ratio.FromPercent(53.8);
            Console.WriteLine($"Changing temperature and humidity reference to {temp.DegreesCelsius:0.00} C, {hum.Percent:0.0} %, baseline for calculation: {ccs811.BaselineAlgorithmCalculation}");
            ccs811.SetEnvironmentData(temp, hum);
            ReadAndDisplayDetails(ccs811, 100);

            temp = Temperature.FromDegreesCelsius(-25);
            hum  = Ratio.FromPercent(0.5);
            Console.WriteLine($"Changing temperature and humidity reference to {temp.DegreesCelsius:0.00} C, {hum.Percent:0.0} %, baseline for calculation: {ccs811.BaselineAlgorithmCalculation}");
            ccs811.SetEnvironmentData(temp, hum);
            ReadAndDisplayDetails(ccs811, 100);
            // Back to normal which still can lead to different results than initially
            // This is due to the baseline
            temp = Temperature.FromDegreesCelsius(25);
            hum  = Ratio.FromPercent(50);
            Console.WriteLine($"Changing temperature and humidity reference to {temp.DegreesCelsius:0.00} C, {hum.Percent:0.0} %, baseline for calculation: {ccs811.BaselineAlgorithmCalculation}");
            ccs811.SetEnvironmentData(temp, hum);
            ReadAndDisplayDetails(ccs811, 100);
        }
示例#2
0
        private static void ReadAndLog(Ccs811Sensor ccs811, int count = 10)
        {
            string toWrite = "Time;Success;eCO2 (ppm);eTVOC (ppb);Current (µA);ADC;ADC (V);Baseline";

            using (var fl = new StreamWriter("log.csv"))
            {
                fl.WriteLine(toWrite);
                for (int i = 0; i < count; i++)
                {
                    while (!ccs811.IsDataReady)
                    {
                        Thread.Sleep(10);
                    }

                    var error = ccs811.TryReadGasData(out VolumeConcentration eCO2, out VolumeConcentration eTVOC, out ElectricCurrent curr, out int adc);
                    toWrite = $"{DateTime.Now};{error};{eCO2.PartsPerMillion};{eTVOC.PartsPerBillion};{curr.Microamperes};{adc};{adc * 1.65 / 1023};{ccs811.BaselineAlgorithmCalculation}";
                    fl.WriteLine(toWrite);
                    Console.WriteLine(toWrite);
                    if (i % 100 == 0)
                    {
                        fl.Flush();
                    }
                }
            }
        }
示例#3
0
 private static void DisplayBasicInformatio(Ccs811Sensor ccs811)
 {
     Console.WriteLine($"Hardware identification: 0x{ccs811.HardwareIdentification:X2}, must be 0x81");
     Console.WriteLine($"Hardware version: 0x{ccs811.HardwareVersion:X2}, must be 0x1X where any X is valid");
     Console.WriteLine($"Application version: {ccs811.ApplicationVersion}");
     Console.WriteLine($"Boot loader version: {ccs811.BootloaderVersion}");
 }
示例#4
0
        private static void TestBaseline(Ccs811Sensor ccs811)
        {
            var baseline = ccs811.BaselineAlgorithmCalculation;

            Console.WriteLine($"Baseline calculation value: {baseline}, changing baseline");
            // Please refer to documentation, baseline is not a human readable number
            ccs811.BaselineAlgorithmCalculation = 50300;
            Console.WriteLine($"Baseline calculation value: {ccs811.BaselineAlgorithmCalculation}, changing baseline for the previous one");
            ccs811.BaselineAlgorithmCalculation = baseline;
            Console.WriteLine($"Baseline calculation value: {ccs811.BaselineAlgorithmCalculation}");
        }
示例#5
0
        private static void ReadAndDisplayDetails(Ccs811Sensor ccs811, int count = 10)
        {
            for (int i = 0; i < count; i++)
            {
                while (!ccs811.IsDataReady)
                {
                    Thread.Sleep(10);
                }

                var error = ccs811.TryReadGasData(out VolumeConcentration eCO2, out VolumeConcentration eTVOC, out ElectricCurrent curr, out int adc);
                Console.WriteLine($"Success: {error}, eCO2: {eCO2.PartsPerMillion} ppm, eTVOC: {eTVOC.PartsPerBillion} ppb, Current: {curr.Microamperes} µA, ADC: {adc} = {adc * 1.65 / 1023} V.");
            }
        }
示例#6
0
        private static void ReadAnDisplay(Ccs811Sensor ccs811, int count = 10)
        {
            for (int i = 0; i < count; i++)
            {
                while (!ccs811.IsDataReady)
                {
                    Thread.Sleep(10);
                }

                var error = ccs811.TryReadGasData(out VolumeConcentration eCO2, out VolumeConcentration eTVOC);
                Console.WriteLine($"Success: {error}, eCO2: {eCO2.PartsPerMillion} ppm, eTVOC: {eTVOC.PartsPerBillion} ppb");
            }
        }
示例#7
0
        private static void TestThresholdAndInterrupt(Ccs811Sensor ccs811)
        {
            if (!ccs811.InterruptEnable)
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine("Error: interrupt needs to be activated to run this test");
                Console.ResetColor();
                return;
            }

            ccs811.MeasurementReady += Ccs811MeasurementReady;
            // Setting up a range where we will see something in a normal environment
            VolumeConcentration low  = VolumeConcentration.FromPartsPerMillion(400);
            VolumeConcentration high = VolumeConcentration.FromPartsPerMillion(600);

            Console.WriteLine($"Setting up {low.PartsPerMillion}-{high.PartsPerMillion} range, in clear environment, that should raise interrupts. Wait 3 minutes and change mode. Blow on the sensor and wait a bit.");
            Console.ForegroundColor = ConsoleColor.Yellow;
            Console.WriteLine("Warning: only the first measurement to cross the threshold is raised.");
            Console.ResetColor();
            ccs811.SetThreshold(low, high);
            DateTime dt = DateTime.Now.AddMinutes(3);

            while (dt > DateTime.Now)
            {
                Thread.Sleep(10);
            }

            low  = VolumeConcentration.FromPartsPerMillion(15000);
            high = VolumeConcentration.FromPartsPerMillion(20000);
            Console.WriteLine($"Changing threshold for {low.PartsPerMillion}-{high.PartsPerMillion}, a non reachable range in clear environment. No measurement should appear in next 3 minutes");
            dt = DateTime.Now.AddMinutes(3);
            ccs811.SetThreshold(low, high);
            while (dt > DateTime.Now)
            {
                Thread.Sleep(10);
            }
        }
示例#8
0
        /// <inheritdoc/>
        public override void Initialize()
        {
            this.LogStartInitialization();
            this.i2cDevice = this.Controller.GetI2CConnection(this.DeviceId);
            this.sensor    = new Ccs811Sensor(this.i2cDevice)
            {
                OperationMode = OperationMode.Idle,
            };

            this.LogMessage($"Hardware identification: 0x{this.sensor.HardwareIdentification:X2}, must be 0x81");
            this.LogMessage($"Hardware version: 0x{this.sensor.HardwareVersion:X2}, must be 0x1X where any X is valid");
            this.LogMessage($"Application version: {this.sensor.ApplicationVersion}");
            this.LogMessage($"Boot loader version: {this.sensor.BootloaderVersion}");
            var baseline = this.sensor.BaselineAlgorithmCalculation;

            this.LogMessage($"Baseline calculation value: {baseline}, changing baseline");
            this.sensor.BaselineAlgorithmCalculation = 50300;
            this.LogMessage($"Baseline calculation value: {this.sensor.BaselineAlgorithmCalculation}, changing baseline for the previous one");
            this.sensor.BaselineAlgorithmCalculation = baseline;
            this.LogMessage($"Baseline calculation value: {this.sensor.BaselineAlgorithmCalculation}");
            this.sensor.OperationMode = OperationMode.ConstantPower1Second;
            this.IsInitialized        = true;
            this.LogStartSuccess();
        }
示例#9
0
        private static void Main(string[] args)
        {
            Ccs811Sensor ccs811;

            Console.WriteLine("Hello CCS811!");
            // Simple menu to select native I2C/GPIO or thru FT4222, with GPIO pins and specific features to test
            Console.WriteLine("Select which platform I2C/GPIO you want to use:");
            Console.WriteLine(" 1. Native I2C/GPIO");
            Console.WriteLine(" 2. FT4222");
            var platformChoice = Console.ReadKey();

            Console.WriteLine();
            Console.WriteLine("Which I2C address do you want to use? Use the first one if Address pin is to ground, use the second one if to VCC.");
            Console.WriteLine($" 1. First 0x{Ccs811Sensor.I2cFirstAddress:X2}");
            Console.WriteLine($" 2. Second 0x{Ccs811Sensor.I2cSecondAddress:X2}");
            var addressChoice = Console.ReadKey();

            Console.WriteLine();
            Console.WriteLine("Do you want to the interrupt pin and events?");
            Console.WriteLine("(Y)es,(N)o");
            var pinChoice = Console.ReadKey();

            Console.WriteLine();
            int pinInterrupt = CheckAndAskPinNumber(pinChoice.KeyChar);

            Console.WriteLine($"Do you want to use the Wake pin?");
            Console.WriteLine("(Y)es,(N)o");
            pinChoice = Console.ReadKey();
            Console.WriteLine();
            int pinWake = CheckAndAskPinNumber(pinChoice.KeyChar);

            Console.WriteLine($"Do you want to use the Reset pin?");
            Console.WriteLine("(Y)es,(N)o");
            pinChoice = Console.ReadKey();
            Console.WriteLine();
            int pinReset = CheckAndAskPinNumber(pinChoice.KeyChar);

            if (platformChoice.KeyChar == '1')
            {
                Console.WriteLine("Creating an instance of a CCS811 using the platform drivers.");
                ccs811 = new Ccs811Sensor(I2cDevice.Create(new I2cConnectionSettings(3, addressChoice.KeyChar == '1' ? Ccs811Sensor.I2cFirstAddress : Ccs811Sensor.I2cSecondAddress)), pinWake: pinWake, pinInterruption: pinInterrupt, pinReset: pinReset);
            }
            else if (platformChoice.KeyChar == '2')
            {
                Console.WriteLine("Creating an instance of a CCS811 using FT4222 drivers.");
                var ftdiI2C        = new Ft4222I2c(new I2cConnectionSettings(0, addressChoice.KeyChar == '1' ? Ccs811Sensor.I2cFirstAddress : Ccs811Sensor.I2cSecondAddress));
                var gpioController = new GpioController(PinNumberingScheme.Board, new Ft4222Gpio());
                ccs811 = new Ccs811Sensor(ftdiI2C, gpioController, pinWake, pinInterrupt, pinReset, false);
            }
            else
            {
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine("Error: Invalid platform choice.");
                Console.ResetColor();
                return;
            }

            Console.WriteLine("Choose your operation mode:");
            int           i             = 0;
            OperationMode operationMode = OperationMode.ConstantPower1Second;

            foreach (var mode in Enum.GetValues(typeof(OperationMode)))
            {
                Console.WriteLine($" {i++}. {mode}");
            }

            var modeChoice = Console.ReadKey();

            try
            {
                // Converting the char to decimal, removing '0' = 0x30
                int selectedMode = Convert.ToInt32(modeChoice.KeyChar) - 0x30;
                if ((selectedMode >= 0) && (selectedMode <= 4))
                {
                    operationMode = (OperationMode)Convert.ToInt32(selectedMode);
                }
                else
                {
                    Console.ForegroundColor = ConsoleColor.Red;
                    Console.WriteLine($"Error selecting mode, default {operationMode} will be selected");
                }
            }
            catch (StackOverflowException)
            {
                Console.ForegroundColor = ConsoleColor.Yellow;
                Console.WriteLine($"Error selecting mode, default {operationMode} will be selected");
            }

            Console.ResetColor();
            DisplayBasicInformatio(ccs811);
            Console.WriteLine($"Current operating mode: {ccs811.OperationMode}, changing for {operationMode}");
            ccs811.OperationMode = operationMode;
            Console.WriteLine($"Current operating mode: {ccs811.OperationMode}");
            Console.ForegroundColor = ConsoleColor.Yellow;
            Console.WriteLine($"Warning: the sensor needs to run for 48h in operation mode {OperationMode.ConstantPower1Second} before getting accurate results. " +
                              $"Also, every time you'll start the sensor, it will need approximately 20 minutes to get accurate results as well");
            Console.ResetColor();

            if (pinInterrupt >= 0)
            {
                Console.WriteLine("Interruption mode selected.");
                Console.WriteLine("Do you want to enable Threshold interruption?");
                Console.WriteLine("(Y)es,(N)o");
                var threshChoice = Console.ReadKey();
                Console.WriteLine();
                if ((threshChoice.KeyChar == 'Y') || (threshChoice.KeyChar == 'y'))
                {
                    TestThresholdAndInterrupt(ccs811);
                }
                else
                {
                    Console.Write(", once a measurement will be available, it will be displayed. Press any key to exit the program.");
                    ccs811.MeasurementReady += Ccs811MeasurementReady;
                    while (!Console.KeyAvailable)
                    {
                        Thread.Sleep(10);
                    }
                }
            }
            else
            {
                Console.WriteLine("What to you want to test?");
                Console.WriteLine(" 1. Read and display gas information for 10 times.");
                Console.WriteLine(" 2. Read and display gas information for 1000 times.");
                Console.WriteLine(" 3. Read and display detailed gas information for 10 times.");
                Console.WriteLine(" 4. Read and display detailed gas information for 1000 times.");
                Console.WriteLine(" 5. Read, load and change back the baseline.");
                Console.WriteLine(" 6. Test temperature and humidity changes.");
                Console.WriteLine(" 7. Read and log gas information 10000 times.");
                var operationChoice = Console.ReadKey();
                Console.WriteLine();
                switch (operationChoice.KeyChar)
                {
                case '1':
                    ReadAnDisplay(ccs811);
                    break;

                case '2':
                    ReadAnDisplay(ccs811, 1000);
                    break;

                case '3':
                    ReadAndDisplayDetails(ccs811);
                    break;

                case '4':
                    ReadAndDisplayDetails(ccs811, 1000);
                    break;

                case '5':
                    TestBaseline(ccs811);
                    break;

                case '6':
                    TestTemperatureHumidityAdjustment(ccs811);
                    break;

                case '7':
                    Console.WriteLine("Result file will be log.csv. The file is flushed on the disk every 100 results.");
                    ReadAndLog(ccs811, 10000);
                    break;

                default:
                    Console.ForegroundColor = ConsoleColor.Red;
                    Console.WriteLine("Error: Sorry, didn't get your choice, program will now exit.");
                    Console.ResetColor();
                    break;
                }
            }

            Console.WriteLine($"Current operating mode: {ccs811.OperationMode}, changing for {OperationMode.Idle}");
            ccs811.OperationMode = OperationMode.Idle;
            Console.WriteLine($"Current operating mode: {ccs811.OperationMode}");
            // Dispose the CCS811 sensor
            ccs811.Dispose();
        }