⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 item.cpp

📁 此为Insight opc client InfoServerExplorer源程序
💻 CPP
字号:
/////////////////////////////////////////////////////////////////////////////
//
//  OPC DataAccess VC++ Client:	Item.CPP
//								(Source File)
//
/////////////////////////////////////////////////////////////////////////////
//
//          Author: Raphael Imhof
//    Initial Date: 11/04/98
//       $Workfile: Item.cpp $
//       $Revision: 2 $
//           $Date: 9/09/99 11:01a $
//   Target System: Microsoft Windows NT 4.0
//     Environment: Visual C++ 5.0 / OPC DataAccess 1.0/2.0
//         Remarks: 
//
/////////////////////////////////////////////////////////////////////////////
//
//     Description: implementation of the CItem class.
//					Encapsulation of item related methods.
//					
//
/////////////////////////////////////////////////////////////////////////////
//
//  History of Changes     (Please remove very old comments and blank lines!)
//            $Log: /IDK/OPCServer/clients/VC++/InfoServerExplorer/Item.cpp $
// 
// 2     9/09/99 11:01a Imhof
// DCS 3227: Set changed flag to true and set the timestamp for read sync
// 
// 1     7/27/99 5:23p Imhof
// 
// 1     7/27/99 5:19p Imhof
// 
// 14    2/24/99 11:33a Imhof
// Changed the use of ValidateItem in EditItem() 
// 
// 13    1/15/99 6:43p Imhof
// Updated legal notice.
// 
// 12    1/06/99 10:34a Imhof
// Added a changed attribute to the CItem class which is used to optimize
// the content view update.
// 
// 11    12/28/98 3:20p Betrisey
// Do not Read the value of an item after changing its state from active
// to inactive and vice-versa. 
// InfoServer automatically sends the new update value/quality.
// 
// 10    12/14/98 4:46p Imhof
// Modifications for OPC 2.0
// 
// 9     12/11/98 5:58p Imhof
// Made modifications for OPC 2.0.
// 
// 8     12/03/98 1:53p Imhof
// Removed read after additems
// 
// 7     11/10/98 2:20p Imhof
// Added file header's.
// 
// 
//  $Nokeywords:$ (To avoid useless search while checking in.)
/////////////////////////////////////////////////////////////////////////////
//  Copyright (C) 1998, Siemens Building Technologies, Inc. Landis Division
//
// SIEMENS BUILDING TECHNOLOGIES, INC. IS PROVIDING THE FOLLOWING
// EXAMPLES OF CODE AS SAMPLE ONLY.
//
// SIEMENS BUILDING TECHNOLOGIES, INC.  MAKES NO REPRESENTATIONS
// OR WARRANTIES OF ANY KIND  WITH RESPECT TO THE VALIDTY OF THE 
// CODES   OR   DESIRED   RESULTS   AND   DISCLAIMS   ALL   SUCH 
// REPRESENTATIONS   AND   WARRANTIES,  INCLUDING  FOR  EXAMPLE, 
// WARRANTIES  OF  MERCHANTABILITY  AND FITNESS FOR A PARTICULAR 
// PURPOSE.    SIEMENS  BUILIDNG  TECHNOLOGIES,  INC.  DOES  NOT 
// REPRESENT  OR  WARRANT  THAT  THE  FOLLOWING CODE SAMPLES ARE 
// ACCURATE, VALID, COMPLETE OR CURRENT.
//
/////////////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "infoserverexplorer.h"
#include "Item.h"
#include "IOPCSyncIO.h"
#include "IOPCAsyncIO.h"
#include "IOPCAsyncIO2.h"
#include "IOPCItemMgt.h"
#include "ItemDlg.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif



//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
IMPLEMENT_DYNCREATE(CItem,	CObject)

CItem::CItem()
{
	memset(&m_timeStamp,0, sizeof(FILETIME));
	VariantClear(&m_value);
	m_data_type = VT_EMPTY;
	m_pGroup = NULL;
	m_quality = OPC_QUALITY_UNCERTAIN;
	m_bChanged = FALSE;
}

CItem::~CItem()
{
}

void CItem::Serialize(CArchive& ar)
{
	CBase<IOPCItemMgt>::Serialize(ar);	
	
	if (ar.IsStoring())
	{
		// TODO: add storing code here
		ar << m_data_type;
	}
	else
	{
		// TODO: add loading code here
		ar >> m_data_type;	
	}
}

