Call function from helper in different .js


#1

i initialize variables in initvar.js

Session.set(‘scoreNlcp’, window.localStorage.getItem(‘scoreNlcp’) || 0);
Session.set(‘scoreNcpf’, window.localStorage.getItem(‘scoreNcpf’) || 0);

function setScoreNutrition() {
alert(“setScoreNutrition”); // this is executed
Session.set(‘scoreNutrition’,
Math.round(
(
parseInt(Session.get(‘scoreNlcp’)) +
parseInt(Session.get(‘scoreNcpf’))
)/2
)
);
}

setScoreNutrition();

this is executed once

when i call the function from another .js with the template’s helpers, the function is not executed - why?

Template.body.events({

"change .fhSlider": function(event, template){
  event.stopPropagation();
  var sliderValue = event.target.value;
  var sliderId = event.target.id;
  alert("test"); //##### this is executed
  setScoreNutrition();  //##### this is not executed
  Session.set(sliderId, sliderValue);
  }

});

when i put it all in one file it works.

this is confusing, i thought i can view all .js files as one …

could someone please elaborate. and what would be the proper way to call the function setScoreNutrition(); from within a seperate templateHelper.js

thanks in advance


#2

I may be wrong but i think all the javascript file are wrapped within an immediate function by meteor. Thus a function that is defined within a javascript file will not be available to helpers in a different file.

If you are writing a helper function to use within all templates use Tempate.registerHelper or you can assign your function to a variable without a var and thus making it global.

setXXX = function(…) {}

Now in a different file you can use setXXX(…);


#3

So this has to do with scoping and the way your function is defined. @suhaila is partially right here and this is being caused by the file level closure that Meteor creates when it builds your app but it’s not something that is hopeless as variables that are globally scoped are not restricted by this closure.

When you define your function as a named function and do not assign it to a variable the function will be scoped to the scope at which the function definition was encountered and will be available in code that runs before it’s definition due to the reference to the function being created at parse-time rather than run time like variable declarations are.

funcOne(); //available at runtime before the function definition

function funcOne() {}; //<--function definition

funcTwo(); //error

var funcTwo = function() {}; //<-- variable declaration

//can be used in combination as well

var funcThree = function funcThree() {};

With your code you are using a named function declaration and so it will not be able to be accessed outside the file level closure. To fix this all you need do is assign the function to a variable that is not declared using a var statement. This will give it a global scope and allow you to access it within other files (respecting of load order of course).

//notice no var or let
setScoreNutrition = function setScoreNutrition() {
    Session.set('scoreNutrition', Math.round((
        parseInt(Session.get('scoreNlcp')) +
        parseInt(Session.get('scoreNcpf')) ) / 2
    ));
}

Hopfully this helps wrap your mind around scoping issues in Meteor :smiley:


#4

__________________________thank you!!!