DEV Community

Juan Pablo Guisasola
Juan Pablo Guisasola

Posted on

Short example of :has selector

The idea

Make a label transition from above the input to its initial position when you focus the input using :has selector

Image description

Basic Form

Let's put a basic form just as an example

<form action="">
    <div class="form-field">
        <label for="">Name</label>
        <div class="field">
            <input type="text">
        </div>
    </div>
</form>
Enter fullscreen mode Exit fullscreen mode

Basic Style

I'm going to add some padding to the input, and put the label above the input

    input{
        padding: 5px 20px;
    }
    label{
        color:#666;
        transform:translate(.8rem, 1.5rem);
        transition:all .3s ease;
        display: block;
        pointer-events: none; 
    }
Enter fullscreen mode Exit fullscreen mode

We are going to add pointer-events: none; to the label aswell to allow focus on the input since the label messes with the focus interactions

Now it looks like this

Image description

:has

First we need to target any <div> sibling of <label>

we can use the ~ sibling combinator which targets any sibling, no matter if it is a previous or next one and along with that we can check in <div> has an input:focus as child

    label:has(~ div input:focus){
        transform: translate(0, 0);
    }
Enter fullscreen mode Exit fullscreen mode

Final result

    input{
        padding: 5px 20px;
    }
    label{
        color:#666;
        transform:translate(.8rem, 1.5rem);
        transition:all .3s ease;
        display: block;
        pointer-events: none;
    }
    label:has(~ div input:focus){
        transform: translate(0, 0);
    }
Enter fullscreen mode Exit fullscreen mode

If you know more about this selector and have recommendations for compatibility let me know in the comments

Some sources:
https://css-tricks.com/child-and-sibling-selectors/
https://ishadeed.com/article/css-has-parent-selector/

Top comments (0)