1

I'm trying to replicate an effect I've seen on a form web page.

When the user clicks on an input field to insert a text

  1. the placeholder label is moved on top
  2. the bottom line border is highlighted with an animation

like the one you see here, but made with angular: http://md-pro-angular.creative-tim.com/forms/wizard

I think that gives a very clear and effective user experience, especially on long forms

Do you know if there is a plugin for jquery to create an effect like this?

1
  • Check my answer, i made it to start from the center ;) Commented Nov 3, 2017 at 18:32

3 Answers 3

3

Here's a similar solution using only css, hope it helps.

input:focus~label,
input:valid~label
{
  font-size: 0.75em;
  color: #999;
  top: -2.25rem;
  transition: all 0.625s cubic-bezier(0.2, 0, 0.03, 1);
}

.styled-input {
  float: left;
  width: 33.3333%;
  margin: 2rem 0 1rem;
  position: relative;
}

.styled-input label {
  color: #999;
  padding: 1rem;
  position: absolute;
  top: 0;
  left: 0;
  transition: all 0.25s cubic-bezier(0.2, 0, 0.03, 1);
  pointer-events: none;
}

input {
  padding: 1rem 1rem;
  border: 0;
  border-bottom:1px solid #999;
  width: 84%;
  font-size: 1rem;
}

input~span {
  display: block;
  width: 0;
  height: 3px;
  background: #e91e63;
  position: absolute;
  bottom: 0;
  left: 0;
  transition: all 0.625s cubic-bezier(0.2, 0, 0.03, 1);
}

input:focus {
  outline: 0;
}

input:focus~span {
  width: 100%;
  transition: all 0.625s cubic-bezier(0.2, 0, 0.03, 1);
}
<div class="styled-input">
  <input type="text" required />
  <label>Name</label>
  <span></span>
</div>

Sign up to request clarification or add additional context in comments.

4 Comments

many thanks!! it's perfect. I'll check how to have the highlight start from the center expanding on left and right.
@Giox You're welcome, is what is missing to be the same as the example of the question, =)
@Giox you may also have a look to my answer :)
@Giox, please look my answer, it is according to web standards using classie.js
1

Here is a pure CSS solution for this :

.input-container {
  max-width: 200px;
  position: relative;
  display: inline-block;
}

.input-container span {
  position: absolute;
  right: 50%;
  left:50%;
  height: 2px;
  bottom: 0;
  background: red;
  transition: 0.5s;
}

label {
  position: absolute;
  font-size: 18px;
  color: #a5a5a5;
  top: 20px;
  left: 10px;
  transition: 0.5s;
  cursor:initial;
}

input {
  padding: 20px 10px 10px;
  border: none;
  border-bottom: 2px solid #ccc;
  transition: 0.5s;
}

input:focus {
  outline: none;
}

input:focus+label {
  font-size: 12px;
  top: 5px;
}

input:focus~span {
  right: 0;
  left: 0;
}
<div class="input-container">
  <input id="in_1" type="text" />
  <label for="in_1">Label text</label>
  <span></span>
</div>

1 Comment

Of course, a solution with greater compatibility ;)
-1

Input must be look like website text field, not mobile app edit text field. See my solution according to website standards with classie.js, I have used classie.js inside script, you can include as separate file as resource inside head tag. Read more about classie.js, please visit https://github.com/desandro/classie

/*classie.js  Strat*/ 

/*!
 * classie - class helper functions
 * from bonzo https://github.com/ded/bonzo
 * 
 * classie.has( elem, 'my-class' ) -> true/false
 * classie.add( elem, 'my-new-class' )
 * classie.remove( elem, 'my-unwanted-class' )
 * classie.toggle( elem, 'my-class' )
 */

/*jshint browser: true, strict: true, undef: true */
/*global define: false */

( function( window ) {

'use strict';

// class helper functions from bonzo https://github.com/ded/bonzo

function classReg( className ) {
  return new RegExp("(^|\\s+)" + className + "(\\s+|$)");
}

// classList support for class management
// altho to be fair, the api sucks because it won't accept multiple classes at once
var hasClass, addClass, removeClass;

if ( 'classList' in document.documentElement ) {
  hasClass = function( elem, c ) {
    return elem.classList.contains( c );
  };
  addClass = function( elem, c ) {
    elem.classList.add( c );
  };
  removeClass = function( elem, c ) {
    elem.classList.remove( c );
  };
}
else {
  hasClass = function( elem, c ) {
    return classReg( c ).test( elem.className );
  };
  addClass = function( elem, c ) {
    if ( !hasClass( elem, c ) ) {
      elem.className = elem.className + ' ' + c;
    }
  };
  removeClass = function( elem, c ) {
    elem.className = elem.className.replace( classReg( c ), ' ' );
  };
}

function toggleClass( elem, c ) {
  var fn = hasClass( elem, c ) ? removeClass : addClass;
  fn( elem, c );
}

var classie = {
  // full names
  hasClass: hasClass,
  addClass: addClass,
  removeClass: removeClass,
  toggleClass: toggleClass,
  // short names
  has: hasClass,
  add: addClass,
  remove: removeClass,
  toggle: toggleClass
};

// transport
if ( typeof define === 'function' && define.amd ) {
  // AMD
  define( classie );
} else {
  // browser global
  window.classie = classie;
}

})( window );

