.net2.0 PropertyGrid 显示中文后无法使用自定义的编辑器

.NET2.0中如何在PropertyGrid中显示中文,首先你要确认你不得不使用继承ICustomTypeDescriptor、继承PropertyDescriptor,继承UITyperEditor的方法。

然后使用之后发现不能调用自己定义的编辑器了?那么,希望下面的代码能够给你提供帮助。

解决办法核心:

主要在继承ICustomTypeDescriptor的类在重载GetProperties方法时,里面构造PropertyDescriptor子类时

需要传入 正确的属性集合。 代码,attributes = Attribute.GetCustomAttributes(p);。 具体实现看下面的代码

主要是因为 MemberDescriptor中GetEditor的实现,他是根据自身的Attributes查找是否有EditorAttribute

没有则使用默认的。而这个Atrrbutes是外界传入的。继承关系 你的PropertyDescriptor 继承 系统的PropertyDescriptor

系统的PropertyDescriptor 继承 系统的MemberDescriptor。 

感谢.NET Reflector  网上好用的.NET Reflector 已经不多了,需要的可以邮件的。klvk.com@gmail.com

图片,左边有个按钮,能够调用我自定义的对话框。右边的则不会出现。

2011051212110714.jpg

两份代码,一份既可以显示中文又可以调用自定义的编辑器,一份只能显示中文,不能调用自定义的编辑器。

 
  
public class MyTestClass : ICustomTypeDescriptor
{

#region 类内部变量

private string _Name = string .Empty;

[Editor(
typeof (MyEditor), typeof (UITypeEditor))]
public string Name
{
get { return _Name; }
set { _Name = value; }
}


private int _Age = 0 ;

[Editor(
typeof (MyEditor), typeof (UITypeEditor))]
public int Age
{
get { return _Age; }
set { _Age = value; }
}


#endregion


/// <summary>
/// 下面这段代码来源于: http://www.bluespace.cn/Html/Csdn/2_47/View_4702219.html
/// </summary>
/// <returns></returns>
#region ICustomTypeDescriptor 显式接口定义

#region 没什么特别改动的

AttributeCollection ICustomTypeDescriptor.GetAttributes()
{
return TypeDescriptor.GetAttributes( this , true );
}
string ICustomTypeDescriptor.GetClassName()
{
return TypeDescriptor.GetClassName( this , true );
}
string ICustomTypeDescriptor.GetComponentName()
{
return TypeDescriptor.GetComponentName( this , true );
}
TypeConverter ICustomTypeDescriptor.GetConverter()
{
return TypeDescriptor.GetConverter( this , true );
}
EventDescriptor ICustomTypeDescriptor.GetDefaultEvent()
{
return TypeDescriptor.GetDefaultEvent( this , true );
}
PropertyDescriptor ICustomTypeDescriptor.GetDefaultProperty()
{
return null ;
}
object ICustomTypeDescriptor.GetEditor(Type editorBaseType)
{
return TypeDescriptor.GetEditor( this , editorBaseType, true );
}
EventDescriptorCollection ICustomTypeDescriptor.GetEvents()
{
return TypeDescriptor.GetEvents( this , true );
}
EventDescriptorCollection ICustomTypeDescriptor.GetEvents(Attribute[] attributes)
{
return TypeDescriptor.GetEvents( this , attributes, true );
}
PropertyDescriptorCollection ICustomTypeDescriptor.GetProperties()
{
return ((ICustomTypeDescriptor) this ).GetProperties( new Attribute[ 0 ]);
}

object ICustomTypeDescriptor.GetPropertyOwner(PropertyDescriptor pd)
{
return this ;
}

#endregion

#region 主要工作在这里

PropertyDescriptorCollection ICustomTypeDescriptor.GetProperties(Attribute[] attributes)
{
ArrayList props
= new ArrayList();
Type thisType
= this .GetType();
PropertyInfo[] pis
= thisType.GetProperties();
foreach (PropertyInfo p in pis)
{
          //主要是这句代码的作用
//这样,可以在编辑时调用自定义的编辑框
attributes =
Attribute.GetCustomAttributes(p);

if (p.DeclaringType == thisType || p.PropertyType.ToString() == " System.Drawing.Color " )
{
// 判断属性是否显示
BrowsableAttribute Browsable = (BrowsableAttribute)Attribute.GetCustomAttribute(p, typeof (BrowsableAttribute));
if (Browsable != null )
{
if (Browsable.Browsable == true || p.PropertyType.ToString() == " System.Drawing.Color " )
{
PropertyStub psd
= new PropertyStub(p, attributes);
props.Add(psd);
}
}
else
{
PropertyStub psd
= new PropertyStub(p, attributes);
props.Add(psd);
}
}
}
PropertyDescriptor[] propArray
= (PropertyDescriptor[])props.ToArray( typeof (PropertyDescriptor));
return new PropertyDescriptorCollection(propArray);
}

#endregion

#endregion

}



