但是按键后,引脚没有pwm波形。。于是去掉中断函数中的延时,有波形输出。。
main.c 函数
#include "stm32f10x.h"
#include "stm32f10x_tim.h"
#include "stm32f10x_exti.h"
#include "main.h"
#include "misc.h"
extern void time_ini(void);
void TimingDelay_Decrement(void);
void Delay(__IO uint32_t nTime);
static __IO uint32_t TimingDelay;
void NVIC_Configuration(void);
unsigned char _it0=0,num=0;
unsigned int CCR2_Val1=800,CCR2_Val2=800;
/****************************************************************************
* 名 称:void RCC_Configuration(void)
* 功 能:系统时钟配置为72MHZ, 外设时钟配置
* 入口参数:无
* 出口参数:无
* 说 明:
* 调用方法:无
****************************************************************************/
void RCC_Configuration(void){
SystemInit();
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC
| RCC_APB2Periph_GPIOD| RCC_APB2Periph_GPIOE , ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1,ENABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
}
/****************************************************************************
* 名 称:int main(void)
* 功 能:主函数
* 入口参数:无
* 出口参数:无
* 说 明:
* 调用方法:无
****************************************************************************/
int main(void)
{
// unsigned char a=0;
RCC_Configuration();
NVIC_Configuration( );
GPIO_Configuration();
SysTick_Config(72000); //配置SYSTICK时钟节拍为1ms一次
while(1)
{
Delay(10);
GPIO_ResetBits(GPIOE,GPIO_Pin_11);
GPIO_SetBits( GPIOE,GPIO_Pin_10);
}
}
/****************************************************************************
* 名 称:void Delay(__IO uint32_t nTime)
* 功 能:定时延时程序 1ms为单位
****************************************************************************/
void Delay(__IO uint32_t nTime)
{
TimingDelay = nTime;
while(TimingDelay != 0);
}
/****************************************************************************
* 名 称:void TimingDelay_Decrement(void)
* 功 能:获取节拍程序
****************************************************************************/
void TimingDelay_Decrement(void)
{
if (TimingDelay != 0x00)
{
TimingDelay--;
}
}
/****************************************************************************
* 名 称:void NVIC_Configuration(void)
* 功 能:中断源配置
* 入口参数:无
* 出口参数:无
* 说 明:
* 调用方法:无
****************************************************************************/
void NVIC_Configuration(void)
{
NVIC_InitTypeDef NVIC_InitStructure;
EXTI_InitTypeDef EXTI_InitStructure;
/* Configure one bit for preemption priority */
/* 优先级组 说明了抢占优先级所用的位数,和子优先级所用的位数 在这里是1, 7 */
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
/* Enable the EXTI Interrupt */
NVIC_InitStructure.NVIC_IRQChannel =EXTI3_IRQn; //外部中断3
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //子优先级1
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
NVIC_Init(&NVIC_InitStructure);
NVIC_InitStructure.NVIC_IRQChannel = EXTI4_IRQn; //外部中断4
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //抢占优先级 0
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2; //子优先级2
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
NVIC_Init(&NVIC_InitStructure);
NVIC_InitStructure.NVIC_IRQChannel =EXTI9_5_IRQn; //外部中断9-5
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; //抢占优先级 1
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //子优先级1
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能
NVIC_Init(&NVIC_InitStructure);
//用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI1外部中断的输入源是PE3。
GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource3); //外部中断配置AFIO--ETXI3
//用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI2外部中断的输入源是PE4。
GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource4); //外部中断配置AFIO--ETXI4
//用于配置AFIO外部中断配置寄存器AFIO_EXTICR1,用于选择EXTI2外部中断的输入源是PE5。
GPIO_EXTILineConfig(GPIO_PortSourceGPIOE, GPIO_PinSource5); //外部中断配置AFIO--ETXI5
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource7); //障碍物中断
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource8);
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource10);
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource11);
GPIO_EXTILineConfig(GPIO_PortSourceGPIOC, GPIO_PinSource12);
EXTI_InitStructure.EXTI_Line = EXTI_Line3; //PE1 作为键盘K1 检测状态
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; //中断模式
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; //下降沿触发
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_Init(&EXTI_InitStructure);
EXTI_InitStructure.EXTI_Line = EXTI_Line4; //PE2 作为键盘K2 检测状态
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; //中断模式
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; //下降沿触发
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_Init(&EXTI_InitStructure);
EXTI_InitStructure.EXTI_Line = EXTI_Line5; //PE5作为键盘K3 检测状态
EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; //中断模式
EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Falling; //下降沿触发
EXTI_InitStructure.EXTI_LineCmd = ENABLE;
EXTI_Init(&EXTI_InitStructure);
/**************************************
**函数名称:obstacle_action()
**函数描述:对障碍物信号做出反应
**************************************/
void obstacle_action(void)
{
if(_it0==7) //检测到障碍物
{
_it0=0;
back( );
}
else if(_it0==8) //B2检测到障碍物
{
_it0=0;
back( );
}
else if(_it0==10) //A2和B2都没有检测到,A1检测到
{
_it0=0;
back( );
}
else if(_it0==11) //A3检测到
{
_it0=0;
back( );
turnleft( );
}
else if(_it0==12) //B1检测到
{
_it0=0;
back( );
} //结合左右碰触开关
}
void GPIO_Configuration(void) //GPIO口配置,实际用的是GPIO口的哪些引脚,打开即可
{
GPIO_InitTypeDef GPIO_InitStructure;
//配置E端口的输出引脚,PE9恒高,PE8/CA1输出脉冲(左轮),PE10(MOTOR)H-L,PE12(J142)PWM,PE11/KR(L)
GPIO_InitStructure.GPIO_Pin=( GPIO_Pin_8 |GPIO_Pin_12 |GPIO_Pin_13 | GPIO_Pin_14 );
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_Init(GPIOE, &GPIO_InitStructure);
//TIM1完全复用功能开启
GPIO_PinRemapConfig(GPIO_FullRemap_TIM1 , ENABLE);
GPIO_InitStructure.GPIO_Pin = (GPIO_Pin_7 |GPIO_Pin_10 |GPIO_Pin_9| GPIO_Pin_11);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOE, &GPIO_InitStructure);
GPIO_SetBits( GPIOE,GPIO_Pin_9);
GPIO_SetBits( GPIOE,GPIO_Pin_7);
//配置E端口的输入引脚,按键功能启动或者停止 PE3-5 /KEY1-3
GPIO_InitStructure.GPIO_Pin = (GPIO_Pin_3 |GPIO_Pin_4|GPIO_Pin_5 );
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;//上拉
GPIO_Init(GPIOE, &GPIO_InitStructure);
GPIO_SetBits( GPIOE,GPIO_Pin_3);
//配置B端口的输出引脚PB0复用为TIM3的通道3,右轮
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
//PB1 pin start configure and initialization
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
GPIO_SetBits( GPIOB,GPIO_Pin_1);
}
void turnleft(void) // 左转
{
CCR2_Val1=800;
CCR2_Val2=1400;
time_ini( );
}
void turnright(void) //右转
{
CCR2_Val1=1400;
CCR2_Val2=800 ;
time_ini( );
}
void go(void) // 前进
{
Delay(50);
time_ini( );
}
void back(void) // 后退
{
GPIO_InitTypeDef GPIO_InitStructure;
//PB0置0
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
GPIO_ResetBits( GPIOB,GPIO_Pin_1);
//PE9置0
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOE, &GPIO_InitStructure);
GPIO_ResetBits( GPIOE,GPIO_Pin_9);
Delay(50);
CCR2_Val1=1400;
CCR2_Val2=1400;
}
void stop(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
Delay(10);
TIM_Cmd(TIM3, DISABLE); // 关闭TIM3-CH3
PB0复用为TIM3的通道3
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOB, &GPIO_InitStructure);
GPIO_SetBits( GPIOB,GPIO_Pin_0);
PB9置高
TIM_Cmd(TIM1,DISABLE); //关闭TIM1-CH1
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOE, &GPIO_InitStructure);
GPIO_SetBits( GPIOE,GPIO_Pin_8);
}
void KEY_scan(void) //按键扫描
{
num=0;
if(_it0==1){ //按键按下标志
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0)
{ //KEY1/SW2
Delay(0xffff);
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0){ //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_3)==0);//是否松开按键
num=1; //键值1 为K1按下
goto n_exit;
}
}
}
else if(_it0==2){ //按键按下标志
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0){ //KEY2/SW3
Delay(0xffff);
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0){ //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_4)==0);//是否松开按键
num=2; //键值2 为K2按下
goto n_exit;
}
}
}
else if(_it0==3){ //按键按下标志
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0){ //K3/SW4
Delay(0xffff);
if(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0){ //按键消抖动
while(GPIO_ReadInputDataBit(GPIOE,GPIO_Pin_5)==0);//是否松开按键
num=3; //键值3 为K3按下
goto n_exit;
}
}
}
n_exit:;
_it0=0;
}
void KEY_start(void) //根据按键确定电机行走方向
{
if(num==1)
{
Delay(10);
go();
}
if(num==2)
{
Delay(10);
stop();
}
else
{
stop();
}
}
中断函数
void EXTI3_IRQHandler(void)
{
if(EXTI_GetITStatus(EXTI_Line3) != RESET) //判别是KEY1按下
{
_it0=1;
go(); //按键中断标志
EXTI_ClearITPendingBit(EXTI_Line3); //清除中断请求标志
}
}