CGroup* CItem::GetGroup()
{
	return m_pGroup;
}

void CItem::SetGroup(CGroup* pGroup)
{
	m_pGroup = pGroup;
}

void CItem::SetDataType(VARTYPE data_type)
{
	m_data_type = data_type;
}

VARTYPE CItem::GetDataType()
{
	return m_data_type;
}

void CItem::SetQuality(WORD quality)
{
	m_quality = quality;
}

WORD CItem::GetQuality()
{
	return m_quality;
}

void CItem::SetValue(VARIANT value)
{
	m_value.Copy(&value);
}

VARIANT CItem::GetValue()
{
	return m_value;
}

void CItem::SetTimeStamp(FILETIME time_stamp)
{
	m_timeStamp = time_stamp;
}

FILETIME CItem::GetTimeStamp()
{
	return m_timeStamp;
}

BOOL CItem::IsChanged()
{
	return m_bChanged;
}

void CItem::SetChanged(BOOL bChanged)
{
	m_bChanged = bChanged;
}

BOOL CItem::CommandSync(CString sValue)
{
	CIOPCSyncIO	opcSyncIO(GetGroup()->GetInterface());
	HRESULT		res;
	HRESULT*	pErrors;
	OPCHANDLE	hServer = GetHandle();
	COleVariant ItemValues(sValue); //input: string
	BOOL		bRet = FALSE;
    
	ItemValues.ChangeType(GetDataType()); //COleVariant converts to the correct point type

	res = opcSyncIO.Write(1, &hServer, &ItemValues, &pErrors);
	if(SUCCEEDED(res))
	{
		if(SUCCEEDED(pErrors[0]))
		{			
			bRet = TRUE;
		}
		else
		{
			GetGroup()->GetInfoServer()->DisplayError(pErrors[0]);
		}
	}
	else GetGroup()->GetInfoServer()->DisplayError(res);

	CoTaskMemFree(pErrors);

	return bRet;
}

BOOL CItem::CommandAsync(CString sValue)
{
	HRESULT			res;
	HRESULT*		pErrors;
	OPCHANDLE		hServer = GetHandle();
	COleVariant		ItemValues(sValue); //input: string  
	BOOL			bRet = FALSE;

	GetGroup()->CheckForOpenTransactions();

	ItemValues.ChangeType(GetDataType()); //COleVariant converts to the correct point type

	if(GetGroup()->GetInfoServer()->GetOPCVersion() >= OPC_VERSION_20)
	{
		CIOPCAsyncIO2	opcAsyncIO2(GetGroup()->GetInterface());
		DWORD			dwTransactionID = TRANSACTION_WRITE;	//in (returned in OnWriteComplete()) can be any number
		DWORD			dwCancelID;		//out
						
		res = opcAsyncIO2.Write(1, &hServer, &ItemValues, dwTransactionID, &dwCancelID, &pErrors);

		GetGroup()->SetCurrentTransactionID(dwTransactionID);
		GetGroup()->SetCurrentCancelID(dwCancelID);
	}
	else
	{
		CIOPCAsyncIO	opcAsyncIO(GetGroup()->GetInterface());
		 DWORD			dwTransactionID;	//out

		res = opcAsyncIO.Write(GetGroup()->GetOPCSTMFormatWriteCompleteConnection() , 1, &hServer, &ItemValues, &dwTransactionID, &pErrors);

		GetGroup()->SetCurrentTransactionID(dwTransactionID);
	}

	if(SUCCEEDED(res))
	{
		if(SUCCEEDED(pErrors[0]))
		{			
			bRet = TRUE;
		}
		else
		{
			GetGroup()->GetInfoServer()->DisplayError(pErrors[0]);
		}
	}
	else GetGroup()->GetInfoServer()->DisplayError(res);

	CoTaskMemFree(pErrors);

	return bRet;
}

