WS2812B简介

  1. 每个像素点都能实现256级亮度显示。
  2. 当刷新率为30帧/秒时,级联数不小于1024点。
  3. 数据发送速度为800Kbps。
  4. 通过DIN口输入数据,将复位后的第一组24bit数据保存,此后输入的数据都会从DO口发送给下一个级联像素点。
  5. 数据传输时间:

T0H

0码,高电平时间

220ns~420ns

T1H

1码,高电平时间

750ns~1.6μs

T0L

0码,低电平时间

750ns~1.6μs

T1L

1码,低电平时间

220ns~420ns

RES

帧单位,低电平时间

300μs以上

一、开发流程

1、PWM+DMA原理

2、配置RCC

3、配置SYS

4、配置时钟树

5、配置定时器TIMx

6、Keil5代码

二、具体操作

2.1、控制原理

PWM+DMA可以实现数量和占空比可控的脉冲,具体实现原理是在开启DMA的情况下,定时器在每次计数满后,会自动将DMA传输过来的数据作为新一轮的比较数值。如果DMA传输的数据每次不同,那么每次的方波占空比就不一样的。在本例程中,我们将数据存放在一个数组,通过DMA传输数组的内容,根据数组中数据的个数和每个数据的大小,就能实现数量和占空比可控的PWM。

DMA传输将数据从一个地址空间复制到另一个地址空间,提供在外设和存储器之间或者存储器和存储器之间的高速数据传输。

2.2、配置RCC

2.3配置SYS

2.4配置时钟树

2.5配置定时器TIM1

计算方法:

1、已知WS2812B的最大传输速率为800kbps,一次数据传输的时间在1.25μs。

2、设置定时器不分频(Prescaler为0即不分频)和计数周期(Couter Period)为89+1(软件会自动+1,填写的时候要减去1)。

3、波形频率算式:72M / (89+1)=800K,一个周期为1 / 800 = 1.25μs。

4、具体过程:

  1. 我们先配置Parameter settings,Parameter配置不分频,则f=1/72Mhz=0.0138888889us
  2. 时序符合388.8888us的复位时间。
  3. 通过计算,将89分为61和28时,时间为0.8472222229us和0.388888892us,符合传输条件。
  4. 89*0.0138888889us=1.2361111111us,符合一个数据传输的时间。

2.6在定时器中,Keil5代码开启DMA

2.7Keil5代码(此部分是复制别人的)

(1)创建RGB.c和RGB.h文件

(2)添加上述的RGB.c文件进工程

(3)RGB.c和RGB.h代码

RGB.h代码

#ifndef __RGB_H
#define __RGB_H
#include "main.h"
#define Hight_Data            ( 64  )                           //1 码相对计数值
#define Low_Data              ( 36  )                           //0 码相对计数值
#define Reste_Data            ( 80  )                           //80 复位电平相对计数值
#define Led_Num               (  4  )                           //WS2812灯个数
#define Led_Data_Len          ( 24  )                           //WS2812数据长度,单个需要24个字节
#define WS2812_Data_Len   (Led_Num * Led_Data_Len)              //ws2812级联后需要的数组长度//uint16_t RGB_buffur[Reste_Data + WS2812_Data_Len] = { 0 }; //数据缓存数组void WS2812_Display_1(uint32_t Color, uint16_t num);
void WS2812_Display_2( uint8_t red, uint8_t green, uint8_t blue,uint16_t num);void WS2812_Number_4(uint32_t Color1,uint32_t Color2,uint32_t Color3,uint32_t Color4);//封装好的四个灯函数,只需要分别输入四个灯的颜色即可#endif

RGB.c代码

