Daniel Grimes Daniel Grimes - 5 days ago 5
Javascript Question

Why can't I establish two cleave.js formatted fields in the same js file?

I want to format both phone and credit card input using cleave.js (in rails). I've got the formatting working if I only declare one

new Cleave
object, but I get this error if I attempt to declare two:

Uncaught Error: [cleave.js] Please check the element


Here's the relevant parts of the JS file:



var Global = {};

Global.onLoad = function(){
Global.setupDatepickers(); //unrelated function
Global.setupCleavePhone();
Global.setupCleaveCreditCard();
};

$(document).on('turbolinks:load', function(){
Global.onLoad();
});

Global.setupCleavePhone = function() {
new Cleave('.phone-input', {
phone: true,
phoneRegionCode: 'US',
delimiter: '-'
});
}

Global.setupCleaveCreditCard = function() {
new Cleave('.card-input', {
delimiter: '-',
blocks: [4,4,4,4]
});
}


I've tried a few remixes of this including assigning the Cleave objects to variables and declaring them in the same function, but no dice. Here's a jsfiddle of multiple cleave objects being delared at once, and I can't see any meaningful differences between my code and theirs. The selector classes are properly applied in the view. Any thoughts why I can't seem to format two fields at once?

Answer

SOLVED:

As it turned out it needs the objects to exist in order to run new Cleave. If one of the elements doesn't exist on the page, the whole thing fails for some reason. I ended up going with wrapping each new Cleave, checking if an element with that class existed or not, for example:

if ($('.card-input').length) {
  new Cleave('.card-input', {
    delimiter: '-',
    blocks: [4,4,4,4]
  });
}

UPDATE:

Or even better, if you're like me and need to format more than one object of the same class on a page (which causes cleave to only format the first one with the code above) retrieve the array of objects and run cleave on each. It performs the same 'does it exist' check as well as formatting each object. For example:

for(let field of $('.zip_code').toArray()){
  new Cleave(field, {
    numericOnly: true,
    delimiter: ' ',
    blocks: [5,4]
  });
}
Comments