0

I have javascript embedded to a view in Rails that uses Turbolinks, e.g:

ViewX.html.haml:

.blah
  Blah

:javascript
 $(function() {
   $(".blah").offset().top;
 });

Everything works fine when I load ViewX. But then when I navigate to View Y I get the following error in console:

Uncaught TypeError: Cannot read property 'top' of undefined

And that error persists as I navigate to other views. It goes away when doing a hard refresh, but returns next time I render ViewX.

My question is how do I have some JS snippets render only for a particular view and not pollute to the rest of the app?

EDIT

Ok, I figured out a way, which is somewhat of a hack, but a contained hack. Change ViewX.html.haml to:

ViewX.html.haml:

.blah
  Blah

%script{:type => "text/javascript", 'data-turbolinks-eval' => 'false'}
 :plain
   $(function() {
     $(".blah").offset().top;
   });
melder
  • 463
  • 2
  • 5
  • 9

1 Answers1

0

A simple way is to have each view have a different css class on the body tag:

var bodyClass = $('body').attr('class');

switch(bodyClass) {
    case 'home-page':
    // do stuff
    break;

    case 'about-page':
    // do stuff
    break;
}

If there is a lot of code for each page, you can use the a module pattern and make each module a separate .js file.

case 'home-page'
  MyModule.initialize(); // set up form validation or whatever you need
break;

Another option (if you can't add a CSS class to the body tag) is to use a hidden <input> tag that holds the name of the view and use that to switch.

var switchJS = $('input[type=hidden]').attr('data-view');
/* i.e. <input type="hidden" data-view="my-home-page" /> */
switch(switchJS) { ...
redconservatory
  • 21,438
  • 40
  • 120
  • 189
  • This is hacky. Yes I can simply do that, or simply wrap code with: if ($(".blah").length == 0), but bookkeeping will become more of an issue when adding more JS down the line. – melder Sep 20 '13 at 01:14
  • I think for a larger scale project it would be something more like this then: http://stackoverflow.com/questions/6167805/using-rails-3-1-where-do-you-put-your-page-specific-javascript-code – redconservatory Sep 20 '13 at 01:20
  • The JS is not in the asset pipeline to begin with... It's embedded in the HAML file and loads when the view is rendered. Afterwards it persists due to turbolinks. That is, when turbolinks is disabled, navigating to another page won't bring up the console error. – melder Sep 20 '13 at 01:48