diff --git a/Opc.Ua.ModelCompiler/ModelGenerator2.cs b/Opc.Ua.ModelCompiler/ModelGenerator2.cs
index f838c1d..9ad00cc 100644
--- a/Opc.Ua.ModelCompiler/ModelGenerator2.cs
+++ b/Opc.Ua.ModelCompiler/ModelGenerator2.cs
@@ -3916,6 +3916,14 @@ private bool WriteTemplate_ListOfTypes(Template template, Context context)
new LoadTemplateEventHandler(LoadTemplate_ListOfEncodingMaskFields),
null);
+ AddTemplate(
+ template,
+ "// EncodingMaskProperty",
+ TemplatePath + "Version2.EncodingMaskProperty.cs",
+ new DataTypeDesign[] { dataType },
+ new LoadTemplateEventHandler(LoadTemplate_EncodingMaskProperty),
+ new WriteTemplateEventHandler(WriteTemplate_EncodingMaskProperty));
+
AddTemplate(
template,
"// ListOfEncodedFields",
@@ -4701,7 +4709,7 @@ private string LoadTemplate_ListOfEncodedFields(Template template, Context conte
if (field.IsOptional)
{
- template.Write($"if ((EncodingMask & (uint){dataType.ClassName}Fields.{field.Name}) != 0) ");
+ template.Write($"if ((EncodingMask & {dataType.ClassName}Fields.{field.Name}) != 0) ");
}
string functionName = field.DataTypeNode.BasicDataType.ToString();
@@ -4872,7 +4880,7 @@ private string LoadTemplate_ListOfDecodedFields(Template template, Context conte
if (field.IsOptional)
{
- template.Write($"if ((EncodingMask & (uint){dataType.ClassName}Fields.{field.Name}) != 0) ");
+ template.Write($"if ((EncodingMask & {dataType.ClassName}Fields.{field.Name}) != 0) ");
}
string functionName = field.DataTypeNode.BasicDataType.ToString();
@@ -5030,7 +5038,7 @@ private string LoadTemplate_ListOfComparedFields(Template template, Context cont
if (field.IsOptional)
{
- template.Write($"if ((EncodingMask & (uint){dataType.ClassName}Fields.{field.Name}) != 0) ");
+ template.Write($"if ((EncodingMask & {dataType.ClassName}Fields.{field.Name}) != 0) ");
}
template.Write("if (!Utils.IsEqual({0}, value.{0})) return false;", GetChildFieldName(field));
@@ -5065,7 +5073,7 @@ private string LoadTemplate_ListOfClonedFields(Template template, Context contex
if (field.IsOptional)
{
- template.Write($"if ((EncodingMask & (uint){dataType.ClassName}Fields.{field.Name}) != 0) ");
+ template.Write($"if ((EncodingMask & {dataType.ClassName}Fields.{field.Name}) != 0) ");
}
template.Write("clone.{0} = ({1})Utils.Clone(this.{0});", GetChildFieldName(field), GetSystemTypeName(field.DataTypeNode, field.ValueRank));
@@ -5483,6 +5491,54 @@ private bool WriteTemplate_InitializeOptionalChildren(Template template, Context
}
#endregion
+ #region "// EncodingMaskProperty"
+
+ private string LoadTemplate_EncodingMaskProperty(Template template, Context context)
+ {
+ if (context.Target is not DataTypeDesign _)
+ {
+ return null;
+ }
+
+ return TemplatePath + "Version2.DataTypes.EncodingMaskProperty.cs";
+ }
+
+ private bool WriteTemplate_EncodingMaskProperty(Template template, Context context)
+ {
+ if (context.Target is not DataTypeDesign dataType)
+ {
+ return false;
+ }
+
+ template.AddReplacement("_hide_by_new_", IsFirstDataTypeWithOptionalFields(dataType) ? string.Empty : "new ");
+ template.AddReplacement("_ClassName_", dataType.ClassName);
+
+ var result = template.WriteTemplate(context);
+ template.WriteLine(string.Empty);
+
+ return result;
+ }
+
+ private static bool HasOptionalFields(DataTypeDesign dataType)
+ {
+ return dataType.Fields?.Any(field => field.IsOptional) ?? false;
+ }
+
+ private static bool HasOptionalFieldsInherited(DataTypeDesign dataType)
+ {
+ return dataType.BaseTypeNode is DataTypeDesign baseDataType
+ && (HasOptionalFields(baseDataType) || HasOptionalFieldsInherited(baseDataType));
+ }
+
+ private static bool IsFirstDataTypeWithOptionalFields(DataTypeDesign dataType)
+ {
+ return dataType.IsStructure
+ && HasOptionalFields(dataType)
+ && !HasOptionalFieldsInherited(dataType);
+ }
+
+ #endregion
+
#region "// ListOfPropertiesForType and // ListOfProperties"
private string LoadTemplate_ListOfPropertiesForType(Template template, Context context)
{
diff --git a/Opc.Ua.ModelCompiler/Opc.Ua.ModelCompiler.csproj b/Opc.Ua.ModelCompiler/Opc.Ua.ModelCompiler.csproj
index 26e89da..74cbaf7 100644
--- a/Opc.Ua.ModelCompiler/Opc.Ua.ModelCompiler.csproj
+++ b/Opc.Ua.ModelCompiler/Opc.Ua.ModelCompiler.csproj
@@ -128,6 +128,7 @@
+
@@ -437,6 +438,7 @@
+
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/ConstantsFile.cs b/Opc.Ua.ModelCompiler/Templates/Version2/ConstantsFile.cs
index f6402cc..958afac 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/ConstantsFile.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/ConstantsFile.cs
@@ -26,6 +26,7 @@
*
* The complete license agreement can be found here:
* http://opcfoundation.org/License/MIT/1.00/
+ *
* ======================================================================*/
using System;
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/Class.cs b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/Class.cs
index 5bdc39e..03e3fbf 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/Class.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/Class.cs
@@ -8,10 +8,33 @@ namespace X {
[DataContract(Namespace = _XmlNamespaceUri_)]
public _IsAbstract_partial class _BrowseName_ : IEncodeable, IJsonEncodeable
{
+ #region Fields
+
+ private readonly ExpandedNodeId _typeId;
+ private readonly ExpandedNodeId _binaryEncodingId;
+ private readonly ExpandedNodeId _xmlEncodingId;
+ private readonly ExpandedNodeId _jsonEncodingId;
+
+ #endregion
+
#region Constructors
///
- public _BrowseName_()
+ public _BrowseName_() : this(
+ DataTypeIds._BrowseName_,
+ ObjectIds._BrowseName__Encoding_DefaultBinary,
+ ObjectIds._BrowseName__Encoding_DefaultXml,
+ ObjectIds._BrowseName__Encoding_DefaultJson)
{
+ }
+
+ ///
+ protected _BrowseName_(ExpandedNodeId typeId, ExpandedNodeId binaryEncodingId, ExpandedNodeId xmlEncodingId, ExpandedNodeId jsonEncodingId)
+ {
+ _typeId = typeId;
+ _binaryEncodingId = binaryEncodingId;
+ _xmlEncodingId = xmlEncodingId;
+ _jsonEncodingId = jsonEncodingId;
+
Initialize();
}
@@ -33,37 +56,53 @@ private void Initialize()
#region IEncodeable Members
///
- public virtual ExpandedNodeId TypeId => DataTypeIds._BrowseName_;
+ ExpandedNodeId IEncodeable.TypeId => _typeId;
///
- public virtual ExpandedNodeId BinaryEncodingId => ObjectIds._BrowseName__Encoding_DefaultBinary;
+ ExpandedNodeId IEncodeable.BinaryEncodingId => _binaryEncodingId;
///
- public virtual ExpandedNodeId XmlEncodingId => ObjectIds._BrowseName__Encoding_DefaultXml;
+ ExpandedNodeId IEncodeable.XmlEncodingId => _xmlEncodingId;
///
- public virtual ExpandedNodeId JsonEncodingId => ObjectIds._BrowseName__Encoding_DefaultJson;
+ ExpandedNodeId IJsonEncodeable.JsonEncodingId => _jsonEncodingId;
///
- public virtual void Encode(IEncoder encoder)
+ void IEncodeable.Encode(IEncoder encoder)
{
encoder.PushNamespace(_XmlNamespaceUri_);
- // ListOfEncodedFields
+ OnWriteEncodingMask(encoder);
+ OnEncodeFields(encoder);
encoder.PopNamespace();
}
+ protected virtual void OnWriteEncodingMask(IEncoder encoder) { }
+
+ protected virtual void OnEncodeFields(IEncoder encoder)
+ {
+ // ListOfEncodedFields
+ }
+
///
- public virtual void Decode(IDecoder decoder)
+ void IEncodeable.Decode(IDecoder decoder)
{
decoder.PushNamespace(_XmlNamespaceUri_);
- // ListOfDecodedFields
+ OnReadEncodingMask(decoder);
+ OnDecodeFields(decoder);
decoder.PopNamespace();
}
+ protected virtual void OnReadEncodingMask(IDecoder decoder) { }
+
+ protected virtual void OnDecodeFields(IDecoder decoder)
+ {
+ // ListOfDecodedFields
+ }
+
///
public virtual bool IsEqual(IEncodeable encodeable)
{
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/ClassWithOptionalFields.cs b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/ClassWithOptionalFields.cs
index 92b8997..6f6b3f9 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/ClassWithOptionalFields.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/ClassWithOptionalFields.cs
@@ -21,10 +21,33 @@ public enum _ClassName_Fields : uint
[DataContract(Namespace = _XmlNamespaceUri_)]
public partial class _BrowseName_ : IEncodeable, IJsonEncodeable
{
+ #region Fields
+
+ private readonly ExpandedNodeId _typeId;
+ private readonly ExpandedNodeId _binaryEncodingId;
+ private readonly ExpandedNodeId _xmlEncodingId;
+ private readonly ExpandedNodeId _jsonEncodingId;
+
+ #endregion
+
#region Constructors
///
- public _BrowseName_()
+ public _BrowseName_() : this(
+ DataTypeIds._BrowseName_,
+ ObjectIds._BrowseName__Encoding_DefaultBinary,
+ ObjectIds._BrowseName__Encoding_DefaultXml,
+ ObjectIds._BrowseName__Encoding_DefaultJson)
+ {
+ }
+
+ ///
+ protected _BrowseName_(ExpandedNodeId typeId, ExpandedNodeId binaryEncodingId, ExpandedNodeId xmlEncodingId, ExpandedNodeId jsonEncodingId)
{
+ _typeId = typeId;
+ _binaryEncodingId = binaryEncodingId;
+ _xmlEncodingId = xmlEncodingId;
+ _jsonEncodingId = jsonEncodingId;
+
Initialize();
}
@@ -36,7 +59,7 @@ private void Initialize(StreamingContext context)
private void Initialize()
{
- EncodingMask = (uint)_ClassName_Fields.None;
+ EncodingMask = _ClassName_Fields.None;
// ListOfFieldInitializers
}
#endregion
@@ -44,47 +67,67 @@ private void Initialize()
#region Public Properties
///
[DataMember(Name = "EncodingMask", IsRequired = true, Order = 0)]
- public virtual uint EncodingMask { get; set; }
+ public _ClassName_Fields EncodingMask { get; set; }
// ListOfProperties
#endregion
#region IEncodeable Members
///
- public virtual ExpandedNodeId TypeId => DataTypeIds._BrowseName_;
+ ExpandedNodeId IEncodeable.TypeId => _typeId;
///
- public virtual ExpandedNodeId BinaryEncodingId => ObjectIds._BrowseName__Encoding_DefaultBinary;
+ ExpandedNodeId IEncodeable.BinaryEncodingId => _binaryEncodingId;
///
- public virtual ExpandedNodeId XmlEncodingId => ObjectIds._BrowseName__Encoding_DefaultXml;
+ ExpandedNodeId IEncodeable.XmlEncodingId => _xmlEncodingId;
///
- public virtual ExpandedNodeId JsonEncodingId => ObjectIds._BrowseName__Encoding_DefaultJson;
+ ExpandedNodeId IJsonEncodeable.JsonEncodingId => _jsonEncodingId;
///
- public virtual void Encode(IEncoder encoder)
+ void IEncodeable.Encode(IEncoder encoder)
{
encoder.PushNamespace(_XmlNamespaceUri_);
- encoder.WriteEncodingMask((uint)EncodingMask);
- // ListOfEncodedFields
+ OnWriteEncodingMask(encoder);
+ OnEncodeFields(encoder);
encoder.PopNamespace();
}
+ protected virtual void OnWriteEncodingMask(IEncoder encoder)
+ {
+ encoder.WriteEncodingMask((uint)EncodingMask);
+ }
+
+ protected virtual void OnEncodeFields(IEncoder encoder)
+ {
+ // ListOfEncodedFields
+ }
+
+
///
- public virtual void Decode(IDecoder decoder)
+ void IEncodeable.Decode(IDecoder decoder)
{
decoder.PushNamespace(_XmlNamespaceUri_);
- EncodingMask = decoder.ReadEncodingMask(m_FieldNames);
-
- // ListOfDecodedFields
+ OnReadEncodingMask(decoder);
+ OnDecodeFields(decoder);
decoder.PopNamespace();
}
+ protected virtual void OnReadEncodingMask(IDecoder decoder)
+ {
+ EncodingMask = (_ClassName_Fields)decoder.ReadEncodingMask(m_FieldNames);
+ }
+
+ protected virtual void OnDecodeFields(IDecoder decoder)
+ {
+ // ListOfDecodedFields
+ }
+
///
public virtual bool IsEqual(IEncodeable encodeable)
{
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClass.cs b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClass.cs
index 3c2e147..f03bf31 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClass.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClass.cs
@@ -9,8 +9,19 @@ namespace X {
public partial class _BrowseName_ : _BaseType_
{
#region Constructors
+
///
- public _BrowseName_()
+ public _BrowseName_() : this(
+ DataTypeIds._BrowseName_,
+ ObjectIds._BrowseName__Encoding_DefaultBinary,
+ ObjectIds._BrowseName__Encoding_DefaultXml,
+ ObjectIds._BrowseName__Encoding_DefaultJson)
+ {
+ }
+
+ ///
+ protected _BrowseName_(ExpandedNodeId typeId, ExpandedNodeId binaryEncodingId, ExpandedNodeId xmlEncodingId, ExpandedNodeId jsonEncodingId)
+ : base(typeId, binaryEncodingId, xmlEncodingId, jsonEncodingId)
{
Initialize();
}
@@ -31,41 +42,19 @@ private void Initialize()
// ListOfProperties
#endregion
- #region IEncodeable Members
- ///
- public override ExpandedNodeId TypeId => DataTypeIds._BrowseName_;
-
- ///
- public override ExpandedNodeId BinaryEncodingId => ObjectIds._BrowseName__Encoding_DefaultBinary;
-
- ///
- public override ExpandedNodeId XmlEncodingId => ObjectIds._BrowseName__Encoding_DefaultXml;
+ #region Overridden Members
- ///
- public override ExpandedNodeId JsonEncodingId => ObjectIds._BrowseName__Encoding_DefaultJson;
-
- ///
- public override void Encode(IEncoder encoder)
+ ///
+ protected override void OnEncodeFields(IEncoder encoder)
{
- base.Encode(encoder);
-
- encoder.PushNamespace(_XmlNamespaceUri_);
-
+ base.OnEncodeFields(encoder);
// ListOfEncodedFields
-
- encoder.PopNamespace();
}
- ///
- public override void Decode(IDecoder decoder)
+ protected override void OnDecodeFields(IDecoder decoder)
{
- base.Decode(decoder);
-
- decoder.PushNamespace(_XmlNamespaceUri_);
-
+ base.OnDecodeFields(decoder);
// ListOfDecodedFields
-
- decoder.PopNamespace();
}
///
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClassWithOptionalFields.cs b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClassWithOptionalFields.cs
index 6712b5e..6ac7adb 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClassWithOptionalFields.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/DerivedClassWithOptionalFields.cs
@@ -22,8 +22,18 @@ public enum _ClassName_Fields : uint
public partial class _BrowseName_ : _BaseType_
{
#region Constructors
+
+ public _BrowseName_() : this(
+ DataTypeIds._BrowseName_,
+ ObjectIds._BrowseName__Encoding_DefaultBinary,
+ ObjectIds._BrowseName__Encoding_DefaultXml,
+ ObjectIds._BrowseName__Encoding_DefaultJson)
+ {
+ }
+
///
- public _BrowseName_()
+ protected _BrowseName_(ExpandedNodeId typeId, ExpandedNodeId binaryEncodingId, ExpandedNodeId xmlEncodingId, ExpandedNodeId jsonEncodingId)
+ : base(typeId, binaryEncodingId, xmlEncodingId, jsonEncodingId)
{
Initialize();
}
@@ -41,44 +51,34 @@ private void Initialize()
#endregion
#region Public Properties
+ // EncodingMaskProperty
// ListOfProperties
#endregion
- #region IEncodeable Members
- ///
- public override ExpandedNodeId TypeId => DataTypeIds._BrowseName_;
-
- ///
- public override ExpandedNodeId BinaryEncodingId => ObjectIds._BrowseName__Encoding_DefaultBinary;
+ #region Overridden Members
- ///
- public override ExpandedNodeId XmlEncodingId => ObjectIds._BrowseName__Encoding_DefaultXml;
+ ///
+ protected override void OnWriteEncodingMask(IEncoder encoder)
+ {
+ encoder.WriteEncodingMask((uint)EncodingMask);
+ }
- ///
- public override ExpandedNodeId JsonEncodingId => ObjectIds._BrowseName__Encoding_DefaultJson;
-
- ///
- public override void Encode(IEncoder encoder)
+ ///
+ protected override void OnEncodeFields(IEncoder encoder)
{
- base.Encode(encoder);
-
- encoder.PushNamespace(_XmlNamespaceUri_);
-
+ base.OnEncodeFields(encoder);
// ListOfEncodedFields
-
- encoder.PopNamespace();
}
- ///
- public override void Decode(IDecoder decoder)
+ protected override void OnReadEncodingMask(IDecoder decoder)
{
- base.Decode(decoder);
-
- decoder.PushNamespace(_XmlNamespaceUri_);
+ EncodingMask = (_ClassName_Fields)decoder.ReadEncodingMask(m_FieldNames);
+ }
+ protected override void OnDecodeFields(IDecoder decoder)
+ {
+ base.OnDecodeFields(decoder);
// ListOfDecodedFields
-
- decoder.PopNamespace();
}
///
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/EncodingMaskProperty.cs b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/EncodingMaskProperty.cs
new file mode 100644
index 0000000..da232c1
--- /dev/null
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/DataTypes/EncodingMaskProperty.cs
@@ -0,0 +1,7 @@
+class _Name_{
+// ***START***
+///
+[DataMember(Name = "EncodingMask", IsRequired = true, Order = 0)]
+public _hide_by_new__ClassName_Fields EncodingMask { get; set; }
+// ***END***
+}
\ No newline at end of file
diff --git a/Opc.Ua.ModelCompiler/Templates/Version2/TypesFile.cs b/Opc.Ua.ModelCompiler/Templates/Version2/TypesFile.cs
index fdb6c23..d6391b2 100644
--- a/Opc.Ua.ModelCompiler/Templates/Version2/TypesFile.cs
+++ b/Opc.Ua.ModelCompiler/Templates/Version2/TypesFile.cs
@@ -26,6 +26,7 @@
*
* The complete license agreement can be found here:
* http://opcfoundation.org/License/MIT/1.00/
+ *
* ======================================================================*/
using System;