#include "RGB.h"
#include "main.h"
#include "tim.h"uint16_t RGB_buffur[Reste_Data + WS2812_Data_Len] = { 0 }; //数据缓存数组void WS2812_Display_1(uint32_t Color, uint16_t num)
{//指针偏移:需要跳过复位信号的N个0uint16_t* p = (RGB_buffur + Reste_Data) + (num * Led_Data_Len);for (uint8_t i = 0; i < 8; ++i)         p[i+8]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);for (uint8_t i = 8; i < 16; ++i)p[i-8]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);for (uint8_t i = 16; i < 24; ++i)p[i]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);  }void WS2812_Display_2( uint8_t red, uint8_t green, uint8_t blue,uint16_t num)
{uint8_t i;uint32_t Color=(green << 16 | red << 8 | blue);//将2个8位数据合并转化为32位数据类型//指针偏移:需要跳过复位信号的N个0uint16_t* p = (RGB_buffur + Reste_Data) + (num * Led_Data_Len);for (i = 0; i < 24; ++i)    //对数组进行编辑p[i]= (((Color << i) & 0X800000) ? Hight_Data : Low_Data);   }void WS2812_Number_4(uint32_t Color1,uint32_t Color2,uint32_t Color3,uint32_t Color4)
{uint16_t  RGB_Buff_4[Reste_Data + 4 * WS2812_Data_Len] = { 0 };uint16_t* p;uint32_t Color;for( uint8_t k=0;k<4;k++){      switch (k)    //进行指针偏移{case 0: p= (RGB_Buff_4 + Reste_Data) + (0 * Led_Data_Len),Color=Color1;break;case 1: p= (RGB_Buff_4 + Reste_Data) + (1 * Led_Data_Len),Color=Color2;break;case 2: p= (RGB_Buff_4 + Reste_Data) + (2 * Led_Data_Len),Color=Color3;break;case 3: p= (RGB_Buff_4 + Reste_Data) + (3 * Led_Data_Len),Color=Color4;break;default : ;break;     }for (uint8_t i = 0; i < 8; ++i)   //对数组进行编辑{   for (uint8_t i = 0; i < 8; ++i)p[i+8]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);for (uint8_t i = 8; i < 16; ++i)p[i-8]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);for (uint8_t i = 16; i < 24; ++i)p[i]= (((Color << i) & 0X800000) ? Hight_Data :Low_Data);} }   HAL_TIM_PWM_Start_DMA(&htim1,TIM_CHANNEL_1,(uint32_t *)RGB_Buff_4,(176));//启动DMA传输}//  DMA 传输完成回调函数
void HAL_TIM_PWM_PulseFinishedCallback(TIM_HandleTypeDef *htim)
{HAL_TIM_PWM_Stop_DMA(&htim1,TIM_CHANNEL_1);
}

Main函数代码

#include "RGB.h"int main(void)
{extern uint16_t RGB_buffur[Reste_Data + WS2812_Data_Len];HAL_Init();SystemClock_Config();MX_GPIO_Init();MX_DMA_Init();MX_TIM1_Init();//        //点亮4个灯
//        WS2812_Display_1(0x180000, 0);
//        WS2812_Display_1(0x001800, 1);
//        WS2812_Display_1(0x000018, 2);
//        WS2812_Display_1(0x181818, 3);
//        HAL_TIM_PWM_Start_DMA(&htim1,TIM_CHANNEL_1,(uint32_t *)RGB_buffur,(176));//启动DMA传输        //        //以下代码和上述效果一致,只是颜色数据表示形式不一样
//        WS2812_Display_2( 22 , 0 , 0, 0);
//        WS2812_Display_2(  0 , 22, 0, 1);
//        WS2812_Display_2(  0 , 0, 22, 2);
//        WS2812_Display_2( 22, 22 , 22, 3);
//        HAL_TIM_PWM_Start_DMA(&htim1,TIM_CHANNEL_1,(uint32_t *)RGB_buffur,(176));//启动DMA传输 while (1){//流水效果WS2812_Number_4(0x180000,0x001800,0x000018,0);HAL_Delay(500);WS2812_Number_4(0,0x180000,0x001800,0x000018);HAL_Delay(500);WS2812_Number_4(0x000018,0,0x180000,0x001800);HAL_Delay(500);WS2812_Number_4(0x001800,0x000018,0,0x180000);HAL_Delay(500);}
}

【STM32+STM32CubeMX】控制ws2812b灯珠相关推荐

  1. STM32F427库函数PWM+DMA控制ws2812b灯带

    STM32F427IIHx库函数PWM+DMA控制ws2812b灯带 一.参考资料 查看ws2812b用户手册可知: 二.代码部分 添加文件ws2812b.c,ws2812b.h 配置的F427IIH ...

  2. STM32定时器控制LED灯闪烁及PWM练习

    一.STM32定时器控制LED灯闪烁 1.相关配置 1)配置RCC和SYS 2)配置IO 配置PC15,并命名为D1. 3)配置定时器 选定时器2,配置Clock Source为Internal Cl ...

  3. 三、使用Arduino控制WS2812B灯

    1.硬件 该硬件是基于ESP32设计的板子.如下图所示. 2.原理图 2.1.WS2812B原理图 2.2.ESP32部分原理图 综上:只需要控制IO17便可控制RGB灯. 3.软件编程 3.1.添加 ...

  4. STM32中断控制LED灯亮灭

    目录 一.中断介绍 1.中断分类 硬件中断(Hardware Interrupt) 软件中断(Software Interrupt) 2.中断优先级 3.中断源种类 4.中断响应原则 二.新建项目 1 ...

  5. STM32按键控制LED灯(中断实现)

    文章目录 1- 轮询模式和中断模式 2- 配置管脚为中断模式 3- 添加代码 4- 具体实现原理 5- main()--第一个执行程序? 在一般情况下,我们希望实现按键控制灯的亮和灭,这次学习的是中断 ...

  6. STM32按钮控制LED灯的开关

    Hi, I'm Shendi 在之前已经可以控制 PC13 LED灯了,这次加上按钮来控制 首先上效果 STM32按钮控制LED 我使用的是四脚按钮,默认引脚弯折相同的相通,不同不同,按下后四脚都通 ...

  7. STM32中断控制LED灯

    文章目录 一.相关概念 1.中断概念 2.中断过程 3.中断作用 4.中断优先级 5.中断响应过程 二. CubeMX中断控制LED灯 1.创建项目 2.代码修改 3.运行结果 三.HAL库中断串口通 ...

  8. STM32按键控制LED灯亮灭(四)

    编程要点: 1)使能GPIO端口时钟: 2)初始化GPIO目标引脚为输入模式(浮空输入): 3)编写简单测试程序,检测按键的状态,实现按键控制LED灯: bsp_led.h文件 #ifndef T_L ...

  9. STM32中断控制LED灯闪烁

    文章目录 一.中断 1.中断全过程 2.中断优先级 3.HAL库外部中断处理流程 4.中断回调函数 二.实现LED灯 三.实现项目 四.实验结果 五.总结 一.中断 1.中断全过程 中断发生 当CPU ...

  10. stm32【RGB_LED_WS2812灯珠】

    RGB_LED 内置驱动IC:WS2812 测试平台:stm32f103c8t6 库版本:官方标准库3.5.0版本 LED规格:RGB-5050 内置IC:ws2812 驱动方式:归零码 相比普通的L ...

