从另一个更改一个 Select2 的值会创建递归

Changing value of one Select2 from another creates recursion

我有两个 Select2 元素。如果另一个改变了,我想改变一个的值。它创建递归。

$('.select2').select2().on('change.select2', function(e) {
    if (e.target.id == 'select-1') {
        $('#select-2').val('all').trigger('change')
    } else if (e.target.id == 'select-2') {
        $('#select-1').val('all').trigger('change')
    }
})
<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/css/select2.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/js/select2.min.js"></script>
<select id="select-1" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

<br><br>
<select id="select-2" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

我更改了代码以不触发其他元素的更改。但是还是要进行递归。

let allowChange = true;
$('.select2').select2().on('change.select2', function(e) {
    if (e.target.id == 'select-1') {
        if (allowChange) {
            $('#select-2').val('all').trigger('change')
            allowChange = false;
        } else {
            allowChange = true;
        }
    } else if (e.target.id == 'select-2') {
        if (allowChange) {
            $('#select-1').val('all').trigger('change')
            allowChange = false;
        } else {
            allowChange = true;
        }
    }
})
<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/css/select2.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/js/select2.min.js"></script>
<select id="select-1" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

<br><br>
<select id="select-2" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

有没有办法解决这个问题并实现我想要实现的目标?

使用.on('input'检测当前select2变化怎么样?

$('.select2').select2().on('input', function(e) {
  console.clear();
  console.log('#' + e.target.id + ' value: ' + e.target.value);
  if (e.target.id == 'select-1') {
    $('#select-2').val('all').trigger('change')
  } else if (e.target.id == 'select-2') {
    $('#select-1').val('all').trigger('change')
  }
})
<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/css/select2.min.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/js/select2.min.js"></script>

<select id="select-1" class="select2">
  <option value="all">All</option>
  <option value="1">One</option>
  <option value="2">Two</option>
  <option value="3">Three</option>

</select>

<br><br>
<select id="select-2" class="select2">
  <option value="all">All</option>
  <option value="1">One</option>
  <option value="2">Two</option>
  <option value="3">Three</option>

</select>

let allowChange = true;
$('.select2').select2().on('input', function(e) {
      if (e.target.id == 'select-1') {
        if (allowChange) {
            $('#select-2').val('all').trigger('change')
            allowChange = false;
        } else {
            allowChange = true;
        }
    } else if (e.target.id == 'select-2') {
        if (allowChange) {
            $('#select-1').val('all').trigger('change')
            allowChange = false;
        } else {
            allowChange = true;
        }
    }
    })
<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/css/select2.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.13/js/select2.min.js"></script>
<select id="select-1" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

<br><br>
<select id="select-2" class="select2">
  <option value="all">All</option>
    <option value="1">One</option>
    <option value="2">Two</option>
    <option value="3">Three</option>

</select>

首先,当您使用 $('.select2').select2().on('change.select2', somefunction(){}); 附加事件时,它正在查找所有带有 class .select2 的元素,在您的情况下是两个下拉标签并将事件处理程序附加到所有元素。 您的代码中发生的事情是,当您调用下拉列表的更改时,它会调用处理程序,并且在处理程序中您以编程方式调用更改事件,因此处理程序被递归调用。有两种方法可以解决这个问题。首先,您需要为下拉菜单分离事件绑定和处理程序,或者您可以使用 class 选择器更改要绑定的事件类型。 我希望这可以帮助您理解问题。