手頭有帶轉向電機和動力電機小車底盤,買了很久一直在吃灰。
最近查了一下小車的驅動IC是富滿微的8D420L,是一款傳統的RX2接收解碼芯片,帶馬達驅動。
手頭沒有TX2發送芯片,所以考慮用MCU直接發送PWM直接接入RX2,可能可以驅動。
一、8D420L芯片
RX2芯片一般是通過天線接收TX2發送的無線信號,解碼后用自帶的馬達驅動電機,帶動小車運行。
本文將用Mini-F5265發送PWM信號直接驅動RX2芯片。8D420L應該是一款簡化版RX2芯片,因為一般的RX2芯片,3腳是編碼輸入引腳,可以PWM信號接入該腳做測試使用。8D420L沒有編碼輸入引腳,可以將PWM接入14腳VI1,這個引腳是天線接收引腳可以替代編碼輸入引腳。
下圖是一個一般的RX2芯片管腳圖:
二、編碼規則
需要發送2種PWM信號:
W1:頻率1khz,占空比 50%。
W2:頻率500hz,占空比75%。
W2是引導碼,一個引導碼要連續發4個PWM信號。
W1是功能碼,發送個數視功能而定。
舉例說明:
如果要小車前進:先發4個W2,再發10個W1;
如果要小車左轉:先發4個W2,再發58個W1;
三、硬件連接
如圖MM32F5260和接收板連接。
四、程序
1、利用TIM8初始化
void TIM1_8_Configure(void)
{GPIO_InitTypeDef GPIO_InitStruct;TIM_OCInitTypeDef TIM_OCInitStruct;TIM_TimeBaseInitTypeDef TIM_TimeBaseStruct;uint32_t Prescaler8;uint32_t TimerPeriod8 = 0, Channel1Pulse8 = 0;Prescaler8=TIM_GetTIMxClock(TIM8)/10000-1;RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM8, ENABLE);TIM_TimeBaseStructInit(&TIM_TimeBaseStruct);TIM_TimeBaseStruct.TIM_Prescaler = Prescaler8;TIM_TimeBaseStruct.TIM_CounterMode = TIM_CounterMode_Up;TIM_TimeBaseStruct.TIM_Period = TimerPeriod8;TIM_TimeBaseStruct.TIM_ClockDivision = TIM_CKD_Div1;TIM_TimeBaseStruct.TIM_RepetitionCounter = 0;TIM_TimeBaseInit(TIM8, &TIM_TimeBaseStruct);TIM_OCStructInit(&TIM_OCInitStruct);TIM_OCInitStruct.TIM_OCMode = TIM_OCMode_PWM1;TIM_OCInitStruct.TIM_OutputState = TIM_OutputState_Enable;TIM_OCInitStruct.TIM_Pulse = 0;TIM_OCInitStruct.TIM_OCPolarity = TIM_OCPolarity_High;TIM_OCInitStruct.TIM_OCIdleState = TIM_OCIdleState_Set;TIM_OCInitStruct.TIM_Pulse = Channel1Pulse8;TIM_OC1Init(TIM8, &TIM_OCInitStruct);RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOC, ENABLE);GPIO_PinAFConfig(GPIOC, GPIO_PinSource6, GPIO_AF_3); /* TIM8_CH1 */GPIO_StructInit(&GPIO_InitStruct);GPIO_InitStruct.GPIO_Pin = GPIO_Pin_6 ;GPIO_InitStruct.GPIO_Speed = GPIO_Speed_High;GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;GPIO_Init(GPIOC, &GPIO_InitStruct);TIM_Cmd(TIM8, ENABLE);//TIM_CtrlPWMOutputs(TIM8, ENABLE);}
2、發送W2信號
void send_W2(void)
{TIM_SetAutoreload(TIM8,19); //500HzTIM_SetCompare1(TIM8,16); //3/4占空比delay_ms(8); //4個W2
}
3、發送W1信號
void send_W1(uint8_t nW1)
{uint8_t i;TIM_SetAutoreload(TIM8,9); //1000HzTIM_SetCompare1(TIM8,5); //1/2占空比delay_ms(nW1);
}
4、發送前進指令
#define FORWARD_CMD 10
void forward(void)
{TIM_CtrlPWMOutputs(TIM8, ENABLE);send_W2();send_W1(FORWARD_CMD);TIM_CtrlPWMOutputs(TIM8, DISABLE);
}
5、發送左轉指令
#define LEFT_CMD 58
void left(void)
{TIM_CtrlPWMOutputs(TIM8, ENABLE);send_W2();send_W1(LEFT_CMD);TIM_CtrlPWMOutputs(TIM8, DISABLE);
}
6、主程序
void TIM1_8_PWM_Output_Sample(void)
{uint8_t i;printf("\r\nTest %s", __FUNCTION__);TIM1_8_Configure();EXTI_Configure();//先發一些pwm信號,讓子彈飛一會兒,算做8D420L初始化吧TIM_CtrlPWMOutputs(TIM8, ENABLE);send_W2();send_W1(100);send_W2();send_W1(STOP_CMD);TIM_CtrlPWMOutputs(TIM8, DISABLE);while (1){if(car_cmd_flag==FORWARD_CMD){printf("car_cmd_flag==1\r\n");for(i=0;i<20;i++) forward();car_cmd_flag=0;}if(car_cmd_flag==LEFT_CMD){ for(i=0;i<20;i++)left();car_cmd_flag=0;}delay_ms(200);}
}
7、外部中斷控制發送指令
void EXTI0_IRQHandler(void)
{/* KEY1 */if (SET == EXTI_GetITStatus(EXTI_Line0)){PLATFORM_LED_Toggle(LED1);car_cmd_flag=FORWARD_CMD;EXTI_ClearITPendingBit(EXTI_Line0);}
}void EXTI1_IRQHandler(void)
{/* KEY2 */if (SET == EXTI_GetITStatus(EXTI_Line1)){PLATFORM_LED_Toggle(LED2);car_cmd_flag=LEFT_CMD;EXTI_ClearITPendingBit(EXTI_Line1);}
}
五、效果
后記
Mini-F5265可以用重載、改變比較值、延時這幾個非常簡單語句就實現了對PWM周期、占空比的控制意見指定PWM個數的輸出,真是十分方便。也試圖在其他MCU用類似方法實現該功能都沒有成功。
TIM_SetAutoreload(TIM8,9); //1000HzTIM_SetCompare1(TIM8,5); //1/2占空比delay_ms(nW1);
RX2是遙控芯片,上面驅動失去了遙控的意義,只是利用RX2的馬達驅動。
如何進一步開發可以將遙控車改造成循跡小車,還可以加一個藍牙模塊,升級為藍牙驅動小車。
當然直接利用藍牙模塊二次開發驅動也可以,只是還要考慮如何發送指定PWM個數的問題。