परिवर्तन से पहले चयन (ड्रॉपडाउन) का मूल्य प्राप्त करना


237

मैं जो कुछ हासिल करना चाहता हूं वह यह है कि जब भी <select>बदलाव होता है तो मैं बदलाव से पहले ड्रॉपडाउन का मूल्य चाहता हूं। मैं jQuery के 1.3.2 संस्करण का उपयोग कर रहा हूं और परिवर्तन घटना पर उपयोग कर रहा हूं, लेकिन जो मूल्य मुझे मिल रहा है वह परिवर्तन के बाद है।

<select name="test">
<option value="stack">Stack</option>
<option value="overflow">Overflow</option>
<option value="my">My</option>
<option value="question">Question</option>
</select>

वर्तमान में विकल्प कहते हैं कि मेरा विकल्प अभी चुना गया है जब मैं इसे ऑनकॉन्ग इवेंट (यानी जब मैंने इसे स्टैक में बदल दिया है) में स्टैक करने के लिए बदलता हूं तो मैं चाहता हूं कि यह पिछले मूल्य का हो अर्थात इस मामले में मेरी उम्मीद है।

यह कैसे हासिल किया जा सकता है?

संपादित करें: मेरे मामले में मैं एक ही पृष्ठ में कई चुनिंदा बॉक्स रख रहा हूं और चाहता हूं कि उन सभी पर एक ही चीज लागू हो। इसके अलावा मेरे सभी चुनिंदा पेज लोड के बाद अजाक्स के माध्यम से डाले जाते हैं।


1
क्या आपने इसकी जाँच की है: stackoverflow.com/questions/1983535/…
रजत

जवाबों:


434

परिवर्तन ईवेंट के साथ फ़ोकस इवेंट को मिलाएं जो आप चाहते हैं:

(function () {
    var previous;

    $("select").on('focus', function () {
        // Store the current value on focus and on change
        previous = this.value;
    }).change(function() {
        // Do something with the previous value after the change
        alert(previous);

        // Make sure the previous value is updated
        previous = this.value;
    });
})();

काम करने का उदाहरण: http://jsfiddle.net/x5PKf/766


1
@ अल्पेश: दुर्भाग्य से नहीं, क्योंकि आप jQuery 1.4.1 या उसके बाद का उपयोग नहीं कर रहे हैं, आप फोकस और परिवर्तन की घटनाओं के साथ लाइव () का उपयोग करने में असमर्थ हैं। केवल एक चीज जो आप कर सकते हैं वह है कि पृष्ठ में तत्वों को डालने के बाद अपनी स्क्रिप्ट को बाँधने के लिए समायोजित करें।
एंडी ई

1
धन्यवाद मैं पहले ही दोनों को लाइव के साथ बांध चुका हूं और इसने सफलतापूर्वक काम किया है। :)
अल्पेश

4
ध्यान दें कि आपको अपने परिवर्तन हैंडलर में चुनिंदा तत्व पर भी ध्यान देना चाहिए, अन्यथा बार-बार होने वाले मूल्य परिवर्तन के बाद इसे ट्रिगर नहीं किया जाएगा
एलेक्स

52
मैं इस समाधान से सहमत नहीं हूँ। यदि आप एक बार यह काम करते हैं, तो मान बदल जाते हैं, लेकिन यदि आप इसे एक बार करेंगे तो यह नहीं होगा। आपको कहीं न कहीं फोकस पर क्लिक करना होगा और ड्रॉपडाउन पर एक और क्लिक करना होगा। मेरा सुझाव है: $ ("# dropdownId")। ('परिवर्तन', फ़ंक्शन () {var ddl = $ (यह); var पिछला = ddl.data ('पिछला'); ddl.data ('पिछला'), ddl .val ());});
15:

5
@ free4ride, यह तय करने के लिए कि मैं सिर्फ $(this).blur();परिवर्तन समारोह के अंत में कॉल करता हूं
chiliNUT

135

