amoBBS 阿莫电子论坛

 找回密码
 注册
搜索
bottom↓
查看: 33776|回复: 264

不思带你【从零开始】做四轴--软件/硬件/上位机--随时更新

  [复制链接]
发表于 2013-3-17 17:27:15 | 显示全部楼层 |阅读模式
本帖最后由 wangjt1988 于 2013-3-17 21:14 编辑

    很多童鞋已经拿到了套件,由于基础不同,大家在硬件焊接/模块驱动/程序调试等方面会遇到各种各样的问题,为了给大家解答,也为了方便大家少走弯路,特此开贴,从最开始的硬件焊接调试,到最后的飞行调试,一一给大家介绍,争取让大家跟着教程都能做出自己的飞控.(当然楼主也是刚开始做不久,飞机也只是可以飞行,还是很不稳定,还需要不断学习,努力)
    本贴会持续,不断更新,楼主会跟着大家一同开始四轴的学习.




    首先是之前帖子的链接:
    开源自己的微型四轴—全套原理图.程序.上位机.    http://www.amobbs.com/thread-5515784-1-1.html
    匿名四轴--介绍上位机     http://www.amobbs.com/thread-5516299-1-1.html   
    试飞视频:http://www.56.com/u56/v_ODQ0ODczNDk.html
   
    几个月过去了,上位机经过算法和功能的优化,现在给大家提供新版本的上位机.








    大家刚开始使用可能有点摸不到头脑,这里给大家简单介绍一下         (上位机在使用时按F12会有帮助界面)
基本介绍:http://v.youku.com/v_show/id_XNTI4MDczNzI0.html
基本收发:http://v.youku.com/v_show/id_XNTI4MDc0NzEy.html
高级收码:http://v.youku.com/v_show/id_XNTI4MDc2MTMy.html
高级收码2+波形显示:http://v.youku.com/v_show/id_XNTI4MDg0NjQ4.html
飞控状态:http://v.youku.com/v_show/id_XNTI4MDk2ODk2.html

上位机的数据处理速度可以1毫秒处理一个几十字节的数据帧(无线数据包为32字节,这里就以32字节为例),也就是说1秒可以处理32000字节的数据. (1ms接收32字节的数据,并分析,显示数据波形)  这里可以说是写上位机时最难的,占据了大量的时间,因为如果做到10ms接收一帧数据并显示,是比较容易的,如果频率快了,比如现在的1ms一帧数据的话,pc的数据处理和显示刷新要处理的很好才行,要不程序就很容易"死掉",因为windows不是实时系统,还有很多事情要做,不能把所有资源都给上位机程序. 目前传感器的采样频率也是1ms一次,这样就可以用上位机直接观察采样值和滤波后的值,很方便,可以实时观察滤波效果,不用再把数据先保存在内存卡或者电脑上,飞完了在调出来看波形了.
    而且听取大家意见,很多人没有航模遥控,这里加上了鼠标键盘控制功能,可以用鼠标和键盘控制飞机了,当然,手感肯定没有遥控好了.


马上会有新版的飞机,遥控板,下载调试板,充电板,板子还在路上...

为了减轻重量,飞机上没有设计遥控接收模块,飞机的遥控通过飞控上自带的NRF24L01芯片完成,同时该芯片还负责数据的传输,所以飞机不能直接通过商业遥控遥控飞行,需要用一个单片机采集遥控信号再通过NRF模块发给飞机来完成遥控,同时飞机可以将飞行数据通过NRF模块发给单片机,单片机再通过串口发送到pc上位机,上位机也可以把飞行参数通过NRF模块实时发给飞机.等于是同时存在以下几个数据连接:
1:遥控->遥控板->飞机
2:PC上位机->遥控板->飞机
3:飞机->遥控板->PC上位机
可以看出所有的数据传输都要通过遥控板.这样的好处是在遥控飞行的同时可以用上位机接收飞机的飞行数据,并在上位机实时显示,上位机也可以在飞行过程中或飞机落地后,修改飞控参数,十分方便.

    硬件调试:大家拿到套件后,请根据原理图进行焊接,芯片方向要注意,不清楚的找楼主要高清大图,按照图片焊接也挺简单.(完全都是贴片的元件,考验大家的焊工了.这里我们也想给大家焊接好的,但是是业余爱好搞搞这个,平时还要上班工作,实在是没有时间,还请大家理解)

    焊接好后,就要开始软件调试了,这里才是四轴最"好玩"的地方,当初决定玩四轴也是因为这个,因为四轴硬件简单,主要拼的是软件,不像直机什么的,硬件太复杂了.
