2012-05-17 16 views
7

Si consideri il seguente codice (http://jsfiddle.net/FW36F/1/):fuoco un evento su input.checked = true/false _without_ jQuery

<input type="checkbox" onchange="alert(this.checked)"> 
<button onclick="document.getElementsByTagName('input')[0].checked=!document.getElementsByTagName('input')[0].checked;">toggle</button> 

Se si fa clic sulla casella di controllo, si ottiene un avviso che indica se è selezionata o meno. Grande. Tuttavia, se fai clic sul pulsante di attivazione/disattivazione, la casella di controllo cambia lo stato selezionato, ma l'evento onchange NON viene attivato.

In sostanza, la casella di spunta per una casella di controllo viene attivata solo se l'utente fa effettivamente clic sulla casella di controllo, non se la casella di controllo viene modificata tramite JavaScript. Questo è vero in IE, FF e Chrome. Sembra che questo comportamento sia anche alla specifica.

Tuttavia, ho davvero bisogno di un qualche tipo di evento da attivare se, per qualsiasi motivo, lo stato della casella di controllo cambia. È possibile?

Oh sì, e jQuery non è consentito. E per favore no setTimeout/setInterval soluzioni basate ...

Aggiornamento: Inoltre, dovrei chiarire che il codice sopra è solo a scopo illustrativo. Nel codice reale, è necessario verificare che lo stato della casella di controllo sia selezionato o deselezionato, non solo abilitarlo. Forse sarebbe meglio il codice per illustrare che:

<input type="checkbox" onchange="alert(this.checked)"> 
<button onclick="document.getElementsByTagName('input')[0].checked=true;">check</button> 
<button onclick="document.getElementsByTagName('input')[0].checked=false;">un check</button> 

Inoltre, ci può essere il codice in altre aree non lo facciamo completamente il controllo, che potrebbe fare un semplice .checked = true/false - vorremmo per essere sicuri di vederlo anche

+0

jQuery sarebbe non sparare l'evento di modifica nativo semplicemente impostando il suo valore –

+0

Cosa c'è di sbagliato con i timeout? Non penso che ci sia qualcos'altro che funzionerà. – Jivings

+0

@Jivings: Non posso credere che tu abbia effettivamente chiesto cosa c'è di sbagliato nel polling usando un timeout. È come buttare via i cicli e aggiungere un ritardo al momento della notifica. Meno ritardo, più sprechi i cicli della CPU. Ci sono molte risposte qui che soddisfano il requisito dell'OP –

risposta

5

Le risposte esistenti funzionano perfettamente, anche con l'aggiornamento . Basta essere intelligenti e non chiamare il clic se non è necessario. Inoltre, si prega di non utilizzare JS in linea. È stato OK 10 anni fa.

<input type="checkbox" onchange="alert(this.checked)"> 
<button id='check'>check</button> 
<button id='uncheck'>uncheck</button> 

document.getElementById('check').onclick = function() { 
    if (!this.checked) { 
     this.click(); 
    } 
} 

Se hai bisogno di essere modificati quando uno script modifica il valore, in Firefox, è possibile utilizzare https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Object/watch

Esempio qui http://jsfiddle.net/PPuZ8/

// In FF $ is a shortcut for document.getElementById 
// It doesn't fire when set from the UI, you have to use a regular handler for that 
$('cb').watch("checked", function(){ 
    console.log('Checked state changed from script', arguments); 
    return true; 
}); 

Per esempio, si può usare onpropertychangehttp://msdn.microsoft.com/en-us/library/ie/ms536956(v=vs.85).aspx (Grazie ai jivings per il promemoria)

Esempio: http://jsfiddle.net/PPuZ8/1/

document.getElementById('cb').onpropertychange = function() {  
    if (event.propertyName == 'checked') { 
     console.log('Checked state changed onproperty change');  
    } 
}; 

Per altri browser, è necessario eseguire il polling utilizzando setInterval/setTimeout

+0

@joelarson: cura di commentare? Questo risolve il problema per 2 dei 4 principali browser. –

+0

Questa sembra essere una raccolta di risposte in modo da fare +1 su di me. – Jivings

+0

@JuanMendes - grazie per lo sforzo che ci hai dedicato. Penso che hai coperto tutte le basi, e qualcosa come il tuo primo blocco di codice è alla fine quello che sono andato con. Avremo bisogno di chiamare specificatamente una funzione setCheck per selezionare/deselezionare in javascript, e se altri programmatori dimenticano e semplicemente 'ele.checked = true/false', triste a tale proposito. FWIW, ho usato solo JavaScript inline per questo esempio, non in generale: P – jlarson

1

Usa click()

<button onclick="document.getElementsByTagName('input')[0].checked=!document.getElementsByTagName('input')[0].click();">toggle</button> 
2

Avere il pulsante di commutazione in realtà click la casella di controllo:

<input type="checkbox" onchange="alert(this.checked)"> 
<button onclick="document.getElementsByTagName('input')[0].click()"> 
    toggle 
</button> 

Se si voleva alcuna modifica la casella di informarvi della sua nuova posizione, quindi vorrei creare un metodo globale per modificare il valore della casella di controllo e gestirlo come proxy:

Ora ogni volta che si imposta o si attiva la casella di controllo, si ottiene di nuovo lo stato controllato.

Un'ultima cosa, eviterei di utilizzare l'attributo onClick e invece di associare gli eventi di clic all'interno del codice JavaScript.

+0

Buon suggerimento _BUT_ dobbiamo assicurarci che se un altro codice che non controlliamo fa un checked = true/false che lo catturiamo anche. Inoltre, non abbiamo davvero bisogno di un interruttore, poiché il mio esempio potrebbe essere stato fuorviato: abbiamo bisogno di impostare esplicitamente true o false. – jlarson

+0

@ larson4 Scusate, ma era una brutta domanda allora. – Jivings

+0

@ larson4 Ti suggerisco di utilizzare un metodo proxy per fare clic sulla casella di controllo. – Sampson

Problemi correlati