JSFiddle - React, Tailwind, and code Playground
by Sergey Aleshin
HTML
<input type="text" id="card" placeholder="**** **** **** ****">
CSS
input {
text-align: left;
}
JavaScript
var caretpos = {
start: 0,
end: 0
};
var currentCaretPos = 0;
const isDeleteMod = () => ( caretpos.end < caretpos.start );
document.getElementById("card").onkeydown = (e) => {
caretpos.start = e.currentTarget.selectionStart;
}
document.getElementById("card").onkeyup = (e) => {
if (!e.currentTarget.value.replace(/\s*/g, '').length) return;
/* if (!e.currentTarget.value.replace(/\sg, '').match(/^[0-9]*$/g)) {
e.currentTarget.value = e.currentTarget.value.replace(/[^0-9]+/g, '')
} */
caretpos.end = e.currentTarget.selectionEnd;
currentCaretPos = caretpos.end;
let spacesIndex = [];
for (let i = 0, pos = 0; i < e.currentTarget.value.replace(/\s*/g, '').length; i++, pos ++) {
if (pos >= 4) {
pos = 0;
spacesIndex.push(i);
}
}
let j = 0,
outStringArr = [];
spacesIndex.map(i => {
outStringArr.push(e.currentTarget.value.replace(/\s*/g, '').slice(j, i));
j = i;
});
e.currentTarget.value = outStringArr.join(' ') + (outStringArr.join(' ').length > 0 ? ' ' : '') + e.currentTarget.value.replace(/\s*/g, '').slice(
outStringArr.join('').length, e.currentTarget.value.replace(/\s*/g, '').length
);
if (isDeleteMod() || currentCaretPos < e.currentTarget.value.replace(/\s*/g, '').length) {
e.currentTarget.selectionStart = currentCaretPos;
e.currentTarget.selectionEnd = currentCaretPos;
}
/* console.log(e.currentTarget.value.replace(/\sg, '')) */
};