Android Search Highlight Full Word

110 Views Asked by At

String fullText = "Our Honorable Prime Minister";

String searchText = "onor";

I can highlight "onor" text well. [by using bottom codes]

But I want to highlight full "Honorable" text when my search string is "onor".

My code is:

public static void setSearchText(TextView textView, String fullText, String searchText) {
    // highlight search text
    if (null != searchText && !searchText.isEmpty()) {
        int startPos = fullText.indexOf(searchText);
        int endPos = startPos + searchText.length();
        if (startPos != -1) {

            int ofe = fullText.indexOf(searchText, 0);
            Spannable WordtoSpan = new SpannableString(fullText);

            for (int ofs = 0; ofs < fullText.length() && ofe != -1; ofs = ofe + 1) {
                ofe = fullText.indexOf(searchText, ofs);
                if (ofe == -1)
                    break;
                else {
                    ColorStateList redColor = new ColorStateList(new int[][]{new int[]{}}, new int[]{Color.RED});
                    TextAppearanceSpan highlightSpan = new TextAppearanceSpan(null, Typeface.BOLD, -1, redColor, null);
                    WordtoSpan.setSpan(highlightSpan, ofe, ofe + searchText.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                    WordtoSpan.setSpan(new BackgroundColorSpan(0xFFFFFF00), ofe, ofe + searchText.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                    WordtoSpan.setSpan(new RelativeSizeSpan(1.5f), ofe, ofe + searchText.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                    textView.setText(WordtoSpan, TextView.BufferType.SPANNABLE);
                }
            }
        } else {
            textView.setText(fullText);
        }

    } else {
        textView.setText(fullText);
    }
}
1

There are 1 best solutions below

0
On

Once you've found a match for your search string in the full text, you need to expand that match outwards to the word boundaries (spaces).

This is one way to do it:

// For single Item search

private static void setSearchText(TextView textView, final String fullText, final String searchText) {
  // highlight search text
  if (null != searchText && !searchText.isEmpty()) {
    int startPos = fullText.indexOf(searchText);
    int endPos = startPos + searchText.length();

    if (startPos != -1) {
      // Found a match to the partial text -- now search outward to
      // the word boundaries
      final char WORD_BOUNDARY = ' ';
      final char WORD_BOUNDARY1 = '\n';

      int wordStart = startPos;
                    while (wordStart >= 0 && fullText.charAt(wordStart) != WORD_BOUNDARY && fullText.charAt(wordStart) != WORD_BOUNDARY1) {
                        --wordStart;
                    }
                    wordStart = wordStart + 1;

                    int wordEnd = endPos;
                    while (wordEnd < fullText.length() && fullText.charAt(wordEnd) != WORD_BOUNDARY && fullText.charAt(wordEnd) != WORD_BOUNDARY1) {
                        ++wordEnd;
                    }

      // Now highlight based on the word boundaries
      ColorStateList redColor = new ColorStateList(new int[][]{new int[]{}}, new int[]{Color.RED});
      TextAppearanceSpan highlightSpan = new TextAppearanceSpan(null, Typeface.BOLD, -1, redColor, null);

      Spannable wordtoSpan = new SpannableString(fullText);

      wordtoSpan.setSpan(highlightSpan, wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
      wordtoSpan.setSpan(new BackgroundColorSpan(0xFFFFFF00), wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
      wordtoSpan.setSpan(new RelativeSizeSpan(1.5f), wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

      textView.setText(wordtoSpan, TextView.BufferType.SPANNABLE);
    } else {
      textView.setText(fullText);
    }
  } else {
    textView.setText(fullText);
  }
}

// For Multiple String Search Use following Codes:

public static void setSearchText(TextView textView, final String fullText, final String searchText) {
    // highlight search text
    if (null != searchText && !searchText.isEmpty()) {
        int startPos = fullText.indexOf(searchText, 0);
        int endPos = startPos + searchText.length();

        if (startPos != -1) {
            // Found a match to the partial text -- now search outward to
            // the word boundaries

            Spannable wordtoSpan = new SpannableString(fullText);

            for (int i = 0; i < fullText.length() && startPos != -1; i = startPos + 1) {
                startPos = fullText.indexOf(searchText, i);
                endPos = startPos + searchText.length();
                if (startPos == -1)
                    break;
                else {
                    final char WORD_BOUNDARY = ' ';
                    final char WORD_BOUNDARY1 = '\n';

                    int wordStart = startPos;
                    while (wordStart >= 0 && fullText.charAt(wordStart) != WORD_BOUNDARY && fullText.charAt(wordStart) != WORD_BOUNDARY1) {
                        --wordStart;
                    }
                    wordStart = wordStart + 1;

                    int wordEnd = endPos;
                    while (wordEnd < fullText.length() && fullText.charAt(wordEnd) != WORD_BOUNDARY && fullText.charAt(wordEnd) != WORD_BOUNDARY1) {
                        ++wordEnd;
                    }

                    // Now highlight based on the word boundaries
                    ColorStateList redColor = new ColorStateList(new int[][]{new int[]{}}, new int[]{Color.RED});
                    TextAppearanceSpan highlightSpan = new TextAppearanceSpan(null, Typeface.BOLD, -1, redColor, null);

                    wordtoSpan.setSpan(highlightSpan, wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                    wordtoSpan.setSpan(new BackgroundColorSpan(0xFFFFFF00), wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
                    wordtoSpan.setSpan(new RelativeSizeSpan(1.5f), wordStart, wordEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

                    textView.setText(wordtoSpan, TextView.BufferType.SPANNABLE);

                }
            }
        } else {
            textView.setText(fullText);
        }
    } else {
        textView.setText(fullText);
    }
}