G
Guest
I want to use the property grid to display instances of dynamic types. A
problem I'm having is that the property grid is not respecting attributes
that are set with SetCustomAttribute. I've taken an example from MSDN and
added a few lines to set the CateoryAttribute of my property. Unfortunetly
it still comes up as misc. What's wrong with this sample?
public static Assembly DefineDynamicAssembly(AppDomain domain)
{
// Build a dynamic assembly using Reflection Emit API.
AssemblyName assemblyName = new AssemblyName();
assemblyName.Name = "MyDynamicAssembly";
AssemblyBuilder assemblyBuilder =
domain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
ModuleBuilder moduleBuilder =
assemblyBuilder.DefineDynamicModule("MyDynamicModule");
typeBuilder = moduleBuilder.DefineType("MyDynamicType",
TypeAttributes.Public);
FieldBuilder customerNameBldr = typeBuilder.DefineField("customerName",
typeof(string),
FieldAttributes.Private);
PropertyBuilder custNamePropBldr =
typeBuilder.DefineProperty("CustomerName",
PropertyAttributes.RTSpecialName |PropertyAttributes.SpecialName,
typeof(string),
new Type[] { typeof(string) });
Type attType = typeof(System.ComponentModel.CategoryAttribute);
ConstructorInfo constructorInfo = attType.GetConstructor(new
Type[]{typeof(string)});
CustomAttributeBuilder attributeBuilder = new
CustomAttributeBuilder(constructorInfo, new object[]{"Category"});
custNamePropBldr.SetCustomAttribute(attributeBuilder);
// First, we'll define the behavior of the "get" property for
CustomerName as a method.
MethodBuilder custNameGetPropMthdBldr =
typeBuilder.DefineMethod("GetCustomerName",
MethodAttributes.Public,
typeof(string),
new Type[] { });
ILGenerator custNameGetIL = custNameGetPropMthdBldr.GetILGenerator();
custNameGetIL.Emit(OpCodes.Ldarg_0);
custNameGetIL.Emit(OpCodes.Ldfld, customerNameBldr);
custNameGetIL.Emit(OpCodes.Ret);
// Now, we'll define the behavior of the "set" property for CustomerName.
MethodBuilder custNameSetPropMthdBldr =
typeBuilder.DefineMethod("SetCustomerName",
MethodAttributes.Public,
null,
new Type[] { typeof(string) });
ILGenerator custNameSetIL = custNameSetPropMthdBldr.GetILGenerator();
custNameSetIL.Emit(OpCodes.Ldarg_0);
custNameSetIL.Emit(OpCodes.Ldarg_1);
custNameSetIL.Emit(OpCodes.Stfld, customerNameBldr);
custNameSetIL.Emit(OpCodes.Ret);
// Last, we must map the two methods created above to our PropertyBuilder
to
// their corresponding behaviors, "get" and "set" respectively.
custNamePropBldr.SetGetMethod(custNameGetPropMthdBldr);
custNamePropBldr.SetSetMethod(custNameSetPropMthdBldr);
ConstructorBuilder constructorBuilder =
typeBuilder.DefineConstructor(MethodAttributes.Public,
CallingConventions.Standard, null);
ILGenerator ilGenerator = constructorBuilder.GetILGenerator();
ilGenerator.EmitWriteLine("MyDynamicType instantiated!");
ilGenerator.Emit(OpCodes.Ret);
typeBuilder.CreateType();
return assemblyBuilder;
}
}
problem I'm having is that the property grid is not respecting attributes
that are set with SetCustomAttribute. I've taken an example from MSDN and
added a few lines to set the CateoryAttribute of my property. Unfortunetly
it still comes up as misc. What's wrong with this sample?
public static Assembly DefineDynamicAssembly(AppDomain domain)
{
// Build a dynamic assembly using Reflection Emit API.
AssemblyName assemblyName = new AssemblyName();
assemblyName.Name = "MyDynamicAssembly";
AssemblyBuilder assemblyBuilder =
domain.DefineDynamicAssembly(assemblyName, AssemblyBuilderAccess.Run);
ModuleBuilder moduleBuilder =
assemblyBuilder.DefineDynamicModule("MyDynamicModule");
typeBuilder = moduleBuilder.DefineType("MyDynamicType",
TypeAttributes.Public);
FieldBuilder customerNameBldr = typeBuilder.DefineField("customerName",
typeof(string),
FieldAttributes.Private);
PropertyBuilder custNamePropBldr =
typeBuilder.DefineProperty("CustomerName",
PropertyAttributes.RTSpecialName |PropertyAttributes.SpecialName,
typeof(string),
new Type[] { typeof(string) });
Type attType = typeof(System.ComponentModel.CategoryAttribute);
ConstructorInfo constructorInfo = attType.GetConstructor(new
Type[]{typeof(string)});
CustomAttributeBuilder attributeBuilder = new
CustomAttributeBuilder(constructorInfo, new object[]{"Category"});
custNamePropBldr.SetCustomAttribute(attributeBuilder);
// First, we'll define the behavior of the "get" property for
CustomerName as a method.
MethodBuilder custNameGetPropMthdBldr =
typeBuilder.DefineMethod("GetCustomerName",
MethodAttributes.Public,
typeof(string),
new Type[] { });
ILGenerator custNameGetIL = custNameGetPropMthdBldr.GetILGenerator();
custNameGetIL.Emit(OpCodes.Ldarg_0);
custNameGetIL.Emit(OpCodes.Ldfld, customerNameBldr);
custNameGetIL.Emit(OpCodes.Ret);
// Now, we'll define the behavior of the "set" property for CustomerName.
MethodBuilder custNameSetPropMthdBldr =
typeBuilder.DefineMethod("SetCustomerName",
MethodAttributes.Public,
null,
new Type[] { typeof(string) });
ILGenerator custNameSetIL = custNameSetPropMthdBldr.GetILGenerator();
custNameSetIL.Emit(OpCodes.Ldarg_0);
custNameSetIL.Emit(OpCodes.Ldarg_1);
custNameSetIL.Emit(OpCodes.Stfld, customerNameBldr);
custNameSetIL.Emit(OpCodes.Ret);
// Last, we must map the two methods created above to our PropertyBuilder
to
// their corresponding behaviors, "get" and "set" respectively.
custNamePropBldr.SetGetMethod(custNameGetPropMthdBldr);
custNamePropBldr.SetSetMethod(custNameSetPropMthdBldr);
ConstructorBuilder constructorBuilder =
typeBuilder.DefineConstructor(MethodAttributes.Public,
CallingConventions.Standard, null);
ILGenerator ilGenerator = constructorBuilder.GetILGenerator();
ilGenerator.EmitWriteLine("MyDynamicType instantiated!");
ilGenerator.Emit(OpCodes.Ret);
typeBuilder.CreateType();
return assemblyBuilder;
}
}