谷动谷力

 找回密码
 立即注册
查看: 1662|回复: 0
收起左侧

Arduino库可以直接在RT-Thread上运行啦!

[复制链接]
发表于 2022-8-31 22:49:24 | 显示全部楼层 |阅读模式
Arduino库可以直接在RT-Thread上运行啦!1 简介RTduino为RT-Thread的Arduino生态兼容层,是RT-Thread社区的下属子社区,旨在兼容Arduino社区生态(如上千种分门别类的Arduino库,以及Arduino社区优秀的开源项目),来丰富RT-Thread社区软件包生态,并降低RT-Thread操作系统以及与RT-Thread适配的芯片的学习门槛。可以让用户通过Arduino的函数和编程方法,轻松地将RT-Thread以及特定的芯片使用起来。用户也可以直接使用Arduino社区的库(例如I2C传感器驱动库、算法库等)直接用在RT-Thread工程中,极大地补充了RT-Thread社区生态。该项目由RT-Thread社区核心开发和维护者满鉴霆发起。本软件包可以运行在RT-Thread Studio IDE和Keil编译环境下,因为Arduino的库都是基于GCC环境开发的,因此强烈推荐使用RT-Thread Studio IDE运行。1.1 已经支持Arduino生态兼容层的RT-Thread BSP
BSP名称
备注

