当前位置: 首页 > news >正文

STM32 使用IQmath实现SVPWM 正弦波无刷电机控制

         带有浮点运算的MCU在市场上已经越来越多了,但是便宜好开发的却没有。可不可以使用我们常用的ST的103系列的MCU来做一个svpwm的控制器呢?当然是可以了,但是直接使用不太行,因为M3内核的MCU不具备浮点运算功能,F4系列的具有浮点运算功能,可惜价格不便宜,假货还挺多。在这里介绍一下TI的浮点运算库,IQmath。以及如何应用在SVPWM无刷电机控制,充分降低控制器的成本。

IQmath优势:

        用于定点处理器的数学函数库,加快了计算浮点值的速度。

提供Sin,cos,tan,arcsin,arccos,sqrt,fractional mpy,dv等的计算

在以下应用领域可以提高处理速度:

        电机控制

        伺服控制

        音频/图像编码和解码

        定点Q数学

        图形旋转 :根据应用要求调节分辨率

        指定GLOBAL_Q24:可在定点和浮点器件之间实现代码的无缝兼容性。

我们这里主要是对电机控制的应用,下面我们一起看一下程序。

 case Ready:
         Offset_CurrentReading();     //读取偏移量
         if(AdcValue.OffestFlag ==1 && Keynob == KeyStart)
         {     
           if(Controdmode == Hallloop)
           {
             mcState = Start;
						 IqStartSet = IqStart;
           }
           else 
           {
             mcState = Align;
           }
         }    
      break;

程序中我们在判断控制模式是否为hallloop,紧接着是状态赋值,IqstartSet = Iqstart;

 电机的状态定义了一个enum

typedef enum
{
  Ready,
  Align,
  Start,
  Run,
  Stop,
}McStateTypedef;

IQstart宏定义一个启动电流,调用__IQ().

#define IqStart        _IQ(0.28); //启动电流

在整个控制的过程中主要使用了__IQ(),没有调用其他的函数,下面我们看一下完成的控制部分代码