软件的调试,建议大家还是一步一步来.虽然我开源了飞控的全部程序,大家烧进去就可以实现基本的飞行了,但是我们自己做飞控最关键的就是程序了,直接copy一个工程过来,想必大家直接消化还是很不容易的.就像学习骑车一样,还不会走路,就学骑自行车,怎么会骑好.所以还是建议大家从基础的开始.

    从哪里开始呢,因为我们使用的是stm32f103,大家就从最简单的stm32的驱动开始吧.
以下都是针对我的飞控板写的,大家如果用的自己的,记得需要把IO和端口都改为自己的
    stm32可以说就是飞控的大脑,mpu6050和hmc5883就是飞控的眼睛,耳朵.飞控的所有功能,都是通过stm32实现的,所以大家清楚了stm32做什么了以后,就要好好的把他驱动好,让他按照我们的想法来运转,这样飞控才能好好的工作.
    首先下载我们需要的软件环境,就是MDK (KEIL FOR ARM),我用的是4.7版本,有了自动补全功能,挺好用.当然,还要有个JLINK,使用swd方式进行调试.然后就可以开始第一步的程序编写了.按照网上的教程,使用库函数建立一个空白的工程,从最简单的,点亮一个LED开始.
    要点亮一个led,也不是一件简单的事情,首先,系统时钟要配置好(最新库函数在初始化时已经帮我们把时钟初始化好了,不用我们再初始化了,当然,除非你有特殊要求),然后要配置端口的输入输出,还要打开响应端口的外设时钟.
void LED_INIT(void)
{
        GPIO_InitTypeDef GPIO_InitStructure;        这个是端口配置结构体
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB , ENABLE);             打开外设GPIOB的时钟,因为LED是通过GPIOB的9,11,14,15来驱动的
        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_14 | GPIO_Pin_15 | GPIO_Pin_9 ;                 选择响应的管脚
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;                  设置IO速度
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;                   设置IO驱动方式,out为输出,PP为推挽输出
        GPIO_Init(GPIOB, &GPIO_InitStructure);                                         对GPIOB进行初始化
}
初始化好了,再写几个函数来操作LED,更加方便
#define LED1_OFF          GPIO_SetBits(GPIOB, GPIO_Pin_11)
#define LED1_ON                 GPIO_ResetBits(GPIOB, GPIO_Pin_11)
#define LED2_OFF          GPIO_SetBits(GPIOB, GPIO_Pin_14)
#define LED2_ON                 GPIO_ResetBits(GPIOB, GPIO_Pin_14)
#define LED3_OFF          GPIO_SetBits(GPIOB, GPIO_Pin_15)
#define LED3_ON                 GPIO_ResetBits(GPIOB, GPIO_Pin_15)
#define LED4_OFF          GPIO_SetBits(GPIOB, GPIO_Pin_9)
#define LED4_ON                 GPIO_ResetBits(GPIOB, GPIO_Pin_9)
#define LEDALL_OFF  GPIO_SetBits(GPIOB, GPIO_Pin_11 | GPIO_Pin_14 | GPIO_Pin_15 | GPIO_Pin_9)
#define LEDALL_ON         GPIO_ResetBits(GPIOB, GPIO_Pin_11 | GPIO_Pin_14 | GPIO_Pin_15 | GPIO_Pin_9)
这几个函数功能很简单,就是对IO的输出电平进行操作.当LED可以点亮后,更高级的比如LED的闪烁,就需要大家自己写了,实现的方法很多,可以用循环实现,也可以用定时中断实现.选用哪种方式实现,就要看具体的使用地点和情况了.

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
发表于 2013-3-17 17:33:14 | 显示全部楼层
支持下,继续加油!让自己的四轴飞起来。
发表于 2013-3-17 17:33:54 | 显示全部楼层
支持下,
发表于 2013-3-17 17:33:56 | 显示全部楼层
顶,关注!
发表于 2013-3-17 17:37:58 | 显示全部楼层
关注,正在储备这方面的知识,也想自己有个四轴撒
发表于 2013-3-17 18:04:01 | 显示全部楼层
楼主的四轴做得很不错,严重关注中~~~~~~~~~~~~~~~~~~~~~~~~
发表于 2013-3-17 18:12:50 | 显示全部楼层
顶楼主。继续关注。。。
发表于 2013-3-17 18:13:31 | 显示全部楼层
前排留名,支持!!!
发表于 2013-3-17 18:59:24 | 显示全部楼层
C#写的?
有套件吗?
发表于 2013-3-17 19:27:54 | 显示全部楼层
顶,关注!
 楼主| 发表于 2013-3-17 20:04:41 | 显示全部楼层
william_rain 发表于 2013-3-17 18:59
C#写的?
有套件吗?