, E6 a! ?" W  j7 W
STM32L475潘多拉
引脚异构布局,但外设丰富
' X/ [3 k* I+ U9 g! ?0 R
STM32F072 Nucleo
标准Arduino UNO引脚布局
! i; T9 Z( z. n
STM32F401 Nucleo
标准Arduino UNO引脚布局

0 O6 A( D! U4 [* V/ ?( y% E
STM32F469 Discovery
标准Arduino UNO引脚布局
. d7 @( }3 ~6 d0 b7 ]2 _
STM32F103 BluePill
引脚异构布局
& t( N0 m6 i$ E, ~$ i4 _; t" g
ES32F3696
引脚异构布局
注:RTduino也可以无需适配特定BSP,直接运行在任意RT-Thread BSP上,请参考第5章-RTduino精简模式。
2 如何使用本兼容层本软件包需要对特定的BSP进行适配之后才可以使用,适配方法很简单请参考。本节以STM32L475潘多拉开发板和RT-Studio开发环境为例,来讲解如何使用本兼容层。2.1 参考资料
  • 2022年RT-Thread全球开发者大会报告视频
    # q5 J. |2 X3 \2 _- m2 Z/ W
2.2 工程的创建和导入请到RT-Thread Github官方仓库,下载最新的源码。对于部分用户下载Github源码慢的问题,可以百度或者到B站搜索“Github加速”等关键字来解决,此处不再赘述。
640?wx_fmt=png.jpg
下载好之后请解压,打开RT-Studio IDE,选择文件(File) -> 导入(Import),并选择RT-Thread BSP Project into Workspace,也就是将BSP工程导入到Studio的选项。. v  Y2 t0 z) f6 l
640?wx_fmt=png.jpg
640?wx_fmt=png.jpg
路径选择,你刚刚下载解压好的RT-Thread源码,以STM32L475潘多拉板为例:rt-thread\bsp\stm32\stm32l475-atk-pandora。工程名字随便起一个就好,比如STM32
640?wx_fmt=png.jpg
点击完成(Finish),稍等片刻即可完成工程导入。
导入成功之后,双击RT-Thread Settings,进入到RT-Thread工程配置界面,点击<<按钮,进入到详细配置页面:
640?wx_fmt=png.jpg

5 [, K; M: L+ x  P: l' B2 h9 Q( o
640?wx_fmt=png.jpg

! }! Z( y# C2 c
点击Hardware,选择Support Arduino,只需要点一下即可,其他依赖项会自动处理。然后点击小锤子按钮进行编译,RT-Thread Studio会自动保存你当前的配置并下载RTduino软件包以及依赖项软件包,并将这些软件包加入到工程中,最后自动编译整个工程。
总的来讲,你只需要选择Support Arduino,并点一下小锤子按钮,就坐等编译成功即可。
640?wx_fmt=png.jpg
至此,RTduino软件包安装完成,此BSP工程已经具备了兼容Arduino生态的能力。
2.3 RTduino文件夹目录结构
RTduino软件包包含有两个主要的文件夹:core和libraries。
  • core文件夹主要是提供Arduino内置的所有的API函数,例如analogWrite、analogRead函数等等,这些函数可以在Arduino官方找到详细的介绍。
  • libraries文件夹是Arduino库所在文件夹。其中:
  • buildin文件夹下存放着Arduino内置的一些库,例如Servo舵机驱动库,Wire I2C驱动库等等;
  • user文件夹是用户文件夹,这是对用户来说很重要的一个文件夹,里边默认是空的,用户可以把下载好的Arduino库拖入到此文件夹中来,在下个章节会细说这个操作。
    $ V: W+ U- |  E# e, n- H& S7 D
2.4 Arduino经典的setup和loop函数在哪里?对于Arduino,最经典的莫过于setup和loop函数。这两个函数位于BSP目录下的applications文件夹内arduino_main.cpp文件中。以潘多拉板为例,这两个函数位于:bsp/stm32/stm32l475-atk-pandora/applications/arduino_main.cpp文件中,在开启RTduino软件包后,你可以直接在工程的Applications组中找到它。2.5 点一个LED灯吧! 1#include <Arduino.h>
$ y" [. I# P* V) m% \; s 2
4 t! B5 D, h7 [* p( m# U4 \ 3void setup(void)* o( A1 X! W$ d% C+ m% L
4
{
- \/ \- C: z2 u6 c( ^8 n$ H  g 5    // put your setup code here, to run once:
+ b% B0 X  F6 E# y8 p4 s- G 6    pinMode(LED_BUILTIN, OUTPUT);
4 }; |5 z0 b2 R' k5 D2 ] 7}
: D5 S' z  E6 D5 ]2 N; L 8! l+ F! @( _5 Q1 G7 A* g
9void loop(void)1 b# \! v' [# C* L
10
{4 x) W% b  f- n4 c/ c( z2 P
11    // put your main code here, to run repeatedly:9 h( [# n* Z2 d3 I+ F6 U
12    digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
4 h3 }, G' s* X; E9 w13    Serial.println("Hello Arduino!");
5 Q& n6 K* q. r* k- }* N' |& m14    delay(100);
- b% J7 I  U+ a7 v( R2 q9 v; ~15}
8 t# q9 S* M: f
可以看到,板载的LED灯已经开始闪烁,串口开始输出了。
注意:
+ F3 q7 A& o. ?* X5 h! _4 D$ N
由于RT-Thread的main.c文件内,也会默认闪烁一个LED灯,如果板子上只有一个LED灯的话,两个线程会发生干涉。但是你会发现这个LED的闪烁速度明显变快了。因为main.c那边的闪烁周期是1000ms,上面这个例程是200ms。

. n" |% t- P$ `4 [. c+ H8 M" n
如果你用潘多拉板,main.c闪烁的是红灯,RTduino兼容层的Arduino程序默认闪烁的是绿色的灯,二者不会发生干扰。
2.6 具体Arduino引脚分布信息
由于每个BSP的板子设计、以及芯片型号等,引脚分布是有区别的,因此需要到指定BSP的applications/arduino文件夹下的README.md文件查看详细信息。例如:
STM32L475潘多拉板的Arduino引脚布局的详细说明 | STM32F072 Nucleo板的Arduino引脚布局的详细说明
3 Arduino库的导入和使用3.1 术语说明
软件包:英文为 software package,是指RT-Thread社区所属维护的第三方扩展,是RT-Thread原生生态一部分。
库:英文为library,是指Arduino社区所属维护的第三方扩展,是Arduino原生生态一部分。
库和软件包其实是一个意思,只不过两个社区叫法不一样。
3.2 RTduino兼容层对Arduino库的兼容情况
目前RTduino兼容层可以实现对Arduino纯软件类(例如算法类、数据处理类等)、串口相关、I2C传感器相关的库做到100%兼容。
支持的详细情况和计划,请查看:
https://github.com/RTduino/RTduino/discussions/26
3.3 导入一个Arduino库到RT-Thread工程(以潘多拉板为例)首先,你需要到Arduino官方的软件包分类中心去查找你想要的库,或者直接在Github上搜索你想要的库,一般都是C++类型的。比如,我想要一个驱动AHT10温湿度传感器的库,可以在此处下载。此处以潘多拉板为例,因为潘多拉板板载了AHT10传感器。下载好之后,直接将zip压缩包拖进RTduino文件夹下的libraries\user这个目录下即可。选择当前工程右键选择Sync Sconscript to project也就是让RT-Studio重新扫描并组织一遍工程目录,在扫描的过程中,RT-Studio会自动将zip压缩包解压,并按照Arduino IDE的文件添加逻辑(也就是忽略examples文件夹,并将其他文件夹的.c文件和.h路径添加到工程),将Arduino库添加到RT-Thread工程中来。然后再点一下小锤子按钮来重新编译一下工程。
# [8 j: b) U, W: a3 O! N( q( w
640?wx_fmt=png.jpg

9 x6 E+ A9 F1 m$ d2 Z工程编译通过之后,你可以将这个AHT10 Arduino库的例程(位于该库文件夹下的examples文件夹)直接复制到arduino_main.cpp文件下运行,你可以看到,串口会输出当前的温湿度,Arduino的例程是直接可以在RT-Thread上运行起来的。3.4 RTduino内置库
在RTduino中内置了两类库,方便用户直接使用。
一类是在Arduino中原生内建(buildin)的库,存放于 libraries/buildin 文件夹内。具体如下表所示:
640?wx_fmt=png.jpg 4 如何给某个BSP适配RTduino4.1 创建文件夹和文件
需要在某个BSP的applications文件夹下创建如下文件、文件夹:
参考示例BSP:STM32F072 Nucleo板applications文件夹 | STM32L475 潘多拉板applications文件夹
4.1.1 arduino_main.cpp文件
该文件是Arduino的编程入口,提供setup和loop函数。在loop函数默认以200ms为周期,闪烁Arduino内建LED灯(LED_BUILTIN)。如果该BSP默认支持SPI功能且为UNO引脚布局,由于SPI和LED_BUILTIN可能存在冲突(D13),可以在loop函数内以 Serial.println("Hello Arduino\n"); 代替频闪LED(例如STM32F401 Nucleo板)。
4.1.2 arduino_pinout文件夹
需要在applications文件夹下创建arduino_pinout文件夹,这个文件夹主要包含 arduino_pinout.c 和 arduino_pinout.h 两个关键的文件,这两个文件是对接的关键。用户只需要做好这两个文件,即可完成与RTduino的对接。
同时,这个文件夹内也需要SConscript脚本文件,以及提供Arduino引脚布局的README说明文档。请参照上面的示例BSP来完成对这两个文件的编写。
4.1.3 arduino_pinout.c 文件的编写
arduino_pinout.c 内需要完成一个IO编号和功能的映射表。由于Arduino的习惯是采用1-13 (D0-D13) 以及 A0-A5的引脚编号,而正规的MCU的引脚编号一般都是PA1之类,因此需要将MCU真正的引脚编号与Arduino引脚编号映射起来。
以下段代码来举例讲解:
1/*1 b# J# S9 [3 h
2    {Arduino Pin, RT-Thread Pin [, Device Name(PWM or ADC), Channel]}
0 c; i& m; w- h 3    [] means optional
* n0 ]* Y7 R2 s- s4 T2 r* \7 ~2 u; H: F 4    Digital pins must NOT give the device name and channel.
7 X" V& E; X+ Y  C# B- `$ r 5    Analog pins MUST give the device name and channel(ADC, PWM or DAC).* d% A0 \0 z1 E
6    Arduino Pin must keep in sequence.
/ {' O. Y5 O! _9 I 7*/

4 F0 [8 [. x# B8 o  I6 b 8/* 按照先数字引脚后模拟引脚的顺序从0开始,一定要按序排列 */
* h! `( F4 q7 E# H 9/* 可以按照板卡实际IO情况,灵活调整功能,不一定非得按照Arduino UNO的引脚功能布局,但是建议按此布局设计 */' K% S8 H2 j1 _8 M& G/ n* C- h
10const pin_map_t pin_map_table[]=
4 }+ r1 R5 X6 u2 P: L11{) B, j" o4 }! O- P- r( ~
12    {D0}, /* RX */4 t: h8 u; c& O2 \- `3 x
13    {D1}, /* TX */
3 k; V) D* G; p3 M14    {D2, GET_PIN(A,10)},
8 h. P2 h3 Z6 Q. g3 M$ W3 m0 M15    {D3, GET_PIN(B,3), "pwm2", 2}, /* PWM */
1 Z% j% C) o  _, }, f16    {D4, GET_PIN(B,5)},! K4 {+ V( d* o$ r8 B# b+ d; P& \
17    {D5, GET_PIN(B,4), "pwm3", 1}, /* PWM */
7 c5 q7 x- R6 l7 v18    {D6, GET_PIN(B,10), "pwm2", 3}, /* PWM */
8 |; T" B3 [3 v19    {D7, GET_PIN(A,8)},
: {  n7 p/ Z! T; D0 P% R$ ^20    {D8, GET_PIN(A,9)},4 y1 u5 D: f  y8 U
21    {D9, GET_PIN(C,7), "pwm3", 2}, /* PWM */
( O/ A2 F1 B& Q. h4 E& t/ K. K9 C22    {D10, GET_PIN(B,6), "pwm16", 1}, /* PWM */" i7 r- r4 B4 j) c" X" h
23    {D11, GET_PIN(A,7), "pwm17", 1}, /* PWM */2 _& S8 q9 E' O) s0 |/ L4 F8 S
24    {D12, GET_PIN(A,6)},. B8 J. y  t. `) }" j% x: g+ _  L( E
25    {D13, GET_PIN(A,5)},
4 T. |0 W' U1 f: Y8 p) T26    {D14}, /* I2C1-SDA */
/ k: e  D, f( s! u- V$ Q27    {D15}, /* I2C1-SCL */
/ [& }" H2 h) d6 Z" R; Q+ `% Q" e3 P5 |28    {D16, GET_PIN(C,13)}, /* user button */& d" w9 q' u8 [2 m6 c" l5 k/ \& ^9 p
29    {A0, GET_PIN(A,0), "adc1", 0}, /* ADC */
: L& t8 R2 S/ m2 k' {2 p30    {A1, GET_PIN(A,1), "adc1", 1}, /* ADC */" |# j" y; ?: c3 n% G/ ?" [
31    {A2, GET_PIN(A,4), "adc1", 4}, /* ADC */# A7 J7 _. o+ a# B& K7 X# \& k
32    {A3, GET_PIN(B,0), "adc1", 8}, /* ADC */
. Z9 m6 \% ?% ^9 I! t* n- b, ]2 w33    {A4, GET_PIN(C,1), "adc1", 11}, /* ADC */
; B0 w# t6 P0 b34    {A5, GET_PIN(C,0), "adc1", 10}, /* ADC */8 h* e$ V- U( U! F: ^
35}
( @: T) k6 L$ c8 R/ D6 h6 F
如上截取展示了IO编号和功能映射表,每一行用花括号包裹(实际是一个结构体)来建议一个IO的映射关系:
1{Arduino引脚编号, RT-Thread引脚编号(通过GET_PIN宏获取), 复用功能的设备名(PWM、ADC或DAC), 该复用功能设备的通道号}! O5 G% I0 j4 \9 }8 X2 X- u
其中,Arduino引脚编号,即是第一个参数,是必填的,D0 - Dx 或者是 A0 - Ax。注意一定要按先数字引脚后模拟引脚照顺序来填写。
RT-Thread引脚编号,即第二个参数,rt_pin_write中引脚编号填什么,这里就填什么,一般使用 GET_PIN 宏来获取。注意:D0、D1以及I2C、SPI IO需要将此参数略过。
后两个参数是复用功能IO才需要填写的,普通引脚只需要略过即可。
4.1.4 arduino_pinout.h 文件的编写
参考示例BSP:STM32L475 潘多拉板applications文件夹
该文件主要负责定义各种宏,包括:
D0、A0等引脚的数字宏,该宏一定要按照先数字引脚后模拟引脚的顺序进行排号。
定义默认开启的一些硬件功能,如下表所示:
1/* pins alias. Must keep in sequence */1 N. ~* x& y4 E7 Q% {+ Q: l: C/ T
2/* 按照先数字引脚后模拟引脚的顺序从0开始,一定要按序排列 */: h/ a0 x0 r" g; O9 g) l
3/* 可以按照板卡实际IO情况,灵活调整功能,不一定非得按照Arduino UNO的引脚功能布局,但是建议按此布局设计 */
( c. ?4 x$ N/ ~5 l& G* ?: t, B 4#define D0   (0)3 n3 a2 c( |  V
5#define D1   (1)
6 G# K9 H: m2 Q( u 6#define D2   (2)2 A) D: H# Y) m# g5 \  y3 S/ `5 w
7#define D3   (3)
% p+ g( p; E! h 8#define D4   (4)4 Y1 o8 v- J# W
9#define D5   (5)
" b8 f1 d& D, S- @) b0 i2 ~+ j10#define D6   (6)
* L$ k1 [' n3 J; Q! V. M% i: d11#define D7   (7)
# P: P) ~$ x5 R* K' d; X$ M8 Y12#define D8   (8)( ]  I( U5 m1 e
13#define D9   (9)" H" y) [3 Z3 c' m# j8 ?' _
14#define D10  (10)
8 A0 ~" W& ?: a7 i9 d. I15#define D11  (11)" L; U  Q/ _( q  H
16#define D12  (12)7 U  [. l9 D' V/ M
17#define D13  (13)
) Y! [" k7 n1 @$ r8 ^, d! f18#define D14  (14)* O/ `5 m4 h* D. L! g
19#define D15  (15)
0 K: w! f( ~9 m; }3 E20#define D16  (16)" S+ B  ~" Y; [/ h& ]
21#define D17  (17)6 K" I; L9 v5 c5 G9 e+ R
22#define D18  (18)- s# s3 C+ s: ?. y
23#define D19  (19)
% A4 o5 ~$ w9 K! @% ?% {- r24#define D20  (20)# j- W& G# _0 ]7 b5 M
25#define D21  (21)
2 `& A: ?6 a! l3 [$ H26#define D22  (22)
5 [( x% r& _0 f, K6 Z27#define D23  (23)+ }# m% }5 Y2 u- R
28#define D24  (24)
  I( o* d8 M$ {! w; s; K) k29#define D25  (25)( j8 y6 j" V0 N/ o1 _9 K/ W/ G
30#define D26  (26)
- b/ e! ~' R/ o0 m7 y& o31#define D27  (27)
) ]( q6 e* O* X. J/ L32#define D28  (28)0 a! Y1 U" D. U( y9 Y
33#define D29  (29)+ d$ j3 ?  ?5 k+ S5 L/ p4 \; I6 v
34#define D30  (30)
# @* O6 o2 U+ N' A" g35#define D31  (31)
9 W- I7 O' I  j2 M3 N2 _3 B! N36#define D32  (32)8 {5 Z. k7 Z% ~, F8 \, |
37#define A0   (33)
+ C. T: t7 Z& S( A# b38#define A1   (34)) k9 T" D5 b( e! M4 @/ Z  c# {- }
39#define A2   (35)
% e/ |3 c; p6 B' u& D* o40#define A3   (36)
3 `( k9 N( @; a+ a' }/ B5 H2 `41#define DAC0 (37)
. B7 M/ ]7 K/ E, ^42" k, O. A0 c8 C  j9 K5 R
43#define F_CPU  80000000L /* CPU: 80MHz,定义CPU的主频 */
7 C) q5 n# G. D, D2 _8 d" Q44#define LED_BUILTIN  D22 /* Default Built-in LED,定义Arduino内置LED的引脚编号 */- I( u4 N/ T5 t
45( q. q- R7 {- C- W2 F
46/* 定义I2C设备名称,在使用Wire库时会直接调用。可选,如果没有I2C功能,不需要定义该宏 */4 P' o6 f; U# ]+ u; ?% `
47#define RTDUINO_DEFAULT_IIC_BUS_NAME            "i2c4"
0 @* n; H  b/ u- u48
; O6 h' J: p* V3 B( e( E49/* 定义SPI设备名称,在使用SPI库时会直接调用。可选,如果没有SPI功能,不需要定义该宏 */- `* b  h6 e! f% C% O: E# e; _2 h
50#define RTDUINO_DEFAULT_SPI_BUS_NAME            "spi2"
. x' @8 t, `3 ]9 f' m51
8 T) N- I% \; B+ i9 Z# ^52/* ( Y1 s. r# y0 ?# P
53   定义高精度定时器设备名称,该宏主要是提供us时基信号使用。+ M* d$ y9 D; T* W) d3 t# }
54   所有Cortex-M核MCU均不需要定义此宏,RTduino会自动调用systick来计算us级时间戳。
+ d: p, t  @+ V; [, }55   非Cortex-M核的MCU需要提供一个硬件定时器来提供us级时间戳。( X4 `6 u& G- ^. D
56 */
3 E/ ~8 Z! Z: {
57#define RTDUINO_DEFAULT_HWTIMER_DEVICE_NAME     "timer7"
7 L4 X8 v! A. s58
1 ?; B+ Z; X: T# R: u% d0 E4 N59/* 如果有串口2、串口3可以定义串口2、3的设备名称,若没有可直接不定义此宏 */
" H7 f& o6 |1 M60#define RTDUINO_SERIAL2_DEVICE_NAME             "uart2"* v# Z2 d1 r) G3 J6 c
4.2 修改Kconfig文件
Kconfig文件位于BSP的board文件夹下:
参考示例BSP:
STM32F072 Nucleo板Kconfig | STM32L475 潘多拉板Kconfig
1menu "Onboard Peripheral Drivers"
0 q; R( \. _( ]  T5 | 2    config BSP_USING_STLINK_TO_USART
! T; R7 u2 b# l/ w3 S# _ 3        bool "Enable STLINK TO USART (uart2)"
! w% @# W& r. J& H 4        select BSP_USING_UART6 m. n7 Y0 u& P5 r2 o
5        select BSP_USING_UART2
- `( H, E. h- s6 E1 ` 6        default y) Y- m: r: n; I, @8 s# P* _
7; r/ }9 V, f1 F+ j2 x6 R! ?
8    #增加 BSP_USING_ARDUINO 配置选项
* C; s& U* w- A. ~ 9    config BSP_USING_ARDUINO
* ^8 {  M% R2 _, S9 W- y( e8 Z) N10        bool "Support Arduino"
; T- a6 F4 z) i5 _( ?) A9 ~11        select PKG_USING_RTDUINO2 I0 w( [& L  k$ B  H6 l# Y
12        select BSP_USING_STLINK_TO_USART
  D) Y# g! ]  k% b" C13        select BSP_USING_GPIO/ P. I5 q) n; y
14        select BSP_USING_ADC7 Y' K4 N4 J! w9 S8 y% b. O
15        select BSP_USING_ADC1/ P; G. E, |& E! ?- d$ p" U7 E
16        select BSP_USING_PWM
% R% @. L  y, o8 d& c( }0 ]$ Z17        select BSP_USING_PWM2/ i6 s' ]* B) L, I" T5 L
18        select BSP_USING_PWM2_CH2
5 h% T7 N' _6 p2 Q2 ]" U: K# c19        select BSP_USING_PWM2_CH3
0 Q( N7 h1 S/ j20        select BSP_USING_PWM3! g$ v. i4 u/ f1 K6 l8 D1 w+ a
21        select BSP_USING_PWM3_CH1
0 c, u. ?5 y; Q' K# e& L2 ]% `/ M& S22        select BSP_USING_PWM3_CH2. w1 s) I: C, K: _  u
23        select BSP_USING_PWM16/ L2 o' s$ o8 }1 |7 O
24        select BSP_USING_PWM16_CH13 o3 c$ \' i& X9 Y3 U2 z( s; @) R' G9 Z
25        select BSP_USING_PWM17
' |+ |  R7 `; t! A26        select BSP_USING_PWM17_CH1$ J+ H: ?; J* s0 l9 H/ b
27        select BSP_USING_I2C
( e& W1 @+ e* ~9 O/ A3 l28        select BSP_USING_I2C1
1 S/ \- H1 T3 }# h( r29        imply RTDUINO_USING_SERVO
2 A: P) l  R. r3 a30        imply RTDUINO_USING_WIRE5 q; {# |7 @. v2 z2 A& G
31        imply RTDUINO_USING_ADAFRUIT* ?( x6 q; ~5 c5 P! o  l/ X
32        default n9 x- h2 h$ G0 W0 Q; Y+ }
338 v& k* v* t$ S. P) V8 h. U5 h! m
34endmenu8 |* W2 d8 W/ r* e6 u9 \7 @2 N
需要在Onboard Peripheral Drivers栏下增加 BSP_USING_ARDUINO 配置选项,并依赖相应的PWM、ADC、UART、I2C以及SPI等设备框架,满足一键化开启RTduino的能力。4.3 编写Arduino引脚布局(pinout)的README说明文档示例:STM32F072 Nucleo的Arduino引脚布局说明文档 | STM32L475潘多拉的Arduino引脚布局说明文档该文档需位于applications/arduino_pinout/README.md,主要介绍该BSP下的Arduino引脚编号和引脚功能,以及注意事项等。5 RTduino精简模式(快速使用,无需适配特定BSP)5.1 不使用setup-loop编程模型setup()loop() 函数是Arduino编程中非常经典的函数,当你在Arduino IDE中新建一个文件时,默认就提供了这两个函数。这两个函数RTduino是完全支持的(参见第4章),但是一些较为复杂或庞大的业务逻辑如果放在setup-loop函数中就会受到一些束缚。因此,可以在Env或者RT-Thread Studio的RT-Thread Settings中取消setup-loop编程模型:1RT-Thread online packages  --->
& x+ M# l8 h7 J5 z+ b1 @- ?2    system packages  --->0 f) ^+ z6 G' x$ `2 w
3         
  • RTduino: Arduino Ecological Compatibility Layer  --->
    1 J1 l" Y( v# O  K* ]& }4              
  •    Don't use setup-loop structure  --->! }) f" g" \$ A5 t1 J* i
    选择此选项后,用户可以直接在 core/arduino_thread.c 中的 arduino_entry 线程函数中直接编程,或者在任意.cpp文件中调用Arduino API(不局限于Arduino线程,只要是.cpp文件下调用即可)。5.2 如何不用定义引脚映射表,更方便的使用RTduino?通过上文,我们可以看到,RTduino软件包并不是直接可以用的,需要RT-Thread BSP方面提供一些配套的支持,如引脚映射表(arduino_pinout)等。但是,如果用户不想使用Arduino引脚(IO)相关的API(如analogRead等),只想借助RTduino软件包,来直接兼容运行I2C芯片驱动库、纯软件算法库等和IO无关的函数和库,如何快速的使用起来呢?用户可以直接在Env或者RT-Thread Studio的RT-Thread Settings中选择精简模式 (Enable tiny mode)。在选择精简模式后,用户就无需定义引脚映射表,直接就可以使用Arduino库中的非IO相关的函数和库了。开启精简模式后,会自动开启 5.1 章节所介绍的不使用setup-loop编程模型选项,用户可以在任意.cpp文件下使用Arduino API。1RT-Thread online packages  --->. R2 z9 [/ S8 ]2 X* ~+ l5 H
    2    system packages  --->
    9 k/ {! U; [6 ]6 ]* ^3 P3         
  • RTduino: Arduino Ecological Compatibility Layer  --->
    ) y$ y' W8 o: l! n4 C% k4              -*-   Don't use setup-loop structure
    " o' M& v: |2 K1 f. W5              
  •    Enable tiny mode  --->
    " z6 i. ], M  E- j; U5.3 常规模式(参见第4章)vs 精简模式(参见第5章)
    下表列举了在两种不同模式下,RTduino对Arduino API的兼容情况:
    640?wx_fmt=png.jpg
    640?wx_fmt=png.jpg
    640?wx_fmt=png.jpg
    640?wx_fmt=png.jpg
    640?wx_fmt=png.jpg
    注:SPI库目前还在施工中,暂不开放使用。
    6 需要注意的事项6.1 包含Arduino.h头文件
    调用到Arduino相关函数和宏的源文件,请包含Arduino.h头文件,否则可能会报错:
    640?wx_fmt=png.jpg
    5 }' x+ {4 i" F/ z2 n
    640?wx_fmt=png.jpg
    6.2 Keil AC5
    如果使用Keil AC5环境,需要勾选GNU extension。AC6不需要。
    6.3 启用PWM不能调用pinMode函数,否则PWM会失效,ADC、DAC同理 1void setup() {* J6 d0 z- ]2 D5 ^) J
    2  //Declaring LED pin as output4 |  V% q5 r. B. i4 N' M- Q9 p
    3  //pinMode(led_pin, OUTPUT); //不能设置为OUTPUT,否则PWM会失效
    " [7 M" ^: R8 _8 Q( R 4}
    ; T  l. x- V1 h& |3 }4 Y 5void loop() {9 l  j1 ~; x  E( ^
    6  //Fading the LED
    + W' H# \% b/ z% S* T 7  for(int i=0; i<255; i++){2 l% @+ B, i; p1 U! B6 [2 v1 W( c9 Q
    8    analogWrite(led_pin, i);
    8 q2 w! n' G' Q8 s1 k7 ] 9    delay(5);6 m* S9 A$ z. \4 ^  K' ]) V, C
    10  }/ e7 |6 ], V8 S( |: L9 Z  e
    11  for(int i=255; i>0; i--){! E" y$ p( q/ u; F! }4 S. A0 z
    12    analogWrite(led_pin, i);
    & l: j! q; l# c5 m13    delay(5);& M, K* [+ O# j+ A
    14  }
      A% b% V1 A8 n/ N15}; c2 K- j2 V& d
    因为底层已经将对应的PWM、ADC或DAC的IO设置为模拟输入或者复用推挽,调用pinMode之后把IO模式改成了纯输入输出,原有的PWM、ADC或DAC功能将无法使用。该问题无要修正,只需要知道调用analogRead和analogWrite的时候不需要设置pinMode即可。一旦调用pinMode,该引脚将丧失analogWrite或者analogRead功能,后续只能当做普通IO使用。
    Arduino 官方文档也是这么建议的:
    1You do not need to call pinMode() to set the pin as an output before calling analogWrite().
    2 R8 j4 [0 P( v4 Y" Y; T5 Y2The analogWrite function has nothing to do with the analog pins or the analogRead function.
    & W9 h" b+ f) u* \; W+ J
    用户如果对PWM、ADC或DAC引脚使用pinMode函数,在终端也会给出警告:
    640?wx_fmt=png.jpg
    当然,如果用户已经知道这样做的后果,但是故意需要将PWM、ADC或DAC引脚通过pinMode函数转为普通IO也是完全可以的。
    6.4 Serial.begin
    在很多Arduino例程中,都喜欢使用如下语句来初始化串口:
    1  Serial.begin(9600);
    4 c+ ]% w! L( y5 B) N( J# O. Z6 L& n
    这句话将串口默认初始化成波特率为9600. 但是在RT-Thread中,串口的初始化实际是有RT-Thread驱动框架负责的,并且默认波特率为115200. 因此如果调用Serial.begin(9600) 函数后,串口的波特率将会从默认的115200调整为9600。如果你的终端或者串口助手还保持在115200的波特率,那么接收数据将出现乱码。
    因此建议:
    使用Serial.begin()代替Serial.begin(9600)。Serial.begin()无参数方法是RTduino的扩充方法,其表示跟随使用RT-Thread串口配置,不重新配置串口。
    7 贡献与维护7.1 项目仓库地址
    https://github.com/RTduino/RTduino
    https://gitee.com/rtduino/RTduino
    如果喜欢请Star,这是对本开源项目最大的鼓励,谢谢;如果想要贡献PR,请fork7.2 感谢以下小伙伴对本仓库的贡献
    640?wx_fmt=png.jpg
    查看全部名单请上GitHub
    2 z2 X+ N; t9 m

    ' M2 }8 I4 [! _% W4 Y
    7 X1 f! N; ]+ S0 x4 J" i- h
    END

    / z; P: R5 e* I9 w
    8 F' S' C7 N; ?0 b) T+ g2 }
    640?wx_fmt=jpeg.jpg
    . _2 |$ H; z+ a" [  J. B

    " e2 V$ ^) L. v* V- \
  • 回复

    使用道具 举报

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

    本版积分规则

    QQ|Archiver|手机版|深圳市光明谷科技有限公司|光明谷商城|Sunshine Silicon Corpporation ( 粤ICP备14060730号|Sitemap

    GMT+8, 2024-3-29 20:29 , Processed in 0.124524 second(s), 37 queries .

    Powered by Discuz! X3.2 Licensed

    © 2001-2013 Comsenz Inc.

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