Один TextView з декількома кольоровими текстами


167

Як говориться в заголовку, я хочу знати, чи можна досягти двох різнокольорових символів в одному елементі перегляду тексту.



1
Це не дублікат, оскільки запитувач просить конкретно кольору.
Ікбал

Для цього є приємна бібліотека, я думаю: blog.stylingandroid.com/rialto-downloadable-fonts github.com/StylingAndroid/Rialto
андроїд розробник

Я теж написав бібліотеку, яка має подібну поведінку до цього: github.com/ha-yi/MultiColorTextView
Hayi Nukman,

Відповіді:


328

да, якщо ви форматувати Stringз html«S font-colorвласності потім передати його методуHtml.fromHtml(your text here)

String text = "<font color=#cc0029>First Color</font> <font color=#ffcc00>Second Color</font>";
yourtextview.setText(Html.fromHtml(text));

Спасибі також корисні для мене. +1
Хардік Джоші

10
Не забудьте уникнути користувальницького введення, використовуючи Html.escapeHtml(str).
kelunik

1
Додано в api рівень 1
2red13

3
Просто попередження. У мене виникли проблеми, коли мені потрібен був великий текст. Я використовував android: textAllCaps = "true" у XML і, водночас, мав вміст HTML у верхньому регістрі. Це не працювало. Я видалив атрибут XML і він зараз працює добре. Будьте обережні, адже якщо ви використовуєте код коду setAllCaps (), з’явиться та сама проблема.
joao2fast4u

5
Html.fromHtml(String)тепер застаріло, замість цього використовувати Html.fromHtml(String, Html.FROM_HTML_MODE_LEGACY). Більше інформації можна знайти тут.
JediBurrell

165

Ви можете друкувати лінії з кількома кольорами без HTML як:

TextView textView = (TextView) findViewById(R.id.mytextview01);
Spannable word = new SpannableString("Your message");        

word.setSpan(new ForegroundColorSpan(Color.BLUE), 0, word.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);

textView.setText(word);
Spannable wordTwo = new SpannableString("Your new message");        

