6
\$\begingroup\$

I am just testing how I solved simple stuff.

Goal: The aim is to expand the width of an input and collapse it.

When mouseover expand,.

When mouseout collapse.

When you have text inside the input keep it expanded.


To me it seems too much, repeating some stuff in JS. Also thought about adding a debouncer or throttle but was not successful.

There's probably another way to solve it with pure CSS.

HTML:

<body>
<p>
    2 inputs, 1 is collapsed 
    the other is expanded

</p>    
<br>
collapsed   
<br>
    <input type="text" class="collapsed">
    <br>
    <br>
    expanded
    <br>
    <input type="text" class="expanded">
</body>

CSS:

input {
    width: 20px;
    transition: width 1s;
}

.expanded{
    width: 256px;
}

JS:

let collapsedInput = document.querySelector('.collapsed');

const handleMouseOut = () => {
    collapsedInput.classList.remove('expanded');
}

const handleMouseOVer = () => {
    collapsedInput.classList.add('expanded');
}

collapsedInput.addEventListener('mouseover', handleMouseOVer);

collapsedInput.addEventListener('mouseout', handleMouseOut);

collapsedInput.addEventListener('input', () => {
    if(collapsedInput.value !== ""){
        collapsedInput.classList.add('expanded');
        collapsedInput.removeEventListener('mouseout', handleMouseOut);
    } else {
        collapsedInput.classList.remove('expanded');
        collapsedInput.addEventListener('mouseout', handleMouseOut);
    }
})
\$\endgroup\$
5
\$\begingroup\$

The biggest critique about the Javascript I have is that collapsedInput could be declared with const because it doesn't get re-assigned.

It is possible that the code in the event listener for the input event could be simplified using classList.toggle().

If there is only one element with class name collapsed then perhaps it would be better to use an id attribute and use document.getElementById() to select it. Those older methods are faster than the querySelector() varieties.

There's probably another way to solve it with pure CSS.

Yes... one way is to use the required attribute on the first <input> element along with the :valid and :hover pseudo-selectors :

input {
    width: 20px;
    transition: width 1s;
}

input:valid,
input:hover,
.expanded {
    width: 256px;
}
<p>
    2 inputs, 1 is collapsed 
    the other is expanded

</p>    
<br>
collapsed   
<br>
    <input type="text" class="collapsed" required>
    <br>
    <br>
    expanded
    <br>
    <input type="text" class="expanded">

\$\endgroup\$
  • \$\begingroup\$ +1 however a very minor point in regard to transitions. 1 second is way too long, 1/5th - 1/3rd second still adds wiz-bang without giving an interface a slow feel \$\endgroup\$ – Blindman67 Sep 10 at 23:55
  • \$\begingroup\$ At the risk of sounding naive, could you explain more about "wiz-bang"? If you have enough for an answer maybe we could get this up to a HNQ... \$\endgroup\$ – Sᴀᴍ Onᴇᴌᴀ Sep 11 at 0:01
  • \$\begingroup\$ wiz-bang as in look good, or slick. Better than no transition at all. \$\endgroup\$ – Blindman67 Sep 11 at 0:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.