在选择列表之间移动选项时消失的元素 [英] Disappearing elements when moving options between select lists

查看:72
本文介绍了在选择列表之间移动选项时消失的元素的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个用户界面,用户可以在其中在两个选择列表之间移动多个选项.看起来就像这里的模拟:

I have a user interface where a user can move multiple options between two select lists. It looks just like this mock up here:

您选择一个或多个项目,然后按箭头按钮,它将它们移动到另一个列表中.

You select one or multiple items then press the arrow button and it moves them into the other list.

问题是我有一个排序功能,可以在选项被移动并且确实发生奇怪的事情后重新使用这些选项.当您第一次从左向右移动选项时,它可以正常工作.如果从左到右移动另一个项目,它将覆盖已经存在的项目.但是,如果再次单击左侧列表,则这些项目将显示为正常状态!如果检查dom,您会看到其中的项目,没有没有使它们不显示的css规则,并且当它们再次显示时,看起来并没有应用任何额外的css.将项目移到上面的代码如下:

The problem is I have a sort function to resort the options after they've been moved and really weird stuff is happening. When you first move options from the left to the right it works fine. If you move another item from the left to right it overwrites what is already there. BUT if you click on the left list again the items appear like normal! If you inspect the dom you can see the items are there, there is no css rules that would make them not show up, and it doesn't look like any extra css is applied when they show up again. The code to move the items over looks like this:

$('#moveRight').click(function () {

  // Get all selection options
  var selectedOptions = $('#from option:selected');

  // Let's remove our items from the from list...
  $('#from option:selected').remove();

  // Add them to the to list...
  $('#to').append(selectedOptions);

  // Sort alphabetically
  $('#to option').sort(sortAlpha).appendTo('#to');
});

我用一个接口的工作示例创建了这个Codepen:

I created this codepen with a working example of the interface:

https://codepen.io/onekidney_/pen/YzyrYKX

复制步骤:

  1. 突出显示左侧列表中的任意数量的选项.
  2. 单击->"按钮.
  3. 突出显示左侧列表中的任意数量的选项.
  4. 单击->"按钮.

请注意,如果再次单击左侧列表,则新项目是列表中唯一显示的项目!该错误似乎是在排序中,因为删除可解决此问题.

Notice that the new items are the only one that show up in the list BUT if you click the left list again they all appear! The error appears to be in the sorting because removing that fixes this issue.

此问题有相同的问题,但看起来它们通过删除排序来修复它.这是新的行为-几年前部署此代码时还没有这样做(这就是为什么要在jtw中使用jquery的原因.)我仍然希望在移动选项后对它们进行排序.有人知道这里发生了什么吗?

This question had the same issue but it appears that they fixed it by removing the sort. This is new behavior - it didn't do this years ago when this code was deployed (which is why jquery is used btw.) I still would like the feature of having the options sorted after they've been moved. Does anyone have an idea of what's going on here?

推荐答案

这似乎是浏览器渲染错误.我无法弄清楚为什么会发生这种情况,但是似乎在快速分离/删除/追加操作后使用排序逻辑会使浏览器渲染器感到困惑.如果您查看DOM检查器,则可以看到option元素在正确的位置,但是渲染器不会显示它们.

This appears to be a browser rendering bug. I'm unable to figure out exactly why it happens, but it appears that the use of sort logic after the quick detach/remove/append operations causes the browser renderer to get confused. If you look at the DOM inspector you can see the option element are in the correct place, however the renderer does not display them.

我建议将此作为浏览器供应商的错误提出.

I'd suggest raising this as a bug with the browser vendors.

为此,我发现的唯一解决方法是在目标select上触发一个focus事件,以强制在DOM中重新绘制该元素. blur对于此修复程序不是必需的,它只是为了避免CSS轮廓出现在所选元素周围,这会造成一些麻烦.

The only workaround I've found for this is to trigger a focus event on the target select to force the element to be re-drawn in the DOM. The blur is not necessary for this fix, it's only to avoid the CSS outline appearing around the selected element which is a little jarring.

还要注意,我在select元素和按钮上都使用了data属性来泛化逻辑.

Also note that I genericised the logic using data attributes on both select elements and buttons.

let els = {
  from: $('#from'),
  to: $('#to')
};

$('.move').click(function() {
  let $target = els[this.dataset.target];
  let $source = els[this.dataset.source];
  $source.children('option:selected').appendTo($target);
  $target.children('option').sort(sortAlpha).appendTo($target);
  $target.focus().blur();
});

let sortAlpha = (a, b) => parseInt(a.textContent, 10) > parseInt(b.textContent, 10) ? 1 : -1;

body {
  background-color: #a3d5d3;
}

select {
  width: 200px;
  height: 200px;
}

button {
  width: 100px;
  padding: 5px;
  margin: 0 5px 5px 5px;
}

#button-container {
  display: inline-block;
  vertical-align: top;
}

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<select id="from" multiple>
  <option>1</option>
  <option>2</option>
  <option>3</option>
  <option>4</option>
  <option>5</option>
  <option>6</option>
  <option>7</option>
  <option>8</option>
  <option>9</option>
  <option>10</option>
</select>
<div id="button-container">
  <button class="move" id="moveRight" data-target="to" data-source="from">-&gt;</button><br />
  <button class="move" id="moveLeft" data-target="from" data-source="to">&lt;-</button>
</div>
<select id="to" multiple>
</select>

这篇关于在选择列表之间移动选项时消失的元素的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