Is application state in Ember too much coupled to the URL?

Does Ember support a paradigm like the UINavigationController in Cocoa? It would be great if there was some way to use view controllers to create complex view hierarchies that don’t match the URL one-to-one. Like navigation controllers inside tab controllers for example.

It seems Ember currently relies on a lot of singleton controllers and the router doesn’t really support anything like a controller that manages a ‘controller hierarchy’.

Perhaps I’m just not familiar enough with Ember and it’s inner workings, and it does support something like this?

2 Likes

I actually have the same question. It would be pretty useful if a controller can manage a controller hierarchy. It is really common that a component would have its own logic which should be put into its own controller, and there is a parent controller that manages this controller. I feel I have to “bend” the framework every time when I want to share some complex component.

Maybe I just do not know the ember way of doing this properly?

Nobody could give insight on this? It would be a pity if this wasn’t possible with Ember. I really love the framework so far but I feel it could be so much more powerful with a paradigm like this.

There’s an important distinction between a Cocoa view hierarchy and the way Ember does things: in Ember, every state needs to map to a URL, and needs to play nice with the browser’s own navigation.

So in an Ember application, you essentially always have a UINavigationController managing a stack of states for you – the browser itself!

We can use the router DSL to succinctly define arbitrarily nested hierarchies of view controllers, and the browser takes care of letting the user navigate forward and backward through them.

This is actually a critical point. The whole reason Ember exists is to embrace the nature of the web instead of trying to fight it. That’s why Ember forked off from Sproutcore, which tries to hide the web and make it look like native application development.

Yeah, it’s true that the URL/browser is basically the stack manager. There is however one difference:

With UINavigationControllers, you can indefinitely push the same controller on the stack. In Ember this doesn’t work because the router destroys the previous view when rendering into the same outlet, and the controller is a singleton.

This is partly because there is a one-to-one relationship between the current controller and the URL. If we could break this relationship, more complex views would be possible IMHO.

For example: An interface that layers the current controller on top of the previously visited controllers. When transitioning to a new route, the new controller is rendered on top of the previous one, even the same controller class with a different model. The URL does not need to reflect the whole tree, it can just display the current active item. When reloading the URL, all the intermediary controllers are not recreated, but merely the first and current one.

EDIT
The more I think of this, the more I start to question the one-view-at-a-time outlets and the way of toggling child views.

{{if greetVisible}}
  Hi there
{{/if}}

It’s nice to have code like this because it enables very rapid development. But it also creates some form of a lock in. You can’t easily animate in/out the childView and stacked views etc. can’t be done easily.

Hey @Rengers, does https://github.com/emberjs/ember.js/pull/3424 help?

That’s a nice feature and definitely seems useful. But it’s not a real solution for the problem of application state being coupled to the URL.

How, for example, would you implement: a popup view, inside which is a ‘navigation controller’ that allows you to drill drown into the view hierarchy using animation, without changing the URL? Since state is very tightly coupled to the URL, it’s not that easy AFAIK.


By the way, I don’t want to sound negative and just post negative points. I would love to dive into the framework and submit some pull requests, but since I don’t have enough knowledge for that yet, I am to posting here ;).

What you’re actually accessing are routes and resources, which have an optional path for the URL. For example, you may have this.route(“login”, { path: ‘/sign-out’}) that would log you in regardless of what the URL is telling you.

What you actually want to look into if you want modals/popups and you dont want to switch routes, then you can either use a nested outlet or render a view in place. Use {{render}} or an {{outlet}} and manage state from within your controller.

Yeah I could use {{render}} or components to render without the router. But it requires a lot of work to make something like a view/controller stack/ The default Ember router cannot be used, because it’s coupled to the URL too much.

And since controllers shouldn’t know about the view, where would I put stuff to render new views and manage the hierarchy?