void MC_Control(void)
{ 
  switch(mcState)
  { 
    case Ready:
         Offset_CurrentReading();     //读取偏移量
         if(AdcValue.OffestFlag ==1 && Keynob == KeyStart)
         {     
           if(Controdmode == Hallloop)
           {
             mcState = Start;
						 IqStartSet = IqStart;
           }
           else 
           {
             mcState = Align;
           }
         }    
      break;
    
    case Align:
         Motor_Align();
         if(TimeStateCount == 0)
         { 
           mcState = Start;   
         }
                  
      break;
    case Start:
         if(Controdmode == Openloop)
         {
              mcState = Run; 
              Angle.Acc_a = _IQ(0.005); //加速度
              Angle.Setp_Max = 50;// 匀速度	          
					    
					 
         }
         else if(Controdmode == Hallloop)
         {  
						if(StateFlag.HallStartSetFlag ==0)
						{
							StateFlag.HallStartSetFlag = 1;
							HallStartAngle();
							Angle.Acc_a = _IQ(0.005); //加速度
							Angle.Setp_Max = 60;// 匀速度	
							Angle.Temp = Hall_Three.ele_angleIQ;
							TimeStateCount = 5000;
						}
						HallStart();
						
            ThreeHallanglecale();//得到角度

						if(TimeStateCount == 0)
						{
						 mcState = Run;     
						}							     
         }
         else if(Controdmode == SMOloop)
         {   
            if(StateFlag.StartSetFlag == 0)
            {
              StateFlag.StartSetFlag =1;
              TimeStateCount = 5000;
						  Angle.Acc_a = _IQ(0.005); //加速度
              Angle.Setp_Max = 55;// 匀速度
							IqStartSet = IqStart;
						}
						  Motor_IFStart();  
            if(TimeStateCount == 0)
            { 
               mcState = Run;
            }            
         }
      break;
    
    case Run:
         if(Controdmode == Openloop)
         {
              Motor_Open(); 
					    ThreeHallanglecale();//得到角度

         }
         else if(Controdmode == Hallloop)
         { 
              Mode_Hall_loop();    
         }
         else if(Controdmode == SMOloop)
         {
              SMO_SpeedLoop();
         }
      break;
    case Stop: 
         StopMotor();
		     if(Keynob == KeyStart)
					{
					  mcState = Ready;
						StateFlag.AlignSetFlag =0;
						StateFlag.StartSetFlag = 0 ;
						TimeStateCount = 0;
						Hall_Three.OldHall_State = 0;
						PWMZD_count = 0;
						Hall_Three.Speed_RPM = 0;
						Hall_Three.old_ele_angleIQ = 0;
						StateFlag.HallStartSetFlag = 0;
					}
      break;
  }

从实验现象来看,电机转动的还是很流畅。

ky_motor Foc 测试视频

实验开发板:开发板

相关文章:

  • Openstack的安装部署教程
  • 密码学_AES加密算法
  • 个人博客系统(前后端分离)
  • Linux常用基本指令详解
  • Linux c编程之静态库与动态库
  • 【消息中间件】RocketMQ如何实现Producer的负载均衡
  • 阳了在家没事干?教大家用python在家做一个万能看视频软件,绝对正经啦~
  • Footprint Analytics 如何帮助区块链研究人员进行数据研究
  • 代码质量管理平台实战| SonarQube 安装、配置及 JaCoCo、Maven 集成
  • 黑马Hive+Spark离线数仓工业项目--数仓事实层DWB层构建(2)
  • VIAVI唯亚威光纤高分辨率多模 OTDR 测试方案
  • rust program英文和汉语混合笔记(4)
  • Attention:何为注意力机制?
  • 高级网络复习——防火墙,OSPF协议,rip协议,三层,DHCP中继知识题解(带答案)
  • 【BF算法】
  • httpie使用详解
  • JavaScript中的对象个人分享
  • Java的Interrupt与线程中断
  • LeetCode刷题——29. Divide Two Integers(Part 1靠自己)
  • LintCode 31. partitionArray 数组划分
  • mysql 5.6 原生Online DDL解析
  • PAT A1050
  • thinkphp5.1 easywechat4 微信第三方开放平台
  • Twitter赢在开放,三年创造奇迹
  • 阿里云前端周刊 - 第 26 期
  • 包装类对象
  • 服务器之间,相同帐号,实现免密钥登录
  • 关于Flux,Vuex,Redux的思考
  • 那些被忽略的 JavaScript 数组方法细节
  • 前端自动化解决方案
  • 容器化应用: 在阿里云搭建多节点 Openshift 集群
  • 设计模式(12)迭代器模式(讲解+应用)
  • 优化 Vue 项目编译文件大小
  • 找一份好的前端工作,起点很重要
  • ​如何使用ArcGIS Pro制作渐变河流效果
  • ###C语言程序设计-----C语言学习(3)#
  • #mysql 8.0 踩坑日记
  • #pragma data_seg 共享数据区(转)
  • #我与Java虚拟机的故事#连载19:等我技术变强了,我会去看你的 ​
  • (day 12)JavaScript学习笔记(数组3)
  • (DFS + 剪枝)【洛谷P1731】 [NOI1999] 生日蛋糕
  • (分布式缓存)Redis分片集群
  • (附源码)spring boot网络空间安全实验教学示范中心网站 毕业设计 111454
  • (考研湖科大教书匠计算机网络)第一章概述-第五节1:计算机网络体系结构之分层思想和举例
  • (强烈推荐)移动端音视频从零到上手(上)
  • (十三)Flask之特殊装饰器详解
  • (十三)Java springcloud B2B2C o2o多用户商城 springcloud架构 - SSO单点登录之OAuth2.0 根据token获取用户信息(4)...
  • (一) storm的集群安装与配置
  • (转)c++ std::pair 与 std::make
  • **PHP二维数组遍历时同时赋值
  • .Net 代码性能 - (1)
  • .NET 中使用 Mutex 进行跨越进程边界的同步
  • .NET 自定义中间件 判断是否存在 AllowAnonymousAttribute 特性 来判断是否需要身份验证
  • .netcore如何运行环境安装到Linux服务器
  • //解决validator验证插件多个name相同只验证第一的问题