कृपया इसके लिए एक वैश्विक संस्करण का उपयोग न करें - यहां डेटा पर मौजूद मूल्य को संग्रहीत करें एक उदाहरण है: http://jsbin.com/uqupu3/2/edit

रेफरी के लिए कोड:

$(document).ready(function(){
  var sel = $("#sel");
  sel.data("prev",sel.val());

  sel.change(function(data){
     var jqThis = $(this);
     alert(jqThis.data("prev"));
     jqThis.data("prev",jqThis.val());
  });
});

बस देखा कि आपके पास पृष्ठ पर कई चयन हैं - यह दृष्टिकोण आपके लिए भी काम करेगा क्योंकि प्रत्येक चयन के लिए आप चयन के डेटा पर मौजूद मूल्य को संग्रहीत करेंगे


jQuery.data यहाँ एक अच्छा समाधान है। आपके समाधान पर आप प्रत्येक चुनिंदा के लिए एक क्लोजर बना रहे हैं, जिसका एक संपूर्ण प्रभाव है यदि बहुत सारे चुनिंदा तत्व हैं
Avi Pinto

मेरी चिंता प्रदर्शन की नहीं थी, और मुझे विश्वास नहीं है कि कार्य बनाना किसी jQuery.dataभी तरह से धीमा है ।
अगस्त लिलियास 12

9
तो jQuery.data का उपयोग करने के लिए आपकी आपत्ति क्या है? जहाँ तक मुझे पता है कि jQuery पुस्तकालय भी आंतरिक रूप से इसका उपयोग करता है, और इसे उपयोग करने की सिफारिश करता है
Avi Pinto

निश्चित रूप से jQuery डेटा का उपयोग करने के साथ सहमत हूँ- मुझे याद दिलाने के लिए धन्यवाद मैं वैश्विक संस्करण का उपयोग करने वाला था .. वैश्विक संस्करण के साथ गलत नहीं है लेकिन डेटा का उपयोग करना अधिक संक्षिप्त है। लेकिन फ़ोकस का पीछा करना और फिर बदलाव भी अच्छा है :)
पिय्रत कुला

4
@ppumkin: एक निश्चित रूप से एक वैश्विक चर के साथ गलत है: यह केवल एक का समर्थन करता है select! स्वीकृत उत्तर टूट जाएगा क्योंकि यह सभी से मेल खाता है selectलेकिन केवल पहले वाले के मूल्य को संग्रहीत करता है। data यह करने के लिए बेहतर तरीका है। +1 :)
कोडिंग हुआ

86

मैं एवी पिंटो के समाधान के लिए जाता हूं जो उपयोग करता है jquery.data()

फोकस का उपयोग करना एक वैध समाधान नहीं है। यह पहली बार आपके द्वारा विकल्पों को बदलने पर काम करता है, लेकिन यदि आप उस चुनिंदा तत्व पर बने रहते हैं, और कुंजी "ऊपर" या "नीचे" दबाएं। यह फ़ोकस ईवेंट के माध्यम से फिर से नहीं जाएगा।

तो समाधान निम्नलिखित की तरह दिखना चाहिए,

//set the pre data, usually needed after you initialize the select element
$('mySelect').data('pre', $(this).val());

$('mySelect').change(function(e){
    var before_change = $(this).data('pre');//get the pre data
    //Do your work here
    $(this).data('pre', $(this).val());//update the pre data
})

3
महान समाधान, चयनित उत्तर से बहुत बेहतर!
TJL

2
दूसरा भाग ठीक काम करता है लेकिन पहला भाग डेटा विशेषता सेट नहीं कर रहा है। कोई विचार?
सिनास्टेटिक

1
@ सीनेस्टैटिक, मेरे पास एक ही मुद्दा था (और पहले से ही इस उत्तर को उखाड़ दिया)। मुझे नहीं लगता कि $ (यह) .data () विधि से बचता है। एवी पिंटो का जवाब अपने मूल्य के लिए चयनित तत्व पर वापस जाता है, और यह मेरे लिए काम करता है (इसलिए मैंने एवी के रूप में अच्छी तरह से उत्थान किया)।
goodeye