wordTwo.setSpan(new ForegroundColorSpan(Color.RED), 0, wordTwo.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
textView.append(wordTwo);

чудово, спасибі, також можна зробити BackgroundColorSpan. у вашому прикладі є невеликий помилок, WordToSpan та WordtoSpan, зверніть увагу на випадок на
Стів

Як можна йти про одиницю тестування TextView , щоб гарантувати , що текст закінчується в Color.RED stackoverflow.com/questions/26611533 / ...
sudocoder

1
Не працює для мене, отримуючи `java.lang.StringIndexOutOfBoundsException: length = 3; індекс = 12`
Мухаммад Бабар

1
StringIndexOutOfBoundsException сама пояснювальна. Ви отримуєте доступ до рядка понад його довжину.
Swapnil Kotwal

1
Мої рядки не були виправлені, тому рядки створюватимуться під час роботи програми. Я перепробував майже всі відповіді на це питання. Але тільки це рішення працювало на мене.
Пані Саббір Ахмед

33

Ви можете використовувати, Spannableщоб застосувати ефекти до своїх TextView:

Ось мій приклад для фарбування лише першої частини TextViewтексту (дозволяючи вам задавати колір динамічно, а не жорстко кодувати його у рядку, як у прикладі HTML!)

    mTextView.setText("Red text is here", BufferType.SPANNABLE);
    Spannable span = (Spannable) mTextView.getText();
    span.setSpan(new ForegroundColorSpan(0xFFFF0000), 0, "Red".length(),
             Spannable.SPAN_INCLUSIVE_EXCLUSIVE);

У цьому прикладі ви можете замінити 0xFFFF0000 на a getResources().getColor(R.color.red)


1
Якщо вам потрібен верхній регістр, просто toUpperCase () рядки.
Graeme

33

Я зробив так:

Перевірте посилання

Встановіть колір тексту на текст , передаючи рядок і колір :

private String getColoredSpanned(String text, String color) {
    String input = "<font color=" + color + ">" + text + "</font>";
    return input;
}

Встановіть текст у TextView / Кнопці / EditText тощо, зателефонувавши під кодом нижче:

TextView:

TextView txtView = (TextView)findViewById(R.id.txtView);

Отримайте кольорову рядок:

String name = getColoredSpanned("Hiren", "#800000");
String surName = getColoredSpanned("Patel","#000080");

Встановити текст на TextView двох рядків з різними кольорами:

txtView.setText(Html.fromHtml(name+" "+surName));

Зроблено


1
nyc one, але HTML.fromHtml застаріло від API 24
Anuraj R

Ви можете замінити дзвінки на Html.fromHtml("...")дзвінки доHtml.fromHtml("...", FROM_HTML_MODE_LEGACY)
строк

31

Використовуйте SpannableStringBuilder

SpannableStringBuilder builder = new SpannableStringBuilder();

SpannableString str1= new SpannableString("Text1");
str1.setSpan(new ForegroundColorSpan(Color.RED), 0, str1.length(), 0);
builder.append(str1);

SpannableString str2= new SpannableString(appMode.toString());
str2.setSpan(new ForegroundColorSpan(Color.GREEN), 0, str2.length(), 0);
builder.append(str2);

TextView tv = (TextView) view.findViewById(android.R.id.text1);
tv.setText( builder, TextView.BufferType.SPANNABLE);

8

Гей, хлопці, я це зробив, спробуйте

TextView textView=(TextView)findViewById(R.id.yourTextView);//init

//here I am appending two string into my textView with two diff colors.
//I have done from fragment so I used here getActivity(), 
//If you are trying it from Activity then pass className.this or this; 

textView.append(TextViewUtils.getColoredString(getString(R.string.preString),ContextCompat.getColor(getActivity(),R.color.firstColor)));
textView.append(TextViewUtils.getColoredString(getString(R.string.postString),ContextCompat.getColor(getActivity(),R.color.secondColor)));

Всередині вас клас TextViewUtils додайте цей метод

 /***
 *
 * @param mString this will setup to your textView
 * @param colorId  text will fill with this color.
 * @return string with color, it will append to textView.
 */
public static Spannable getColoredString(String mString, int colorId) {
    Spannable spannable = new SpannableString(mString);
    spannable.setSpan(new ForegroundColorSpan(colorId), 0, spannable.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    Log.d(TAG,spannable.toString());
    return spannable;
}

Я оновив лише зараз, перевірте це, він працює для мене.
Абдул Різван

Myabe, ти використовуєш Html.fromHtml для використання цього рядка?
Сергій Шустіков

всередині string.xml-файлу Я створив змінну і встановив це, він працює для мене просто зараз, я це роблю, чи можете ви, будь ласка, дати тут свою рядок.
Абдул Різван

5

Краще використовувати рядок у файлі рядків як такий:

    <string name="some_text">
<![CDATA[
normal color <font color=\'#06a7eb\'>special color</font>]]>
    </string>

Використання:

textView.text=HtmlCompat.fromHtml(getString(R.string.some_text), HtmlCompat.FROM_HTML_MODE_LEGACY)

4

У мене є записування коду на інше запитання, яке схоже на це, але це питання дублюється, тому я не можу відповісти, тому я просто ставлю свій код тут, якщо хтось шукає тієї ж вимоги.

Це не повністю працюючий код, для його роботи потрібно внести деякі незначні зміни.

Ось код:

Я використав ідею @Graeme щодо використання тексту, що перекладається.

String colorfulText = "colorfulText";       
    Spannable span = new SpannableString(colorfulText);             

    for ( int i = 0, len = colorfulText.length(); i < len; i++ ){
        span.setSpan(new ForegroundColorSpan(getRandomColor()), i, i+1,Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);                     
    }   

    ((TextView)findViewById(R.id.txtSplashscreenCopywrite)).setText(span);

Випадковий кольоровий метод:

  private int getRandomColor(){
        Random rnd = new Random();
        return Color.argb(255, rnd.nextInt(256), rnd.nextInt(256), rnd.nextInt(256));
    }

2

Спробуйте це:

mBox = new TextView(context);
mBox.setText(Html.fromHtml("<b>" + title + "</b>" +  "<br />" + 
      "<small>" + description + "</small>" + "<br />" + 
      "<small>" + DateAdded + "</small>"));

2

Використовуйте клас SpannableBuilder замість форматування HTML, де це можливо, оскільки це швидше, ніж розбір формату HTML. Дивіться власний орієнтир "SpannableBuilder vs HTML" на Github Спасибі!


1

Дивовижні відповіді! Мені вдалося використати Spannable для створення тексту в кольорі веселки (щоб це можна було повторити для будь-якого масиву кольорів). Ось мій метод, якщо він комусь допомагає:

private Spannable buildRainbowText(String pack_name) {
        int[] colors = new int[]{Color.RED, 0xFFFF9933, Color.YELLOW, Color.GREEN, Color.BLUE, Color.RED, 0xFFFF9933, Color.YELLOW, Color.GREEN, Color.BLUE, Color.RED, 0xFFFF9933, Color.YELLOW, Color.GREEN, Color.BLUE, Color.RED, 0xFFFF9933, Color.YELLOW, Color.GREEN, Color.BLUE};
        Spannable word = new SpannableString(pack_name);
        for(int i = 0; i < word.length(); i++) {
            word.setSpan(new ForegroundColorSpan(colors[i]), i, i+1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
        }
        return word;
    }

І тоді я просто встановлююText (buildRainboxText (ім'я пакета)); Зауважте, що всі слова, які я передаю, містять менше 15 символів, і це просто повторює 5 кольорів 3 рази - ви хочете налаштувати кольори / довжину масиву для свого використання!


1
if (Build.VERSION.SDK_INT >= 24) {
     Html.fromHtml(String, flag) // for 24 API  and more
 } else {
     Html.fromHtml(String) // or for older API 
 }

для 24 API та більше (прапор)

public static final int FROM_HTML_MODE_COMPACT = 63;
public static final int FROM_HTML_MODE_LEGACY = 0;
public static final int FROM_HTML_OPTION_USE_CSS_COLORS = 256;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_BLOCKQUOTE = 32;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_DIV = 16;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_HEADING = 2;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_LIST = 8;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_LIST_ITEM = 4;
public static final int FROM_HTML_SEPARATOR_LINE_BREAK_PARAGRAPH = 1;
public static final int TO_HTML_PARAGRAPH_LINES_CONSECUTIVE = 0;
public static final int TO_HTML_PARAGRAPH_LINES_INDIVIDUAL = 1;

Більше інформації


1

Оскільки в API 24 у вас є FROM_HTML_OPTION_USE_CSS_COLORS, тож ви можете визначити кольори в CSS замість того, щоб повторювати це все font color=" набагато чіткіше - коли у вас є трохи html і ви хочете виділити деякі попередньо визначені теги - вам просто потрібно додати фрагмент CSS у верхній частині html


0

25 червня 2020 року від @canerkaseler

Я хотів би поділитися відповіддю Котліна :

fun setTextColor(tv:TextView, startPosition:Int, endPosition:Int, color:Int){
    val spannableStr = SpannableString(tv.text)

    val underlineSpan = UnderlineSpan()
    spannableStr.setSpan(
        underlineSpan,
        startPosition,
        endPosition,
        Spanned.SPAN_INCLUSIVE_EXCLUSIVE
    )

    val backgroundColorSpan = ForegroundColorSpan(this.resources.getColor(R.color.agreement_color))
    spannableStr.setSpan(
        backgroundColorSpan,
        startPosition,
        endPosition,
        Spanned.SPAN_INCLUSIVE_EXCLUSIVE
    )

    val styleSpanItalic = StyleSpan(Typeface.BOLD)
    spannableStr.setSpan(
        styleSpanItalic,
        startPosition,
        endPosition,
        Spanned.SPAN_INCLUSIVE_EXCLUSIVE
    )

    tv.text = spannableStr
}

Після, виклик вище функції. Ви можете зателефонувати більше:

setTextColor(textView, 0, 61, R.color.agreement_color)
setTextColor(textView, 65, 75, R.color.colorPrimary)

Вихід: Ви можете бачити підкреслені та різні кольори один з одним.

@canerkaseler

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.