硬件修改
多圈絕對(duì)值功能需要用一個(gè)3.6V的電池接到伺服電機(jī)編碼器上來(lái)實(shí)現(xiàn)斷電保存多圈數(shù)據(jù)。電池淘寶地址(帶安裝座)


將電池的正負(fù)極接到編碼器接口的1、2端,正極和編碼器紅線對(duì)應(yīng),負(fù)極和編碼器桃色線對(duì)應(yīng)。

這里可能需要買(mǎi)金屬連接件進(jìn)行配合→淘寶地址
也可以直接把編碼器出線上的紅色桃色線剪斷,和電池電源線焊上。
清除多圈數(shù)據(jù)得到初始原點(diǎn):

把PR15的參數(shù)設(shè)置為0:

多圈絕對(duì)值通訊


STM32主要程序232通訊
u8 UART5_RX_BUF[20]; //接收緩沖,最大20個(gè)字節(jié),用于儲(chǔ)存編碼器位置信息
u8 U5_i=0;
struct _code
{
u32 code_value;//編碼器值
u32 cylinder_number;//圈數(shù)
u8 check_bit;//校驗(yàn)位
};
//編碼器通訊串口5初始化。伺服驅(qū)動(dòng)默認(rèn)是9600,可修改pr5.29改變
void SERVO_CODE_Init(u32 bound)
{
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC|RCC_APB2Periph_GPIOD, ENABLE); //使能UART5,GPIOC、GPIOD時(shí)鐘
RCC_APB1PeriphClockCmd(RCC_APB1Periph_UART5, ENABLE);
//UART5_TX GPIOC.12初始化
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12; //PC.12
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; //復(fù)用推挽輸出
GPIO_Init(GPIOC, &GPIO_InitStructure);//初始化GPIOC.12
//UART5_RX GPIOD.2初始化
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;//PD.2
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空輸入
GPIO_Init(GPIOD, &GPIO_InitStructure);//初始化GPIOD.2
//UART5 NVIC 配置
NVIC_InitStructure.NVIC_IRQChannel = UART5_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0;//搶占優(yōu)先級(jí)1
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; //子優(yōu)先級(jí)0
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能
NVIC_Init(&NVIC_InitStructure); //根據(jù)指定的參數(shù)初始化VIC寄存器
//USART 初始化設(shè)置
USART_InitStructure.USART_BaudRate = bound;//串口波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b;//字長(zhǎng)為8位數(shù)據(jù)格式
USART_InitStructure.USART_StopBits = USART_StopBits_1;//一個(gè)停止位
USART_InitStructure.USART_Parity = USART_Parity_No;//無(wú)奇偶校驗(yàn)位
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//無(wú)硬件數(shù)據(jù)流控制
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //收發(fā)模式
USART_Init(UART5, &USART_InitStructure); //初始化串口5
USART_ITConfig(UART5, USART_IT_RXNE, ENABLE);//開(kāi)啟串口接受中斷
USART_Cmd(UART5, ENABLE); //使能串口5
}
//從串口5發(fā)送一個(gè)字節(jié)的函數(shù)
void UART5_SendByte(u8 k)
{
USART_SendData(UART5, k);
while(USART_GetFlagStatus(UART5,USART_FLAG_TC)!=SET);//等待發(fā)送結(jié)束
}
//串口5中斷,把伺服編碼器的值返回到UART5_RX_BUF[]數(shù)組中
void UART5_IRQHandler(void)
{
u8 Res;
if(USART_GetITStatus(UART5, USART_IT_RXNE) != RESET) //接收中斷
{
Res =USART_ReceiveData(UART5);//(UART5->DR); //讀取接收到的數(shù)據(jù)
UART5_RX_BUF[U5_i]=Res;
U5_i++;
if(U5_i>=20)
{U5_i=0;}
}
}
//獲得圈數(shù)和編碼值
struct _code Get_Code(void)
{
struct _code CODE;
CODE.check_bit = 0;//校驗(yàn)位初始化
U5_i = 0;
UART5_SendByte(0x05);
nopdelay_ms(4);
UART5_SendByte(0x00);
UART5_SendByte(0x01);
UART5_SendByte(0xD2);
UART5_SendByte(0x2D);
nopdelay_ms(4);
UART5_SendByte(0x04);
nopdelay_ms(4);
UART5_SendByte(0x06);
//編碼值
CODE.code_value = (u32)(UART5_RX_BUF[10]+UART5_RX_BUF[11]*0x100+UART5_RX_BUF[12]*0x10000);//低位+中位*0x100+高位*0x10000
//圈數(shù)
CODE.cylinder_number = UART5_RX_BUF[13]+UART5_RX_BUF[14]*0x100;
if(CODE.cylinder_number <= 32767)
CODE.cylinder_number = CODE.cylinder_number + 65536;//32768~65535為負(fù),65536~98303為正,65536為原點(diǎn)
if((UART5_RX_BUF[0]!=0x04)|(UART5_RX_BUF[1]!=0x06)|(UART5_RX_BUF[2]!=0x05)|(UART5_RX_BUF[3]!=0x0B))
{
CODE.code_value = 0x00800000;//讀數(shù)失敗時(shí),返回8388608
CODE.check_bit = 1;//失敗
}
U5_i = 0;
return CODE;
}