You could just disable the Thumb
and the PropertyGrid
...
Of course, for the PropertyGrid it is not ideal... it would be better to keep it enabled, but read-only, unfortunately the PropertyGrid
doesn't have a ReadOnly
property... A possible solution would be to wrap your object in a custom type descriptor which would present the properties as read-only. Here are two classes to achieve that (sorry for the long code...) :
ReadOnlyTypeDescriptor
:
public class ReadOnlyTypeDescriptor : ICustomTypeDescriptor
{
public ReadOnlyTypeDescriptor(object target)
{
TypeDescriptionProvider provider = TypeDescriptor.GetProvider(target);
_originalDescriptor = provider.GetTypeDescriptor(target);
}
public ReadOnlyTypeDescriptor(ICustomTypeDescriptor descriptor)
{
_originalDescriptor = descriptor;
}
private ICustomTypeDescriptor _originalDescriptor;
private PropertyDescriptor MakeReadOnly(PropertyDescriptor propertyDescriptor)
{
return new ReadOnlyPropertyDescriptor(propertyDescriptor);
}
private PropertyDescriptorCollection MakeReadOnly(PropertyDescriptorCollection propertyDescriptors)
{
var descriptors = propertyDescriptors
.Cast<PropertyDescriptor>()
.Select(pd => new ReadOnlyPropertyDescriptor(pd))
.ToArray();
return new PropertyDescriptorCollection(descriptors, true);
}
#region ICustomTypeDescriptor Members
public AttributeCollection GetAttributes()
{
return _originalDescriptor.GetAttributes();
}
public string GetClassName()
{
return _originalDescriptor.GetClassName();
}
public string GetComponentName()
{
return _originalDescriptor.GetComponentName();
}
public TypeConverter GetConverter()
{
return _originalDescriptor.GetConverter();
}
public EventDescriptor GetDefaultEvent()
{
return _originalDescriptor.GetDefaultEvent();
}
public PropertyDescriptor GetDefaultProperty()
{
return MakeReadOnly(_originalDescriptor.GetDefaultProperty());
}
public object GetEditor(Type editorBaseType)
{
return _originalDescriptor.GetEditor(editorBaseType);
}
public EventDescriptorCollection GetEvents(Attribute[] attributes)
{
return _originalDescriptor.GetEvents(attributes);
}
public EventDescriptorCollection GetEvents()
{
return _originalDescriptor.GetEvents();
}
public PropertyDescriptorCollection GetProperties(Attribute[] attributes)
{
return MakeReadOnly(_originalDescriptor.GetProperties(attributes));
}
public PropertyDescriptorCollection GetProperties()
{
return MakeReadOnly(_originalDescriptor.GetProperties());
}
public object GetPropertyOwner(PropertyDescriptor pd)
{
return _originalDescriptor.GetPropertyOwner(pd);
}
#endregion
}
ReadOnlyPropertyDescriptor
:
public class ReadOnlyPropertyDescriptor : PropertyDescriptor
{
public ReadOnlyPropertyDescriptor(PropertyDescriptor descriptor)
: base(
descriptor.Name,
descriptor.Attributes.Cast<Attribute>().ToArray())
{
_originalDescriptor = descriptor;
}
private PropertyDescriptor _originalDescriptor;
public override bool CanResetValue(object component)
{
return false;
}
public override Type ComponentType
{
get { return _originalDescriptor.ComponentType; }
}
public override object GetValue(object component)
{
return _originalDescriptor.GetValue(component);
}
public override bool IsReadOnly
{
get { return true; }
}
public override Type PropertyType
{
get { return _originalDescriptor.PropertyType; }
}
public override void ResetValue(object component)
{
throw new NotSupportedException();
}
public override void SetValue(object component, object value)
{
throw new NotSupportedException();
}
public override bool ShouldSerializeValue(object component)
{
return _originalDescriptor.ShouldSerializeValue(component);
}
}
To show the object target
as read-only in the PropertyGrid
, just do that :
propertyGrid.SelectedObject = new ReadOnlyTypeDescriptor(target);
It will show the same properties, but they won't be editable...
OK, this solution is probably a little overkill for your needs... but I think it can be handy in some cases ;)