2010-12-16 13 views
10

Pytanieprzechodzą w zmiennej lokalnej do funkcji zwrotnej

Jak funkcja zwrotna może zachować zmiennej lokalnej, z którego został on utworzony?

Prosty przykład

Tworzę odtwarzacz wideo. Będzie miał suwaki kontrolujące nasycenie, kontrast i odcień. Kiedy użytkownik bawi się suwakami, musi potwierdzić, który suwak został zmieniony i do jakiej wartości został zmieniony. Problem polega na tym, że nazwa suwaka jest lokalną zmienną z zakresu twórcy tego wywołania zwrotnego onChange. W jaki sposób to oddzwanianie może zachować nazwę suwaka?

HTML

<div id="saturation"> 
<div class="track"></div> 
    <div class="knob"></div> 
</div> 
</div> 

<div id="contrast"> 
<div class="track"></div> 
    <div class="knob"></div> 
</div> 
</div> 

<div id="hue"> 
<div class="track"></div> 
    <div class="knob"></div> 
</div> 
</div> 

JS

var elements = [ 
'saturation', 
'contrast', 
'gamma' 
]; 

for(var i = 0; i < sliders.size(); i++) { 
new Control.Slider(
    $(elements[i]).down('.knob'), 
    $(elements[i]).down('.track'), { 
    onChange: function(value) { 
    // ERROR: elements[i] is undefined 
    alert(elements[i] + ' has been changed to ' + value); 
    } 
} 
} 

Odpowiedz

6

tej samej zmiennej, i - kto jest wartość kończy się 4 - jest zobowiązany do każdej funkcji utworzonej wewnątrz pętli. Można owinąć funkcję w innej funkcji, które nazywamy na miejscu i przekazać i jako parametr do tej funkcji:

for(var i = 0; i < sliders.size(); i++) { 
new Control.Slider(
    $(elements[i]).down('.knob'), 
    $(elements[i]).down('.track'), { 
    onChange: (function(inner_i) { function(value) { 
    alert(elements[inner_i] + ' has been changed to ' + value); 
    } })(i) 
} 
} 
+0

To dało mi błąd składni. – JoJo

+3

Wierzę, że to jest poprawna rzecz: onChange: funkcja() { funkcja zwracania (wartość) alert { (elementy [i] + wartość); } } (elements [i]) – JoJo

+0

Patrząc na to, myślałem, że autor był sprytny, pomijając oświadczenie zwrotne; Języki podobne do Lispa domyślnie zwracają ostatnie wyrażenie. Niestety javascript nie jest jednym z nich :( –

8

utworzyć kopię zmiennej dla każdego wywołania zwrotnego, można to zrobić z anonimowej funkcji, która przekazać wartości:

for(var i = 0; i < sliders.size(); i++) { 

    (function(e) { // get a local copy of the current value 

     new Control.Slider(
      $(elements[e]).down('.knob'), 
      $(elements[e]).down('.track'), { 
      onChange: function(value) { 
      // ERROR: elements[e] is undefined 
      alert(elements[e] + ' has been changed to ' + value); 
      } 
     } 

    })(i); // pass in the current value 
} 

ten sposób nie odwołać te same i X razy.

0

Wskaż swoją funkcję wewnątrz zamknięcia w ten sposób:


for(var i = 0; i < sliders.size(); i++) { 
(function(q){ 
new Control.Slider(
    $(elements[q]).down('.knob'), 
    $(elements[q]).down('.track'), { 
    onChange: function(value) { 
    // ERROR: elements[q] is undefined 
    alert(elements[q] + ' has been changed to ' + value); 
    } 
} 
})(i) 
} 
Powiązane problemy