enthought/enaml — pull request #187 by corranwebster (2012-09-06 14:06:30+00:00)
Title: Using non-Enaml UI components in Async Enaml

*This is not ready to be merged*

This is a start of support for embedding non-Enaml UIs as parts of an Enaml UI (eg. embedding a traits ui inside an Enaml UI), and vice-versa (eg. embedding an Enaml UI inside a Tasks pane).

The basic idea is to add 3 new widgets which I'm currently calling: ProxyWidget, ClientWidget and ClientPanel (I will accept suggestions for other names).

ProxyWidget is a class which holds the basic logic for a place-holder widget which the client is responsible for. It has one attribute, 'proxy_id', and a create_widget() method which asks the client session for an appropriately parented underlying toolkit widget which matches the proxy_id. The default client session implementation maintains a lookup table of proxy_ids to factory functions.

ClientWidget is a ProxyWidget which is also a ConstraintsWidget (yes, that means multiple inheritance, which I'm not entirely happy with), so that it participates in constraints-based layout. ClientWidget is what you would use to embed another UI (eg. an old TraitsUI) inside an Enaml UI.

ClientPanel is a ProxyWidget which will implement the same basic single widget layout strategy as other top-levels, like Window and DockPane (ie. should have a single child which is a Container). This is what you would use to embed an Enaml UI inside a non-Enaml UI (eg. a TaskPane). At this moment, the layout support has not yet been implemented.

The QtLocalClient is modified so that when you start a session, you can pass in an optional client session factory, which defaults to the standard QtClientSession, but could potentially be anything with the right callable signature. The basic pattern that I'm using right now for the client widgets is that this is a factory which creates a standard QtClientSession and then adds the client proxies to that session, but I can see the utility in being able to just give proxies to the client and be done with it.

An example of usage can be found in the examples embedded_traits. It's not pretty, but it works.