- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我完全不熟悉 PLC,但我有一个项目需要从 OPC 客户端服务器获取数据,然后将其发送到 Access 数据库表。减去 OPCWriteGroupItems 的大部分代码来自其他人。我只是迷失了将从 OPCReadGroupItems 获取的数据传输到我的函数 OPCWriteGroupItems 中的适当变量的过程。我只想获取读入变量的值。谢谢。供引用。我知道我的查询语句需要进行调整,以便它能够正确读取变量,但这是我正在处理的另一个问题。这是更紧迫的问题。
下面是我提到的两个函数:
//---------------------------------------------------------
// Read items from an OPC Group
//---------------------------------------------------------
OPCStat OPCReadGroupItems (int iGrp, struct Var_Stru v[] )
{
HRESULT r1;
HRESULT *hr;
OPCITEMSTATE *is;
int iItem;
OPCStat RetVal=OPCSuccess;
if (pGRPTagSIO[iGrp]) {
if (bOPCDebug) printf("Reading data .... \n");
r1 = pGRPTagSIO[iGrp]->Read(OPC_DS_CACHE,
OPCDataGroup[iGrp].iNumItems,
OPCDataGroup[iGrp].hItem,
&is,
&hr);
if (FAILED(r1)) {
printf("Error from Read(%lx)\n", r1);
RetVal = OPCError;
} else {
// if the read worked then copy results to the v structure based on type
for (iItem=0;iItem<OPCDataGroup[iGrp].iNumItems;iItem++ ) {
//printf("Read item= %d, hr= %lx, Quality= %2x", iItem, hr[iItem], is[iItem].wQuality);
if(!FAILED(hr[iItem])) {
// printf("%d", is[iItem].vDataValue.vt);
//printf("%d", iGrp);
switch(is[iItem].vDataValue.vt) {
case VT_I2: // 2
v[iItem].iVal = is[iItem].vDataValue.iVal;
break;
case VT_I4: // 3
v[iItem].lVal = is[iItem].vDataValue.lVal;
break;
case VT_R4: // 4
// printf("Z");
v[iItem].fVal = is[iItem].vDataValue.fltVal;
break;
case VT_R8: // 5
v[iItem].dblVal = is[iItem].vDataValue.dblVal;
break;
case VT_BOOL: // 11
v[iItem].bVal = is[iItem].vDataValue.boolVal;
break;
case VT_UI1: // 11
printf("TEST");
sprintf(v[iItem].cVal, "%s", is[iItem].vDataValue.cVal);
printf("%s", v[iItem].cVal);
printf("%c", v[iItem].cVal);
break;
case VT_BSTR: // 8
// printf("TEST");
sprintf(v[iItem].cVal,"%-.*ls", kOPCStringSize,is[iItem].vDataValue.bstrVal );
//printf("\n STRING STRING %s \n", v[iItem].cVal);
break;
default:
break;
}
}
if(iGrp >= 0 && iGrp <=)
{
stuct_double[iGrp-1][iItem] = v[iItem].dblVal;
// printf("group %d ", iGrp);
// printf("Tag %i: %10.2f\n", iItem, root_plc[iItem]);
}
if(iGrp > 0 && iGrp <= 44)
{
struc_floats[iGrp-1][iItem] = v[iItem].fVal;
//printf("GROUP %d ", iGrp);
//printf("Tag %i: %10.2f\n", iItem, struc_floats[iGrp-1][iItem]);
}
else
{
printf("Error reading data item %d\n", iItem);
//RetVal=OPCError; //Make not as severe -- rjf 06/03/02
RetVal=OPCWarning;
//break; //Escape the for-loop -- rjf- 5/13/02
}
*/
pIMalloc->Free(hr);
for (iItem=0;iItem<OPCDataGroup[iGrp].iNumItems;iItem)
{
VariantClear($is[iItem].vdatavalue)
}
pIMalloc->Free(is);
}
}
else{
RetVal=OPCError;
}
return (RetVal);
}
//-----------------------------------------
// Write items contained in an OPC Group
//-----------------------------------------
OPCStat OPCWriteGroupItems (int iGrp, struct Var_Stru vOut[] )
{
/* Data Access Method used in this sample */
const char* DAM = "Direct ODBC";
/* Connection string for Direct ODBC */
char szDSN[256] = "DSN=Gas_Meter_check;";
HRESULT r1,r2;
HRESULT *hr;
VARIANT v[nMaxOPCItems];
int iItem;
OPCStat RetVal=OPCSuccess;
if (pGRPTagSIO[iGrp]) {
for (iItem=0;iItem<OPCDataGroup[iGrp].iNumItems;iItem++) {
v[iItem].vt = OPCDataGroup[iGrp].iType;
switch(OPCDataGroup[iGrp].iType) {
case VT_I2: // 2
v[iItem].iVal = vOut[iItem].iVal;
break;
case VT_I4: // 3
v[iItem].lVal = vOut[iItem].lVal;
break;
case VT_R4: // 4
v[iItem].fltVal = vOut[iItem].fVal;
break;
case VT_R8: // 5
v[iItem].dblVal = vOut[iItem].dblVal;
HENV hEnv; HDBC hDbc;
/* ODBC API return status */ RETCODE rc;
int iConnStrLength2Ptr;
char szConnStrOut[256];
int i= 0;
char datetime[256];
double HMCO=1.0;
double HMR,HMT;
unsigned char* InsertQuery = "INSERT INTO Data ( [Date / Time], [Hot Strip Mill rate], [Hot Strip Mill Comm Okay], [Hot Strip Mill Total] ) SELECT #datetime# AS Expr1, HMR AS Expr2, 1 AS Expr3, HMCO AS Expr4, HMT AS Expr5;";
SQLCHAR chval1[128], chval2[128], colName[128];
int ret1;
int ret2;
/* Number of rows and columns in result set */
SQLINTEGER rowCount = 0;
SQLSMALLINT fieldCount = 0, currentField = 0;
HSTMT hStmt;
/* Allocate an environment handle */
rc = SQLAllocEnv(&hEnv);
/* Allocate a connection handle */
rc = SQLAllocConnect(hEnv, &hDbc);
/* Connect to the TakeCharge database */
rc = SQLDriverConnect(hDbc, NULL, (unsigned char*)szDSN,
SQL_NTS, (unsigned char*)szConnStrOut,
255, (SQLSMALLINT*)&iConnStrLength2Ptr, SQL_DRIVER_NOPROMPT);
if (SQL_SUCCEEDED(rc))
{
printf("%s: Successfully connected to database. Data source name: \n %s\n",
DAM, szConnStrOut);
/* Prepare SQL query */
printf("%s: SQL InsertQuery:\n %s\n", DAM, InsertQuery);
rc = SQLAllocStmt(hDbc,&hStmt);
rc = SQLPrepare(hStmt, InsertQuery, SQL_NTS);
/* Excecute the query and create a record set */
rc = SQLExecute(hStmt);
if (SQL_SUCCEEDED(rc))
{
printf("Executing query...");
printf("\n");
}
while (SQL_SUCCEEDED(rc))
{
printf(" insert passed\n");
rc = SQLFetch(hStmt);
rowCount++;
};
}
else
{
printf("%s: Couldn't connect to %s.\n", DAM, szDSN);
}
/* Disconnect*/
SQLDisconnect(hDbc);
printf("%s: Cleanup. Done.\n", DAM);
break;
case VT_BOOL: // 11
v[iItem].bVal = vOut[iItem].bVal;
break;
case VT_BSTR: // 8
// printf(" In Message value (VT_BSTR) = %s \n",vOut[iItem].cVal );
r2 = LPTSTR_to_BSTR ( &v[iItem].bstrVal , vOut[iItem].cVal);
if ( r2 != S_OK ) {
printf ("error in memory \n");
RetVal = OPCError;
}
// printf(" Write Msg value(VT_BSTR) = %ls \n", v[iItem].bstrVal );
report(0,0,0, "STRINGS data %s",vOut[iItem].cVal);
break;
default:
printf(" value(unknown type:%d) ", OPCDataGroup[iGrp].iType );
RetVal = OPCError;
break;
}
//if (bOPCDebug) DumpVariant(OPCDataGroup[iGrp].cTagNames[iItem], &v[iItem]);
}
r1 = pGRPTagSIO[iGrp]->Write(
OPCDataGroup[iGrp].iNumItems,
OPCDataGroup[iGrp].hItem,
v,
&hr);
if (FAILED(r1))
{
printf("Error from Write(%lx)\n", r1);
RetVal = OPCError;
} else {
//if (bOPCDebug) printf("Successful Write ... \n");
// Clear the Variant
for (iItem=0;iItem<OPCDataGroup[iGrp].iNumItems;iItem++) {
VariantClear(&v[iItem]);
}
pIMalloc->Free(hr);
}
} else {
RetVal = OPCError;
}
return(RetVal);
}
最佳答案
C/C++ 不是我的第一语言,我不熟悉你的特定 OPC 库(有这么多),但根据我对代码的理解,你正在阅读某种变体变量,并且带有大小写您确定其类型的语句并将其存储到 v[iItem] 的适当属性中。您对该组中的所有标签循环重复该操作。一定有一些属性告诉你刚刚读取的标签的名称,你可以用它来解决问题。
比如你当前读取的标签是single float类型,那么会执行这个case部分:
case VT_R4:
v[iItem].fVal = is[iItem].vDataValue.fltVal;
break;
所以 v[iItem].fVal 包含 OPC 标签的 4 字节单浮点值。如果你当前阅读的标签是double float类型,那么这个case部分就会被执行:
case VT_R8:
v[iItem].dblVal = is[iItem].vDataValue.dblVal;
break;
和v[iItem].dblVal 包含OPC 标签的8 字节双浮点值。我想你明白了。
您真的应该花一些时间在 http://www.opcfoundation.org 上学习 OPC DA 教程.
关于c - 从 PLC(OPC 客户端服务器 Kepware)传输到 MS Access,C,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6666480/
请解释 OPC UA 和 OPC DA 之间的区别是什么? 在哪种情况下应该使用哪个,如果可以为 OPC UA 和 OPC DA 提供任何示例,这将有所帮助 最佳答案 OPC UA 不仅适用于 OPC
我有一个 Kepware OPC 服务器,我能够连接到我的客户端(OPC Foundation UA lib)。我在 Kepware 中创建了一个设备,并在其中创建了一个组。我想从数据库中读取 opc
我想从头开始实现我自己的 OPC DA 客户端(版本 2.02、2.05a、3.00),但不使用任何第三方。我还想利用 OPCEnum.exe 服务来获取已安装 OPC 服务器的列表。是否有任何类型的
我想从头开始实现我自己的 OPC DA 客户端(版本 2.02、2.05a、3.00),但不使用任何第三方。我还想利用 OPCEnum.exe 服务来获取已安装 OPC 服务器的列表。是否有任何类型的
我是 OPC 统一架构世界的新手,我正在从基础开始学习它。命名空间到底是什么?为什么它总是附加 NodeID? 最佳答案 OPC UA 中的命名空间就像节点 ID 的容器。OPC 基金会有索引为 0
我正在尝试通过 openscada 连接到 OPC 服务器。 我已经知道 MatrikonOPC explorer 给出的 OPC 服务器程序 ID,但连接不工作可能是由于错误的 DCOM 配置。在更
我一直在互联网上阅读,以很好地解释 OPC-UA 中的节点。似乎有一些库可以用于它,但实际上没有一个解释节点。 OPC-UA 中节点的用途是什么? 注意:此处为 OPC 和 OPC-UA 菜鸟 最佳答
在我的公司中,我们有许多分布式站点,每个站点都使用一个单一的 Scada 系统供应商(一个使用 Wincc,其他地方使用另一个......)并且该系统使用几乎相同类型的信息。 我们需要从这些系统中检索
我对 OPC-UA 世界完全陌生。 我需要建立一个关于如何让我们的 ERP 与 PLC 通信的概念证明。我正在评估充当 OPC-UA 服务器的软件(它正在运行)。我发现了 Milo 并让代码在 Ecl
我注意到所有 OPC 标记 ID 都以 ns=2;s= 为前缀. 可能的 NodeId 值的一些示例是: ns=2;s=AcquisitionTimeRemaining ns=2;s=Status n
我是 OPC UA 新手,我正在使用 milo OPC Subscriber client连接到本地发现服务。我有 Prosys 模拟服务器,它连接到我的本地发现服务。 注意:如果我直接连接到 pro
我想使用 OPC UA 服务器将我的应用程序生成的数据发送到 OPC UA 客户端。我已经完成了 Eclipse Milo 项目,这是一个很好的资源。但我不知道如何将它集成到我们的应用程序中。应用程序
我有一个应用程序,我需要将数据从 PLC 读取到数据库中,因此我需要开发自己的应用程序来执行此操作。我只需要从 PLC 读取 5 个值并将其记录到数据库中。我有一个正在运行的演示 OPC 服务器,可以
我是一名 OPC-UA 新手,使用 Milo 堆栈将非 OPC-UA 系统集成到 OPC-UA 服务器。其中一部分包括将值写入 OPC-UA 服务器中的节点。我的问题之一是来自其他系统的值以 Java
我已经减少并检查了 SamplingInterval 和 PublishingInterval..values 没有影响。你能提出任何建议吗?让我知道。 最佳答案 如前所述,SamplingInter
我正在使用 opc.net api 部分开发 opc 客户端应用程序,但在连接远程 opc 服务器时遇到了一些问题。下面请看我写的连接opc服务器的代码。 Opc. URL url = new Opc
我正在开发一个 OPC UA 客户端应用程序,它读取存储在 OPC UA 服务器上的文件。出于测试目的,我需要一个 OPC UA 服务器模拟器,我可以在其中添加 FileType 节点并配置这些节点。
我是 OPC-UA 世界和 Eclipse Milo 的新手。我不明白这里的保安是如何运作的,讨论eclipse-milo提供的client-example 我发现连接 OPCUA 服务器时使用了一些
我正在尝试使用 unifiedautomation 的 opc ua DLL 从 Opc ua 服务器(西门子)读取日期和时间 (#DT)。但是我得到了错误的值: 西门子 S7 1500 opc ua
我正在尝试遵循这些教程: https://sandervandevelde.wordpress.com/2018/11/06/getting-started-with-opc-ua-on-azure-
我是一名优秀的程序员,十分优秀!