#include <rs232.h>
#include <utility.h>
#include <userint.h>
#include <ansi_c.h>
#include <pw18-1.8aq.h>
#include "TempCtrl.h"
FILE *gFp;
#define RSTREG(a,x) (a&=(~(x)))
#define SETREG(a,x) (a|=x)
int gMask=0xF;
static int pa;
#define TEXT_LENGTH 2000
char read_data[TEXT_LENGTH];
int read_term_index;
int read_term;
int read_cnt;
int bytes_read;
#define COM_PORT 11
typedef struct
{
double dState; // Last temperature input
double iState; // Integrator state
double iMax, iMin; // Maximum and minimum allowable integrator state
double iGain, // integral gain
pGain, // proportional gain
dGain; // derivative gain
} SPid;
SPid pid;
double UpdatePID(SPid * pid, double error, double temperature)
{
double pTerm, dTerm, iTerm;
pTerm = pid->pGain * error;
// calculate the proportional term
// calculate the integral state with appropriate limiting
pid->iState += error;
if (pid->iState > pid->iMax) pid->iState = pid->iMax;
else if (pid->iState < pid->iMin) pid->iState = pid->iMin;
//if (debug )
iTerm = pid->iGain * pid->iState; // calculate the integral term
dTerm = pid->dGain * (temperature - pid->dState);
pid->dState = temperature;
return pTerm + iTerm - dTerm;
}
void SetDimming(int state) {
SetCtrlAttribute (pa, PA_START, ATTR_DIMMED, state);
SetCtrlAttribute (pa, PA_EXIT, ATTR_DIMMED, state);
SetCtrlAttribute (pa, PA_STOP, ATTR_DIMMED, !state);
}
int CVICALLBACK ReadVoltageCurrentCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
int iRet;
char ch=0;
double Voltage;
double Current;
char cv_cc;
switch (event)
{
case EVENT_COMMIT:
GetCtrlVal(pa,PA_CHANNEL, &ch);
iRet = TMI_TimeOut(TMI_DeviceId, 1);
iRet = TMI_Refresh(TMI_DeviceId);
iRet = TMI_MoniDataQ(TMI_DeviceId, ch+1, &Voltage, &Current, &cv_cc);
SetCtrlVal(panel, PA_VMON, Voltage);
SetCtrlVal(panel, PA_IMON, Current);
SetCtrlVal(panel, PA_CVCC, cv_cc);
break;
}
return 0;
}
int CVICALLBACK SelectChannelCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
unsigned char state, preset;
double Voltage, Current;
unsigned char ch;
switch (event)
{
case EVENT_COMMIT:
GetCtrlVal(pa,PA_CHANNEL, &ch);
GetCtrlVal(pa,PA_PRESET, &preset);
TMI_VoltageQ(TMI_DeviceId, ch+1, preset, &Voltage);
TMI_CurrentQ(TMI_DeviceId, ch+1, preset, &Current);
SetCtrlVal(pa, PA_VSET, Voltage);
SetCtrlVal(pa, PA_ISET, Current);
break;
}
return 0;
}
int main (int argc, char *argv[])
{
int DeviceId=0;
unsigned char ch;
unsigned char MainOutput, preset;
double Voltage, Current, tinterval;
char str[0xFF];
if (InitCVIRTE (0, argv, 0) == 0)
return -1; /* out of memory */
SetStdioPort (CVI_STDIO_WINDOW);
pid.iGain= 0.3;
pid.dGain= 0.5;
pid.pGain = 3;
pid.iMax =100;
pid.iMin =-100 ;
pid.iState=0;
pid.dState=0;
if ((pa = LoadPanel (0, "TempCtrl.uir", PA)) < 0)
return -1;
if (TMI_Open()== 0) MessagePopup("Error","Cannot open USB device");
DeviceId = TMI_OpenHandle ("PW-A","USB:1:1");
if (TMI_Test() == 0 )MessagePopup("DLL error","Dll Error");
if (DeviceId < 0) MessagePopup("Error","Not Connected");
printf("TMI device ID %d\n",TMI_DeviceId
);
TMI_MainOutputQ(TMI_DeviceId, &MainOutput);
TMI_PresetQ(TMI_DeviceId, &preset);
SetCtrlVal(pa, PA_ONOFF, MainOutput);
SetCtrlVal(pa, PA_PRESET, preset);
/*
GetCtrlVal(pa, P1_TINTERVAL, &tinterval);
SetCtrlAttribute (pa, P1_TIMER, ATTR_INTERVAL, tinterval);
*/
SelectChannelCB (pa, PA_CHANNEL, EVENT_COMMIT, NULL, 0,0);
ReadVoltageCurrentCB (pa, PA_CHANNEL, EVENT_COMMIT, NULL, 0,0);
DisplayPanel (pa);
SetDimming(0);
RunUserInterface ();
CloseCom(COM_PORT);
DiscardPanel (pa);
TMI_Close();
return 0;
}
int CVICALLBACK ExitCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
QuitUserInterface (0);
break;
}
return 0;
}
int CVICALLBACK SwitchOnOffCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2)
{
unsigned char state;
switch (event)
{
case EVENT_COMMIT:
GetCtrlVal(panel, control, &state);
TMI_MainOutput(TMI_DeviceId, state);
break;
}
return 0;
}
/* Callback Function */
void ComCallback(int portNumber, int eventMask, void *callbackdata) {
if (eventMask & LWRS_RXFLAG) {
//printf("Received specified character\n");
int strLen = GetInQLen (COM_PORT);
bytes_read = ComRd (COM_PORT, read_data, strLen);
double temp
= atof(read_data
);
double f[10];
int debug1;
GetCtrlVal(pa,PA_DEBUG_1, &debug1);
//printf("%f#%s#", temp, read_data);
sscanf(read_data
,"%lf %lf %lf %lf %lf %lf",&f
[0],&f
[1],&f
[2],&f
[3],&f
[4],&f
[5]);
double humidity = f[5];
// printf("%lf %lf %lf %lf %lf %lf",f[0],f[1],f[2],f[3],f[4],f[5]);
int RS232Error = ReturnRS232Err ();
if (ReturnRS232Err ()) {
sprintf(read_data
,"#%s\n", GetRS232ErrorString
(RS232Error
));
MessagePopup("RS232Err",read_data);
} else {
int polar;
SelectChannelCB (pa, PA_CHANNEL, EVENT_COMMIT, NULL, 0,0);
ReadVoltageCurrentCB (pa, PA_CHANNEL, EVENT_COMMIT, NULL, 0,0);
double tset,vmon,imon,vset,iset,vmax;
unsigned char ch, preset;
GetCtrlVal(pa,PA_TSET,&tset);
GetCtrlVal(pa,PA_VMON,&vmon);
GetCtrlVal(pa,PA_IMON,&imon);
GetCtrlVal(pa,PA_CHANNEL, &ch);
GetCtrlVal(pa,PA_PRESET,&preset);
TMI_Preset(TMI_DeviceId,preset);
GetCtrlVal(pa,PA_POLAR,&polar);
double tdiff = temp - tset;
double retpid = UpdatePID(&pid, tdiff, temp);
const double troom = 20;
double Pheat= 0.2 * (temp - troom);
double Ptec = retpid - Pheat*2;
vset
= (polar
*Ptec
>0) ? sqrt(fabs(Ptec
)) : 0;
if (debug1
) printf("%d PID tmon=%f tset=%f tdiff=%f vmon=%f imom=%f pid=%f Pheat=%f =>vset %f", ch
, temp
, tset
, tdiff
, vmon
, imon
,retpid
,Pheat
, vset
);
GetCtrlVal(pa,PA_VMAX,&vmax);
if (vset >vmax) vset=vmax;
if (vset <0) vset =0;
if (debug1
) printf("vset --->%f \n",vset
);
TMI_Voltage(TMI_DeviceId, ch+1, preset, vset);
GetCtrlVal(pa,PA_IMAX,&iset);
TMI_Current(TMI_DeviceId, ch+1, preset, iset);
ReadVoltageCurrentCB (pa, PA_CHANNEL, EVENT_COMMIT, NULL, 0,0);
PlotStripChart (pa, PA_GRAPH, &temp, 1, 0, 0, VAL_DOUBLE);
double pgraph[2]={vmon,imon};
PlotStripChart (pa, PA_GRAPH_VMON, pgraph, 2, 0, 0, VAL_DOUBLE);
PlotStripChart (pa, PA_GRAPH_3, &humidity, 1, 0, 0, VAL_DOUBLE);
SetCtrlVal(pa,PA_TMON,temp);
GetCtrlVal
(pa
,PA_LOG
, &log);
char fname[0xFF];
GetCtrlVal(pa,PA_FNAME, fname);
FILE
*fp
= fopen (fname
,"a");
}
}
}
if (eventMask & LWRS_TXEMPTY)
printf("Transmit queue now empty\n");
if (eventMask & LWRS_RECEIVE) {
printf("50 or more bytes in input queue\n");
}
}
int CVICALLBACK StartCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
OpenComConfig (COM_PORT, "", 115200, 0, 8, 1, 512, 512);
/* Turn off Hardware handshaking (loopback test will not function with it on) */
SetCTSMode (COM_PORT, LWRS_HWHANDSHAKE_OFF);
/* Make sure Serial buffers are empty */
FlushInQ (COM_PORT);
FlushOutQ (COM_PORT);
int notifyCount = 50; /* Wait for at least 50 bytes in queue. */
int eventChar = 10; /* Wait for LF. */
int eventMask = LWRS_RXFLAG | LWRS_TXEMPTY | LWRS_RECEIVE;
InstallComCallback (COM_PORT, eventMask, notifyCount, eventChar, ComCallback, NULL);
SetDimming(1);
break;
}
return 0;
}
int CVICALLBACK StopCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:
CloseCom(COM_PORT);
SetDimming(0);
break;
}
return 0;
}
int CVICALLBACK SetPresetCB (int panel, int control, int event,
void *callbackData, int eventData1, int eventData2) {
switch (event) {
case EVENT_COMMIT:{
unsigned char preset;
double Voltage, Current;
GetCtrlVal(panel, control, &preset);
TMI_Preset(TMI_DeviceId, preset);
break;
}
}
return 0;
}