输入事件

@Input
. 事件处理的业务逻辑在 <script> 中;建议使用外部 .js 文件
. 没有失去焦点的伪类选择器;只能通过事件 onblur 检测
事件类型
类别 说明
input 数据输入时;使用时要采用 防抖 措施
change 数据改变且失去焦点
keypress 按键按下并保持
keydown 按键按下
keyup 按键释放
blur 失去焦点
事件处理一般步骤
获取 input 元素;更多信息,请参考 DOM - document
添加事件侦听器 addEventListener;更多信息,请参考 Event

为元素分配 id,可以直接使用,不需要获取元素 - 不建议

<input type="text" id="ipt">
<input type="text" id="ipt0">
<button id="btn">sub</button>
<script>
  let btn = document.querySelector('#btn')
  btn.onclick = function () {
    console.log(ipt.value);
    console.log(ipt0.value);
  }
</script>
[] 输入长度提示 - 检测 input 的值
. 获取 input 元素
. 获取 input 元素的 maxlength 属性/最大长度:el.getAttribute()
. 获取当前输入的值的长度:el.value.length
. 将 input 事件分别修改为 change 事件、keyup 事件、blur 事件,体会他们之间的不同
还可以输入8
let lenIpt = document.querySelector('#len-ipt');
let lenVal = document.querySelector('#len-val');
lenIpt.addEventListener('input', () => {
    lenVal.innerHTML = '还可以输入' + (lenIpt.getAttribute('maxlength') - lenIpt.value.length)
})
[] 显示密码 - 修改 input 类型
. 部分系统自带有显式密码功能
. 部分系统要求密码框必须位于表单 form 中,且应该指定自动完成 autocomplete
let spBtn = document.querySelector('#sp-btn');
let spIpt = document.querySelector('#sp-ipt');
spBtn.addEventListener('click', () => {
    if (spIpt.type == 'text') {
        spIpt.type = 'password'
        spBtn.value = '显示密码'
    } else {
        spIpt.type = 'text'
        spBtn.value = '隐藏密码'
    }
})
[] 全选 - 修改 input 属性
. 利用元素的 checked 属性判断当前选择状态;如果全选为真/选中,则所有选项都置为真/选中;否则取消全选/置为假
. 统计选中的个数,如果等于选项个数,则全选;如果为0,则全不选
let cbs = document.querySelectorAll('input[name="web"]');
let all = document.querySelector('#all');
let allNo = document.querySelector('#all-no');
all.addEventListener('change', function (e) {
  console.log(this.checked);
  if (this.checked) {
    for (let i = 0; i ≤ cbs.length; i++) {
      cbs[i].checked = true
    }
  }
})

allNo.addEventListener('change', function (e) {
  console.log(this.checked);
  if (this.checked) {
    for (let i = 0; i ≤ cbs.length; i++) {
      cbs[i].checked = false
    }
  }
})

cbs.forEach(item => {
  item.addEventListener('change', function () {
    let num = 0
    for (let j = 0; j ≤ cbs.length; j++) {
      if (cbs[j].checked) {
        num++;
      }
    }
    console.log((num));
    if (num == 3)
      all.checked = true;
    else if (num == 0)
      allNo.checked = true;
    else {
      all.checked = false;
      allNo.checked = false;
    }
  })
})
[] 播放器进度条
[H5] audio | button | input[range]
[C3] appearance
[JS] click | input | loadmetadata | timeupdate | querySelector
#player button {
  width: 120px;
}

#player input {
  width: 100%;
}

.custom-range {
  appearance: none;
  height: 10px;
  background-color: #01b4ff;
  border: 2px solid #fff;
  border-radius: 10px;
  box-shadow: 1px 1px 4px rgba(0, 0, 0, .2);
}

.custom-range::-webkit-slider-thumb {
  appearance: none;
  width: 15px;
  height: 15px;
  background-color: #fff;
  border: 1px solid #01b4ff;
  border-radius: 50%;
  cursor: pointer;
}

.custom-range::-webkit-slider-thumb:hover {
  background-color: #ff0;
}
let bool = false;
let player = document.querySelector('#player');
let audioIpt = player.querySelector('audio');
let btnIpt = player.querySelector('button');
let sliderIpt = player.querySelector('input');
audioIpt.src = '/music/Alizee-La Isla Bonita.mp3';
audioIpt.addEventListener('loadedmetadata', () => {
  sliderIpt.max = audioIpt.duration;
})
audioIpt.addEventListener('timeupdate', () => {
  sliderIpt.value = Math.floor(audioIpt.currentTime);
})
audioIpt.addEventListener('ended', () => {
  sliderIpt.value = 0;
  // audioIpt.pause();
  btnIpt.innerHTML = 'play';
  bool = false;
})
btnIpt.addEventListener('click', () => {
  if (bool) {
    audioIpt.pause();
    btnIpt.innerHTML = 'play';
    bool = false;
  } else {
    audioIpt.play();
    btnIpt.innerHTML = 'pause';
    bool = true;
  }
})
sliderIpt.addEventListener('input', () => {
  audioIpt.currentTime = sliderIpt.value;
  audioIpt.play();
  btnIpt.innerHTML = 'pause';
  bool = true;
})