#region PropertyStub 定义

/// <summary>
/// 继承与PropertyDescriptor
/// 主要重载DisplayName,以在PropertyGrid中显示中文
/// </summary>
public class PropertyStub : PropertyDescriptor
{

#region 没什么特别的,但必须有

PropertyInfo info;

public PropertyStub(PropertyInfo propertyInfo, Attribute[] attrs)
:
base (propertyInfo.Name, attrs)
{
this .info = propertyInfo;

}
public override Type ComponentType
{
get { return this .info.ReflectedType; }
}

public override bool IsReadOnly
{
get { return this .info.CanWrite == false ; }
}
public override Type PropertyType
{
get { return this .info.PropertyType; }
}

public override bool CanResetValue( object component)
{
return false ;
}

public override object GetValue( object component)
{
try
{
return this .info.GetValue(component, null );
}
catch
{
return null ;
}
}


public override void SetValue( object component, object value)
{
this .info.SetValue(component, value, null );
}

public override void ResetValue( object component)
{

}

public override bool ShouldSerializeValue( object component)
{
return false ;
}

#endregion

#region 主要工作在这里

// 通过重载下面这个属性,可以将属性在PropertyGrid中的显示设置成中文
public override string DisplayName
{
get
{
// 为了简单的,实现更改名称为中文的功能
return " 很好玩啊 " ;
}
}

#endregion

}


#endregion

不能调用自定义编辑器的

 
  
#region 不能调用自定义编辑器的对比类


public class MyTestClassTwo : ICustomTypeDescriptor
{

#region 类内部变量

private string _Name = string .Empty;

[Editor(
typeof (MyEditor), typeof (UITypeEditor))]
public string Name
{
get { return _Name; }
set { _Name = value; }
}


private int _Age = 0 ;

[Editor(
typeof (MyEditor), typeof (UITypeEditor))]
public int Age
{
get { return _Age; }
set { _Age = value; }
}


#endregion


/// <summary>
/// 下面这段代码来源于: http://www.bluespace.cn/Html/Csdn/2_47/View_4702219.html
/// </summary>
/// <returns></returns>
#region ICustomTypeDescriptor 显式接口定义

#region 没什么特别改动的

AttributeCollection ICustomTypeDescriptor.GetAttributes()
{
return TypeDescriptor.GetAttributes( this , true );
}
string ICustomTypeDescriptor.GetClassName()
{
return TypeDescriptor.GetClassName( this , true );
}
string ICustomTypeDescriptor.GetComponentName()
{
return TypeDescriptor.GetComponentName( this , true );
}
TypeConverter ICustomTypeDescriptor.GetConverter()
{
return TypeDescriptor.GetConverter( this , true );
}
EventDescriptor ICustomTypeDescriptor.GetDefaultEvent()
{
return TypeDescriptor.GetDefaultEvent( this , true );
}
PropertyDescriptor ICustomTypeDescriptor.GetDefaultProperty()
{
return null ;
}
object ICustomTypeDescriptor.GetEditor(Type editorBaseType)
{
return TypeDescriptor.GetEditor( this , editorBaseType, true );
}
EventDescriptorCollection ICustomTypeDescriptor.GetEvents()
{
return TypeDescriptor.GetEvents( this , true );
}
EventDescriptorCollection ICustomTypeDescriptor.GetEvents(Attribute[] attributes)
{
return TypeDescriptor.GetEvents( this , attributes, true );
}
PropertyDescriptorCollection ICustomTypeDescriptor.GetProperties()
{
return ((ICustomTypeDescriptor) this ).GetProperties( new Attribute[ 0 ]);
}

object ICustomTypeDescriptor.GetPropertyOwner(PropertyDescriptor pd)
{
return this ;
}

#endregion

#region 主要工作在这里

PropertyDescriptorCollection ICustomTypeDescriptor.GetProperties(Attribute[] attributes)
{
ArrayList props
= new ArrayList();
Type thisType
= this .GetType();
PropertyInfo[] pis
= thisType.GetProperties();
foreach (PropertyInfo p in pis)
{
// 正式因为缺少下面这句,才不能够调用自定义的编辑对话框
/// /这样,可以在编辑时调用自定义的编辑框
// attributes = Attribute.GetCustomAttributes(p);

if (p.DeclaringType == thisType || p.PropertyType.ToString() == " System.Drawing.Color " )
{
// 判断属性是否显示
BrowsableAttribute Browsable = (BrowsableAttribute)Attribute.GetCustomAttribute(p, typeof (BrowsableAttribute));
if (Browsable != null )
{
if (Browsable.Browsable == true || p.PropertyType.ToString() == " System.Drawing.Color " )
{
PropertyStub psd
= new PropertyStub(p, attributes);
props.Add(psd);
}
}
else
{
PropertyStub psd
= new PropertyStub(p, attributes);
props.Add(psd);
}
}
}
PropertyDescriptor[] propArray
= (PropertyDescriptor[])props.ToArray( typeof (PropertyDescriptor));
return new PropertyDescriptorCollection(propArray);
}

#endregion

#endregion

}