delphi写的
发表于 2013-3-17 20:13:37 | 显示全部楼层
强烈关注
发表于 2013-3-17 22:36:00 | 显示全部楼层
发表于 2013-3-17 22:43:53 | 显示全部楼层
早知道早点回来看的!此贴必火,前排留不到名了!!!

准备开始,向你进军~
发表于 2013-3-17 22:45:41 来自手机 | 显示全部楼层
顶啊,关注!
发表于 2013-3-17 23:05:06 | 显示全部楼层
帮顶。
发表于 2013-3-18 01:24:04 | 显示全部楼层
为楼主坚持不懈的精神赞一个!
发表于 2013-3-18 02:16:50 | 显示全部楼层
收藏一个,一定要做一个!
发表于 2013-3-18 09:16:10 | 显示全部楼层
支持楼主!!!!
发表于 2013-3-18 09:17:12 | 显示全部楼层
wangjt1988 发表于 2013-3-17 20:04
delphi写的

LZ delphi装的是iocomp控件么?装好后OPC显示的是Evaluation么?
 楼主| 发表于 2013-3-18 09:38:10 来自手机 | 显示全部楼层
是iocomp,就用了基本功能  ,没注意opc是什么……opc是什么功能?
发表于 2013-3-18 10:10:17 | 显示全部楼层
关注一下  ~~~~~~~~~~~~~
发表于 2013-3-18 10:12:38 | 显示全部楼层
顶!楼主好样的!
发表于 2013-3-18 12:42:59 | 显示全部楼层
围观!!Stm32f103是个好东西哈!
发表于 2013-3-18 12:48:26 | 显示全部楼层
楼主太强大了,谢谢楼主。
发表于 2013-3-18 12:56:52 | 显示全部楼层
这个必须要顶!现在的版本越来越高了,把天线也一起画在板上了
发表于 2013-3-18 14:35:47 | 显示全部楼层
顶!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
发表于 2013-3-18 15:14:01 | 显示全部楼层
wangjt1988 发表于 2013-3-18 09:38
是iocomp,就用了基本功能  ,没注意opc是什么……opc是什么功能?

额...其实我也不知道...
其实我也想用Delphi做个上位机,然后看到iocomp很不错,就装了,然后是这样的,据说是有试用期的...

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
 楼主| 发表于 2013-3-18 15:18:42 来自手机 | 显示全部楼层
落叶随风 发表于 2013-3-18 15:14
额...其实我也不知道...
其实我也想用Delphi做个上位机,然后看到iocomp很不错,就装了,然后是这样的, ...

能用就好   呵呵
发表于 2013-3-18 15:19:52 | 显示全部楼层
遥控板出了没?.....套件还在待焊ing...
发表于 2013-3-18 15:22:46 | 显示全部楼层
wangjt1988 发表于 2013-3-18 15:18
能用就好   呵呵

恩,不知道LZ陶瓷天线了解过没有
发表于 2013-3-18 15:24:12 | 显示全部楼层
不错。
帮顶。

   
 楼主| 发表于 2013-3-18 15:28:38 来自手机 | 显示全部楼层
damoplus 发表于 2013-3-18 15:19
遥控板出了没?.....套件还在待焊ing...

遥控板这周就有了
发表于 2013-3-18 15:32:48 | 显示全部楼层
期待
发表于 2013-3-18 16:18:48 | 显示全部楼层
期待楼主 ,好像DIY  可自己能力有限,希望得到学习提升!
发表于 2013-3-18 17:04:58 | 显示全部楼层
我又要来顶你了
发表于 2013-3-18 17:14:22 | 显示全部楼层
lz 建议做大四轴。 中国无人机就靠你了
 楼主| 发表于 2013-3-18 17:22:11 | 显示全部楼层
rei1984 发表于 2013-3-18 17:14
lz 建议做大四轴。 中国无人机就靠你了

呵呵  我倒是想为国家做贡献啊   可是咱多大能力还是知道的
 楼主| 发表于 2013-3-18 18:44:16 | 显示全部楼层
