CSS并不简单--个性化输入框的实践

xiaoxiao2021-02-28  78

这次通过这个个性化的输入框,给大家介绍一些容易忽略的知识点。(新手注意:本文的html采用的是jade,css采用的sass,js采用的vue)

一、效果

 大家先看一下效果动态图,思考一波,带着你的思考来看接下来的内容,可能效果更好一点。

PC端demo地址

二、需求

 当我们开始做一样东西的时候一定要先分析它的需求:  * 当输入框获取焦点时,提示文字发生上移动画,同时下面线条产生动画;  * 当输入框失去焦点时,并且未填写内容时,提示文字和线条恢复之前的状态。  * 当输入框失去焦点时,填写内容时,状态不变。

三、结构

 看了上面的效果图,首先就是要确定html的结构:

div.item input(type="text" name="card" id="card" placeholder="身份证" v-card="" maxlength="18") label(for="card") Card div.focusline

 这里唯一遗憾的是input不支持伪元素(::after、::before),所以不得不采用一个额外的div。  这里额外提一下,maxlength 只能用于input的type为password和text的情况,所以不要再问为什么maxlength不起作用了。

四、表现

 其实对于上面所要实现的效果,我们完全可以通过JS来控制,但是一直在强调表现(CSS)与行为(JS)分离,所以我们完全通过CSS的特性解决表现上的问题,更加完美。但是并不是所有CSS属性浏览器多支持(这就尴尬了)。这里我要用的几个特性,大家最好在Chrome中实验。

 其实需求1与需求2是同一个需求,通过伪类focus和过渡属性就能搞定。

input:focus + label { color: rgb(82,97,107); transform: translate(10px, 0) scale(.9); } input:focus ~ div { width: 100%; }

 对于第三个需求,我们就得用一些新玩意了,第一个就是伪元素placeholder(伪类采用: 而伪元素采用::), 这里我们要隐藏placeholder,好显示我们的label:

input { &:placeholder { opacity: 0; } }

 我们知道当输入文字后,placeholder就不再显示了,所以这里来了一个伪类placeholder-shown(可以通过can i use 查一下它的兼容性):

input:not(:placeholder-shown) + label { color: rgb(82,97,107); transform: translate(10px, 0) scale(.9); } input:not(:placeholder-shown) ~ div { width: 100%; }

五、行为

 这里我还要唠叨一下,从上面可以看出这是一个身份证输入框,我们多知道身份证是由数字和字母,而且字母只出现在第18位,而且只能是字母x。所以我上面采用了text类型的输入框,为了让用户很好的输入,会出现这几种问题:  * 切换为中文输入法时存在的问题;  * 复制粘贴的问题;  * 输入其他非法字符的处理。

 这里我们主要通过input、compositionstart、compositionend、paste四个事件解决。

let legalContent, //开启输入法之前的输入内容 LOCK = false; //是否开启中文输入法 el.addEventListener('compositionstart', (e) => { /** * -------------- * 开启中文输入法 * -------------- */ legalContent = e.target.value; //保存中文输入法之前的内容 LOCK = true; //加上锁 }, false); el.addEventListener('compositionend', (e) => { /** * --------------------- * 结束中文输入法 * --------------------- */ e.target.value = legalContent; LOCK = false; // 解锁 }, false); el.addEventListener('input', (e) => { const len = e.target.value.length; /** * 在中文触发时 不进行处理 * 当身份证号码少于18位时只能输入数字 * 当身份证号码为18位时可以输入数字和字母 */ if (!LOCK) { if (len <= 17) { e.target.value = e.target.value.replace(/\D/,''); } else { e.target.value = e.target.value.replace(/[^0-9Xx]/,''); } } }, false); el.addEventListener('paste', (e) => { /** * ---------- * 粘贴 * ---------- */ e.preventDefault(); //阻止默认事件 }, false);

觉得不错的同学,来一波关注吧,你的关注就是我写作的动力。 更多文章 简书 源码: GitHub

转载请注明原文地址: https://www.6miu.com/read-36237.html

最新回复(0)