2012-04-13 3 views
11

Ho letto parecchi metodi diversi per far sì che le checkbox html vengano postate sul server, ma sto davvero cercando di farlo senza modificare nulla tranne $ .serialize. Idealmente, vorrei che le caselle spuntate fossero pubblicate come on e deselezionate per essere pubblicate come 0, vuote o null.come sostituire la casella .serialize di jquery per includere caselle di controllo deselezionate

Sono un po 'confuso dal funzionamento interno di jquery, ma finora ho ottenuto questo risultato, ma imposta le caselle di controllo deselezionate su "on" ... Qualcuno può dirmi come continuare questa modifica di seguito?

$.fn.extend({ 
    serializeArray: function() { 
     return this.map(function(){ 
      return this.elements ? jQuery.makeArray(this.elements) : this; 
     }) 
     .filter(function(){ 
      return this.name && !this.disabled && 
       (this.checked || !this.checked || rselectTextarea.test(this.nodeName) || rinput.test(this.type)); 
     }) 
     .map(function(i, elem){ 
      var val = jQuery(this).val(); 

      return val == null ? 
       null : 
       jQuery.isArray(val) ? 
        jQuery.map(val, function(val, i){ 
         return { name: elem.name, value: val.replace(/\r?\n/g, "\r\n") }; 
        }) : 
        { name: elem.name, value: val.replace(/\r?\n/g, "\r\n") }; 
     }).get(); 
    } 
}); 

risposta

-1

Si tratta di una piccola modifica:

.map(function(i, elem){ 
     var val = jQuery(this).val(); 
     if ((jQuery(this).checked != undefined) && (!jQuery(this).checked)) { 
      val = "false"; 
     } 

non ho ancora testato, ma sembra che l'approccio più logico. Buona fortuna

+0

Ha funzionato quasi perfettamente. Ho appena cambiato jQuery (this) .chiaccato a jQuery (this) .prop ('checked') e ha funzionato alla grande. Grazie! – Jonathon

+0

@ user975571 o semplicemente usare 'this.checked' invece di' jQuery (this) .prop ('checked') ' –

+0

per qualche motivo che non ha funzionato, ma alla fine ha funzionato: jQuery (this) .prop ('type') == 'checkbox' – Jonathon

0

Prima di chiamare serialize(), è necessario impostare in modo esplicito il valore per false se una casella di controllo non è selezionata

$(form).find(':checkbox:not(:checked)').attr('value', false); 

ho provato here.

+1

Questo non sembra funzionare per me: l'attributo è tutto a posto, ma serializzare ancora non lo mostra. La tua pagina di test ha un numero di checkbox, ma in nessun modo (che io possa vedere) per testare la funzione serialize per vedere se effettivamente funziona. – ibrewster

+0

@ibrewster: puoi avvolgerli in un modulo e inviarli (o $ .post) e controllare gli strumenti di rete per vedere cosa viene serializzato. Le caselle di controllo non selezionate –

+0

non vengono inviate al server, indipendentemente dal valore (quindi questa domanda). tutte le caselle di controllo hanno un valore, poiché sono predefinite su "true" indipendentemente dal fatto che ne sia stata impostata una. http://stackoverflow.com/questions/11424037/does-input-type-checkbox-only-post-data-if-its-checked – chiliNUT

3

Mi piace l'approccio di @Robin Maben (pre-elaborazione delle checkbox prima di chiamare nativo .serialize()) ma non può farlo funzionare senza modifiche significative.

sono arrivato fino a questo plugin, che ho chiamato "mySerialize" (probabilmente ha bisogno di un nome migliore):

$.fn.mySerialize = function(options) { 
    var settings = { 
     on: 'on', 
     off: 'off' 
    }; 
    if (options) { 
     settings = $.extend(settings, options); 
    } 
    var $container = $(this).eq(0), 
     $checkboxes = $container.find("input[type='checkbox']").each(function() { 
      $(this).attr('value', this.checked ? settings.on : settings.off).attr('checked', true); 
     }); 
    var s = ($container.serialize()); 
    $checkboxes.each(function() { 
     var $this = $(this); 
     $this.attr('checked', $this.val() == settings.on ? true : false); 
    }); 
    return s; 
}; 

testato in Opera 11.62 e IE9.

Come si può vedere in questo DEMO, è possibile specificare il modo in cui gli stati ON e OFF delle caselle di controllo sono serializzati come oggetto di opzioni passato come parametro a mySerialize(). Per impostazione predefinita, lo stato ON è serializzato come 'name = on' e OFF come 'name = off'. Tutti gli altri elementi del modulo sono serializzati come per jQuery nativo serialize().

+0

Grazie per questo post :) –

+0

questo non funzionerà poi la seconda volta, Non sono sicuro di dove sia andato storto, ma una volta che si chiama mySerialize() sul modulo e quindi si chiama mySerialize() di nuovo, non funzionerà, funzionerà solo la prima volta. –

+0

Ho dovuto modificare leggermente la risposta per jQuery 1.9 e versioni successive. Vedi la mia risposta per gli aggiornamenti. –

5

Questo sostituirà il metodo jquery.serialize() per inviare entrambi i valori selezionati/non selezionati, anziché solo i valori selezionati. Usa true/false, ma puoi cambiare "this.checked" in "this.checked?" Su ": 0" se preferisci.

var originalSerializeArray = $.fn.serializeArray; 
$.fn.extend({ 
    serializeArray: function() { 
     var brokenSerialization = originalSerializeArray.apply(this); 
     var checkboxValues = $(this).find('input[type=checkbox]').map(function() { 
      return { 'name': this.name, 'value': this.checked }; 
     }).get(); 
     var checkboxKeys = $.map(checkboxValues, function (element) { return element.name; }); 
     var withoutCheckboxes = $.grep(brokenSerialization, function (element) { 
      return $.inArray(element.name, checkboxKeys) == -1; 
     }); 

     return $.merge(withoutCheckboxes, checkboxValues); 
    } 
}); 
9

Penso soluzione di Robin Maben manca un passo che è quello di impostare le caselle di avere una proprietà di 'controllato'. jQuery user guide notes on serialise() stato che controllate solo le caselle di controllo sono serializzati, quindi abbiamo bisogno di aggiungere un po ':

$('form').find(':checkbox:not(:checked)').attr('value', '0').prop('checked', true); 

L'unica nota negativa di questo metodo è un breve lampo di modulo che mostra tutte le caselle selezionate - sembra un po' strano.

+0

Questa risposta è stata l'ispirazione per la mia risposta qui sotto: http://stackoverflow.com/a/32189091/34806 –

+0

Grazie per aver incluso "l'unico lato negativo" nella risposta :) – tothemario

