使用的是伺服驱动X2口的RS232通讯
主要是读取伺服电机的单圈绝对值数据。(PS:多圈绝对值需要进行初始清零,和配置带电池的线,掉电时不能随便转动电机,所以是伪绝对式)。
初始设定:
伺服驱动的Pr5.29参数设定为2(默认,9600波特率)
伺服驱动的Pr5.31参数设定为1(默认,轴的编号为1)
通讯协议为:
其中的h表示16进制
其中③中的数据(注意是16进制)为:00 01 D2 2D
数据块结构示意
那么③中的00表示命令字节数为0,01表示轴的编号,D2表示查询编码器状态,2D表示校验位。
⑦数据块返回的结构为:
以接受到的情况为例,⑦数据块具体为:0B 01 D2 0B A7 C1 14 9B 71 57 FE FF 00 00 3B
其中的9B 71 57是我们需要的编码器单圈绝对值位置数值。
接线情况:
其中蓝线接到伺服驱动的RX232口,棕色接到伺服驱动TX232口。黑色接地。
与电脑串口测试:
设置如下:
注意关闭了发送新行。
1、发送05,返回04,若超过10秒没有发送00 01 d2 2d,返回15(16进制)错误码。若下一步发送错误指令,立刻返回15(16进制)错误码。
2、发送00 01 d2 2d,返回 06 05,若超过10秒没有发送04,返回05错误码。若下一步输出指令为其他,比如05,则可以重新跳到相应指令(跳回1)。
3、发送04,返回0B 01 D2 0B A7 C1 14 B0 46 5D FE FF 00 00 4B,若超过10秒没有进行发送06,返回05错误码。若下一步输出指令为其他,比如05,则可以重新跳到相应指令(跳回1)。
与STM32通讯:
电路原理图
程序如下,选的是STM32F103ZET6的串口5(其他串口类似,基本上把UART5改为USARTX或UART4就行了):
u8 UART5_RX_BUF[20];
u8 U5_i;
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时钟
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; //复用推挽输出
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=1;//抢占优先级1
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //子优先级3
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能
NVIC_Init(&NVIC_InitStructure); //根据指定的参数初始化VIC寄存器
//USART 初始化设置
USART_InitStructure.USART_BaudRate = bound;//串口波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b;//字长为8位数据格式
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_Rx | USART_Mode_Tx; //收发模式
USART_Init(UART5, &USART_InitStructure); //初始化串口5
USART_ITConfig(UART5, USART_IT_RXNE, ENABLE);//开启串口接受中断
USART_Cmd(UART5, ENABLE); //使能串口5
}
void UART5_SendByte(u8 k)
{
USART_SendData(UART5, k);//从串口5发送数据
while(USART_GetFlagStatus(UART5,USART_FLAG_TC)!=SET);//等待发送结束
}
//串口中断,把通讯时伺服返回的数据都存入UART5_RX_BUF数组中
void UART5_IRQHandler(void)
{
u8 Res;
if(USART_GetITStatus(UART5, USART_IT_RXNE) != RESET) //接收中断
{
Res =USART_ReceiveData(UART5);//(UART5->DR); //读取接收到的数据
UART5_RX_BUF[U5_i]=Res;
U5_i++;
if(U5_i>20)
{U5_i=0;}
}
}
u32 Get_Posititon(void)//说明手册等待时间须2ms以上
{
U5_i=0;
UART5_SendByte(0x05);
delay_ms(3);
UART5_SendByte(0x00);
UART5_SendByte(0x01);
UART5_SendByte(0xD2);
UART5_SendByte(0x2D);
delay_ms(3);
UART5_SendByte(0x04);
delay_ms(3);
UART5_SendByte(0x06);
position=(u32)(UART5_RX_BUF[10]+UART5_RX_BUF[11]*0x100+UART5_RX_BUF[12]*0x10000);//单圈绝对值数据
if((UART5_RX_BUF[0]!=0x04)|(UART5_RX_BUF[1]!=0x06)|(UART5_RX_BUF[2]!=0x05)|(UART5_RX_BUF[3]!=0x0B))
{
position = 0x00800000;//错误返回
}
U5_i=0;
return position;
}
各种编码器原理:增量值编码器、单圈绝对值编码器、多圈绝对值编码器