额,帖子已经不能编辑了,只能在回复里贴了......
第一步LED驱动好了,下一步做点什么呢?就来驱动下串口吧,串口还是调试时一个很好用的工具.
串口调试也一样,第一步,当然是初始化.
void USART1_INIT(void)
{
        USART_InitTypeDef USART_InitStructure;
        USART_ClockInitTypeDef USART_ClockInitStruct;
        GPIO_InitTypeDef GPIO_InitStructure;
        以上是定义初始化用到的结构体

        RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE); //¿ªÆôUSART1ʱÖÓ
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);       
        打开外设时钟,这里打开串口USART1时钟,那为什么打开GPIOA的时钟呢?因为串口用的GPIOA的管脚.........       

        GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_9;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
        GPIO_Init(GPIOA , &GPIO_InitStructure);
       
        GPIO_InitStructure.GPIO_Pin =  GPIO_Pin_10;
        GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
        GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
        GPIO_Init(GPIOA , &GPIO_InitStructure);
        管脚配置

        USART_InitStructure.USART_BaudRate = 500000;                                        波特率
        USART_InitStructure.USART_WordLength = USART_WordLength_8b;           数据位
        USART_InitStructure.USART_StopBits = USART_StopBits_1;                       停止位
        USART_InitStructure.USART_Parity = USART_Parity_No;                           校验方式
        USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;              流控制
        USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;                       收发模式
       
        USART_ClockInitStruct.USART_Clock = USART_Clock_Disable;                              时钟及其他设置
        USART_ClockInitStruct.USART_CPOL = USART_CPOL_Low;  
        USART_ClockInitStruct.USART_CPHA = USART_CPHA_2Edge;
        USART_ClockInitStruct.USART_LastBit = USART_LastBit_Disable;
       
        USART_Init(USART1, &USART_InitStructure);                                     串口初始化,刚才的都不算初始化,只是修改变量,这里才把变量赋值给寄存器
        USART_ClockInit(USART1, &USART_ClockInitStruct);                           串口时钟初始化

        USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);                         开中断
        USART_Cmd(USART1, ENABLE);                                                使能串口
}
 楼主| 发表于 2013-3-18 18:49:25 | 显示全部楼层
串口初始化好了,就要测试收发了,将串口用串口线和电脑连接起来,先来简单的发送,用上位机看看能不能收到数据.
对了   这里还要设置串口中断
        NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
       
        NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
        NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 3;
        NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3;
        NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
        NVIC_Init(&NVIC_InitStructure);
我用的第二组,串口给了优先级3,subfriority3

串口中断函数:
void USART1_IRQHandler(void)  
{
        USART1_IRQ();
}
void USART1_IRQ(void)
{
        if(USART_GetITStatus(USART1,USART_IT_TXE)!=RESET)
        {
                发送中断
        }
        if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)   
        {
                接收中断
        }
}
 楼主| 发表于 2013-3-18 18:57:36 | 显示全部楼层
本帖最后由 wangjt1988 于 2013-3-18 18:58 编辑

中断也写好后,基本的发送接收应该就没问题了.
但是在使用过程中,没有一个缓冲区肯定是不行的,关于这方面的帖子很多,大家在论坛上搜索下吧.我就简单介绍下我用的简单的环形缓冲吧.
我用了一个环形发送缓冲,比如一个长度为100字节的数组,再定义两个变量,比如num与t_num
num表示缓冲区内下一个空字节在第几字节,t_num表示下一个需要发送的字节在缓冲区的多少字节
比如需要发送12345 这5个数字,分别写入数组的01234字节,共5字节,此时num+=5,表示buf[5]是空的.写入数据后,激活发送,发送完一个字节,t_num+1,并判断t_num与num的大小,如果t_num<num,就急需发送,如果t_num=num,说明数据已经发送完了.
大致意思就是这样,不知道我表达清楚了没有.
 楼主| 发表于 2013-3-18 19:16:59 | 显示全部楼层
串口做好了,再做点什么呢,就Timer吧,这个是以后程序里很重要的一个内容,因为timer是用来计时的,我们以后要用它来触发做很多事情,比如定时去读传感器并控制电机等等.
还是一样,先初始化Timer,以TIMER3为例
void TIM3_INIT(void)
{
        TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
             初始化使用的结构体
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);
             打开timer3的时钟

        TIM_DeInit(TIM3);
        将timer3寄存器设置为默认
        TIM_TimeBaseStructure.TIM_Period=1000;     这个寄存器我理解是比较值,就是用这个值来和cnt比较,判断是否溢出(大于这个数就溢出)

        TIM_TimeBaseStructure.TIM_Prescaler=72-1;  这个寄存器我理解是分频值,就是timer3的时钟除以这个值+1就是计数器的时钟,这里72分频,就是1M,刚才比较值设置为1000,那么溢出的频率就是1000HZ,也就是每次中断1MS

        TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;         采样分频

        TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up;         向上计数
       
        TIM_TimeBaseInit(TIM3,&TIM_TimeBaseStructure);                             时钟初始化
       
        TIM_ClearFlag(TIM3,TIM_FLAG_Update);                                     清楚标志
       
        TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE);                            开中断
       
        TIM_Cmd(TIM3,ENABLE);                                                      使能timer3
}
发表于 2013-3-18 20:21:53 | 显示全部楼层
鉴定完毕!本贴对于我们这些小白来说是福利,彻底的福利
发表于 2013-3-18 20:35:56 | 显示全部楼层
楼主大公无私 必须要顶,共同娱乐。
 楼主| 发表于 2013-3-18 20:36:01 | 显示全部楼层