1
इसके बाद से यह काम नहीं करेगा! == $ ('mySelect')। यहाँ एक निश्चित संस्करण है। var $selectStatus = $('.my-select'); $selectStatus.on('change', function () { var newStatus = $(this).val(); var oldStatus = $(this).data('pre'); }).data('pre', $selectStatus.val());
कैपी

2
@Sinaesthetic यह पंक्ति सभी "mySelect" तत्वों के लिए एक मान निर्धारित करती है जो इस प्रकार $('mySelect').data('pre', $(this).val());होनी चाहिए: $('mySelect').each(function() { $(this).data('pre', $(this).val()); });उत्तर को संपादित करने के लिए मेरे पास पर्याप्त प्रतिष्ठा नहीं है: /
Abderrahim

8

मूल्य को हाथ से ट्रैक करें।

var selects = jQuery("select.track_me");

selects.each(function (i, element) {
  var select = jQuery(element);
  var previousValue = select.val();
  select.bind("change", function () {
    var currentValue = select.val();

    // Use currentValue and previousValue
    // ...

    previousValue = currentValue;
  });
});

मैं उपरोक्त दृष्टिकोण का उपयोग नहीं कर सकता क्योंकि मैं उसी पृष्ठ पर कई चुनिंदा बक्से रख रहा हूं जिनके साथ मुझे निपटना है।
अल्पेश

1
आपने अपने प्रश्न में कई चुनिंदा बटन के बारे में कुछ नहीं कहा। हालांकि कई बक्से का समर्थन करने के लिए मेरा जवाब अपडेट किया गया।
अगस्त लिलियास

1
सबसे बढ़िया उत्तर। मुझे लगता है कि यह समाधान usign फ़ोकस () और परिवर्तन () के कारण बेहतर है क्योंकि यह ब्राउज़र की अनुकूलता के लिए jquery पर निर्भर करता है और फिर दोनों तरीकों का सही प्रवाह ef का निष्पादन
coorasse

@ कोरस: निष्पादन का सही प्रवाह कभी भी अलग नहीं हो सकता है। उपयोगकर्ता द्वारा फ़ोकस लेने से पहले कुछ चुनिंदा बॉक्स वैल्यू को कभी भी नहीं बदला जा सकता है । कहा जा रहा है, इस दृष्टिकोण के साथ कुछ भी गलत नहीं है :-)
एंडी ई

'बंद' उपयोग के दृष्टिकोण से, मुझे यकीन नहीं है कि यह 'फोकस' समाधान से बेहतर है।
जेम्स पॉउलॉज

8
 $("#dropdownId").on('focus', function () {
    var ddl = $(this);
    ddl.data('previous', ddl.val());
}).on('change', function () {
    var ddl = $(this);
    var previous = ddl.data('previous');
    ddl.data('previous', ddl.val());
});

यह मेरे लिए केवल मामूली सुधार पर काम कर रहा है dropdownId चयनकर्ता पर इसके बजाय एक है, धन्यवाद
malkoty

2
उपयोगकर्ता सहभागिता के बिना परिवर्तन की घटना हो सकती है, इसलिए यह एक
ब्रेनर

3

मैं ईवेंट "लाइव" का उपयोग कर रहा हूं, मेरा समाधान मूल रूप से दिमित्रि के साथ परिचित है, लेकिन "फ़ोकस" का उपयोग करने के बजाय, "पिछला" ट्रिगर होने पर मेरा पिछला मान संग्रहीत होता है।

var previous = "initial prev value";
$("select").live('click', function () {
        //update previous value
        previous = $(this).val();
    }).change(function() {
        alert(previous); //I have previous value 
    });

2
मैं इस का उपयोग नहीं करेगा। क्या होगा यदि उपयोगकर्ता 'एलिमेंट' को चुनिंदा तत्व में रखता है और एक अलग विकल्प चुनने के लिए अपने कीबोर्ड तीर का उपयोग करता है?
क्रिश्चियन लुंडाहल

