[英]When registering both onchange and onclick on a select, the click event is triggered twice
Goal: Have a select
whose option
have nested structure when user clicks on the select
, but when user selects an option
the option should be displayed "normally" (ie with no leading spaces). 目标:当用户单击select
, select
的option
具有嵌套结构,但是当用户选择一个option
该选项应“正常”显示(即没有前导空格)。
Attempted solution using JS and Jquery: My JS is far from sophisticated so I apologize in advance :) 尝试使用JS和Jquery解决方案:我的JS远非复杂,因此我提前道歉:)
I attempted to use .on("change")
and . 我尝试使用.on("change")
和。 on("click")
to change the selected option
value (by calling .trim()
since I achieve the "nested" structure with
). on("click")
更改选定的option
值(由于我通过
实现了“嵌套”结构,因此调用了.trim()
)。 I'm also storing the original value of the selected option
because I want to revert the select
menu to its original structure in case the user selects another option
. 我还要存储所选option
的原始值,因为如果用户选择其他option
我想将select
菜单还原为其原始结构。
The problem : The function registered for .on("click")
is called twice, thus the select
value immediately resets itself to its original value. 问题 :为.on("click")
注册的函数被调用两次,因此select
值立即将其自身重置为其原始值。
I suspect there is a much, much easier solution using CSS. 我怀疑有使用CSS的解决方案要简单得多。 I will be happy to accept an answer that will suggest such solution. 我很乐意接受将提出这种解决方案的答案。
JSFiddle: https://jsfiddle.net/dv6kky43/9/ JSFiddle: https ://jsfiddle.net/dv6kky43/9/
<form>
<select id="select">
<option value=""></option>
<option value="a"> a</option>
<option value="b"> b</option>
</select>
</form>
<textarea id="output"/>
var orig;
var output = $("#output");
output.val("");
function onDeviceSelection(event){
output.val(output.val() + "\nonDeviceSelection");
var select = event.target;
orig = select.selectedOptions[0].text;
select.selectedOptions[0].text = select.selectedOptions[0].text.trim()
}
function resetDeviceSelectionText(event) {
output.val(output.val() + "\nresetDeviceSelectionText");
var select = event.target;
if (orig !== undefined){
select.selectedOptions[0].text = orig;
}
}
$("#select").on("change", onDeviceSelection);
$("#select").on("click", resetDeviceSelectionText);
Instead of keeping the state of the selected element i would simply go over all options and add the space if that option is not selected: 如果不选择该选项,我将不保留所选元素的状态,而只是遍历所有选项并添加空格:
function onDeviceSelection(event){
// Update textarea
output.val(output.val() + "\nonDeviceSelection");
// Higlight the selected
const {options, selectedIndex} = event.target;
for(let i = 0; i < options.length; i++)
options[i].innerHTML = (i === selectedIndex ? "":" ") + options[i].text.trim();
}
$("#select").on("change", onDeviceSelection);
Note that you need to use innerHTML
to set the whitespace... 请注意,您需要使用innerHTML
设置空格...
If you are already using jQuery, why not utilize data
function to store the original value. 如果您已经在使用jQuery,为什么不利用data
功能存储原始值。 This way you will also be able to specify different nest levels. 这样,您还可以指定不同的嵌套级别。
(function($){ $(document).on('change', 'select', function(event) { $(this).find('option').each(function(index, element){ var $option = $(element); // Storing original value in html5 friendly custom attribute. if(!$option.data('originalValue')) { $option.data('originalValue', $option.text()); } if($option.is(':selected')) { $option.html($option.data('originalValue').trim()); } else { $option.html($option.data('originalValue')); } }) }); })(jQuery);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <form> <select id="select"> <option value=""></option> <option value="a"> a</option> <option value="b"> b</option> </select> </form>
Once caveat I see is, the selected option will appear trimmed on the list as well, if dropdown is opened after a previous selection has been made: 一旦发现警告,如果在做出先前选择之后打开下拉列表,则所选选项也会在列表上显示为修整:
Will it still work for you? 它仍然可以为您服务吗?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.