Revisiting vanilla JavaScript after years of using frameworks
Tags: webdev, javascript, html, css
Published: 2019-06-05 22:47:50

# Vanilla JavaScript...so refreshing

I was recently assigned a small project to build the pricing tables for our web app. At first I thought nothing of it, but when my co-worker sent me the code for what to build off of, it struck me; I have to use vanilla JavaScript/HTML/CSS for this.

As a front end developer of 7 years I'll admit this is a little embarrassing. I write JavaScript every day, but it's mostly framework specific code like React. Yes, React is JavaScript, but this project consisted of DOM manipulation which you don't do a whole lot of in React. No problem though, let's get to it.

## Project Requirements

Like I mentioned, this project was to create the pricing page for our app. I was given some code that was a good start, I just needed to add a couple simple things:

- Update the styles/design
- A slider input that changed the prices, including a "Let's chat" for the top price

## Getting Reacquainted

The code I was given looked like this:

{% codesandbox 8z0kg %}

## Styling

Not a bad start! HTML/CSS isn't in the scope of this post so I'll just summarize the things I changed.

- Added CSS variables for theme colors and margin/padding spacing
- Restyled to match our style guide
- Ran the CSS through auto-prefixer for vendor prefixes
- Moved some things around
- Styled the slider input

## To the JavaScript!

Now I just needed to make the slider update the prices when it changes. The JavaScript for this is pretty basic; watch the slider `oninput` event, grab the corresponding HTML elements and change the `innerHTML`.

```javascript
let input = document.getElementById("followers"),
  priceLite = document.getElementById("ep_lite"),
  priceMod = document.getElementById("ep_mod"),
  followerCount = document.getElementById("follows");

input.oninput = function() {
  let value = this.value;
  priceLite.innerHTML = values[value].price.lite;
  priceMod.innerHTML = values[value].price.mod;
  followerCount.innerHTML = values[value].label;
};
input.oninput();
```

Next I went on to define the `values` array. At first, I just updated the number by itself which worked fine, but then I got to where I needed to display "Let's Chat" which didn't mix well with the `$` and `/mo` parts of the HTML. So I created another element that I would hide/show when necessary which looked something like this:

```html
<div class="price">...</div>
<div class="lets-chat hidden">Let's Chat!</div>
```

```css
.hidden {
  display: none;
}
```

```javascript
let input = document.getElementById("followers"),
...
   priceEls = document.getElementsByClassName("price"),
   chatEls = document.getElementsByClassName("lets-chat");

function checkPrice = (value) => {
  if (value === parseInt(input.max)) {
  // if value is max of input, hide prices and show let's chat
    Array.prototype.forEach.call(priceEls, (el) => {
      el.classList.add("hidden");
    });
    Array.prototype.forEach.call(chatEls, (el) => {
      el.classList.remove("hidden");
    });
  } else {
  // else hide let's chat and show prices
    Array.prototype.forEach.call(priceEls, (el) => {
      el.classList.remove("hidden");
    });
    Array.prototype.forEach.call(chatEls, (el) => {
      el.classList.add("hidden");
    });
  }
}
```

This did the job but was getting a little messy for my liking. It could probably be written more efficiently, but then...

💡

"I can create reusable components just like in React", I thought. This is a perfect time to use template literals (template strings).

So I moved the HTML to the JS and created two functions:

```javascript
const Price = (price) => {
  return `<p class="price">
    $<span>${price}</span><span class="price_time"> /mo</span>
  </p>`;
};

const LetsChat = () => {
  return `<p class="lets-chat">Let's chat!</p>`;
};
```

This probably looks familiar if you know React or any other framework really. They're basically functional components, just returning a string rather than JSX.

Now we can create the `values` array using these functions.

```javascript
let values = [
  { label: "< 100k", price: { lite: Price(10), mod: Price(18) } },
  { label: "< 500k", price: { lite: Price(18), mod: Price(29) } },
  { label: "< 1M", price: { lite: Price(25), mod: Price(59) } },
  { label: "1M+", price: { lite: LetsChat(), mod: LetsChat() } }
];
```

And here's the final result:

{% codesandbox 4nrv8 %}

## Final Thoughts

Even though small and simple, I really enjoyed working on this project. I think revisiting vanilla JavaScript is extremely important as a front end dev. It can be easy to get caught up in the framework magic and forget about what's under the hood.