专栏首页鱼头的Web海洋我的<input />不可能这么可爱

我的<input />不可能这么可爱

  • 作者:陈大鱼头
  • github:KRISACHAN

<input /> 标签是我们日常开发中非常常见的替换元素了,但是最近在刷 whattwg 跟 MDN 的时候发现 跟 <input /> 有很多相关的属性,选择器都没怎么用过,所以就开篇文章来整理一下一些比较有趣或者实用的知识点。

本篇文章默认大家已经知道 <input /> 标签的基本用法,不会做过多的基础说明~

没想到,这些选择器居然跟 input …

到写文章为止,根据最新的 drafts 指出,一共有3大类,16种跟 input 相关的选择。其实都挺有用的,善用它们,会让我们的用户体验更加美好。

下面我们来分享一下这3大类选择器的作用:

第一类:控制系(Input Control States)

选择可使用状态的 <input />
 元素

第二类:输出系(Input Value States)

选择处于选中状态的 <input type="radio" />

第三类:侦查系(Input Value-checking)

选择处于空值时的 <input>
,暂未被浏览器支持

可怕,除了选择器,居然还跟这些属性有关系

<input> 除了有很多相关的选择器,结合不同的type还有不同的属性可以供使用。他们的作用如下:

属性

作用

maxlength

可输入的最大长度

minlength

可输入的最小长度

size

输入框的长度

readonly

输入框是否只读

required

输入框是否必填

multiple

输入框是否可以多选

pattern

输入框验证规则

min

可输入的最小值

max

可输入的最大值

step

输入框每次的增量

list

输入框绑定的可选值数据

placeholder

输入框预选文字

实战

通过上面的三类说明,我们大致了解了 <input /> 标签的相关信息,但是你们以为我是来列list的吗?

当然不是,还有实操啊~

纯CSS实现表单提交功能

首先我们来看个效果图

上面的效果就是一个纯CSS实现的表单提交功能,这是怎么实现的呢?下面我们直接看源码,然后一步一步地来分拆(不想看的可以直接CV下面的源码自己做测试~)

<style>
    :root {
      --error-color: red;
    }
    .form > input {
      margin-bottom: 10px;
    }
    .form > .f-tips {
      color: var(--error-color);
      display: none;
    }
    input[type="text"]:invalid ~ input[type="submit"],
    input[type="password"]:invalid ~ input[type="submit"] {
      display: none;
    }
    input[required]:focus:invalid + span {
      display: inline;
    }
    input[required]:empty + span {
      display: none;
    }
    input[required]:invalid:not(:placeholder-shown) + span {
      display: inline;
    }
</style>
<form class="form" id="form" method="get" action="/api/form">
    账号:
    <input data-title="账号" placeholder="请输入正确的账号" pattern="\w{6,10}" name="account" type="text" required />
    <span class="f-tips">请输入正确的账号</span>
    <br />
    密码:
    <input data-title="密码" placeholder="请输入正确的密码" pattern="\w{6,10}" name="password" type="password" required />
    <span class="f-tips">请输入正确的密码</span>
    <br />
    <input name="button" type="submit" value="提交" />
</form>

第一步:写好基础结构

首先我们来把基础结构给写好,代码如下:

<style>
    :root {
      --error-color: red;
    }
    .form > input {
      margin-bottom: 10px;
    }
    .form > .f-tips {
      color: var(--error-color);
      display: none;
    }
</style>
<form class="form" id="form" method="get" action="/api/form">
    账号:
    <input data-title="账号" placeholder="请输入正确的账号" pattern="\w{6,10}" name="account" type="text" required />
    <span class="f-tips">请输入正确的账号</span>
    <br />
    密码:
    <input data-title="密码" placeholder="请输入正确的密码" pattern="\w{6,10}" name="password" type="password" required />
    <span class="f-tips">请输入正确的密码</span>
    <br />
    <input name="button" type="submit" value="提交" />
</form>

扫一眼,嗯,挺简单的,都是常用的东西。咦,不对,这个 pattern 是什么东西?

在这里我们重点分享下 pattern 这个属性,这是一个用来验证 input[value] 是否合法的属性,里面的内容就是匹配value的,语法便是正则的语法,例子如下:

<label>
    <!--
    当前pattern的内容就是验证input[name="part"]的value的,其规则如同里面的正则一样,匹配input[name="part"]的value是否是一个数字+3个大写字母
    -->
    <input pattern="[0-9][A-Z]{3}" name="part" />
</label>

当然,不同的 input[type] 也会默认带有相应的 pattern ,例如 input[type="email"] 就是默认匹配了以下规则:

/^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/

第二步:重点功能

input[type="text"]:invalid ~ input[type="submit"],
input[type="password"]:invalid ~ input[type="submit"] {
    display: none;
}
input[required]:focus:invalid + span {
    display: inline;
}
input[required]:empty + span {
    display: none;
}
input[required]:invalid:not(:placeholder-shown) + span {
    display: inline;
}

上面便是核心交互的实现。

首先第一个class就是保证了在两个输入框不通过的时候隐藏,就是当输入框值为空或者不符合验证规则,则隐藏提交按钮。

第二个,第三个class则是控制当用户在输入框输入内容时,如果不符合验证规则,则显示错误信息,否则则隐藏。