+0

Salvato il giorno! Ai nuovi ragazzi su Jquery, usa questo codice PRIMA di serializzare. –

9

allegare semplicemente i dati. Nel mio salvataggio di routine è sufficiente per inviare incontrollato come stringa vuota e controllata come "on":

var formData = $('form').serialize(); 

// include unchecked checkboxes. use filter to only include unchecked boxes. 
$.each($('form input[type=checkbox]') 
    .filter(function(idx){ 
     return $(this).prop('checked') === false 
    }), 
    function(idx, el){ 
     // attach matched element names to the formData with a chosen value. 
     var emptyVal = ""; 
     formData += '&' + $(el).attr('name') + '=' + emptyVal; 
    } 
); 
+0

Non so perché, ma la tua soluzione è l'aggiunta di serializzare anche le checkbox selezionate. Quindi il mio array serializzato ha 2 valori per la stessa casella di controllo, uno selezionato e l'ultimo deselezionato. –

0

ho fatto la seguente, trovando le caselle non controllate, controllandoli prima di chiamare serializeArray, poi li deselezionando così la forma sarebbe essere nello stesso stato in cui l'utente ha lasciato: la risposta di

var unchecked = chartCfgForm.find(':checkbox:not(:checked)'); 
unchecked.each(function() {$(this).prop('checked', true)}); 
var formValues = chartCfgForm.serializeArray(); 
unchecked.each(function() {$(this).prop('checked', false)}); 
0

Barbabietola-Barbabietole non ha funzionato per me in jQuery 1.9 e versioni successive. Ho utilizzato .val() e .prop() e ho eliminato il requisito .eq(0) sul contenitore, che ha limitato la serializzazione a un modulo nel selettore. Avevo un raro caso in cui dovevo serializzare più moduli contemporaneamente, quindi rimuovere quel requisito lo risolveva. Ecco la mia soluzione modificata:

$.fn.mySerialize = function(options) { 
    // default values to send when checkbox is on or off 
    var settings = { 
     on: 'on', 
     off: 'off' 
    }; 

    // override settings if given 
    if (options) { 
     settings = $.extend(settings, options); 
    } 

    // set all checkboxes to checked with the on/off setting value 
    // so they get picked up by serialize() 
    var $container = $(this), 
     $checkboxes = $container.find("input[type='checkbox']").each(function() { 
      $(this).val(this.checked ? settings.on : settings.off).prop('checked', true); 
     }); 

    var serialized = ($container.serialize()); 

    $checkboxes.each(function() { 
     var $this = $(this); 
     $this.prop('checked', $this.val() == settings.on); 
    }); 

    return serialized; 
}; 

Si può vedere il corrispondente fiddle here.