2

I have this code:

var res = [1024, 1280, 1600],
    vals = [1, 2, 3];

I want to assign a value to a variable on window.resize depending on the resolution that matches in the res array. So i came up with this:

function update() {
  res.forEach(function( res, i ) {
    someVariable = $(window).width() < res ? vals[ i ] : 4;
  });
}

$(window).resize( update );

The problem is that it only works for 1600 but not for all the other resolutions. But if I do the following (hard-coded) it works just fine:

function update() {
  someVariable = $(window).width() < 1024 ? 1
   : $(window).width() < 1280 ? 2
   : $(window).width() < 1600 ? 3
   : 4;
}

Any ideas on how to make this work dynamically?

Edit: I'm thinking I have to break the loop at some point but can't figure out the condition to test...

elclanrs
  • 92,861
  • 21
  • 134
  • 171
  • Where do you define `winWidth` variable? – Ram Jan 07 '13 at 09:04
  • @undefined: I see what you mean, I'm using `$(window).width()` actually so that's not the problem. I'll update that. – elclanrs Jan 07 '13 at 09:07
  • @elclanrs Adil's answer doesn't work. Please accept the other answer so that if people with a similar question find this question, they can find the correct answer. – AlexStack Jan 07 '13 at 10:43

2 Answers2

1

You need to break the loop when first time the condition becomes true and value is assigned to someVariable as with width less then 1024 is also less then 1280 and 1600 and finally you will get the last one which is 1600.

function update() {
  res.forEach(function( res, i ) {
    if(winWidth < res)
     {
       someVariable = vals[ i ];
       return; //break the loop here
     }        
  });
}

Edit as per AlexStack comments, to break the forEach loop as dicussed in this post you can use the following technique.

function update() {
  var exp = {}; 
  try
  {
    res.forEach(function( res, i ) {
       if(winWidth < res)
       {
          someVariable = vals[ i ];
          throw exp;
       }        
    });
  }catch(ex){
      if (e!==exp) throw e;
  }
}
Community
  • 1
  • 1
Adil
  • 146,340
  • 25
  • 209
  • 204
  • Got it! Thanks this is what I was looking for. I had to actually `return false` for it to work. Then I set the default value on the `else` statement. Long day ~ – elclanrs Jan 07 '13 at 09:12
  • the `return` statement DOES NOT intettupr the `forEach()` loop! It merely interrupts the current function. http://stackoverflow.com/questions/2641347/how-to-short-circuit-array-foreach-like-calling-break – AlexStack Jan 07 '13 at 09:15
  • I'm using jQuery's `$.each` with `return false`. My question was merely about "where to break". This helped. – elclanrs Jan 07 '13 at 09:16
  • @Adil please read the link I provided. The `break` command really doesn't interrupt a function. You need to throw an exception. `for` loop is a better candidate than `forEach` for this problem. – AlexStack Jan 07 '13 at 09:17
1

The problem is that forEach is not terminated once a satisfactory result is found. You can solve it like this:

function update() {
  res.sort();//to make sure any future additions to the array doesn't break the order
  for( var i = 0; i < res.length; i++ ) {
    if ( winWidth < res[i] ) {
      someVariable = i + 1;//javascript arrays are 0-based. Add 1 to make it 1-based
      return;//terminate the loop when the result is found
    }
  }
  //if no result is found, this will be executed after the for loop
  someVariable = res.length;
  return;
}

PS. this solution doesn't need the vals array.

AlexStack
  • 16,766
  • 21
  • 72
  • 104