-1

Not an expert on bind functions. I created the snippet below to demonstrate what I'm trying to do.

I want to fire an event every time the 1st character of an input field is entered, but only the first character. I want it to run even if the user clears the input and starts over.

$("#userCardNumber") If I use .one("keyup", function() then it only runs once and if the user clears the field, hits backspace, or otherwise types over the 1st character it doesn't run again (as in my understanding it has been unbound/unbind)

$("#userCardNumber2") I can quasi-accomplish my intent by using .on("keyup", function() adding an if (element.length === 1) { } inside that function, but this seems terribly inefficient as it runs on every keyup and since this is a card number field that's 14-15 extra times it runs unnecessarily.

Trying to learn the most efficient way to do things, so curious how I can achieve the desired outcome without burning the extra keyups computations like I do in $("#userCardNumber2")?

(function($) {
  // On ready functions
  $(function() {

    $("#userCardNumber").one("keyup", function() {
      var el = $(this);
      cardType = el.val();
      if (cardType = 3) {
        console.log("AmEx");
      } else if (cardType = 4) {
        console.log("Visa");
      } else if (cardType = 5) {
        console.log("Mastercard");
      } else if (cardType = 6) {
        console.log("Discover");
      } else {
        console.log("something else");
      }
      console.log("Ran function")
    });

    $("#userCardNumber2").on("keyup", function() {
      var el = $(this);
      cardType = el.val();
      if (cardType.length === 1) {
        if (cardType = 3) {
          console.log("AmEx");
        } else if (cardType = 4) {
          console.log("Visa");
        } else if (cardType = 5) {
          console.log("Mastercard");
        } else if (cardType = 6) {
          console.log("Discover");
        } else {
          console.log("something else");
        }
      }
      console.log("Ran function")
    });

  });

}(jQuery));
div {
  margin-top: 20px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div>
  <input id="userCardNumber" type="text">
</div>

<div>
  <input id="userCardNumber2" type="text">
</div>
Parker
  • 225
  • 3
  • 11

3 Answers3

0

There are some error in your JS. In the if condition instead of "==" you have used "=". Apart from that I used a different logic to solve the problem. The code as below.

(function($) {
  // On ready functions
  $(function() {
    var flag1 = false;
    var flag2 = false;
     $("#userCardNumber").on("keydown", function() {
       if($("#userCardNumber").val().length < 1){
        flag1 = true;
      }
     });
    $("#userCardNumber2").on("keydown", function() {
       if($("#userCardNumber2").val().length < 1){
        flag2 = true;
      }
     });

    $("#userCardNumber").on("keyup", function() {
      if(flag1 === false){
        return;
      }
      flag1 = false;
      var el = $(this);
      cardType = el.val();
      if (cardType == 3) {
        console.log("AmEx");
      } else if (cardType == 4) {
        console.log("Visa");
      } else if (cardType == 5) {
        console.log("Mastercard");
      } else if (cardType == 6) {
        console.log("Discover");
      } else {
        console.log("something else");
      }
      console.log("Ran function")
    });

    $("#userCardNumber2").on("keyup", function() {
      if(flag2 === false){
        return;
      }
      flag2 = false;
      var el = $(this);
      cardType = el.val();
      if (cardType.length === 1) {
        if (cardType == 3) {
          console.log("AmEx");
        } else if (cardType == 4) {
          console.log("Visa");
        } else if (cardType == 5) {
          console.log("Mastercard");
        } else if (cardType == 6) {
          console.log("Discover");
        } else {
          console.log("something else");
        }
      }
      console.log("Ran function")
    });

  });

}(jQuery));
Aniruddha
  • 55
  • 2
  • 10
0

Onkeyup just check for selectionStart.

(function($) {
  // On ready functions
  $(function() {

    $("#userCardNumber2").on("keyup", function(e) {
      var el = $(this);
      cardType = parseInt(el.val());
      if (this.selectionStart == 1) {
        if (cardType == 3) {
          console.log("AmEx");
        } else if (cardType == 4) {
          console.log("Visa");
        } else if (cardType == 5) {
          console.log("Mastercard");
        } else if (cardType == 6) {
          console.log("Discover");
        } else {
          console.log("something else");
        }
      }
    });

  });

}(jQuery));
div {
  margin-top: 20px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

<div>
  <input id="userCardNumber2" type="text">
</div>

Note: Use Compare operator(==) instead of Assignment operator(=)

4b0
  • 21,981
  • 30
  • 95
  • 142
-1

It'd probably be more efficient to use regex and only validate on "blur" (when the user's focus moves away from the input). Try something like this:

(function($) {
  // On ready functions
  $(function() {

    $("#userCardNumber,#userCardNumber2").on("blur", function() {
      var number = $(this).val();
      var ccType = getCardType(number);
      console.log(ccType);
      // Implement whatever other code you want to use ccType for
    });
    
    function getCardType(number) {
      // Visa Electron
      re = new RegExp("^(4026|417500|4508|4844|491(3|7))");
      if (number.match(re) != null)
          return "Visa Electron";
          
      // visa
      var re = new RegExp("^4");
      if (number.match(re) != null)
          return "Visa";

      // Mastercard 
      // Updated for Mastercard 2017 BINs expansion
       if (/^(5[1-5][0-9]{14}|2(22[1-9][0-9]{12}|2[3-9][0-9]{13}|[3-6][0-9]{14}|7[0-1][0-9]{13}|720[0-9]{12}))$/.test(number)) 
          return "Mastercard";

      // AMEX
      re = new RegExp("^3[47]");
      if (number.match(re) != null)
          return "AMEX";

      // Discover
      re = new RegExp("^(6011|622(12[6-9]|1[3-9][0-9]|[2-8][0-9]{2}|9[0-1][0-9]|92[0-5]|64[4-9])|65)");
      if (number.match(re) != null)
          return "Discover";

      // Diners
      re = new RegExp("^36");
      if (number.match(re) != null)
          return "Diners";

      // Diners - Carte Blanche
      re = new RegExp("^30[0-5]");
      if (number.match(re) != null)
          return "Diners - Carte Blanche";

      // JCB
      re = new RegExp("^35(2[89]|[3-8][0-9])");
      if (number.match(re) != null)
          return "JCB";


      return "";
  }

  });

}(jQuery));
div {
  margin-top: 20px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div>
  <input id="userCardNumber" type="text">
</div>

<div>
  <input id="userCardNumber2" type="text">
</div>
RCB
  • 377
  • 1
  • 6