Learn Form Validation by Building a Calorie Counter - Step 32

Number inputs only allow the e to occur between two digits. To match any number, you can use the character class [0-9]. This will match any digit between 0 and 9.

Add this character class before and after e in your pattern.

function isInvalidInput(str) {
  const regex = /[0-9]e[0-9]/i;
}

Can someone explain what does this code do? I know it’s correct but I don’t know what does regex mean and why are there numbers and the letter e in it?

Your browser information:

User Agent is: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36

Challenge Information:

Learn Form Validation by Building a Calorie Counter - Step 32

and now In another step it’s telling to add a + and replace the [0-9] with \d, I’m so confused.

Didn’t look at these challenges so.

I would assume the “e” is for scientific notation (decimal exponential notation)

1e2 === 100; // true

\d is digites just as [0-9] is.

+ means one or more.

1 Like

ok I get that \d is digits from 0-9, 1e2 ===100 ( is it equal 100 because after the e there’s 2 so I add 2 zeros after the 1?), but I still don’t get what does (\d+e\d+/i) mean? There’s 2 \d seperated by an e which I guess it means a million? any number from0-9 + e another 0-9 which can max out at 9 999 999 999, is this correct? And the +/i I don’t know what that does.

The regex is used to validate the user input.

The HTML input element has built-in “validation” which only allows for numbers to be typed in, but it also allows for an “e” between two numbers (it actually allows an e at the start as well but never mind that) because that is a valid form of number notation.

We do however not want to allow such an input. So we match on one or more numbers followed by the character e followed by one or more numbers, using a case-insensitive search. If we match on the input we (later in the code) will reject it as an invalid input.

We are basically just augmenting the built-in validation with an extra check for “numbers e numbers” as an invalid input.

i is a flag used for case-insensitive search.

Oh ok so I wrote this function so when I accept an input from the user I can call this function and put the input in it and it checks if there’s an “e” in the input?

When I started html it was easier, I feel like I’m not fully understanding my code in Javascript even though I have taken a little bit of java. I feel like the course’s pace is a little fast. Is that normal at the start?

For example I just wrote this function code from the 2nd js lesson and I don’t really understand what it does

function addEntry() {
  const targetInputContainer = document.querySelector(`#${entryDropdown.value} .input-container`);
  const entryNumber = targetInputContainer.querySelectorAll('input[type="text"]').length;
  const HTMLString = `
  <label for="${entryDropdown.value}-${entryNumber}-name">Entry ${entryNumber} Name</label>
  <input type="text" id="${entryDropdown.value}-${entryNumber}-name" placeholder="Name" />
  <label for="${entryDropdown.value}-${entryNumber}-calories">Entry ${entryNumber} Calories</label>
  <input
    type="number"
    min="0"
    id="${entryDropdown.value}-${entryNumber}-calories"
    placeholder="Calories"
  />`;
  targetInputContainer.innerHTML += HTMLString;
}

Well, numbers followed by an e followed by numbers.

It is normal to be confused in the beginning, this isn’t easy to learn. The new curriculum is also still being updated and many of the challenge steps may need to have better explanations.

What specifically is confusing you in the code you posted?


If you look in the HTML you can see fieldset elements with ids. The ids match the value attribute on the option elements inside the select element.

<fieldset id="breakfast">
  <legend>Breakfast</legend>
  <div class="input-container"></div>
</fieldset>
<select id="entry-dropdown" name="options">
  <option value="breakfast" selected>Breakfast</option>
</select>

JS

const targetInputContainer = document.querySelector(`#${entryDropdown.value} .input-container`);

entryDropdown.value is the option value and its value will match one of the fieldset element ids. We can use that to select the correct child .input-container element using its parent id.

const entryNumber = targetInputContainer.querySelectorAll('input[type="text"]').length;

We then get all the input elements using querySelectorAll.

It returns a NodeList which is an array-like structure and just like a normal array it has a length property. We can use that to “count” the number of elements and we use that count in the template literal to give a number to each of the elements we add. Every time we add more elements the number increases.

We then construct the template literal, using the option value and count for the element attributes.

Then we add the new elements we created in the template literal to the .input-container element we selected on the first line in the function.

Oh ok so the targetInputContainer is the one that returns the value of the selected dropwdown option and entryNumber is supposed return how many entries I’ve made? But what does HTMLString do?

targetInputContainer is the element returned from querySelector using the dynamic selector passed to it.

The selector consists of the selected option value plus the class .input-container. If it was not dynamic and only using the breakfast element as an example it would look like this.

const targetInputContainer = document.querySelector(`#breakfast .input-container`);

Yes, entryNumber is the number of input[type="text"] elements. So it will increase/decrease as elements are added or removed.

HTMLString is the template literal that contains the constructed HTML. Using template literals you can write a string that contains HTML and add it to the DOM as HTML. It is used instead of having to use createElement and then adding values and attributes to the created elements.