Examples of Complex and Nested UIs

In so many subtle ways I find myself fighting with router logic with ember. It may be the mental model I stubbornly cling to, but personally I am finding that thinking about URLs first is more difficult than it seems at first blush.

I will fully admit that I may just be over thinking it, and per Yehuda’s point that this might be an indication of doing something wrong.

I am wondering if anybody has good reference examples that demonstrate complex UI design in practice with ember. By “complex” I mean cases where you have nested view hierarchy and multiple models on a page, and perhaps aggressive use of components to encapsulate view logic, and ultimately a lot going on under a specific route or route state.

Looking for examples to get my mind out of its stubborn point of view and expand my thinking to be more idiomatically ember.

Sorry for the broad question. To be more concrete ideal examples would include

  • compelling and creative use of controllerFor and modelFor as well as needs
  • multiple components on a page
  • visual representation of application and route state in a navigation menu, hud, aside, breadcrumb, or other status area on the page.
  • condensed jump menu that lets you quickly move around items in a collection and between router states
  • master/detail view with nested elements within the detail
  • at the model data layer heavy use of composition from lower more basic models/classes, polymorphism, as opposed to classical inheritance and hierarchy.
  • creative use of filters and computed properties.
3 Likes

We are a fairly complex but have not released yet and we will not open source.

I am not sure what you wanna see exactly. Do you want some code snippets or just want to know how people did it? I do not think we completely followed Ember’s convention though.

Code snippets and common code patterns. Or good examples on github. Just trying to study ways people tackle the issue of complexity when nesting content. I feel I always hit a block when trying to display multiple models and trying to deal with multiple controllers within the context of single specific route. More specifically seeing how people pass data around between components and setup multiple interrelated controllers.

If you don’t want to share source I am also curious to just hear how you tackled specific aspects of complexity.

One case I can think of that applies to what I am working on is a master/detail view but within any given detail view is yet another layer of nested elements or perhaps secondary master/detail type view.

Think tab controller with another secondary tab controller inside some of the tab body elements.

Getting two ArrayControllers to work together can seem a little confusing.

I feel like overall I have list data from multiple and discrete places (models and controllers) I want to bring together on the same page. Some content is backed by ArrayControllers and others parts are specific ObjectControllers. And in some cases I want to show multiple selections from an ArrayController side by side in a comparison view.

Visually what I am trying to accomplish makes sense to me, but wiring together controllers gets a little confusing sometimes.

Components feel like a useful abstraction. But you still have to organize around a specific route and some controller. And the data binding behavior can get complicated.

Another UI pattern I am trying to implement is a table of condensed tabular rows. But as you click a row it expands to reveal more detailed view. Think accordion view that looks like a spreadsheet. But not sure if I should have a route for each expanded view.

But more generally just interested in seeing different ways people nest content.

I should also say that I am assuming large screens for most scenarios but handling responsive design is another wrinkle that adds to the complexity.

We are doing the same thing with an Ember app at work and I would appreciate some examples. It won’t be opensource, but I believe it would be nice to share back to the community things learned after we launch.

You can take a look at my non-trivial open-source project Shepherd Digital Asset Management.

I use modelFor to get the model from another route, such as when editing a record that is being shown (model from show route to edit route). I use needs to reference other controllers,such as the controller for related data.

3 Likes

Very interesting thanks for sharing.

For the table of condensed tabular rows you could render all the data but hide part of it via a CSS class. Then when the user clicks on it you can set a property on that item that triggers a CSS change to show the whole item details. You can do this with a component and a ‘showAll’ action targeted at the component view.

Master/detail you could do by listing all models in the resource route and then showing the selected item in the detail route in a resource route outlet. This preserves the list of items while showing the detail and allows you to nest views inside each other.

2 Likes

I think the one-controller-per-route paradigm makes a lot of sense for many apps, and it’s the simplest to understand, which is why it’s the default. But when your apps start getting as complex as yours are, I don’t think there’s any reason to stay attached to that model too closely.

In these situations I just think of controllers as global collections of objects, using needs to expose the data to whatever view or component needs it. While urls are crucial, ultimately your “business domain” is a separate thing. Your routes and UI could change without affecting your domain objects at all.

Is this the same mental model that you have, but you’re getting stuck on implementation details? Or do you think about it differently?

I second this. One thing Angular brings to the table that I found interesting was the more “modular” approach. I read really thoroughly about the partial inclusion and also the modelFor and controllerFor definitions, but it’d be awesome to see anyone’s real world examples!

@samselikoff that is a very good point about controllers being global collections of objects. Just a bunch of proxies. That is how I think of it too. But then what is the difference between a route and a controller. Perhaps controller is an overloaded concept.

I think I get hung up on the router and always asking myself when I should put logic in the route vs the controller. And more specifically thinking about nested routes. The specific tension is how much state is too much state in any given route. And to answer your question, sometimes just the implementation details and mechanics of setupController seem a little confusing. One specific case is using the model hook in controllers, or attempting to load multiple types of models (not records) in a given route.

Probably I am just over thinking it and being a little too zealous trying to maintain one controller per route. Better just to go with what works and makes sense.

Again thinking of a route as tied to a controller as tied to a model (or array of models), is a simple approach that works with many apps. But I think they definitely have different roles.

I think of a route as higher-level; it’s a state-manager, more like a controller in traditional server-side MVC frameworks like Rails. You enter the route, and the route is responsible for making sure the thing your entering is all set up correctly. Sometimes this involves getting a single array of models, like users, or a single model, like a user. In this case Ember makes it easy, because a route automatically generates a respective controller, view and template.

But in the case where a single state needs multiple arrays of models, use the route to set those different collections up independent from one another. In this case the route isn’t really tied to any of those; maybe you enter the ApplicationRoute which bootstraps up all the global collections, making them available to different pieces of the UI. The route is more of a managing object in that case.

In my mind controller is both a global collection of objects, and a decorator (i.e. presenter in rails):

  • It’s a global collection of objects, because it persists; even if the model(s) change, they are swapped out on a persistent controller. So in that sense it’s like writing var persons = new Backbone.Collection() in Backbone.

  • It’s also a decorator, so any logic you need to massage the data from its server-side state usually belongs on the controller.

Unfortunately I don’t have a ton of experience with deeply nested UIs, and that’s probably where the rubber meets the road. I think a good example would be the most helpful here.

1 Like

Have you checked out the Balanced dashboard?

https://github.com/balanced/balanced-dashboard

3 Likes

That does look like an interesting project example. Thanks for the link.

I should probably add that I think one of the areas where my mental model is stubborn is with binding. I keep wanting to pass around values via functions and arguments. But getting a handle on the two way data binding in more complex scenarios can be a little tricky. At least in my experience.