找回密码
 立即注册
查看: 988|回复: 7

使用SPI-DMA无限驱动WS2812灯带!无需反相器,STC32F上验证成功

[复制链接]
  • TA的每日心情
    开心
    2 分钟前
  • 签到天数: 114 天

    [LV.6]常住居民II

    31

    主题

    390

    回帖

    1992

    积分

    荣誉版主

    积分
    1992
    发表于 2024-1-5 19:35:31 | 显示全部楼层 |阅读模式
    前言:
    近来考试周,感觉复习的多了总是有点烦躁的。正好前几天看到有几个帖子在讨论W2812灯珠驱动的问题。
    借此机会就写点驱动和灯效解解闷
    STC DMA-SPI 驱动 WS2812 实现:无需反相器,无限长度WS2812驱动
    ===(我没有那么长的灯带,理论测定,底下有理论分析依据)。
    先上个效果视频

    回顾现在论坛里面的主要问题有这么几个:
    1.首先是就是SPI-DMA发送数据的时候每一个8位数据之间会存在一段拉高的电平
    ==这个可以通过初始设置 SCLK,MISO,MOSI 为0,就可以解决了,具体原因不详。
    2.大家说的特别长的灯带没法驱动
    ==经过验证,SPI-DMA间隔只有4.8us(较高优先级),而手册上说数据位的低电平时间不能超过20us。所以时间是完全够用的。
    3.还看到梁工说可以使用四位驱动,更节省内存占用。
    ==我尝试了一下,可以实现。我的设定是300ns的SPI单bit周期。
    此时0码是1000,1码是1110。正好对应手册典型值300ns和900ns。
    截图202401051926047150.jpg

    300ns的准确周期我是使用了HPLL拉高频率后进行分频得到的,理论上来说常见的频率都可以这么变换到所需要的频率
    以下是我的驱动时序:
    MOSI和SCLK时序.BMP

    可以看到0码的驱动周期为准确的300ns。


    DMA的测试是通过在SPI-DMA中断里拉高测试IO口得到的:
    两次DMA触发间隔.BMP

    可以看到上一个数据发送完成后,到下一个书发送开始只隔了4.8ns。


    程序等我整理一下发上来,因为是套了个别的工程,分离出来需要一点时间。
    注明:我的程序直接使用并不能驱动非常长的W2812灯带,因为我还没用双缓冲来做SPI-DMA
    我仅仅是验证了一下理论存在,目前可以驱动的最大长度大约在340个灯珠左右。


    ==文件已经上传,文件main.c文件前几行写明了注意事项。文件内基本都有注释,不清楚的可以在本贴问我。





    WS2812灯带.zip

    151.81 KB, 下载次数: 92

    1 喜欢他/她就送朵鲜花吧,赠人玫瑰,手有余香!
    回复 送花

    使用道具 举报

  • TA的每日心情
    开心
    4 天前
  • 签到天数: 32 天

    [LV.5]常住居民I

    2

    主题

    16

    回帖

    396

    积分

    中级会员

    积分
    396
    发表于 2024-1-6 08:01:35 | 显示全部楼层
    看看,学习一下
    回复 支持 反对 送花

    使用道具 举报

  • TA的每日心情
    开心
    昨天 08:25
  • 签到天数: 117 天

    [LV.6]常住居民II

    1

    主题

    34

    回帖

    611

    积分

    高级会员

    积分
    611
    发表于 2024-1-6 08:46:28 | 显示全部楼层
    由于DMA缓存数据只有256字节,一颗灯占12字节。长灯都需要灯数可调,所以数据组只能以12为单位,就等于DMA每次只能缓存一颗灯,会导致灯数多了之后刷新时间会拉得很长。实验的刷3000个灯的时间基本超过1秒

    点评

    长灯刷新时间长很正常,不过你说的DMA每次只能缓存一颗灯我不是很理解,灯数可调完全可以做到最后一个不能被整除的灯数时再分割,而不是开始就一个一个分割。 还有一个问题是,我这个DMA最大能64K,这个是STC32F,和  详情 回复 发表于 2024-1-6 12:47
    回复 支持 反对 送花

    使用道具 举报

  • TA的每日心情
    开心
    2 分钟前
  • 签到天数: 114 天

    [LV.6]常住居民II

    31

    主题

    390

    回帖

    1992

    积分

    荣誉版主

    积分
    1992
     楼主| 发表于 2024-1-6 12:47:23 | 显示全部楼层
    lihappy 发表于 2024-1-6 08:46
    由于DMA缓存数据只有256字节,一颗灯占12字节。长灯都需要灯数可调,所以数据组只能以12为单位,就等于DMA ...

    长灯刷新时间长很正常,不过你说的DMA每次只能缓存一颗灯我不是很理解,灯数可调完全可以做到最后一个不能被整除的灯数时再分割,而不是开始就一个一个分割。
    还有一个问题是,我这个DMA最大能64K,这个是STC32F,和STC8H还是有点不一样的
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    550

    主题

    9346

    回帖

    1万

    积分

    管理员

    积分
    13920
    发表于 2024-1-6 13:22:26 | 显示全部楼层
    STC8H8K64U的 DMA 可以用 多缓冲技术,显示数据先放到 不同起始地址的 xdata,DMA送完1包,改 DMA 起始地址就行
    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    550

    主题

    9346

    回帖

    1万

    积分

    管理员

    积分
    13920
    发表于 2024-1-9 08:42:53 | 显示全部楼层
    SPI方案:
    只用到MOSI驱动WS2812,但由于SPI的3个信号是捆绑在一起的,MISO、SCLK不能做它用。
    ===将 MISO 不做其他用途;
    ===将 MISO管脚 先设置为对外输出0;
    ===MOSI 发送完成后,对外停止时输出的是 MISO 读到的状态, 0 ,这 STC-R&D 留了这么个绝活支持 WS2812B !!!

    回复 支持 反对 送花

    使用道具 举报

    该用户从未签到

    0

    主题

    1

    回帖

    6

    积分

    新手上路

    积分
    6
    发表于 2024-4-30 12:20:52 | 显示全部楼层
    大师,初学者从哪里开始学习,谢谢!

    点评

    可以从官方的例程开始,仔细看看技术手册  详情 回复 发表于 2024-4-30 14:09
    回复 支持 反对 送花

    使用道具 举报

  • TA的每日心情
    开心
    2 分钟前
  • 签到天数: 114 天

    [LV.6]常住居民II

    31

    主题

    390

    回帖

    1992

    积分

    荣誉版主

    积分
    1992
     楼主| 发表于 2024-4-30 14:09:18 | 显示全部楼层
    RWJ576871 发表于 2024-4-30 12:20
    大师,初学者从哪里开始学习,谢谢!

    可以从官方的例程开始,仔细看看技术手册
    回复 支持 反对 送花

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|深圳国芯人工智能有限公司 ( 粤ICP备2022108929号-2 )

    GMT+8, 2024-5-9 07:54 , Processed in 0.068318 second(s), 61 queries .

    Powered by Discuz! X3.5

    © 2001-2024 Discuz! Team.

    快速回复 返回顶部 返回列表