最新文章

  1. 三大深度学习生成模型:VAE、GAN及其变种
  2. 《Apache Common CLI官方文档
  3. WINKEY功能键你会用吗??
  4. 我的第一个Scrapy 程序 - 爬取当当网信息
  5. 购物车Demo,前端使用AngularJS,后端使用ASP.NET Web API(2)--前端,以及前后端Session
  6. Eclipse is running in a JRE, but a JDK is required 解决方法(转)
  7. 更改文件和目录(及子目录)的拥有者
  8. 《Imperfect C++中文版》——1.3 运行期契约:前置条件、后置条件和不变式
  9. POJ 1426 Find The Multiple BFS
  10. this is a test
  11. matlab外接矩形,matlab求二值圖像最小外接矩形
  12. Java之添加环境变量
  13. DeepFake技术--实际操作
  14. 解决ubuntu 用anaconda 安装R 语言后,无法安装R语言package的问题
  15. 计算机编码,二进制编码数字
  16. 工程流体力学笔记暂记35 (平板层流边界层和平板混合边界层)
  17. “不能初始化photoshop,因为暂存盘已满”图文解决方案
  18. 电动车登记上牌系统源码免费分享
  19. 腾讯微博android版本,腾讯微博
  20. pythonencoding etf-8_Python 量化分析ETF指数基金投资

热门文章

  1. firefox的webmail notifier网易邮箱设置
  2. Python自动化结算工资和统计报表
  3. PlayReady 和WideVine
  4. PHP的CI框架接入redis
  5. 直播APP源码(干货):搭建直播平台的具体方案
  6. IsPostBack详解
  7. 升级版4850竖曲线
  8. 汽车票售票系统 php,客车网上售票系统(2)
  9. 欢迎使用CSDN-markdown编辑器闲置iPhone别扔 利用Carplay打造智能汽车
  10. CTF密码学——常见编解码及加解密总结