0

I want to highlight certain text background with some color with case insensitive. I tried the code below but it's not working. It only highlights when the keyword is in lowercase.

 private static CharSequence highlightText(String search, String originalText) {
    if (search != null && !search.equalsIgnoreCase("")) {
        String normalizedText = Normalizer.normalize(originalText, Normalizer.Form.NFD).replaceAll("\\p{InCombiningDiacriticalMarks}+", "").toLowerCase().;
        int start = normalizedText.indexOf(search);
        if (start < 0) {
            return originalText;
        } else {
            Spannable highlighted = new SpannableString(originalText);
            while (start >= 0) {
                int spanStart = Math.min(start, originalText.length());
                int spanEnd = Math.min(start + search.length(), originalText.length());
                highlighted.setSpan(new BackgroundColorSpan(Color.YELLOW), spanStart, spanEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                start = normalizedText.indexOf(search, spanEnd);
            }
            return highlighted;
        }
    }
    return originalText;
}

For example I have a original text = "I Love Stackoverflow" and the keyword is "i love". How can I highlight the text background of "i love" without changing it to lower case and maintain the case.

enter image description here

Thank you.

Mei Yi
  • 341
  • 3
  • 14

3 Answers3

4

I got the answer from here: Android: Coloring part of a string using TextView.setText()?

String notes = "aaa AAA xAaax abc aaA xxx";
SpannableStringBuilder sb = new SpannableStringBuilder(notes);
Pattern p = Pattern.compile("aaa", Pattern.CASE_INSENSITIVE);
Matcher m = p.matcher(notes);
while (m.find()){
//String word = m.group();
//String word1 = notes.substring(m.start(), m.end());

sb.setSpan(new BackgroundColorSpan(Color.YELLOW), m.start(), m.end(), Spannable.SPAN_INCLUSIVE_INCLUSIVE);
}
editText.setText(sb);
Raghav Satyadev
  • 728
  • 2
  • 11
  • 38
Mei Yi
  • 341
  • 3
  • 14
0

As an update Mei Yi's answer:

If you set a layout attribute on the TextView such as android:textAllCaps="true" it may overwrite the Spannable string used to set the highlight and look like it isn't working. That is easy to work around; just set the layout attributes programmatically.

Ex. textView.setText(text.toUpperCase()) instead of android:textAllCaps="true"

Stephen Rauch
  • 47,830
  • 31
  • 106
  • 135
Sampson
  • 662
  • 6
  • 17
0

This will solve your issue

String text = "I Love StackOverflow";
String hilyt = "i love";

 //to avoid issues ahead make sure your
// to be highlighted exists in de text
if( !(text.toLowerCase().contains(hilyt.toLowerCase())) )
return;

int x = text.toLowerCase().indexOf(hilyt.toLowerCase());
int y = x + hilyt.length();

Spannable span = new SpannableString(text);        
span.setSpan(new BackgroundColorSpan(Color.YELLOW), x, y, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

yourTextView.setText(span);

The secret is changing all cases of both strings to lower case while trying to get de position of our text to be highlighted. I hope it will help someone.

Unheilig
  • 16,196
  • 193
  • 68
  • 98
Ray
  • 11
  • 2