[STM32+HAL]DengFOC移植之闭环位置控制

news2024/11/26 2:11:01

一、源码来源

DengFOC官方文档

二、HAL库配置

1、开启硬件IIC低速模式

低速更稳定

2、PWM波开启

三、keil填写代码

1、AS5600读取编码器数值
#include "AS5600.h"
#include "math.h"


float angle_prev=0;
int full_rotations=0; 		// full rotation tracking;
float angle_d;				//GetAngle_Without_Track()的返回值
float angle_cd;				//GetAngle()的返回值


//IIC读多字节
void AS5600_Read_Reg(uint16_t reg, uint8_t* buf, uint8_t len)
{
	HAL_I2C_Mem_Read(&hi2c1, AS5600_ADDRESS, reg, I2C_MEMADD_SIZE_8BIT, buf, len, 100);
}



//得到弧度制的角度,范围在0-6.28
float GetAngle_Without_Track(void)
{
	int16_t in_angle;
	uint8_t temp[DATA_SIZE]={0};
	AS5600_Read_Reg( Angle_Hight_Register_Addr, temp, DATA_SIZE);
	in_angle = ((int16_t)temp[0] <<8) | (temp[1]);

	angle_d = (float)in_angle * (2.0f*PI) / 4096;
//angle_d为弧度制,范围在0-6.28
	return angle_d;
}



//得到弧度制的带圈数角度
float GetAngle(void)
{
    float val = angle_d;
    float d_angle = val - angle_prev;
    //计算旋转的总圈数
    //通过判断角度变化是否大于80%的一圈(0.8f*6.28318530718f)来判断是否发生了溢出,如果发生了,则将full_rotations增加1(如果d_angle小于0)或减少1(如果d_angle大于0)。
    if(fabs(d_angle) > (0.8f*2.0f*PI) ) full_rotations += ( d_angle > 0 ) ? -1 : 1;
    angle_prev = val;

	angle_cd = full_rotations * (2.0f*PI) + angle_prev;
	return angle_cd;
}



void Track(void)
{
	GetAngle_Without_Track();
	GetAngle();
}

2、闭环FOC控制
#include "AS5600.h"
#include "FOC1.h"
#include <math.h>


#define PWMA TIM1 -> CCR1
#define PWMB TIM1 -> CCR2
#define PWMC TIM1 -> CCR3
#define CNT  TIM1 -> ARR-1


float voltage_limit=12.6;
float voltage_power_supply=12.6;
float shaft_angle=0,open_loop_timestamp=0;
float zero_electric_angle=0,Ualpha,Ubeta=0,Ua=0,Ub=0,Uc=0,dc_a=0,dc_b=0,dc_c=0;
int PP=7,DIR=-1;


float _electricalAngle(void){
  return  _normalizeAngle((float)(DIR *  PP) * GetAngle_Without_Track()-zero_electric_angle);
}


// 归一化角度到 [0,2PI]
float _normalizeAngle(float angle){
  float a = fmod(angle, 2*PI);   //取余运算可以用于归一化,列出特殊值例子算便知
  return a >= 0 ? a : (a + 2*PI);
}


// 设置PWM到控制器输出
void setPwm(float Ua, float Ub, float Uc) {

  // 限制上限
  Ua = _constrain(Ua, 0.0f, voltage_limit);
  Ub = _constrain(Ub, 0.0f, voltage_limit);
  Uc = _constrain(Uc, 0.0f, voltage_limit);
  // 计算占空比
  // 限制占空比从0到1
  dc_a = _constrain(Ua / voltage_power_supply, 0.0f , 1.0f );
  dc_b = _constrain(Ub / voltage_power_supply, 0.0f , 1.0f );
  dc_c = _constrain(Uc / voltage_power_supply, 0.0f , 1.0f );

  //写入PWM到PWM 0 1 2 通道
	PWMA = dc_a*5599;
	PWMB = dc_b*5599;
	PWMC = dc_c*5599;
}

void setPhaseVoltage(float Uq,float Ud, float angle_el) {
  angle_el = _normalizeAngle(angle_el);
  // 帕克逆变换
  Ualpha =  -Uq*sin(angle_el);
  Ubeta =   Uq*cos(angle_el);

  // 克拉克逆变换
  Ua = Ualpha + voltage_power_supply/2;
  Ub = (sqrt(3)*Ubeta-Ualpha)/2 + voltage_power_supply/2;
  Uc = (-Ualpha-sqrt(3)*Ubeta)/2 + voltage_power_supply/2;
  setPwm(Ua,Ub,Uc);
}



