Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Passing objects to a UITypeEditor

I am currently hoping to use a PropertyGrid to allow users to edit some of my classes, however I've hit a wall with passing objects to the UITypeEditor(s) they use. When the user presses the drop down I want to show a listbox of already loaded textures to choose from, if they want to use a texture the application hasn't loaded yet they can click a button to choose one from a file dialog. In case I make no sense here a mock of the form:

Dropdown Image.

My problem: To fill the listbox I need access to the class that manages the list of resources from the UITypeEditor.

Now I've solved this problem for my own classes by giving them a reference on creation to their managing object. In the UITypeEditor I then use that reference to access what I need. However I can't do this for classes I haven't written, such as the XNA Texture2D class.

Here are what the classes I'm using look like:

class StaticGeometryChunk
{
    // Geometry data to draw with. Contains a reference to its managing 
    // class for use in its UITypeEditor.
    public GeometryData { get; set; }
    ....
}

class Material
{
    // These are XNA classes. I can't just add a reference to its managing 
    // class (I think?).
    public Texture2D Texture1 { get; set; }
    public Texture2D Texture2 { get; set; }
    ....
}

I've been looking at my options and they seem to be:

  1. Make the managing classes static.

I don't really want to do this. There are several managing classes as each resource is loaded differently. There are also classes that need to be created before these and are passed in.

  1. Make the managing classes singletons.

I don't really want to do this either. It seems like a quick and dirty way to "hide" the problem instead of "solve" it. I also might want the option of having several managing classes in the future which the singletons eliminate.

  1. Create a wrapper class which holds the reference to a managing class and its target (such as the XNA Texture2D).

This is currently what I'm thinking of doing. Its would be quite simple and quick to do but something about it nags me but I don't know what.

Any thoughts on the above or other methods to pass what I need into the UITypeEditor?

Thank you for reading.

like image 599
Kath Avatar asked Jun 18 '09 03:06

Kath


2 Answers

In the EditValue method, you are given a context. Use context.Instance to access the object that holds your property. This object should also contain a property that gives you access to the list of things you want to display. You could test if context.Instance is ITextureProvider for example, then cast it and access the textures. Not sure if this makes sense in your design but let me know.

like image 148
Nicolas Cadilhac Avatar answered Oct 02 '22 08:10

Nicolas Cadilhac


As an alternative you can try the following approach. I find it very elegant, because it does not require to store a list of available property values in the object. Therefore, for example, you can show one set of values on one form and another set on another.

  1. Create an interface IYourDataProviderService.
  2. Create an implementation of IYourDataProviderService, which knows the concrete data to provide.
  3. Create a class implementing ISite. In GetService() method return an instance of class which implements IYourDataProviderService, if the serviceType parameter is typeof(IYourDataProviderService). I left rest of ISite methods throwing NotImplementedException (except DesignMode property) and for me it worked, but probably this is not an ideal solution.
  4. In 'Load' event handler assign your implementation to the Site property of your propertygrid.
  5. Enjoy!
like image 32
ironic Avatar answered Oct 02 '22 08:10

ironic