有人让我解释一下我程序里面PID计算的过程,这里就插一节吧,就是介绍下我的PID,当然,还很不完善,后期肯定还要经过很多改动才行,这里就先介绍下现在的"初级版"吧.
void PID_CAL(void)                PID计算函数
{
        static float thr=0,rool=0,pitch=0,yaw=0;          控制量
        static float rool_i=0,pitch_i=0;                         积分
       
        int16_t Motor1,Motor2,Motor3,Motor4;             四个电机输出
       
        IMU_TEST();                                                   计算姿态
        GET_EXPRAD();                                             获得控制量
////////////////////////////////////////////////////////////////////////////////
        rool         = PID_RP.P * DIF_ANGLE.X;                    roll方向的P计算
       
        if(Q_ANGLE.Rool>-0.1 && Q_ANGLE.Rool<0.1)   判断I是否需要清零
        {                                                                           
                rool_i = 0;
        }
        rool_i -= PID_RP.I * Q_ANGLE.Rool;                   I计算
        PID_RP.IMAX = DIF_ANGLE.X * 10;                    积分限幅
        if(PID_RP.IMAX<0)       
        {
                PID_RP.IMAX = (-PID_RP.IMAX) + 100;
        }
        else
        {
                PID_RP.IMAX += 100;
        }
        if(rool_i>PID_RP.IMAX)         rool_i = PID_RP.IMAX;
        if(rool_i<-PID_RP.IMAX)        rool_i = -PID_RP.IMAX;
        rool += rool_i;                                                            积分
       
        rool -= PID_RP.D * GYRO_F.X;                                      D计算
///////////       
        pitch         = PID_RP.P * DIF_ANGLE.Y;                                 同上
               
        if(Q_ANGLE.Pitch>-0.1 && Q_ANGLE.Pitch<0.1)
        {
                pitch_i = 0;
        }
        pitch_i -= PID_RP.I * Q_ANGLE.Pitch;
        if(PID_RP.IMAX<0)       
        {
                PID_RP.IMAX = (-PID_RP.IMAX) + 100;
        }
        else
        {
                PID_RP.IMAX += 100;
        }
        if(PID_RP.IMAX<0)        PID_RP.IMAX = -PID_RP.IMAX;
        if(pitch_i>PID_RP.IMAX)         pitch_i = PID_RP.IMAX;
        if(pitch_i<-PID_RP.IMAX)        pitch_i = -PID_RP.IMAX;
        pitch += pitch_i;
       
        pitch -= PID_RP.D * GYRO_F.Y;
/////////////
        GYRO_I[0].Z += EXP_ANGLE.Z/3000;                              yaw方向就简单的用了陀螺的积分    PD
        yaw = -10 * GYRO_I[0].Z;
       
        yaw -= 3 * GYRO_F.Z;
//       
        thr = RC_DATA.THROTTLE+400;
////////////////////////////////////////////////////////////////////////////////将控制量输出给电机
        Motor1=(int16_t)(thr + rool - pitch + yaw);
        Motor2=(int16_t)(thr + rool + pitch - yaw);
        Motor3=(int16_t)(thr - rool + pitch + yaw);
        Motor4=(int16_t)(thr - rool - pitch - yaw);
        if(FLY_ENABLE && (RC_DATA.THROTTLE>-400))                          和解锁有关,未解锁或油门太低电机禁止转动
                MOTO_PWMRFLASH(Motor1,Motor2,Motor3,Motor4);
        else
                MOTO_PWMRFLASH(0,0,0,0);
}
程序就这么简单,当然还需要很多改进,PID参数也需要慢慢调试才行
发表于 2013-3-18 21:12:53 | 显示全部楼层
搬凳子,听楼主悉心教诲
 楼主| 发表于 2013-3-19 08:50:41 来自手机 | 显示全部楼层
chliken 发表于 2013-3-18 21:12
搬凳子,听楼主悉心教诲

教诲谈不上啊…只是把我的思路跟大家聊一聊
发表于 2013-3-19 09:02:07 | 显示全部楼层
外形很漂亮,看起来不错。
发表于 2013-3-19 13:02:05 | 显示全部楼层
落叶随风 发表于 2013-3-18 15:22
恩,不知道LZ陶瓷天线了解过没有

你了解陶瓷天线吗?我曾经试过,效果不怎么好,不知道是不是我买的天线有问题
发表于 2013-3-19 15:15:59 | 显示全部楼层
楼主强大啊,火
发表于 2013-3-19 16:35:02 | 显示全部楼层
顶一下    期待中
发表于 2013-3-19 16:36:30 | 显示全部楼层
小号 发表于 2013-3-19 13:02
你了解陶瓷天线吗?我曾经试过,效果不怎么好,不知道是不是我买的天线有问题 ...

