Multicolor Text Highlighting in a Textarea or Text Input

Multicolor Text Highlighting in a Textarea or Text Input

No, you can't do this in a textarea or text input. Any CSS text-related property will affect the whole text within the the textarea/input. You'll need an editable element or document to achieve syntax highlighting. Example (works in all recent browsers; the last major browser not to support contenteditable was Firefox 2.0):

<code contenteditable="true">  <span style="color: blue">var</span> foo = <span style="color: green">"bar"</span>;</code>

How to change the highlight color of selected text in a textarea, using selection range?

I don't understand exactly what you want.

Did you want an answer like the code below?

https://codepen.io/jyh7a/pen/xxpLMZZ

HTML

<input type="text" id="text-box" size="20" value="Mozilla">
<button onclick="selectText()">Select text</button>

<hr/>

<textarea rows="6" cols="40">Lorem, ipsum dolor sit amet consectetur adipisicing elit. Porro maxime excepturi autem nostrum minus quae magni, esse optio ab, dolor ut iste earum sapiente molestiae nihil totam rem ipsam officia?</textarea>

<hr/>

<p>Lorem, ipsum dolor sit amet consectetur adipisicing elit. Porro maxime excepturi autem nostrum minus quae magni, esse optio ab, dolor ut iste earum sapiente molestiae nihil totam rem ipsam officia?</p>

CSS

::selection {
background-color: rgba(255,0,0,0.2);
}

JS

function selectText() {

const input = document.getElementById('text-box');
input.focus();
input.setSelectionRange(2, 5);

setTimeout(() => {
const textarea = document.querySelector('textarea');
textarea.focus();
textarea.setSelectionRange(0, 20);
}, 1000)


// // ERROR!
// // setSelectionRange function only use HTMLInputElements
// const p = document.querySelector('p');
// p.setSelectionRange(0, 20);
}

I searched for setSelectionRange

I made the above example by looking at the MDN official documentation.

(Link: https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/setSelectionRange )

Hope the above code was helpful to you.

Implementing highlighted textarea in angular

There are a few things you could do, all of them involve CSS (so you need a custom CSS file).

If you want to use the same color you could add this rule:

.text-input-highlight-container .text-highlight-tag {
color: some_color;
}

If you want to have a fixed color with different background colors:

.bg-blue {
color: some_color;
}

.bg-pink {
color: some_other_color;
}

If you want to be able to put different colors per background color:

.text-blue {
color: blue
}

.text-red {
color: red;
}

And then you change your code to add those text color classes:

tags: HighlightTag[] = [{
indices: { start: 8, end: 12 },
cssClass: 'bg-blue text-red',
data: { user: { id: 1 } }
}];

This only works with a few colors though because it appears to be superimposed on the original black text.

So in order to make this work with every kind of color you need to make the regular text transparent:

.text-input-highlight-container textarea {
color: transparent;
}

And in your code you apply the hightlight to all text but don't put any classes for regular text e.g.

tags: HighlightTag[] = [{
indices: { start: 0, end: 11 },
cssClass: '',
data: { user: { id: 1 } }
},
{
indices: { start: 8, end: 12 },
cssClass: 'bg-blue text-red',
data: { user: { id: 1 } }
}];

The first part will look like regular text and the latter will have a blue background with red text.

Hope this makes sense.

Update:

Be sure to add the indices of the non-highlighted text to the HighlightTag array as well, as shown here: https://stackblitz.com/edit/angular-ivy-my8her?file=src%2Fapp%2Fapp.component.ts (the css doesn't apply on Stackblitz though), so that it get wrapped in a span as well.

And if you have set the color to transparent you need to provide a default color for the text within the spans.

.text-input-highlight-container .text-highlight-tag {
color: black; //or any other color you want for the non-highlighted text
}

Then you can do

.bg-blue { color: lightblue !important; } //background-color for bg-blue is lightblue so I wouldn't set text color to lightblue though

With color set to white for .bg-blue it'll look like this:

Sample Image

Update 2:

I looked a little deeper at the HTML and you don't have to wrap the unhighlighted text in a span if you don't want to.
This should do the trick:

.text-input-highlight-container .text-input-element { //the textarea
color: transparent;
}
.text-input-highlight-container .text-highlight-element { //the superimposed text
color: black;
border-color: transparent; //otherwise you'll get a black border
}
.bg-blue {
color: white;
}

Applied to the demo page:

Sample Image

Change color of specific words in textarea

You can't change the colours of words in a <textarea>, but you can use the contenteditable attribute to make a <div>, <span>, or <p> look like a <textarea>.

To do this you can use a JavaScript plugin, but if you want to create a new one, the code below may help you.

For this purpose, you need to get any word in the text. Then check that if it's a SQL keyword.

