#include <cvirte.h>
#include <userint.h>
#include "dianji.h"
#include "dask.h"
unsigned short date;
double out;
double biaozhun;
int zhuangtai;
int a,b;
int cardID;
int start=0;
unsigned short u;
double position;
int oe; //上一次偏差
int ec; //偏差的变化
int e; //偏差
//int piderror[10000];
double piderror1=0;
double piderror2=0;
double segmaerror=0;
int i;
int j;
double A=0;
double KP, KI,KD;
//double TI,TD;
double T=0.001; //T为定时器间隔
//int b;
double show[2];
int matrix[14][13]={
{7,6,7,6,7,7,7,4,4,2,0,0,0},
{6,6,6,6,6,6,6,4,4,2,0,0,0},
{7,6,7,6,7,7,7,4,4,2,0,0,0},
{7,6,6,6,6,6,6,3,2,0,-1,-1,-1},
{4,4,4,5,4,4,4,1,0,0,-1,-1,-1},
{4,4,4,5,4,4,1,0,0,0,-3,-2,-1},
{4,4,4,5,1,1,0,-1,-1,-1,-4,-4,-4},
{4,4,4,5,1,1,0,-1,-1,-1,-4,-4,-4},
{2,2,2,2,0,0,-1,-4,-4,-3,-4,-4,-4},
{1,2,1,2,0,-3,-4,-4,-4,-3,-4,-4,-4},
{0,0,0,0,-3,-3,-6,-6,-6,-6,-6,-6,-6},
{0,0,0,-2,-4,-4,-7,-7,-7,-6,-7,-6,-7},
{0,0,0,-2,-4,-4,-6,-6,-6,-6,-6,-6,-6},
{0,0,0,-2,-4,-4,-7,-7,-7,-6,-7,-6,-7}
};
double temp=0;
double fuzzy[7]={6.00,3.00,1.0,0.5,0.1,0.05,0.01};
static int panelHandle;
int main (int argc, char *argv[])
{
if (InitCVIRTE (0, argv, 0) == 0)
return -1; /* out of memory */
if ((panelHandle = LoadPanel (0, "dianji.uir", PANEL)) < 0)
return -1;
DisplayPanel (panelHandle);
RunUserInterface ();
DiscardPanel (panelHandle);
return 0;
}
int CVICALLBACK callbackstart (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
// if(cardID>=0)
// {
// Release_Card(cardID);
// }
cardID=Register_Card(PCI_9112,0);
if(cardID<0)
{
MessagePopup("warning","startfail");
}
AI_ReadChannel(cardID,0,AD_U_5_V,&date); //读AD转换结果
date=(date>>4)&0x0fff;
out=date*16/4096;
SetCtrlVal(panelHandle,PANEL_NUMERICSLIDE,out); //令游标NUMERICSLIDE显示测量值
AO_WriteChannel(cardID,0,2048); //DA转换
start=1;
zhuangtai=4;
break;
}
return 0;
}
int CVICALLBACK callbackstop (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
zhuangtai=4;
//start=0;
AO_WriteChannel(cardID,0,2048);
break;
}
return 0;
}
int CVICALLBACK callbackquit (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
AO_WriteChannel(cardID,0,2048);
if(cardID>=0)
{
Release_Card(cardID);
}
QuitUserInterface (0);
break;
}
return 0;
}
int CVICALLBACK callbacktimer (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_TIMER_TICK:
if(cardID<0)
{
}
else
{
AI_ReadChannel(cardID,0,AD_U_5_V,&date); //读当前游标位置
date=(date>>4)&0x0fff;
out=(double)date*16.0/4096.0;
SetCtrlVal(panelHandle,PANEL_NUMERICSLIDE,out); //输出当前游标位置out
if(start==1)
{if(zhuangtai!=4)
// PlotStripChartPoint(panelHandle,PANEL_STRIPCHART,out);
show[0]=out;
show[1]=biaozhun;
PlotStripChart (panelHandle, PANEL_STRIPCHART, show, 2, 0, 0, VAL_DOUBLE);
if(zhuangtai==0) //PID控制
{
GetCtrlVal(panelHandle,PANEL_NUMERIC,&KP);
GetCtrlVal(panelHandle,PANEL_NUMERIC_2,&KI);
GetCtrlVal(panelHandle,PANEL_NUMERIC_3,&KD);
// KI=KP*T/TI;KD=KP*TD/T; //T取多少???
piderror2=-1.0*(biaozhun-out);
segmaerror+=piderror2;
position=-1.0*(KP*piderror2+KI*segmaerror+KD*(piderror2-piderror1))*2048.0/16.0+2048.0;
if(position>4095) position=4095.0;
if(position<0) position=0.0;
piderror1=piderror2;
AO_WriteChannel(cardID,0,(unsigned short)position);
// SetCtrlVal(panelHandle,PANEL_NUMERIC,position);
}
else if(zhuangtai==1) //模糊控制
{
temp=out-biaozhun;
if(temp>=fuzzy[0]) e=7;
else if (temp<=(-1*fuzzy[0])) e=-7;
else if (temp>=fuzzy[1]) e=6;
else if (temp<=(-1*fuzzy[1])) e=-6;
else if (temp>=fuzzy[2]) e=5;
else if (temp<(-1*fuzzy[2])) e=-5;
else if (temp>=fuzzy[3]) e=4;
else if (temp<=(-1*fuzzy[3])) e=-4;
else if (temp>=fuzzy[4]) e=3;
else if (temp<=(-1*fuzzy[4])) e=-3;
else if (temp>=fuzzy[5]) e=2;
else if (temp<=(-1*fuzzy[5])) e=-2;
else if (temp>=fuzzy[6]) e=1;
else if (temp<=(-1*fuzzy[6])) e=-1;
if((e-oe)>6) ec=6;
else if((e-oe)<-6) ec=-6;
else ec=e-oe;
oe=e;
if (e>0) e=e-1;
i=e+7;j=ec+6;
u=2048/7*matrix[i][j]+2048;
AO_WriteChannel(cardID,0,u);
}
else if(zhuangtai==2)
{AO_WriteChannel(cardID,0,0); //左移
if(out<=0) AO_WriteChannel(cardID,0,3000);
}
else if(zhuangtai==3)
{AO_WriteChannel(cardID,0,4095); //右移
if(out>=16) AO_WriteChannel(cardID,0,0);
}
else if(zhuangtai==4)
AO_WriteChannel(cardID,0,2048);
}
else
AO_WriteChannel(cardID,0,2048);
}
break;
}
return 0;
}
int CVICALLBACK callbacktypeselect (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
GetCtrlIndex(panelHandle,PANEL_RING,&b); // 如何读下拉菜单状态
if(b==0) {zhuangtai=0;i=0;j=0;segmaerror=0;} //PID控制状态
else if(b==1) {zhuangtai=1;i=0;j=0;} //模糊控制状态
// SetCtrlVal(panelHandle,PANEL_NUMERIC,b);
break;
}
return 0;
}
int CVICALLBACK chi (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
GetCtrlVal(panelHandle,PANEL_NUMERICSLIDE_2,&biaozhun); //从设定位移的游标上读取数据
// zhuangtai=1;
break;
}
return 0;
}
int CVICALLBACK yidong (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
switch (event)
{
case EVENT_COMMIT:
GetCtrlVal(panelHandle,PANEL_BINARYSWITCH,&a); //读可拨键状态
zhuangtai=2+a;
break;
}
return 0;
}