单片机读取光照强度在电脑的串口调试助手显示光强:
源文件 #include "GY30.h" #include "delay.h" #include "myiic.h" void bh_data_send(u8 command) { do{ IIC_Start(); //iic开始 IIC_Send_Byte(BHAddWrite); //写地址 }while(IIC_Wait_Ack()); //等待响应 IIC_Send_Byte(command); //发送命令 IIC_Wait_Ack(); //等待响应 IIC_Stop(); //iic停止 } u16 bh_data_read(void) { u16 buf; IIC_Start(); //iic开始 IIC_Send_Byte(BHAddRead); //发送读地址 IIC_Wait_Ack(); //等待响应 buf=IIC_Read_Byte(1); //读取数据 buf=buf<<8; //读取并保存高八位数据 buf+=0x00ff&IIC_Read_Byte(0); //读取并保存第八位数据 IIC_Stop(); //发送停止信号 return buf; } void BH1750init(void) { bh_data_send(BHPowOn); //发送启动信号 bh_data_send(BHReset); //清除寄存器 bh_data_send(BHModeH1); //设置为模式2 delay_ms(180); //最高延时180ms }
头文件 #ifndef __SHT30_H__ #define __SHT30_H__ //命令 #define BHAddWrite 0x46 //写地址 #define BHAddRead 0x47 //读地址 #define BHPowDown 0x00 //关闭模块 #define BHPowOn 0x01 //打开模块等待指令 #define BHReset 0x07 //重置数据寄存器仅在BHpowOn模式下有效 #define BHModeH1 0x10 //高分辨率 模式1 单位 11X 测量时间 120ms #define BHModeH2 0x11 //高分辨率 模式2 单位 11X 测量时间 120ms #define BHModeL 0x13 //低分辨率 单位4lx 测量时间16ms #define BHSigModeH 0x20 //一次测量高分辨率模式1,然后转到powerdown模式 #define BHSigModeH2 0x21 //同上类似 #define BHSigModeL 0x23 //同上类似 void bh_data_send(unsigned char command); unsigned short bh_data_read(void); void BH1750init(void); #endif
IIC源文件 #include "myiic.h" #include "delay.h" static void SDA_Input(void); //声明static SDA_Input用于配置为输入模式 static void SDA_Output(void); //声明static SDA_Output,用于配置为输出模式 static void SDA_Input(void) //设置DHT11引脚输入模式 { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(SDA_RCC,ENABLE); //??GPIOD??? GPIO_InitStructure.GPIO_Pin = SDA_PIN; //?????PD13 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; //??50MHz GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; //上拉输入模式 GPIO_Init(SDA_GPIO, &GPIO_InitStructure); } static void SDA_Output(void)//设置DHT11引脚 输出模式 { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(SDA_RCC,ENABLE);//??GPIOD?? GPIO_InitStructure.GPIO_Pin = SDA_PIN;//?????PD13 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;//推挽输出 GPIO_Init(SDA_GPIO, &GPIO_InitStructure);//??? } //初始化IIC void IIC_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOB, ENABLE ); //使能GPIOB时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6|GPIO_Pin_7; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ; //推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOB, &GPIO_InitStructure); GPIO_SetBits(GPIOB,GPIO_Pin_6|GPIO_Pin_7); //PB6,PB7 输出高 } //产生IIC起始信号 void IIC_Start(void) { SDA_Output(); //sda线输出 IIC_SDA=1; IIC_SCL=1; delay_us(5);//延时大于4.7us IIC_SDA=0;//START:when CLK is high,DATA change form high to low delay_us(5);//延时大于4us IIC_SCL=0;//钳住I2C总线,准备发送或接收数据 } //产生IIC停止信号 void IIC_Stop(void) { SDA_Output();//sda线输出 IIC_SCL=0; IIC_SDA=0;//STOP:when CLK is high DATA change form low to high delay_us(5);//延时大于4us IIC_SCL=1; IIC_SDA=1;//发送I2C总线结束信号 delay_us(5); //延时大于4.7us } //从机等待应答信号到来 //返回值:1,接收应答失败 // 0,接收应答成功 u8 IIC_Wait_Ack(void) { u8 ucErrTime=0; SDA_Input(); //SDA设置为输入 IIC_SDA=1;delay_us(1); IIC_SCL=1;delay_us(1); while(READ_SDA) { ucErrTime++; if(ucErrTime>250) { IIC_Stop(); return 1; } } IIC_SCL=0;//时钟输出0 return 0; } //产生ACK应答 void IIC_Ack(void) { IIC_SCL=0; SDA_Output(); IIC_SDA=0; delay_us(2); IIC_SCL=1; delay_us(2); IIC_SCL=0; } //不产生ACK应答 void IIC_NAck(void) { IIC_SCL=0; SDA_Output(); IIC_SDA=1; delay_us(2); IIC_SCL=1; delay_us(2); IIC_SCL=0; } //IIC发送一个字节 //返回从机有无应答 //1,有应答 //0,无应答 void IIC_Send_Byte(u8 txd) { u8 t; SDA_Output(); IIC_SCL=0;//拉低时钟开始数据传输 for(t=0;t<8;t++) { //IIC_SDA=(txd&0x80)>>7; if((txd&0x80)>>7) IIC_SDA=1; else IIC_SDA=0; txd<<=1; delay_us(2); //对TEA5767这三个延时都是必须的 IIC_SCL=1; delay_us(2); IIC_SCL=0; delay_us(2); } } //读1个字节,ack=1时,发送ACK,ack=0,发送nACK u8 IIC_Read_Byte(unsigned char ack) { unsigned char i,receive=0; SDA_Input();//SDA设置为输入 for(i=0;i<8;i++ ) { IIC_SCL=0; delay_us(2); IIC_SCL=1; receive<<=1; if(READ_SDA)receive++; delay_us(1); } if (!ack) IIC_NAck();//发送nACK else IIC_Ack(); //发送ACK return receive; }
文章来源: https://blog.csdn.net/qq_38215697/article/details/90635916