完成"输入框"取得核心时外边框变蓝

背景

之前做了一个网页,网页中的一切输入框都被设想为“取得鼠标核心时外边框稳定蓝”。倏忽某一天,产物以为如许用户体验不好,不能很显著地通知用户当前鼠标停在那里,因而请求改成“当输入框取得鼠标核心时,外边框自动变蓝;落空核心时外边框恢复原样”。

浏览器自动会给输入框inputtextareaoutline 属性设置一个默许值,效果就是当输入框取得鼠标核心时外边框会自动带上色彩,落空核心时外边框色彩消逝。由于差别浏览器outline 属性的默许值差别,致使外边框的色彩也差别。假如不想要浏览器的outline默许设置,只需要将 outline 属性设置为none 即可。

所以一开始听到这个需求,觉得迥殊简朴,不就是纯 CSS 的题目嘛!我只要将一切输入框的 outline 属性设置为浏览器默许的值就好了,但我想的太无邪了。。。。

1、怎样复制浏览器默许的 outline 款式

由于网页中已有的输入框的款式遍及在各个文件中,有一种异常机器的要领,那就是到每一个文件中去删撤除输入框的 outline:none款式,如许输入框就会运用浏览器默许的 outline 款式了。然则如许做要改的处所太多了,会疯掉的!再想想有没有更费事的要领,有了!在最基本的base.css款式文件中给输入框增加一个focus时候的outline款式不就处置惩罚了么。那末题目来了,该将outline 设置何值,才自动运用浏览器默许的outline款式呢?

我第一个想到的要领是将 outline设置为auto,但发明只要webkit 内核的浏览器才支撑这个属性值,firefox 不支撑,由于auto 并非范例的outline 值。所以要想直接复制浏览器默许的outline款式是做不到的。岂非我要针对每一个浏览器设置差别的outline 值,为了这么一点破需求费那末大时间?!算了,费事点的体式格局照样直接摒弃浏览器的默许outline款式,统一将outline设置为一种款式好了。

2、避开 outline,挑选 border

但我发明了新题目,经由过程设置outline款式为输入框增加外边框,效果并不好。由于 outline 没有相似 border-radius的属性来转变边角的弧度。如许就致使了一个题目:当输入框设置了border色彩,同时border-radius3px以上时,能显著的看到outline 外边框并没有和border 重合。看来设置 outline 来到达边框变蓝效果并非最好的挑选,为何不选用设置 border 来到达一样的效果呢?只要将border再设置下 border-shadow,那末看起来也是和outline效果一样的,而且border还能设置border-radius,显现效果更满足需求。

3、怎样让任何一个元素都能 focusable

经由过程设置 border 处置惩罚了大多数输入框,但发明又有了新题目。

网页中有些输入框实在并非单一运用 input/textarea来完成的,这类“输入框”看起来和平常输入框并没有两样,但实在 HTML 构造是一个 div 内里包含着一个 input/textarea 来完成的。而且输入框的边框设置在了父元素 div 上,一切当输入框取得核心时,看到的应该是父元素 div 上的边框变蓝,而不是内里的input/textarea 的边框变蓝。

要想取得核心时父元素 div的边框变蓝,一定可行的要领是经由过程 JS 来完成:给input/textarea 绑定一个 focus 和 一个blur事宜,在focus 事宜处置惩罚函数中将父元素div的边框置蓝,在blur事宜处置惩罚函数中将父元素div的边框恢复原样。这类要领时相对可行的,然则我总以为应该有更简朴的,地道运用 css 完成的要领。

假如想纯真经由过程css 完成,起首想到的是用挑选器div:focus。然则发明div上没法运用:focus伪类。因而我就猜测:能够并非一切的元素都是 focusable的,那末得找一份申明哪些元素 focusable的范例。

哪些元素是 focusable的?

搜刮效果:

依据 DOM Level 2 HTML范例,focusable 的DOM元素都邑有一个原生的focus()要领,只要 focusable 的DOM 元素才有 focus 事宜,才运用:focus伪类。具有原生的focus()要领的DOM元素包含几种:HTMLInputElement, HTMLSelectElement, HTMLTextAreaElement and HTMLAnchorElement。很显著,范例中遗漏了HTMLButtonElement and HTMLAreaElement。

虽然范例这么定义,但浏览器在完成时倒是别的一套。浏览器给任何一个 HTMLElement 都定义focus()要领,但并非任何一个HTMLElement 都能取得核心(取得核心术语叫 active, 详细请参考:http://help.dottoro.com/ljqmdirr.php)。平常来说,任何一个时候HTML 文档中只会有一个active元素,但并非任何一个元素都能成为active元素。能成为active 的元素包含:

  1. 表单元素(form controllers):input/option/textarea/button

  2. 链接元素(links):a标签、area标签(必需要带 href 属性,包含 href 属性为空)

  3. 能够被编辑的元素(包含经由过程增加 contenteditable = "true"属性变成可编辑的状况)

  4. 设置了 tabindex 属性(tabindex 值非-1)的元素

  5. window:当页面窗口从隐蔽变成前置可见时,focus 事宜就会触发

依据搜刮效果,要想将父元素div变成focusable,只需要在元素上设置 tabindex 属性,然后经由过程:focus伪类设置父元素div 取得核心时的border款式。但我发明当鼠标点击内里的 input 元素时,父元素div并没有取得核心,取得核心的是子元素input

所以末了照样没能经由过程纯 css 的要领来处置惩罚这个题目,无法之下我照样经由过程js去处置惩罚了。。。。。。

    原文作者:ruoyiqing
    原文地址: https://segmentfault.com/a/1190000003936268
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