求助 求大神帮忙
时间:10-02
整理:3721RD
点击:
#include <C8051F040.h>
#include <string.h>
#define T2RUN temppage=SFRPAGE;SFRPAGE=0x00;TR2=1;SFRPAGE=temppage
#define T4RUN temppage=SFRPAGE;SFRPAGE=0x02;TR4=1;SFRPAGE=temppage
#define T4STOP temppage=SFRPAGE;SFRPAGE=0x02;TR4=0;SFRPAGE=temppage
#define T2STOP temppage=SFRPAGE;SFRPAGE=0x00;TR2=0;SFRPAGE=temppage
typedef unsigned int uint;
typedef unsigned long ulong;
typedef unsigned char uchar;
float y;
uchar temppage;
uint Error,tempi,verror;
typedef struct PID{
uint setpoint; /*设定值*/
uint proportion; /*比例系数*/
uint integral; /*积分系数*/
uint derivative; /*微分系数 */
uint lasterror; /*前一拍误差*/
uint preerror; /*前两拍误差*/
}PID;
PID vPID;
union stu{
uint value;
uchar num[2];
}laser;
/* void PIDInit(PID *pp)
{
memset (pp,0,sizeof(pp));
}*/
void T2_ini(){
temppage=SFRPAGE;
SFRPAGE=0x00;
TMR2CN=0x02; //T2工作在计数状态 自动重载装置
TMR2CF=0x00;
TMR2H=0x00;
TMR2L=0x00;
RCAP2L=0x00;
RCAP2H=0x00;
SFRPAGE=temppage;
}
void T4_ini(){
temppage=SFRPAGE;
SFRPAGE=0x02;
TMR4H=(65536-2000)/256;
TMR4L=(65536-2000)%256;
TMR4CN=0x00;
TMR4CF=0x02; //采用系统时钟12分频
RCAP4L=0x3F;
RCAP4H=0xB0; //定时10ms
SFRPAGE=temppage;
EIE2|=0x04; //开启中断
SFRPAGE=temppage;
}
void pca0ini(){
SFRPAGE=0x00; //CEX0 为8位PWM输出模式,频率为
PCA0CPM0=0x42;
}
void PWM0_set(uchar low){
SFRPAGE=0x00;
PCA0CPH0=low; //设置占空比
}
void pcaini(){
SFRPAGE=0x00;
PCA0MD=0x00; //PCA采用系统时钟12分频,禁止PCA中断
PCA0CN=0x40; //启动PCA计数
}
void config(){
WDTCN=0x07;
WDTCN=0xde;
WDTCN=0xad;
SFRPAGE=0x0f; //交叉开关配置,TX0=P0.0,RX0=P0.1,CEX0=P0.2,CEX1=P0.3 CEX2=P0.4 CEX3=P0.4 CEX4=P1.0 CEX5=P1.1
XBR0=0x34;
XBR1=0x20; // T2=P1.3
XBR2=0x42; //跳过P0.5,P0.6 ,P0.7
XBR3=0x00;
SFRPAGE=0x0f;
P0MDOUT=0xff; //P0 P1 位推挽输出
P1MDOUT=0xff;
P2MDOUT=0xff;
P1MDIN=0xff;
//采用内部晶振1分频
SFRPAGE=0x0f;
CLKSEL=0x00;
OSCXCN=0x00;
OSCICN=0x83;
}
/*PID算法函数,返回误差增量*/
uint PIDcal(PID *pp,char thisError){
int pError,dError,iError;
int templ;
pError=thisError-pp->lasterror;
iError=thisError;
dError=thisError-2*(pp->lasterror)+pp->preerror;
templ=(pp->proportion)*pError+(pp->integral)*iError+(pp->derivative)*dError; /*增量计算*/
pp->preerror=pp->lasterror; /*存放误差用于下次运算*/
pp->lasterror=thisError;
return ((uint)(templ>>4));
}
/* void delay1ms(uint time){ //延时1 ms
uint i;
uint j;
for(i=0;i<time;i++)
for(j=0;j<300;j++);
}*/
void main(){
// PIDInit(&vPID);
vPID.preerror=0;
vPID.lasterror=0;
vPID.proportion=2.5; /*设置PID比例系数为*/
vPID.integral=2.5; /*设定PID积分系数 为*/
vPID.derivative=0.001; /*设定PID微分系数为*/
vPID.setpoint=30; /*根据实际情况设定*/
config();
pcaini();
pca0ini();
T4_ini();
T2_ini();
EA=1;
T2RUN;
T4RUN;
while(1){
}
}
void T4_rupt() interrupt 16
{
xdata uchar lowset; /*误差增量*/
TF4=0;
T2STOP;
temppage=SFRPAGE;
SFRPAGE=0x00;
y=(TMR2H*256+TMR2L)*6;
TMR2H=0x00;
TMR2L=0x00;
SFRPAGE=temppage;
verror=(int)y; /*得到T4的计数值 */
Error=(vPID.setpoint)-verror; /*得到误差值*/
tempi=PIDcal(&vPID,Error); /*调用PID算法函数 得到误差增量*/
laser.value+=tempi;
if(laser.value>=255)
laser.value =255;
else if(laser.value<=20)
laser.value=22;
else
laser.value=laser.value;
lowset=255-laser.value;
PWM0_set(lowset);
T2RUN;
}
大神帮忙看看这是产生Pwm波的吗 是的话在哪里可以更改初始占空比 2607386161QQ联系 谢谢 紧急情况 是C8051F040单片机
#include <string.h>
#define T2RUN temppage=SFRPAGE;SFRPAGE=0x00;TR2=1;SFRPAGE=temppage
#define T4RUN temppage=SFRPAGE;SFRPAGE=0x02;TR4=1;SFRPAGE=temppage
#define T4STOP temppage=SFRPAGE;SFRPAGE=0x02;TR4=0;SFRPAGE=temppage
#define T2STOP temppage=SFRPAGE;SFRPAGE=0x00;TR2=0;SFRPAGE=temppage
typedef unsigned int uint;
typedef unsigned long ulong;
typedef unsigned char uchar;
float y;
uchar temppage;
uint Error,tempi,verror;
typedef struct PID{
uint setpoint; /*设定值*/
uint proportion; /*比例系数*/
uint integral; /*积分系数*/
uint derivative; /*微分系数 */
uint lasterror; /*前一拍误差*/
uint preerror; /*前两拍误差*/
}PID;
PID vPID;
union stu{
uint value;
uchar num[2];
}laser;
/* void PIDInit(PID *pp)
{
memset (pp,0,sizeof(pp));
}*/
void T2_ini(){
temppage=SFRPAGE;
SFRPAGE=0x00;
TMR2CN=0x02; //T2工作在计数状态 自动重载装置
TMR2CF=0x00;
TMR2H=0x00;
TMR2L=0x00;
RCAP2L=0x00;
RCAP2H=0x00;
SFRPAGE=temppage;
}
void T4_ini(){
temppage=SFRPAGE;
SFRPAGE=0x02;
TMR4H=(65536-2000)/256;
TMR4L=(65536-2000)%256;
TMR4CN=0x00;
TMR4CF=0x02; //采用系统时钟12分频
RCAP4L=0x3F;
RCAP4H=0xB0; //定时10ms
SFRPAGE=temppage;
EIE2|=0x04; //开启中断
SFRPAGE=temppage;
}
void pca0ini(){
SFRPAGE=0x00; //CEX0 为8位PWM输出模式,频率为
PCA0CPM0=0x42;
}
void PWM0_set(uchar low){
SFRPAGE=0x00;
PCA0CPH0=low; //设置占空比
}
void pcaini(){
SFRPAGE=0x00;
PCA0MD=0x00; //PCA采用系统时钟12分频,禁止PCA中断
PCA0CN=0x40; //启动PCA计数
}
void config(){
WDTCN=0x07;
WDTCN=0xde;
WDTCN=0xad;
SFRPAGE=0x0f; //交叉开关配置,TX0=P0.0,RX0=P0.1,CEX0=P0.2,CEX1=P0.3 CEX2=P0.4 CEX3=P0.4 CEX4=P1.0 CEX5=P1.1
XBR0=0x34;
XBR1=0x20; // T2=P1.3
XBR2=0x42; //跳过P0.5,P0.6 ,P0.7
XBR3=0x00;
SFRPAGE=0x0f;
P0MDOUT=0xff; //P0 P1 位推挽输出
P1MDOUT=0xff;
P2MDOUT=0xff;
P1MDIN=0xff;
//采用内部晶振1分频
SFRPAGE=0x0f;
CLKSEL=0x00;
OSCXCN=0x00;
OSCICN=0x83;
}
/*PID算法函数,返回误差增量*/
uint PIDcal(PID *pp,char thisError){
int pError,dError,iError;
int templ;
pError=thisError-pp->lasterror;
iError=thisError;
dError=thisError-2*(pp->lasterror)+pp->preerror;
templ=(pp->proportion)*pError+(pp->integral)*iError+(pp->derivative)*dError; /*增量计算*/
pp->preerror=pp->lasterror; /*存放误差用于下次运算*/
pp->lasterror=thisError;
return ((uint)(templ>>4));
}
/* void delay1ms(uint time){ //延时1 ms
uint i;
uint j;
for(i=0;i<time;i++)
for(j=0;j<300;j++);
}*/
void main(){
// PIDInit(&vPID);
vPID.preerror=0;
vPID.lasterror=0;
vPID.proportion=2.5; /*设置PID比例系数为*/
vPID.integral=2.5; /*设定PID积分系数 为*/
vPID.derivative=0.001; /*设定PID微分系数为*/
vPID.setpoint=30; /*根据实际情况设定*/
config();
pcaini();
pca0ini();
T4_ini();
T2_ini();
EA=1;
T2RUN;
T4RUN;
while(1){
}
}
void T4_rupt() interrupt 16
{
xdata uchar lowset; /*误差增量*/
TF4=0;
T2STOP;
temppage=SFRPAGE;
SFRPAGE=0x00;
y=(TMR2H*256+TMR2L)*6;
TMR2H=0x00;
TMR2L=0x00;
SFRPAGE=temppage;
verror=(int)y; /*得到T4的计数值 */
Error=(vPID.setpoint)-verror; /*得到误差值*/
tempi=PIDcal(&vPID,Error); /*调用PID算法函数 得到误差增量*/
laser.value+=tempi;
if(laser.value>=255)
laser.value =255;
else if(laser.value<=20)
laser.value=22;
else
laser.value=laser.value;
lowset=255-laser.value;
PWM0_set(lowset);
T2RUN;
}
大神帮忙看看这是产生Pwm波的吗 是的话在哪里可以更改初始占空比 2607386161QQ联系 谢谢 紧急情况 是C8051F040单片机