jQuery 的一个小坑

趁印象还比较深, 记一下今天遇到的一个不大不小的坑.

起因是这样…

最近在做的工作有关表格的CRUD, 找了个开源的第三方包来做, 功能还是蛮多的, 而且是国人开发的, 顺手推荐一下, bootstrap-table.

照着开发者提供的一个 CRUD example 改造成自己需要的样子. 附上 CodePen.

题外话, 最近经常使用 CodePen 和 jsFiddle, 本来觉得 jsFiddle 长得比较小清新, 更好看些, 可是实际用下来竟然觉得 CodePen 更好用. 主要两个地方不爽jsFiddle, 一是经常很卡打开很慢, 二是添加 external resources 的时候竟然要求一定要 CDN 的. 另外 CodePen 有个可以自由选取预处理器的功能比jsFiddle也方便一些. 抽时间做个自己的 CodePen theme

See the Pen zBjLwQ by bamboo (@bambooom) on CodePen.

stuck in radio….?!

因为不想跳转页面, 就希望更新表格数据什么的也可以在同一页完成, 所以就选择了弹窗.

正常考虑打开弹窗编辑, 会自动填充好表格中已有的值. 这个通过 showModal 实现了. 一开始觉得挺好, 后来发现一个神奇的问题, 那就是如果多次打开 modal, radio checked 却表现诡异. 查看元素后, 明明显示是正确的元素 checked="checked", 但是页面就是不显示哪个选项被选择了. 我一般用 chrome, 换成 safari 也是一样的问题.

菜鸟懵逼好几分钟….搜索一圈, 尝试了几种网上说的方法无果, 抓头发抓疯了后请求同事帮忙, 同事设断点什么的 debug, 然后表示也很奇怪, 但说反正肯定是我代码有问题. 那为什么重新刷新页面, 第一次点开 modal 的话就显示的是正确的呢?

正值午饭时间, 带着一肚子 黑人问号.jpg 吃完了饭+发了个呆+睡了个午觉, 下午看到上午打开的一个 SO 页面, How to check a radio button with jQuery ? - Stack Overflow, 又瞟了一眼, 发现自己又犯了视而不见的醉点, 没有认真读答案, 票数最高的答案写的很清楚,

$("#radio_1").prop("checked", true)
For versions of jQuery prior to 1.6, use: $("#radio_1").attr('checked', 'checked');

也就是说我在给 radio element 填充数值的时候不应该用 .attr(), 而应该用 .prop(), 非常明显我使用的 jQuery 版本早就超过1.6了.

就说 radio 这种常用元素怎么可能留这么奇怪的问题到现在…..😂

修正之后多次打开弹窗就正常了.

See the Pen AXagzB by bamboo (@bambooom) on CodePen.

辣么propattr 有啥区别

搜了才发现, 这是 jQuery 在版本更新到1.6.1 开始的变化, 官方 blog 5年前发布的时候就说很清楚了….(啊啊啊啊啊啊, 又没好好读官方文档…抽)

曾经只有 attr() 这一个 method 去控制元素的 attribute, 1.6.1 开始新增加了一个 prop(), 由于旧有的attr()很难维护才重新增加的. 最重要的区别就是, 对于类似checked, selected, readonly, disabled 这种 boolean attribute, jQuery 都需要使用 prop() 去控制, 而旧的attr()设置只会影响 initial value, 所以我的弹窗第一次点开的时候显示是正确的.

经实验, 就算在页面更改 radio 或者 checkbox 选择的选项, 在 html 里是不会看到所谓 checked="checked" 这个 attribute 有任何变化.

另外两个值得一读的资料: