0

I have a html code where I want the text I type in an input textbox to be taken as input, saved into an object, and be matched as keyword when I type in a simulated textarea.

Example:

<tr>
  <td>KEYWORD:</td>
  <td><input type="text" name="key_word" value="" id="tm"></td>
</tr>

My text area where I type text:

<div class="container">
  <textarea id="myTextArea"></textarea>
  <div class="backdrop">
    <div class="colors">
    </div>
  </div>
</div>

Javascript code:

const color = 
{
  "connected ..":"green",
  "connected .....": "green", 
  "connection failure .....": "red"
};

let textArea = document.getElementById("myTextArea");
let colorsArea = document.querySelector(".colors");
let backdrop = document.querySelector(".backdrop");

// Event listeners.

textArea.addEventListener("input", function()
{
    colorsArea.innerHTML = applyColors(textArea.value);
});

textArea.addEventListener("scroll", function()
{
    backdrop.scrollTop = textArea.scrollTop;
});

function applyColors(text)
{
    let re = new RegExp(Object.keys(color).join("|"), "gi");

    return text.replace(re, function(m)
    {
        let c = color[m.toLowerCase()];
        return `<spam style="color:${c}">${m}</spam>`;
    });
}       

So, the scenario is like this: when I type the keyword in the input textbox, like "connected" for example, then this "connected" keyword should be passed as match condition to the above javascript. So whenever I type the keyword later in the textarea, that keyword should get the green color in the textarea.

This is the code where I want the textbox value to be stored, So I can get rid of hard coded data:

const color = 
{
  "connected ..":"green",
  "connected .....": "green", 
  "connection failure .....": "red"
};
Shidersz
  • 16,846
  • 2
  • 23
  • 48
  • That code sounds familiar to me... So, do you want to add match conditions into the color object (used for mapping) every time you input something into the input? If that is the case you will need an `add` button too. – Shidersz May 12 '19 at 18:43
  • how do i do it when i add keyword in textbox then it should pass as string to "connected ..":"green", as "textbox.value"."green" this is what i want to achieve so there is no need to hard code match condition in code itself just taking value (keyword) from user only –  May 12 '19 at 19:08

2 Answers2

0

I'd suggest you loop through the object keys and use contains or test method for regex and return the color from your object.

You can play around this:

const color =  {
  "connected":"green",
  "connection failure": "red"
};

const applyColors = (text) => {
  let c = "blue"; //default color
  Object.keys(color).map(function(key, index){
      if(text.contains(key)) {
        c = color[key];
      }
  });
  return `<span style="color:${c}">${text}</span>`;
}

console.log(applyColors("connected"))
Akinjiola Toni
  • 658
  • 7
  • 9
0

You can create an Add button to add new keywords into the map of keywords and colors. You will need to handle the click event on that new button, and put the logic to extend the "map" there. Something like this:

HTML:

<table>
  <tr>
    <td>Keyword:</td>
    <td>
      <input type="text" name="key_word" id="tm">
    </td>
    <td>
      <button type="button" id="addBtn">Add</button>
    </td>
  </tr>
</table>

Javascript:

// Logic to add new keyword:

let addButton = document.getElementById("addBtn");

addButton.addEventListener("click", function()
{
    let newKey = document.getElementById("tm").value;

    if (newKey.trim())
        colorMap[newKey] = "green";
});

In reference to previous answer I made about this question: How to change color of text in a textarea. I will also add a select with options to choice the color, resulting on the next code:

// Initialization.

const colorMap = {/* EMPTY */};
let textArea = document.getElementById("myTextArea");
let customArea = document.querySelector(".custom-area");
let backdrop = document.querySelector(".backdrop");

// Event listeners.

textArea.addEventListener("input", function()
{
    customArea.innerHTML = applyColors(textArea.value);
});

textArea.addEventListener("scroll", function()
{
    backdrop.scrollTop = textArea.scrollTop;
});

function applyColors(text)
{
    let re = new RegExp(Object.keys(colorMap).join("|"), "gi");

    return text.replace(re, function(m)
    {
        let c = colorMap[m.toLowerCase()];
        return `<spam style="color:${c}">${m}</spam>`;
    });
}

// Logic to add new keyword:

let addButton = document.getElementById("addBtn");

addButton.addEventListener("click", function()
{
    let newKey = document.getElementById("tm").value;
    let newColor = document.getElementById("colorSel").value;
    
    if (newKey.trim() && newColor)
    {
        colorMap[newKey] = newColor;
        textArea.dispatchEvent(new Event("input"));
    }
});
.backdrop, #myTextArea {
  font: 12px 'Open Sans', sans-serif;
  letter-spacing: 1px;
  width: 300px;
  height: 100px;
}

#myTextArea {
  margin: 0;
  position: absolute;
  border-radius: 0;
  background-color: transparent;
  color: transparent;
  caret-color: #555555;
  z-index: 2;
  resize: none;
}

.backdrop {
  position: absolute;
  z-index: 1;
  border: 2px solid transparent;
  overflow: auto;
  pointer-events: none;
}

.custom-area {
  white-space: pre-wrap;
  word-wrap: break-word;
}
<table>
  <tr>
    <td>Keyword:</td>
    <td>
      <input type="text" name="key_word" id="tm">
    </td>
    <td>Color:</td>
    <td>
      <select id="colorSel">
        <option value="green">Green</option>
        <option value="orange">Orange</option>
        <option value="red">Red</option>
      </select>
    </td>
    <td>
      <button type="button" id="addBtn">Add</button>
    </td>
  </tr>
</table>

<hr>

<div class="container">
  <div class="backdrop">
    <div class="custom-area">
        <!-- Cloned text with colors will go here -->
    </div>
  </div>
  <textarea id="myTextArea"></textarea>
</div>
Shidersz
  • 16,846
  • 2
  • 23
  • 48