A trick way would be to block the keystrokes in the PropertyGrid when focus is in the item which you want to be read only, to do this, you should derive from the PropertyGrid control, override its ProcessDialogKey event to return true if the current selected item is the one need to be read only. Something like this:
Code Block
partial class Form1 : Form
public Form1()
private void Form1_Load(object sender, EventArgs e)
this.myPropertyGrid1.SelectedObject = new test();
class test
private string propToBeReadOnly = "aaa";
public string PropToBeReadOnly
get { return propToBeReadOnly; }
set { propToBeReadOnly = value; }
private string something;
public string Something
get { return something; }
set { something = value; }
class myPropertyGrid : PropertyGrid
protected override bool ProcessDialogKey(Keys keyData)
if (this.SelectedGridItem.PropertyDescriptor.DisplayName == "PropToBeReadOnly")
return true;
return base.ProcessDialogKey(keyData);
However, to make it better, you should also block the ContextMenuStrip when right click in the TextBox when focus is in the item you want to be read only, to do this, you have to Implement the IMessageFilter interface to block the right click event, something like this:
Code Block
partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
this.myPropertyGrid1.SelectedObject = new test();
Application.AddMessageFilter(this.myPropertyGrid1);
}
}
class test
{
private string propToBeReadOnly = "aaa";
public string PropToBeReadOnly
{
get { return propToBeReadOnly; }
set { propToBeReadOnly = value; }
}
private string something;
public string Something
{
get { return something; }
set { something = value; }
}
}
class myPropertyGrid : PropertyGrid,IMessageFilter
{
protected override bool ProcessDialogKey(Keys keyData)
{
if (this.SelectedGridItem.PropertyDescriptor.DisplayName
== "PropToBeReadOnly")
{
return true;
}
return base.ProcessDialogKey(keyData);
}
#region public bool PreFilterMessage(ref Message m)
{
if (m.Msg == 0x0204) //WM_RBUTTONDOWN
{
if (this.SelectedGridItem.PropertyDescriptor.DisplayName
== "PropToBeReadOnly")
{
return true;
}
}
return false;
}
#endregion
}
Hello, Perhaps you can add dynamically the property?
PropertySpec ps = ThePropertySpecOf( "PropToBeReadOnly" );
ps.Attributes = new Attribute[1]; ps.Attributes[0] = new ReadOnlyAttribute(true); |