Files
Future/Future.Contract/Attributes/ParameterDefine.cs

972 lines
45 KiB
C#
Raw Permalink Normal View History

2025-08-30 17:19:57 +08:00
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Reflection;
using System.Runtime.Serialization;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Controls;
namespace Future.Contract
{
/// <summary>
/// 用于将一个属性标记为一个可以使用参数设计器编辑的参数值
/// </summary>
[DataContract]
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = true)]
public class ParameterDefineAttribute : Attribute, INotifyPropertyChanged, IFuture
{
public event PropertyChangedEventHandler PropertyChanged;
/// <summary>
/// 参数的归类信息
/// </summary>
[DataMember]
private EParameterKind mKind = EParameterKind.General;
public EParameterKind Kind
{
get => this.mKind;
set
{
if (this.mKind != value)
{
this.mKind = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Kind"));
}
}
}
/// <summary>
/// 用于存储自定义参数设置器的类型
/// </summary>
[DataMember]
private Type mSetterType = null;
/// <summary>
/// 自定义参数设置器使用的类型定义
/// </summary>
public Type SetterType
{
get => this.mSetterType;
set { this.mSetterType = value; }
}
/// <summary>
/// 用于存储参数数据类型的内部变量
/// </summary>
[DataMember]
private EParameterType mType = EParameterType.Number;
/// <summary>
/// 参数的数据类型
/// </summary>
public EParameterType Type
{
get => this.mType;
set
{
if (this.mType != value)
{
this.mType = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Type"));
}
}
}
/// <summary>
/// 用于存储参数名称的内部变量
/// </summary>
[DataMember]
private string mName = "PName";
/// <summary>
/// 参数的标识名称
/// </summary>
public string Name
{
get => this.mName;
set
{
if (this.mName != value)
{
this.mName = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Name"));
}
}
}
/// <summary>
/// 用于存储参数标题名称的内部变量
/// </summary>
[DataMember]
private string mTitle = "动态参数";
/// <summary>
/// 参数的标题
/// </summary>
public string Title
{
get => this.mTitle;
set
{
if (mTitle != value)
{
mTitle = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Title"));
}
}
}
/// <summary>
/// 用于存储参数描述信息的内部变量
/// </summary>
[DataMember]
private string mRemark = "动态参数";
/// <summary>
/// 参数描述
/// </summary>
public string Remark
{
get => this.mRemark;
set
{
if (mRemark != value)
{
mRemark = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Remark"));
}
}
}
/// <summary>
/// 用于存储以文本格式记录的参数默认值的内部变量
/// </summary>
[DataMember]
private string mDefault = "";
/// <summary>
/// 以文本形式存储参数的默认取值或是可取值集合
/// </summary>
public string Default
{
get => this.mDefault;
set
{
if (this.mDefault != value)
{
mDefault = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Default"));
}
}
}
/// <summary>
/// 为设计器指示ValueExp是值还是引用
/// </summary>
public bool IsLinked { get => (this.Expression?.StartsWith(FutureInstruct.PR_StartString)) ?? false; }
/// <summary>
/// 用于存储值表达式的内部变量
/// </summary>
[DataMember]
private string mExpression = "";
/// <summary>
/// 参数引用表达式设计器操作的永远是这个属性而非真正的参数值Value属性
/// </summary>
public string Expression
{
get => this.mExpression;
set
{
if (this.mExpression != value)
{
this.mExpression = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("ValueExp"));
this.PropertyChanged(this, new PropertyChangedEventArgs("IsLinked"));
}
}
}
/// <summary>
/// 用于存储候选值的内部变量
/// </summary>
[DataMember]
private string mCandidate = "";
/// <summary>
/// 候选值如果类型存在候选值则必须使用标准Json格式描述可以是JsonObject格式或是JsonArray格式的任意一种描述方式
/// </summary>
public string Candidate
{
get => this.mCandidate;
set
{
if (this.mCandidate != value)
{
this.Candidate = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("Candidate"));
}
}
}
/// <summary>
/// 候选词字典实例专为设计器使用
/// </summary>
public Dictionary<string, object> CandidateMapping
{
get
{
Dictionary<string, object> dicCandidate = null;
if (!string.IsNullOrEmpty(this.Candidate))
{
try
{
//有可能是JsonArray定义的候选词集合
if (this.Candidate[0] == '[')
{
List<object> list = this.Candidate.Decode4Json<List<object>>();
foreach (var item in list) dicCandidate.Add(item.ToString(), item);
}
//有可能是JsonObject定义的候选词集合
else if (this.Candidate[0] == '{') dicCandidate = this.Candidate.Decode4Json<Dictionary<string, object>>();
//不是有效的Json定义格式
else dicCandidate = new Dictionary<string, object>();
}
catch
{
//Json格式有问题丢弃异常不处理返回一个空的字典以免外部引用时出错
dicCandidate = new Dictionary<string, object>();
}
}
return dicCandidate;
}
}
/// <summary>
/// 是否只允许使用候选值进行选择
/// </summary>
[DataMember]
private bool mIsCandidateOnly = false;
/// <summary>
/// 是否只允许使用候选值进行选择
/// </summary>
public bool IsCandidateOnly
{
get
{
//部分类型此项设置无效,只能使用选择模式
if (this.Type == EParameterType.Boolean) return true;
else return mIsCandidateOnly;
}
set { this.mIsCandidateOnly = value; }
}
/// <summary>
/// 标记一个参数是否允许重新定义,数据类型,参数名称,参数标题,参数描述
/// </summary>
[DataMember]
public bool AllowRefine { get; set; } = false;
/// <summary>
/// 标记参数是否允许重设单位名称
/// </summary>
[DataMember]
public bool AllowReUnit { get; set; } = true;
/// <summary>
/// 参数的单位名称字段
/// </summary>
[DataMember]
private string mUnitName;
/// <summary>
/// 参数的单位名称
/// </summary>
public string UnitName
{
get => this.mUnitName;
set
{
if (this.mUnitName == value) return;
mUnitName = value;
this.PropertyChanged(this, new PropertyChangedEventArgs("UnitName"));
}
}
/// <summary>
/// 标记一个属性是否允许用户编辑
/// </summary>
[DataMember]
public bool IsReadOnly { get; set; } = true;
/// <summary>
/// 设置一个参数的排序,不可为负
/// </summary>
[DataMember]
public int DesignSort { get; set; } = 0;
/// <summary>
/// 参数设计器中显示的参数分组名
/// </summary>
[DataMember]
public string GroupName { get; set; } = "";
public PropertyInfo AttachProperty { get; internal set; }
public object AttachObject { get; internal set; }
/// <summary>
/// 克隆当前对象
/// </summary>
/// <returns>克隆后的对象</returns>
public IFuture Clone()
{
return new ParameterDefineAttribute()
{
Name = this.Name,
AllowRefine = this.AllowRefine,
AllowReUnit = this.AllowReUnit,
AttachObject = this.AttachObject,
AttachProperty = this.AttachProperty,
Default = this.Default,
DesignSort = this.DesignSort,
GroupName = this.GroupName,
IsReadOnly = this.IsReadOnly,
Kind = this.Kind,
Remark = this.Remark,
Title = this.Title,
Type = this.Type,
UnitName = this.UnitName,
Expression = this.Expression
};
}
/// <summary>
/// 对象属性覆盖:用引用对象属性覆盖当前对象属性,对引用属性只会实现引用赋值,不做深拷贝
/// </summary>
/// <param name="refer">用于覆盖当前对象属性的源对象</param>
/// <returns>如果源对象类型不是当前对象或是其子类类型则直接覆盖失败返回False</returns>
public bool Cover(IFuture refer)
{
if (refer == null) return false;
ParameterDefineAttribute pda = refer as ParameterDefineAttribute;
if (pda == null) return false;
this.Name = pda.Name;
this.AllowRefine = pda.AllowRefine;
this.AllowRefine = pda.AllowRefine;
this.AttachObject = pda.AttachObject;
this.AttachProperty = pda.AttachProperty;
this.Default = pda.Default;
this.DesignSort = pda.DesignSort;
this.GroupName = pda.GroupName;
this.IsReadOnly = pda.IsReadOnly;
this.Kind = pda.Kind;
this.Remark = pda.Remark;
this.Title = pda.Title;
this.Type = pda.Type;
this.UnitName = pda.UnitName;
this.Expression = pda.Expression;
return true;
}
/// <summary>
/// 校验当前参数的设置是否有效;主要校验【Default默认值】、【ValueExp=值表达式】【Candidate候选词】不检查[""]与[null]
/// </summary>
/// <param name="owner">参数归属</param>
/// <returns>如果校验失败则返回错误信息</returns>
public string Verify(string owner = null)
{
EParameterType type = this.Type;
string ownerName = owner ?? (this.AttachObject as IConfigurableObject)?.Title;
string etypeName = type.GetParameterTypeName();
string eValue = this.mExpression ?? "";
string dValue = this.mDefault ?? "";
string cValue = this.mCandidate ?? "";
StringBuilder result = new StringBuilder();
switch (type)
{
case EParameterType.Boolean:
{
bool sign = true;
bool value = false;
//检查默认值表达式,忽略空值[null]与[""]
if (dValue != "")
{
sign = bool.TryParse(dValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值;请重新设置!");
}
//检查实际值表达式,忽略空值[null]与[""]和上下文引用表达式
if (eValue != "" && !eValue.StartsWith(FutureInstruct.PR_StartString))
{
sign = bool.TryParse(eValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【{eValue}】不是有效的“{etypeName}”值;请重新设置!");
}
//检查候选词表达式,忽略空值[null]与[""]
if (cValue != "" && this.CandidateMapping.Count == 0) result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合【{cValue}】格式不是有效的“非空”JsonArray或JsonObject格式");
else
{
foreach (object cval in this.CandidateMapping.Values)
{
if (!(cval is bool))
{
result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合中存在非布尔值【{(cval?.ToString()) ?? ""}】;请重新设置!");
break;
}
}
}
}
break;
case EParameterType.DateTime:
{
bool sign = true;
DateTime value = DateTime.MinValue;
if (dValue != "")
{
sign = DateTime.TryParse(dValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值;请重新设置!");
}
if (eValue != "" && !eValue.StartsWith(FutureInstruct.PR_StartString))
{
sign = DateTime.TryParse(eValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【{eValue}】不是有效的“{etypeName}”值;请重新设置!");
}
if (cValue != "" && this.CandidateMapping.Count == 0) result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合【{cValue}】格式不是有效的“非空”JsonArray或JsonObject格式");
else
{
foreach (object cval in this.CandidateMapping.Values)
{
if (!(cval is DateTime))
{
result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合中存在非布尔值【{(cval?.ToString()) ?? ""}】;请重新设置!");
break;
}
}
}
}
break;
case EParameterType.Enums:
{
bool sign = true;
int value = 0;
if (dValue != "")
{
sign = int.TryParse(dValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值;请重新设置!");
}
if (eValue != "" && eValue.StartsWith(FutureInstruct.PR_StartString))
{
sign = int.TryParse(eValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【{eValue}】不是有效的“{etypeName}”值;请重新设置!");
}
if (cValue != "" && this.CandidateMapping.Count == 0) result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合【{cValue}】格式不是有效的“非空”JsonArray或JsonObject格式");
else
{
foreach (object cval in this.CandidateMapping.Values)
{
if (!(cval is int))
{
result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合中存在非布尔值【{(cval?.ToString()) ?? ""}】;请重新设置!");
break;
}
}
}
}
break;
case EParameterType.Integer:
{
bool sign = true;
int value = 0;
if (dValue != "")
{
sign = int.TryParse(dValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值;请重新设置!");
}
if (eValue != "" && eValue.StartsWith(FutureInstruct.PR_StartString))
{
sign = int.TryParse(eValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【{eValue}】不是有效的“{etypeName}”值;请重新设置!");
}
if (cValue != "" && this.CandidateMapping.Count == 0) result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合【{cValue}】格式不是有效的“非空”JsonArray或JsonObject格式");
else
{
foreach (object cval in this.CandidateMapping.Values)
{
if (!(cval is int))
{
result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合中存在非布尔值【{(cval?.ToString()) ?? ""}】;请重新设置!");
break;
}
}
}
}
break;
case EParameterType.Number:
{
bool sign = true;
double value = 0;
if (dValue != "")
{
sign = double.TryParse(dValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值;请重新设置!");
}
if (eValue != "" && eValue.StartsWith(FutureInstruct.PR_StartString))
{
sign = double.TryParse(eValue, out value);
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【{eValue}】不是有效的“{etypeName}”值;请重新设置!");
}
if (cValue != "" && this.CandidateMapping.Count == 0) result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合【{cValue}】格式不是有效的“非空”JsonArray或JsonObject格式");
else
{
foreach (object cval in this.CandidateMapping.Values)
{
if (!(cval is double))
{
result.AppendLine($"【{owner}】的参数【{this.Title}】的“候选值”集合中存在非布尔值【{(cval?.ToString()) ?? ""}】;请重新设置!");
break;
}
}
}
}
break;
case EParameterType.String: { } break;//不校验
case EParameterType.RichText: { } break;//不校验
case EParameterType.Variant: { } break;//不校验
case EParameterType.IntArray://不校验候选值
{
if (dValue != "")
{
try { dValue.Decode4Json<List<int>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
if (eValue != "")
{
try { eValue.Decode4Json<List<int>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
}
break;
case EParameterType.NumArray://不校验候选值
{
if (dValue != "")
{
try { dValue.Decode4Json<List<double>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
if (eValue != "")
{
try { eValue.Decode4Json<List<double>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
}
break;
case EParameterType.TxtArray:
{
if (dValue != "")
{
try { dValue.Decode4Json<List<string>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
if (eValue != "")
{
try { eValue.Decode4Json<List<string>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
}
break;
case EParameterType.ValArray:
{
if (dValue != "")
{
try { dValue.Decode4Json<List<object>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
if (eValue != "")
{
try { eValue.Decode4Json<List<object>>(); }
catch { result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】不是有效的“{etypeName}”值请使用标准JsonArray格式设置"); }
}
}
break;
default://暂时先不校验候选值
{
if (dValue != "")
{
dValue = dValue.ToUpper();
if (dValue.StartsWith("0X")) dValue = dValue.Substring(2);
bool sign = true;
foreach (char c in dValue)
{
if (c < 48 || c > 70 || (c > 57 && c < 65))
{
sign = false;
break;
}
}
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】不是有效的“{etypeName}”值请使用标准16进制字符串表示");
}
if (eValue != "")
{
eValue = eValue.ToUpper();
if (eValue.StartsWith("0X")) eValue = eValue.Substring(2);
bool sign = true;
foreach (char c in eValue)
{
if (c < 48 || c > 70 || (c > 57 && c < 65))
{
sign = false;
break;
}
}
if (!sign) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】不是有效的“{etypeName}”值请使用标准16进制字符串表示");
}
switch (type)
{
case EParameterType.Byte:
{
if (dValue != "" && dValue.Length != 2) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】应该是“0x”引导的{2}位16进制数例如“0xA1”");
if (eValue != "" && eValue.Length != 2) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】应该是“0x”引导的{2}位16进制数例如“0xA1”");
}
break;
case EParameterType.Word:
{
if (dValue != "" && dValue.Length != 4) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】应该是“0x”引导的{4}位16进制数例如“0xA123”");
if (eValue != "" && eValue.Length != 4) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】应该是“0x”引导的{4}位16进制数例如“0xA123”");
}
break;
case EParameterType.DWord:
{
if (dValue != "" && dValue.Length != 4) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】应该是“0x”引导的{4}位16进制数例如“0xA1234567”");
if (eValue != "" && eValue.Length != 8) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】应该是“0x”引导的{8}位16进制数例如“0xA1234567”");
}
break;
case EParameterType.LWord:
{
if (dValue != "" && dValue.Length != 4) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】应该是“0x”引导的{4}位16进制数例如“0x0123456789ABCDEF”");
if (eValue != "" && eValue.Length != 16) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】应该是“0x”引导的{16}位16进制数例如“0x0123456789ABCDEF”");
}
break;
case EParameterType.ByteArray:
{
if (dValue != "" && dValue.Length != 4) result.AppendLine($"【{owner}】的参数【{this.Title}】的“默认值”【 {dValue} 】应该是“0x”引导的{4}位16进制数例如“0xAAFF00”");
if (eValue != "" && ((eValue.Length % 2) != 0)) result.AppendLine($"【{owner}】的参数【{this.Title}】的“设置值”【 {eValue} 】应该是“0x”偶数个16进制数例如“0xAAFF00”");
}
break;
default: break;
}
}
break;
}
string strBuffer = result.ToString();
return string.IsNullOrEmpty(strBuffer) ? null : strBuffer;
}
/// <summary>
/// 为一个使用子符串表示的变量变值;注意:不能使用引用表达式,[""]与[null]会返回参数的默认值或C#语言的“类型”默认值!
/// </summary>
/// <param name="sValue">用字符串表示的变量</param>
/// <param name="value">如果成功则存储变量的值</param>
/// <returns>如果失败则返回失败原因,成功则返回“null”</returns>
public string Evaluate(string sValue, out object value)
{
EParameterType type = this.Type;
sValue = string.IsNullOrWhiteSpace(sValue) ? (string.IsNullOrWhiteSpace(this.Default) ? "" : this.Default) : sValue;
if (sValue.StartsWith(FutureInstruct.PR_StartString))
{
value = null;
return $"请先从上下文中获取引用表达式【{sValue}】的值表式再进行求值操作!";
}
string typeName = type.GetParameterTypeName();
string ownerName = ((this.AttachObject as IConfigurableObject)?.Title) ?? "???";
bool sign = true;
object result = null;
StringBuilder strBuilder = new StringBuilder();
//根据不同的参数类型进行不同的求值逻辑;
switch (type)
{
case EParameterType.Boolean:
{
bool oValue = false;
sign = bool.TryParse(sValue, out oValue);
result = oValue;
}
break;
case EParameterType.DateTime:
{
DateTime oValue = DateTime.Now;
sign = DateTime.TryParse(sValue, out oValue);
result = oValue;
}
break;
case EParameterType.Enums:
{
int oValue = 0;
sign = int.TryParse(sValue, out oValue);
result = oValue;
}
break;//需要检查候选值
case EParameterType.Integer:
{
int oValue = 0;
sign = int.TryParse(sValue, out oValue);
result = oValue;
}
break;//需要检查候选值
case EParameterType.Number:
{
double oValue = 0;
sign = double.TryParse(sValue, out oValue);
result = oValue;
}
break;//需要检查候选值
case EParameterType.String: { result = sValue; } break;//需要检查候选值
case EParameterType.RichText: { result = sValue; } break;
case EParameterType.Variant: { result = sValue; } break;
case EParameterType.IntArray:
{
if (sValue == "") result = new List<int>();
else
{
try { result = sValue.Decode4Json<List<int>>(); }
catch { sign = false; result = null; }
}
}
break;
case EParameterType.NumArray:
{
if (sValue == "") result = new List<double>();
else
{
try { result = sValue.Decode4Json<List<double>>(); }
catch { sign = false; result = null; }
}
}
break;
case EParameterType.TxtArray:
{
if (sValue == "") result = new List<string>();
else
{
try { result = sValue.Decode4Json<List<string>>(); }
catch { sign = false; result = null; }
}
}
break;
case EParameterType.ValArray:
{
if (sValue == "") result = new List<object>();
else
{
try { result = sValue.Decode4Json<List<object>>(); }
catch { sign = false; result = null; }
}
}
break;//需要检查候选值
default://所有不同长度的字节码类型
{
string hxValue = sValue ?? "";
hxValue = hxValue.Trim().ToUpper();
if (hxValue.Length > 1 && hxValue.StartsWith("0X")) hxValue = hxValue.Substring(2);
foreach (char c in hxValue)
{
if (c < 48 || c > 70 || (c > 57 && c < 65))
{
sign = false;
break;
}
}
if (!sign) result = null;
else
{
switch (this.Type)
{
case EParameterType.Byte:
{
if (hxValue.Length < 2) hxValue.PadLeft(2, '0');
else hxValue = hxValue.Substring(hxValue.Length - 2);
}
break;
case EParameterType.Word:
{
if (hxValue.Length < 4) hxValue.PadLeft(4, '0');
else hxValue = hxValue.Substring(hxValue.Length - 4);
}
break;
case EParameterType.DWord:
{
if (hxValue.Length < 8) hxValue.PadLeft(8, '0');
else hxValue = hxValue.Substring(hxValue.Length - 8);
}
break;
case EParameterType.LWord:
{
if (hxValue.Length < 16) hxValue.PadLeft(16, '0');
else hxValue = hxValue.Substring(hxValue.Length - 16);
}
break;
case EParameterType.ByteArray:
{
if ((hxValue.Length % 2) != 0) hxValue = $"0{hxValue}";
}
break;
default: break;
}
byte[] bytes = new byte[hxValue.Length / 2];
for (int i = 0; i < bytes.Length; i++)
{
string vhx = hxValue.Substring(i * 2, 2);
bytes[i] = Convert.ToByte(vhx, 16);
}
result = bytes;
}
}
break;
}
value = result;
if (sign) return null;
else
{
string strBuffer = strBuilder.ToString();
return string.IsNullOrEmpty(strBuffer) ? null : strBuffer;
}
}
/// <summary>
/// 获取当前变量的默认值;请使用可空类型接收
/// </summary>
/// <returns>如果未设置则返回该类型的缺省值如果设置错误则返回null</returns>
public object GetDefault()
{
EParameterType type = this.Type;
string sValue = this.Default ?? "";
switch (type)
{
case EParameterType.Boolean:
{
if (sValue == "") return false;
bool result = false;
bool sign = bool.TryParse(sValue, out result);
if (sign) return result;
else return null;
}
case EParameterType.DateTime:
{
if (sValue == "") return DateTime.Now;
DateTime result = DateTime.Now;
bool sign = DateTime.TryParse(sValue, out result);
if (sign) return result;
else return null;
}
case EParameterType.Enums: //本质上是Int
{
if (sValue == "") return default(EParameterType);
int result = 0;
bool sign = int.TryParse(sValue, out result);
if (sign) return result;
else return null;
}
case EParameterType.Integer:
{
if (sValue == "") return default(EParameterType);
int result = 0;
bool sign = int.TryParse(sValue, out result);
if (sign) return result;
else return null;
}
case EParameterType.Number:
{
if (sValue == "") return default(EParameterType);
double result = 0;
bool sign = double.TryParse(sValue, out result);
if (sign) return result;
else return null;
}
case EParameterType.String: return sValue;
case EParameterType.RichText: return sValue;
case EParameterType.Variant: return sValue;
case EParameterType.IntArray:
{
if (sValue == "") return new List<string>();
else
{
try { return sValue.Decode4Json<List<int>>(); }
catch { return null; }
}
}
case EParameterType.NumArray:
{
if (sValue == "") return new List<string>();
else
{
try { return sValue.Decode4Json<List<double>>(); }
catch { return null; }
}
}
case EParameterType.TxtArray:
{
if (sValue == "") return new List<string>();
else
{
try { return sValue.Decode4Json<List<string>>(); }
catch { return null; }
}
}
case EParameterType.ValArray:
{
if (sValue == "") return new List<object>();
else
{
try { return sValue.Decode4Json<List<object>>(); }
catch { return null; }
}
}
default:
{
string hxValue = sValue ?? "";
hxValue = hxValue.Trim().ToUpper();
if (hxValue.Length > 1 && hxValue.StartsWith("0X")) hxValue = hxValue.Substring(2);
bool sign = true;
foreach (char c in hxValue)
{
if (c < 48 || c > 70 || (c > 57 && c < 65))
{
sign = false;
break;
}
}
//如果不是有效的16进制字符串则直接返回null
if (!sign) return null;
else
{
switch (type)
{
case EParameterType.Byte:
{
if (hxValue.Length < 2) hxValue.PadLeft(2, '0');
else hxValue = hxValue.Substring(hxValue.Length - 2);
}
break;
case EParameterType.Word:
{
if (hxValue.Length < 4) hxValue.PadLeft(4, '0');
else hxValue = hxValue.Substring(hxValue.Length - 4);
}
break;
case EParameterType.DWord:
{
if (hxValue.Length < 8) hxValue.PadLeft(8, '0');
else hxValue = hxValue.Substring(hxValue.Length - 8);
}
break;
case EParameterType.LWord:
{
if (hxValue.Length < 16) hxValue.PadLeft(16, '0');
else hxValue = hxValue.Substring(hxValue.Length - 16);
}
break;
case EParameterType.ByteArray:
{
if ((hxValue.Length % 2) != 0) hxValue = $"0{hxValue}";
}
break;
default: break;
}
byte[] bytes = new byte[hxValue.Length / 2];
for (int i = 0; i < bytes.Length; i++)
{
string vhx = hxValue.Substring(i * 2, 2);
bytes[i] = Convert.ToByte(vhx, 16);
}
return bytes;
}
}
}
}
}
}