|
拿到开发板有一段时间,看了下资料,使用mbed平台那简直是太简单了,但mbed封装的太严实,实在是不利于我们了解MCU内部运作机理,所以还是要使用ST的库(直接寄存器操作就免了,我不想回到石器时代),现在ST库除了F1系列已经改变,采用新的HAL Drivers的方式,这种方式更友好,更符合软件工程。使用STM32CubeMX把和MCU相关的代码已经生成的90%了,剩下和10%需要自己来完成,所有的中断基本上采用“伪回调”的方式,使用用户更专注于业务算法本身。废话不多说了,直接上代码:; A0 u) ?, ~ I4 l- B -------------------------------------------------------------------------------传说中的分界线----------------------------------------------------------------------------8 n A( i1 j8 p! z; w main.c2 N/ X8 L- b; U$ q( ] #include "stm32l0xx_hal.h"2 F/ g# D' L+ p6 } #include "dma.h" #include "i2c.h" #include "tim.h" #include "usart.h"& I* p/ Q7 e! N" o- P #include "gpio.h" #include "mpu6050.h"! t8 V( N, k3 Z p6 u! T) G( u #include "visualscope.h"" I4 S9 n% O- W) s6 d2 j" u 0 ]/ w. H: }4 X( x3 f6 X7 ?* B( C #include <string.h>, N# Y4 d4 A2 G; U. M$ L #include <math.h># R9 t' R" r6 t3 {0 x /* Private variables ---------------------------------------------------------*/ #define RXSIZE 89 {" H1 R/ x$ R# J; V$ f1 | #define TXSIZE 8 uint8_t rxBuffer[RXSIZE]; uint8_t txBuffer[TXSIZE];8 _* \+ ?. E' Z1 u! Z9 k+ J float Angle_accel = 0;5 I( W4 Z( S3 m% t! A float Angle_gyro = 0; float Angle_comp = 0;) h) f. `+ Y0 w* }- O uint8_t outAngleData[10]; /* USER CODE BEGIN 0 */ 4 k. x I7 _5 i A* j /*---------------------------------------------------------------------------------------------------------*/) v0 g) h! ^# Q# F$ e) z1 _9 | /* 重力加速度算出的角度 */# N/ j# d7 X5 Z /*---------------------------------------------------------------------------------------------------------*/; K* s: v& i. @1 X8 t: E. R8 Q' i int32_t Calc_AngleAccel()$ e( l) n) k' t( ~+ @3 n$ k { int32_t value = 0;3 `/ I1 N' k" \# s : ^' s% v0 x( A9 G X7 S value = GetAccelValue('x'); if(value > 16384)' K3 U/ t) e3 G Angle_accel = -(asin(1) * 180 / 3.1415296);& C" p2 s9 r. s# c else Angle_accel = -(asin(value * 1.0 / 16384) * 180 / 3.1415296);5 F$ b5 h! i2 E. X4 W ; Z2 H4 y) W: F# p1 o& W return value; } /*---------------------------------------------------------------------------------------------------------*/ /* 角速度算出来的角度(积分) */ /*---------------------------------------------------------------------------------------------------------*// @. ]7 q- X' y4 f0 m. N& a int32_t Calc_AngleGyro() {5 S; q5 F% D6 }: ? int32_t value = 0;, v0 g, O- d6 B P7 {. }7 g: f value = GetGyroValue('y');; W, X) k; _9 G C Angle_gyro += (value / 16.384 * 0.01); return value;# Y0 P1 h' S# |9 n% p7 j- k( \' X X } /*---------------------------------------------------------------------------------------------------------*/ /* 互补滤波求角度 */! S6 c+ {6 ]3 f. l* F5 _: K4 k /*---------------------------------------------------------------------------------------------------------*/$ Z3 S; S8 g+ c. g9 s: X float ComplementFilter(int32_t simpleGyro)8 B8 f9 W! n- f7 g5 ] { Angle_comp = 0.98 * (Angle_comp + -simpleGyro / 16.384 * 0.01) + 0.02 * Angle_accel; return Angle_comp; }: e! m# D" s$ m" F9 V, h" \" [ / W: c. U3 f8 v4 U- d' K /*---------------------------------------------------------------------------------------------------------*/ /* 输出角度至上位机 */- _2 i' Z$ B+ x! F8 ^3 U# k /*---------------------------------------------------------------------------------------------------------*/ void VisualScopeAngleOutput()* i' ?% ~4 x4 `: v2 ^; Q {2 i. E% |( F: O; o( H int AngleValue_Accel,AngleValue_Gyro,AngleValue_Comp;$ ~% t2 l) a3 N% D7 A6 F3 V/ } uint16_t crcValue; " X' A0 U$ `/ ~# a AngleValue_Accel = ceil(Angle_accel * 10 -0.5); AngleValue_Gyro = ceil(Angle_gyro * 10 - 0.5);; {1 t% O7 E* Y2 U( h& z" ]) D1 b- C6 x5 w AngleValue_Comp = ceil(Angle_comp * 10 - 0.5); 0 f7 F/ m' F+ }1 C0 Z& ~ outAngleData[0] = AngleValue_Accel & 0xFF;; \- g% d3 s5 D) h' b) B outAngleData[1] = AngleValue_Accel >> 8;8 d) n+ J5 p5 c3 j outAngleData[2] = AngleValue_Gyro & 0xFF;% o: p% f* u+ u6 d. ]+ b4 p& C! M outAngleData[3] = AngleValue_Gyro >> 8; outAngleData[4] = AngleValue_Comp & 0xFF;- v' ]. t% s' H' B# P" W' p# K3 U0 L outAngleData[5] = AngleValue_Comp >> 8; //计算CRC crcValue = CRC_CHECK(outAngleData,8);; T, s# x0 ?* I9 W outAngleData[8] = crcValue & 0xFF;8 c& ]1 p8 u ?) n5 ] outAngleData[9] = crcValue >> 8; //发送至上位机& a7 }' W" v% Q$ v% {! \$ o HAL_UART_Transmit_DMA(&huart2,outAngleData,sizeof(outAngleData)); } /* USER CODE END 0 */2 Z* C1 d$ l* ^7 n /* Private function prototypes -----------------------------------------------*/5 Z: m; [- B: X& P s4 z& c+ R void SystemClock_Config(void); 4 L7 C' ^2 \( }2 [3 z 硬件连接图:: ~6 G) R* _1 v% ], S' R/ _
波形图:, ~& S; R* f6 a1 Y) e& g6 ~; s
最后加一个视频: STM32L053 演示 |
STM32MP1 自举程序编程:USB DFU/USART 协议全解析
STM32大神笔记,超详细单片机学习汇总资料
实战经验 | 如何配置STM32MP257的RMII Switch
简单实用!STM32硬件错误的调试技巧
OpenSTLinux 6.1发布:M33-TD加持+安全升级,STM32MPU开发效率翻倍!
STM32MP135 MP157 MP257 CoreMark移植&&跑分对比&&多核心负载不均衡问题排查与解决
STM32系列芯片之间相互移植注意事项
STM32如何成为现代科技的隐形引擎
STM32--STM32 微控制器详解
大神都是怎么学习STM32的,我也跟着学
微信公众号
手机版
#include "i2c.h"
#include "gpio.h"
/* USER CODE BEGIN 0 */" V3 C) r' B0 K. t0 Z; X4 x& p
- s" l7 D e9 m4 v# a4 n
/* USER CODE END 0 */8 ^6 m7 e, \; m1 I: Q, \% Y
7 S1 ^ H! [: ~: I7 l! h+ j0 d
I2C_HandleTypeDef hi2cx;
( i2 T0 h4 h9 ]9 d
/* I2C1 init function */" `) @# P# N+ o; N4 H) i3 R
void MX_I2C1_Init(void)% \. Z. j8 R( a% G# K4 B% o2 u+ a
{& X% f: Q3 j: _: v$ k
hi2cx.Instance = I2C1;
hi2cx.Init.Timing = 0x20D22930;
hi2cx.Init.OwnAddress1 = 0;
hi2cx.Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT;6 q4 x: \+ p& O S+ Y, S) z7 I
hi2cx.Init.DualAddressMode = I2C_DUALADDRESS_DISABLED;
hi2cx.Init.OwnAddress2 = 0;$ s0 x6 ]4 I- O2 j9 ~
hi2cx.Init.OwnAddress2Masks = I2C_OA2_NOMASK;" A) W) l9 y: w8 S) ]
hi2cx.Init.GeneralCallMode = I2C_GENERALCALL_DISABLED;, a0 P* w' ^' d# S: g: A. Q) e
hi2cx.Init.NoStretchMode = I2C_NOSTRETCH_DISABLED;
HAL_I2C_Init(&hi2cx);9 I9 s, t ?' t
/**Configure Analogue filter
*/6 q1 F" O& v( z& c+ R' H
HAL_I2CEx_AnalogFilter_Config(&hi2cx, I2C_ANALOGFILTER_ENABLED);
}8 G2 l( C: A' |5 n }, t8 v) _ n! I$ z
void HAL_I2C_MspInit(I2C_HandleTypeDef* hi2c); f# {# T+ i) |- E' U) V, v5 a6 d( B2 x
{
1 ?2 ?, _. Z9 D
GPIO_InitTypeDef GPIO_InitStruct;
if(hi2c->Instance==I2C1)2 [9 M4 H b. i
{
/* Peripheral clock enable */
__I2C1_CLK_ENABLE();
/**I2C1 GPIO Configuration / h4 U# O' H" o; F8 [: q- F; z
PB6 ------> I2C1_SCL
PB7 ------> I2C1_SDA- t! ]$ k* U8 x- C
*/
GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;
GPIO_InitStruct.Mode = GPIO_MODE_AF_OD;9 v6 A- q( l# A( v6 t1 o4 v9 G
GPIO_InitStruct.Pull = GPIO_NOPULL;# |& H+ _* k) J* g
GPIO_InitStruct.Speed = GPIO_SPEED_HIGH;
GPIO_InitStruct.Alternate = GPIO_AF1_I2C1;+ y5 {! h: H0 I5 ?# \1 ^8 u& K2 r
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
7 n, H) \3 S' W& E/ s5 P: ?
}- T, _9 i! X, |7 ~
}& P5 z! k ~3 u3 C
void HAL_I2C_MspDeInit(I2C_HandleTypeDef* hi2c)
{# Z2 G1 U$ C* m$ r
- A) H$ }% C2 j% {1 g- [
if(hi2c->Instance==I2C1)3 G5 h- G d1 r# e5 H& U
{* r. J! B: i6 r
/* Peripheral clock disable */# \+ h& o' y* @* z9 b
__I2C1_CLK_DISABLE();
/**I2C1 GPIO Configuration
PB6 ------> I2C1_SCL
PB7 ------> I2C1_SDA
*/
HAL_GPIO_DeInit(GPIOB, GPIO_PIN_6|GPIO_PIN_7);' E- R3 F: i6 k' Q {) N- e, b
: c( |/ @4 B' ^1 d- | j
}3 o: A2 D0 M# I
}7 M$ Q _2 X9 p! O9 \
------------------------------------------------------------------------------- 传说中的分界线 ----------------------------------------------------------------------------/ O- R$ Y: O0 I& g& ?+ V
usart.c
#include "usart.h"
#include "gpio.h"# H$ P3 F0 R3 L) [
#include "dma.h"+ p X! R4 X- c, r6 M
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
^6 ]* U" h2 U' z8 l; o7 K( \
UART_HandleTypeDef huart2;
DMA_HandleTypeDef hdma_usart2_rx;
DMA_HandleTypeDef hdma_usart2_tx;
/* USART2 init function */
void MX_USART2_UART_Init(void)
{
; W. g+ @0 ?/ Q# p- S" a
huart2.Instance = USART2;
huart2.Init.BaudRate = 9600;) x# i$ @5 n. Y4 `. `2 z+ V8 X) p7 N
huart2.Init.WordLength = UART_WORDLENGTH_8B;
huart2.Init.StopBits = UART_STOPBITS_1;; s- U- G, ]9 v3 I/ N
huart2.Init.Parity = UART_PARITY_NONE;( w" ^' ]7 W1 `$ j% ~
huart2.Init.Mode = UART_MODE_TX_RX;
huart2.Init.HwFlowCtl = UART_HWCONTROL_NONE;
huart2.Init.OverSampling = UART_OVERSAMPLING_16;
huart2.Init.OneBitSampling = UART_ONEBIT_SAMPLING_DISABLED;/ ]# X. m8 Q; h) b" y3 {) p' Z5 F% {% V
huart2.AdvancedInit.AdvFeatureInit = UART_ADVFEATURE_NO_INIT;
HAL_UART_Init(&huart2);
9 j# Q. I' f5 W
}; F; _! m: d7 M( w
5 }3 U) f* Z7 d" H8 \' g7 N
void HAL_UART_MspInit(UART_HandleTypeDef* huart)/ k* j! L0 s5 i! W$ G
{
+ d# t/ L: v2 M: U3 G& H
GPIO_InitTypeDef GPIO_InitStruct;. h: Q7 t' k8 L, @ E& o8 {
if(huart->Instance==USART2)
{
/* Peripheral clock enable */
__USART2_CLK_ENABLE();- R6 p* V. y6 H. h" \
& Q' r) y5 o: M2 a
/**USART2 GPIO Configuration , R8 H& ]) ?+ T, `3 S- K4 o, t/ O
PA2 ------> USART2_TX9 r- R; z. Z% y. l! p
PA3 ------> USART2_RX
*// G. Z% q; e1 j3 N k7 _. D+ O+ H! u
GPIO_InitStruct.Pin = GPIO_PIN_2;5 k, ^% d5 R2 |. }( r( X
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;+ i5 \ H+ M! B' \% g& j9 p/ [( w
GPIO_InitStruct.Pull = GPIO_NOPULL;6 t, u) j# r5 ]1 g* T
GPIO_InitStruct.Speed = GPIO_SPEED_HIGH;0 V4 b2 s, j/ I( Q e1 e; A# Z
GPIO_InitStruct.Alternate = GPIO_AF4_USART2;
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);5 Z( H6 B8 R' H% l2 o9 ?
; H7 H {- {/ ]1 N3 L* J3 l
GPIO_InitStruct.Pin = GPIO_PIN_3;( u. A4 n8 O! `
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_LOW;. y0 g8 B* y8 t
GPIO_InitStruct.Alternate = GPIO_AF4_USART2;# F4 _8 D7 M/ Y) o5 G6 a
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);' X, e# j5 R1 W: I3 v: V
/* Peripheral DMA init*/
) G6 T' a( M1 z" d
hdma_usart2_rx.Instance = DMA1_Channel5;: Z9 `2 Q8 [2 f( u2 t& k- T
hdma_usart2_rx.Init.Request = DMA_REQUEST_4;+ V) t3 p+ A1 X" S: z) z! B7 H
hdma_usart2_rx.Init.Direction = DMA_PERIPH_TO_MEMORY;. O' D/ y# e, {
hdma_usart2_rx.Init.PeriphInc = DMA_PINC_DISABLE;) ~0 W; }- ?4 u0 f; k
hdma_usart2_rx.Init.MemInc = DMA_MINC_ENABLE;8 |" m' x$ `9 i) c
hdma_usart2_rx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE;
hdma_usart2_rx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE;' g# X! s. P; T3 V
hdma_usart2_rx.Init.Mode = DMA_NORMAL;2 }! O6 a4 T4 o8 E# j( `* l
hdma_usart2_rx.Init.Priority = DMA_PRIORITY_LOW;
HAL_DMA_Init(&hdma_usart2_rx);( m. N7 D: |; E) P! ]/ x
__HAL_LINKDMA(huart,hdmarx,hdma_usart2_rx);: {( I w* G7 d/ e" j# m# E) _' e5 H
' m) M7 Z/ K0 D8 \9 K1 r% k# t
hdma_usart2_tx.Instance = DMA1_Channel4;
hdma_usart2_tx.Init.Request = DMA_REQUEST_4;6 p+ @# U1 U! K8 |
hdma_usart2_tx.Init.Direction = DMA_MEMORY_TO_PERIPH;1 t" q Y. u1 n
hdma_usart2_tx.Init.PeriphInc = DMA_PINC_DISABLE;
hdma_usart2_tx.Init.MemInc = DMA_MINC_ENABLE;2 m S Z0 R9 F1 R& F
hdma_usart2_tx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE;
hdma_usart2_tx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE;: U" @7 R& A' x$ ~# S. x* t6 }
hdma_usart2_tx.Init.Mode = DMA_NORMAL;
hdma_usart2_tx.Init.Priority = DMA_PRIORITY_LOW;6 ^/ Y4 W9 N. a
HAL_DMA_Init(&hdma_usart2_tx);
__HAL_LINKDMA(huart,hdmatx,hdma_usart2_tx);
9 \& O; e w1 I1 ]" L0 {# @
}
}9 n- ~" U( G* @8 w3 Z
void HAL_UART_MspDeInit(UART_HandleTypeDef* huart)
{2 L) b0 N9 M) y7 e7 A" x
if(huart->Instance==USART2)6 y& _$ x2 d0 ^: k. L* s4 j
{8 h7 i+ j, M2 v7 v/ @
/* Peripheral clock disable */1 s2 _7 c3 P% u! c a& ^% g8 z
__USART2_CLK_DISABLE();! Q" O" \2 @1 P: c
/**USART2 GPIO Configuration ^! R+ i8 u' |# i% v7 \. {/ K
PA2 ------> USART2_TX
PA3 ------> USART2_RX* u7 ~) d' K! P" ~
*/
HAL_GPIO_DeInit(GPIOA, GPIO_PIN_2|GPIO_PIN_3);3 N- U6 t) E3 s7 s$ X& l: Q! B r
& F: u5 O" y5 I7 `" z# R: ?+ e
/* Peripheral DMA DeInit*/& q8 f) C9 m# v j: [
HAL_DMA_DeInit(huart->hdmarx);! k* Q( E( {8 O2 r0 ] i! b! O
HAL_DMA_DeInit(huart->hdmatx);
}
}# s7 _/ g# I5 s- E/ U" g- ]8 _
------------------------------------------------------------------------------- 传说中的分界线 ----------------------------------------------------------------------------
mpu6050.c
#include "stm32l0xx_hal.h"
#include "MPU6050.h", z* K4 |% A( ^
6 d S- }0 _+ g2 f5 Y" W
//各坐标轴上静止偏差(重力,角速度)
int16_t offsetAccelX = -195;
int16_t offsetAccelY = 560;4 X: ~4 V& P& I$ q8 c F+ j
int16_t offsetAccelZ = -169;
- ]& t: T) ~* k9 b# S ^- [3 ~2 e
int16_t offsetGyroX = 12;' C7 M) b" F4 y
int16_t offsetGyroY = 33;& G" D, U. C( R' t) |0 b9 e
int16_t offsetGyroZ = 4;
4 a" i& G, t; R `& d ?
extern I2C_HandleTypeDef hi2cx;9 x/ W2 U3 M2 {% k9 f. h r- U3 x
//**************************************' \9 l- K- o- h" N+ K$ N" d5 H
//向I2C设备写入一个字节数据
//**************************************& H( W! t+ K& [2 |' x) C
void Single_WriteI2C(uint8_t REG_Address,uint8_t REG_data)
{% f) q& e& [2 Z3 Y
uint8_t rxData[2] = {REG_Address,REG_data};
while(HAL_I2C_Master_Transmit(&hi2cx,SlaveAddress,rxData,2,5000) != HAL_OK)) U2 D7 R+ l4 r [8 z+ L/ F4 ?
{* ]; d& e1 c$ `4 @0 \" m% d% B
if(HAL_I2C_GetError(&hi2cx) != HAL_I2C_ERROR_AF)
{}+ x; x1 j& q6 C
}
}
//**************************************
//从I2C设备读取一个字节数据
//**************************************8 d' `8 r. J6 p6 h8 H2 F6 F( r
uint8_t Single_ReadI2C(uint8_t REG_Address)4 R; o2 R1 Y+ k% P
{
uint8_t REG_data;
while(HAL_I2C_Master_Transmit(&hi2cx,SlaveAddress,®_Address,1,5000) != HAL_OK)
{
if(HAL_I2C_GetError(&hi2cx) != HAL_I2C_ERROR_AF)
{}$ D) j! X- D! D2 ]) }3 O
}
7 u: b/ _+ k- ?1 b0 S
if(HAL_I2C_Master_Receive(&hi2cx,SlaveAddress+1,®_data,1,5000) != HAL_OK)
{
if(HAL_I2C_GetError(&hi2cx) != HAL_I2C_ERROR_AF). u* }: K% m6 R- v
{}
}! d6 u- {7 ~6 e V4 e7 D9 I' A
return REG_data;" S5 P+ O/ f& E- F8 }
}. s$ i6 b% w/ y8 Z( ]
//**************************************: e! Z* {) Y* v N ?+ Q
//初始化MPU6050
//**************************************
void InitMPU6050()5 O+ W+ o2 I+ l" r" W1 E* ]
{, m6 P# O% H5 N* O( f' \
Single_WriteI2C(PWR_MGMT_1, 0x00); //解除休眠状态 f+ R( r: ?0 M6 Q2 J, ^
/ S( m# D" q5 S+ D/ A
Single_WriteI2C(SMPLRT_DIV, 0x07);; q9 s* K3 p4 u6 n. [
Single_WriteI2C(CONFIG, 0x06);
Single_WriteI2C(GYRO_CONFIG, 0x18);( ^* w: a' x+ e1 Z1 d0 d' m
5 F* c0 Q: Q$ A* Y [
Single_WriteI2C(ACCEL_CONFIG, 0x01);
}0 {3 M ?- B- G
//**************************************
//合成数据
//**************************************
int16_t GetMPUOutValue(uint8_t REG_Address)! M S/ i$ t. R3 L/ \0 F' K y( q
{
int16_t result;* C* `8 ~3 M% ]2 F. Q
uint8_t H,L;# L# ]6 I/ o; X. Q) F$ d
H=Single_ReadI2C(REG_Address);) N: Y& Q) |1 B) ^$ ^) J* _
L=Single_ReadI2C(REG_Address+1);
result = (H<<8)+L;- W1 h D, g( M% _
return result; //合成数据
}
9 w. f+ e" A" J7 i8 S( G
//**************************************
//取某一轴上的加速度数据
//**************************************0 r4 P5 E! t7 y5 R
int16_t GetAccelValue(char axis)
{
int16_t result = 0;, o* V! Y r8 x3 D4 D) `9 p
switch(axis)9 r5 ]1 ] u1 E3 i* s
{
case 'x':" j9 M4 E- A/ m' m& q# w, P
case 'X':
{ w% C( o q+ H! T# b5 [
result = GetMPUOutValue(ACCEL_XOUT_H) - offsetAccelX;
}
break;* J- m! w# e/ R3 W
case 'y':
case 'Y':
{
result = GetMPUOutValue(ACCEL_YOUT_H) - offsetAccelY;
}
break;
case 'z':
case 'Z':
{/ ^. l( |1 p: v
result = GetMPUOutValue(ACCEL_ZOUT_H) - offsetAccelZ;+ ^/ g: S4 O* e
}
break;
}5 z% s' Q. Z- L2 m
return result;
}6 S; o$ j4 _5 h5 t% Y1 Y
" A+ {3 ?) t1 F! E$ S
//**************************************$ h( ]( r9 j: ~3 s7 g
//取某一轴上的角速度数据
//**************************************! m3 E/ S2 P, D# ?" n* Z5 U s
int16_t GetGyroValue(char axis)/ x0 y3 ^ [ J5 L" E3 a
{
int16_t result = 0;. Y7 k+ ~2 E: H% I0 |
switch(axis)
{* v" i$ [" U! W s5 A2 H
case 'x':% F' V( [# p/ s% z
case 'X': t2 _6 O& n$ T. z, D
{
result = GetMPUOutValue(GYRO_XOUT_H) - offsetGyroX;& m3 n. N m% A6 W! o$ X' V' ]7 @6 Y S
}
break;! E" o4 A3 _( U& r& Q$ h
case 'y':( V( Y* T2 O( j' N
case 'Y':
{4 Y4 w9 W5 ]) t7 _
result = GetMPUOutValue(GYRO_YOUT_H) - offsetGyroY;
}
break;) x8 n4 `: n: u& b
case 'z':
case 'Z':
{
result = GetMPUOutValue(GYRO_ZOUT_H) - offsetGyroZ;6 C0 Q; U+ w* q
}
break;9 t' {- f# M# K
}9 ?8 e% N$ T. ~* u
return result;' g5 X$ u: T3 {' m! @
}
评分
查看全部评分
{6 |% F5 Y I8 ]- |! Z
/* USER CODE BEGIN 1 */
5 i I2 c6 e2 E) u
/* USER CODE END 1 */! |( F" a& c5 ]( z( q
/* MCU Configuration----------------------------------------------------------*/; v( U& A G' u( a+ j, [
2 X. q! w/ c7 M: L
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */: ]7 E+ _" A0 Y. ?
HAL_Init();
/* Configure the system clock */
SystemClock_Config();0 ?6 I$ r* `( T
! C5 H% X! O9 U& l0 {$ c
/* System interrupt init*/
HAL_NVIC_SetPriority(SysTick_IRQn, 0, 0);
3 ^# K% c6 B( A! R# X0 ~$ i3 i! j
/* Initialize all configured peripherals */ ~; Q. R7 J' \3 ]
MX_GPIO_Init();" `- ? R! X: Z5 H! _) X9 P$ X
MX_DMA_Init();1 F! I# D j; ?: V* a- I! T
MX_I2C1_Init();
MX_TIM2_Init();5 _: @5 J5 ~! ^* |) r8 b: [
MX_USART2_UART_Init();
InitMPU6050();
0 e2 Q$ Z7 F/ ^" Y" i
/* USER CODE BEGIN 2 */4 ]7 _4 ]( g' u, A5 v$ O
HAL_UART_Receive_DMA(&huart2,rxBuffer,RXSIZE);
HAL_TIM_Base_Start_IT(&htim2);/ b2 p! H C! h5 L' f
/* USER CODE END 2 */) r6 A+ G; C% i O: p3 T
9 W n& i/ |! I. k& c, H6 I5 x/ q8 J" M
/* USER CODE BEGIN 3 */* [# L3 x' c+ W" l! F( h1 d" X7 n
/* Infinite loop */
while (1), d8 F/ S* m5 j) j0 ~$ l7 n6 A
{2 R5 n* h; g5 ^8 @5 t2 @& N; X
HAL_GPIO_TogglePin(GPIOA,GPIO_PIN_5);: z! {, ?1 j: Q+ T
VisualScopeAngleOutput();
HAL_Delay(100);- L. t$ o& e7 r. C; a4 M
}$ k% f1 H4 [: ^- i: g
/* USER CODE END 3 */9 a1 `: h+ f( l
( A9 E9 k& Q* F- I) ?5 L5 G
}0 c3 \1 F* V4 N
" u: k2 ~# P, J) T
/** System Clock Configuration
*/
void SystemClock_Config(void)
{# J/ ]9 C, d5 O4 X- P5 ]
6 [: \4 p0 c1 u" U8 p5 e1 |! [. @
RCC_ClkInitTypeDef RCC_ClkInitStruct;
RCC_PeriphCLKInitTypeDef PeriphClkInit; k5 S% X- E, i5 @
RCC_OscInitTypeDef RCC_OscInitStruct; l2 e3 m- P! `1 R/ M! _
__PWR_CLK_ENABLE();
__HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);& g1 ?5 m7 C$ }- Q3 O9 p2 [
$ g3 q0 K- e, O# M
RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI;! _8 F/ t8 E% _7 H+ N# d1 s
RCC_OscInitStruct.HSIState = RCC_HSI_ON;: L& o) [5 I7 a+ K) I- ~4 B- u
RCC_OscInitStruct.HSICalibrationValue = 16;+ h2 t5 W9 l% F+ r
RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI;
RCC_OscInitStruct.PLL.PLLMUL = RCC_PLLMUL_6;
RCC_OscInitStruct.PLL.PLLDIV = RCC_PLLDIV_3;
HAL_RCC_OscConfig(&RCC_OscInitStruct);6 v% o3 k2 t$ x$ Z
RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_SYSCLK; o% [4 ?. k, u1 |6 T
RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK;
RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;
RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;# i! \' [6 Y* L+ I, x
RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;% d6 g4 m0 ?5 D3 g5 Q$ c" T/ J
HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_1); P* S" Z' B: T; q: x* b: v* Q
7 R! M, `; Q0 ^
PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_USART2;) V1 x9 q& ^& A1 }6 }: b# m7 V
PeriphClkInit.Usart2ClockSelection = RCC_USART2CLKSOURCE_PCLK1;: {6 v$ J: B. n& {
HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit);
: G$ y; r8 y3 D+ u; y5 J
__SYSCFG_CLK_ENABLE();/ D0 Q; J2 ~/ {) m
}
: q3 ]6 m5 G$ P3 ]
/* USER CODE BEGIN 4 */# P: b, F8 `/ z
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)$ H0 O6 J2 \7 T) P+ ~: c9 [
{
if(huart->Instance == USART2)
{' k6 G6 z0 _% C' n8 g
memcpy(txBuffer,rxBuffer,RXSIZE);& N5 P$ w, p3 b6 o1 u( K& y
HAL_UART_Receive_DMA(huart,rxBuffer,RXSIZE);
HAL_UART_Transmit_DMA(huart,txBuffer,TXSIZE);
}( E: p8 S0 o9 Z9 `8 y1 f3 l
}
+ a* h, J& m" i: s5 F
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart)
{7 `( x; Z* v6 j; S# f2 l
}
( y) v. E" E1 x- r
void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef *htim)# d" R' o( {$ m! Y. U
{
int32_t GyroValue;
Calc_AngleAccel();
GyroValue = Calc_AngleGyro();
ComplementFilter(GyroValue);7 c- }+ |' c0 C/ L. b0 n5 w
}
使用DMA方式,接收发送数据必须是个固定长度。
如果是长度不固定,你使用中断方式,然后加起止,停止标志位来判断。
好的,多谢指点!
请问应该注意什么地方
我使用是没有问题的呀。