我要介绍的这种方法是基于rt-thread操作系统的,先介绍一下操作系统,我们初学单片机一般都是不跑操作系统的(俗称裸机),那些开发板的教程还有网上能找到的例程绝大部分也都是不跑操作系统的,初学者听到操作系统可能会害怕,其实使用操作系统并没有想象中那么难,在某些方面甚至比裸机更简单(比如我今天要讲的这个bh1750的驱动),好了,废话不多说,马上开整(步骤我分的比较细,看起来好像很复杂,其实用过RT-thread的都知道,这个操作很简单)。
如果你不想使用操作系统,要用裸机的话,可以参考我发布的博文:BH1750光照传感器超详细攻略 (从原理到代码讲解,看完你就懂了)
一、搭载RT-thread需要的环境
参考我的博文:RT-Thread零基础快速入门第0讲——环境安装
我们这里需要用到的软件主要有2个:1:keil5(版本在5.24以上),2:env
当然,如果你不确定是否要用rtt操作系统的话,也可以先不搭建环境,先跳到第二步下载我已经做好的工程,先运行一下看下效果(我用的是stm32f103)。
二、获取RT-thread官方源码,并新建一个工程
参考我的博文:RT-Thread零基础快速入门第1讲——新建工程
根据你的单片机型号,选择合适的bsp,生成一个新的工程。
我这里用的是stm32f103,整个工程都已经做好了,需要的话可以在下面的链接下载。
源码下载链接1:https://pan.baidu.com/s/1HnedCg3sC4HU8iEOf4dYOw ,提取码:xs8o
源码下载链接2:https://pan.baidu.com/s/1QOC01P5M99LzP4i1Voro6g,提取码:abcd
三、下载bh1750软件包
参考我的博文:RT-Thread零基础快速入门第8讲——软件包的使用
注意:RT-thread的bh1750软件包有几个版本,v1.0.0是单独的驱动(只有IIC通信部分的驱动,和裸机的程序类似),v2.0.0和latest版本除了IIC通信部分的驱动还加入了sensor的框架(这是rtt自己做的一个中间层框架,它的意义在于把很多不同种类的传感器合并到同一个框架里面,这样应用层就不需要针对不同的传感器编写不同的模块代码),总的来说就是,选择的版本不同,应用层的代码会有所区别(我这里用的是v1.0.0版本)。
env配置如下:
下载完之后在工程目录下可以找到一个bh1750-v1.0.0文件夹,里面有两个文件,bh1750.c和bh1750.h,这个就是我们需要的驱动代码。
四、配置IIC引脚
在工程根目录下打开env,输入menuconfig进入配置菜单,选择路径Hardware Drivers Config -> on-chip Peripheral Drivers -> Enable I2C1 BUS,配置IIC1的引脚号(不需要特定的IIC引脚,随便两个普通IO即可)
注意:1、不同芯片的工程(不同的bsp),配置菜单上面的选项在描述上可能有所不同。2、不一定要选择IIC1,也可以选IIC2或者IIC3,后面编写应用层代码时,IIC使用的通道号和现在选的一致即可。
五、编写应用层程序
RTT的工程里面都有一个maic.c文件,默认写的都是一个呼吸灯,我在这里添加一个线程专门用于bh1750的数据采集和打印,当然,也可以不用线程直接在main函数里面调用bh1750相关的函数。
不知道什么是线程概念的话可以看下我的博文:RT-Thread零基础快速入门第6讲——线程管理
/* main.c
* 功能:采集bh1750的数据并通过串口1打印,另外还有一个LED灯定时闪烁
*/
#include "rtthread.h"
#include "rtdevice.h"
#include "board.h"
#include "bh1750.h"
#include <string.h>
#include <stdio.h>
#include "math.h"
#include "stdio.h"
/* 宏定义 */
#define LED0_PIN GET_PIN(E, 5) // LED:PE5
#define BH1750_DEV "i2c1" // 这里和第五步配置的IIC通道要保持一致
float light; // 光照值,注意:这里定义的是浮点型,如果要通过串口打印或者显示屏显示,需要转换一下数据
/* BH1750数据处理线程 */
int bh1750_handle_entry(void)
{
static bh1750_device_t dev = RT_NULL;
if (dev)
{
bh1750_deinit(dev);
}
dev = bh1750_init(BH1750_DEV);
while(1)
{
light = bh1750_read_light(dev); // 该函数就在第四步下载的bh1750.c文件里面
// 串口1打印光照值
rt_kprintf("read bh1750 sensor intensity: %d%d%d%d%d.%d lxn", (int)(light * 10)/100000%10, (int)(light * 10)/10000%10, (int)(light * 10)/1000%10,
(int)(light * 10)/100%10, (int)(light * 10)/10%10, (int)(light * 10)/1%10);
rt_thread_mdelay(500); // 采集周期500ms
}
}
/* 主函数 */
int main(void)
{
// LED引脚初始化
rt_pin_mode(LED0_PIN, PIN_MODE_OUTPUT);
// 创建一个线程(用来单独做bh1750的数据采集和打印)
rt_thread_t bh1750_thread = rt_thread_create("bh1750_handle", bh1750_handle_entry, RT_NULL, 1024, 20, 20);
if(bh1750_thread)
{
rt_thread_startup(bh1750_thread); // 启动线程
}
while (1)
{
// LED灯定时闪烁
rt_pin_write(LED0_PIN, PIN_HIGH);
rt_thread_mdelay(500);
rt_pin_write(LED0_PIN, PIN_LOW);
rt_thread_mdelay(500);
}
}
六、总结
1、先搭载好rt-thread操作系统所需要的环境
2、了解rtt-thread的基本使用方法
3、编写应用层驱动代码(rtt的优点在于很多底层驱动都不需要自己写,只要在应用层调用相关的函数即可,所以使用操作系统有些时候比裸机更简单)
4、编译运行
本文用到的工程源码可以在下面的链接下载:
源码下载链接1:https://pan.baidu.com/s/1HnedCg3sC4HU8iEOf4dYOw ,提取码:xs8o
源码下载链接2:https://pan.baidu.com/s/1QOC01P5M99LzP4i1Voro6g,提取码:abcd
不熟悉rt-thread操作系统的话可以参考我发布的博文:
RT-Thread零基础快速入门第9讲——串口(UART/RS485)
BH1750电路原理部分我这边没有介绍,可以看下我之前发布的博文:BH1750光照传感器超详细攻略 (从原理到代码讲解,看完你就懂了)