Utility library for HSP SPo2 HR demo including user interface, board support adn accelerometer.
Revision 0:a12d6976d64c, committed 2018-12-17
- Comitter:
- gmehmet
- Date:
- Mon Dec 17 13:58:56 2018 +0300
- Commit message:
- create and put source to HSP demo utility repo
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoAccelerometer/bmi160.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,723 @@ +/********************************************************************** +* Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES +* OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +* +* Except as contained in this notice, the name of Maxim Integrated +* Products, Inc. shall not be used except as stated in the Maxim Integrated +* Products, Inc. Branding Policy. +* +* The mere transfer of this software does not imply any licenses +* of trade secrets, proprietary technology, copyrights, patents, +* trademarks, maskwork rights, or any other form of intellectual +* property whatsoever. Maxim Integrated Products, Inc. retains all +* ownership rights. +**********************************************************************/ + + +#include "bmi160.h" + + +const struct BMI160::AccConfig BMI160::DEFAULT_ACC_CONFIG = {SENS_2G, + ACC_US_OFF, + ACC_BWP_2, + ACC_ODR_8}; + +const struct BMI160::GyroConfig BMI160::DEFAULT_GYRO_CONFIG = {DPS_2000, + GYRO_BWP_2, + GYRO_ODR_8}; + + +//***************************************************************************** +int32_t BMI160::setSensorPowerMode(Sensors sensor, PowerModes pwrMode) +{ + int32_t rtnVal = -1; + + switch(sensor) + { + case MAG: + rtnVal = writeRegister(CMD, (MAG_SET_PMU_MODE | pwrMode)); + break; + + case GYRO: + rtnVal = writeRegister(CMD, (GYR_SET_PMU_MODE | pwrMode)); + break; + + case ACC: + rtnVal = writeRegister(CMD, (ACC_SET_PMU_MODE | pwrMode)); + break; + + default: + rtnVal = -1; + break; + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::setSensorConfig(const AccConfig &config) +{ + uint8_t data[2]; + + data[0] = ((config.us << ACC_US_POS) | (config.bwp << ACC_BWP_POS) | + (config.odr << ACC_ODR_POS)); + data[1] = config.range; + + return writeBlock(ACC_CONF, ACC_RANGE, data); +} + + +//***************************************************************************** +int32_t BMI160::setSensorConfig(const GyroConfig &config) +{ + uint8_t data[2]; + + data[0] = ((config.bwp << GYRO_BWP_POS) | (config.odr << GYRO_ODR_POS)); + data[1] = config.range; + + return writeBlock(GYR_CONF, GYR_RANGE, data); +} + + +//***************************************************************************** +int32_t BMI160::getSensorConfig(AccConfig &config) +{ + uint8_t data[2]; + int32_t rtnVal = readBlock(ACC_CONF, ACC_RANGE, data); + + if(rtnVal == RTN_NO_ERROR) + { + config.range = static_cast<BMI160::AccRange>( + (data[1] & ACC_RANGE_MASK)); + config.us = static_cast<BMI160::AccUnderSampling>( + ((data[0] & ACC_US_MASK) >> ACC_US_POS)); + config.bwp = static_cast<BMI160::AccBandWidthParam>( + ((data[0] & ACC_BWP_MASK) >> ACC_BWP_POS)); + config.odr = static_cast<BMI160::AccOutputDataRate>( + ((data[0] & ACC_ODR_MASK) >> ACC_ODR_POS)); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorConfig(GyroConfig &config) +{ + uint8_t data[2]; + int32_t rtnVal = readBlock(GYR_CONF, GYR_RANGE, data); + + if(rtnVal == RTN_NO_ERROR) + { + config.range = static_cast<BMI160::GyroRange>( + (data[1] & GYRO_RANGE_MASK)); + config.bwp = static_cast<BMI160::GyroBandWidthParam>( + ((data[0] & GYRO_BWP_MASK) >> GYRO_BWP_POS)); + config.odr = static_cast<BMI160::GyroOutputDataRate>( + ((data[0] & GYRO_ODR_MASK) >> GYRO_ODR_POS)); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorAxis(SensorAxis axis, AxisData &data, AccRange range) +{ + uint8_t localData[2]; + int32_t rtnVal; + + switch(axis) + { + case X_AXIS: + rtnVal = readBlock(DATA_14, DATA_15, localData); + break; + + case Y_AXIS: + rtnVal = readBlock(DATA_16, DATA_17, localData); + break; + + case Z_AXIS: + rtnVal = readBlock(DATA_18, DATA_19, localData); + break; + + default: + rtnVal = -1; + break; + } + + if(rtnVal == RTN_NO_ERROR) + { + data.raw = ((localData[1] << 8) | localData[0]); + switch(range) + { + case SENS_2G: + data.scaled = (data.raw/SENS_2G_LSB_PER_G); + break; + + case SENS_4G: + data.scaled = (data.raw/SENS_4G_LSB_PER_G); + break; + + case SENS_8G: + data.scaled = (data.raw/SENS_8G_LSB_PER_G); + break; + + case SENS_16G: + data.scaled = (data.raw/SENS_16G_LSB_PER_G); + break; + } + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorAxis(SensorAxis axis, AxisData &data, GyroRange range) +{ + uint8_t localData[2]; + int32_t rtnVal; + + switch(axis) + { + case X_AXIS: + rtnVal = readBlock(DATA_8, DATA_9, localData); + break; + + case Y_AXIS: + rtnVal = readBlock(DATA_10, DATA_11, localData); + break; + + case Z_AXIS: + rtnVal = readBlock(DATA_12, DATA_13, localData); + break; + + default: + rtnVal = -1; + break; + } + + if(rtnVal == RTN_NO_ERROR) + { + data.raw = ((localData[1] << 8) | localData[0]); + switch(range) + { + case DPS_2000: + data.scaled = (data.raw/SENS_2000_DPS_LSB_PER_DPS); + break; + + case DPS_1000: + data.scaled = (data.raw/SENS_1000_DPS_LSB_PER_DPS); + break; + + case DPS_500: + data.scaled = (data.raw/SENS_500_DPS_LSB_PER_DPS); + break; + + case DPS_250: + data.scaled = (data.raw/SENS_250_DPS_LSB_PER_DPS); + break; + + case DPS_125: + data.scaled = (data.raw/SENS_125_DPS_LSB_PER_DPS); + break; + } + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorXYZ(SensorData &data, AccRange range) +{ + uint8_t localData[6]; + int32_t rtnVal = readBlock(DATA_14, DATA_19, localData); + + if (m_use_irq == true && bmi160_irq_asserted == false) + return -1; + + bmi160_irq_asserted = false; + if(rtnVal == RTN_NO_ERROR) + { + data.xAxis.raw = ((localData[1] << 8) | localData[0]); + data.yAxis.raw = ((localData[3] << 8) | localData[2]); + data.zAxis.raw = ((localData[5] << 8) | localData[4]); + + switch(range) + { + case SENS_2G: + data.xAxis.scaled = (data.xAxis.raw/SENS_2G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_2G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_2G_LSB_PER_G); + break; + + case SENS_4G: + data.xAxis.scaled = (data.xAxis.raw/SENS_4G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_4G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_4G_LSB_PER_G); + break; + + case SENS_8G: + data.xAxis.scaled = (data.xAxis.raw/SENS_8G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_8G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_8G_LSB_PER_G); + break; + + case SENS_16G: + data.xAxis.scaled = (data.xAxis.raw/SENS_16G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_16G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_16G_LSB_PER_G); + break; + } + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorXYZ(SensorData &data, GyroRange range) +{ + uint8_t localData[6]; + int32_t rtnVal = readBlock(DATA_8, DATA_13, localData); + + if(rtnVal == RTN_NO_ERROR) + { + data.xAxis.raw = ((localData[1] << 8) | localData[0]); + data.yAxis.raw = ((localData[3] << 8) | localData[2]); + data.zAxis.raw = ((localData[5] << 8) | localData[4]); + + switch(range) + { + case DPS_2000: + data.xAxis.scaled = (data.xAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + break; + + case DPS_1000: + data.xAxis.scaled = (data.xAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + break; + + case DPS_500: + data.xAxis.scaled = (data.xAxis.raw/SENS_500_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_500_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_500_DPS_LSB_PER_DPS); + break; + + case DPS_250: + data.xAxis.scaled = (data.xAxis.raw/SENS_250_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_250_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_250_DPS_LSB_PER_DPS); + break; + + case DPS_125: + data.xAxis.scaled = (data.xAxis.raw/SENS_125_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_125_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_125_DPS_LSB_PER_DPS); + break; + } + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorXYZandSensorTime(SensorData &data, + SensorTime &sensorTime, + AccRange range) +{ + uint8_t localData[9]; + int32_t rtnVal = readBlock(DATA_14, SENSORTIME_2, localData); + if(rtnVal == RTN_NO_ERROR) + { + data.xAxis.raw = ((localData[1] << 8) | localData[0]); + data.yAxis.raw = ((localData[3] << 8) | localData[2]); + data.zAxis.raw = ((localData[5] << 8) | localData[4]); + + switch(range) + { + case SENS_2G: + data.xAxis.scaled = (data.xAxis.raw/SENS_2G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_2G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_2G_LSB_PER_G); + break; + + case SENS_4G: + data.xAxis.scaled = (data.xAxis.raw/SENS_4G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_4G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_4G_LSB_PER_G); + break; + + case SENS_8G: + data.xAxis.scaled = (data.xAxis.raw/SENS_8G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_8G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_8G_LSB_PER_G); + break; + + case SENS_16G: + data.xAxis.scaled = (data.xAxis.raw/SENS_16G_LSB_PER_G); + data.yAxis.scaled = (data.yAxis.raw/SENS_16G_LSB_PER_G); + data.zAxis.scaled = (data.zAxis.raw/SENS_16G_LSB_PER_G); + break; + } + + sensorTime.raw = ((localData[8] << 16) | (localData[7] << 8) | + localData[6]); + sensorTime.seconds = (sensorTime.raw * SENSOR_TIME_LSB); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getSensorXYZandSensorTime(SensorData &data, + SensorTime &sensorTime, + GyroRange range) +{ + uint8_t localData[16]; + int32_t rtnVal = readBlock(DATA_8, SENSORTIME_2, localData); + if(rtnVal == RTN_NO_ERROR) + { + data.xAxis.raw = ((localData[1] << 8) | localData[0]); + data.yAxis.raw = ((localData[3] << 8) | localData[2]); + data.zAxis.raw = ((localData[5] << 8) | localData[4]); + + switch(range) + { + case DPS_2000: + data.xAxis.scaled = (data.xAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + break; + + case DPS_1000: + data.xAxis.scaled = (data.xAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + break; + + case DPS_500: + data.xAxis.scaled = (data.xAxis.raw/SENS_500_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_500_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_500_DPS_LSB_PER_DPS); + break; + + case DPS_250: + data.xAxis.scaled = (data.xAxis.raw/SENS_250_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_250_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_250_DPS_LSB_PER_DPS); + break; + + case DPS_125: + data.xAxis.scaled = (data.xAxis.raw/SENS_125_DPS_LSB_PER_DPS); + data.yAxis.scaled = (data.yAxis.raw/SENS_125_DPS_LSB_PER_DPS); + data.zAxis.scaled = (data.zAxis.raw/SENS_125_DPS_LSB_PER_DPS); + break; + } + + sensorTime.raw = ((localData[14] << 16) | (localData[13] << 8) | + localData[12]); + sensorTime.seconds = (sensorTime.raw * SENSOR_TIME_LSB); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getGyroAccXYZandSensorTime(SensorData &accData, + SensorData &gyroData, + SensorTime &sensorTime, + AccRange accRange, + GyroRange gyroRange) +{ + uint8_t localData[16]; + int32_t rtnVal = readBlock(DATA_8, SENSORTIME_2, localData); + if(rtnVal == RTN_NO_ERROR) + { + gyroData.xAxis.raw = ((localData[1] << 8) | localData[0]); + gyroData.yAxis.raw = ((localData[3] << 8) | localData[2]); + gyroData.zAxis.raw = ((localData[5] << 8) | localData[4]); + + accData.xAxis.raw = ((localData[7] << 8) | localData[6]); + accData.yAxis.raw = ((localData[9] << 8) | localData[8]); + accData.zAxis.raw = ((localData[11] << 8) | localData[10]); + + switch(gyroRange) + { + case DPS_2000: + gyroData.xAxis.scaled = (gyroData.xAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + gyroData.yAxis.scaled = (gyroData.yAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + gyroData.zAxis.scaled = (gyroData.zAxis.raw/SENS_2000_DPS_LSB_PER_DPS); + break; + + case DPS_1000: + gyroData.xAxis.scaled = (gyroData.xAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + gyroData.yAxis.scaled = (gyroData.yAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + gyroData.zAxis.scaled = (gyroData.zAxis.raw/SENS_1000_DPS_LSB_PER_DPS); + break; + + case DPS_500: + gyroData.xAxis.scaled = (gyroData.xAxis.raw/SENS_500_DPS_LSB_PER_DPS); + gyroData.yAxis.scaled = (gyroData.yAxis.raw/SENS_500_DPS_LSB_PER_DPS); + gyroData.zAxis.scaled = (gyroData.zAxis.raw/SENS_500_DPS_LSB_PER_DPS); + break; + + case DPS_250: + gyroData.xAxis.scaled = (gyroData.xAxis.raw/SENS_250_DPS_LSB_PER_DPS); + gyroData.yAxis.scaled = (gyroData.yAxis.raw/SENS_250_DPS_LSB_PER_DPS); + gyroData.zAxis.scaled = (gyroData.zAxis.raw/SENS_250_DPS_LSB_PER_DPS); + break; + + case DPS_125: + gyroData.xAxis.scaled = (gyroData.xAxis.raw/SENS_125_DPS_LSB_PER_DPS); + gyroData.yAxis.scaled = (gyroData.yAxis.raw/SENS_125_DPS_LSB_PER_DPS); + gyroData.zAxis.scaled = (gyroData.zAxis.raw/SENS_125_DPS_LSB_PER_DPS); + break; + } + + switch(accRange) + { + case SENS_2G: + accData.xAxis.scaled = (accData.xAxis.raw/SENS_2G_LSB_PER_G); + accData.yAxis.scaled = (accData.yAxis.raw/SENS_2G_LSB_PER_G); + accData.zAxis.scaled = (accData.zAxis.raw/SENS_2G_LSB_PER_G); + break; + + case SENS_4G: + accData.xAxis.scaled = (accData.xAxis.raw/SENS_4G_LSB_PER_G); + accData.yAxis.scaled = (accData.yAxis.raw/SENS_4G_LSB_PER_G); + accData.zAxis.scaled = (accData.zAxis.raw/SENS_4G_LSB_PER_G); + break; + + case SENS_8G: + accData.xAxis.scaled = (accData.xAxis.raw/SENS_8G_LSB_PER_G); + accData.yAxis.scaled = (accData.yAxis.raw/SENS_8G_LSB_PER_G); + accData.zAxis.scaled = (accData.zAxis.raw/SENS_8G_LSB_PER_G); + break; + + case SENS_16G: + accData.xAxis.scaled = (accData.xAxis.raw/SENS_16G_LSB_PER_G); + accData.yAxis.scaled = (accData.yAxis.raw/SENS_16G_LSB_PER_G); + accData.zAxis.scaled = (accData.zAxis.raw/SENS_16G_LSB_PER_G); + break; + } + + sensorTime.raw = ((localData[14] << 16) | (localData[13] << 8) | + localData[12]); + sensorTime.seconds = (sensorTime.raw * SENSOR_TIME_LSB); + } + + return rtnVal; +} + +int32_t BMI160::setSampleRate(int sample_rate) +{ + int sr_reg_val = -1; + int i; + const uint16_t odr_table[][2] = { + {25, GYRO_ODR_6}, ///<25Hz + {50, GYRO_ODR_7}, ///<50Hz + {100, GYRO_ODR_8}, ///<100Hz + {200, GYRO_ODR_9}, ///<200Hz + {400, GYRO_ODR_10}, ///<400Hz + {800, GYRO_ODR_11}, ///<800Hz + {1600, GYRO_ODR_12}, ///<1600Hz + {3200, GYRO_ODR_13}, ///<3200Hz + }; + + int num_sr = sizeof(odr_table)/sizeof(odr_table[0]); + for (i = 0; i < num_sr; i++) { + if (sample_rate == odr_table[i][0]) { + sr_reg_val = odr_table[i][1]; + break; + } + } + + if (sr_reg_val == -1) + return -2; + + AccConfig accConfigRead; + if (getSensorConfig(accConfigRead) == BMI160::RTN_NO_ERROR) { + accConfigRead.odr = (AccOutputDataRate)sr_reg_val; + return setSensorConfig(accConfigRead) == BMI160::RTN_NO_ERROR ? 0 : -1; + } else + return -1; +} + + +//***************************************************************************** +int32_t BMI160::getSensorTime(SensorTime &sensorTime) +{ + uint8_t localData[3]; + int32_t rtnVal = readBlock(SENSORTIME_0, SENSORTIME_2, localData); + + if(rtnVal == RTN_NO_ERROR) + { + sensorTime.raw = ((localData[2] << 16) | (localData[1] << 8) | + localData[0]); + sensorTime.seconds = (sensorTime.raw * SENSOR_TIME_LSB); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160::getTemperature(float *temp) +{ + uint8_t data[2]; + uint16_t rawTemp; + + int32_t rtnVal = readBlock(TEMPERATURE_0, TEMPERATURE_1, data); + if(rtnVal == RTN_NO_ERROR) + { + rawTemp = ((data[1] << 8) | data[0]); + if(rawTemp & 0x8000) + { + *temp = (23.0F - ((0x10000 - rawTemp)/512.0F)); + } + else + { + *temp = ((rawTemp/512.0F) + 23.0F); + } + } + + return rtnVal; +} + +//*********************************************************************************** +int32_t BMI160::BMI160_DefaultInitalize(){ + + //soft reset the accelerometer + writeRegister(CMD ,SOFT_RESET); + wait(0.1); + + //Power up sensors in normal mode + if(setSensorPowerMode(BMI160::GYRO, BMI160::SUSPEND) != BMI160::RTN_NO_ERROR){ + printf("Failed to set gyroscope power mode\n"); + } + + wait(0.1); + + if(setSensorPowerMode(BMI160::ACC, BMI160::NORMAL) != BMI160::RTN_NO_ERROR){ + printf("Failed to set accelerometer power mode\n"); + } + wait(0.1); + + BMI160::AccConfig accConfig; + BMI160::AccConfig accConfigRead; + accConfig.range = BMI160::SENS_2G; + accConfig.us = BMI160::ACC_US_OFF; + accConfig.bwp = BMI160::ACC_BWP_2; + accConfig.odr = BMI160::ACC_ODR_6; + if(setSensorConfig(accConfig) == BMI160::RTN_NO_ERROR) + { + if(getSensorConfig(accConfigRead) == BMI160::RTN_NO_ERROR) + { + if((accConfig.range != accConfigRead.range) || + (accConfig.us != accConfigRead.us) || + (accConfig.bwp != accConfigRead.bwp) || + (accConfig.odr != accConfigRead.odr)) + { + printf("ACC read data desn't equal set data\n\n"); + printf("ACC Set Range = %d\n", accConfig.range); + printf("ACC Set UnderSampling = %d\n", accConfig.us); + printf("ACC Set BandWidthParam = %d\n", accConfig.bwp); + printf("ACC Set OutputDataRate = %d\n\n", accConfig.odr); + printf("ACC Read Range = %d\n", accConfigRead.range); + printf("ACC Read UnderSampling = %d\n", accConfigRead.us); + printf("ACC Read BandWidthParam = %d\n", accConfigRead.bwp); + printf("ACC Read OutputDataRate = %d\n\n", accConfigRead.odr); + } + + } + else + { + printf("Failed to read back accelerometer configuration\n"); + } + } + else + { + printf("Failed to set accelerometer configuration\n"); + } + return 0; +} + +//*********************************************************************************** +int32_t BMI160::enable_data_ready_interrupt() { + uint8_t data = 0; + uint8_t temp = 0; + int32_t result; + + result = readRegister(INT_EN_1, &data); + temp = data & ~0x10; + data = temp | ((1 << 4) & 0x10); + /* Writing data to INT ENABLE 1 Address */ + result |= writeRegister(INT_EN_1, data); + + // configure in_out ctrl + //bmi160_get_regs(BMI160_INT_OUT_CTRL_ADDR, &data, 1, dev); + result |= readRegister(INT_OUT_CTRL, &data); + data = 0x09; + result |= writeRegister(INT_OUT_CTRL,data); + + //config int latch + //bmi160_get_regs(BMI160_INT_LATCH_ADDR, &data, 1, dev); + result |= readRegister(INT_LATCH, &data); + data = 0x0F; + result |= writeRegister(INT_LATCH, data); + + //bmi160_get_regs(BMI160_INT_MAP_1_ADDR, &data, 1, dev); + result |= readRegister(INT_MAP_1, &data); + data = 0x80; + result |= writeRegister(INT_MAP_1, data); + + if(result != 0){ + printf("BMI160::%s failed.\r\n", __func__); + return -1; + } + + m_bmi160_irq->disable_irq(); + m_bmi160_irq->mode(PullUp); + m_bmi160_irq->fall(this, &BMI160::irq_handler); + m_bmi160_irq->enable_irq(); + return 0; +} + +void BMI160::irq_handler() { + bmi160_irq_asserted = true; +} + +int32_t BMI160::reset() { + if (m_use_irq) + m_bmi160_irq->disable_irq(); + bmi160_irq_asserted = false; + writeRegister(CMD, SOFT_RESET); + return 0; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoAccelerometer/bmi160.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,845 @@ +/********************************************************************** +* Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES +* OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +* +* Except as contained in this notice, the name of Maxim Integrated +* Products, Inc. shall not be used except as stated in the Maxim Integrated +* Products, Inc. Branding Policy. +* +* The mere transfer of this software does not imply any licenses +* of trade secrets, proprietary technology, copyrights, patents, +* trademarks, maskwork rights, or any other form of intellectual +* property whatsoever. Maxim Integrated Products, Inc. retains all +* ownership rights. +**********************************************************************/ + + +#ifndef BMI160_H +#define BMI160_H + +#include "mbed.h" + +/** +@brief The BMI160 is a small, low power, low noise 16-bit inertial measurement +unit designed for use in mobile applications like augmented reality or indoor +navigation which require highly accurate, real-time sensor data. + +In full operation mode, with both the accelerometer and gyroscope enabled, the +current consumption is typically 950 μA, enabling always-on applications in +battery driven devices. It is available in a compact 14-pin 2.5 x 3.0 x 0.8 mm³ +LGA package." + +This class is an abstract base class and can not be instaniated, use BMI160_I2C +or BMI160_SPI. +*/ +class BMI160 +{ +public: + + ///Return value on success. + static const uint8_t RTN_NO_ERROR = 0; + + ///Sensor types + enum Sensors + { + MAG = 0, ///<Optional external sensor + GYRO, ///<Angular rate sensor + ACC ///<g sensor + }; + + ///Sensor Axis + enum SensorAxis + { + X_AXIS = 0, + Y_AXIS, + Z_AXIS + }; + + ///Structure for axis data + struct AxisData + { + int16_t raw; ///<Axis raw data + float scaled; ///<Axis scaled data + }; + + ///Structure for sensor time data + struct SensorTime + { + uint32_t raw; ///<raw SensorTime + float seconds; ///<SensorTime as seconds + }; + + ///Period of internal counter + static const float SENSOR_TIME_LSB = 39e-6; + + ///Structure for holding sensor data + struct SensorData + { + AxisData xAxis; ///<Sensor X axis data + AxisData yAxis; ///<Sensor Y axis data + AxisData zAxis; ///<Sensor Z axis data + }; + + + ///BMI160 registers + enum Registers + { + CHIP_ID = 0x00, ///<Chip Identification. + ERR_REG = 0x02, ///<Reports sensor error flags. Flags reset when read. + PMU_STATUS, ///<Reports current power mode for sensors. + DATA_0, ///<MAG_X axis bits7:0 + DATA_1, ///<MAG_X axis bits15:8 + DATA_2, ///<MAG_Y axis bits7:0 + DATA_3, ///<MAG_Y axis bits15:8 + DATA_4, ///<MAG_Z axis bits7:0 + DATA_5, ///<MAG_Z axis bits15:8 + DATA_6, ///<RHALL bits7:0 + DATA_7, ///<RHALL bits15:8 + DATA_8, ///<GYR_X axis bits7:0 + DATA_9, ///<GYR_X axis bits15:8 + DATA_10, ///<GYR_Y axis bits7:0 + DATA_11, ///<GYR_Y axis bits15:8 + DATA_12, ///<GYR_Z axis bits7:0 + DATA_13, ///<GYR_Z axis bits15:8 + DATA_14, ///<ACC_X axis bits7:0 + DATA_15, ///<ACC_X axis bits15:8 + DATA_16, ///<ACC_Y axis bits7:0 + DATA_17, ///<ACC_Y axis bits15:8 + DATA_18, ///<ACC_Z axis bits7:0 + DATA_19, ///<ACC_Z axis bits15:8 + SENSORTIME_0, ///<24bit counter synchronized with data, bits7:0 + SENSORTIME_1, ///<24bit counter synchronized with data, bits15:8 + SENSORTIME_2, ///<24bit counter synchronized with data, bits23:16 + STATUS, ///<Reports sensors status flags + INT_STATUS_0, ///<Contains interrupt status flags + INT_STATUS_1, ///<Contains interrupt status flags + INT_STATUS_2, ///<Contains interrupt status flags + INT_STATUS_3, ///<Contains interrupt status flags + TEMPERATURE_0, ///<Contains temperature of sensor, bits7:0 + TEMPERATURE_1, ///<Contains temperature of sensor, bits15:8 + FIFO_LENGTH_0, ///<Current fill level of FIFO, bits7:0 + FIFO_LENGTH_1, ///<Current fill level of FIFO, bits10:8 + FIFO_DATA, ///<FIFO data read out register, burst read + ACC_CONF = 0x40, ///<Set ODR, bandwidth, and read mode of accelerometer + ACC_RANGE, ///<Sets accelerometer g-range + GYR_CONF, ///<Set ODR, bandwidth, and read mode of gyroscope + GYR_RANGE, ///<Sets gyroscope angular rate measurement range + MAG_CONF, ///<Sets ODR of magnetometer interface + FIFO_DOWNS, ///<Sets down sampling ratios of accel and gyro data + ///<for FIFO + FIFO_CONFIG_0, ///<Sets FIFO Watermark + FIFO_CONFIG_1, ///<Sets which sensor data is available in FIFO, + ///<Header/Headerless mode, Ext Int tagging, Sensortime + MAG_IF_0 = 0x4B, ///<Magnetometer 7-bit I2C address, bits7:1 + MAG_IF_1, ///<Magnetometer interface configuration + MAG_IF_2, ///<Magnetometer address to read + MAG_IF_3, ///<Magnetometer address to write + MAG_IF_4, ///<Magnetometer data to write + INT_EN_0, ///<Interrupt enable bits + INT_EN_1, ///<Interrupt enable bits + INT_EN_2, ///<Interrupt enable bits + INT_OUT_CTRL, ///<Contains the behavioral configuration of INT pins + INT_LATCH, ///<Contains the interrupt rest bit and the interrupt + ///<mode selection + INT_MAP_0, ///<Controls which interrupt signals are mapped to the + ///<INT1 and INT2 pins + INT_MAP_1, ///<Controls which interrupt signals are mapped to the + ///<INT1 and INT2 pins + INT_MAP_2, ///<Controls which interrupt signals are mapped to the + ///<INT1 and INT2 pins + INT_DATA_0, ///<Contains the data source definition for the two + ///<interrupt groups + INT_DATA_1, ///<Contains the data source definition for the two + ///<interrupt groups + INT_LOWHIGH_0, ///<Contains the configuration for the low g interrupt + INT_LOWHIGH_1, ///<Contains the configuration for the low g interrupt + INT_LOWHIGH_2, ///<Contains the configuration for the low g interrupt + INT_LOWHIGH_3, ///<Contains the configuration for the low g interrupt + INT_LOWHIGH_4, ///<Contains the configuration for the low g interrupt + INT_MOTION_0, ///<Contains the configuration for the any motion and + ///<no motion interrupts + INT_MOTION_1, ///<Contains the configuration for the any motion and + ///<no motion interrupts + INT_MOTION_2, ///<Contains the configuration for the any motion and + ///<no motion interrupts + INT_MOTION_3, ///<Contains the configuration for the any motion and + ///<no motion interrupts + INT_TAP_0, ///<Contains the configuration for the tap interrupts + INT_TAP_1, ///<Contains the configuration for the tap interrupts + INT_ORIENT_0, ///<Contains the configuration for the oeientation + ///<interrupt + INT_ORIENT_1, ///<Contains the configuration for the oeientation + ///<interrupt + INT_FLAT_0, ///<Contains the configuration for the flat interrupt + INT_FLAT_1, ///<Contains the configuration for the flat interrupt + FOC_CONF, ///<Contains configuration for the fast offset + ///<compensation for the accelerometer and gyroscope + CONF, ///<Configuration of sensor, nvm_prog_en bit + IF_CONF, ///<Contains settings for the digital interface + PMU_TRIGGER, ///<Sets trigger conditions to change gyro power modes + SELF_TEST, ///<Self test configuration + NV_CONF = 0x70, ///<Contains settings for the digital interface + OFFSET_0, ///<Contains offset comp values for acc_off_x7:0 + OFFSET_1, ///<Contains offset comp values for acc_off_y7:0 + OFFSET_2, ///<Contains offset comp values for acc_off_z7:0 + OFFSET_3, ///<Contains offset comp values for gyr_off_x7:0 + OFFSET_4, ///<Contains offset comp values for gyr_off_y7:0 + OFFSET_5, ///<Contains offset comp values for gyr_off_z7:0 + OFFSET_6, ///<gyr/acc offset enable bit and gyr_off_(zyx) bits9:8 + STEP_CNT_0, ///<Step counter bits 15:8 + STEP_CNT_1, ///<Step counter bits 7:0 + STEP_CONF_0, ///<Contains configuration of the step detector + STEP_CONF_1, ///<Contains configuration of the step detector + CMD = 0x7E ///<Command register triggers operations like + ///<softreset, NVM programming, etc. + }; + + + ///@name ERR_REG(0x02) + ///Error register data + ///@{ + + static const uint8_t FATAL_ERR_MASK = 0x01; + static const uint8_t FATAL_ERR_POS = 0x00; + static const uint8_t ERR_CODE_MASK = 0x1E; + static const uint8_t ERR_CODE_POS = 0x01; + static const uint8_t I2C_FAIL_ERR_MASK = 0x20; + static const uint8_t I2C_FAIL_ERR_POS = 0x05; + static const uint8_t DROP_CMD_ERR_MASK = 0x40; + static const uint8_t DROP_CMD_ERR_POS = 0x06; + static const uint8_t MAG_DRDY_ERR_MASK = 0x80; + static const uint8_t MAG_DRDY_ERR_POS = 0x08; + + ///Enumerated error codes + enum ErrorCodes + { + NO_ERROR = 0, ///<No Error + ERROR_1, ///<Listed as error + ERROR_2, ///<Listed as error + LPM_INT_PFD, ///<Low-power mode and interrupt uses pre-filtered + ///<data + ODR_MISMATCH = 0x06, ///<ODRs of enabled sensors in headerless mode do + ///<not match + PFD_USED_LPM ///<Pre-filtered data are used in low power mode + }; + ///@} + + + ///@name ACC_CONF(0x40) and ACC_RANGE(0x41) + ///Data for configuring accelerometer + ///@{ + + static const uint8_t ACC_ODR_MASK = 0x0F; + static const uint8_t ACC_ODR_POS = 0x00; + static const uint8_t ACC_BWP_MASK = 0x70; + static const uint8_t ACC_BWP_POS = 0x04; + static const uint8_t ACC_US_MASK = 0x80; + static const uint8_t ACC_US_POS = 0x07; + static const uint8_t ACC_RANGE_MASK = 0x0F; + static const uint8_t ACC_RANGE_POS = 0x00; + + ///Accelerometer output data rates + enum AccOutputDataRate + { + ACC_ODR_1 = 1, ///< 25/32Hz + ACC_ODR_2, ///< 25/16Hz + ACC_ODR_3, ///< 25/8Hz + ACC_ODR_4, ///< 25/4Hz + ACC_ODR_5, ///< 25/2Hz + ACC_ODR_6, ///< 25Hz + ACC_ODR_7, ///< 50Hz + ACC_ODR_8, ///< 100Hz + ACC_ODR_9, ///< 200Hz + ACC_ODR_10, ///< 400Hz + ACC_ODR_11, ///< 800Hz + ACC_ODR_12 ///< 1600Hz + }; + + ///Accelerometer bandwidth parameters + enum AccBandWidthParam + { + ACC_BWP_0 = 0, ///< Average 1 cycle; when acc_us = 0 OSR4 + ACC_BWP_1, ///< Average 2 cycles; when acc_us = 0 OSR2 + ACC_BWP_2, ///< Average 4 cycles; when acc_us = 0 normal mode + ACC_BWP_3, ///< Average 8 cycles + ACC_BWP_4, ///< Average 16 cycles + ACC_BWP_5, ///< Average 32 cycles + ACC_BWP_6, ///< Average 64 cycles + ACC_BWP_7 ///< Average 128 cycles + }; + + ///Accelerometer undersampling + enum AccUnderSampling + { + ACC_US_OFF = 0, + ACC_US_ON + }; + + ///Accelerometer ranges + enum AccRange + { + SENS_2G = 0x03, ///<Accelerometer range +-2G + SENS_4G = 0x05, ///<Accelerometer range +-4G + SENS_8G = 0x08, ///<Accelerometer range +-8G + SENS_16G = 0x0C ///<Accelerometer range +-16G + }; + + static const float SENS_2G_LSB_PER_G = 16384.0F; + static const float SENS_4G_LSB_PER_G = 8192.0F; + static const float SENS_8G_LSB_PER_G = 4096.0F; + static const float SENS_16G_LSB_PER_G = 2048.0F; + + ///Accelerometer configuration data structure + struct AccConfig + { + AccRange range; ///<Accelerometer range + AccUnderSampling us; ///<Accelerometr undersampling mode + AccBandWidthParam bwp; ///<Accelerometer bandwidth param + AccOutputDataRate odr; ///<Accelerometr output data rate + }; + + ///Accelerometer default configuration + static const AccConfig DEFAULT_ACC_CONFIG; + ///@} + + + ///@name GYR_CONF(0x42) and GYR_RANGE(0x43) + ///Data for configuring gyroscope + ///@{ + + static const uint8_t GYRO_ODR_MASK = 0x0F; + static const uint8_t GYRO_ODR_POS = 0x00; + static const uint8_t GYRO_BWP_MASK = 0x30; + static const uint8_t GYRO_BWP_POS = 0x04; + static const uint8_t GYRO_RANGE_MASK = 0x07; + static const uint8_t GYRO_RANGE_POS = 0x00; + + ///Gyroscope output data rates + enum GyroOutputDataRate + { + GYRO_ODR_6 = 0x06, ///<25Hz + GYRO_ODR_7 = 0x07, ///<50Hz + GYRO_ODR_8 = 0x08, ///<100Hz + GYRO_ODR_9 = 0x09, ///<200Hz + GYRO_ODR_10 = 0x0A, ///<400Hz + GYRO_ODR_11 = 0x0B, ///<800Hz + GYRO_ODR_12 = 0x0C, ///<1600Hz + GYRO_ODR_13 = 0x0D ///<3200Hz + }; + + ///Gyroscope bandwidth paramaters + enum GyroBandWidthParam + { + GYRO_BWP_0 = 0, ///<OSR4 Over Sampling Rate of 4 + GYRO_BWP_1, ///<OSR2 Over Sampling Rate of 2 + GYRO_BWP_2 ///<Normal Mode, Equidistant Sampling + }; + + ///Gyroscope ranges + enum GyroRange + { + DPS_2000 = 0, ///<+-2000dps, 16.4LSB/dps + DPS_1000, ///<+-1000dps, 32.8LSB/dps + DPS_500, ///<+-500dps, 65.6LSB/dps + DPS_250, ///<+-250dps, 131.2LSB/dps + DPS_125 ///<+-125dps, 262.4LSB/dps, + }; + + static const float SENS_2000_DPS_LSB_PER_DPS = 16.4F; + static const float SENS_1000_DPS_LSB_PER_DPS = 32.8F; + static const float SENS_500_DPS_LSB_PER_DPS = 65.6F; + static const float SENS_250_DPS_LSB_PER_DPS = 131.2F; + static const float SENS_125_DPS_LSB_PER_DPS = 262.4F; + + ///Gyroscope configuration data structure + struct GyroConfig + { + GyroRange range; ///<Gyroscope range + GyroBandWidthParam bwp; ///<Gyroscope bandwidth param + GyroOutputDataRate odr; ///<Gyroscope output data rate + }; + + ///Gyroscope default configuration + static const GyroConfig DEFAULT_GYRO_CONFIG; + ///@} + + + ///Enumerated power modes + enum PowerModes + { + SUSPEND = 0, ///<Acc and Gyro, No sampling, No FIFO data readout + NORMAL, ///<Acc and Gyro, Full chip operation + LOW_POWER, ///<Acc duty-cycling between suspend and normal + FAST_START_UP ///<Gyro start up delay time to normal mode <= 10 ms + }; + + + ///Enumerated commands used with CMD register + enum Commands + { + START_FOC = 0x03, ///<Starts Fast Offset Calibrartion + ACC_SET_PMU_MODE = 0x10, ///<Sets acc power mode + GYR_SET_PMU_MODE = 0x14, ///<Sets gyro power mode + MAG_SET_PMU_MODE = 0x18, ///<Sets mag power mode + PROG_NVM = 0xA0, ///<Writes NVM backed registers into NVM + FIFO_FLUSH = 0xB0, ///<Clears FIFO + INT_RESET, ///<Clears interrupt engine, INT_STATUS, and + ///<the interrupt pin + STEP_CNT_CLR, ///<Triggers reset of the step counter + SOFT_RESET = 0xB6 ///<Triggers a reset including a reboot. + }; + + + ///@brief BMI160 Destructor.\n + /// + ///On Entry: + ///@param[in] none + /// + ///On Exit: + ///@param[out] none + /// + ///@returns none + virtual ~BMI160(){ } + + + ///@brief Reads a single register.\n + /// + ///On Entry: + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read register on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readRegister(Registers reg, uint8_t *data) = 0; + + + ///@brief Writes a single register.\n + /// + ///On Entry: + ///@param[in] data - data to write to register + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeRegister(Registers reg, const uint8_t data) = 0; + + + ///@brief Reads a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are readable. Function reads up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start reading from + ///@param[in] stopReg - register to stop reading from + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read registers on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readBlock(Registers startReg, Registers stopReg, + uint8_t *data) = 0; + + + ///@brief Writes a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are writeable. Function writes up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start writing at + ///@param[in] stopReg - register to stop writing at + ///@param[in] data - pointer to data to write to registers + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeBlock(Registers startReg, Registers stopReg, + const uint8_t *data) = 0; + + + ///@brief Sets sensors power mode through CMD register.\n + ///@details Observe command execution times given in datasheet.\n + /// + ///On Entry: + ///@param[in] sensor - Sensor which power mode we are setting + ///@param[in] pwrMode - Desired powermode of the sensor + /// + ///On Exit: + ///@param[out] + /// + ///@returns 0 on success, non 0 on failure + int32_t setSensorPowerMode(Sensors sensor, PowerModes pwrMode); + + + ///@brief Configure sensor.\n + /// + ///On Entry: + ///@param[in] config - sSensor configuration data structure + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + int32_t setSensorConfig(const AccConfig &config); + int32_t setSensorConfig(const GyroConfig &config); + + + ///@brief Get sensor configuration.\n + /// + ///On Entry: + ///@param[in] config - Sensor configuration data structure + /// + ///On Exit: + ///@param[out] config - on success, holds sensor's current + ///configuration + /// + ///@returns 0 on success, non 0 on failure + int32_t getSensorConfig(AccConfig &config); + int32_t getSensorConfig(GyroConfig &config); + + + ///@brief Get sensor axis.\n + /// + ///On Entry: + ///@param[in] axis - Sensor axis + ///@param[in] data - AxisData structure + ///@param[in] range - Sensor range + /// + ///On Exit: + ///@param[out] data - Structure holds raw and scaled axis data + /// + ///@returns 0 on success, non 0 on failure + int32_t getSensorAxis(SensorAxis axis, AxisData &data, AccRange range); + int32_t getSensorAxis(SensorAxis axis, AxisData &data, GyroRange range); + + + ///@brief Get sensor xyz axis.\n + /// + ///On Entry: + ///@param[in] data - SensorData structure + ///@param[in] range - Sensor range + /// + ///On Exit: + ///@param[out] data - Structure holds raw and scaled data for all three axis + /// + ///@returns 0 on success, non 0 on failure + int32_t getSensorXYZ(SensorData &data, AccRange range); + int32_t getSensorXYZ(SensorData &data, GyroRange range); + + + ///@brief Get sensor xyz axis and sensor time.\n + /// + ///On Entry: + ///@param[in] data - SensorData structure + ///@param[in] sensorTime - SensorTime structure for data + ///@param[in] range - Sensor range + /// + ///On Exit: + ///@param[out] data - Structure holds raw and scaled data for all three axis + ///@param[out] sensorTime - Holds sensor time on success + /// + ///@returns 0 on success, non 0 on failure + int32_t getSensorXYZandSensorTime(SensorData &data, SensorTime &sensorTime, + AccRange range); + int32_t getSensorXYZandSensorTime(SensorData &data, SensorTime &sensorTime, + GyroRange range); + + + ///@brief Get Gyroscope/Accelerometer data and sensor time.\n + /// + ///On Entry: + ///@param[in] accData - Sensor data structure for accelerometer + ///@param[in] gyroData - Sensor data structure for gyroscope + ///@param[in] sensorTime - SensorTime data structure + ///@param[in] accRange - Accelerometer range + ///@param[in] gyroRange - Gyroscope range + /// + ///On Exit: + ///@param[out] accData - Synchronized accelerometer data + ///@param[out] gyroData - Synchronized gyroscope data + ///@param[out] sensorTime - Synchronized sensor time + /// + ///@returns 0 on success, non 0 on failure + int32_t getGyroAccXYZandSensorTime(SensorData &accData, + SensorData &gyroData, + SensorTime &sensorTime, + AccRange accRange, GyroRange gyroRange); + + + ///@brief Get sensor time.\n + /// + ///On Entry: + ///@param[in] sensorTime - SensorTime structure for data + /// + ///On Exit: + ///@param[out] sensorTime - Holds sensor time on success + /// + ///@returns returns 0 on success, non 0 on failure + int32_t getSensorTime(SensorTime &sensorTime); + + + ///@brief Get die temperature.\n + /// + ///On Entry: + ///@param[in] temp - pointer to float for temperature + /// + ///On Exit: + ///@param[out] temp - on success, holds the die temperature + /// + ///@returns 0 on success, non 0 on failure + int32_t getTemperature(float *temp); + + // Initialize BMI160 with default parameters: + // set GYRO: Suspended, Acc Normal Mode, ODR:25 Hz + int32_t BMI160_DefaultInitalize(); + + // + // + int32_t enable_data_ready_interrupt(); + + // + // Set sample rate + // This function can be alled after BMI160_DefaultInitalize + int32_t setSampleRate(int sample_rate); + + /// @brief Soft reset + /// + int32_t reset(); + +private: + bool m_use_irq; + bool bmi160_irq_asserted; + InterruptIn *m_bmi160_irq; + void irq_handler(); + +protected: + BMI160(InterruptIn *int_pin): m_bmi160_irq(int_pin), m_use_irq(true) { + bmi160_irq_asserted = false; + } + + BMI160(): m_use_irq(false) { } +}; + + +/** +@brief BMI160_I2C - supports BMI160 object with I2C interface +*/ +class BMI160_I2C: public BMI160 +{ +public: + + ///BMI160 default I2C address. + static const uint8_t I2C_ADRS_SDO_LO = 0x68; + ///BMI160 optional I2C address. + static const uint8_t I2C_ADRS_SDO_HI = 0x69; + + + ///@brief BMI160_I2C Constructor.\n + /// + ///On Entry: + ///@param[in] i2cBus - reference to I2C bus for this device + ///@param[in] i2cAdrs - 7-bit I2C address + /// + ///On Exit: + ///@param[out] none + /// + ///@returns none + BMI160_I2C(I2C *i2cBus, uint8_t i2cAdrs); + + ///@brief BMI160_I2C Constructor.\n + /// + ///On Entry: + ///@param[in] i2cBus - reference to I2C bus for this device + ///@param[in] i2cAdrs - 7-bit I2C address + ///@param[in] int_pin - Interrupt pin + /// + ///On Exit: + ///@param[out] none + /// + ///@returns none + BMI160_I2C(I2C *i2cBus, uint8_t i2cAdrs, InterruptIn *int_pin); + + ///@brief Reads a single register.\n + /// + ///On Entry: + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read register on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readRegister(Registers reg, uint8_t *data); + + + ///@brief Writes a single register.\n + /// + ///On Entry: + ///@param[in] data - data to write to register + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeRegister(Registers reg, const uint8_t data); + + + ///@brief Reads a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are readable. Function reads up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start reading from + ///@param[in] stopReg - register to stop reading from + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read registers on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readBlock(Registers startReg, Registers stopReg, + uint8_t *data); + + + ///@brief Writes a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are writeable. Function writes up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start writing at + ///@param[in] stopReg - register to stop writing at + ///@param[in] data - pointer to data to write to registers + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeBlock(Registers startReg, Registers stopReg, + const uint8_t *data); + +private: + I2C *m_i2cBus; + uint8_t m_Wadrs, m_Radrs; +}; + + +/** +@brief BMI160_SPI - supports BMI160 object with SPI interface +*/ +class BMI160_SPI: public BMI160 +{ +public: + + ///@brief BMI160_SPI Constructor.\n + /// + ///On Entry: + ///@param[in] spiBus - reference to SPI bus for this device + ///@param[in] cs - reference to DigitalOut used for chip select + /// + ///On Exit: + ///@param[out] none + /// + ///@returns none + BMI160_SPI(SPI *spiBus, DigitalOut &cs); + + + ///@brief Reads a single register.\n + /// + ///On Entry: + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read register on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readRegister(Registers reg, uint8_t *data); + + + ///@brief Writes a single register.\n + /// + ///On Entry: + ///@param[in] data - data to write to register + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeRegister(Registers reg, const uint8_t data); + + + ///@brief Reads a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are readable. Function reads up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start reading from + ///@param[in] stopReg - register to stop reading from + ///@param[in] data - pointer to memory for storing read data + /// + ///On Exit: + ///@param[out] data - holds contents of read registers on success + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t readBlock(Registers startReg, Registers stopReg, + uint8_t *data); + + + ///@brief Writes a block of registers.\n + ///@detail User must ensure that all registers between 'startReg' and + ///'stopReg' exist and are writeable. Function writes up to, including, + ///'stopReg'.\n + /// + ///On Entry: + ///@param[in] startReg - register to start writing at + ///@param[in] stopReg - register to stop writing at + ///@param[in] data - pointer to data to write to registers + /// + ///On Exit: + ///@param[out] none + /// + ///@returns 0 on success, non 0 on failure + virtual int32_t writeBlock(Registers startReg, Registers stopReg, + const uint8_t *data); + +private: + + SPI *m_spiBus; + DigitalOut m_cs; +}; + +#endif /* BMI160_H */ + + +///@brief fx documentation template.\n +/// +///On Entry: +///@param[in] none +/// +///On Exit: +///@param[out] none +/// +///@returns none
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoAccelerometer/bmi160_i2c.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,103 @@ +/********************************************************************** +* Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES +* OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +* +* Except as contained in this notice, the name of Maxim Integrated +* Products, Inc. shall not be used except as stated in the Maxim Integrated +* Products, Inc. Branding Policy. +* +* The mere transfer of this software does not imply any licenses +* of trade secrets, proprietary technology, copyrights, patents, +* trademarks, maskwork rights, or any other form of intellectual +* property whatsoever. Maxim Integrated Products, Inc. retains all +* ownership rights. +**********************************************************************/ + + +#include "bmi160.h" + + +//***************************************************************************** +BMI160_I2C::BMI160_I2C(I2C *i2cBus, uint8_t i2cAdrs) +:m_i2cBus(i2cBus), m_Wadrs(i2cAdrs << 1), m_Radrs((i2cAdrs << 1) | 1) +{ + +} + +BMI160_I2C::BMI160_I2C(I2C *i2cBus, uint8_t i2cAdrs, InterruptIn *int_pin) +:m_i2cBus(i2cBus), m_Wadrs(i2cAdrs << 1), m_Radrs((i2cAdrs << 1) | 1), BMI160(int_pin) +{ + +} + +//***************************************************************************** +int32_t BMI160_I2C::readRegister(Registers reg, uint8_t *data) +{ + int32_t rtnVal = -1; + char packet[] = {static_cast<char>(reg)}; + + if(m_i2cBus->write(m_Wadrs, packet, 1) == 0) + { + rtnVal = m_i2cBus->read(m_Radrs, reinterpret_cast<char *>(data), 1); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160_I2C::writeRegister(Registers reg, const uint8_t data) +{ + char packet[] = {static_cast<char>(reg), static_cast<char>(data)}; + + return m_i2cBus->write(m_Wadrs, packet, sizeof(packet)); +} + + +//***************************************************************************** +int32_t BMI160_I2C::readBlock(Registers startReg, Registers stopReg, +uint8_t *data) +{ + int32_t rtnVal = -1; + int32_t numBytes = ((stopReg - startReg) + 1); + char packet[] = {static_cast<char>(startReg)}; + + if(m_i2cBus->write(m_Wadrs, packet, 1) == 0) + { + rtnVal = m_i2cBus->read(m_Radrs, reinterpret_cast<char *>(data), numBytes); + } + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160_I2C::writeBlock(Registers startReg, Registers stopReg, +const uint8_t *data) +{ + int32_t numBytes = ((stopReg - startReg) + 1); + char packet[numBytes + 1]; + + packet[0] = static_cast<char>(startReg); + + memcpy(packet + 1, data, numBytes); + + return m_i2cBus->write(m_Wadrs, packet, sizeof(packet)); +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoAccelerometer/bmi160_spi.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,80 @@ +/********************************************************************** +* Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. +* +* Permission is hereby granted, free of charge, to any person obtaining a +* copy of this software and associated documentation files (the "Software"), +* to deal in the Software without restriction, including without limitation +* the rights to use, copy, modify, merge, publish, distribute, sublicense, +* and/or sell copies of the Software, and to permit persons to whom the +* Software is furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included +* in all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS +* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +* IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES +* OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, +* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +* OTHER DEALINGS IN THE SOFTWARE. +* +* Except as contained in this notice, the name of Maxim Integrated +* Products, Inc. shall not be used except as stated in the Maxim Integrated +* Products, Inc. Branding Policy. +* +* The mere transfer of this software does not imply any licenses +* of trade secrets, proprietary technology, copyrights, patents, +* trademarks, maskwork rights, or any other form of intellectual +* property whatsoever. Maxim Integrated Products, Inc. retains all +* ownership rights. +**********************************************************************/ + + +#include "bmi160.h" + + +//***************************************************************************** +BMI160_SPI::BMI160_SPI(SPI *spiBus, DigitalOut &cs) +:m_spiBus(spiBus), m_cs(cs) +{ + +} + + +//***************************************************************************** +int32_t BMI160_SPI::readRegister(Registers reg, uint8_t *data) +{ + int32_t rtnVal = -1; + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160_SPI::writeRegister(Registers reg, const uint8_t data) +{ + int32_t rtnVal = -1; + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160_SPI::readBlock(Registers startReg, Registers stopReg, +uint8_t *data) +{ + int32_t rtnVal = -1; + + return rtnVal; +} + + +//***************************************************************************** +int32_t BMI160_SPI::writeBlock(Registers startReg, Registers stopReg, +const uint8_t *data) +{ + int32_t rtnVal = -1; + + return rtnVal; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoPlatform/MAX20303.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,366 @@ +/******************************************************************************* + * Copyright (C) 2018 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ + + +#include "MAX20303.h" + + + +//****************************************************************************** +MAX20303::MAX20303(I2C *i2c): + m_i2c(i2c), m_writeAddress(MAX20303_SLAVE_WR_ADDR), + m_readAddress(MAX20303_SLAVE_RD_ADDR) +{ +} + + +//****************************************************************************** +MAX20303::~MAX20303(void) +{ + //empty block +} + + +//****************************************************************************** +int MAX20303::LDO1Config() +{ + int32_t ret = 0; + uint8_t val; +// ret |= writeReg(MAX20303::REG_AP_CMDOUT, 0x40); +// ret |= writeReg(MAX20303::REG_AP_DATOUT0, 0x05); +// ret |= writeReg(MAX20303::REG_AP_DATOUT1, 0x34); +// +// readReg(MAX20303::REG_AP_CMDOUT, val); +// readReg(MAX20303::REG_AP_DATOUT0, val); +// readReg(MAX20303::REG_AP_DATOUT1, val); + appcmdoutvalue_ = 0x40; + appdatainoutbuffer_[0] = 0x05; + appdatainoutbuffer_[1] = 0x34; + AppWrite(2); + + return ret; +} + +//****************************************************************************** +int MAX20303::LDO2Config() +{ + int32_t ret = 0; + uint8_t val; + appcmdoutvalue_ = 0x42; + appdatainoutbuffer_[0] = 0x01; + appdatainoutbuffer_[1] = 0x15; // 0.9V + (0.1V * number) = 3V + AppWrite(2); + + return ret; +} + + +//****************************************************************************** +int MAX20303::writeReg(registers_t reg, uint8_t value) +{ + int32_t ret; + + char cmdData[2] = {reg, value}; + + ret = m_i2c->write(m_writeAddress, cmdData, sizeof(cmdData)); + //printf("MAX20303 write reg[0x%X]=0x%X, ret=%d\r\n", (uint32_t)reg, value, ret) + + if (ret != 0) + return MAX20303_ERROR; + + return MAX20303_NO_ERROR; +} + + +//****************************************************************************** +int MAX20303::readReg(registers_t reg, uint8_t &value) +{ + int32_t ret; + + char data = reg; + + ret = m_i2c->write(m_writeAddress, &data, sizeof(data)); + if (ret != 0) { + printf("%s - failed - ret: %d\n", __func__); + return MAX20303_ERROR; + } + + ret = m_i2c->read(m_readAddress, &data, sizeof(data)); + if (ret != 0) { + printf("%s - failed - ret: %d\n", __func__); + return MAX20303_ERROR; + } + + value = data; + printf("MAX20303 read reg[0x%X]=0x%X, ret=%d\r\n", (uint32_t)reg, value, ret); + return MAX20303_NO_ERROR; +} + +//****************************************************************************** +int MAX20303::readRegMulti(registers_t reg, uint8_t *value, uint8_t len){ + int32_t ret; + char data = reg; + + ret = m_i2c->write(m_writeAddress, &data, sizeof(data)); + if (ret != 0) { + printf("%s - failed - ret: %d\n", __func__); + return MAX20303_ERROR; + } + + ret = m_i2c->read(m_readAddress, (char *)value, len); + if (ret != 0) { + printf("%s - failed - ret: %d\n", __func__); + return MAX20303_ERROR; + } + + printf("MAX20303 read reg[0x%X]=0x%X, ret=%d\r\n", (uint32_t)reg, value, ret); + return MAX20303_NO_ERROR; +} + +//****************************************************************************** +int MAX20303::writeRegMulti(registers_t reg, uint8_t *value, uint8_t len){ + int32_t ret; + i2cbuffer_[0] = reg; + memcpy(&i2cbuffer_[1], value, len); + + ret = m_i2c->write(m_writeAddress, (char *)i2cbuffer_, (len+1)); + //printf("MAX20303 write reg[0x%X]=0x%X, ret=%d\r\n", (uint32_t)reg, value, ret) + + if (ret != 0) + return MAX20303_ERROR; + + return MAX20303_NO_ERROR; +} +//****************************************************************************** +int MAX20303::mv2bits(int mV) +{ + int regBits; + + if (( MAX20303_LDO_MIN_MV <= mV) && (mV <= MAX20303_LDO_MAX_MV)) { + regBits = (mV - MAX20303_LDO_MIN_MV) / MAX20303_LDO_STEP_MV; + } else { + return -1; + } + + return regBits; +} +//****************************************************************************** +int MAX20303::PowerOffthePMIC(){ + int ret; + appdatainoutbuffer_[0] = 0xB2; + appcmdoutvalue_ = 0x80; + ret = AppWrite(1); + + if(appcmdoutvalue_ != 0x80){ + ret |= MAX20303_ERROR; + } + + return ret; +} +//****************************************************************************** +int MAX20303::PowerOffDelaythePMIC(){ + int ret; + appdatainoutbuffer_[0] = 0xB2; + appcmdoutvalue_ = 0x84; + ret = AppWrite(1); + + if(appcmdoutvalue_ != 0x80){ + ret |= MAX20303_ERROR; + } + + return ret; +} + +//****************************************************************************** +int MAX20303::SoftResetthePMIC(){ + int ret; + appdatainoutbuffer_[0] = 0xB3; + appcmdoutvalue_ = 0x81; + ret = AppWrite(1); + + if(appcmdoutvalue_ != 0x81){ + ret |= MAX20303_ERROR; + } + + return ret; +} +//****************************************************************************** +int MAX20303::HardResetthePMIC(){ + int ret; + appdatainoutbuffer_[0] = 0xB4; + appcmdoutvalue_ = 0x82; + ret = AppWrite(1); + + if(appcmdoutvalue_ != 0x82){ + ret |= MAX20303_ERROR; + } + + return ret; +} + +//****************************************************************************** +int MAX20303::AppWrite(uint8_t dataoutlen){ + int ret; + + ret = writeRegMulti(MAX20303::REG_AP_DATOUT0, appdatainoutbuffer_, dataoutlen); + ret |= writeReg(MAX20303::REG_AP_CMDOUT, appcmdoutvalue_); + wait_ms(10); + ret |= readReg(MAX20303::REG_AP_RESPONSE, appcmdoutvalue_); + + if(ret != 0) + return MAX20303_ERROR; + + return MAX20303_NO_ERROR; +} + + +//****************************************************************************** +int MAX20303::AppRead(uint8_t datainlen){ + int ret; + + ret = writeReg(MAX20303::REG_AP_CMDOUT, appcmdoutvalue_); + wait_ms(10); + ret |= readRegMulti(MAX20303::REG_AP_RESPONSE, i2cbuffer_, datainlen); + if(ret != 0) + return MAX20303_ERROR; + + return MAX20303_NO_ERROR; +} + +//****************************************************************************** +char MAX20303::CheckPMICHWID(){ + int ret; + uint8_t value = 0x00; + + ret = readReg(MAX20303::REG_HARDWARE_ID, value); + if(ret != MAX20303_NO_ERROR) + return false; + + if(value == 0x02) + return true; + else + return false; +} + +//****************************************************************************** +int MAX20303::CheckPMICStatusRegisters(unsigned char buf_results[5]){ + int ret; + ret = readReg(MAX20303::REG_STATUS0, buf_results[0]); + ret |= readReg(MAX20303::REG_STATUS1, buf_results[1]); + ret |= readReg(MAX20303::REG_STATUS2, buf_results[2]); + ret |= readReg(MAX20303::REG_STATUS3, buf_results[3]); + ret |= readReg(MAX20303::REG_SYSTEM_ERROR, buf_results[4]); + return ret; +} + +//****************************************************************************** +int MAX20303::Max20303_BatteryGauge(unsigned char *batterylevel){ + int ret; + char data[2]; + + data[0] = 0x04; + ret = m_i2c->write(MAX20303_I2C_ADDR_FUEL_GAUGE, data, 1); + if(ret != 0){ + printf("Max20303_FuelGauge has failed\r\n"); + } + + ret = m_i2c->read(MAX20303_I2C_ADDR_FUEL_GAUGE | 1, data, 2); + if(ret != 0){ + printf("Max20303_FuelGauge has failed\r\n"); + } + + // if the level is more than 100 assume the battery is not connected + if(data[0] > 100){ + *batterylevel = 0; + } else{ + + *batterylevel = data[0]; + } + return 0; +} + + +//****************************************************************************** +int MAX20303::led0on(char enable) { + + if(enable) + return writeReg(REG_LED0_DIRECT, 0x21); + else + return writeReg(REG_LED0_DIRECT, 0x01); +} + +//****************************************************************************** +int MAX20303::led1on(char enable) { + if(enable) + return writeReg(REG_LED1_DIRECT, 0x21); + else + return writeReg(REG_LED1_DIRECT, 0x01); +} + +//****************************************************************************** +int MAX20303::led2on(char enable) { + if(enable) + return writeReg(REG_LED2_DIRECT, 0x21); + else + return writeReg(REG_LED2_DIRECT, 0x01); +} + + +//****************************************************************************** +int MAX20303::BoostEnable(void) { + writeReg(REG_AP_DATOUT3, 0x00); // 00 : 5V + writeReg(REG_AP_DATOUT0, 0x01); // Boost Enabled + writeReg(REG_AP_CMDOUT, 0x30); + return MAX20303_NO_ERROR; +} + +//****************************************************************************** +int MAX20303::BuckBoostEnable(void) +{ + int ret = 0; + + ret |= writeReg( REG_AP_DATOUT0, 0x00); // Reserved = 0x00 + ret |= writeReg( REG_AP_DATOUT1, 0x04); // BBstlSet = 0b'100 Buck Boost Peak current Limit = 200mA + ret |= writeReg( REG_AP_DATOUT2, 0x19); // BBstVSet = 0b'11001 Buck Boost Output Voltage = 5V + ret |= writeReg( REG_AP_DATOUT3, 0x01); // BBstRipRed = 1 Ripple Reduction + // BBstAct = 1 Actively discharged in Hard-Reset or Enable Low + // BBstPas = 1 Passively discharged in Hard-Reset or Enable Low + // BBstMd = 1 Damping Enabled + // BBstInd = 0 Inductance is 4.7uH + // BBstEn = 0b'01 Enabled + ret |= writeReg( REG_AP_CMDOUT, 0x70); + if (ret != 0) + return MAX20303_ERROR; + + return MAX20303_NO_ERROR; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoPlatform/MAX20303.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,221 @@ +/******************************************************************************* + * Copyright (C) 2018 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ +#ifndef __MAX20303_H_ +#define __MAX20303_H_ + +#include "mbed.h" + +#define MAX20303_SLAVE_ADDR (0x50 >> 1) +#define MAX20303_SLAVE_WR_ADDR ((MAX20303_SLAVE_ADDR << 1)) +#define MAX20303_SLAVE_RD_ADDR ((MAX20303_SLAVE_ADDR << 1) | 1) + + +#define MAX20303_NO_ERROR 0 +#define MAX20303_ERROR -1 + +#define MAX20303_I2C_ADDR_FUEL_GAUGE 0x6c +#define MAX20303_I2C_ADDR_FUEL_GAUGE 0x6C + +#define MAX20303_LDO_MIN_MV 800 +#define MAX20303_LDO_MAX_MV 3600 +#define MAX20303_LDO_STEP_MV 100 + +#define MAX20303_OFF_COMMAND 0xB2 + +class MAX20303 +{ + +public: + /** + * @brief Register Addresses + * @details Enumerated MAX20303 register addresses + */ + enum registers_t { + REG_HARDWARE_ID = 0x00, ///< HardwareID Register + REG_FIRMWARE_REV = 0x01, ///< FirmwareID Register + // = 0x02, ///< + REG_INT0 = 0x03, ///< Int0 Register + REG_INT1 = 0x04, ///< Int1 Register + REG_INT2 = 0x05, ///< Int2 Register + REG_STATUS0 = 0x06, ///< Status Register 0 + REG_STATUS1 = 0x07, ///< Status Register 1 + REG_STATUS2 = 0x08, ///< Status Register 2 + REG_STATUS3 = 0x09, ///< Status Register 2 + // = 0x0A, ///< + REG_SYSTEM_ERROR = 0x0B, ///< SystemError Register + REG_INT_MASK0 = 0x0C, ///< IntMask0 Register + REG_INT_MASK1 = 0x0D, ///< IntMask1 Register + REG_INT_MASK2 = 0x0E, ///< IntMask1 Register + REG_AP_DATOUT0 = 0x0F, ///< APDataOut0 Register + REG_AP_DATOUT1 = 0x10, ///< APDataOut1 Register + REG_AP_DATOUT2 = 0x11, ///< APDataOut2 Register + REG_AP_DATOUT3 = 0x12, ///< APDataOut3 Register + REG_AP_DATOUT4 = 0x13, ///< APDataOut4 Register + REG_AP_DATOUT5 = 0x14, ///< APDataOut5 Register + REG_AP_DATOUT6 = 0x15, ///< APDataOut6 Register + REG_AP_CMDOUT = 0x17, ///< APCmdOut Register + REG_AP_RESPONSE = 0x18, ///< APResponse Register + REG_AP_DATAIN0 = 0x19, + REG_AP_DATAIN1 = 0x1A, + REG_AP_DATAIN2 = 0x1B, + REG_AP_DATAIN3 = 0x1C, + REG_AP_DATAIN4 = 0x1D, + REG_AP_DATAIN5 = 0x1E, + // = 0x1F, ///< + REG_LDO_DIRECT = 0x20, + REG_MPC_DIRECTWRITE = 0x21, + REG_MPC_DIRECTRED = 0x22, + + REG_LED_STEP_DIRECT = 0x2C, + REG_LED0_DIRECT = 0x2D, + REG_LED1_DIRECT = 0x2E, + REG_LED2_DIRECT = 0x2F, + + + REG_LDO1_CONFIG_WRITE = 0x40, + REG_LDO1_CONFIG_READ = 0x41, + REG_LDO2_CONFIG_WRITE = 0x42, + REG_LDO2_CONFIG_READ = 0x43 + + /* + REG_CHG_TMR = 0x0C, ///< Charger Timers + REG_BUCK1_CFG = 0x0D, ///< Buck 1 Configuration + REG_BUCK1_VSET = 0x0E, ///< Buck 1 Voltage Setting + REG_BUCK2_CFG = 0x0F, ///< Buck 2 Configuration + REG_BUCK2_VSET = 0x10, ///< Buck 2 Voltage Setting + REG_RSVD_11 = 0x11, ///< Reserved 0x11 + REG_LDO1_CFG = 0x12, ///< LDO 1 Configuration + REG_LDO1_VSET = 0x13, ///< LDO 1 Voltage Setting + REG_LDO2_CFG = 0x14, ///< LDO 2 Configuration + REG_LDO2_VSET = 0x15, ///< LDO 2 Voltage Setting + REG_LDO3_CFG = 0x16, ///< LDO 3 Configuration + REG_LDO3_VSET = 0x17, ///< LDO 3 Voltage Setting + REG_THRM_CFG = 0x18, ///< Thermistor Configuration + REG_MON_CFG = 0x19, ///< Monitor Multiplexer Configuration + REG_BOOT_CFG = 0x1A, ///< Boot Configuration + REG_PIN_STATUS = 0x1B, ///< Pin Status + REG_BUCK_EXTRA = 0x1C, ///< Additional Buck Settings + REG_PWR_CFG = 0x1D, ///< Power Configuration + REG_NULL = 0x1E, ///< Reserved 0x1E + REG_PWR_OFF = 0x1F, ///< Power Off Register + */ + }; + + /** + * @brief Constructor using reference to I2C object + * @param i2c - Reference to I2C object + * @param slaveAddress - 7-bit I2C address + */ + MAX20303(I2C *i2c); + + /** @brief Destructor */ + ~MAX20303(void); + + int led0on(char enable); + int led1on(char enable); + int led2on(char enable); + int BoostEnable(void); + int BuckBoostEnable(void); + + /// @brief Enable the 1.8V output rail **/ + int LDO1Config(void); + + /// @brief Enable the 3V output rail **/ + int LDO2Config(void); + + + int mv2bits(int mV); + + /** @brief Power Off the board + */ + int PowerOffthePMIC(); + + /** @brief Power Off the board with 30ms delay + */ + int PowerOffDelaythePMIC(); + + /** @brief Soft reset the PMIC + */ + int SoftResetthePMIC(); + + /** @brief Hard reset the PMIC + */ + int HardResetthePMIC(); + + /** @brief check if can communicate with max20303 + */ + char CheckPMICHWID(); + + /** @brief CheckPMICStatusRegisters + */ + int CheckPMICStatusRegisters(unsigned char buf_results[5]); + + int Max20303_BatteryGauge(unsigned char *batterylevel); + +private: + + int writeReg(registers_t reg, uint8_t value); + int readReg(registers_t reg, uint8_t &value); + + int writeRegMulti(registers_t reg, uint8_t *value, uint8_t len); + int readRegMulti(registers_t reg, uint8_t *value, uint8_t len); + + /// I2C object + I2C *m_i2c; + + /// Device slave addresses + uint8_t m_writeAddress, m_readAddress; + + // Application Processor Interface Related Variables + uint8_t i2cbuffer_[16]; + uint8_t appdatainoutbuffer_[8]; + uint8_t appcmdoutvalue_; + + + /** @brief API Related Functions ***/ + + /*** + * @brief starts writing from ApResponse register 0x0F + * check the datasheet to determine the value of dataoutlen + */ + int AppWrite(uint8_t dataoutlen); + + /** @brief starts reading from ApResponse register 0x18 + * check the datasheet to determine the value of datainlen + * the result values are written into i2cbuffer + * + */ + int AppRead(uint8_t datainlen); +}; + +#endif /* __MAX20303_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoPlatform/max32630hsp.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,235 @@ +/******************************************************************************* + * Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ + +#include "mbed.h" +#include "max3263x.h" +#include "ioman_regs.h" +#include "PinNames.h" +#include "max32630hsp.h" + + +//****************************************************************************** +MAX32630HSP::MAX32630HSP() : i2c(P5_7, P6_0), max20303(&i2c) +{ +} + +//****************************************************************************** +MAX32630HSP::MAX32630HSP(vio_t vio) : i2c(P5_7, P6_0), max20303(&i2c) +{ + + init(vio); +} + +//****************************************************************************** +MAX32630HSP::MAX32630HSP(vio_t vio, InterruptIn *max32630hsp3_powerButtonInterrupt) : i2c(P5_7, P6_0), max20303(&i2c), m_max32630hsp3_powerButtonInterrupt(max32630hsp3_powerButtonInterrupt) +{ + init(vio); + + m_max32630hsp3_powerButtonInterrupt->disable_irq(); + m_max32630hsp3_powerButtonInterrupt->rise(this, &MAX32630HSP::event_powerButtonReleased); + m_max32630hsp3_powerButtonInterrupt->mode(PullUp); + m_max32630hsp3_powerButtonInterrupt->enable_irq(); +} + + +//****************************************************************************** +MAX32630HSP::~MAX32630HSP() +{ + +} + + +//****************************************************************************** +int MAX32630HSP::init(vio_t hdrVio) +{ + /* Wait for pmic to settle down */ + wait_ms(800); + + + + /*Set LDO1 to 1.8v*/ + max20303.LDO1Config(); + + /*Set LDO2 to 3v*/ + max20303.LDO2Config(); + + //max20303.BoostEnable(); + max20303.BuckBoostEnable(); + + + max20303.led0on(0); + max20303.led1on(0); + max20303.led2on(0); + + /* Wait for pmic to settle down */ + wait_ms(200); + + // Set LED pins to 3.3V + vddioh(P2_4, VIO_3V3); + vddioh(P2_5, VIO_3V3); + vddioh(P2_6, VIO_3V3); + + // set i2c pins to 1.8V + vddioh(P3_4, VIO_1V8); + vddioh(P3_5, VIO_1V8); + //ble module pins to 1.8V + vddioh(P0_0, VIO_1V8); + vddioh(P0_1, VIO_1V8); + vddioh(P0_2, VIO_1V8); + vddioh(P0_3, VIO_1V8); + + // Set header pins to hdrVio + vddioh(P3_0, hdrVio); + vddioh(P3_1, hdrVio); + vddioh(P3_2, hdrVio); + vddioh(P3_3, hdrVio); + vddioh(P4_0, hdrVio); + vddioh(P4_1, hdrVio); + vddioh(P4_2, hdrVio); + vddioh(P4_3, hdrVio); + vddioh(P4_4, hdrVio); + vddioh(P4_5, hdrVio); + vddioh(P4_6, hdrVio); + vddioh(P4_7, hdrVio); + vddioh(P5_0, hdrVio); + vddioh(P5_1, hdrVio); + vddioh(P5_2, hdrVio); + vddioh(P5_3, hdrVio); + vddioh(P5_4, hdrVio); + vddioh(P5_5, hdrVio); + vddioh(P5_6, hdrVio); + + + button_longpressdetected = false; + + return 0; +} + + +void MAX32630HSP::event_powerButtonPressed(void) { + + max20303.led0on(0); + max20303.led1on(0); + max20303.led2on(1); + + /* Button press detected. Wait for button release */ + m_max32630hsp3_powerButtonInterrupt->disable_irq(); + m_max32630hsp3_powerButtonInterrupt->rise(this, &MAX32630HSP::event_powerButtonReleased); + m_max32630hsp3_powerButtonInterrupt->mode(PullUp); + m_max32630hsp3_powerButtonInterrupt->enable_irq(); + + /* Button press detected. Start Timeout object for checking long key press event */ + button_timeout.attach( this, &MAX32630HSP::event_longpresscheck , 2.0 ); + + /* Button is pressed */ + button_status = true; +} + +//****************************************************************************** +void MAX32630HSP::event_powerButtonReleased(void) { + + + if ( button_longpressdetected ) { + + /* Power of the PMIC if long key press is detected */ + max20303.PowerOffDelaythePMIC(); + + } + else { + + /* Button released before a long key press is detected */ + button_status = false; + + } + + /* Button is released. Stop timeout object */ + button_timeout.detach(); + + max20303.led0on(0); + max20303.led1on(0); + max20303.led2on(0); + + /* Button is released. Expect for button press event next time */ + m_max32630hsp3_powerButtonInterrupt->disable_irq(); + m_max32630hsp3_powerButtonInterrupt->fall(this, &MAX32630HSP::event_powerButtonPressed); + m_max32630hsp3_powerButtonInterrupt->mode(PullUp); + m_max32630hsp3_powerButtonInterrupt->enable_irq(); + + +} + +void MAX32630HSP::event_longpresscheck(void) { + + /* This is the callback for timeout object to detect long key press for power down */ + + if ( button_status == 1 ) { + + /* If button_status is still 1 when timeout is triggered, it will be interpreted as a long key press */ + button_longpressdetected = true; + + /* The PMIC will be powered of when the button is released */ + max20303.led0on(0); + max20303.led1on(1); + max20303.led2on(0); + } + +} + +void MAX32630HSP::enableDisplay(void) +{ + vddioh(P6_4, VIO_3V3); //EXTCOM + vddioh(P6_1, VIO_3V3); //SCLK + vddioh(P6_2, VIO_3V3); //MOSI1 + vddioh(P6_5, VIO_3V3); //SCS + vddioh(P6_4, VIO_3V3); //EXTCOM + vddioh(P6_6, VIO_3V3); //DISP +} + +//****************************************************************************** +int MAX32630HSP::vddioh(PinName pin, vio_t vio) +{ + __IO uint32_t *use_vddioh = &((mxc_ioman_regs_t *)MXC_IOMAN)->use_vddioh_0; + + if (pin == NOT_CONNECTED) { + return -1; + } + + use_vddioh += PINNAME_TO_PORT(pin) >> 2; + if (vio) { + *use_vddioh |= (1 << (PINNAME_TO_PIN(pin) + ((PINNAME_TO_PORT(pin) & 0x3) << 3))); + } else { + *use_vddioh &= ~(1 << (PINNAME_TO_PIN(pin) + ((PINNAME_TO_PORT(pin) & 0x3) << 3))); + } + + return 0; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoPlatform/max32630hsp.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,178 @@ +/******************************************************************************* + * Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ + +#ifndef _MAX32630HSP_H_ +#define _MAX32630HSP_H_ + +#include "mbed.h" +#include "MAX20303.h" + + +/** + * @brief MAX32630HSP Board Support Library + * + * @details The MAX32630HSP is a rapid development application board for + * ultra low power wearable applications. It includes common peripherals and + * expansion connectors all power optimized for getting the longest life from + * the battery. This library configures the power and I/O for the board. + * <br>https://www.maximintegrated.com/max32630hsp + * + * @code + * #include "mbed.h" + * #include "max32630hsp.h" + * + * DigitalOut led1(LED1); + * MAX32630HSP icarus(MAX32630HSP::VIO_3V3); + * + * // main() runs in its own thread in the OS + * // (note the calls to Thread::wait below for delays) + * int main() + * { + * // initialize power and I/O on MAX32630HSP board + * icarus.init(); + * + * while (true) { + * led1 = !led1; + * Thread::wait(500); + * } + * } + * @endcode + */ + +// Sharp LS013B7DH03 Memory Display +#define SCK_PIN P6_1 +#define MOSI_PIN P6_2 +#define CS_PIN P6_5 +#define EXTCOM_PIN P6_4 +#define DISP_PIN P6_6 +#define DISPSEL_PIN NC +#define PIN_POWERBUTTON P7_6 +#define PIN_UPBUTTON P2_3 +#define PIN_DOWNBUTTON P6_5 + +class MAX32630HSP +{ +public: +// max32630hsp configuration utilities + + /** + * @brief IO Voltage + * @details Enumerated options for operating voltage + */ + typedef enum { + VIO_1V8 = 0x00, ///< 1.8V IO voltage at headers (from BUCK2) + VIO_3V3 = 0x01, ///< 3.3V IO voltage at headers (from LDO2) + } vio_t; + + enum ButtonStatus { + BUTTONSTATUS_RELEASED = 1, + BUTTONSTATUS_PRESSED + } ; + + /** + * MAX32630HSP constructor. + * + */ + MAX32630HSP(); + + /** + * MAX32630HSP constructor. + * + */ + MAX32630HSP(vio_t vio); + + /** + * MAX32630HSP constructor. + * + */ + MAX32630HSP(vio_t vio, InterruptIn *max32630hsp3_powerButtonInterrupt); + + /** + * MAX32630HSP destructor. + */ + ~MAX32630HSP(); + + //InterruptIn _interruptIn_PowerButton; + + /** + * @brief Initialize MAX32630HSP board + * @details Initializes PMIC and I/O on MAX32630HSP board. + * Configures PMIC to enable LDO2 and LDO3 at 3.3V. + * Disables resisitive pulldown on MON(AIN_0) + * Sets default I/O voltages to 3V3 for micro SD card. + * Sets I/O voltage for header pins to hdrVio specified. + * @param hdrVio I/O voltage for header pins + * @returns 0 if no errors, -1 if error. + */ + int init(vio_t hdrVio); + + /** + * @brief Sets I/O Voltage + * @details Sets the voltage rail to be used for a given pin. + * VIO_1V8 selects VDDIO which is supplied by Buck2, which is set at 1.8V, + * VIO_3V3 selects VDDIOH which is supplied by LDO2, which is typically 3.3V/ + * @param pin Pin whose voltage supply is being assigned. + * @param vio Voltage rail to be used for specified pin. + * @returns 0 if no errors, -1 if error. + */ + int vddioh(PinName pin, vio_t vio); + + /**Interrupt Hander for Power Button Press**/ + + //InterruptIn _interruptIn_UpButton(PIN_UPBUTTON); + //InterruptIn _interruptIn_DownButton(PIN_DOWNBUTTON); + + /* Set vddio for Sharp LS013B7DH03 Display */ + void enableDisplay(void); + + /// Local I2C bus for configuring PMIC and accessing BMI160 IMU. + I2C i2c; + + /// MAX20303 PMIC Instance + MAX20303 max20303; + + + InterruptIn *m_max32630hsp3_powerButtonInterrupt; + bool button_status; + bool button_longpressdetected; + Timeout button_timeout; + + ButtonStatus status_powerButton; + ButtonStatus status_upButton; + ButtonStatus status_downButton; + void event_powerButtonPressed(void); + void event_powerButtonReleased(void); + void event_longpresscheck(void); +}; + +#endif /* _MAX32630HSP_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/demoUI.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,398 @@ +/******************************************************************************* + * Copyright (C) 2018 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ + +/* + * Note: This API i intended for demo purposes and specific to display screen LS013B7DH03. Being targeted for result display only + * performance/memory measures are not taken into account! It is kept simple and some rules of embedded sw developmentare are + * sacrified for being easily understandable. + * + * */ + +#include "demoUI.h" +/*demo specific display screen driver*/ +#include "screen/LS013B7DH03.h" + +const unsigned char UbuntuCondensed16x21[] = { + 49, 16,21,3, + 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xCF, 0x01, 0xFC, 0xCF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ! + 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char " + 0x0B, 0x00, 0x00, 0x00, 0x40, 0x10, 0x00, 0x40, 0xFE, 0x01, 0xFC, 0x1F, 0x00, 0x7C, 0x10, 0x00, 0x40, 0x10, 0x00, 0x40, 0xF0, 0x01, 0xC0, 0xFF, 0x01, 0xFC, 0x1F, 0x00, 0x7C, 0x10, 0x00, 0x40, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char # + 0x08, 0x00, 0x00, 0x00, 0xE0, 0x60, 0x00, 0xF0, 0xC1, 0x00, 0x18, 0xC3, 0x00, 0x1E, 0xC7, 0x07, 0x1E, 0xC6, 0x07, 0x18, 0xFE, 0x00, 0x18, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char $ + 0x0D, 0x00, 0x00, 0x00, 0xF8, 0x01, 0x00, 0xFC, 0x03, 0x00, 0x04, 0x02, 0x01, 0xFC, 0xE3, 0x01, 0xF8, 0x79, 0x00, 0x00, 0x1E, 0x00, 0xC0, 0x03, 0x00, 0xF0, 0xFC, 0x00, 0x3C, 0xFE, 0x01, 0x04, 0x02, 0x01, 0x00, 0xFE, 0x01, 0x00, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char % + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x78, 0x00, 0x78, 0xFE, 0x00, 0xFC, 0xC7, 0x01, 0x8C, 0x83, 0x01, 0x8C, 0x8F, 0x01, 0xFC, 0x9C, 0x01, 0x78, 0xF0, 0x00, 0x00, 0xFE, 0x01, 0x00, 0x8E, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char & + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ' + 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x7F, 0x00, 0xF0, 0xFF, 0x03, 0x3C, 0x00, 0x0F, 0x06, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ( + 0x04, 0x06, 0x00, 0x18, 0x3C, 0x00, 0x0F, 0xF0, 0xFF, 0x03, 0x80, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ) + 0x08, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x58, 0x00, 0x00, 0xD4, 0x00, 0x00, 0x3C, 0x00, 0x00, 0xD4, 0x00, 0x00, 0x58, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char * + 0x09, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x80, 0x7F, 0x00, 0x80, 0x7F, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char + + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x80, 0x0F, 0x00, 0x80, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char , + 0x05, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char - + 0x03, 0x00, 0x00, 0x00, 0x00, 0xC0, 0x01, 0x00, 0xC0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char . + 0x06, 0x00, 0x80, 0x1F, 0x00, 0xF8, 0x07, 0x80, 0x7F, 0x00, 0xF8, 0x07, 0x00, 0x7E, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char / + 0x08, 0x00, 0x00, 0x00, 0xF0, 0x7F, 0x00, 0xF8, 0xFF, 0x00, 0x1C, 0xC0, 0x01, 0x0C, 0x80, 0x01, 0x1C, 0xC0, 0x01, 0xF8, 0xFF, 0x00, 0xF0, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 0 + 0x06, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x30, 0x00, 0x00, 0x18, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 1 + 0x07, 0x00, 0x00, 0x00, 0x08, 0xC0, 0x01, 0x0C, 0xF8, 0x01, 0x0C, 0x9C, 0x01, 0x0C, 0x87, 0x01, 0xFC, 0x83, 0x01, 0xF8, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 2 + 0x08, 0x00, 0x00, 0x00, 0x08, 0xC0, 0x00, 0x0C, 0x80, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x9C, 0xC7, 0x01, 0xF8, 0xFF, 0x00, 0xF0, 0x7C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 3 + 0x08, 0x00, 0x00, 0x00, 0x00, 0x1E, 0x00, 0x80, 0x1F, 0x00, 0xF0, 0x19, 0x00, 0x3C, 0x18, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 4 + 0x08, 0x00, 0x00, 0x00, 0x00, 0x80, 0x01, 0xFC, 0x83, 0x01, 0xFC, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0xC7, 0x01, 0x0C, 0xFE, 0x00, 0x0C, 0x7C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 5 + 0x08, 0x00, 0x00, 0x00, 0x80, 0x7F, 0x00, 0xF0, 0xFF, 0x00, 0x78, 0xC3, 0x01, 0x18, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0xFF, 0x00, 0x00, 0x7C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 6 + 0x08, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0xC0, 0x01, 0x0C, 0xFC, 0x01, 0x8C, 0x1F, 0x00, 0xEC, 0x01, 0x00, 0x7C, 0x00, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 7 + 0x08, 0x00, 0x00, 0x00, 0xF0, 0x78, 0x00, 0xF8, 0xFD, 0x00, 0x0C, 0x87, 0x01, 0x0C, 0x82, 0x01, 0x0C, 0x87, 0x01, 0xF8, 0xFD, 0x00, 0x78, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 8 + 0x08, 0x00, 0x00, 0x00, 0xF0, 0x01, 0x00, 0xF8, 0x83, 0x01, 0x0C, 0x87, 0x01, 0x0C, 0xC6, 0x00, 0x1C, 0xF6, 0x00, 0xF8, 0x7F, 0x00, 0xF0, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char 9 + 0x03, 0x00, 0x00, 0x00, 0xE0, 0xC0, 0x01, 0xE0, 0xC0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char : + 0x04, 0x00, 0x00, 0x00, 0xE0, 0x00, 0x18, 0xE0, 0x80, 0x0F, 0x00, 0x80, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ; + 0x08, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x1B, 0x00, 0x00, 0x11, 0x00, 0x80, 0x31, 0x00, 0xC0, 0x60, 0x00, 0xC0, 0x60, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char < + 0x08, 0x00, 0x00, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x80, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char = + 0x08, 0x00, 0x00, 0x00, 0xC0, 0x60, 0x00, 0xC0, 0x60, 0x00, 0x80, 0x31, 0x00, 0x00, 0x11, 0x00, 0x00, 0x1B, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char > + 0x07, 0x08, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0xCE, 0x01, 0x0C, 0xCF, 0x01, 0x8C, 0x03, 0x00, 0xF8, 0x00, 0x00, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ? + 0x10, 0x00, 0x00, 0x00, 0x80, 0x7F, 0x00, 0xE0, 0xFF, 0x01, 0xF0, 0xC0, 0x03, 0x38, 0x00, 0x07, 0x18, 0x3E, 0x0E, 0x0C, 0x7F, 0x0C, 0x8C, 0x61, 0x0C, 0x8C, 0x61, 0x0C, 0x8C, 0x3F, 0x0C, 0x8C, 0x7F, 0x0C, 0x1C, 0x60, 0x00, 0x18, 0x60, 0x00, 0x70, 0x70, 0x00, 0xE0, 0x3F, 0x00, 0xC0, 0x1F, 0x00, // Code for char @ + 0x0B, 0x00, 0x80, 0x01, 0x00, 0xF8, 0x01, 0x00, 0x7F, 0x00, 0xE0, 0x3F, 0x00, 0xFC, 0x30, 0x00, 0x0C, 0x30, 0x00, 0xFC, 0x30, 0x00, 0xE0, 0x37, 0x00, 0x00, 0x7F, 0x00, 0x00, 0xF0, 0x01, 0x00, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char A + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x9C, 0xC7, 0x01, 0xF8, 0xFF, 0x00, 0xF0, 0x7C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char B + 0x09, 0x00, 0x00, 0x00, 0xC0, 0x1F, 0x00, 0xF0, 0x7F, 0x00, 0x38, 0xE0, 0x00, 0x0C, 0xC0, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x18, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char C + 0x0B, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x1C, 0xC0, 0x01, 0x38, 0xE0, 0x00, 0xF0, 0x7F, 0x00, 0xC0, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char D + 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x83, 0x01, 0x0C, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char E + 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x03, 0x00, 0x0C, 0x03, 0x00, 0x0C, 0x03, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char F + 0x0A, 0x00, 0x00, 0x00, 0xC0, 0x1F, 0x00, 0xF0, 0x7F, 0x00, 0x38, 0xE0, 0x00, 0x1C, 0xC0, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0xFE, 0x01, 0x08, 0xFE, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char G + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x03, 0x00, 0x00, 0x03, 0x00, 0x00, 0x03, 0x00, 0x00, 0x03, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char H + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char I + 0x06, 0x00, 0xC0, 0x00, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0xFC, 0xFF, 0x01, 0xFC, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char J + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x80, 0x03, 0x00, 0xE0, 0x07, 0x00, 0x78, 0x1C, 0x00, 0x1C, 0xF8, 0x00, 0x04, 0xE0, 0x01, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char K + 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char L + 0x0E, 0x00, 0x00, 0x00, 0xE0, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x1C, 0x00, 0x00, 0xFC, 0x00, 0x00, 0xE0, 0x0F, 0x00, 0x00, 0x7E, 0x00, 0x00, 0x70, 0x00, 0x00, 0x7E, 0x00, 0xE0, 0x0F, 0x00, 0xFC, 0x00, 0x00, 0x1C, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xE0, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char M + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x7C, 0x00, 0x00, 0xE0, 0x03, 0x00, 0x00, 0x1F, 0x00, 0x00, 0xF8, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char N + 0x0C, 0x00, 0x00, 0x00, 0xC0, 0x1F, 0x00, 0xF0, 0x7F, 0x00, 0x38, 0xE0, 0x00, 0x1C, 0xC0, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x01, 0x1C, 0xC0, 0x01, 0x38, 0xE0, 0x00, 0xF0, 0x7F, 0x00, 0xC0, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char O + 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x0C, 0x00, 0x0C, 0x0C, 0x00, 0x1C, 0x0E, 0x00, 0xF8, 0x07, 0x00, 0xF0, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char P + 0x0C, 0x00, 0x00, 0x00, 0xC0, 0x1F, 0x00, 0xF0, 0x7F, 0x00, 0x38, 0xE0, 0x00, 0x1C, 0xC0, 0x01, 0x0C, 0x80, 0x01, 0x0C, 0x80, 0x07, 0x0C, 0x80, 0x0F, 0x1C, 0xC0, 0x0D, 0x38, 0xE0, 0x18, 0xF0, 0x7F, 0x18, 0xC0, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char Q + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x0C, 0x00, 0x0C, 0x0C, 0x00, 0x1C, 0x3E, 0x00, 0xF8, 0xF7, 0x00, 0xF0, 0xC3, 0x01, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char R + 0x07, 0x00, 0x00, 0x00, 0xF0, 0xC0, 0x00, 0xF8, 0x83, 0x01, 0x8C, 0x83, 0x01, 0x0C, 0x87, 0x01, 0x0C, 0xFE, 0x00, 0x1C, 0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char S + 0x09, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFC, 0xFF, 0x01, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char T + 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0x7F, 0x00, 0xFC, 0xFF, 0x00, 0x00, 0xC0, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0xC0, 0x01, 0xFC, 0xFF, 0x00, 0xFC, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char U + 0x09, 0x1C, 0x00, 0x00, 0xFC, 0x03, 0x00, 0xE0, 0x7F, 0x00, 0x00, 0xFC, 0x01, 0x00, 0x80, 0x01, 0x00, 0xFC, 0x01, 0xE0, 0x7F, 0x00, 0xFC, 0x07, 0x00, 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char V + 0x0F, 0x00, 0x00, 0x00, 0x7C, 0x00, 0x00, 0xFC, 0x7F, 0x00, 0x80, 0xFF, 0x01, 0x00, 0x80, 0x01, 0x00, 0xF8, 0x01, 0x80, 0x7F, 0x00, 0xF0, 0x07, 0x00, 0x70, 0x00, 0x00, 0xF0, 0x3F, 0x00, 0x00, 0xFF, 0x01, 0x00, 0x80, 0x01, 0x80, 0xFF, 0x01, 0xFC, 0xFF, 0x00, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char W + 0x09, 0x04, 0x00, 0x01, 0x1C, 0xC0, 0x01, 0x78, 0xF0, 0x00, 0xE0, 0x1F, 0x00, 0x80, 0x07, 0x00, 0xE0, 0x1F, 0x00, 0x78, 0xF0, 0x00, 0x1C, 0xC0, 0x01, 0x04, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char X + 0x0A, 0x04, 0x00, 0x00, 0x3C, 0x00, 0x00, 0xF8, 0x00, 0x00, 0xC0, 0x03, 0x00, 0x00, 0xFF, 0x01, 0x00, 0xFF, 0x01, 0xC0, 0x03, 0x00, 0xF8, 0x00, 0x00, 0x3C, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char Y + 0x08, 0x00, 0x00, 0x00, 0x0C, 0xC0, 0x01, 0x0C, 0xF0, 0x01, 0x0C, 0xBE, 0x01, 0x8C, 0x8F, 0x01, 0xEC, 0x81, 0x01, 0x7C, 0x80, 0x01, 0x1C, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char Z + 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x1F, 0xFE, 0xFF, 0x1F, 0x06, 0x00, 0x18, 0x06, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char [ + 0x06, 0x7E, 0x00, 0x00, 0xF8, 0x07, 0x00, 0x80, 0x7F, 0x00, 0x00, 0xF8, 0x07, 0x00, 0x80, 0x1F, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char BackSlash + 0x04, 0x06, 0x00, 0x18, 0x06, 0x00, 0x18, 0xFE, 0xFF, 0x1F, 0xFE, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ] + 0x08, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0xE0, 0x03, 0x00, 0x7C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x7C, 0x00, 0x00, 0xE0, 0x03, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ^ + 0x08, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char _ + 0x05, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ` + 0x07, 0x00, 0x00, 0x00, 0x00, 0xF8, 0x00, 0xC0, 0xFC, 0x01, 0xC0, 0x8C, 0x01, 0xC0, 0x8C, 0x01, 0xC0, 0xFF, 0x01, 0x80, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char a + 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x01, 0xFE, 0xFF, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0xC1, 0x01, 0x80, 0xFF, 0x00, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char b + 0x07, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xC1, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char c + 0x08, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xC1, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xFE, 0xFF, 0x01, 0xFE, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char d + 0x08, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xCD, 0x01, 0xC0, 0x8C, 0x01, 0xC0, 0x8C, 0x01, 0x80, 0x8F, 0x01, 0x00, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char e + 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFC, 0xFF, 0x01, 0xFE, 0xFF, 0x01, 0xC6, 0x00, 0x00, 0xC6, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char f + 0x08, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x18, 0xC0, 0xC1, 0x19, 0xC0, 0x80, 0x19, 0xC0, 0x80, 0x19, 0xC0, 0xFF, 0x0F, 0xC0, 0xFF, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char g + 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x01, 0xFE, 0xFF, 0x01, 0xC0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0x80, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char h + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xCC, 0xFF, 0x01, 0xCC, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char i + 0x04, 0x00, 0x00, 0x18, 0x00, 0x00, 0x18, 0xCC, 0xFF, 0x1F, 0xCC, 0xFF, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char j + 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x01, 0xFE, 0xFF, 0x01, 0x00, 0x1C, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xE3, 0x01, 0x40, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char k + 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x00, 0xFE, 0xFF, 0x01, 0x00, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char l + 0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0xC0, 0xFF, 0x01, 0xC0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0xC0, 0x01, 0x00, 0x80, 0xFF, 0x01, 0xC0, 0xFF, 0x01, 0xC0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0x80, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char m + 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0xC0, 0xFF, 0x01, 0xC0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0x00, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char n + 0x09, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xC1, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0xC1, 0x01, 0x80, 0xFF, 0x00, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char o + 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0xFF, 0x1F, 0xC0, 0xFF, 0x1F, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0xC1, 0x01, 0x80, 0xFF, 0x00, 0x00, 0x7F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char p + 0x08, 0x00, 0x00, 0x00, 0x00, 0x7F, 0x00, 0x80, 0xFF, 0x00, 0xC0, 0xC1, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0xFF, 0x1F, 0xC0, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char q + 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0xFF, 0x01, 0xC0, 0xFF, 0x01, 0xC0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char r + 0x06, 0x00, 0x00, 0x00, 0x80, 0x87, 0x01, 0xC0, 0x8F, 0x01, 0xC0, 0x9C, 0x01, 0xC0, 0xF8, 0x01, 0xC0, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char s + 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8, 0xFF, 0x00, 0xF8, 0xFF, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0xC0, 0x80, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char t + 0x08, 0x00, 0x00, 0x00, 0xC0, 0x7F, 0x00, 0xC0, 0xFF, 0x00, 0x00, 0xC0, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0xC0, 0xFF, 0x01, 0xC0, 0xFF, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char u + 0x08, 0xC0, 0x01, 0x00, 0xC0, 0x7F, 0x00, 0x00, 0xFE, 0x01, 0x00, 0x80, 0x01, 0x00, 0x80, 0x01, 0x00, 0xFE, 0x01, 0xC0, 0x7F, 0x00, 0xC0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char v + 0x0B, 0xC0, 0x03, 0x00, 0xC0, 0xFF, 0x00, 0x00, 0xFE, 0x01, 0x00, 0x80, 0x01, 0x00, 0xFE, 0x00, 0xC0, 0x03, 0x00, 0x00, 0x7C, 0x00, 0x00, 0x80, 0x01, 0x00, 0xFE, 0x01, 0xC0, 0xFF, 0x00, 0xC0, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char w + 0x08, 0x40, 0x00, 0x01, 0xC0, 0xC1, 0x01, 0x80, 0xF7, 0x00, 0x00, 0x3E, 0x00, 0x00, 0x3E, 0x00, 0x80, 0xF7, 0x00, 0xC0, 0xC1, 0x01, 0x40, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char x + 0x07, 0xC0, 0x01, 0x18, 0xC0, 0x3F, 0x18, 0x00, 0xFE, 0x1F, 0x00, 0xE0, 0x0F, 0x00, 0xFE, 0x03, 0xC0, 0x3F, 0x00, 0xC0, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char y + 0x06, 0x00, 0x00, 0x00, 0xC0, 0xC0, 0x01, 0xC0, 0xF8, 0x01, 0xC0, 0xBE, 0x01, 0xC0, 0x87, 0x01, 0xC0, 0x81, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char z + 0x06, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x00, 0xFC, 0xFF, 0x0F, 0xFE, 0xF3, 0x1F, 0x06, 0x00, 0x18, 0x06, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char { + 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE, 0xFF, 0x1F, 0xFE, 0xFF, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char | + 0x05, 0x06, 0x00, 0x18, 0x06, 0x00, 0x18, 0xFE, 0xF3, 0x1F, 0xFC, 0xFF, 0x0F, 0x00, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char } + 0x09, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x03, 0x00, 0x00, 0x03, 0x00, 0x00, 0x07, 0x00, 0x00, 0x0E, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x0C, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Code for char ~ + 0x06, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x00, 0x01, 0x80, 0x00, 0x01, 0x80, 0x00, 0x01, 0x80, 0x00, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 // Code for char + }; + + + +static const unsigned char maxim128Bitmaps[] = +{ + + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x07, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ######### + 0x00, 0x00, 0x1F, 0xFF, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ############## + 0x00, 0x00, 0x7F, 0xFF, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, // ################## ## + 0x00, 0x01, 0xFF, 0xFF, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, // ##################### ## + 0x00, 0x03, 0xFF, 0xFF, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ######################## + 0x00, 0x07, 0xFF, 0xFF, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ########################## + 0x00, 0x0F, 0xFF, 0xFF, 0xFE, 0x00, 0x2F, 0xB8, 0x7C, 0xE3, 0x32, 0x7B, 0xC0, 0x00, 0x00, 0x00, // ########################### # ##### ### ##### ### ## ## # #### #### + 0x00, 0x1F, 0xFF, 0xFF, 0xFF, 0x00, 0x3F, 0xFC, 0x7E, 0x77, 0x33, 0xFF, 0xE0, 0x00, 0x00, 0x00, // ############################# ############ ###### ### ### ## ############# + 0x00, 0x1F, 0xFF, 0xFF, 0xFF, 0x80, 0x31, 0x8C, 0x02, 0x3E, 0x33, 0x1C, 0x60, 0x00, 0x00, 0x00, // ############################## ## ## ## # ##### ## ## ### ## + 0x00, 0x3F, 0xFF, 0xFF, 0xFF, 0x80, 0x31, 0x8C, 0x1E, 0x1C, 0x33, 0x18, 0x60, 0x00, 0x00, 0x00, // ############################### ## ## ## #### ### ## ## ## ## + 0x00, 0x3E, 0x01, 0xF8, 0x0F, 0xC0, 0x31, 0x8C, 0xFA, 0x1C, 0x33, 0x18, 0x60, 0x00, 0x00, 0x00, // ##### ###### ###### ## ## ## ##### # ### ## ## ## ## + 0x00, 0x7E, 0x00, 0xF0, 0x07, 0xE0, 0x31, 0x8C, 0xC2, 0x1E, 0x33, 0x18, 0x60, 0x00, 0x00, 0x00, // ###### #### ###### ## ## ## ## # #### ## ## ## ## + 0x00, 0x7E, 0x18, 0xE1, 0x87, 0xE0, 0x31, 0x8C, 0xC6, 0x37, 0x33, 0x18, 0x60, 0x00, 0x00, 0x00, // ###### ## ### ## ###### ## ## ## ## ## ## ### ## ## ## ## + 0x00, 0xFE, 0x18, 0xE3, 0x87, 0xE0, 0x31, 0x8C, 0xEE, 0x63, 0xB3, 0x18, 0x60, 0x00, 0x00, 0x00, // ####### ## ### ### ###### ## ## ## ### ### ## ### ## ## ## ## + 0x00, 0xFE, 0x1C, 0xC3, 0x87, 0xE0, 0x31, 0x8C, 0x7A, 0xE1, 0xB3, 0x18, 0x60, 0x00, 0x00, 0x00, // ####### ### ## ### ###### ## ## ## #### # ### ## ## ## ## ## + 0x00, 0xFE, 0x1C, 0xC7, 0x87, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ####### ### ## #### ###### + 0x00, 0xFE, 0x1F, 0x87, 0x87, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ####### ###### #### ###### + 0x00, 0xFE, 0x1F, 0x8F, 0x87, 0xE0, 0x30, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, // ####### ###### ##### ###### ## ## + 0x00, 0xFE, 0x1F, 0x0F, 0x87, 0xE0, 0x30, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x30, // ####### ##### ##### ###### ## ## ## ## + 0x00, 0xFE, 0x1E, 0x0F, 0x87, 0xE0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x30, // ####### #### ##### ###### ## ## ## + 0x00, 0xFE, 0x1E, 0x07, 0x87, 0xE0, 0x00, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x30, // ####### #### #### ###### ## ## ## + 0x00, 0xFE, 0x1E, 0x07, 0x87, 0xE0, 0x33, 0xF1, 0xF3, 0xF1, 0xFD, 0xBB, 0xE7, 0xE7, 0xC3, 0xF0, // ####### #### #### ###### ## ###### ##### ###### ####### ## ### ##### ###### ##### ###### + 0x00, 0x7E, 0x1C, 0x43, 0x87, 0xE0, 0x33, 0x98, 0xC2, 0x31, 0x19, 0xE4, 0x33, 0x0C, 0x66, 0x30, // ###### ### # ### ###### ## ### ## ## # ## # ## #### # ## ## ## ## ## ## + 0x00, 0x7E, 0x18, 0x63, 0x87, 0xE0, 0x33, 0x18, 0xC6, 0x1B, 0x19, 0xC0, 0x33, 0x0C, 0x66, 0x30, // ###### ## ## ### ###### ## ## ## ## ## ## ## ## ### ## ## ## ## ## ## + 0x00, 0x7E, 0x18, 0xE1, 0x87, 0xC0, 0x33, 0x18, 0xC7, 0xFB, 0x19, 0x81, 0xF3, 0x1F, 0xEE, 0x30, // ###### ## ### ## ##### ## ## ## ## ######## ## ## ## ##### ## ######## ### ## + 0x00, 0x3E, 0x10, 0xF1, 0x87, 0xC0, 0x33, 0x18, 0xC7, 0xF1, 0xF1, 0x87, 0xB3, 0x1F, 0xCC, 0x30, // ##### # #### ## ##### ## ## ## ## ####### ##### ## #### ## ## ####### ## ## + 0x00, 0x3F, 0xFF, 0xFF, 0xFF, 0x80, 0x33, 0x18, 0xC6, 0x01, 0xE1, 0x86, 0x33, 0x0C, 0x0E, 0x30, // ############################### ## ## ## ## ## #### ## ## ## ## ## ### ## + 0x00, 0x1F, 0xFF, 0xFF, 0xFF, 0x80, 0x33, 0x18, 0xC6, 0x09, 0x81, 0x84, 0x33, 0x8C, 0x26, 0x30, // ############################## ## ## ## ## ## # ## ## # ## ### ## # ## ## + 0x00, 0x0F, 0xFF, 0xFF, 0xFF, 0x00, 0x33, 0x18, 0xF3, 0xF1, 0xF9, 0x87, 0xF1, 0xEF, 0xE7, 0xF0, // ############################ ## ## ## #### ###### ###### ## ####### #### ####### ####### + 0x00, 0x07, 0xFF, 0xFF, 0xFE, 0x00, 0x33, 0x18, 0x71, 0xE3, 0x1D, 0x83, 0xD0, 0xE3, 0x83, 0x90, // ########################## ## ## ## ### #### ## ### ## #### # ### ### ### # + 0x00, 0x03, 0xFF, 0xFF, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x06, 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, // ######################## ## ## + 0x00, 0x01, 0xFF, 0xFF, 0xF8, 0x00, 0x00, 0x00, 0x00, 0x03, 0xBC, 0x00, 0x00, 0x00, 0x00, 0x00, // ###################### ### #### + 0x00, 0x00, 0xFF, 0xFF, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x01, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, // #################### ##### + 0x00, 0x00, 0x3F, 0xFF, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ################ + 0x00, 0x00, 0x0F, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // ########### + 0x00, 0x00, 0x00, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // #### + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, +}; + +// Bitmap sizes for maxim128 +const unsigned char maxim128WidthPages = 16; +const unsigned char maxim128HeightPixels = 36; + +#define PIN_displayCS P0_7 +#define PIN_displayEXTCOM P6_4 +#define PIN_MODE_BUTTON P6_5 +#define PIN_MODE_BUTTON P2_3 + +//#define USE_BIGFONT + + +typedef struct{ + PwmOut *dispPWM; + SPI *dispPSI; + DigitalOut *dispCS; + silabs::LS013B7DH03 *display; + InterruptIn *button; + uint8_t buttonMode; + volatile uint8_t algoMode; + volatile uint8_t prevAlgoMode; + char buffer[32]; + +}demo_ui_t; + +static demo_ui_t demoUIDEV; + +/*need protection with mutex or update in critical section outside isr context*/ +static unsigned int dispCnt = 0; + +void button_isr(void){ + + int i; + volatile uint32_t isr_delay = 0; + demoUIDEV.button->disable_irq(); + demoUIDEV.algoMode = 1- demoUIDEV.algoMode; + + for(i = 10000000 ; i; i--){ + isr_delay++; + } + dispCnt = 0; + demoUIDEV.button->enable_irq(); +} + + +void demoUI_init_(demo_ui_t *demoUIDEV ) +{ + + static PwmOut displayPWM(PIN_displayEXTCOM); + static SPI displaySPI(P0_5, P0_6, P0_4, NC); + static DigitalOut displayCS(PIN_displayCS); + static silabs::LS013B7DH03 display(&displaySPI , &displayCS); + static InterruptIn button(PIN_MODE_BUTTON); + + demoUIDEV->dispCS = &displayCS; + demoUIDEV->dispPWM = &displayPWM; + demoUIDEV->dispPSI = &displaySPI; + demoUIDEV->display = &display; + + demoUIDEV->button = &button; + demoUIDEV->buttonMode = 0; + demoUIDEV->algoMode = DISPLAY_WHRM; + demoUIDEV->prevAlgoMode = DISPLAY_WHRM; + + demoUIDEV->dispPSI->frequency(1000000); + demoUIDEV->dispPWM->period_ms(16); + demoUIDEV->dispPWM->pulsewidth_ms(8); + demoUIDEV->display->clearImmediate(NULL); +#if defined(USE_BIGFONT) + display.set_font(UbuntuCondensed16x21); +#endif + demoUIDEV->button->fall(button_isr); + demoUIDEV->button->disable_irq(); + wait_ms(20); + demoUIDEV->button->enable_irq(); +} + + +void demoUI_display_algo_estimations_(demo_ui_t *demoUIDEV , int integer) +{ + + + //demoUIDEV->display->locate(3,10); + demoUIDEV->display->foreground(Black); + demoUIDEV->display->background(White); + +#if defined(USE_BIGFONT) + demoUIDEV->display->locate(2,6); + +#else + demoUIDEV->display->locate(2,4); +#endif + + switch( demoUIDEV->algoMode ){ + case DISPLAY_WHRM: +#if defined(USE_BIGFONT) + demoUIDEV->display->locate(2,22); + demoUIDEV->display->printf("HEART RATE"); + + if(integer > 10 && integer < 100) + snprintf(demoUIDEV->buffer, 32, "BpS: %s%d "," ", integer); + else if( integer > 100 && integer < 205) + snprintf(demoUIDEV->buffer, 32, "BpS: %s%d "," ", integer); +#else + + demoUIDEV->display->printf("HEART RATE "); + if(integer > 10 && integer < 100) + snprintf(demoUIDEV->buffer, 32, "BpS: %s%d "," ", integer); + else if( integer > 100 && integer < 205) + snprintf(demoUIDEV->buffer, 32, "BpS: %s%d "," ", integer); +#endif + break; + + case DISPLAY_WSPo2: +#if defined(USE_BIGFONT) + demoUIDEV->display->locate(2,22); + demoUIDEV->display->printf("BLD OXYGEN"); + if(integer >= 0 && integer < 100) + snprintf(demoUIDEV->buffer, 32, "SPo2: %s%d ","%%", integer); +#else + demoUIDEV->display->printf("BLOOD OXYGEN"); + if( integer < 80 ){ + dispCnt++; + + unsigned int quanta = (dispCnt >> 2) & 0x00000003; + if( quanta == 0) + snprintf(demoUIDEV->buffer, 32, "COMPUTING "); + else if( quanta == 1) + snprintf(demoUIDEV->buffer, 32, "COMPUTING. "); + else if( quanta == 2) + snprintf(demoUIDEV->buffer, 32, "COMPUTING.. "); + else + snprintf(demoUIDEV->buffer, 32, "COMPUTING... "); + + if( dispCnt > 100 && dispCnt < 120 ) + snprintf(demoUIDEV->buffer, 32, "LOW SNR "); + else if( dispCnt > 120) + dispCnt = 0; + } + else{ + snprintf(demoUIDEV->buffer, 32, "SPo2: %s%d ","%%", integer); + dispCnt = 0; + } + +#endif + break; + + } +#if defined(USE_BIGFONT) + demoUIDEV->display->locate(10,42); +#else + demoUIDEV->display->locate(2,6); +#endif + demoUIDEV->display->printf(demoUIDEV->buffer); + + demoUIDEV->display->showBMP((uint8_t*)maxim128Bitmaps, 128, 40, 0, 86); + demoUIDEV->display->update(); + + /*DEBUG*///wait_ms(20); +} + +void demoUI_display_set_algoMode_( demo_ui_t *demoUIDEV , int algo){ + + demoUIDEV->algoMode = (algo == 0)? DISPLAY_WHRM : DISPLAY_WSPo2; +} +int demoUI_display_get_algoMode_(demo_ui_t *demoUIDEV){ + return (demoUIDEV->algoMode); +} + +void demoUI_init(void ){ + demoUI_init_(&demoUIDEV); + demoUI_display_set_algoMode_(&demoUIDEV ,DISPLAY_WHRM); + return; +} + +void demoUI_display_algo_estimations(int integer){ + demoUI_display_algo_estimations_(&demoUIDEV,integer); + return; + +} + +void demoUI_display_set_algoMode(int algo){ + demoUI_display_set_algoMode_(&demoUIDEV ,algo); + return; +} + +int demoUI_display_get_mode(void){ + return demoUI_display_get_algoMode_(&demoUIDEV); +} + +void demoUI_display(int algoResult){ + static bool is_initialized = false; + if( !is_initialized){ + demoUI_init_(&demoUIDEV); + is_initialized = true; + return; + } + demoUI_display_algo_estimations_(&demoUIDEV,algoResult); +} + + + + + + + +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/demoUI.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,69 @@ +/******************************************************************************* + * Copyright (C) 2018 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + ******************************************************************************* + */ + +#ifndef SOURCE_DEMOUI_DEMOUI_H_ +#define SOURCE_DEMOUI_DEMOUI_H_ + +#include <events/mbed_events.h> +#include <mbed.h> + +#include "screen/LS013B7DH03.h" + +enum{ + DISPLAY_WHRM = 0, + DISPLAY_WSPo2 = 1 +}; + +#define USE_DEMO_DISPDEV +#if defined(USE_DEMO_DISPDEV) + + + void demoUI_init(); + void demoUI_display_algo_estimations(int integer); + void demoUI_display_set_algoMode(int algo); + int demoUI_display_get_mode(void); + void demoUI_display(int algoResult); + + + +#else + void start_demo_display(void); + void display_algo_estimations( uint8_t mode , int integer, int fraction); + void setup_mode_button(void); + +#endif + + +extern volatile uint8_t algoMode; + +#endif /* SOURCE_DEMOUI_DEMOUI_H_ */
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/BufferedDisplay.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,139 @@ +/***************************************************************************//** + * @file BufferedDisplay.cpp + * @brief Buffered version of GraphicsDisplay + ******************************************************************************* + * @section License + * <b>(C) Copyright 2015 Silicon Labs, http://www.silabs.com</b> + ******************************************************************************* + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * 3. This notice may not be removed or altered from any source distribution. + * + * DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Silicon Labs has no + * obligation to support this Software. Silicon Labs is providing the + * Software "AS IS", with no express or implied warranties of any kind, + * including, but not limited to, any implied warranties of merchantability + * or fitness for any particular purpose or warranties against infringement + * of any proprietary rights of a third party. + * + * Silicon Labs will not be liable for any consequential, incidental, or + * special damages, or any other relief, or for any claim by any third party, + * arising from your use of this Software. + * + ******************************************************************************/ + +#include "../screen/BufferedDisplay.h" + +#define SWAP8(a) ((((a) & 0x80) >> 7) | (((a) & 0x40) >> 5) | (((a) & 0x20) >> 3) | (((a) & 0x10) >> 1) | (((a) & 0x08) << 1) | (((a) & 0x04) << 3) | (((a) & 0x02) << 5) | (((a) & 0x01) << 7)) + +namespace silabs { + + BufferedDisplay::BufferedDisplay(const char *name) : GraphicsDisplay(name) { + memset((uint8_t*)_pixelBuffer, White, sizeof(_pixelBuffer)); // init full frame buffer + memset((uint8_t*)_dirtyRows, 0xFF, sizeof(_dirtyRows)); // init dirty status + } + + /** + * Override of GraphicsDisplay's pixel() + */ + + void BufferedDisplay::pixel(int x, int y, int colour) { + /* Apply constraint to x and y */ + if(x < 0 || y < 0) return; + if(x >= DISPLAY_WIDTH || y >= DISPLAY_HEIGHT) return; + + /***************************************************************************************************************** + * The display expects LSB input, while the SPI is configured for 8bit MSB transfers. Therefore, we should + * construct the framebuffer accordingly, so that an MSB transmission will put pixel 0 first on the wire. + * + * So the actual pixel layout in framebuffer (for 128x128) is as follows: + * { //Framebuffer + * { //Line 0 + * {p0, p1, p2, p3, p4, p5, p6, p7}, //Line 0 byte 0 (byte 0) + * {p8, p9,p10,p11,p12,p13,p14,p15}, //Line 0 byte 1 (byte 1) + * ... + * {p120,p121,p122,p123,p124,p125,p126,p127} //Line 0 byte 15 (byte 15) + * }, + * { //Line 1 + * {p128,p129,p130,p131,p132,p133,p134,p135}, //Line 1 byte 0 (byte 16) + * ... + * }, + * ... + * { //Line 127 + * {...}, //Line 127 byte 0 (byte 2032) + * ... + * {...} //Line 127 byte 15 (byte 2047) = 128*128 bits + * } + * } + * + * This means that to calculate the actual bit position in the framebuffer byte, we need to swap the bit + * order of the lower three bits. So pixel 7 becomes bit offset 0, 6 -> 1, 5 -> 2, 4->3, 3->4, 2->5, 1->6 and 0->7. + *****************************************************************************************************************/ + uint8_t swapx = 7 - ((unsigned int)x & 0x07); + x = ((unsigned int)x & 0xFFFFFFF8) | swapx; + + /* Since we are dealing with 1-bit pixels, we can avoid having to do bitshift and comparison operations twice. + * Basically, do the comparison with the requested state and current state, and if it changed, do an XOR on the framebuffer pixel and set the line to dirty. + */ + bool change = ((_pixelBuffer[((y * DISPLAY_WIDTH) + x) / DISPLAY_BUFFER_TYPE_SIZE] & (1 << (x & DISPLAY_BUFFER_TYPE_MASK))) != ((colour & 0x01) << (x & DISPLAY_BUFFER_TYPE_MASK))); + if(change) { + /* Pixel's value and requested value are different, so since it's binary, we can simply do an XOR */ + _pixelBuffer[((y * DISPLAY_WIDTH) + x) / DISPLAY_BUFFER_TYPE_SIZE] ^= (1 << (x & DISPLAY_BUFFER_TYPE_MASK)); + + /* notify dirty status of this line */ + _dirtyRows[y / DISPLAY_BUFFER_TYPE_SIZE] |= (1 << (y & DISPLAY_BUFFER_TYPE_MASK)); + } + } + + int BufferedDisplay::width() { + return DISPLAY_WIDTH; + } + int BufferedDisplay::height() { + return DISPLAY_HEIGHT; + } + + /** + * Function to move bitmap into frame buffer + * arguments: + * * bitmap: pointer to uint8 array containing horizontal pixel data + * * bmpWidth: width of the bitmap in pixels (must be multiple of 8) + * * bmpHeight: height of the bitmap in pixels + * * startX: starting position to apply bitmap in horizontal direction (0 = leftmost) (must be multiple of 8) + * * startY: starting position to apply bitmap in vertical direction (0 = topmost) + */ + void BufferedDisplay::showBMP(const uint8_t* bitmap, const uint32_t bmpWidth, const uint32_t bmpHeight, const uint32_t startX, const uint32_t startY) { + uint32_t bmpLine = 0, y = startY, bytesPerLine = ((bmpWidth >= (DISPLAY_WIDTH - startX)) ? (DISPLAY_WIDTH - startX) : bmpWidth) / 8; + + /* Apply constraints */ + if((bmpWidth & 0x07) != 0) return; + if((startX & 0x07) != 0) return; + if(startX >= DISPLAY_WIDTH) return; + + //Superflouous due to for-loop check + //if((startY >= DISPLAY_HEIGHT) return; + + /* Copy over bytes to the framebuffer, do not write outside framebuffer boundary */ + for(; y < DISPLAY_HEIGHT; y++) { + /* Check that we are not writing more than the BMP height */ + if(bmpLine >= bmpHeight) break; + + /* Copy over one line (bmpLine) from the BMP file to the corresponding line (y) in the pixel buffer */ + memcpy( (void*) &(((uint8_t*)_pixelBuffer)[((y * DISPLAY_WIDTH) + startX) / 8]), + (const void*) &(bitmap[bmpLine * (bmpWidth / 8)]), + bytesPerLine); + + /* Set dirty status for the line we just overwrote */ + _dirtyRows[y / DISPLAY_BUFFER_TYPE_SIZE] |= (1 << (y % DISPLAY_BUFFER_TYPE_SIZE)); + bmpLine++; + } + + return; + } +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/BufferedDisplay.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,81 @@ +/***************************************************************************//** + * @file BufferedDisplay.h + * @brief Framebuffered version of GraphicsDisplay + ******************************************************************************* + * @section License + * <b>(C) Copyright 2015 Silicon Labs, http://www.silabs.com</b> + ******************************************************************************* + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * 3. This notice may not be removed or altered from any source distribution. + * + * DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Silicon Labs has no + * obligation to support this Software. Silicon Labs is providing the + * Software "AS IS", with no express or implied warranties of any kind, + * including, but not limited to, any implied warranties of merchantability + * or fitness for any particular purpose or warranties against infringement + * of any proprietary rights of a third party. + * + * Silicon Labs will not be liable for any consequential, incidental, or + * special damages, or any other relief, or for any claim by any third party, + * arising from your use of this Software. + * + ******************************************************************************/ + +#ifndef SILABS_BUFFEREDDISPLAY_H +#define SILABS_BUFFEREDDISPLAY_H + +#include "../screen/GraphicsDisplay.h" +#include "../screen/LCDSettings.h" + +namespace silabs { +/** Framebuffered version of GraphicsDisplay + * + * This has been implemented as part of the MemoryLCD library. + */ +class BufferedDisplay : public GraphicsDisplay { + +public: + + BufferedDisplay(const char *name=NULL); + + /** + * Override of GraphicsDisplay pixel() function to set a pixel in the buffer + * + * @param x Zero-based x-axis index of pixel to set. 0 = leftmost. + * @param y Zero-based y-axis index of pixel to set. 0 = topmost. + * @param colour Colour value to set pixel to. In this implementation, only LSB is taken into account. + */ + virtual void pixel(int x, int y, int colour); + virtual int width(); + virtual int height(); + + /** + * Function to move bitmap into frame buffer + * + * @param bitmap pointer to uint8 array containing horizontal pixel data + * @param bmpWidth width of the bitmap in pixels (must be multiple of 8) + * @param bmpHeight height of the bitmap in pixels + * @param startX starting position to apply bitmap in horizontal direction (0 = leftmost) (must be multiple of 8) + * @param startY starting position to apply bitmap in vertical direction (0 = topmost) + */ + void showBMP(const uint8_t* bitmap, const uint32_t bmpWidth, const uint32_t bmpHeight, const uint32_t startX, const uint32_t startY); + +protected: + volatile DISPLAY_BUFFER_TYPE _pixelBuffer[DISPLAY_BUFFER_ELEMENTS]; // one full frame buffer + volatile DISPLAY_BUFFER_TYPE _dirtyRows[DISPLAY_HEIGHT/DISPLAY_BUFFER_TYPE_SIZE]; // 1 bit per row to indicate dirty status +}; + +} // namespace silabs + + + + +#endif //SILABS_BUFFEREDDISPLAY_H
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/GraphicsDisplay.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,456 @@ +/* mbed GraphicsDisplay Display Library Base Class + * Copyright (c) 2007-2009 sford + * Released under the MIT License: http://mbed.org/license/mit + */ + +#include "../screen/GraphicsDisplay.h" + +#define incx() x++, dxt += d2xt, t += dxt +#define incy() y--, dyt += d2yt, t += dyt + +const unsigned char FONT8x8[97][8] = { +{0x08,0x08,0x08,0x00,0x00,0x00,0x00,0x00}, // columns, rows, num_bytes_per_char +{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}, // space 0x20 +{0x30,0x78,0x78,0x30,0x30,0x00,0x30,0x00}, // ! +{0x6C,0x6C,0x6C,0x00,0x00,0x00,0x00,0x00}, // " +{0x6C,0x6C,0xFE,0x6C,0xFE,0x6C,0x6C,0x00}, // # +{0x18,0x3E,0x60,0x3C,0x06,0x7C,0x18,0x00}, // $ +{0x00,0x63,0x66,0x0C,0x18,0x33,0x63,0x00}, // % +{0x1C,0x36,0x1C,0x3B,0x6E,0x66,0x3B,0x00}, // & +{0x30,0x30,0x60,0x00,0x00,0x00,0x00,0x00}, // ' +{0x0C,0x18,0x30,0x30,0x30,0x18,0x0C,0x00}, // ( +{0x30,0x18,0x0C,0x0C,0x0C,0x18,0x30,0x00}, // ) +{0x00,0x66,0x3C,0xFF,0x3C,0x66,0x00,0x00}, // * +{0x00,0x30,0x30,0xFC,0x30,0x30,0x00,0x00}, // + +{0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x30}, // , +{0x00,0x00,0x00,0x7E,0x00,0x00,0x00,0x00}, // - +{0x00,0x00,0x00,0x00,0x00,0x18,0x18,0x00}, // . +{0x03,0x06,0x0C,0x18,0x30,0x60,0x40,0x00}, // / (forward slash) +{0x3E,0x63,0x63,0x6B,0x63,0x63,0x3E,0x00}, // 0 0x30 +{0x18,0x38,0x58,0x18,0x18,0x18,0x7E,0x00}, // 1 +{0x3C,0x66,0x06,0x1C,0x30,0x66,0x7E,0x00}, // 2 +{0x3C,0x66,0x06,0x1C,0x06,0x66,0x3C,0x00}, // 3 +{0x0E,0x1E,0x36,0x66,0x7F,0x06,0x0F,0x00}, // 4 +{0x7E,0x60,0x7C,0x06,0x06,0x66,0x3C,0x00}, // 5 +{0x1C,0x30,0x60,0x7C,0x66,0x66,0x3C,0x00}, // 6 +{0x7E,0x66,0x06,0x0C,0x18,0x18,0x18,0x00}, // 7 +{0x3C,0x66,0x66,0x3C,0x66,0x66,0x3C,0x00}, // 8 +{0x3C,0x66,0x66,0x3E,0x06,0x0C,0x38,0x00}, // 9 +{0x00,0x18,0x18,0x00,0x00,0x18,0x18,0x00}, // : +{0x00,0x18,0x18,0x00,0x00,0x18,0x18,0x30}, // ; +{0x0C,0x18,0x30,0x60,0x30,0x18,0x0C,0x00}, // < +{0x00,0x00,0x7E,0x00,0x00,0x7E,0x00,0x00}, // = +{0x30,0x18,0x0C,0x06,0x0C,0x18,0x30,0x00}, // > +{0x3C,0x66,0x06,0x0C,0x18,0x00,0x18,0x00}, // ? +{0x3E,0x63,0x6F,0x69,0x6F,0x60,0x3E,0x00}, // @ 0x40 +{0x18,0x3C,0x66,0x66,0x7E,0x66,0x66,0x00}, // A +{0x7E,0x33,0x33,0x3E,0x33,0x33,0x7E,0x00}, // B +{0x1E,0x33,0x60,0x60,0x60,0x33,0x1E,0x00}, // C +{0x7C,0x36,0x33,0x33,0x33,0x36,0x7C,0x00}, // D +{0x7F,0x31,0x34,0x3C,0x34,0x31,0x7F,0x00}, // E +{0x7F,0x31,0x34,0x3C,0x34,0x30,0x78,0x00}, // F +{0x1E,0x33,0x60,0x60,0x67,0x33,0x1F,0x00}, // G +{0x66,0x66,0x66,0x7E,0x66,0x66,0x66,0x00}, // H +{0x3C,0x18,0x18,0x18,0x18,0x18,0x3C,0x00}, // I +{0x0F,0x06,0x06,0x06,0x66,0x66,0x3C,0x00}, // J +{0x73,0x33,0x36,0x3C,0x36,0x33,0x73,0x00}, // K +{0x78,0x30,0x30,0x30,0x31,0x33,0x7F,0x00}, // L +{0x63,0x77,0x7F,0x7F,0x6B,0x63,0x63,0x00}, // M +{0x63,0x73,0x7B,0x6F,0x67,0x63,0x63,0x00}, // N +{0x3E,0x63,0x63,0x63,0x63,0x63,0x3E,0x00}, // O +{0x7E,0x33,0x33,0x3E,0x30,0x30,0x78,0x00}, // P 0x50 +{0x3C,0x66,0x66,0x66,0x6E,0x3C,0x0E,0x00}, // Q +{0x7E,0x33,0x33,0x3E,0x36,0x33,0x73,0x00}, // R +{0x3C,0x66,0x30,0x18,0x0C,0x66,0x3C,0x00}, // S +{0x7E,0x5A,0x18,0x18,0x18,0x18,0x3C,0x00}, // T +{0x66,0x66,0x66,0x66,0x66,0x66,0x7E,0x00}, // U +{0x66,0x66,0x66,0x66,0x66,0x3C,0x18,0x00}, // V +{0x63,0x63,0x63,0x6B,0x7F,0x77,0x63,0x00}, // W +{0x63,0x63,0x36,0x1C,0x1C,0x36,0x63,0x00}, // X +{0x66,0x66,0x66,0x3C,0x18,0x18,0x3C,0x00}, // Y +{0x7F,0x63,0x46,0x0C,0x19,0x33,0x7F,0x00}, // Z +{0x3C,0x30,0x30,0x30,0x30,0x30,0x3C,0x00}, // [ +{0x60,0x30,0x18,0x0C,0x06,0x03,0x01,0x00}, // \ (back slash) +{0x3C,0x0C,0x0C,0x0C,0x0C,0x0C,0x3C,0x00}, // ] +{0x08,0x1C,0x36,0x63,0x00,0x00,0x00,0x00}, // ^ +{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFF}, // _ +{0x18,0x18,0x0C,0x00,0x00,0x00,0x00,0x00}, // ` 0x60 +{0x00,0x00,0x3C,0x06,0x3E,0x66,0x3B,0x00}, // a +{0x70,0x30,0x3E,0x33,0x33,0x33,0x6E,0x00}, // b +{0x00,0x00,0x3C,0x66,0x60,0x66,0x3C,0x00}, // c +{0x0E,0x06,0x3E,0x66,0x66,0x66,0x3B,0x00}, // d +{0x00,0x00,0x3C,0x66,0x7E,0x60,0x3C,0x00}, // e +{0x1C,0x36,0x30,0x78,0x30,0x30,0x78,0x00}, // f +{0x00,0x00,0x3B,0x66,0x66,0x3E,0x06,0x7C}, // g +{0x70,0x30,0x36,0x3B,0x33,0x33,0x73,0x00}, // h +{0x18,0x00,0x38,0x18,0x18,0x18,0x3C,0x00}, // i +{0x06,0x00,0x06,0x06,0x06,0x66,0x66,0x3C}, // j +{0x70,0x30,0x33,0x36,0x3C,0x36,0x73,0x00}, // k +{0x38,0x18,0x18,0x18,0x18,0x18,0x3C,0x00}, // l +{0x00,0x00,0x66,0x7F,0x7F,0x6B,0x63,0x00}, // m +{0x00,0x00,0x7C,0x66,0x66,0x66,0x66,0x00}, // n +{0x00,0x00,0x3C,0x66,0x66,0x66,0x3C,0x00}, // o +{0x00,0x00,0x6E,0x33,0x33,0x3E,0x30,0x78}, // p +{0x00,0x00,0x3B,0x66,0x66,0x3E,0x06,0x0F}, // q +{0x00,0x00,0x6E,0x3B,0x33,0x30,0x78,0x00}, // r +{0x00,0x00,0x3E,0x60,0x3C,0x06,0x7C,0x00}, // s +{0x08,0x18,0x3E,0x18,0x18,0x1A,0x0C,0x00}, // t +{0x00,0x00,0x66,0x66,0x66,0x66,0x3B,0x00}, // u +{0x00,0x00,0x66,0x66,0x66,0x3C,0x18,0x00}, // v +{0x00,0x00,0x63,0x6B,0x7F,0x7F,0x36,0x00}, // w +{0x00,0x00,0x63,0x36,0x1C,0x36,0x63,0x00}, // x +{0x00,0x00,0x66,0x66,0x66,0x3E,0x06,0x7C}, // y +{0x00,0x00,0x7E,0x4C,0x18,0x32,0x7E,0x00}, // z +{0x0E,0x18,0x18,0x70,0x18,0x18,0x0E,0x00}, // { +{0x0C,0x0C,0x0C,0x00,0x0C,0x0C,0x0C,0x00}, // | +{0x70,0x18,0x18,0x0E,0x18,0x18,0x70,0x00}, // } +{0x3B,0x6E,0x00,0x00,0x00,0x00,0x00,0x00}, // ~ +{0x1C,0x36,0x36,0x1C,0x00,0x00,0x00,0x00}}; // DEL + +GraphicsDisplay::GraphicsDisplay(const char *name):TextDisplay(name) { + foreground((uint16_t)Black); + background((uint16_t)White); + // current pixel location + _x = 0; + _y = 0; + // window settings + _x1 = 0; + _x2 = 0; + _y1 = 0; + _y2 = 0; +} + +void GraphicsDisplay::character(int column, int row, int value) { + if(externalfont){ // send external font + unsigned int hor,vert,offset,bpl,j,i,b; + const unsigned char* sign; + unsigned char z,w; + if ((value < 31) || (value > 127)) return; // test char range + // read font parameter from start of array + offset = font[0]; // bytes / char + hor = font[1]; // get hor size of font + vert = font[2]; // get vert size of font + bpl = font[3]; // bytes per line + if (char_x + hor > width()) { + char_x = 0; + char_y = char_y + vert; + if (char_y >= height() - font[2]) { + char_y = 0; + } + } + window(char_x, char_y,hor,vert); // char box + sign = &font[((value -32) * offset) + 4]; // start of char bitmap + w = sign[0]; // width of actual char + for (j=0; j<vert; j++) { // vert line + for (i=0; i<hor; i++) { // horz line + z = sign[bpl * i + ((j & 0xF8) >> 3)+1]; + b = 1 << (j & 0x07); + if (( z & b ) == 0x00) { + putp(_foreground); + } + else { + putp(_background); + } + } + } + if ((w + 2) < hor) { // x offset to next char + char_x += w + 2; + } + else char_x += hor; + } + // send default font + else { + blitbit(column * 8, row * 8, 8, 8, (char*)&(FONT8x8[value - 0x1F][0])); + } +} + +void GraphicsDisplay::window(int x, int y, int w, int h) { + // current pixel location + _x = x; + _y = y; + // window settings + _x1 = x; + _x2 = x + w - 1; + _y1 = y; + _y2 = y + h - 1; +} + +void GraphicsDisplay::putp(int colour) { + // put pixel at current pixel location + pixel(_x, _y, colour); + // update pixel location based on window settings + _x++; + if(_x > _x2) { + _x = _x1; + _y++; + if(_y > _y2) { + _y = _y1; + } + } +} + +void GraphicsDisplay::rect(int x0, int y0, int x1, int y1, int color) { + if (x1 > x0) hline(x0,x1,y0,color); + else hline(x1,x0,y0,color); + if (y1 > y0) vline(x0,y0,y1,color); + else vline(x0,y1,y0,color); + if (x1 > x0) hline(x0,x1,y1,color); + else hline(x1,x0,y1,color); + if (y1 > y0) vline(x1,y0,y1,color); + else vline(x1,y1,y0,color); + return; +} + +void GraphicsDisplay::fillrect(int x0, int y0, int w, int h, int colour) { + unsigned long int index=0; + if (w < 0) { + x0 = x0 + w; + w = -w; + } + if (h < 0) { + y0 = y0 + h; + h = -h; + } + window(x0,y0,w,h); + int num = h*w; + for( index = 0; index<num; index++ ) { + putp(colour); + } + return; +} + +void GraphicsDisplay::fill(int x, int y, int w, int h, int colour) { + fillrect(x, y, w, h, colour); +} + +void GraphicsDisplay::circle(int x, int y, int r,int colour){ + int ce = -r; + int cx = r; + int cy = 0; + while(cx >= cy){ + pixel(x+cx,y+cy,colour); + pixel(x-cx,y-cy,colour); + pixel(x-cx,y+cy,colour); + pixel(x+cx,y-cy,colour); + pixel(x+cy,y+cx,colour); + pixel(x-cy,y+cx,colour); + pixel(x-cy,y-cx,colour); + pixel(x+cy,y-cx,colour); + ce += 2*cy++ + 1; + if(ce >= 0){ + ce -= 2*cx---1; + } + + } + +} + +// To draw circle set a and b to the same values +void GraphicsDisplay::ellipse(int xc, int yc, int a, int b, unsigned int colour) +{ + /* e(x,y) = b^2*x^2 + a^2*y^2 - a^2*b^2 */ + int x = 0, y = b; + long a2 = (long)a*a, b2 = (long)b*b; + long crit1 = -(a2/4 + a%2 + b2); + long crit2 = -(b2/4 + b%2 + a2); + long crit3 = -(b2/4 + b%2); + long t = -a2*y; // e(x+1/2,y-1/2) - (a^2+b^2)/4 + long dxt = 2*b2*x, dyt = -2*a2*y; + long d2xt = 2*b2, d2yt = 2*a2; + + while (y>=0 && x<=a) { + pixel(xc+x, yc+y, colour); + if (x!=0 || y!=0) + pixel(xc-x, yc-y, colour); + if (x!=0 && y!=0) { + pixel(xc+x, yc-y, colour); + pixel(xc-x, yc+y, colour); + } + if (t + b2*x <= crit1 || // e(x+1,y-1/2) <= 0 + t + a2*y <= crit3) // e(x+1/2,y) <= 0 + incx(); + else if (t - a2*y > crit2) // e(x+1/2,y-1) > 0 + incy(); + else { + incx(); + incy(); + } + } +} +// To draw circle set a and b to the same values +void GraphicsDisplay::fillellipse(int xc, int yc, int a, int b, unsigned int colour) +{ + /* e(x,y) = b^2*x^2 + a^2*y^2 - a^2*b^2 */ + int x = 0, y = b; + int rx = x, ry = y; + unsigned int width = 1; + unsigned int height = 1; + long a2 = (long)a*a, b2 = (long)b*b; + long crit1 = -(a2/4 + a%2 + b2); + long crit2 = -(b2/4 + b%2 + a2); + long crit3 = -(b2/4 + b%2); + long t = -a2*y; // e(x+1/2,y-1/2) - (a^2+b^2)/4 + long dxt = 2*b2*x, dyt = -2*a2*y; + long d2xt = 2*b2, d2yt = 2*a2; + if (b == 0) { + fillrect(xc-a, yc, 2*a+1, 1, colour); + return; + } + while (y>=0 && x<=a) { + if (t + b2*x <= crit1 || // e(x+1,y-1/2) <= 0 + t + a2*y <= crit3) { // e(x+1/2,y) <= 0 + if (height == 1) + ; // draw nothing + else if (ry*2+1 > (height-1)*2) { + fillrect(xc-rx, yc-ry, width, height-1, colour); + fillrect(xc-rx, yc+ry+1, width, 1-height, colour); + ry -= height-1; + height = 1; + } else { + fillrect(xc-rx, yc-ry, width, ry*2+1, colour); + ry -= ry; + height = 1; + } + incx(); + rx++; + width += 2; + } else if (t - a2*y > crit2) { // e(x+1/2,y-1) > 0 + incy(); + height++; + } else { + if (ry*2+1 > height*2) { + fillrect(xc-rx, yc-ry, width, height, colour); + fillrect(xc-rx, yc+ry+1, width, -height, colour); + } else { + fillrect(xc-rx, yc-ry, width, ry*2+1, colour); + } + incx(); + incy(); + rx++; + width += 2; + ry -= height; + height = 1; + } + } + if (ry > height) { + fillrect(xc-rx, yc-ry, width, height, colour); + fillrect(xc-rx, yc+ry+1, width, -height, colour); + } else { + fillrect(xc-rx, yc-ry, width, ry*2+1, colour); + } +} + + +void GraphicsDisplay::line(int x0, int y0, int x1, int y1, int colour) { + //window(x0, y, w, h); + int dx = 0, dy = 0; + int dx_sym = 0, dy_sym = 0; + int dx_x2 = 0, dy_x2 = 0; + int di = 0; + dx = x1-x0; + dy = y1-y0; + + if (dx == 0) { /* vertical line */ + if (y1 > y0) vline(x0,y0,y1,colour); + else vline(x0,y1,y0,colour); + return; + } + if (dx > 0) { + dx_sym = 1; + } else { + dx_sym = -1; + } + if (dy == 0) { /* horizontal line */ + if (x1 > x0) hline(x0,x1,y0,colour); + else hline(x1,x0,y0,colour); + return; + } + if (dy > 0) { + dy_sym = 1; + } else { + dy_sym = -1; + } + dx = dx_sym*dx; + dy = dy_sym*dy; + dx_x2 = dx*2; + dy_x2 = dy*2; + if (dx >= dy) { + di = dy_x2 - dx; + while (x0 != x1) { + + pixel(x0, y0, colour); + x0 += dx_sym; + if (di<0) { + di += dy_x2; + } else { + di += dy_x2 - dx_x2; + y0 += dy_sym; + } + } + pixel(x0, y0, colour); + } else { + di = dx_x2 - dy; + while (y0 != y1) { + pixel(x0, y0, colour); + y0 += dy_sym; + if (di < 0) { + di += dx_x2; + } else { + di += dx_x2 - dy_x2; + x0 += dx_sym; + } + } + pixel(x0, y0, colour); + } + return; +} + +void GraphicsDisplay::hline(int x0, int x1, int y, int colour) { + int w; + w = x1 - x0 + 1; + window(x0,y,w,1); + for (int x=0; x<w; x++) { + putp(colour); + } + return; +} + +void GraphicsDisplay::vline(int x, int y0, int y1, int colour) { + int h; + h = y1 - y0 + 1; + window(x,y0,1,h); + for (int y=0; y<h; y++) { + putp(colour); + } + return; +} + +void GraphicsDisplay::cls() { + fill(0, 0, width(), height(), _background); +} + +void GraphicsDisplay::blit(int x, int y, int w, int h, const int *colour) { + window(x, y, w, h); + for(int i=0; i<w*h; i++) { + putp(colour[i]); + } +} + +void GraphicsDisplay::blitbit(int x, int y, int w, int h, const char* colour) { + window(x, y, w, h); + for(int i = 0; i < w*h; i++) { + char byte = colour[i >> 3]; + int offset = i & 0x7; + int c = ((byte << (offset)) & 0x80) ? _foreground : _background; + putp(c); + } +} + +int GraphicsDisplay::columns() { + return width() / 8; +} + +int GraphicsDisplay::rows() { + return height() / 8; +} +
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/GraphicsDisplay.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,68 @@ +/* mbed GraphicsDisplay Display Library Base Class + * Copyright (c) 2007-2009 sford + * Released under the MIT License: http://mbed.org/license/mit + * + * A library for providing a common base class for Graphics displays + * To port a new display, derive from this class and implement + * the constructor (setup the display), pixel (put a pixel + * at a location), width and height functions. Everything else + * (locate, printf, putc, cls, window, putp, fill, blit, blitbit) + * will come for free. You can also provide a specialised implementation + * of window and putp to speed up the results + */ + +#ifndef MBED_GRAPHICSDISPLAY_H +#define MBED_GRAPHICSDISPLAY_H + +#include "../screen/TextDisplay.h" + +class GraphicsDisplay : public TextDisplay { + +public: + + GraphicsDisplay(const char* name); + + virtual void pixel(int x, int y, int colour) = 0; + virtual int width() = 0; + virtual int height() = 0; + + virtual void window(int x, int y, int w, int h); + virtual void putp(int colour); + + virtual void cls(); + virtual void rect(int x0, int y0, int x1, int y1, int colour); + virtual void fillrect(int x0, int y0, int w, int h, int colour); + // fill equals fillrect, name has been kept to not break compatibility + virtual void fill(int x, int y, int w, int h, int colour); + + // To draw circle using ellipse, set a and b to the same values + virtual void ellipse(int xc, int yc, int a, int b, unsigned int colour); + virtual void fillellipse(int xc, int yc, int a, int b, unsigned int colour); + virtual void circle(int x, int y, int r, int colour); + + virtual void hline(int x0, int x1, int y, int colour); + virtual void vline(int x0, int y0, int y1, int colour); + virtual void line(int x0, int y0, int x1, int y1, int colour); + + virtual void blit(int x, int y, int w, int h, const int *colour); + virtual void blitbit(int x, int y, int w, int h, const char* colour); + + virtual void character(int column, int row, int value); + virtual int columns(); + virtual int rows(); + +protected: + + // pixel location + short _x; + short _y; + + // window location + short _x1; + short _x2; + short _y1; + short _y2; + +}; + +#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/LCDSettings.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,29 @@ +#ifndef LCDSETTINGS_H +#define LCDSETTINGS_H + +/** MemoryLCD width in pixels */ +#define DISPLAY_WIDTH (128) + +/** MemoryLCD height in pixels */ +#define DISPLAY_HEIGHT (128) + +/** Data type for storing buffer the pixel buffer */ +#if ((DISPLAY_WIDTH % 32) == 0) +#define DISPLAY_BUFFER_TYPE uint32_t +#define DISPLAY_BUFFER_TYPE_MASK (0x1F) +#else +#define DISPLAY_BUFFER_TYPE uint8_t +#define DISPLAY_BUFFER_TYPE_MASK (0x07) +#endif + +#define DISPLAY_BUFFER_TYPE_SIZE (sizeof(DISPLAY_BUFFER_TYPE) * 8) +#define DISPLAY_BUFFER_ELEMENTS ((DISPLAY_WIDTH*DISPLAY_HEIGHT)/DISPLAY_BUFFER_TYPE_SIZE) + +/** Maximum length of a printf to the display */ +#define MAX_PRINTF_CHARS 40 + +/** Color definitions */ +#define White 0xFFFFFFFF +#define Black 0x00000000 + +#endif
Binary file demoUI/screen/LS013B7DH03.ZIP has changed
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/LS013B7DH03.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,245 @@ +/***************************************************************************//** + * @file LS013B7DH03.cpp + * @brief Driver class for the Sharp LS013B7DH03 memory LCD on some kits. + ******************************************************************************* + * @section License + * <b>(C) Copyright 2015 Silicon Labs, http://www.silabs.com</b> + ******************************************************************************* + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * 3. This notice may not be removed or altered from any source distribution. + * + * DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Silicon Labs has no + * obligation to support this Software. Silicon Labs is providing the + * Software "AS IS", with no express or implied warranties of any kind, + * including, but not limited to, any implied warranties of merchantability + * or fitness for any particular purpose or warranties against infringement + * of any proprietary rights of a third party. + * + * Silicon Labs will not be liable for any consequential, incidental, or + * special damages, or any other relief, or for any claim by any third party, + * arising from your use of this Software. + * + ******************************************************************************/ + +#include "../screen/LS013B7DH03.h" + +#include <mbed.h> +#include "SPI.h" +//#include "Peripherals.h" + +/* LS013B7DH03 SPI commands */ +#define LS013B7DH03_CMD_UPDATE (0x01) +#define LS013B7DH03_CMD_ALL_CLEAR (0x04) + +/* Macro to switch endianness on char value */ +#define SWAP8(a) ((((a) & 0x80) >> 7) | (((a) & 0x40) >> 5) | (((a) & 0x20) >> 3) | (((a) & 0x10) >> 1) | (((a) & 0x08) << 1) | (((a) & 0x04) << 3) | (((a) & 0x02) << 5) | (((a) & 0x01) << 7)) + +namespace silabs { + + +LS013B7DH03::LS013B7DH03(mbed::SPI * spi, DigitalOut * CS, const char *name) : BufferedDisplay( name ) { + //Save pointer to ChipSelect pin + _CS = CS; + _CS->write(0); + DigitalOut DISP(P6_6); + +//Save pointer to ExtCom pin +/// _EXTCOM = ExtCom; +/// _EXTCOM->write(0); + + DISP = 0; + wait_ms(1); + DISP = 1; + + //Save pointer to spi peripheral + _spi = spi; + //_spi->frequency(600000); + _spi->format( 8, 0 ); + + _internalEventCallback.attach(this, &LS013B7DH03::_cbHandler); + + //Initialize + //_spi->set_dma_usage((DMAUsage)DMA_USAGE_NEVER); + _refreshCount = 0; + _lcdPolarity = 0; + _state = IDLE; + _completionCallbackPtr = NULL; + _rowCount = 0; + + //Start toggling the EXTCOM pin + //_displayToggler.attach(this, &LS013B7DH03::toggle, 0.008f); +} + +/** + * Call this function at 55 ~ 65 Hz to keep the display up-to-date. + */ +void LS013B7DH03::toggle() { +// _EXTCOM->write(!_EXTCOM->read()); +// _refreshCount++; +} + +/** + * Function to get internal refresh counter + */ +uint32_t LS013B7DH03::getRefreshTicks() { + return _refreshCount; +} + +/** + * Call this function to push all changes to the display + */ +int LS013B7DH03::update( cbptr_t callback ) { + uint32_t rowCount = 0; + bool update = false; + + // Check if something actually changed in the pixelbuffer + for(rowCount = 0; rowCount < DISPLAY_HEIGHT/DISPLAY_BUFFER_TYPE_SIZE; rowCount++) { + if(_dirtyRows[rowCount] != 0) update = true; + } + + if(update == false) return LS013B7DH03_NO_ACTION; + + // Watch out to not mess up a transfer + if(_state != IDLE) return LS013B7DH03_ERROR_BUSY; + + _completionCallbackPtr = callback; + + // Take control + _state = WAIT_WRITE; + _rowCount = 0; + + //Initialize the command vector + _cmd[0] = (uint8_t)SWAP8(LS013B7DH03_CMD_UPDATE); + _cmd[1] = SWAP8(1); + + // Activate LCD + _CS->write(1); + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.01f); + + return LS013B7DH03_OK; +} + +/** + * Function to test display buffer + */ +int LS013B7DH03::showDemo() { + for(uint32_t i = 0; i < DISPLAY_BUFFER_ELEMENTS; i+=2) { + _pixelBuffer[i] = 0x00555345; + } + memset((void*)_dirtyRows, 0x33, sizeof(_dirtyRows)); + + return LS013B7DH03_OK; +} + +/** + * Call this function to immediately clear the display + */ +int LS013B7DH03::clearImmediate( cbptr_t callback ) { + // Watch out to not mess up a transfer + if(_state != IDLE) return LS013B7DH03_ERROR_BUSY; + + _state = WAIT_CLEAR; + _completionCallbackPtr = callback; + + // Clear out the pixel buffer + memset((void*)_pixelBuffer, White, sizeof(_pixelBuffer)); + memset((void*)_dirtyRows, 0, sizeof(_dirtyRows)); + + _cmd[0] = (uint8_t)(SWAP8(LS013B7DH03_CMD_ALL_CLEAR | _lcdPolarity)); + _cmd[1] = 0; + + // Wait for the ChipSelect line + _CS->write(1); + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.01f); + + return LS013B7DH03_OK; +} + +void LS013B7DH03::_cbHandlerTimeout( void ) { + this->_cbHandler(0); +} + +void LS013B7DH03::_cbHandler( int event ) { + if((_state == WAIT_WRITE) || (_state == WRITING)) + { + _state = WRITING; + while(_rowCount < DISPLAY_HEIGHT) { + // Determine the next line to send + if((_dirtyRows[_rowCount / DISPLAY_BUFFER_TYPE_SIZE] & (1 << (_rowCount % DISPLAY_BUFFER_TYPE_SIZE))) != 0) { + + // Row is dirty, send an update to the display + _cmd[1] = (uint8_t)SWAP8(_rowCount + 1); + memcpy((void*)&(_cmd[2]), (const void*)&(_pixelBuffer[_rowCount*(DISPLAY_WIDTH/DISPLAY_BUFFER_TYPE_SIZE)]), DISPLAY_WIDTH / DISPLAY_BUFFER_TYPE_SIZE * sizeof(DISPLAY_BUFFER_TYPE)); + + if(_spi->write((const char*)_cmd, (2 + (DISPLAY_WIDTH / DISPLAY_BUFFER_TYPE_SIZE * sizeof(DISPLAY_BUFFER_TYPE))) , (char*)NULL, 0/*, _internalEventCallback, SPI_EVENT_COMPLETE*/) != (2 + (DISPLAY_WIDTH / DISPLAY_BUFFER_TYPE_SIZE * sizeof(DISPLAY_BUFFER_TYPE)))) { + // SPI is busy, with another transaction. This means the data to the LCD has been corrupted, so fail here. + _state = DONE; + //printf("Failed at _cbHandler\n"); + // Make sure the handler is called again + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.1f); + }else{ //sc... + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.001f); + } + + // Transaction is in progress, so update row state + _dirtyRows[_rowCount / DISPLAY_BUFFER_TYPE_SIZE] &= ~(1 << (_rowCount % DISPLAY_BUFFER_TYPE_SIZE)); + _rowCount++; + return; + } + + // Row wasn't touched, so check the next row + _rowCount++; + } + + // Done sending! + _cmd[1] = 0xFF; + _state = TRANSFERS_DONE; + if(_spi->write((const char*)_cmd, 2, (char*)NULL, 0/*, _internalEventCallback, SPI_EVENT_COMPLETE*/) != 2) { + // SPI is busy, with another transaction. This means the data to the LCD has been corrupted, so fail here. + _state = DONE; + + // Make sure the handler is called again + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.1f); + }else{ //sc... + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.001f); + } + return; + } + else if (_state == WAIT_CLEAR) + { + _state = TRANSFERS_DONE; + if(_spi->write((const char*)_cmd, 2, (char*)NULL, 0/*, _internalEventCallback, SPI_EVENT_COMPLETE*/) != 2) { + // SPI is busy, with another transaction. This means the data to the LCD has been corrupted, so fail here. + _state = DONE; + + // Make sure the handler is called again + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.1f); + }else{ //sc... + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.001f); + } + return; + } + else if (_state == TRANSFERS_DONE) + { + _state = DONE; + _csTimeout.attach(this, &LS013B7DH03::_cbHandlerTimeout, 0.01f); + return; + } + else if (_state == DONE) + { + _CS->write(0); + _state = IDLE; + if(_completionCallbackPtr != 0) _completionCallbackPtr(); + return; + } +} + +} // namespace silabs
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/LS013B7DH03.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,123 @@ +/***************************************************************************//** + * @file LS013B7DH03.h + * @brief Driver class for the Sharp LS013B7DH03 memory LCD on some kits. + ******************************************************************************* + * @section License + * <b>(C) Copyright 2015 Silicon Labs, http://www.silabs.com</b> + ******************************************************************************* + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * 3. This notice may not be removed or altered from any source distribution. + * + * DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Silicon Labs has no + * obligation to support this Software. Silicon Labs is providing the + * Software "AS IS", with no express or implied warranties of any kind, + * including, but not limited to, any implied warranties of merchantability + * or fitness for any particular purpose or warranties against infringement + * of any proprietary rights of a third party. + * + * Silicon Labs will not be liable for any consequential, incidental, or + * special damages, or any other relief, or for any claim by any third party, + * arising from your use of this Software. + * + ******************************************************************************/ + +#ifndef SILABS_LS013B7DH03_H +#define SILABS_LS013B7DH03_H + +#include "platform.h" +#include <mbed.h> +#include "../screen/BufferedDisplay.h" +#include "../screen/LCDSettings.h" +//#include "Peripherals.h" + +typedef void (*cbptr_t)(void); + +#define LS013B7DH03_ERROR_BUSY -1 +#define LS013B7DH03_ERROR_SPI_BUSY -2 +#define LS013B7DH03_NO_ACTION -3 +#define LS013B7DH03_ERROR_ARGUMENT -4 +#define LS013B7DH03_OK 0 + +typedef enum { + IDLE, // No operation currently ongoing + CLEARING, // In the process of clearing the display + WRITING, // In the process of sending a display update + WAIT_CLEAR, // Going to clear after CS pin timeout + WAIT_WRITE, // Going to write after CS pin timeout + TRANSFERS_DONE, // Last transfer in progress + DONE // Done with transmission, waiting for CS pin to become high +} LS013B7DH03_state_t; + +namespace silabs { +class LS013B7DH03 : public BufferedDisplay { + +public: + + LS013B7DH03(SPI * spi, DigitalOut * CS, const char *name=NULL); + + /** + * Call this function to push all changes to the display + */ + int update( cbptr_t callback = NULL ); + + /** + * Immediately clear the display: set pixel buffer to zero and clear out the display. + */ + int clearImmediate( cbptr_t callback = NULL ); + + /** + * Function to test display buffer + */ + int showDemo(); + + + + /** + * Function to get internal refresh counter + */ + uint32_t getRefreshTicks(); + + +protected: + mbed::SPI *_spi; + //mbed::DigitalOut *_EXTCOM; + mbed::DigitalOut *_CS; + + mbed::Ticker _displayToggler; + mbed::Timeout _csTimeout; + + event_callback_t _internalEventCallback; + volatile uint32_t _refreshCount; + uint8_t _lcdPolarity; + LS013B7DH03_state_t _state; + cbptr_t _completionCallbackPtr; + volatile uint32_t _rowCount; + uint8_t _cmd[2 + (DISPLAY_WIDTH / DISPLAY_BUFFER_TYPE_SIZE * sizeof(DISPLAY_BUFFER_TYPE))]; + + /** + * Callback handler for internal SPI transfers. + */ + void _cbHandler( int event ); + + /** + * Callback handler for internal SPI transfers triggered by timeout. + */ + void _cbHandlerTimeout( void ); + + /** + * Call this function at 55 ~ 65 Hz to keep the display from losing contrast. + */ + void toggle(); +}; + +} // namespace silabs + +#endif //SILABS_LS013B7DH03_H
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/TextDisplay.cpp Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,93 @@ +/* mbed TextDisplay Display Library Base Class + * Copyright (c) 2007-2009 sford + * Released under the MIT License: http://mbed.org/license/mit + */ + +#include "../screen/TextDisplay.h" + +#include <cstdarg> + +TextDisplay::TextDisplay(const char *name){ + _row = 0; + _column = 0; + + if (name == NULL) { + _path = NULL; + } else { + _path = new char[strlen(name) + 2]; + sprintf(_path, "/%s", name); + } +} + +int TextDisplay::_putc(int value) { + if(value == '\n') { + _column = 0; + _row++; + if(_row >= rows()) { + _row = 0; + } + } else { + character(_column, _row, value); + _column++; + if(_column >= columns()) { + _column = 0; + _row++; + if(_row >= rows()) { + _row = 0; + } + } + } + return value; +} + +// crude cls implementation, should generally be overwritten in derived class +void TextDisplay::cls() { + locate(0, 0); + for(int i=0; i<columns()*rows(); i++) { + _putc(' '); + } +} + +void TextDisplay::set_font(const unsigned char * f) { + font = f; + if(font==NULL) { + externalfont = 0; // set display.font + locate(0, 0); + } + else{ + externalfont = 1; + locate(0, 0); + } +} + +void TextDisplay::locate(int column, int row) { + _column = column; + _row = row; + char_x = column; + char_y = row; +} + +int TextDisplay::_getc() { + return -1; +} + +void TextDisplay::foreground(uint16_t colour) { + _foreground = colour; +} + +void TextDisplay::background(uint16_t colour) { + _background = colour; +} + +void TextDisplay::printf(const char* format, ...) { + char buffer[MAX_PRINTF_CHARS + 1] = { 0 }; + uint32_t iterator = 0; + va_list args; + va_start(args, format); + vsprintf(buffer, format, args); + va_end(args); + + while((buffer[iterator] != 0) && (iterator < MAX_PRINTF_CHARS)) { + _putc(buffer[iterator++]); + } +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/demoUI/screen/TextDisplay.h Mon Dec 17 13:58:56 2018 +0300 @@ -0,0 +1,92 @@ +/* mbed TextDisplay Library Base Class + * Copyright (c) 2007-2009 sford + * Released under the MIT License: http://mbed.org/license/mit + * + * A common base class for Text displays + * To port a new display, derive from this class and implement + * the constructor (setup the display), character (put a character + * at a location), rows and columns (number of rows/cols) functions. + * Everything else (locate, printf, putc, cls) will come for free + * + * The model is the display will wrap at the right and bottom, so you can + * keep writing and will always get valid characters. The location is + * maintained internally to the class to make this easy + */ + +#ifndef MBED_TEXTDISPLAY_H +#define MBED_TEXTDISPLAY_H + +#include "../screen/LCDSettings.h" +#include "mbed.h" + +class TextDisplay { +public: + + // functions needing implementation in derived implementation class + /** Create a TextDisplay interface + * + * @param name The name used in the path to access the strean through the filesystem + */ + TextDisplay(const char *name = NULL); + + /** output a character at the given position + * + * @param column column where charater must be written + * @param row where character must be written + * @param c the character to be written to the TextDisplay + */ + virtual void character(int column, int row, int c) = 0; + + /** return number if rows on TextDisplay + * @result number of rows + */ + virtual int rows() = 0; + + /** return number if columns on TextDisplay + * @result number of rows + */ + virtual int columns() = 0; + + // Sets external font usage, eg. dispaly.set_font(Arial12x12); + // This uses pixel positioning. + // display.set_font(NULL); returns to internal default font. + void set_font(const unsigned char * f); + + // set position of the next character or string print. + // External font, set pixel x(column),y(row) position. + // internal(default) font, set character column and row position + virtual void locate(int column, int row); + + // functions that come for free, but can be overwritten + + /** clear screen + */ + virtual void cls(); + virtual void foreground(uint16_t colour); + virtual void background(uint16_t colour); + // putc (from Stream) + // printf (from Stream) + virtual void printf(const char* format, ...); + +protected: + + virtual int _putc(int value); + virtual int _getc(); + + // external font functions + const unsigned char* font; + int externalfont; + + // character location + uint16_t _column; + uint16_t _row; + unsigned int char_x; + unsigned int char_y; + + // colours + uint16_t _foreground; + uint16_t _background; + char *_path; +}; + +#endif