JSFiddle - React, Tailwind, and code Playground
by danya_postfactum
HTML
<!-- <script src="addEventListener.js"></script>
<script src="classList.js"></script> -->
<form action="">
<p><input type="text" name="name" required="" pattern="[a-zA-Z]{2,64}" title="От 2 до 64 символов латинского алфавита." placeholder="Имя" /></p>
<p><input type="email" name="email" required="" pattern="[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+" placeholder="Email" /></p>
<p><input type="password" name="password" required="" pattern=".{2,64}" placeholder="Пароль" /></p>
<p><input type="password" name="passwordConfirm" required="" placeholder="Пароль еще раз" /></p>
<p><button type="submit">Отправить</button></p>
</form>
<script>
var form = document.querySelector('form');
var validator = new FormValidator(form, {
'passwordConfirm': function(input) {
return {state: input.value == input.form.password.value, error: 'Пароли не совпадают.'}
}
});
</script>
CSS
input{
border: 1px solid #777;
}
input:focus{
outline: none;
box-shadow: 0 0 5px rgb(179, 179, 179);
}
.state-error{
border-color: red;
}
.state-success{
border-color: green;
}
.validation-message {
padding: 15px;
background: #fff;
border-radius: 4px;
border: 1px solid #C5C5C5;
box-shadow: 0 0 6px rgba(0, 0, 0, 0.23);
position: fixed;
margin-top: 10px;
font: 11px/1.4 Verdana;
cursor: default;
white-space: pre-wrap;
max-width: 26em;
}
.validation-message:after, .validation-message:before {
bottom: 100%;
left: 1.2em;
border: solid transparent;
content: " ";
height: 0;
width: 0;
position: absolute;
pointer-events: none;
}
.validation-message:before {
border-color: rgba(197, 197, 197, 0);
border-bottom-color: #C5C5C5;
border-width: 10px;
margin-left: -10px;
}
.validation-message:after {
border-color: rgba(255, 255, 255, 0);
border-bottom-color: #fff;
border-width: 9px;
margin-left: -9px;
}
JavaScript
function FormValidator(form, rules) {
form.noValidate = true;
var events = ['submit', 'input'];
if (!('oninput' in form))
events = ['submit', 'keydown', 'paste', 'cut', 'drop', 'dragend'];
for (var i = 0; i < events.length; i++)
form.addEventListener(events[i], this);
this.form = form;
this.rules = rules;
this.message = null;
this.activeElement = null;
}
FormValidator.prototype = {
constructor: FormValidator,
handleEvent: function(event) {
switch (event.type) {
case 'input':
var validity = this.validateInput(event.target)
if (this.activeElement === event.target) {
if (validity.state)
this.hideMessage()
else
this.updateMessage(validity.error);
}
break;
case 'submit':
if (!this.validateInputs(this.getInputs()))
event.preventDefault();
break;
case 'blur':
this.hideMessage(event.target);
default:
var target = event.target;
var self = this;
setTimeout(function(){
self.validateInput(target);
}, 0);
}
},
createMessage: function() {
this.message = document.createElement('div');
this.message.className = 'validation-message';
this.message.addEventListener('mousedown', function(e) {
e.preventDefault();
});
},
showMessage: function(element, text) {
this.activeElement = element;
element.focus();
if (!this.message)
this.createMessage();
var rect =...