void __fastcall TframTag::cmbTypeChange(TObject *Sender)
{
	//
	ValidateView();
	switch(cmbType->ItemIndex){
	case 0:
		set_value_type(m_Tag.s.Flags, dt_bool);
		break;
	case 1:
		set_value_type(m_Tag.s.Flags, dt_real4);
		break;
	case 2:
		set_value_type(m_Tag.s.Flags, dt_real8);
		break;
	case 3:
		set_value_type(m_Tag.s.Flags, dt_int16);
		break;
	case 4:
		set_value_type(m_Tag.s.Flags, dt_int32);
		break;
	}
	UpdateView();
	PageControl1->ActivePageIndex = 0;
	// PageControl1->Pages[0]->Visible = true;
}
Exemple #2
0
/*
功能:从设备驱动中更新并得到实时值
参数:
      tag       更新的标签结构体,包含更新实时值所需要的配置信息[in]
	  new_value  实时值指针,用于存储更新所得到的实时值[in, out]
	  now        更新时间[in]
返回:
      1        成功
	  0       tag中动态属性的设备信息丢失
	       或 tag中动态属性设备信息的驱动信息丢失
		   或 tag中驱动信息中的更新tag的导出函数丢失
*/
IO_API __bool PMC_API io_update_tag(
	PCRTK_TAG tag, 
	Ppmc_value_t new_value,
	PCRTK_TIME now
	)
{
	PDRIVER_INFO drv;
    
	//1 设置新实时值的Flags
	new_value->Flags = 0;
	set_value_type(new_value->Flags,  get_value_type(tag->s.Flags));
	
	//2 将实时值的union清0,u64是union中的最大元素,即可表示union的大小
	/* 
	pre-set all unused bytes to zero, this will make it easier to
	write code depending on the tag types
	*/
	new_value->Value.u64 = 0;
	
	// assert(tag->d.DeviceObj == io_open_device(&tag->s.Device));

    //3 从标签的动态属性中得到设备驱动信息的结构体
	if(!tag->d.DeviceObj){
		return __false;
	}
	drv = ((PDEVICE_INFO)tag->d.DeviceObj)->d;
	if(!drv){
		return __false;
	}

	//4 调用设备驱动DLL的导出函数更新实时值
	if(!drv->update_tag){
		return __false;
	}
	
	if(drv->update_tag){
		drv->update_tag(tag, new_value, now);
	}
    
	//5 某些设备驱动可能会重写实时值的类型标识,需要再用标签静态属性中的类型标识设置一下
	// some ill-behavioured driver will overwrite the type field
	set_value_type(new_value->Flags, get_value_type(tag->s.Flags));
	
	//6 若静态属性配置为开关量,则将true转化为1,false转化为0
	if(get_value_type(tag->s.Flags) == dt_bool){
		/* make digital variable cannonical */
		new_value->Value.b = new_value->Value.b? 1 : 0;
	}
	
	return __true;
}
Exemple #3
0
RTDB_API RTK_CURSOR PMC_API create_tag(
	RTK_CURSOR group,
	PCTAG_KEY tag, 
	PCSTATIC_TAG_DATA sd
	)
{
	RTK_CURSOR	handle;
	RTK_GROUP * grp;
	RTK_TAG 	t;

	handle = open_tag_g(group, tag);
	if(handle){
		return handle;
	}

	if(g_dwTags >= g_dwMaxTags){
		rtk_set_last_error(RTDB_HARD_CONSTRAINTS);
		return 0;
	}

	grp = (RTK_GROUP*)cursor_get_item(group);
	if(!grp){
		return 0;
	}
	ZeroMemory(&t, sizeof(t));
	t.key = *tag;
	make_unified_key(t.key);
	t.s = *sd;
	t.node = grp->node;
	t.group = grp->key;
	handle = (RTK_CURSOR)_HTAG::create((TAG_TABLE*)grp->itemtable, t.key, t);
	RTK_TAG * pTag = (RTK_TAG*)cursor_get_item(handle);
	if(pTag){
		ZeroMemory(&pTag->d, sizeof(pTag->d));
		set_value_type(pTag->d.Value.Flags, get_value_type(pTag->s.Flags));
		RtkInitializeListHead(&pTag->d.DeviceLink);
		RtkInitializeListHead(&pTag->d.RefreshLink);
		FIRE_EVENT(OnAddTag, (pTag));
		g_dwTags++;
	}

	return handle;
}
//---------------------------------------------------------------------------
void __fastcall TframTag::btnWriteDeviceClick(TObject *Sender)
{
	AnsiString value;
	pmc_value_t strVal, val;
	value = InputBox(
		"输入要写的数值",
		(char*)CTagName(m_TagName.sname.tag),
		""
		);
	if(value.Length() == 0){
		return;
	}
    set_value_type(strVal.Flags, dt_string);
    strVal.Value.str = value.c_str();
    val.Flags = m_Tag.s.Flags;
    pmc_type_cast(&strVal, &val);
	if(proxy_write_tags(1, &m_TagName, &val.Value) ){
		m_Hint = "写入成功";
	}else{
		m_Hint = "写入失败";
	}
}
Exemple #5
0
/*
功能:将pmc_value_t实时值写入设备
参数:
      name    待写入实时值对应的   组名.标签名
	  value   待写入的实时值
返回:即设备驱动导出函数write_device()的返回值
*/
IO_API __bool PMC_API io_write_device_ex(
	PCSHORT_TAG_NAME name, 
	PCpmc_value_t value
	)
{
	pmc_value_t value2;
	__bool retval = __false;

	if(!lock_rtdb(__false, 100)){
		return __false;
	}
	PRTK_TAG p = query_tag(HNODE_LOCAL_MACHINE, name);
	if(p && !(p->d.Value.Flags & TF_ReadOnly)){
		ZeroMemory(&value2, sizeof(value2));
		set_value_type(value2.Flags, get_value_type(p->s.Flags));
		if(pmc_type_cast(value, &value2)){
			retval = _writeDevice(p, &value2.Value);
		}
	}
	unlock_rtdb();

	return retval;
}
void __fastcall TframTag::tmrUpdaterTimer(TObject *Sender)
{
	pmc_value_t value;
	AnsiString txtValue;
	char buf[64];
	FILETIME ft;
	SYSTEMTIME st;

	proxy_read_tags(1, &m_TagName, &value, 0);
	if(value.Flags & TF_Valid){
    	pmc_value_t strVal;
        set_value_type(strVal.Flags, dt_string);
        pmc_type_cast(&value, &strVal);
        txtValue = strVal.Value.str;
        pmc_clear(&strVal);
	}else{
		txtValue = "N.A.";
	}
	edtValue->Text = txtValue;

	RTK_TAG * p = query_tag_f(&m_TagName);
	if(p){
		AnsiString s;
		FILETIME   lft;
		SYSTEMTIME st;
		FileTimeToLocalFileTime((LPFILETIME)&p->d.CachedTime, &lft);
		FileTimeToSystemTime(&lft, &st);
		s = "";
		s.cat_printf(
			"%d年%d月%d日  %02d:%02d:%02d",
			st.wYear, st.wMonth, st.wDay, st.wHour, st.wMinute, st.wSecond
			);
		lblStatus->Caption = s;
	}else{
		lblStatus->Caption ="";
	}
}
double CExpression::vexp ( arbore a )
{
	double v;
	SYSTEMTIME tm;
	
	GetSystemTime(&tm);

	if (a->operatie==NULL) {error_code=10;return 0;}
	switch(a->operatie){
	case '+' : return( vexp(a->left)+vexp(a->right) );
	case '-' : return( vexp(a->left)-vexp(a->right) );
	case '*' : return( vexp(a->left)*vexp(a->right) );
	case '%':
		{
			v = vexp(a->right);
			if(v == 0){
				error_code = DIVISION_BY_0;
				return 0;
			}
			return (int)vexp(a->left) % (int)v;
		}
	case '/' : v=vexp(a->right) ;
		if (v==0){
			error_code=DIVISION_BY_0;
			return -vexp(a->left)/0.001;
		}else{
			return(vexp(a->left)/v);
		}
	case 150 : return(sin(vexp(a->left)));
	case 151 : return(cos(vexp(a->left)));
	case 152 : return(exp(vexp(a->left)));
	case 153 : v=vexp(a->left) ;
		if (v<0) {error_code=INVALID_DOMAIN;return 0;}
		else return(sqrt(v));
	case 154 : v=vexp(a->left) ;
		if (v<=0) {error_code=INVALID_DOMAIN;return 0;}
		else return(log(v));
	case 155 : return (tan (vexp(a->left)));
	case 156 : return (1 / tan (vexp(a->left)));
	case 157 : return (asin (vexp(a->left)));
	case 158 : return (acos (vexp(a->left)));
	case 159 : return (atan (vexp(a->left)));
	case 173 : return (fabs (vexp(a->left)));
	case 160 : return tm.wYear;
	case 161 : return tm.wMonth;
	case 162 : return tm.wDay;
	case 163 : return tm.wHour;
	case 164 : return tm.wMinute;
	case 165 : return tm.wSecond;
	case 166 : return max(vexp(a->left),vexp(a->right));
	case 167 : return min(vexp(a->left),vexp(a->right));
	case 168 : return rng_rand(0,RAND_MAX)*vexp(a->left)/RAND_MAX;
	//case '|' : return(fabs(vexp(a->left)));
	case '^' : return(pow(vexp(a->left),vexp(a->right)));
	case '@' : return (a->valoare);
		//logical operations evaluation
	case '<' : return( vexp(a->left) < vexp(a->right) );
	case '>' : return( vexp(a->left) > vexp(a->right) );
	case '!' : return(!vexp(a->right)) ;
	// added by chenj, @2008-5-22
	case '=' : return( vexp(a->left) == vexp(a->right) );
	case '&' : return (int)(vexp(a->left)) & (int)(vexp(a->right));
	case '|' : return (int)(vexp(a->left)) | (int)(vexp(a->right));
		
	case 169:
		{
			RTK_TIME t;
			rtk_time_mark(&t);
			return (double)(__int64)t.Data / 1e7;
		}
		
	case 170:
		{
			/* last update time */
			PRTK_TAG tte;
			__r8 retval = 0;
			
			tte  = (PRTK_TAG)a->left->pvObj;
			if(!tte){
				error_code=UNDEFINED_VARIABLE;
				retval = 0;
			}else{ 
				if(!(tte->d.Value.Flags & TF_Valid)){
					error_code=UNDEFINED_VARIABLE;
					retval = 0;
				}else{
					PRTK_TIME pTime = (PRTK_TIME)&tte->d.BinaryAddress[8];
					retval = (double)(__int64)pTime->Data / 1e7;
					rtk_time_mark(pTime);
				}
			}

			return retval;
		}

	case 171  : 
		{
			// a database tag
			PRTK_TAG tte;
			__r8 retval = 0;
			tte = (PRTK_TAG)a->pvObj;
			if(!tte){
				error_code=UNDEFINED_VARIABLE;
				retval = 0;
			}else{ 
				if(!(tte->d.Value.Flags & TF_Valid)){
					error_code=UNDEFINED_VARIABLE;
					retval = 0;
				}else{
					pmc_value_t dblVal;
					set_value_type(dblVal.Flags, dt_real8);
					pmc_type_cast(&tte->d.Value, &dblVal);
					retval = dblVal.Value.dbl;
				}
			}
			return retval;
		}
	
	case 172:
		{
			/* span time */
			PRTK_TAG tte;
			RTK_TIME now;
			__r8 retval = 0;
			
			tte  = (PRTK_TAG)a->left->pvObj;
			if(!tte){
				error_code=UNDEFINED_VARIABLE;
				retval = 0;
			}else{ 
				if(!(tte->d.Value.Flags & TF_Valid)){
					error_code=UNDEFINED_VARIABLE;
					retval = 0;
				}else{
					PRTK_TIME pTime = (PRTK_TIME)&(tte->d.BinaryAddress[8]);
					rtk_time_mark(&now);
					if(pTime->Data != 0){
						/* yes, the field is previouly stored with a resonable value,
						thus valid for a sub-operation to get a duration time */
						retval = rtk_time_diff(&now, pTime);
					}else{
						/* this might be the first time that a time-span was requested
						for this tag
						*/
						retval = 0;
					}
					
					*pTime = now;
				}
			}

			return retval;
		}

	}

	return 0;
}
Exemple #8
0
void CText::Draw(CDC *pDC)
{
    long x1,y1,x2,y2;
    if(m_DnyAttr.m_Linked && m_DnyAttr.m_na) {
        CPen *pop=(CPen*)(pDC->SelectStockObject(BLACK_PEN));
        CBrush *pob=(CBrush*)(pDC->SelectStockObject(WHITE_BRUSH));
        UPtoLP(m_lox1,m_loy1,&x1,&y1);
        UPtoLP(m_lox2,m_loy2,&x2,&y2);
        pDC->Rectangle(x1,y1,x2,y2);
        /*
        pDC->MoveTo(x1, y1);
        pDC->LineTo(x1 + 10, y1 + 10);
        pDC->MoveTo(x1 + 10, y1);
        pDC->LineTo(x1, y1 + 10);
        */
        pDC->SelectObject(pop);
        pDC->SelectObject(pob);
        pDC->DrawIcon(x1,y1,ghNA);
        return;
    }

    if(m_DnyAttr.m_Linked && !m_DnyAttr.m_vi) return;

    LOGFONT tFont;
    tFont=m_font;
    UPtoLP(tFont.lfHeight,tFont.lfWidth,&tFont.lfHeight,&tFont.lfWidth);
    CFont font;
    font.CreateFontIndirect(&tFont);
    CFont *pOldFont=pDC->SelectObject(&font);

    int i,iWidth;
    long lTemp,lUWidth=0;
    UINT nTemp;
    i=0;
    while(i<m_text.GetLength()) {
        nTemp=(UCHAR)m_text[i];
        if(IsDBCSLeadByte(nTemp)) {
            nTemp=nTemp*256+(UCHAR)m_text[i];
            i++;
        }
        ::GetCharWidth(pDC->GetSafeHdc(),nTemp,nTemp,&iWidth);
        //CMeatFileDC没有属性DC,下面这句话就不灵了。
        //pDC->GetCharWidth(nTemp,nTemp,&iWidth);
        CElement::LPtoUP(iWidth,iWidth,&lTemp,0);
        lUWidth+=lTemp;
        i++;
    }

    pDC->SetBkMode(TRANSPARENT);
    pDC->SetTextColor(m_FaceColor);

    UPtoLP(m_lx1,m_ly1,&x1,&y1);

    CString sTemp;
    sTemp=m_text;
    if(m_DnyAttr.m_ValueA.m_Used) {
        pmc_value_t d;
        set_value_type(d.Flags, dt_real4);
        pmc_type_cast(&m_DnyAttr.m_ValueA.m_TagValue, &d);
        sTemp.Format(m_DnyAttr.m_ValueA.m_Format, d.Value.flt);
    } else if(m_DnyAttr.m_ValueD.m_Used) {
        if(m_DnyAttr.m_ValueD.action_proc && m_DnyAttr.m_ValueD.action_proc != (void*)-1) {
            char * s;
            s = ((char * (WINAPI*)())m_DnyAttr.m_ValueD.action_proc)();
            sTemp = s;
            free_buffer(s);
        } else {
            if(m_DnyAttr.m_ValueD.m_TagValue.Value.iValue) {
                sTemp=m_DnyAttr.m_ValueD.m_OnMsg;
            } else {
                sTemp=m_DnyAttr.m_ValueD.m_OffMsg;
            }
        }
    }
    pDC->TextOut(x1,y1,sTemp);
    pDC->SelectObject(pOldFont);
}
	uniform_node&
	set_value_type(void)
	{
		set_value_type(get_data_type_v<T>);
		return *this;
	}
