简体   繁体   中英

How do i uncheck radio button in one click

I have the code to uncheck radio button, but the problem is, its not happening in one click when the radio button is checked, I am fetching the value of radio button as checked from mysql, so the default value of radio button is checked and when I click on the radio button the value should uncheck upon single click but my code is making it happen on double click. How do I make it happen with single click?

 var check; $('input[type="radio"]').hover(function() { check = $(this).is(':checked'); }); var checkedradio; function docheck(thisradio) { if (checkedradio == thisradio) { thisradio.checked = false; checkedradio = null; } else {checkedradio = thisradio;} }
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <input type="radio" name="check" value="check" onClick="javascript:docheck(this);" checked="checked"/>

Radios by design are meant to be used in a group ( https://html.spec.whatwg.org/#radio-button-state-(type=radio) ) - a group of 2 or more radios should form a group to allow the user to pick a value from the selection in that group. By design the radio group behaviour is this - once a selection is made (either by the user or programatically), that choice sticks, and there is no way to undo it, other than choose another radio option from the group. You'll see in your example, that without the JavaScript bit, if you by default uncheck the radio, then check it manually, you won't be able to uncheck it again. This is how it's supposed to work.

The rule of thumb should be that solving a problem on the backend should not come at the expense of the front-end, as it negatively impacts the user-experience, and will cause problems to the user. If you for any reason HAVE TO stick with such a bad UX solution, here is a way to hack your radio to act like a checkbox, but it is seriously not advised, and you should change your backend to use checkboxes instead.

Here is the radio hack (and a native checkbox input that should be used instead):

 var myRadio = $('input[type="radio"]:checked'); myRadio.on('click', function() { if (myRadio.attr('checked')) { myRadio.removeAttr('checked'); myRadio.prop('checked', false); } else { myRadio.attr('checked', 'checked'); myRadio.prop('checked', true); } });
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <b>This works, but it's bad UX, so avoid!</b><br> <input type="radio" name="check" value="check" checked /> <hr> <b>Use this instead!</b> <br> <input type="checkbox" name="real-check" value="real-check" checked />

You'll see that the jQuery selector is deliberately set to only pick the "checked" radio, so the JavaScript solution only takes over the native behaviour if the radio is checked by default. As soon as the radio is not checked by default, you'll see how the browser forces your selection once it's checked manually - this is a tell tale sign that you're trying to deviate from the expected behaviour.

You'll also see that the checkbox natively works - without the need for JavaScript or jQuery.

RobertP raised an interesting point about the user experience, or in IT-talk: "UX". In some cases it is mandatory that a single option needs to be clicked. This is exactly what radio buttons were made for. However, I have come across cases, where a "none" selection should also be offered. For these cases you could simply supply an extra radio button with the option "none" OR you could make the radio buttons "unselectable" again. This seems to go against the intended radio button behaviour. However, as it is possible to start out with no radio buttons being selected, why should it not be possible to return to this state after, maybe, the user had clicked on an item prematurely?

So, with these considerations in mind I went ahead and put together a way of doing what OP had in mind. I extended the example a little bit by including further radio button options:

 $.fn.RBuncheckable=function(){ // simple jQuery plugin const rb=this.filter('input[type=radio]'); // apply only on radio buttons... rb.each(function(){this.dataset.flag=$(this).is(':checked')?1:''}).on('click',function(){ if (this.dataset.flag) $(this).prop('checked',false) // uncheck current // mark whole group (characterised by same name) as unchecked: else rb.filter('[name='+this.name+']').each(function(){this.dataset.flag=''}); this.dataset.flag=this.dataset.flag?'':1; // invert flag for current }); return this; } $('input').RBuncheckable(); // apply it to all radio buttons on this page...
 <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> <h4>Two groups of radio buttons with "uncheck" option:</h4> <input type="text" value="This input field is unaffected"> <p>group one:</p> <label><input type="radio" name="check" value="a" checked /> Option A</label><br> <label><input type="radio" name="check" value="b"/> Option B</label><br> <label><input type="radio" name="check" value="c"/> Option C</label> <p>group two:</p> <label><input type="radio" name="second" value="d"/> Option D</label><br> <label><input type="radio" name="second" value="e"/> Option E</label><br> <label><input type="radio" name="second" value="f" checked/> Option F</label>

In the .each() loop I collect the initially checked state for all selected radio buttons. I store the individual checked state in a data attribute "flag" for each radio button.

The click event handler function then picks up this data flag and decides whether to step into action by either removing the checked state from the current element or simply resetting the flag data-attributes for the whole group (characterised by having the same name as the currently clicked one). In a last operation it then inverts the flag state for the current element again. As all data attributes are stored as strings, the values 1 and "" are "truthy" and "falsy" values that can be directly tested.

This results in exactly the behaviour you were looking for. I hope;-)

By having the functionality packaged in a little jQuery plugin it can now be applied to any jQuery object directly.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM