今天的题目功能是当我们按下checkbox以后,按着shift不放,再按下另一个checkbox,会把两个checkbox之间的checked都设为true,主要重点为逻辑判断。
如下图:
首先,我们先获取所有type为check的input并利用Array.from转成阵列。
并设置firstCheck来储存第一个按下的下标。
const checkBox = Array.from(document.querySelectorAll('.item input[type="checkbox"]')); let firstCheck = null;
而后我们在赋予每个checkbox click事件。
checkBox.forEach(item => { item.addEventListener('click', clickHandler); });
再来我们写一下按下checkbox的处理:
首先在event下有一个为shiftKey的属性,可以判断是否按着shift
接着,我们在判断是否当前按下的input为checked,没有的话就将第一个按下的firstCheck设为null,有的话就在进行一次判断,判断是否有按下shift不放,且我们第一个按下的firstCheck为true,没有的话,就利用indexOf方法
(会回传元素于阵列中第一个被找到之index)将当前所按下input下标给储存至firstCheck,有的话我们就去设置一个变数nowCheck去获取当前下标。
再来就是对所有checkbox利用slice方法(回传一个新阵列物件,为原阵列选择之 begin 至 end(不含 end)参数为(begin,end))
将两个input之间的所有input的checked都改为true,因为我们可能由下案到上,故firstCheck不一定小于nowCheck
,故利用Math.max,min去抓最大值(放后面)及最小值(放前面)
,最后再利用forEach对每个处理好的input的checked改为true即可。
function clickHandler(e) { // console.log(e.shiftKey); // 当按着shift去check就会为true if (this.checked) { // 当按着shift且当前有按下check if (e.shiftKey && firstCheck !== null) { // 获取当前的下标 let nowCheck = checkBox.indexOf(this); // 利用Math.max,min去抓最大值(放后面)及最小值(放前面) checkBox.slice(Math.min(nowCheck, firstCheck), Math.max(nowCheck, firstCheck)).forEach(item => { item.checked = true; }); } // 如果第一个按下的input为checked,就储存其下标 firstCheck = checkBox.indexOf(this); } else { firstCheck = null; } }