{"id":1762,"date":"2008-02-17T20:37:13","date_gmt":"2008-02-18T00:37:13","guid":{"rendered":"http:\/\/www.hoogervorst.ca\/arthur\/?p=1762"},"modified":"2008-02-27T21:53:23","modified_gmt":"2008-02-28T01:53:23","slug":"propertygrids-in-c","status":"publish","type":"post","link":"http:\/\/www.hoogervorst.ca\/arthur\/?p=1762","title":{"rendered":"PropertyGrids in C#"},"content":{"rendered":"<p><span class=\"dropcap\">Y<\/span>esterday, <a href='http:\/\/www.hoogervorst.ca\/arthur\/?attachment_id=1761' rel='attachment wp-att-1761' title='An example property grid'><img class=\"alignright\"  src='http:\/\/www.hoogervorst.ca\/arthur\/wp-content\/uploads\/2008\/02\/pro_per_ty_grid.thumbnail.jpg' alt='An example property grid' \/><\/a>I decided to tackle .Net&#8217;s <a href=\"http:\/\/msdn2.microsoft.com\/en-us\/library\/system.windows.forms.propertygrid.aspx\">PropertyGrid component<\/a>: for Helios, I was working on code to allow users to view Datasource-specific data at run-time. For this, I already had several support objects programmed and ready to go, and what better to test them right in that PropertyGrid component?\n<\/p>\n<p>This worked out easier than I thought: Basically, the only thing you need to do as a programmer is to actually create those objects and assign it to &#8216;SelectedObject&#8217; property of the component. This works in most cases, however,  I had a TServerPropertyObject contained inside a TDataSourceObject (half-pseudocode follows):\n<\/p>\n<p><pre>\r\npublic class TServerPropertyObject\r\n{\r\n     public string GroupByBehaviour {get; set;}\r\n     public string IdentifierCase{get; set;}\r\n     \/\/ etc...\r\n}\r\n\r\npublic class TDataSourceObject\r\n{\r\n     private TServerPropertyObject fserverproperties = \r\n             new TServerPropertyObject();\r\n\r\n     public string ServerName {get; set; }\r\n\r\n     public string DSN { get; set; }\r\n\r\n     public TServerPropertyObject Properties { \r\n          get { return fserverproperties; }\r\n     }\r\n}\r\n<\/pre>\n<\/p>\n<p>Obviously, the idea is to have the properties object of TDataSourceObject to show as a &#8216;collapsible&#8217; item in the PropertyGrid component. To achieve this, you need to add (those devilish) so called &#8216;property attributes&#8217; (I believe these are the only things that makes .Net look evil). In our case of the collapsible item, we&#8217;re going to use the <a href=\"http:\/\/msdn2.microsoft.com\/en-us\/library\/system.componentmodel.typeconverter.aspx\">&#8216;TypeConverter&#8217;<\/a> class and pass it the ExpandableObjectConvertor type.\n<\/p>\n<p><pre>\r\npublic class TDataSourceObject\r\n{\r\n     private TServerPropertyObject fserverproperties = \r\n             new TServerPropertyObject();\r\n\r\n     public string ServerName {get; set; }\r\n\r\n     public string DSN { get; set; }\r\n\r\n     \/\/ Make this property expandable and let .Net\r\n     \/\/ figure out what to do with the object.\r\n     [ TypeConverter(\r\n           typeof(ExpandableObjectConverter)),\r\n        Category(\"Connection\"),\r\n        Description(\"Server properties\")]\r\n     public TServerPropertyObject Properties { \r\n          get { return fserverproperties; }\r\n     }\r\n}\r\n<\/pre>\n<\/p>\n<p>This will let .Net handle (and figure out) what to do with the object itself: In my case the contained object only exposed simple types (like strings and integers). Naturally, you&#8217;ll have to do a lot more work (read coding) when your objects (and components) need specialized &#8216;property-editors&#8217;: for that, I have to refer you to the .Net documentation.\n<\/p>\n<div class=\"reference\">\n<p>Update: See also <a href=\"http:\/\/www.hoogervorst.ca\/arthur\/?page_id=1757\">here<\/a> for more context and a larger screenshot (outdated though but still relevant).\n<\/p>\n<\/div>\n","protected":false},"excerpt":{"rendered":"<p>Yesterday, I decided to tackle .Net&#8217;s PropertyGrid component: for Helios, I was working on code to allow users to view Datasource-specific data at run-time. For this, I already had several support objects programmed and ready to go, and what better &hellip; <a href=\"http:\/\/www.hoogervorst.ca\/arthur\/?p=1762\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":[],"categories":[4],"tags":[56,88],"_links":{"self":[{"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=\/wp\/v2\/posts\/1762"}],"collection":[{"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1762"}],"version-history":[{"count":0,"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=\/wp\/v2\/posts\/1762\/revisions"}],"wp:attachment":[{"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1762"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1762"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/www.hoogervorst.ca\/arthur\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1762"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}