How do I add classNames to the first element of the page without using a view?

I want to add a wrapper class to the first div element in my page. I used to do this with a view.

view/application.js:

import Ember from 'ember';

export default Ember.View.extend({
	classNames: ['wrapper'],
});

Resulting in the following page:

<body class="ember-application">

<div id="ember573" class="ember-view wrapper">
    the rest of my page in this div
</div>
 
</body>

How is this done now that views are deprecated?

1 Like

If I understand you correctly it’s the same except you use a component.

Yes but routable components have not landed yet. So the first div element of the page can not be a component it is normal template.

1 Like

I don’t think I understand what you’re trying to do, what do you mean by first div element on the page?

If you want to create something like this

<body class="ember-application">
  <div id="ember573" class="ember-view wrapper">
      the rest of my page in this div
  </div>
</body>

you can do something like this

application.hbs

{{#wrapper-component}}
  rest of your app goes here
{{/wrapper-component}}

But this creates additional unnecessary div tags. One of them I can remove by adding tagName: '' But the other one I shouldn’t.

<div id="ember395" class="ember-view">
  <div id="ember416" class="ember-view">
     <div class="wrapper">
       App Content
     </div>
  </div>
</div>

Forgive my slowness but I’m still struggling to understand what you’re going for. Perhaps you could create a jsbin that produces the output you desire with a view and then I can help you make it not a view. http://emberjs.jsbin.com/

I think the real problem is that we are supposed to remove all Ember.Views, but we cannot replace them with Components because there are no Routable Components yet. Would be very cool if we could get some official guidance what to do in such scenarios…

Very Simple:

Ahhh Now I get it,

App = Ember.Application.create();

App.ApplicationView = Ember.Component.extend({
  classNames: ['wrapper'],
});

appears to work fine. Though it seems like over kill to get rid of one div. Out of curiosity are you doing anything else in that view?

I started ember as views were being phased out so I’m not too familiar with the range of problems they solve that can’t be solved by components / controllers in the current setup. Perhaps if you post them, I or others in the community, can try and help.

Not doing anything else there. I just enjoy having a clean DOM. I know it is not the most important thing in the world.

Simply changing it to Component.extend works well to get rid of the deprecation! The File in my ES6 modules is still called application/view.js though. (I’m using POD structure). I know I’m being a little too pedantic here. :wink:

@BenediktD, I usually handle this by adding a <div> in the index.html and binding it in the rootElement on Ember.Application.create().

<body>
<div id="my-ember-app" class="wrapper"></div>
</body>
Ember.Application.create({
  rootElement: '#my-ember-app'
});

Unless you are trying to avoid touching your index.html or have another use for view/application.js; this should be better and you are saving yourself an extra Ember.Component / Ember.View layer that you need to go through.

Nevermind, I just realized this doesn’t solve your problem. You do want to override the ApplicationView, which is deprecated… I have no idea how to solve this and I do remember trying.


Edit: Talked to runspired in Slack. Basically, stick with Ember.View() until the Route Components are added into core :sweat:

2 Likes

Currently we are at Ember 2.2, which has neither views nor routable components. Is there a solution for this? I’m trying to set a class on the outermost ember-view div and don’t want to inadvertently select other sibling divs.

ember install ember-legacy-views

not sure if it works with on application view

Thanks. I was aware of ember-legacy-views. Kind of a big hammer for a small nail, though.

I was more thinking of a way within ember core to achieve this. I assume once the application template becomes a component, this can easily done by setting the classNames on that component. In the interim, I haven’t found a better way than using a little jQuery at runtime.

Doesn’t that break acceptance testing? It did for me.

// app/app.js
Ember.Application.extend({
  ...
  ready() {
    Ember.$('.ember-view').first(); // do what you want with it.
  }
  ...
});

Does that work? I believe the selection is always in traverse order. The first view that’s selected is always the top level node.

So, is it still possible (in 2017) remove/change properties on top level wrapper element ?

3 Likes