必须用 xmselect.render() 渲染多选组件,不可使用原生 select[multiple];el 必须为非 select 容器,data 为含 name/value 的数组,multiple: true 不可省略,value 默认选中需为同类型数组,动态数据须在 ajax 成功后渲染。

必须用 xmSelect.render() 渲染,别碰原生 select[multiple]
Layui 2.x 的 form.render() 和 form.on('select') 完全不处理 multiple 属性——你写了 <select multiple></select>,Layui 不会渲染 UI,也不触发多选事件,this.value 永远是空字符串或第一个选中项。后端收不到数组,表单验证也失效。
正确做法是:用一个空容器(比如 <div id="roleSelect"></div>)代替 select 标签,然后调用 xmSelect.render() 渲染。组件内部用原生 DOM 构建悬浮面板,完全绕过 Layui 的 select 渲染链。
常见错误现象:
- 页面上勾了三项,但
console.log(this.value)打印出""或单个值 - 提交表单时,后端只收到一个 ID,而不是数组
-
form.val()读不出值,或读出的永远是字符串而非数组
xmSelect.render() 最小可用配置缺一不可
漏掉任意一个必填项,组件要么不渲染,要么降级为单选。
-
el:必须是 CSS 选择器(如'#roleSelect')或 DOM 元素,不能是select标签本身 -
data:数组,每个对象至少含name和value;value类型要和后端字段一致(1和"1"不等价) -
multiple: true:不是可选项,是开启多选的开关;漏掉它,点第二项就会取消第一项
最小可用示例:
layui.use(['xmSelect'], function() {
var xmSelect = layui.xmSelect;
xmSelect.render({
el: '#roleSelect',
data: [
{name: '管理员', value: 1},
{name: '编辑', value: 2},
{name: '审核员', value: 3}
],
multiple: true
});
});
默认选中、远程搜索、数量限制怎么配
这些不是“开了就行”的开关,参数类型和结构错一点就失效。
-
value:必须是数组,哪怕只默认选一个也要写成[1];类型必须和data中的value一致([1]vs["1"]不能混) -
max:设了就是硬限制,第三项点击无响应,也不触发on: select;注意初始化时可以传超限值(比如value: [1,2,3]但max: 2),但之后无法取消再选 -
searchType: 'server'+remoteMethod:必须返回标准格式{code: 0, data: []};data数组结构要和本地数据一致(每个对象含name/value);不要用$.get(...).done(...)直接塞进data,那是本地搜索逻辑
提交前必须手动同步值到隐藏域或 form.val()
xm-select 不接管 Layui 表单的值管理机制,不写同步逻辑,表单提交时后端收不到任何值。
- 推荐方案:加一个
<input type="hidden" name="role_ids" id="roleIds">,在on: select或提交前调用instance.getValue('value').join(',')写入 - 如果要用
form.val(),得手动调用form.val('formFilter', {role_ids: instance.getValue('value')}),否则form.val()读不到 - 注意:
getValue()默认返回对象数组,加参数'value'才返回纯值数组;后端期望字符串逗号分隔还是 JSON 数组,取决于你拼接方式
最易被忽略的一点:所有动态加载的数据(比如权限列表通过 AJAX 获取),必须等 data 返回后再调用 xmSelect.render();在 success 回调里渲染,别在 ajax 外部直接 render —— 否则 data 是空数组,下拉框没选项。











