当前位置:网站首页>Learn open62541 -- [67] add custom enum and display name
Learn open62541 -- [67] add custom enum and display name
2022-07-07 18:50:00 【Love is patience】
Enum Variables of type are a little special , stay base data type in , You can see enum Cannot instantiate directly ,
Its properties are as follows , It's an abstract type ,
For customization enum, Need to go through 3 Step by step ,
- Define the corresponding DataType
- Then define the corresponding variable type
- Finally, use this variable type to create enum Variable
This article describes how to add customization Enum, And create corresponding variables
One Code
The code is as follows ,
#include "open62541.h"
static bool running = true;
static void stopHandler(int sig) {
UA_LOG_INFO(UA_Log_Stdout, UA_LOGCATEGORY_USERLAND, "received ctrl-c");
running = false;
}
UA_UInt16 LocalServerNSIndex = 1;
typedef enum {
AA = 0,
BB = 1,
CC = 2,
DD = 3,
__MY_ENUM_FORCE32BIT = 0x7fffffff
} MyEnum;
// Definition DataType
static UA_DataType MyEnumDataType =
{
UA_TYPENAME("MyEnum") /* .typeName */
{
LocalServerNSIndex, UA_NODEIDTYPE_NUMERIC, {
0}}, /* .typeId */
{
LocalServerNSIndex, UA_NODEIDTYPE_NUMERIC, {
0}}, /* .binaryEncodingId */
sizeof(MyEnum), /* .memSize */
UA_DATATYPEKIND_ENUM, /* .typeKind */
true, /* .pointerFree */
1, /* .overlayable */
0, /* .membersSize */
NULL /* .members */
};
// hold enum Of datatype Add to namespace in
UA_StatusCode addMyEnumDataType(UA_Server* server)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_DataTypeAttributes attr = UA_DataTypeAttributes_default;
attr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Data Type");
ret = UA_Server_addDataTypeNode(
server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_ENUMERATION),
UA_NODEID_NUMERIC(0, UA_NS0ID_HASSUBTYPE),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My.Enum"), attr, NULL, &MyEnumDataType.typeId);
return ret;
}
// hold enum The corresponding variable type is added to namespace in
UA_StatusCode addMyEnumVariableType(UA_Server *server, UA_NodeId& myEnumVarTypeId)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_VariableTypeAttributes dattr = UA_VariableTypeAttributes_default;
dattr.description = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var type");
dattr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var type");
dattr.dataType = MyEnumDataType.typeId;
dattr.valueRank = UA_VALUERANK_SCALAR;
MyEnum p = AA;
UA_Variant_setScalar(&dattr.value, &p, &MyEnumDataType);
ret = UA_Server_addVariableTypeNode(server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_BASEDATAVARIABLETYPE),
UA_NODEID_NUMERIC(0, UA_NS0ID_HASSUBTYPE),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My Enum Var type"),
UA_NODEID_NUMERIC(0, UA_NS0ID_BASEDATAVARIABLETYPE),
dattr, NULL, &myEnumVarTypeId);
return ret;
}
// establish enum Variable , To add to namespace in
UA_StatusCode addMyEnumVariable(UA_Server *server, UA_NodeId myEnumVarTypeId)
{
MyEnum p = CC;
UA_VariableAttributes vattr = UA_VariableAttributes_default;
vattr.description = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var");
vattr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var");
vattr.dataType = MyEnumDataType.typeId;
vattr.valueRank = UA_VALUERANK_SCALAR;
UA_Variant_setScalar(&vattr.value, &p, &);
UA_StatusCode ret = UA_STATUSCODE_GOOD;
ret = UA_Server_addVariableNode(server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_OBJECTSFOLDER),
UA_NODEID_NUMERIC(0, UA_NS0ID_ORGANIZES),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My Enum Var"),
myEnumVarTypeId, vattr, NULL, NULL);
return ret;
}
int main(void)
{
signal(SIGINT, stopHandler);
signal(SIGTERM, stopHandler);
UA_Server *server = UA_Server_new();
UA_ServerConfig *config = UA_Server_getConfig(server);
UA_ServerConfig_setDefault(config);
UA_StatusCode ret = addMyEnumDataType(server);
if (UA_StatusCode_isGood(ret))
{
UA_NodeId myEnumVarTypeId;
ret = addMyEnumVariableType(server, myEnumVarTypeId);
if (UA_StatusCode_isGood(ret))
{
ret = addMyEnumVariable(server, myEnumVarTypeId);
}
}
if (UA_StatusCode_isBad(ret))
{
printf("Error\n");
UA_Server_delete(server);
return 0;
}
UA_Server_run(server, &running);
UA_Server_delete(server);
return 0;
}
Run after successful compilation , You can see that the variable is added successfully ,
Its value is 2, because CC The corresponding value is 2
Add custom DataType Also in the namespace in ,
Two add to enum name
From the code above, we can see that although enum Variable added , Seems to be with a int There is no difference between types of data , It's better to reflect its name , Here is how to give enum Type add the corresponding name ,
Here we define a function addEnumString, For giving enum Of DataType Add name , as follows ,
UA_StatusCode addEnumString(UA_Server *server)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_VariableAttributes attr = UA_VariableAttributes_default;
attr.minimumSamplingInterval = 0.000000;
attr.userAccessLevel = 1;
attr.accessLevel = 1;
attr.valueRank = 1;
attr.arrayDimensionsSize = 1;
UA_UInt32 arrayDimensions[1];
arrayDimensions[0] = 0;
attr.arrayDimensions = &arrayDimensions[0];
attr.dataType = UA_NODEID_NUMERIC(0, 21LU);
UA_LocalizedText my_enum_variant_DataContents[4];
my_enum_variant_DataContents[0] = UA_LOCALIZEDTEXT((char*)"", (char*)"AA");
my_enum_variant_DataContents[1] = UA_LOCALIZEDTEXT((char*)"", (char*)"BB");
my_enum_variant_DataContents[2] = UA_LOCALIZEDTEXT((char*)"", (char*)"CC");
my_enum_variant_DataContents[3] = UA_LOCALIZEDTEXT((char*)"", (char*)"DD");
UA_Variant_setArray(&attr.value, &my_enum_variant_DataContents, (UA_Int32) 4, &UA_TYPES[UA_TYPES_LOCALIZEDTEXT]);
attr.displayName = UA_LOCALIZEDTEXT((char*)"", (char*)"EnumStrings");
UA_NodeId enumStringNodeId;
ret = UA_Server_addNode_begin(server, UA_NODECLASS_VARIABLE,
UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
MyEnumDataType.typeId,
UA_NODEID_NUMERIC(0, 46LU),
UA_QUALIFIEDNAME(0, (char*)"EnumStrings"),
UA_NODEID_NUMERIC(0, 68LU),
(const UA_NodeAttributes*)&attr,
&UA_TYPES[UA_TYPES_VARIABLEATTRIBUTES], NULL, &enumStringNodeId);
if (UA_StatusCode_isGood(ret))
{
ret = UA_Server_addNode_finish(server, enumStringNodeId);
}
return ret;
}
Yes 4 Elements are added 4 Names , Be careful enum The value of must be from 0 Start , The following is the sequence plus 1, Otherwise, the name cannot be displayed . In function addMyEnumDataType Call inside addEnumString, as follows ,
UA_StatusCode addMyEnumDataType(UA_Server* server)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_DataTypeAttributes attr = UA_DataTypeAttributes_default;
attr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Data Type");
ret = UA_Server_addDataTypeNode(
server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_ENUMERATION),
UA_NODEID_NUMERIC(0, UA_NS0ID_HASSUBTYPE),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My.Enum"), attr, NULL, &MyEnumDataType.typeId);
if (UA_StatusCode_isGood(ret))
{
ret = addEnumString(server);
}
return ret;
}
Recompile run , You can see that the variable value is followed by its corresponding name ,
stay DataType in , You can also see EnumStrings,
see EnumStrings Value , as follows , Is an array ,
In this way, we have achieved our expectations
The complete code is as follows ,
#include "open62541.h"
static bool running = true;
static void stopHandler(int sig) {
UA_LOG_INFO(UA_Log_Stdout, UA_LOGCATEGORY_USERLAND, "received ctrl-c");
running = false;
}
const UA_UInt16 LocalServerNSIndex = 1;
typedef enum {
AA = 0,
BB = 1,
CC = 2,
DD = 3,
__MY_ENUM_FORCE32BIT = 0x7fffffff
} MyEnum;
static UA_DataType MyEnumDataType =
{
UA_TYPENAME("MyEnum") /* .typeName */
{
LocalServerNSIndex, UA_NODEIDTYPE_NUMERIC, {
0}}, /* .typeId */
{
LocalServerNSIndex, UA_NODEIDTYPE_NUMERIC, {
0}}, /* .binaryEncodingId */
sizeof(MyEnum), /* .memSize */
UA_DATATYPEKIND_ENUM, /* .typeKind */
true, /* .pointerFree */
1, /* .overlayable */
0, /* .membersSize */
NULL /* .members */
};
UA_StatusCode addEnumString(UA_Server *server)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_VariableAttributes attr = UA_VariableAttributes_default;
attr.minimumSamplingInterval = 0.000000;
attr.userAccessLevel = 1;
attr.accessLevel = 1;
attr.valueRank = 1;
attr.arrayDimensionsSize = 1;
UA_UInt32 arrayDimensions[1];
arrayDimensions[0] = 0;
attr.arrayDimensions = &arrayDimensions[0];
attr.dataType = UA_NODEID_NUMERIC(0, 21LU);
UA_LocalizedText my_enum_variant_DataContents[4];
my_enum_variant_DataContents[0] = UA_LOCALIZEDTEXT((char*)"", (char*)"AA");
my_enum_variant_DataContents[1] = UA_LOCALIZEDTEXT((char*)"", (char*)"BB");
my_enum_variant_DataContents[2] = UA_LOCALIZEDTEXT((char*)"", (char*)"CC");
my_enum_variant_DataContents[3] = UA_LOCALIZEDTEXT((char*)"", (char*)"DD");
UA_Variant_setArray(&attr.value, &my_enum_variant_DataContents, (UA_Int32) 4, &UA_TYPES[UA_TYPES_LOCALIZEDTEXT]);
attr.displayName = UA_LOCALIZEDTEXT((char*)"", (char*)"EnumStrings");
UA_NodeId enumStringNodeId;
ret = UA_Server_addNode_begin(server, UA_NODECLASS_VARIABLE,
UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
MyEnumDataType.typeId,
UA_NODEID_NUMERIC(0, 46LU),
UA_QUALIFIEDNAME(0, (char*)"EnumStrings"),
UA_NODEID_NUMERIC(0, 68LU),
(const UA_NodeAttributes*)&attr,
&UA_TYPES[UA_TYPES_VARIABLEATTRIBUTES], NULL, &enumStringNodeId);
if (UA_StatusCode_isGood(ret))
{
ret = UA_Server_addNode_finish(server, enumStringNodeId);
}
return ret;
}
UA_StatusCode addMyEnumDataType(UA_Server* server)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_DataTypeAttributes attr = UA_DataTypeAttributes_default;
attr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Data Type");
ret = UA_Server_addDataTypeNode(
server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_ENUMERATION),
UA_NODEID_NUMERIC(0, UA_NS0ID_HASSUBTYPE),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My.Enum"), attr, NULL, &MyEnumDataType.typeId);
if (UA_StatusCode_isGood(ret))
{
ret = addEnumString(server);
}
return ret;
}
UA_StatusCode addMyEnumVariableType(UA_Server *server, UA_NodeId& myEnumVarTypeId)
{
UA_StatusCode ret = UA_STATUSCODE_GOOD;
UA_VariableTypeAttributes dattr = UA_VariableTypeAttributes_default;
dattr.description = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var type");
dattr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var type");
dattr.dataType = MyEnumDataType.typeId;
dattr.valueRank = UA_VALUERANK_SCALAR;
MyEnum p = AA;
UA_Variant_setScalar(&dattr.value, &p, &MyEnumDataType);
ret = UA_Server_addVariableTypeNode(server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_BASEDATAVARIABLETYPE),
UA_NODEID_NUMERIC(0, UA_NS0ID_HASSUBTYPE),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My Enum Var type"),
UA_NODEID_NUMERIC(0, UA_NS0ID_BASEDATAVARIABLETYPE),
dattr, NULL, &myEnumVarTypeId);
return ret;
}
UA_StatusCode addMyEnumVariable(UA_Server *server, UA_NodeId myEnumVarTypeId)
{
MyEnum p = CC;
UA_VariableAttributes vattr = UA_VariableAttributes_default;
vattr.description = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var");
vattr.displayName = UA_LOCALIZEDTEXT((char*)"en-US", (char*)"My Enum Var");
vattr.dataType = MyEnumDataType.typeId;
vattr.valueRank = UA_VALUERANK_SCALAR;
UA_Variant_setScalar(&vattr.value, &p, &UA_TYPES[UA_TYPES_INT32]);
UA_StatusCode ret = UA_STATUSCODE_GOOD;
ret = UA_Server_addVariableNode(server, UA_NODEID_NUMERIC(LocalServerNSIndex, 0),
UA_NODEID_NUMERIC(0, UA_NS0ID_OBJECTSFOLDER),
UA_NODEID_NUMERIC(0, UA_NS0ID_ORGANIZES),
UA_QUALIFIEDNAME(LocalServerNSIndex, (char*)"My Enum Var"),
myEnumVarTypeId, vattr, NULL, NULL);
return ret;
}
int main(void)
{
signal(SIGINT, stopHandler);
signal(SIGTERM, stopHandler);
UA_Server *server = UA_Server_new();
UA_ServerConfig *config = UA_Server_getConfig(server);
UA_ServerConfig_setDefault(config);
UA_StatusCode ret = addMyEnumDataType(server);
if (UA_StatusCode_isGood(ret))
{
UA_NodeId myEnumVarTypeId;
ret = addMyEnumVariableType(server, myEnumVarTypeId);
if (UA_StatusCode_isGood(ret))
{
ret = addMyEnumVariable(server, myEnumVarTypeId);
}
}
if (UA_StatusCode_isBad(ret))
{
printf("Error\n");
UA_Server_delete(server);
return 0;
}
UA_Server_run(server, &running);
UA_Server_delete(server);
return 0;
}
3、 ... and Summary
This article describes how to add customization enum, And create corresponding variables , Readers can draw a picture of gourd , Add what you need enum. One thing to note , Finally, create enum variable , The type used is int32, Just specify in the variable attribute data type Of id That's it .
边栏推荐
- 学习open62541 --- [67] 添加自定义Enum并显示名字
- Will domestic software testing be biased
- 线程池的拒绝策略
- Tear the Nacos source code by hand (tear the client source code first)
- AI defeated mankind and designed a better economic mechanism
- Learn to make dynamic line chart in 3 minutes!
- 6.关于jwt
- 面试唯品会实习测试岗、抖音实习测试岗【真实投稿】
- [paper sharing] where's crypto?
- A few simple steps to teach you how to see the K-line diagram
猜你喜欢
socket编程之常用api介绍与socket、select、poll、epoll高并发服务器模型代码实现
Year SQL audit platform
【C语言】字符串函数
Performance test process and plan
如何选择合适的自动化测试工具?
[论文分享] Where’s Crypto?
[trusted computing] Lesson 13: TPM extended authorization and key management
清华、剑桥、UIC联合推出首个中文事实核查数据集:基于证据、涵盖医疗社会等多个领域
学习open62541 --- [67] 添加自定义Enum并显示名字
go语言的字符串类型、常量类型和容器类型
随机推荐
[PaddleSeg源码阅读] PaddleSeg Validation 中添加 Boundary IoU的计算(1)——val.py文件细节提示
[trusted computing] Lesson 12: TPM authorization and conversation
Industry case | digital operation base helps the transformation of life insurance industry
[Tawang methodology] Tawang 3W consumption strategy - U & a research method
What is the general yield of financial products in 2022?
Interview vipshop internship testing post, Tiktok internship testing post [true submission]
2022-07-04 matlab读取视频帧并保存
Comparison and selection of kubernetes Devops CD Tools
Kirk Borne的本周学习资源精选【点击标题直接下载】
强化学习-学习笔记8 | Q-learning
不能忽略的现货白银短线操作小技巧
Redis的发布与订阅
CVPR 2022丨学习用于小样本语义分割的非目标知识
2022年理财有哪些产品?哪些适合新手?
低代码助力企业数字化转型会让程序员失业?
String type, constant type and container type of go language
Save the memory of the model! Meta & UC Berkeley proposed memvit. The modeling time support is 30 times longer than the existing model, and the calculation amount is only increased by 4.5%
Simple configuration of single arm routing and layer 3 switching
Antisamy: a solution against XSS attack tutorial
【demo】循环队列及条件锁实现goroutine间的通信