我不太了解,想用陶瓷天线来着,不知道怎么选
发表于 2013-3-19 21:45:49 | 显示全部楼层
现在能力还达不到  不过先mark
发表于 2013-3-19 22:17:39 | 显示全部楼层
想了解一下做PCB天线有什么具体注意事项和要求呢?
发表于 2013-3-20 11:00:50 | 显示全部楼层
wangjt1988 发表于 2013-3-19 08:50
教诲谈不上啊…只是把我的思路跟大家聊一聊

看着三个帖子而来的,想不到又出新教程了,赞一个,预定了
发表于 2013-3-20 13:11:52 | 显示全部楼层
继续支持!!!!!!!!!!
发表于 2013-3-20 14:42:24 | 显示全部楼层
wangjt1988 发表于 2013-3-18 20:36
有人让我解释一下我程序里面PID计算的过程,这里就插一节吧,就是介绍下我的PID,当然,还很不完善,后期肯定还 ...

你的代码我看过了,用到了四元数,但是最后又把四元数转换成欧拉角进行PID控制,不知道,这里面用到四元数是不是有必要
发表于 2013-3-20 16:48:21 | 显示全部楼层
楼主可以否把视频传输也加上呢
 楼主| 发表于 2013-3-20 18:17:44 | 显示全部楼层
xaper 发表于 2013-3-20 14:42
你的代码我看过了,用到了四元数,但是最后又把四元数转换成欧拉角进行PID控制,不知道,这里面用到四元 ...

对四元数直接参加控制还不懂呢......希望有个教程学习一下,请问你知道怎么用四元数直接控制么
 楼主| 发表于 2013-3-20 18:18:00 | 显示全部楼层
工程师030 发表于 2013-3-20 16:48
楼主可以否把视频传输也加上呢

没有摄像头.....
发表于 2013-3-20 19:13:56 | 显示全部楼层
这个可以学习
 楼主| 发表于 2013-3-20 20:06:33 | 显示全部楼层
串口/TIMER都讲过了,这次讲点什么呢,稍微提一提怎么调试吧,因为今天群里有人问我串口是用来做什么的?这个问题让我一下懵了.这该怎么回答?
串口,在我们这个工程里,其实就是用来调试的,无线控制是通过SPI来进行,其实无线调试好以后,串口也就没有用了,可以使用无线进行调试的,这样更加方便.其实串口是完全可以省略的.
那么怎么使用这个串口呢?串口可以理解为一根网线,通过他,可以将飞机上的数据传输到电脑上,就这么简单.........至于传什么,怎么传,学问就大了....
串口驱动好以后,可以帮助我们分析很多问题,有些甚至JLINK也做不到,观察变量,观察标志位,观察程序运行状态,等等,都可以通过串口来实现,上位机为了配合串口和无线调试,还特意做了一个DEBUG功能,就是为了帮助大家更方便的调试,可以通过串口发送一个自定义的命令,打开上位机的LED,或者改变上位机显示的寄存器数字.这样可以帮助大家知道程序的执行状态,比如中断进入没进入啊,进入的频率啊,变量现在的值是多少啊等等信息.
我这里仅仅是一点点自己的调试经验,至于怎么发送,发送一个什么样的格式,大家个人习惯不同,写出来当然也各不相同,有人喜欢用printf,我就喜欢十六进制,各有长短
发表于 2013-3-21 12:35:17 | 显示全部楼层
强人
 楼主| 发表于 2013-3-21 20:14:47 | 显示全部楼层
本帖最后由 wangjt1988 于 2013-3-21 20:23 编辑