/*
	gather data from UI to internal representation
*/
bool TframTag::ValidateView()
{
	PTAG_NAME name;
	PRTK_TAG tag;	
	name = &m_TagName;
	tag = &m_Tag;
	
	try{
	#undef cc

	#define cc(name) tag->s.Flags |= (chk##name->Checked ? TF_##name : 0);

		if( edtTagName->Text.Length() >sizeof(TAG_KEY) ||
			!edtTagName->Text.Length()
		){
			m_Hint = "变量名不正确";
			throw(-1);
		}
		if( !is_valid_name(edtTagName->Text.c_str()) ){
			m_Hint = "变量名只能包含字母、数字和下划线";
			throw(-3);
		}
		if(edtTagName->Text.Length() > sizeof(TAG_KEY)){		
			m_Hint = AnsiString("错误: 标签名不能超过 ") + IntToStr(sizeof(TAG_KEY)) + " 个字节";		 
			throw(-3);
		}
		name->sname.tag = CTagName(edtTagName->Text.c_str());
		tag->s.Device = CDeviceName(cmbDevice->Text.c_str());
		tag->key = name->sname.tag;
		if(edtCName->Text.Length() > sizeof(tag->s.Description)){
			m_Hint = "中文名太长(最长 " + AnsiString(sizeof(tag->s.Description)/2) + " 字)";
			throw(-4);
		}
		strncpy(tag->s.Description, edtCName->Text.c_str(), sizeof(tag->s.Description));
		tag->s.Description[sizeof(tag->s.Description) - 1] = 0;
		if(edtAddr->Text.Length() > sizeof(tag->s.Address)){
			m_Hint = "地址太长(最长 " + AnsiString(sizeof(tag->s.Address)/2) + " 字)";
			throw(-5);
		}
		strncpy(tag->s.Address, edtAddr->Text.c_str(), sizeof(tag->s.Address));
		tag->s.Address[sizeof(tag->s.Address) - 1] = 0;

        tag->s.Flags = 0;
        
		switch(cmbType->ItemIndex){
		case 0:
			set_value_type(tag->s.Flags, dt_bool);
			break;
		case 1:
			set_value_type(tag->s.Flags, dt_real4);
			break;
		case 2:
			set_value_type(tag->s.Flags, dt_real8);
			break;

		case 3:
			set_value_type(tag->s.Flags, dt_int8);
			break;
		case 4:
			set_value_type(tag->s.Flags, dt_int16);
			break;
		case 5:
			set_value_type(tag->s.Flags, dt_int32);
			break;
		case 6:
			set_value_type(tag->s.Flags, dt_int64);
			break;

		case 7:
			set_value_type(tag->s.Flags, dt_uint8);
			break;
		case 8:
			set_value_type(tag->s.Flags, dt_uint16);
			break;
		case 9:
			set_value_type(tag->s.Flags, dt_uint32);
			break;
		case 10:
			set_value_type(tag->s.Flags, dt_uint64);
			break;

        case 11:
            set_value_type(tag->s.Flags, dt_date);
            break;

        case 12:
            m_Hint = "不支持这个数据类型.";
            throw(-41);
            break;
		}

		cc(SaveToHistory);
        cc(Step);

		// collecting common analog attributes
		switch(get_value_type(tag->s.Flags)){
        case dt_int8:
		case dt_int16:
		case dt_int32:
        case dt_int64:
        case dt_uint8:
		case dt_uint16:
		case dt_uint32:
        case dt_uint64:
        case dt_real4:
		case dt_real8:
        case dt_date:
			cc(HiHi);
			cc(Lo);
			cc(Hi);
			cc(LoLo);
			cc(Rate);
			strncpy(
				tag->s.AnalogMsg.EU,
				edtEU->Text.c_str(),
				sizeof(tag->s.AnalogMsg.EU)
				);
			tag->s.AnalogMsg.EU[sizeof(tag->s.AnalogMsg.EU) - 1] = 0;
			break;
		case dt_bool:
			cc(On2Off);
			cc(Off2On);
			
			strncpy(
				tag->s.SwitchMsg.OnMsg,
				edtOnMessage->Text.c_str(),
				sizeof(tag->s.SwitchMsg.OnMsg)
				);
			tag->s.SwitchMsg.OnMsg[sizeof(tag->s.SwitchMsg.OnMsg) - 1] = 0;
			strncpy(
				tag->s.SwitchMsg.OffMsg,
				edtOffMessage->Text.c_str(),
				sizeof(tag->s.SwitchMsg.OffMsg)
				);
			tag->s.SwitchMsg.OffMsg[sizeof(tag->s.SwitchMsg.OffMsg) - 1] = 0;
			break;
		}

#define get(msg, name, ignore_on_condition, _default_value)\
	m_Hint = msg;\
	if( !edt##name->Text.Length() ){\
		if(ignore_on_condition){\
			tag->s.flt##name = _default_value;\
		}else{\
			throw(-1);\
		}\
	}else{\
		tag->s.flt##name = edt##name->Text.ToDouble();\
	}
#pragma warn -ccc
#pragma warn -rch
		switch(get_value_type(tag->s.Flags)){
		case dt_real4:
		case dt_real8:
			get("高高值不正确", HiHi, !chkHiHi->Checked, 0);
			get("低低值不正确", LoLo, !chkLoLo->Checked, 0);
			get("低值不正确", Lo, !chkLo->Checked, 0);
			get("高值不正确", Hi, !chkHi->Checked, 0);
			get("报警死区值不正确", AlarmDeadband, !(tag->s.Flags & 0xffffff00), 0);
			get("最大值不正确", MaxValue, false, 0);
			get("最小值不正确", MinValue, false, 0);
			get("速率报警阈值不正确", Rate, !chkRate->Checked, 0.1);
			break;

		case dt_int8:
		case dt_int16:
		case dt_int32:
        case dt_int64:
		case dt_uint8:
		case dt_uint16:
		case dt_uint32:
        case dt_uint64:
			get("速率报警阈值不正确", Rate, !chkRate->Checked, 0.1);
#undef get
#define get(msg, attrName, uiName, ignore_on_condition, _default_value)\
	m_Hint = msg;\
	if( !edt##uiName->Text.Length() ){\
		if(ignore_on_condition){\
			tag->s.##attrName = _default_value;\
		}else{\
			throw(-1);\
		}\
	}else{\
		tag->s.attrName = edt##uiName->Text.ToDouble();\
	}
			get("高高值不正确", u_hihi.i, HiHi, !chkHiHi->Checked, 0);
			get("低低值不正确", u_lolo.i, LoLo, !chkLoLo->Checked, 0);
			get("低值不正确", u_lo.i, Lo, !chkLo->Checked, 0);
			get("高值不正确", u_hi.i, Hi, !chkHi->Checked, 0);
			get("报警死区值不正确", u_deadband.i, AlarmDeadband, !(tag->s.Flags & 0xffffff00), 0);
			get("最大值不正确", u_max.i, MaxValue, false, 0);
			get("最小值不正确", u_min.i, MinValue, false, 0);
			break;
		}

#pragma warn .ccc
#pragma warn .rch

        if(get_value_type(tag->s.Flags) == dt_bool){
            tag->s.AlarmRank = edtAlarmRank2->Text.ToInt();
        }else{
    		tag->s.AlarmRank = edtAlarmRank->Text.ToInt();
        }

		tag->s.Compressing = Compress_Const;
		tag->s.CompDev = StrToFloat(edtCompDev->Text);
		tag->s.CompMax = StrToInt(edtCompMax->Text);
	}catch(...){
		return false;
	}
	m_Hint = "更新成功";
	return true;
}