* AM2321的取温度间隔得大于2s,否则,i2c会不工作了 * SimpleTimer有个bug,会导致两次快速的读温度,现在读温度函数里加了保护 * Blynk有个bug,会导致无法把数据传到服务器 * 现在可以正常工作了
AM2321.cpp
00001 // 00002 // AM2321 Temperature & Humidity Sensor library for Arduino 00003 // 00004 // The MIT License (MIT) 00005 // 00006 // Copyright (c) 2013 Wang Dong 00007 // 00008 // Permission is hereby granted, free of charge, to any person obtaining a copy 00009 // of this software and associated documentation files (the "Software"), to deal 00010 // in the Software without restriction, including without limitation the rights 00011 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 00012 // copies of the Software, and to permit persons to whom the Software is 00013 // furnished to do so, subject to the following conditions: 00014 // 00015 // The above copyright notice and this permission notice shall be included in 00016 // all copies or substantial portions of the Software. 00017 // 00018 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 00019 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 00020 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 00021 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 00022 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 00023 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 00024 // THE SOFTWARE. 00025 // 00026 00027 #include "AM2321.h" 00028 #include "mbed.h" 00029 extern I2C g_i2c; 00030 extern Serial pc; 00031 00032 #define I2C_ADDR_AM2321 (0xB8 >> 1) //AM2321温湿度计I2C地址 00033 #define PARAM_AM2321_READ 0x03 //读寄存器命令 00034 #define REG_AM2321_HUMIDITY_MSB 0x00 //湿度寄存器高位 00035 #define REG_AM2321_HUMIDITY_LSB 0x01 //湿度寄存器低位 00036 #define REG_AM2321_TEMPERATURE_MSB 0x02 //温度寄存器高位 00037 #define REG_AM2321_TEMPERATURE_LSB 0x03 //温度寄存器低位 00038 #define REG_AM2321_DEVICE_ID_BIT_24_31 0x0B //32位设备ID高8位 00039 00040 template<int I2CADDR, int COMMAND, int REGADDR, int REGCOUNT> 00041 class DataReader 00042 { 00043 protected: 00044 enum { len = 32 }; 00045 uint8_t buf[len]; 00046 00047 protected: 00048 DataReader() { 00049 memset(buf, 0, len); 00050 } 00051 bool readRaw() { 00052 // 00053 // Wakeup 00054 // 00055 //Wire.beginTransmission(I2CADDR); 00056 //Wire.endTransmission(); 00057 g_i2c.write(I2CADDR<<1, (char*)&buf[0], 1); 00058 wait_ms(2.9); 00059 // 00060 // Read Command 00061 // 00062 #if 0 00063 Wire.beginTransmission(I2CADDR); 00064 Wire.write(COMMAND); 00065 Wire.write(REGADDR); 00066 Wire.write(REGCOUNT); 00067 Wire.endTransmission(); 00068 #else 00069 char bu[3] = {COMMAND, REGADDR, REGCOUNT}; 00070 g_i2c.write(I2CADDR<<1, bu, 3); 00071 #endif 00072 00073 // 00074 // Waiting 00075 // 00076 //delayMicroseconds(1600); //>1.5ms 00077 wait_ms(1.6); 00078 00079 // 00080 // Read 00081 // 00082 #if 0 00083 Wire.requestFrom(I2CADDR, 2 + REGCOUNT + 2); // COMMAND + REGCOUNT + DATA + CRCLSB + CRCMSB 00084 int i = 0; 00085 for (; i < 2 + REGCOUNT; ++i) 00086 buf[i] = Wire.read(); 00087 00088 unsigned short crc = 0; 00089 crc = Wire.read(); //CRC LSB 00090 crc |= Wire.read() << 8;//CRC MSB 00091 00092 if (crc == crc16(buf, i)) 00093 return true; 00094 return false; 00095 #else 00096 uint8_t realAddr = (I2CADDR << 1) | 0x01; 00097 //pc.printf("realAddr = 0x%x\r\n", realAddr); 00098 g_i2c.read(realAddr, (char*)buf, 2 + REGCOUNT + 2); 00099 unsigned short crc = 0; 00100 crc = buf[2+REGCOUNT]; //CRC LSB 00101 crc |= buf[2+REGCOUNT+1] << 8;//CRC MSB 00102 #if 1 00103 for (int i = 0; i < 2 + REGCOUNT + 2; i++) { 00104 pc.printf("0x%X ", buf[i]); 00105 } 00106 pc.printf("\r\n"); 00107 #endif 00108 if (crc == crc16(buf, 2 + REGCOUNT)) 00109 return true; 00110 return false; 00111 #endif 00112 } 00113 00114 private: 00115 unsigned short crc16(unsigned char *ptr, unsigned char len) { 00116 unsigned short crc = 0xFFFF; 00117 unsigned char i = 0; 00118 while(len--) { 00119 crc ^= *ptr++; 00120 for(i = 0 ; i < 8 ; i++) { 00121 if(crc & 0x01) { 00122 crc >>= 1; 00123 crc ^= 0xA001; 00124 } else { 00125 crc >>= 1; 00126 } 00127 } 00128 } 00129 return crc; 00130 } 00131 }; 00132 00133 class UidReader : public DataReader<I2C_ADDR_AM2321, PARAM_AM2321_READ, REG_AM2321_DEVICE_ID_BIT_24_31, 4> 00134 { 00135 public: 00136 unsigned int uid; 00137 public: 00138 bool read() { 00139 if(!readRaw()) 00140 return false; 00141 uid = buf[2] << 24; 00142 uid += buf[3] << 16; 00143 uid += buf[4] << 8; 00144 uid += buf[5]; 00145 return true; 00146 } 00147 }; 00148 00149 class AirConditionReader : public DataReader<I2C_ADDR_AM2321, PARAM_AM2321_READ, REG_AM2321_HUMIDITY_MSB, 4> 00150 { 00151 public: 00152 unsigned int humidity; 00153 int temperature; 00154 public: 00155 bool read() { 00156 if(!readRaw()) 00157 return false; 00158 humidity = buf[2] << 8; 00159 humidity += buf[3]; 00160 temperature = (buf[4]&0x7F) << 8; 00161 temperature += buf[5]; 00162 if((buf[4]&0x80) == 0x80) 00163 temperature = -temperature; 00164 return true; 00165 } 00166 }; 00167 00168 00169 AM2321::AM2321() 00170 { 00171 //Wire.begin(); 00172 temperature = 0; 00173 humidity = 0; 00174 } 00175 00176 unsigned long AM2321::uid() 00177 { 00178 UidReader reader; 00179 if (reader.read()) 00180 return reader.uid; 00181 return -1; 00182 } 00183 00184 00185 bool AM2321::available() 00186 { 00187 return !(temperature == 0 && humidity == 0); 00188 } 00189 00190 bool AM2321::read() 00191 { 00192 AirConditionReader reader; 00193 if (reader.read()) { 00194 temperature = reader.temperature; 00195 humidity = reader.humidity; 00196 return true; 00197 } 00198 return false; 00199 } 00200 // 00201 // END OF FILE 00202 //
Generated on Tue Jul 12 2022 13:01:26 by 1.7.2