//初始化FOC,校准零点
void FOC_Init(void)
{
	setPhaseVoltage(3, 0,_3PI_2);
	HAL_Delay(1000);
	zero_electric_angle=_electricalAngle();
	setPhaseVoltage(0, 0,_3PI_2);
}

3、main.c
/* USER CODE BEGIN PV */
extern float voltage_limit;
extern float voltage_power_supply;
extern float shaft_angle,open_loop_timestamp;
extern float zero_electric_angle,Ualpha,Ubeta,Ua,Ub,Uc,dc_a,dc_b,dc_c;
extern int PP,DIR;

float motor_target = 4;
/* USER CODE END PV */  


/* USER CODE BEGIN 2 */
	printf("Hello World\r\n");
	HAL_Delay(500);

	HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_1);
	HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_2);
	HAL_TIM_PWM_Start(&htim1,TIM_CHANNEL_3);
	
	FOC_Init();
	HAL_TIM_Base_Start_IT(&htim2);
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
		float Sensor_Angle=GetAngle();
		float Kp=0.133;
		setPhaseVoltage(_constrain(Kp*(motor_target-DIR*Sensor_Angle)*180/PI,-6,6),0,_electricalAngle());
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  }
  /* USER CODE END 3 */

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1587798.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Day37|贪心算法part06:738.单调递增的数字、968. 监控二叉树、贪心总结

738. 单调递增的数字 总体思想就是从后往前遍历&#xff0c;比较第i位和第i1位的大小&#xff0c;不符合顺序char[i]减1&#xff0c;i1位填9&#xff0c;找到需要填9的最先位置&#xff0c;然后填9。 class Solution {public int monotoneIncreasingDigits(int n) {String s …

负荷预测 | Matlab基于TCN-BiGRU-Attention单输入单输出时间序列多步预测

目录 效果一览基本介绍程序设计参考资料 效果一览 基本介绍 1.Matlab基于TCN-BiGRU-Attention单输入单输出时间序列多步预测&#xff1b; 2.单变量时间序列数据集&#xff0c;采用前12个时刻预测未来96个时刻的数据&#xff1b; 3.excel数据方便替换&#xff0c;运行环境matlab…

领域驱动设计(DDD)学习心得

领域驱动设计&#xff08;DDD&#xff09; 领域驱动设计是一种用于复杂软件系统的软件开发方法论。它强调与软件所服务的业务领域的专家紧密合作&#xff0c;通过深入理解业务领域的复杂性&#xff0c;来构建能够反映业务逻辑的领域模型。DDD的核心思想包括以下几点&#xff1…

你会写SAP技术规格说明书(Specification)吗

有些小伙伴可能还在发愁技术规则说明书应该写什么&#xff0c;做了张思维导图&#xff0c;包含了所有RICEFW。 R - Report - 报表 I - Interface - 接口 C - Conversion - 数据转换 E - Enhancement - 增强 F - Form - 表单 W - Workflow - 工作流

深度学习基础之一:机器学习

文章目录 深度学习基本概念(Basic concepts of deep learning)机器学习典型任务机器学习分类 模型训练的基本概念基本名词机器学习任务流程模型训练详细流程正、反向传播学习率Batch size激活函数激活函数 sigmoid激活函数 softmax & tanh(双曲正切)激活函数 ReLU激活函数 …

深耕国际舞台丨拓数派受邀参与美国 Postgres Conference 2024

在北美地区备受瞩目 Postgres Conference 2024 大会将于4月17日在美国 San Jose 希尔顿举行。拓数派作为立足中国的高科技创新企业&#xff0c;也同时致力于国际开源技术和生态的深耕。本次美国 Postgres Conference 2024 大会中&#xff0c;拓数派将作为黄金赞助商&#xff0c…

Qt | 信号与槽 原理、连接、断开(面试无忧)

1、信号和槽是用于对象之间的通信的,这是 Qt 的核心。为此 Qt 引入了一些关键字,他们是slots、signals、emit,这些都不是 C++关键字,是 Qt 特有的,这些关键字会被 Qt 的 moc转换为标准的 C++语句。 2、Qt 的部件类中有一些已经定义好了的信号和槽,通常的作法是子类化部件…

Vue 工程化开发入门

目录 1. 工程化开发 1.1. 工程化开发模式介绍 1.2. 工程化开发模式下出现的问题&#xff1a; 1.3. 工程化开发模式下出现的问题的解决方法 2. 脚手架Vue CLI 2.1. 脚手架Vue CLI 基本介绍 2.2. 脚手架Vue CLI 的好处 2.3. 脚手架Vue CLI 的使用步骤 2.4. 脚手架目录文…

从大量数据到大数据,King’s SDMS仪器数据采集及科学数据管理系统的应用

