尝试通过更改Browsable属性来删除或放置属性网格上的项目。但是,除非在对象创建时设置了Browsable,否则我的更改Browsable的代码将无法工作。现在我可以手动添加Browsable,但是当我对实体进行更改时(因为仍在开发项目,因此实体有很多变化),我添加的任何其他属性都会消失。我尝试过两种方式设置[Browsable(true)]:链接1和链接2。它们似乎都正确地设置了Browsable,但是当我遍历PropertyDescriptor中的属性时,它不存在(供我更改)。
所以,如果在 Model.Designer.cs 中没有设置“browsable”,我就会得到抛出的异常,但只有当它未被设置时。以下是我的 Model.Designer.cs 的代码示例。
所以我需要一种方法,要么在编辑实体时将可浏览性添加到实体中,使其始终处于打开状态,可能是通过编辑t4来完成,但我甚至不知道从哪里开始;要么另一种添加或删除属性(看到我可能会根据某些逻辑编辑描述)的方法,或者找到我的代码中的漏洞,以便我可以找到并编辑可浏览性(描述和显示名称)。
更新:上面的第二个链接 http://social.msdn.microsoft.com/Forums/en-US/adodotnetentityframework/thread/617ebfca-0f68-4b90-83fd-0da758fadbd0/ 包含了我需要的很多内容,我认为。向类添加一个属性数组变量和一些代码来查看是否设置了该变量似乎具有我正在寻找的效果。但是保持开放以寻找更好的答案。
在我的代码中,我可以更改属性数组以拥有我想要的属性值。
我对此并不完全满意。我必须为每个属性编写代码。
String fieldname = "browsable"; // I also edit "description"
PropertyDescriptor pd = TypeDescriptor.GetProperties(o.GetType())[propertyName];
object attrib = null;
AttributeCollection attribs = pd.Attributes;
foreach (Attribute a in attribs)
{
if (a.GetType() == attributeType)
{
attrib = a;
break;
}
}
// The microsoft documentation leads one to believe the following line of code would find the desired attribute,
// negating the need for the more complete foreach statement above.
// However, it appears to find attribute even when it does not exist. Setting value for "found" attribute
// will result in random memory being changed, which results in very unpredictable behavior.
// attrib = pd.Attributes[t];
if (attrib != null)
{
// locate field that contains value
FieldInfo field = attrib.GetType().GetField(fieldName, BindingFlags.NonPublic | BindingFlags.Instance);
if (field != null)
{
if (field.FieldType == value.GetType())
{
// set field to desired value
field.SetValue(attrib, value);
}
}
}
else
{
throw new Exception("Attribute (" + attributeType.Name + ") does not exist for Property(" + propertyName + ")");
}
所以,如果在 Model.Designer.cs 中没有设置“browsable”,我就会得到抛出的异常,但只有当它未被设置时。以下是我的 Model.Designer.cs 的代码示例。
/// <summary>
/// No Metadata Documentation available.
/// </summary>
[EdmScalarPropertyAttribute(EntityKeyProperty=false, IsNullable=true)]
[DataMemberAttribute()]
[Browsable(false)] // this works, but goes away if change my entity
public Nullable<global::System.TimeSpan> SignoutAfter
{
get
{
return _SignoutAfter;
}
set
{
OnSignoutAfterChanging(value);
ReportPropertyChanging("SignoutAfter");
_SignoutAfter = StructuralObject.SetValidValue(value);
ReportPropertyChanged("SignoutAfter");
OnSignoutAfterChanged();
}
}
private Nullable<global::System.TimeSpan> _SignoutAfter;
partial void OnSignoutAfterChanging(Nullable<global::System.TimeSpan> value);
partial void OnSignoutAfterChanged();
所以我需要一种方法,要么在编辑实体时将可浏览性添加到实体中,使其始终处于打开状态,可能是通过编辑t4来完成,但我甚至不知道从哪里开始;要么另一种添加或删除属性(看到我可能会根据某些逻辑编辑描述)的方法,或者找到我的代码中的漏洞,以便我可以找到并编辑可浏览性(描述和显示名称)。
更新:上面的第二个链接 http://social.msdn.microsoft.com/Forums/en-US/adodotnetentityframework/thread/617ebfca-0f68-4b90-83fd-0da758fadbd0/ 包含了我需要的很多内容,我认为。向类添加一个属性数组变量和一些代码来查看是否设置了该变量似乎具有我正在寻找的效果。但是保持开放以寻找更好的答案。
partial class Client : ICustomTypeDescriptor
{
public Attribute[] SignOutAttributes; // added this
#region ICustomTypeDescriptor Members
... // see the link for the other code
public PropertyDescriptorCollection GetProperties (Attribute[] attributes)
{
var propsColl = TypeDescriptor.GetProperties (this, attributes, true);
var props = new List<PropertyDescriptor> ();
foreach (PropertyDescriptor prop in propsColl)
{
String strUPPERCaseName = prop.Name.ToUpper (); // for my thick fingers
// make sure case values are upper case
switch (strUPPERCaseName)
{
case "SIGNOUTAFTER":
if (SignOutAttributes != null)
{
props.Add(new CustomPropertyDescriptor(prop, SignOutAttributes));
}
else
{
props.Add (new CustomPropertyDescriptor (prop, new Attribute[]
{
new CategoryAttribute("Settings"),
new DisplayNameAttribute("Signout After"),
new BrowsableAttribute(true),
new ReadOnlyAttribute(false)
}));
}
break;
default:
props.Add (prop);
break;
}
}
return new PropertyDescriptorCollection (props.ToArray ());
}
在我的代码中,我可以更改属性数组以拥有我想要的属性值。
_client.SignOutAttributes = new Attribute[]
{
new CategoryAttribute ("My Category"),
new DisplayNameAttribute("Signout After"),
new BrowsableAttribute(true),
new ReadOnlyAttribute(false)
};
我对此并不完全满意。我必须为每个属性编写代码。