可能一个模块一个模块的讲有些啰嗦,而且这些模块的使用方法网上也有很多教程,我以后就不在说这个了.大家有问题就搜索下吧,很容易找到.我目前用到的外设有:timer,usart,iic,spi,flash,gpio,exit,暂时就这么多.
今天想跟大家谈谈加速度计和陀螺仪,不少人在问加速度计陀螺仪的数据读出来了怎么用,咱们就从这两个传感器的特点开始了解下,了解了特点,用法就很容易了.
以下仅代表个人观点,有哪里不对,还请指出....
做个比喻吧,加速度计,以下简称加计,大家可以把它想象成一个铁块,这个铁块是个立方体,有前后左右上下六个面,每个面连接有一个弹簧,弹簧另一端假设固定在一个卡车的集装箱里面,这样这个铁块就被这六个弹簧吊在集装箱里面了,由于铁块有重力,所以汽车不动时,上面的弹簧被拉长,下面的弹簧被压缩,这里假设是通过测量弹簧的拉力来输出加速度(实际有可能是电容什么的,这里不做讨论,了解特性就好),六个弹簧,两两一组,正好3个轴,这就是3轴加速度了,静止不动时,只有Z轴也就是上下两根弹簧有读数,其他两对弹簧是平衡的.现在假设汽车在做加速运动,那么不仅仅上下两根弹簧不平衡了,前后两根弹簧也会有变化,前面的弹簧拉长,后面的弹簧压缩,就有了前后方向的加速度.左右也是一个道理.
知道了加计的大致原理,那么加计有什么特点呢?让我们大家想象一种情况,就是这辆卡车行驶在颠簸的路上,集装箱里面的铁块肯定不会稳稳的吊着了,他会随着汽车左摇右摆,上下颠簸,而且有一点大家注意,铁块的此时的摆动,不是完全和汽车同步的,由于惯性等原因,铁块会在里面"乱动",荡来荡去,此时的加速度输出会是怎么样的呢?肯定也是随着铁块"荡来荡去",所以我们得出加计的一大特点,就是对震动很"敏感",如果把飞控板放在桌子上静止不动,可以说随便一个姿态算法的输出都不错,哪怕不滤波.可以当电机一转动起来,震动来了,加计就有了很大的干扰,此时如果处理不好,姿态就乱掉了.
然后我们再说说陀螺仪,陀螺仪顾名思义,肯定和陀螺有很大关系,没错,特点也和陀螺一样.还是假设在这个车里面,我们放上一个小时候玩的陀螺,不管用了什么方法,让它高速旋转起来,大家都知道,这样陀螺是不会倒的,他会尽量保持当前的姿态,陀螺仪正是利用这个特点.我们看两段视频来了解下.
http://v.youku.com/v_show/id_XMjI5MTc4MjI4.html
http://v.youku.com/v_show/id_XNDIxODk5MDAw.html
通过视频,大家可以看到,陀螺在高速旋转时,是会尽量保持转轴不变的.那么我们就可以想到陀螺仪的特点了,就是对震动是"不敏感"的,因为它会尽量保持自己不被震动改变,但是陀螺会不断累积误差,造成"漂移".
好了,这里我们知道了加计和陀螺仪的特点,再考虑怎么使用,就简单多了,总的来说就是加计短时间不可靠,因为震动,陀螺仪长时间不可靠,因为"漂移".那么对于加计的数据和陀螺仪的数据,我们就应该短时间相信陀螺仪,长时间相信加速度.好了,到了这里,再怎么做也就清晰了,对加速度的数据,我们要滤波,平均值滤波等等,方法很多,对陀螺仪数据,我们积分,短时间内,这个积分得到的角度还是准确的,而过一段时间,就用处理过的加速度数据来矫正陀螺仪积分的角度,抑制"漂移".这样利用两个传感器的特点,取长补短,来达到一个相对稳定的输出.

以上都是个人看法,有什么不对还请大家指出,大家多多讨论.
发表于 2013-3-21 21:26:02 | 显示全部楼层
很形象的描述
发表于 2013-3-21 21:41:59 来自手机 | 显示全部楼层
mark 要好好学学~
发表于 2013-3-21 22:24:59 | 显示全部楼层
一直在跟进,记下,顶上.
发表于 2013-3-21 22:40:07 | 显示全部楼层
看完忘顶贴了,补上
发表于 2013-3-21 23:01:53 | 显示全部楼层
写的不错,谢谢分享,改天我也上传个关于惯性量传感器的介绍。
发表于 2013-3-21 23:02:58 | 显示全部楼层
不错,想搞个套件跟着学习
 楼主| 发表于 2013-3-21 23:06:29 | 显示全部楼层
jordonwu 发表于 2013-3-21 23:02
不错,想搞个套件跟着学习

嗯  大家一同学习 进步  写一套自己的东西
 楼主| 发表于 2013-3-21 23:07:15 | 显示全部楼层
kinghawk 发表于 2013-3-21 23:01
写的不错,谢谢分享,改天我也上传个关于惯性量传感器的介绍。

真是太好了,我们也跟着学习些知识
发表于 2013-3-22 08:44:21 | 显示全部楼层
西门子的传感器介绍
比较直观、形象

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
发表于 2013-3-22 13:20:04 | 显示全部楼层
发表于 2013-3-22 14:12:41 | 显示全部楼层
感谢分享啊,很少有人肯为大家认真讲解四轴控制算法,学习中
发表于 2013-3-23 20:36:51 | 显示全部楼层
版主速更啊
发表于 2013-3-23 21:47:38 | 显示全部楼层
还是喜欢看原理图 通过陀螺仪控制 四个直流有刷电机,PWM控制
 楼主| 发表于 2013-3-23 22:35:12 | 显示全部楼层