@Perplexor हाँ, यह कुंजियों के साथ काम नहीं करेगा, अन्यथा यह हर बार जब आप कुंजी दबाते हैं तो प्रत्येक मान को संग्रहीत करेगा। यह केवल मान लें कि उपयोगकर्ता ड्रॉप डाउन मेनू पर क्लिक करता है। समस्या यह है कि 'लाइव' इवेंट 'फोकस' के साथ काम नहीं करेगा, मुझे कोई बेहतर समाधान नहीं पता है।
सिका गुस्टियानी

आप वर्तमान मान को एक अलग चर में ध्यान केंद्रित कर सकते हैं। यह सिर्फ मेरे सिर के ऊपर से है इसलिए मुझे यकीन नहीं है कि यह आदर्श है।
क्रिश्चियन लुंडहल

अगर 'फोकस' 'लाइव' इवेंट के साथ काम कर सकता है, तो यह एकदम सही होगा। लेकिन अगर आप गतिशील रूप से उन ड्रॉप डाउन मेनू को बनाते हैं, तो आप केवल 'लाइव' का उपयोग कर सकते हैं, यही मुझे पता है। 'लाइव' पर 'फोकस' नए मूल्यों को संग्रहीत करने के लिए घटना को ट्रिगर नहीं करता है, दुर्भाग्य से, लेकिन मैं नए jquery के साथ नहीं जानता हूं
Cica Gustiani