BOOL CItem::Cancel()
{
	/*	cancel an active async operation: read, write or group refresh
		
		OPC 1.0: only a TransactionID is used
		OPC 2.0: transaction and CancelID is used

		Note: transaction handling is CGroup based
	*/

	HRESULT			res;
	BOOL			bRet = FALSE;

	if(GetGroup()->GetCurrentTransactionID() == 0)
	{
		((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("No active transaction !"));
		return FALSE;
	}

	if(GetGroup()->GetInfoServer()->GetOPCVersion() >= OPC_VERSION_20)
	{
		CIOPCAsyncIO2	opcAsyncIO2(GetGroup()->GetInterface());
		DWORD			dwTransactionID = 6015;	//in (returned in OnReadComplete()) can be any number
						
		if(GetGroup()->GetCurrentCancelID() == 0)
		{
			//should not happen since TransactionID and CancelID are managed aleays together
			((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("No active cancel ID !"));
			return FALSE;
		}
		res = opcAsyncIO2.Cancel2(GetGroup()->GetCurrentCancelID());
	}
	else
	{
		CIOPCAsyncIO	opcAsyncIO(GetGroup()->GetInterface());
		
		res = opcAsyncIO.Cancel(GetGroup()->GetCurrentTransactionID());
	}

	if(SUCCEEDED(res))
	{
		GetGroup()->SetCurrentTransactionID(0);
		GetGroup()->SetCurrentCancelID(0);

		bRet = TRUE;
	}
	else GetGroup()->GetInfoServer()->DisplayError(res);

	return bRet;
}

BOOL CItem::ReadAsync(OPCDATASOURCE dwSource)
{
	HRESULT			res;
	HRESULT*		pReadErrors;
	OPCHANDLE		hServer = GetHandle();
	BOOL			bRet = FALSE;

	GetGroup()->CheckForOpenTransactions();

	if(GetGroup()->GetInfoServer()->GetOPCVersion() >= OPC_VERSION_20)
	{
		CIOPCAsyncIO2	opcAsyncIO2(GetGroup()->GetInterface());
		DWORD			dwTransactionID = TRANSACTION_READ;	//in (returned in OnReadComplete()) can be any number
		DWORD			dwCancelID;		//out

		res = opcAsyncIO2.Read(1, &hServer, dwTransactionID, &dwCancelID, &pReadErrors);

		GetGroup()->SetCurrentTransactionID(dwTransactionID);
		GetGroup()->SetCurrentCancelID(dwCancelID);
	}
	else
	{
		CIOPCAsyncIO	opcAsyncIO(GetGroup()->GetInterface());
		DWORD			dwTransactionID;	//out

		if(GetGroup()->GetInfoServer()->GetDataChangeType() > 0) //0 = no timestamp; 1 = with timestamp
			res = opcAsyncIO.Read(GetGroup()->GetOPCSTMFormatDataTimeConnection(), dwSource, 1, &hServer, &dwTransactionID, &pReadErrors);
		else
			res = opcAsyncIO.Read(GetGroup()->GetOPCSTMFormatDataConnection(), dwSource, 1, &hServer, &dwTransactionID, &pReadErrors);

		GetGroup()->SetCurrentTransactionID(dwTransactionID);
	}

	if(SUCCEEDED(res))
	{
		if(FAILED(pReadErrors[0]))
		{
			GetGroup()->GetInfoServer()->DisplayError(pReadErrors[0]);
		}
		
		bRet = TRUE;
	}
	else GetGroup()->GetInfoServer()->DisplayError(res);

	CoTaskMemFree(pReadErrors);

	return bRet;
}

BOOL CItem::ReadSync(OPCDATASOURCE dwSource)
{
	//value gets returned over the IAdvise sink

	CIOPCSyncIO		opcSyncIO(GetGroup()->GetInterface());
	HRESULT			res;
	HRESULT*		pErrors;
	OPCHANDLE		hServer = GetHandle();
	OPCITEMSTATE*	pItemValues;	//out
	BOOL			bRet = FALSE;

	res = opcSyncIO.Read( dwSource, 1, &hServer, &pItemValues, &pErrors);
	if(SUCCEEDED(res))
	{
		if(SUCCEEDED(pErrors[0]))
		{
			//copy the value from pItemValues and write it in the content view
			SetQuality(pItemValues->wQuality);
			SetValue(pItemValues->vDataValue);
			SetTimeStamp(pItemValues->ftTimeStamp);

			//value needs to be updated in the view
			SetChanged(TRUE);
		}
		else
		{
			GetGroup()->GetInfoServer()->DisplayError(pErrors[0]);
		}
		
		bRet = TRUE;
	}
	else GetGroup()->GetInfoServer()->DisplayError(res);

	VariantClear(&pItemValues->vDataValue);
	CoTaskMemFree(pErrors);
	CoTaskMemFree(pItemValues);

	return bRet;
}

BOOL CItem::EditItem()
{
	USES_CONVERSION;

	HRESULT			res;
	CIOPCItemMgt	opcItemMgt(GetGroup()->GetInterface());
	CItemDlg		dlg;
	BOOL			bRet = FALSE;
	OPCITEMDEF		ItemArray[1];
	OPCITEMRESULT*	pValidationResults;
	HRESULT			*pErrorValidate, *pErrorState, *pErrorDataType, *pErrorClientHandle;

	ItemArray[0].szItemID = A2OLE(GetName());
	ItemArray[0].szAccessPath = A2OLE("");
	ItemArray[0].bActive = TRUE;
	ItemArray[0].hClient = (OPCHANDLE)this;
	ItemArray[0].dwBlobSize = 0;
	ItemArray[0].pBlob = NULL;
	ItemArray[0].vtRequestedDataType = GetDataType();

	/*
		ValidateItems is not necessary here, it checks if the item is still in the cache.
	*/

	res = opcItemMgt.ValidateItems(1, ItemArray,FALSE , &pValidationResults, &pErrorValidate);
	if(SUCCEEDED(res))
	{
		if(SUCCEEDED(pErrorValidate[0]))
		{
			TRACE("get active state ???\n");

			((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("CIOPCItemMgt::ValidateItems() was successful."));

			dlg.m_bActive = IsActive();
			dlg.SetDataType(GetDataType());
			dlg.m_dwClientHandle = (DWORD)this;
			dlg.m_sItem = GetName();

			if(IDOK == dlg.DoModal())
			{
				//res = opcItemMgt.SetActiveState(1, &pValidationResults->hServer, dlg.m_bActive, &pError);
				VARTYPE DataType = dlg.GetDataType();
				OPCHANDLE hServer = GetHandle();
				res = opcItemMgt.SetActiveState(1, &hServer, dlg.m_bActive, &pErrorState);
				if(SUCCEEDED(res))
				{
					if(SUCCEEDED(pErrorState[0])) 
					{
						SetActive(dlg.m_bActive);

						((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("CIOPCItemMgt::SetActiveState() was successful."));

						res = opcItemMgt.SetDatatypes(1, &hServer, &DataType, &pErrorDataType);
						if(SUCCEEDED(res))
						{
							if(SUCCEEDED(pErrorDataType[0])) 
							{
								((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("CIOPCItemMgt::SetDataType() was successful."));

								SetDataType(dlg.GetDataType());

								/*
									ChangeType 
									Read instead of only Variant::ChangeType()
									otherwise the view can show an invalid value.
									Example: RT4 value -> RTBOOL -> RT4 value would show -1
								*/
//cjb : InfoServer should update the client automatically 
//								ReadSync(OPC_DS_CACHE);

								if(dlg.m_dwClientHandle != (DWORD)this)
								{
									if(IDYES == AfxMessageBox(_T("Are you sure ?\n\nServer can't find client item afterwards."), MB_YESNOCANCEL | MB_ICONQUESTION ))
									{
										res = opcItemMgt.SetClientHandles(1, &hServer, &dlg.m_dwClientHandle, &pErrorClientHandle);
										if(SUCCEEDED(res))
										{
											if(SUCCEEDED(pErrorClientHandle[0])) 
											{
												//can't change own address !
												((CInfoServerExplorerApp*)AfxGetApp())->DisplayText(_T("CIOPCItemMgt::SetClientHandles() was successful."));
											}
											else
											{
												GetGroup()->GetInfoServer()->DisplayError(pErrorClientHandle[0]);
											}
										}
										else
										{
											GetGroup()->GetInfoServer()->DisplayError(res);
										}
										CoTaskMemFree(pErrorClientHandle);
									}
								}
							}
							else
							{
								GetGroup()->GetInfoServer()->DisplayError(pErrorDataType[0]);
							}
						}
						else
						{
							GetGroup()->GetInfoServer()->DisplayError(res);
						}
						CoTaskMemFree(pErrorDataType);
					}
					else
					{
						GetGroup()->GetInfoServer()->DisplayError(pErrorState[0]);
					}
				}
				else
				{
					GetGroup()->GetInfoServer()->DisplayError(res);
				}
				CoTaskMemFree(pErrorState);
			}
		}
		else
		{
			GetGroup()->GetInfoServer()->DisplayError(pErrorValidate[0]);
		}
		bRet = TRUE;
	}
	else
	{
		GetGroup()->GetInfoServer()->DisplayError(res);
	}
	CoTaskMemFree(pErrorValidate);
	CoTaskMemFree(pValidationResults);

	return bRet;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -