解决 select2 开启 tags 输入中文显示不全的BUG
一、急着修复,不求甚解:
- 直接打开
select2.full.min.js
内容复制到 https://tool.lu/js/ 点击【美化(Beutify)】按钮,格式化一下方便阅读。 - 格式化好后,搜索 “em” 会找到如下这段代码 :
.------------------------------------------------------------------------------------------------
.------------------------------------------------------------------------------------------------
em会有很多,搜完整匹配会更有效。
- 删除
else
中的代码,改成如下内容:
else {
var str = this.$search.val();
var b1 = str.replace(/[^\u4e00-\u9fa5]/gi, "").length * 2;
var b2 = str.replace(/[\u4e00-\u9fa5]/gi, "").length * .75;
a = (b1 + b2 + 1) + "em"
}
- 点击【净化(Purify)】压缩代码,然后保存即可修复。
- 当然如果你已经看懂了,其实在压缩版的
select2.full.min.js
中直接改也是一样的。
二、分享Debug思路
先看原因:
1、分析:汉字显示不全,英文数字正常。应该就是动态改变 input
宽度时中文的宽度没有正常获取。(估计人家根本就没处理中文的情况)
2、证实猜想,去源码中找到动态改变 input
宽度的位置。尝试搜索这个 input
相关的关键字,比如各个属性名。这里优先考虑 “width” 和 “em” 因为动态修改宽度,那属性名和单位出现的几率是最高的。(此时我们去未压缩的版本中找会顺手点)很幸运,火速找到了它。
3、原来作者直接写死了每个字符 0.75 个宽度,js里汉字又只占一个字符。看来完全不考虑我们的死活啊。
修复思路:通过正则分别取出汉字
和英文数字
分别计算: 汉字宽度 + 英文数字宽度 = input实际宽度。
信息:一个汉字2em
修else部分代码:
} else {
//var minimumWidth = this.$search.val().length + 1;
//width = (minimumWidth * 0.75) + 'em';
var str = this.$search.val();
var b1 =str.replace(/[^\u4e00-\u9fa5]/gi,"").length * 2; //统计汉字宽度
var b2 = str.replace(/[\u4e00-\u9fa5]/gi,"").length * .75; //统计非汉字宽度
width = (b1 + b2 + 1) + "em" //算出input宽度
}
经过测试后确定修复。(如果你的项目发布时自动压缩js,那么就到此结束了。否则,继续手动处理一个压缩版)
4、项目中实际使用的肯定是min版。所以按【第一步】进行修改就行了。
三、如果你不想动源码,还有一个非完美修复:
https://select2.org/tagging
直接监听input
的keyup
事件动态修改input
宽度,但这个会有闪烁。(因为每次select2动态修改了一个错误的宽度,然后我们又在 keyup
事件回调中改成一个正确的宽度。所以就闪啊闪啊的。 )
$(document).on('keyup', '.select2-selection--multiple .select2-search__field', function(event){
var $this = $(this);
$this.css('width', '20em');// 写个大点的值就行了。不用计算。
});
相关BUG
解决 select2 部分浏览器开启 tags: true 后无法输入中文的BUG + 解决输入中文后无法回车结束的问题