/*classie.js  Ended*/





(function() {
				// trim polyfill : https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/Trim
				if (!String.prototype.trim) {
					(function() {
						// Make sure we trim BOM and NBSP
						var rtrim = /^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g;
						String.prototype.trim = function() {
							return this.replace(rtrim, '');
						};
					})();
				}

				[].slice.call( document.querySelectorAll( 'input.input-field' ) ).forEach( function( inputEl ) {
					// in case the input is already filled..
					if( inputEl.value.trim() !== '' ) {
						classie.add( inputEl.parentNode, 'input-filled' );
					}

					// events:
					inputEl.addEventListener( 'focus', onInputFocus );
					inputEl.addEventListener( 'blur', onInputBlur );
				} );

				function onInputFocus( ev ) {
					classie.add( ev.target.parentNode, 'input-filled' );
				}

				function onInputBlur( ev ) {
					if( ev.target.value.trim() === '' ) {
						classie.remove( ev.target.parentNode, 'input-filled' );
					}
				}
			})();
		
.input {
position: relative;
z-index: 1;
display: inline-block;
margin: 1em;
max-width: 350px;
width: calc(100% - 2em);
vertical-align: top;
}

.input-field {
position: relative;
display: block;
padding: 16px;
width: 60%;
border: none;
border-radius: 0;
background: #f0f0f0;
color: #aaa;
font-weight: 400;
font-size: 16px;
-webkit-appearance: none;
}

.input-field:focus {
outline: none;
}

.input-label {
display: inline-block;
float: right;
padding: 0 1em;
width: 40%;
color: #696969;
font-weight: bold;
font-size: 70.25%;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}

.input-label-content {
position: relative;
display: block;
padding: 1.6em 0;
width: 100%;
}



/* Yoshiko */
.input-field-animate {
width: 100%;
background-color: #d0d1d0;
border: 2px solid transparent;
-webkit-transition: background-color 0.25s, border-color 0.25s;
transition: background-color 0.25s, border-color 0.25s;
}

.input-label-animate {
width: 100%;
text-align: left;
position: absolute;
bottom: 100%;
pointer-events: none;
overflow: hidden;
padding: 0 1.25em;
-webkit-transform: translate3d(0, 3em, 0);
transform: translate3d(0, 3em, 0);
-webkit-transition: -webkit-transform 0.25s;
transition: transform 0.25s ;
-webkit-transition-timing-function: ease-in-out;
transition-timing-function: ease-in-out;
}

.input-label-content-animate {
color: #8B8C8B;
padding: 0.25em 0;
-webkit-transition: -webkit-transform 0.25s;
transition: transform 0.25s;
-webkit-transition-timing-function: ease-in-out;
transition-timing-function: ease-in-out;
}

.input-label-content-animate::after {
content: attr(data-content);
position: absolute;
font-weight: 800;
bottom: 100%;
left: 0;
height: 100%;
width: 100%;
color: #a3d39c;
padding: 0.25em 0;
text-transform: uppercase;
letter-spacing: 1px;
font-size: 0.85em;
}

.input-field-animate:focus + .input-label-animate,
.input-filled .input-label-animate {
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}

.input-field-animate:focus + .input-label-animate .input-label-content-animate,
.input-filled .input-label-content-animate {
-webkit-transform: translate3d(0, 100%, 0);
transform: translate3d(0, 100%, 0);
}

.input-field-animate:focus + .input-field-animate,
.input-filled .input-field-animate {
background-color: transparent;
border-color: #a3d39c;
}
<!DOCTYPE html>
<html lang="en" class="no-js">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <title>Animate Input</title>
    </head>
    <body>
        <span class="input input-animate">
            <input class="input-field input-field-animate" type="text" id="input-10" />
            <label class="input-label input-label-animate" for="input-10">
                <span class="input-label-content input-label-content-animate" data-content="First Name">First Name</span>
            </label>
        </span>
    </body>
</html>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.