yun20 发表于 2013-3-23 20:36
版主速更啊

这几天忙着测试板子和学习opengl,看能不能在上位机加上3D显示,大家不要着急啊,有时间马上更新
发表于 2013-3-23 22:55:35 | 显示全部楼层
顶一个啊!
发表于 2013-3-23 22:57:32 来自手机 | 显示全部楼层
帮顶…
来自:amoBBS 阿莫电子论坛 Windows Phone 7 客户端
发表于 2013-3-24 08:55:32 | 显示全部楼层
强烈关注
发表于 2013-3-24 09:41:57 | 显示全部楼层
关注................
发表于 2013-3-24 11:03:02 | 显示全部楼层
犀利!数据很稳定!
发表于 2013-3-24 13:48:01 | 显示全部楼层
搬个板凳,站好位。。。。请教楼主一个问题,四元数解算时的误差是用PI修正的,可否加入卡尔曼滤波修正,我一直没想通怎么做
 楼主| 发表于 2013-3-24 16:31:54 来自手机 | 显示全部楼层
mazhenyu 发表于 2013-3-24 13:48
搬个板凳,站好位。。。。请教楼主一个问题,四元数解算时的误差是用PI修正的,可否加入卡尔曼滤波修正,我 ...

我也想加上呢,也是不懂,卡尔曼还没理解,数学不好……
发表于 2013-3-24 19:20:51 | 显示全部楼层
wangjt1988 发表于 2013-3-24 16:31
我也想加上呢,也是不懂,卡尔曼还没理解,数学不好……

哎,什么东西到高处都是数学呀,硬伤。。。最近毕设要用自抗扰控制,感觉比PID好多了,就是各种数学各种看不懂
 楼主| 发表于 2013-3-24 20:03:39 | 显示全部楼层
今天跟大家谈一谈6050的数据吧,首先,量程,
GYRO: ±250, ±500, ±1000, and ±2000°/sec (dps).    这是什么意思呢,就是陀螺数据在输出32767(也就是int16型数据的最大值)的时候,分别表示250度每秒一直到2000度每秒.
ACC: ±2g, ±4g, ±8g, and ±16g.  表示输出32767时表示2倍重力加速度一直到16倍重力加速度.
量程选的小,数据就准确一些(在量程范围内),但是在剧烈动作时,容易超调.
知道了量程和数据的意义,怎么把输出的数据转成角度想必就很简单了吧.
acc的数据出来后,进行一个移动平均值滤波,作用就是个低通滤波,gyro的数据换成角度,积分,就可以得到"姿态角",这里直接得到的姿态角是不对的,要对三轴数据进行"解耦"---应该是这么叫,这个我就不太懂了,大家可以参考一下mwc的程序或者网上寻找教程.
得到了角度,定期用acc的角度来矫正陀螺的误差,就可以实现自稳这个功能了.
发表于 2013-3-24 20:10:50 | 显示全部楼层
给力,楼主继续加油!!!
发表于 2013-3-25 16:10:04 | 显示全部楼层
占楼,顶楼主
发表于 2013-3-26 12:35:17 | 显示全部楼层
顶呀,,第一次有人这样详细讲四轴,期待呀!!!
发表于 2013-3-26 21:30:09 | 显示全部楼层
再次顶楼主的伟大共享精神。。
发表于 2013-3-27 10:05:49 | 显示全部楼层
楼主现在程序有更新吗?
发表于 2013-3-27 14:44:54 来自手机 | 显示全部楼层
学习一下....
发表于 2013-3-28 08:04:13 | 显示全部楼层
加油     正在弄
发表于 2013-3-29 20:34:17 | 显示全部楼层
学习一下....
发表于 2013-3-30 20:50:36 | 显示全部楼层
楼主速更啊,期待
发表于 2013-3-30 22:24:01 | 显示全部楼层
坐等。。。
发表于 2013-3-31 00:13:25 | 显示全部楼层
感谢楼主的无私分享~~~
套件怎么弄到呢
 楼主| 发表于 2013-3-31 01:17:41 | 显示全部楼层
本帖最后由 wangjt1988 于 2013-3-31 01:20 编辑

这几天没有更新,专心学习了下3D,给上位机增加了3D模型显示

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x
发表于 2013-3-31 19:31:27 | 显示全部楼层
楼主能不能共享一下MDK版本的工程文件呢?
友情提示:标题不合格、重复发帖,将会被封锁ID。详情请参考:论坛通告:封锁ID、获得注册邀请码、恢复被封ID、投诉必读
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|阿莫电子论坛(原ourAVR/ourDEV) ( 粤ICP备09047143号 )

GMT+8, 2017-9-25 01:45

阿莫电子论坛, 原"中国电子开发网"

© 2004-2016 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

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