// SQL keywordsvar keywords = ["SELECT","FROM","WHERE","LIKE","BETWEEN","NOT LIKE","FALSE","NULL","FROM","TRUE","NOT IN"];// Keyup event$("#editor").on("keyup", function(e){  // Space key pressed  if (e.keyCode == 32){    var newHTML = "";    // Loop through words    $(this).text().replace(/[\s]+/g, " ").trim().split(" ").forEach(function(val){      // If word is statement      if (keywords.indexOf(val.trim().toUpperCase()) > -1)        newHTML += "<span class='statement'>" + val + " </span>";      else        newHTML += "<span class='other'>" + val + " </span>";     });    $(this).html(newHTML);
// Set cursor postion to end of text var child = $(this).children(); var range = document.createRange(); var sel = window.getSelection(); range.setStart(child[child.length-1], 1); range.collapse(true); sel.removeAllRanges(); sel.addRange(range); this.focus(); }});
#editor {    width: 400px;    height: 100px;    padding: 10px;    background-color: #444;    color: white;    font-size: 14px;    font-family: monospace;}.statement {    color: orange;}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script><div id="editor" contenteditable="true"></div>

Is there a way to have different colored text inside a textarea?

I don't think this is possible with textarea. I think epascarello is trying to tell you that it is possible using a div with the attribute contenteditable="true".

Check out this similar question - Is it possible to have several different textcolors in one textarea?

You will need to style the div to look and feel like a textarea. Here's a basic mockup, you may need to add some Javascript to extend this.

<div id="objtext" contenteditable="true">
not orange
<span class="orange-text">
orange
</span>
not orange
</div>

#objtext {
-moz-appearance: textfield-multiline;
-webkit-appearance: textarea;
border: 1px solid gray;
overflow: auto;
padding: 4px;
width: 400px;
height: 200px;
font: medium -moz-fixed;
font: -webkit-small-control;
}

.orange-text {
color: orange;
}

::selection {
color:orange;
}

::-moz-selection {
color:orange;
}

https://jsfiddle.net/miainchambers/g07rcb5o/2/

Text value can be retrieved by using document.getElementById("objtext").textContent

Is it possible to have several different textcolors in one textarea?

You can't do this inside a <textarea>, not one that's editable. It sounds like you're after a WYSIWYG editor, most of which use a <iframe> to do this.

There are several JavaScript options for this, to name a few:

  • TinyMCE
  • CKEditor

Shiny: Highlight text input in a certain color

Sample Image

library(shiny)
library(tibble)

css <- "
mark {
padding: 0;
background-color: white;
color: red;
}
"

df = tibble(text = c("The quick brown fox", "jumps over", "the lazy dog"))

ui = fluidPage(

tags$head(
tags$style(HTML(css))
),

fluidRow(
column(
width = 12,
textInput("input", "Textinput"),
tableOutput("output")
)
)

)

server = function(input, output){

highligthed <- reactive({
if(input$input != ""){
gsub(paste0("(", input$input, ")"), "<mark>\\1</mark>", df[["text"]])
}else{
df[["text"]]
}
})

df_reactive = reactive({
tibble(text = highligthed())
})

output$output = renderTable({
df_reactive()["text"]
}, sanitize.text = function(x) x)

}

shinyApp(ui, server)

Edit

To filter the column, use this code:

  highligthed <- reactive({
x <- df[["text"]][str_detect(df[["text"]], input$input)]
if(input$input != ""){
gsub(paste0("(", input$input, ")"), "<mark>\\1</mark>", x)
}else{
x
}
})


Old answer (misunderstood the question)

Is it what you want?

Sample Image

library(shiny)
library(tibble)
library(dplyr)
library(stringr)

df = tibble(text = c("The quick brown fox", "jumps over", "the lazy dog"))

ui = fluidPage(

tags$head(
uiOutput("CSS")
),

fluidRow(
column(
width = 12,
textInput("input", "Textinput"),
tableOutput("output")
)
)

)

server = function(input, output){

detect <- reactive({
str_detect(df[["text"]], input$input)
})

df_reactive = reactive({
df %>% filter(detect())
})

output$output = renderTable({
df_reactive()["text"]
})

output$CSS = renderUI({
color <- ifelse(any(detect()), "red", "black")
css <- sprintf("#input {color: %s;}", color)
tags$style(HTML(css))
})

}

shinyApp(ui, server)

Removing blue highlighted text on focus

You can use user-select to avoid the selection of any text

input {  -webkit-user-select: none;  /* Chrome all / Safari all */  -moz-user-select: none;     /* Firefox all */  -ms-user-select: none;      /* IE 10+ */  user-select: none;          /* Likely future */      }
<input type="text">


Related Topics



Leave a reply



Submit