layui select 没有原生“取消选择”事件,需通过判断 data.value === "" 识别空选项选择,并用缓存变量对比上一次值来区分主动取消与首次选空,且必须使用 form.on('select(filter)') 并确保 form.render() 调用。
layui 的 select 本身没有「取消选择」的独立事件,所谓“被取消选择”,实际是用户从已有选项中切到另一个选项(包括切回空值),而 form.on('select(filter)') 每次点击任意 option 都会触发——哪怕选的是同一个值、或选了空 <option value=""></option>。所以不存在原生意义上的“取消”事件,只能靠自己判断。
为什么 form.on('select') 总是触发,却拿不到“上一次的值”
layui 封装的 form.on('select(filter)') 回调只传入当前状态:data.value 是这次选中的值,不带历史。它不区分“首次选择”“切换选项”还是“点回空值”,只要 DOM 被点击就触发。
- 如果你的
select允许空值(比如第一个<option value="">请选择</option>),那么用户点它,data.value就是空字符串"",这就是你所谓的“取消选择” - 但如果没有空选项,用户无法真正“取消”,只能换一个非空值——这时你得自己缓存上一次的
value做比对 -
data.elem.value和$(data.elem).val()在 layui 渲染后不可靠,永远只认data.value
监听“选为空值”这个明确动作
最简单可靠的方式:确保 HTML 中存在一个明确的空选项,并在回调里判断 data.value === ""。
<select lay-filter="status"><option value="">全部状态</option> <option value="1">启用</option> <option value="2">停用</option></select>
form.on('select(status)', function(data){ if(data.value === ''){ console.log('用户选择了“全部状态”,等效于取消筛选'); } });
- 这个判断成立的前提是:空选项的
value确实是空字符串,不是"null"或"undefined" - 如果后端返回的空值是
"0"或"-1",那就按实际约定判断,比如data.value === '0' - 不要依赖
data.elem.selectedIndex === 0,因为 layui 可能重排 DOM,索引不可靠
需要感知“从有值变成空”时的差异处理
如果业务要求严格区分「首次打开就选空」和「从某值切到空」,就得自己维护上一次的值:
let lastSelectValue = '';
form.on('select(status)', function(data){
const current = data.value;
if(current === '' && lastSelectValue !== ''){
console.log('用户主动取消了之前的选择');
}
lastSelectValue = current;
});
- 初始化时
lastSelectValue设为空字符串,表示尚未触发过任何选择 - 动态插入
select或用 AJAX 替换option后,必须调用form.render('select'),否则form.on不生效,缓存逻辑就断了 - 别把缓存变量写在闭包外全局作用域,多个同名
lay-filter的select会互相污染;建议按 filter 名做映射,如lastValues = { status: '', type: '' }
别踩这些坑
有人试图用原生 change 或 jQuery .on('change') 监听,结果完全没反应——因为 layui 把原始 select 设为 display:none,所有交互都发生在它生成的美化 DOM 上,原生事件根本收不到。
- 唯一有效方式只有
form.on('select(filter)'),且lay-filter必须匹配 -
select必须包裹在class="layui-form"的容器内,否则form模块不接管 - 如果页面用 JS 动态加载了新的
select,漏掉form.render('select'),监听函数永远不会执行 - 别混淆
radio和select的事件名:form.on('radio(filter)')才是单选框,写成select就失效
真正的难点不在监听本身,而在如何定义“取消”——是 UI 上的空选项?还是业务逻辑里的重置语义?搞清这点,才能决定要不要加缓存、要不要和服务端对齐空值含义。











