당신은, ... 가능 유지하기 위해 더 나은 것 이상하지 않은 PropertyGrid를 들어, Thumb
과 PropertyGrid
... 물론
을 해제 할 수 그러나 읽기 전용, 불행히도 PropertyGrid
에는 ReadOnly
속성이 없습니다 ... 가능한 해결책은 속성을 읽기 전용으로 제공하는 사용자 지정 형식 설명자에 개체를 래핑하는 것입니다. 여기에 그것을 달성하기 위해 두 개의 클래스 (... 긴 코드에 대한 죄송합니다)입니다
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);
}
}
읽기 전용에서와 같이 객체 target
을 표시하려면 PropertyGrid
, 그냥 그렇게하세요 :
propertyGrid.SelectedObject = new ReadOnlyTypeDescriptor(target);
동일한 속성을 표시하지만 편집 할 수는 없습니다 ...
OK,이 솔루션은 아마도 사용자의 요구에 조금 과잉입니다 ... 그러나 어떤 경우에는 유용 할 수 있다고 생각합니다.)