#endregion



#region PropertyStub 定义 两个PropertyStub使用的是同一份

/// <summary>
/// 继承与PropertyDescriptor
/// 主要重载DisplayName,以在PropertyGrid中显示中文
/// </summary>
public class PropertyStub : PropertyDescriptor
{

#region 没什么特别的,但必须有

PropertyInfo info;

public PropertyStub(PropertyInfo propertyInfo, Attribute[] attrs)
: base(propertyInfo.Name, attrs)
{
this.info = propertyInfo;

}
public override Type ComponentType
{
get { return this.info.ReflectedType; }
}

public override bool IsReadOnly
{
get { return this.info.CanWrite == false; }
}
public override Type PropertyType
{
get { return this.info.PropertyType; }
}

public override bool CanResetValue(object component)
{
return false;
}

public override object GetValue(object component)
{
try
{
return this.info.GetValue(component, null);
}
catch
{
return null;
}
}


public override void SetValue(object component, object value)
{
this.info.SetValue(component, value, null);
}

public override void ResetValue(object component)
{

}

public override bool ShouldSerializeValue(object component)
{
return false;
}

#endregion

#region 主要工作在这里

//通过重载下面这个属性,可以将属性在PropertyGrid中的显示设置成中文
public override string DisplayName
{
get
{
//为了简单的,实现更改名称为中文的功能
return "很好玩啊";
}
}

#endregion

}


#endregion

MyEditor的定义

 
  
class MyEditor : UITypeEditor
{
public override object EditValue(System.ComponentModel.ITypeDescriptorContext context, IServiceProvider provider, object value)
{

IWindowsFormsEditorService edSvc
= ((IWindowsFormsEditorService)provider.GetService( typeof (IWindowsFormsEditorService)));
if (edSvc == null )
return null ;

System.Windows.Forms.MessageBox.Show(
" 有点莫名其妙的想知道,你要不要找男朋友啊? " );

return " 好啊 " ;

return value;
}


public override UITypeEditorEditStyle GetEditStyle(System.ComponentModel.ITypeDescriptorContext context)
{
return UITypeEditorEditStyle.Modal;
}

}

示例程序下载

不知道这个算不算解决这个问题的办法?你有没有其他办法?

转载于:https://www.cnblogs.com/klvk/archive/2011/05/12/2044220.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值