第四个class则是用过 placeholder 是否存在来控制错误信息的显隐,如果 placeholder 不显示,则证明用户正在输入,错误信息则根据用户输入的值来判断是否显隐,否则则隐藏。

状态切换

上面我们有提到一个选择器 :indeterminate ,这个是用于选择状态不确定的表单元素与 <progress> ,玩过扫雷的人都知道,右击除了可以选择红旗,还可以选择问号,就是选中,但不确定;又跟 promisepending 状态类型,介于 resolvereject 之间。

多了 :indeterminate 会给我们带来很多很有趣的体验。

首先我们来看看它的使用案例。

基础使用法

先看效果

代码如下:

<style>
    body {
        background: #333;
        color: #fff;
        padding: 20px;
        text-align: center;
    }
    input {
        margin-right: .25em;
        width: 30px;
        height: 30px;
    }
    label {
        position: relative;
        top: 1px;
        font-size: 30px;
    }
</style>
<form>
    <input type="checkbox" id="checkbox">
    <label for="option">点击左边</label>
</form>
<script>
      'use strict';
      checkbox.addEventListener('click', ev => {
        if (ev.target.readOnly) {
          ev.target.checked = ev.target.readOnly = false;
        } else if (!ev.target.checked) {
          ev.target.readOnly = ev.target.indeterminate = true;
        };
      });
</script>

这里面其实没有什么复杂的实现,只是做了个中间态的判断,就非常轻松的实现了radio的三种状态切换。

秀到头皮发麻法

先看效果

(此天秀效果来自于 Ben Szabo 的 codepen,有兴趣的可以仔细研究下,我何时才能有大佬这么优秀,嘤嘤嘤~)

输入框绑定的可选值

先看效果

其实代码很简单:

<input type="text" list="names" multiple />
<datalist id="names">
    <option value="kris">
    <option value="陈大鱼头">
    <option value="深圳金城武">
</datalist>

<input type="email" list="emails" multiple />
<datalist id="emails">
    <option value="chenjinwen77@foxmail.com" label="kris">
    <option value="chenjinwen77@gmail.com" label="kris">
</datalist>

<input type="date" list="dates" />
<datalist id="dates">
    <option value="2019-09-03">
</datalist>

这里原理就是通过 <input list="dates" /> 来绑定需要下拉显示的数据列表 <datalist id="dates">

那么当我们要实现输入联想的时候,也可以通过修改 <datalist id="dates"> 的子元素来实现,而不是再写一大堆的操作函数来实现。

总结

其实 <input /> 标签还有很多有趣的功能是可以挖掘的,不同的类型,结合不同的选择器与属性,是可以有更多让人为之惊叹的体验的。如果你有兴趣的话,不妨多开开脑洞,亲自动手实现一些有趣的功能,或者有什么有趣的想法也可以在下方给鱼头留言或者加鱼头微信 “krisChans95” 来畅谈。

如果你、喜欢探讨技术,或者对本文有任何的意见或建议,你可以扫描下方二维码,关注微信公众号“鱼头的Web海洋”,随时与鱼头互动。欢迎!衷心希望可以遇见你。

本文分享自微信公众号 - 鱼头的Web海洋(krissarea),作者:陈大鱼头

原文出处及转载信息见文内详细说明,如有侵权,请联系 yunjia_community@tencent.com 删除。

原始发表时间:2019-09-03

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 纯CSS实现表单验证

    在我们的日常业务中,表单验证是个很常见设计需求,像一些登录注册框,问卷调查也都需要用到表单验证。

    陈大鱼头
  • 二营长,快掏个CSS出来给我画个井字棋游戏

    上面的就是本次文章的最终结果,一个用纯CSS实现的AI井字棋游戏,Mmmm,虽然看起来有点蠢。。。

    陈大鱼头
  • 『真香警告』这33个超级好用的CSS选择器,你可能见都没见过。

    CSS 选择器也是如此,然而如今也已经发布了第四版 —— CSS Selectors Level 4 ,这一版最早的草案发布于2011年09月29日,最后更新是...

    陈大鱼头
  • Python区分raw_input()与

    raw_input()与input()均是 python 的内建函数,通过读取控制台的输入与用户实现交互。

    py3study
  • python中input()与raw_input()的区别到底是啥?

    首先先给出总结:input () = int(raw_input()) 有图有真相!!! ? 先看看input的例子: ? 可见用input键入得到int类型的...

    marsggbo
  • python案例-for循环

    编写一个程序,让用户输入3个数字:(f)rom,(t)o和(i)ncrement。以i为步长,从f计数到t,包括f和t。例如,如果输入的是f = 2,t = 2...

    py3study
  • Python2 中 input() 和raw_input()

    在 Python2 中如要想要获得用户从命令行的输入,可以使用 input() 和 raw_input() 两个函数,那么这两者有什么区别呢? 我们先借助 h...

    py3study
  • Python 内置函数大全(上)

    divmod() 函数把除数和余数运算结果结合起来,返回一个包含商和余数的元组(a // b, a % b)。

    Python知识大全
  • 表格内,设置许多元素的大小时,js的速度慢的办法

    思路1:设置td为relative,input为absolute,然后设置input大小为td的大小。

    申君健
  • 【Rust日报】2019-09-06:文字RPG

    作者之前寫過 MUDdy 像MUD的純文字互動遊戲,但只是單機的 Read more

    MikeLoveRust

扫码关注云+社区

领取腾讯云代金券