I am trying to create a form validation, as a modal, using a tutorial on freecodecamp to help with the javaScript side (this is for an assignment I currently have) however, I cannot figure out what the issue is as all id names exist on my HTML doc so not sure where I have gone wrong. What I want to happen is, if nothing is entered in the input field an error message should appear along with an error icon and a success icon if something is entered. It works fine for all input fields up until Card Number and I do not understand why it is catching an error at this input field, if someone can please help me understand where I'mg going wrong I'd be very grateful. The full error on my console is as follows, I have looked at the lines but am completely stumped:
Uncaught TypeError: Cannot read properties of null (reading 'value') at validation (modal.js:79:12) at HTMLFormElement. (modal.js:69:5)
HTML CODE IS:
<!-- Payment Section -->
<div class="pay-section">
<div class="row" id="p-btn-row">
<div class="col-12" id="p-btn-col">
<div class="orderNowButton">
<button id="myBtn" type="button" class="btn-outline-success">Proceed to Checkout</button>
</div>
<!-- The Modal -->
<div id="myModal" class="modal" data-backdrop="static">
<!-- Modal content -->
<div class="modal-overlay">
<script src="modal.js" async></script>
<!-- Payment Form section-->
<form id="payment-form" name="paymentForm" >
<div class="container-fluid" id="payment-section" method="post" required>
<span class="close" id="close-btn">×</span>
<br>
<!--Delivery/Collection Section-->
<div class="row-inline delivery-collection-section">
<label id="select">Please select: </label>
<input type="radio" name="optradio" onclick="deliveryAddressFunction()">
<label class="radio-label"> Collection</label>
<input type="radio" name="optradio" id="delivery" onclick="deliveryAddressFunction()">
<label class="radio-label"> Delivery</label>
</div>
<div class="row-inline" id="delivery-address" style="display: none">
<h6 id= "enterdetails"> Fill in required fields:</h6>
<div class="col" id="firstname">
<label id='firstname-label'>First Name: </label>
<input type="text" name="fname" id="firstname-input" maxlength="45">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="surname">
<label id="surname-label">Surname: </label>
<input type="text" name="sname"id="surname-input" maxlength="45">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col address">
<label id="houseFlat-label">House/Flat Number: </label>
<input type="text" name="HouseFlatNo" id="houseFlat-input" maxlength="10">
<i class="fas fa-exclamation-circle failure-icon "></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col address">
<label id="streetName-label">Street Name: </label>
<input type="text" name="streetName" id="street-input" maxlength="50">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col address">
<label id="town-label">Town: </label>
<input type="text" name="town" id="town-input" maxlength="50">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="postcode">
<label id="postcode-label">Postcode: </label>
<input type="text" name="postcode" id="postcode-input">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="tel">
<label id="contactNo-label">Contact Number: </label>
<input type="tel" name="contactNo" id="tel-input" maxlength="11">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="email">
<label id="email-label">Email: </label>
<input type="email" name="email" id="email-input" placeholder="example@gmail.com" maxlength="50">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
</div>
<div class="row" >
<div class="col-6" id="paymentdetails">
<h3><b>Payment</b></h3>
<label><b> Accepted Cards</b></label>
</div>
<div class="row-inline">
<span> <i class="fa-brands fa-cc-visa fa-2x" style="color: #C7280C"></i> </span>
<span> <i class="fa-brands fa-cc-mastercard fa-2x" style="color: #EEA130"> </i></span>
<span> <i class="fa-solid fa-credit-card fa-2x" style="color: #AC8E05"></i> </span>
<span> <i class="fa-brands fa-cc-amex fa-2x" style="color: #318B8B"></i> </span>
<div class="col" id="nameoncard">
<label id="nameoncard-label">Name on Card:</label>
<input type="text" name="nameoncard" id="nameoncard-input" placeholder="As it appears on your card"maxlength="22">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="cardnumber">
<label id="cardnumber-label">Card Number:</label>
<input type="text" maxlength="16" name="cardnumber" placeholder="16 digit card number" id="cardnumber-input">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="expdate">
<label id="expdate-label">Expiry Date:</label>
<input type="date" name="expdate" id="expdate-input">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="CVV">
<label id="CVV-label">CVV:</label>
<input type="text" name="cvv" placeholder="last 3 digits on back of card" id="CVV-input" maxlength="3">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div class="col" id="billing-post">
<label id="billing-post-label">Billing Postcode:</label>
<input type="text" name="billingPost" id="billing-post-input" placeholder="registered card address" maxlength="10">
<i class="fas fa-exclamation-circle failure-icon"></i>
<i class="far fa-check-circle success-icon"></i>
<div class="error"></div>
</div>
<div id="P-button">
<button type="submit" id="purchase-btn" >Complete Purchase</button>
</div>
</div>
</div>
</div>
</form>
<br>
</div>
</div>
</div>
</div>
</div>
JavaScript is:
//MODAL SECTION
// Get the modal
var modal = document.getElementById("myModal");
// Get the <span> element that closes the modal
var span = document.getElementById("close-btn");
// Get the button that opens the modal
var btn = document.getElementById("myBtn");
// When the user clicks on the button, open the modal
btn.onclick = function () {
modal.style.display = "block";
}
// When the user clicks on <span> (x), close the modal
span.onclick = function() {
modal.style.display = "none";
}
// When the user clicks anywhere outside of the modal, close it
window.onclick = function (event) {
if (event.target === modal) {
modal.style.display = "none";
}
}
//If delivery button is clicked the fields for address input become visible
function deliveryAddressFunction() {
if (document.getElementById('delivery').checked) {
document.getElementById('delivery-address').style.display = 'grid';
}
else{
document.getElementById('delivery-address').style.display = 'none';
}
}
//Validate form
let id = (id) => document.getElementById(id);
let classes = (classes) => document.getElementsByClassName(classes);
let fname = id("firstname-input"), sname = id("surname-input"), houseFlat =
id("houseFlat-input"), street = id("street-input"),town = id("town-input"), postcode = id("postcode-input"), tel = id("tel-input"), email = id("email-input"),
nameOnCard = id("nameoncard-input" ), cardNo = id("cardnumber-input"), expDate =
id("expdate-input"), cvv = id("CVV-input"),
billingPost = id("billing-post-input"), form = id("payment-form"),
errorMsg = classes("error"), successIcon = classes("success-icon"), failureIcon =
classes("failure-icon");
// continue event listener for all input fields.
form.addEventListener("submit", (e) => {
e.preventDefault();
deliveryAddressFunction();
validation(fname, 0, "First name cannot be blank");
validation(sname, 1, "Surname cannot be blank");
validation(houseFlat, 2, "Please enter House/Flat number");
validation(street, 3, "Please enter street name");
validation(town, 4, "Please enter town");
validation(postcode, 5, "Please enter postcode");
validation(tel, 6, "Please enter contact number");
validation(email, 7, "Please enter your email address");
validation(nameOnCard, 8, "Please your name as it appears on your card");
validation(cardNo, 9, "Please enter 14 digit card number");
validation(expDate, 10, "Please enter expiery date");
validation(cvv, 11, "Please enter 3 digit CVV number");
validation(billingPost, 12, "Please enter the postcode registered to your card");
});
let validation = (id, serial, message) => {
if (id.value.trim() === ""){
errorMsg[serial].innerHTML = message;
id.style.border = "2px solid red";
//icons
failureIcon[serial].style.opacity = "1";
successIcon[serial].style.opacity = "0";
}
else {
errorMsg[serial].innerHTML = "";
id.style.border = "2px solid green";
//icons
failureIcon[serial].style.opacity = "0";
successIcon[serial].style.opacity = "1";
}
}