Let's create a dictionary with vanilla javascript

Let's create a dictionary with vanilla javascript

Hi, welcome back. Last night I was making a video for my Javascript playlist and it was the last video of the playlist where I taught how to make a dictionary using vanilla javascript.

Creating your own database for storing all the words and their meanings can be quite a difficult task. The best way which I found was to use any dictionary API available in the market.

I tried searching a lot and found one API which a developer has made available for free.

https://dictionaryapi.dev/

Now, that we have the API, we'll test this API first and then we'll implement this API in our code.

BTW, here is the final version of the project.

I've hosted the app on Vercel and the platform is super easy to deploy your projects for free and it also comes with CI/CD which makes updating your application super easy and fast.

Let's start

Open your browser and go to this link. This is the homepage of the API we are going to use.

Copy the link provided or use the below link.

https://api.dictionaryapi.dev/api/v2/entries/<language_code>/<word>

Change the language_code to the language of your choice (See the list of supported languages in the docs).

https://api.dictionaryapi.dev/api/v2/entries/en/<word>

# I have changed it to en for English

Replace <word> with the word whose meaning you want to find.

https://api.dictionaryapi.dev/api/v2/entries/en/programmer

# this is how the API has to be used

Once you'll hit this URL in your browser, you'll get the JOSN response something like this.

[
  {
    "word": "programmer",
    "phonetics": [
      {
        "text": "/ˈproʊˌɡræmər/",
        "audio": "https://lex-audio.useremarkable.com/mp3/programmer_us_1.mp3",
      }
    ],
    "meanings": [
      {
        "partOfSpeech": "noun",
        "definitions": [
          {
            "definition": "A person who writes computer programs.",
            "example": "computer programmers and analysts"
          }
        ]
      }
    ]
  }
]

From the response, we can easily extract the required data and populate in our HTML elements.

Making request using fetch()

When we try to make any request to any endpoint, fetch() returns a promise. To handle the promise, either we can use .then().catch() or we can use async-await.

Here, I've used async await.

Below is the code for making the request.

// I've made the function async
const fetchData = async (word) => {

  // make a req to the api
  const result = await fetch(
    `https://api.dictionaryapi.dev/api/v2/entries/en/${word}`
  );

  if (!result.ok) {
    alert("No definition found");
    return;
  }

  const data = await result.json();

};

Here is the HTML code

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Dictionary App</title>
    <link rel="stylesheet" href="style.css" />
  </head>
  <body>
    <div class="container">
      <h1 class="h1">Dictionary App</h1>
      <div class="input">
        <input
          onkeypress="handle(event)"
          type="text"
          class="search-field"
          placeholder="Type and press enter"
        />
      </div>
      <div class="result">
        <h1 class="word"></h1>
        <p class="phonetics"></p>
        <audio
          src=""
          controls
        ></audio>
        <p class="wordmeaning"></p>
        <p class="word-definition"></p>
        <p class="wordmeaning"></p>
        <div class="synonyms"></div>
      </div>
    </div>
    <script src="./app.js"></script>
  </body>
</html>

We have some text elements and a search field. For the styling part, you can use your own custom CSS or you can use the CSS code provided below.

CSS

* {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

::-webkit-scrollbar {
  width: 10px;
}

::-webkit-scrollbar-track {
  background: #f1a576;
}

::-webkit-scrollbar-thumb {
  background: #e47632;
}

.container {
  display: flex;
  width: 100%;
  height: 100vh;
  box-sizing: border-box;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  background-color: #ffc5a1;
}

.h1 {
  font-weight: 300;
  margin-bottom: 15px;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
}

.search-field {
  padding: 10px;
  width: 500px;
  font-size: 20px;
  color: #1e1e1e;
  outline: none;
  border-radius: 5px;
  border: 1px solid #1e1e1e;
}

.result {
  display: none;
  margin-top: 20px;
  width: 500px;
  height: 500px;
  border-radius: 5px;
  background-color: #fff;
  padding: 30px;
  overflow-y: scroll;
  border-left: 5px solid #e66a1e;
}

.result > h1 {
  font-size: 40px;
  font-weight: 300;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
  display: inline;
}

.wordmeaning {
  display: inline-block;
  font-size: 24px;
  margin-bottom: 20px;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
}

.phonetics {
  display: inline-block;
  background-color: #ffc5a1;
  padding: 5px 10px;
  border-radius: 50px;
  font-weight: 600;
  margin-bottom: 20px;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
}

.result > audio {
  width: 100%;
  outline: none;
  margin-bottom: 20px;
}

.word-definition {
  font-size: 28px;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
  font-weight: 500;
  margin-bottom: 20px;
}

.synonyms {
  display: flex;
  font-size: 22px;
  flex-direction: row;
  flex-wrap: wrap;
}

.pills {
  margin-right: 10px;
  padding: 5px 20px;
  margin-bottom: 10px;
  border-radius: 5px;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Oxygen,
    Ubuntu, Cantarell, "Open Sans", "Helvetica Neue", sans-serif;
  background-color: #ffc5a1;
}

/* your media query here */
@media only screen and (max-width: 500px) {
  .container {
    padding: 20px;
  }
  .search-field,
  .result {
    width: 100%;
  }
}

I've tried to make the app responsive for mobile as well.

Now the Javascript

const resultDiv = document.querySelector(".result");
const wordEle = document.querySelector(".word");
const phonetics = document.querySelector(".phonetics");
const audio = document.querySelector("audio");
const wordMeaning = document.querySelector(".word-definition");
const synonyms = document.querySelector(".synonyms");

// function to handle all the word
const handle = async (e) => {
  if (e.keyCode === 13) {
    const word = e.target.value;
    // make a req to the api
    const result = await fetch(
      `https://api.dictionaryapi.dev/api/v2/entries/en/${word}`
    );
    if (!result.ok) {
      alert("No definition found");
      return;
    }
    const data = await result.json();
    resultDiv.style.display = "block";
    wordEle.innerText = data[0].word;
    phonetics.innerText = data[0].phonetics[0].text;
    audio.src = data[0].phonetics[0].audio;
    wordMeaning.innerText = data[0].meanings[0].definitions[0].definition;
    const synonymsArray = data[0].meanings[0].definitions[0].synonyms;
    if (synonymsArray) {
      let synonymsData = "";
      for (let i = 0; i < synonymsArray.length; i++) {
        synonymsData += `<p class="pills">${synonymsArray[i]}</p>`;
      }
      synonyms.innerHTML = synonymsData;
    } else {
      synonyms.innerHTML = '<p class="pills">No synonyms available</p>';
    }
  }
};

Now, push the code to Github and from there you can connect your Github to Vercel and you can deploy your app in one click.

Well, this was all for today's post and if you found it helpful, please leave a like & comment.

Thanks for your time and I'll meet you in my next post. Take care and happy coding🙂!

Did you find this article valuable?

Support Pratik Sah by becoming a sponsor. Any amount is appreciated!