Using string's replaceAll function to convert emoticons into emojis
Tags: javascript, emoticons, emojis, fun
Published: 2021-10-26 16:00:44

For us, who are 8Xes and familiar with Yahoo Messenger, using emoticons is fun remembering. And even until today, we and some 10Xes still type them as well 😀. We really miss those days 🙁. Nowadays, people are with smartphones and emojis is the norm. But still, emojis are hard to type especially on desktop keyboards where typing emoticons is much easier. This let me to the thinking 'Can we use emojis in the form of emoticons?' 😀. And clearly, it's a 'yes' and in this article, I'll show you how as well as a clear detailed explanation 😀. Isn't that cool 😎. (Note: The text above use the converter I wrote 😉)

The motivation is to show you how to use string's `replaceAll` function to do the trick in its second form and... for fun, of course 😎.

## The web tool
You can even have fun even before understand the magic behind the tool by just using it to turn the emoticons into emojis :D. To do it, prepare directory and

### Create the UI
Create a html file with the following code:
```html
<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8" />
        <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no, viewport-fit=cover" />
        <meta name="apple-mobile-web-app-capable" content="yes" />
        <title>Emoticons to Emojis</title>
        <script src="regex.js"></script>
        <script src="run.js"></script>
    </head>
    <body>
        <h1>Convert the emoticons to emojis</h1>
        <div>
            <button onclick="handleClick()">Click to convert emoticons to emojis</button>
        </div>
        <div>
            <textarea id="input" rows="10" cols="80"></textarea>
        </div>
        <div>
            <textarea id="output" rows="20" cols="80" readonly></textarea>
        </div>
    </body>
</html>
```
and you have the UI

### Get the helper library
My script I write use a regex builder from [https://github.com/wyantb/js-regex](https://github.com/wyantb/js-regex) so grab the script file at [https://github.com/wyantb/js-regex/raw/master/regex.js](https://github.com/wyantb/js-regex/raw/master/regex.js) and put it into directory. Its name is `regex.js` as referenced by the html.

### Create the main script file
Create a `run.js` file and copy the following code to it
```javascript
let emoticons = {
    "(:": "🙃",
    ":)": "🙂",
    ":')": "🥲",
    ":))": "😂",
    "=))": "🤣",
    ";)": "😉",
    ":D": "😀",
    ":P": "😋",
    "B)": "😎",
    ":*": "😗",
    ":(": "🙁",
    ":'(": "😥",
    ":((": "😭",
    ":o": "😮",
    ">:(": "😠",
    ">:-(": "😡",
}

const pattern = (function () {
    let r = regex.create().either();
    let cmp = function (a, b) {
        let d = a.length - b.length;

        if (d)
            return -d;

        if (a < b)
            return -1;

        if (a > b)
            return 1;

        return 0;
    }

    for (let key of Object.keys(emoticons).sort(cmp))
        r.literals(key)

    return new RegExp(r.endEither().peek(), "gu");
})();

function getEmoji(emoticon) {
    if (emoticon in emoticons)
        return emoticons[emoticon];

    return "";
}

function cvE2E(str) {
    return str.replaceAll(pattern, getEmoji)
}

function handleClick() {
    document.getElementById("output").value = cvE2E(document.getElementById("input").value);
}
```
Open the web page and use it now. Have fun then.

## Understand how it works
In order to convert emoticons to emojis, you have to map and emoticon to an emoji. The following code defines the mapping

```javascript
let emoticons = {
    "(:": "🙃",
    ":)": "🙂",
    ":')": "🥲",
    ":))": "😂",
    "=))": "🤣",
    ";)": "😉",
    ":D": "😀",
    ":P": "😋",
    "B)": "😎",
    ":*": "😗",
    ":(": "🙁",
    ":'(": "😥",
    ":((": "😭",
    ":o": "😮",
    ">:(": "😠",
    ">:-(": "😡",
}
```

As it is an object, it maps emoticons to emojis and you can extend it as well. For this article, I'll use some of them for the demonstration only, try to add more 😉

The key point of converting emoticons to emojis is to use string's `replaceAll` function in junction with a regular expression that matches and extracts emoticons from the string. It is done by using the helper library, with minor trick here. The idea here is to create a regular expression that matches either of emoticons, hence

```javascript
for (let key of Object.keys(emoticons).sort(cmp))
        r.literals(key)
```

in the code. But just iterating through the object fetching its key to add to the pattern isn't enough. There is a catch here. You must match the longer string first, or else, the result is wrong. For example the emoticon `:))` must be matched before `:)`. That is why you have to sort the keys array using a comparer `cmp` as shown in the code before creating the pattern.

The final piece is the string's `replaceAll` function in its second form: `replaceAll(pattern, replacementAsAFunction)`. As many of us use `replaceAll(pattern, replacement)` with `replacement` as a string in most of the cases but here, it would require a function the get the corresponding emoji for the matched emoticon. So `replacementAsFunction` would take a matched emoticon and return the corresponding emoji. It is `getEmoji` function in the code and `cvE2E` is the converting function. The rest can be infered easily.

I hope you understand how the code works as well as knowing the second form of `replaceAll` function in case you haven't 😉. Have fun using the tool and adding emoticons then 😉.

PS: if you added more emoticons, share so everybody can use it^^