जीना jQuery के नए संस्करणों में मर चुका है! [ stackoverflow.com/questions/14354040/…
रेमो

2

वर्तमान में चयनित ड्रॉप डाउन मान को परिवर्तन कार्रवाई क्रिया पर 'ड्रॉप डाउन' लिखने से पहले एक वैश्विक चर में चुने गए मान के साथ रखें। यदि आप फ़ंक्शन में पिछला मान सेट करना चाहते हैं, तो आप वैश्विक चर का उपयोग कर सकते हैं।

//global variable
var previousValue=$("#dropDownList").val();
$("#dropDownList").change(function () {
BootstrapDialog.confirm(' Are you sure you want to continue?',
  function (result) {
  if (result) {
     return true;
  } else {
      $("#dropDownList").val(previousValue).trigger('chosen:updated');  
     return false;
         }
  });
});

1

एक कोणीय घड़ी प्रकार इंटरफ़ेस के साथ एक कस्टम jQuery घटना का उपयोग करने के बारे में कैसे;

// adds a custom jQuery event which gives the previous and current values of an input on change
(function ($) {
    // new event type tl_change
    jQuery.event.special.tl_change = {
        add: function (handleObj) {
            // use mousedown and touchstart so that if you stay focused on the
            // element and keep changing it, it continues to update the prev val
            $(this)
                .on('mousedown.tl_change touchstart.tl_change', handleObj.selector, focusHandler)
                .on('change.tl_change', handleObj.selector, function (e) {
                // use an anonymous funciton here so we have access to the
                // original handle object to call the handler with our args
                var $el = $(this);
                // call our handle function, passing in the event, the previous and current vals
                // override the change event name to our name
                e.type = "tl_change";
                handleObj.handler.apply($el, [e, $el.data('tl-previous-val'), $el.val()]);
            });
        },
        remove: function (handleObj) {
            $(this)
                .off('mousedown.tl_change touchstart.tl_change', handleObj.selector, focusHandler)
                .off('change.tl_change', handleObj.selector)
                .removeData('tl-previous-val');
        }
    };

    // on focus lets set the previous value of the element to a data attr
    function focusHandler(e) {
        var $el = $(this);
        $el.data('tl-previous-val', $el.val());
    }
})(jQuery);

// usage
$('.some-element').on('tl_change', '.delegate-maybe', function (e, prev, current) {
    console.log(e);         // regular event object
    console.log(prev);      // previous value of input (before change)
    console.log(current);   // current value of input (after change)
    console.log(this);      // element
});

1

मुझे पता है कि यह एक पुराना धागा है, लेकिन मैंने सोचा कि मैं थोड़ा अतिरिक्त जोड़ सकता हूं। मेरे मामले में मैं पाठ, वैल और कुछ अन्य डेटा एट्री पर पारित करना चाहता था। इस मामले में इसकी पूरी कीमत को केवल वैल के बजाय एक प्रचलित मूल्य के रूप में संग्रहीत करना बेहतर है।

नीचे दिए गए उदाहरण कोड:

var $sel = $('your select');
$sel.data("prevSel", $sel.clone());
$sel.on('change', function () {
    //grab previous select
    var prevSel = $(this).data("prevSel");

    //do what you want with the previous select
    var prevVal = prevSel.val();
    var prevText = prevSel.text();
    alert("option value - " + prevVal + " option text - " + prevText)

    //reset prev val        
    $(this).data("prevSel", $(this).clone());
});

संपादित करें:

मैं तत्व पर .clone () जोड़ना भूल गया। ऐसा न करने पर, जब आप पिछले के बजाए उन मूल्यों को वापस खींचने की कोशिश करते हैं जिन्हें आप चयन की नई प्रति में खींच रहे हैं। क्लोन () विधि का उपयोग करके इसके उदाहरण के बजाय चयन की एक प्रति संग्रहीत करता है।


0

ठीक है, आप वर्तमान चयनित मूल्य को संग्रहीत क्यों नहीं करते हैं, और जब चयनित आइटम को बदल दिया जाता है तो आपके पास पुराना मूल्य संग्रहीत होगा? (और आप इसे अपनी इच्छानुसार फिर से अपडेट कर सकते हैं)


वैसे मैं ऐसा नहीं कर सकता क्योंकि मेरे मामले में मैं उसी पेज में कई चुनिंदा बॉक्स रख रहा हूं। और शुरुआत में सभी का प्रारंभिक मूल्य बचाना बहुत कठिन होगा।
अल्पेश

0

निम्नलिखित कोड का उपयोग करें, मैंने इसे और इसके काम करने का परीक्षण किया है

var prev_val;
$('.dropdown').focus(function() {
    prev_val = $(this).val();
}).change(function(){
            $(this).unbind('focus');
            var conf = confirm('Are you sure want to change status ?');

            if(conf == true){
                //your code
            }
            else{
                $(this).val(prev_val);
                $(this).bind('focus');
                return false;
            }
});

0
(function() {

    var value = $('[name=request_status]').change(function() {
        if (confirm('You are about to update the status of this request, please confirm')) {
            $(this).closest('form').submit(); // submit the form
        }else {
            $(this).val(value); // set the value back
        }
    }).val();
})();

0

मैं इस मुद्दे को हल करने के लिए एक और विकल्प देना चाहता हूं; चूँकि ऊपर प्रस्तावित समाधान से मेरा परिदृश्य हल नहीं हुआ।

(function()
    {
      // Initialize the previous-attribute
      var selects = $('select');
      selects.data('previous', selects.val());

      // Listen on the body for changes to selects
      $('body').on('change', 'select',
        function()
        {
          $(this).data('previous', $(this).val());
        }
      );
    }
)();

यह jQuery का उपयोग करता है ताकि डीफ़। यहाँ एक निर्भरता है, लेकिन इसे शुद्ध जावास्क्रिप्ट में काम करने के लिए अनुकूलित किया जा सकता है। (एक श्रोता को शरीर में जोड़ें, जांचें कि क्या मूल लक्ष्य एक चयन था, फ़ंक्शन निष्पादित करें, ...)।

परिवर्तन श्रोता को शरीर से जोड़कर, आप चुनिंदा लोगों के लिए विशिष्ट श्रोताओं के बाद यह सुनिश्चित करेंगे कि यह आग लग जाए , अन्यथा 'डेटा-पिछला' का मूल्य आपके द्वारा पढ़ने से पहले ही अधिलेखित हो जाएगा।

यह निश्चित रूप से माना जाता है कि आप अपने सेट-पिछले और चेक-वैल्यू के लिए अलग-अलग श्रोताओं का उपयोग करना पसंद करते हैं। यह एकल-जिम्मेदारी पैटर्न के साथ सही बैठता है।

नोट: यह इस 'पिछले' कार्यक्षमता को सभी चयनों में जोड़ता है , इसलिए यदि आवश्यक हो तो चयनकर्ताओं को फाइन-ट्यून करना सुनिश्चित करें।


0

यह @thisisboris उत्तर पर एक सुधार है। यह डेटा के लिए एक वर्तमान मूल्य जोड़ता है, इसलिए कोड को नियंत्रित कर सकता है जब एक चर सेट वर्तमान मूल्य में बदल जाता है।

(function()
{
    // Initialize the previous-attribute
    var selects = $( 'select' );
    $.each( selects, function( index, myValue ) {
        $( myValue ).data( 'mgc-previous', myValue.value );
        $( myValue ).data( 'mgc-current', myValue.value );  
    });

    // Listen on the body for changes to selects
    $('body').on('change', 'select',
        function()
        {
            alert('I am a body alert');
            $(this).data('mgc-previous', $(this).data( 'mgc-current' ) );
            $(this).data('mgc-current', $(this).val() );
        }
    );
})();

0

सबसे अच्छा उपाय:

$('select').on('selectric-before-change', function (event, element, selectric) {
    var current = element.state.currValue; // index of current value before select a new one
    var selected = element.state.selectedIdx; // index of value that will be selected

    // choose what you need
    console.log(element.items[current].value);
    console.log(element.items[current].text);
    console.log(element.items[current].slug);
});

1
यह उत्तर "Selectric" js लाइब्रेरी पर आधारित है, न कि 'plain' jQuery या जावास्क्रिप्ट पर। Eventhough सबसे अच्छा है, यह मूल प्रश्न के अनुरूप नहीं है और न ही यह कहता है कि उपयोगकर्ता को इसके लिए कुछ और स्थापित करने की आवश्यकता है
गैजेट 00

0

आपके वांछित परिणाम प्राप्त करने के कई तरीके हैं, यह करने का मेरा विनम्र तरीका है:

तत्व को उसके पिछले मान को रखने दें, इसलिए एक विशेषता 'पिछलावैल्यू' जोड़ें।

<select id="mySelect" previousValue=""></select>

एक बार शुरू होने के बाद, 'पिछलेवैल्यू' को अब एक विशेषता के रूप में इस्तेमाल किया जा सकता है। JS में, इस सेलेक्ट के पिछलेवैल्यू को एक्सेस करने के लिए:

$("#mySelect").change(function() {console.log($(this).attr('previousValue'));.....; $(this).attr('previousValue', this.value);}

आपके द्वारा 'पिछलेवैल्यू' का उपयोग करने के बाद, विशेषता को वर्तमान मान में अपडेट करें।


0

मुझे चयन के आधार पर एक अलग div प्रकट करने की आवश्यकता थी

यह आप इसे jquery और es6 सिंटैक्स के साथ कैसे कर सकते हैं

एचटीएमएल

<select class="reveal">
    <option disabled selected value>Select option</option>
    <option value="value1" data-target="#target-1" >Option 1</option>
    <option value="value2" data-target="#target-2" >Option 2</option>
</select>
<div id="target-1" style="display: none">
    option 1
</div>
<div id="target-2" style="display: none">
    option 2
</div>

जे एस

$('select.reveal').each((i, element)=>{
    //create reference variable 
    let $option = $('option:selected', element)
    $(element).on('change', event => {
        //get the current select element
        let selector = event.currentTarget
        //hide previously selected target
        if(typeof $option.data('target') !== 'undefined'){
            $($option.data('target')).hide()
        }
        //set new target id
        $option = $('option:selected', selector)
        //show new target
        if(typeof $option.data('target') !== 'undefined'){
            $($option.data('target')).show()
        }
    })
})
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.