对于实验室或检测机构&#xff0c;仪器设备是所有业务开展的基础&#xff0c;数据则是核心命脉&#xff0c;而传统的仪器设备原始数据收集方式&#xff0c;效率低耗时长、操作流程不规范、不易保存与查找、错误率高、易篡改等成了制约检测机构持续高速发展的瓶颈和弊端&#xf…

在线课程平台LearnDash评测 – 最佳 WordPress LMS插件

在我的LearnDash评测中&#xff0c;我探索了流行的 WordPress LMS 插件&#xff0c;该插件以其用户友好的拖放课程构建器而闻名。我深入研究了各种功能&#xff0c;包括课程创建、测验、作业、滴灌内容、焦点模式、报告、分析和管理工具。 我的评测还讨论了套餐和定价选项&…

初学网络编程

网络编程是指编写能够在网络环境中运行&#xff0c;进行数据通信的程序的过程。它涵盖了从建立网络连接、发送和接收数据&#xff0c;到关闭连接等一系列操作。网络编程是开发网络应用程序的基础&#xff0c;它使得不同的计算机和设备能够通过网络进行数据交换和通信。 三个核…

Imagination APXM-6200 CPU:性能卓越,安全可信

随着消费类和工业应用行业的不断发展&#xff0c;对创新性能和效率的需求永不停歇&#xff0c;我们自豪地推出旗下 Catapult CPU 系列的第二款产品&#xff1a;Imagination APXM-6200 CPU 。这款 64 位的高效 RISC-V 应用处理器具有强大的 AI 功能及性能密度&#xff0c;能够为…

前端处理model.addtribute传来的值

比如开始时间和结束时间&#xff0c;后端传来的样式为 model.addAttribute("startDate", startDate); model.addAttribute("endDate", endDate); 前端接收为 [[${startDate}]]-[[${endDate}]] 如果前端为地图类型的echarts <script>var sitepvs …

B站大数据平台元数据业务分享

背景介绍 元数据是数据平台的衍生数据&#xff0c;比如调度任务信息&#xff0c;离线hive表&#xff0c;实时topic&#xff0c;字段信息&#xff0c;存储信息&#xff0c;质量信息&#xff0c;热度信息等。在数据平台建设初期&#xff0c;这类数据主要散落于各种平台子系统的数…

Android - 安卓概述

什么是安卓? Android 是一种基于 Linux 的开源操作系统&#xff0c;适用于智能手机和平板电脑等移动设备。 Android 是由 Google 和其他公司领导的 Open Handset Alliance 开发的。 Android 为移动设备的应用程序开发提供了统一的方法&#xff0c;这意味着开发人员只需为 And…

OpenAI允许前员工售股,估值达860亿美元

&#x1f989; AI新闻 &#x1f680; OpenAI允许前员工售股&#xff0c;估值达860亿美元 摘要&#xff1a;OpenAI最近向他们的部分前员工开放了股份出售的机会&#xff0c;此举是基于公司860亿美元估值的要约收购的一部分&#xff0c;由Thrive Capital领投。此前&#xff0c;…

第十届蓝桥杯省赛真题(C/C++大学B组)

试题 A: 组队 答案&#xff1a;490 试题 B: 年号字串 #include <bits/stdc.h> using namespace std;int main() {//26进制数 int n;cin>>n;string s "111";for(int i s.length() - 1;i >0;i--){s[i] A - 1 n % 26;n / 26;}cout<<s<<…

解决在Mac上的SourceTree中导入的项目拉取提交代码时总是弹出要输入登陆钥匙串问题

解决方案 复制以下代码到终端上执行一下&#xff1a; git config --global credential.helper osxkeychain 执行完成后&#xff0c;会跳出钥匙串的对话框此处填写的是电脑开机密码&#xff0c;并且勾选始终允许&#xff0c;否则&#xff0c;还是要一直跳出现在的这个登陆窗口…

【Linux系统编程】第一弹---背景介绍

✨个人主页&#xff1a; 熬夜学编程的小林 &#x1f497;系列专栏&#xff1a; 【C语言详解】 【数据结构详解】【C详解】【Linux系统编程】 目录 1、Linux 背景介绍 1.1、发展史 1.1.1、UNIX发展的历史 1.1.2、Linux发展历史 2、开源精神 3、Linux内核官网 4、企业应用…

SQL Serve---查询

概要 1、order by子句 —默认asc&#xff08;升序&#xff09;、desc&#xff08;降序&#xff09; 2、distinct关键字 3、group by子句 4、聚合函数 —max()、min()、sum()、avg()、count() 5、having子句 6、compute子句 英文关键字 order by 排序 asc…