Vista de texto único con texto de varios colores

168

Como dice el título, quiero saber si es posible lograr dos caracteres de diferentes colores en un solo elemento de vista de texto.

Andro Selva
fuente
1
No está duplicado ya que el autor de la pregunta está pidiendo color específicamente.
Iqbal
Creo que hay una buena biblioteca para esto: blog.stylingandroid.com/rialto-downloadable-fonts github.com/StylingAndroid/Rialto
desarrollador de Android
También escribí una biblioteca que tiene un comportamiento similar a este: github.com/ha-yi/MultiColorTextView
Hayi Nukman

Respuestas:

328

Sí, si formatea el Stringcon html's font-colorpropiedad luego pasarlo al métodoHtml.fromHtml(your text here)

String text = "<font color=#cc0029>First Color</font> <font color=#ffcc00>Second Color</font>";
yourtextview.setText(Html.fromHtml(text));
2red13
fuente
Gracias también útil para mí. +1
Hardik Joshi
10
No olvides escapar de la entrada de usuario usando Html.escapeHtml(str).
Kelunik
1
Añadido en el nivel de API 1
2red13
3
Sólo una advertencia. Estaba teniendo un problema cuando necesitaba que mi texto estuviera en mayúscula. Estaba usando android: textAllCaps = "true" en XML y, al mismo tiempo, tenía mi contenido HTML en mayúsculas. No estaba funcionando Eliminé el atributo XML y ahora funciona bien. Tenga cuidado, porque si usa setAllCaps () en el código, aparecerá el mismo problema.
joao2fast4u
55
Html.fromHtml(String)ahora está en desuso, en lugar de usar Html.fromHtml(String, Html.FROM_HTML_MODE_LEGACY). Más información se puede encontrar aquí.
JediBurrell
165

Puede imprimir líneas con múltiples colores sin HTML como:

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);
Swapnil Kotwal
fuente
genial, gracias, también puedes hacer BackgroundColorSpan. hay un pequeño error tipográfico en su ejemplo, WordToSpan y WordtoSpan, tenga en cuenta el caso en To
steveh
¿cómo se hace para probar la vista de texto de la unidad para asegurarse de que el texto termina en Color.RED stackoverflow.com/questions/26611533/…
sudocoder
1
No funciona para mí obtener `java.lang.StringIndexOutOfBoundsException: length = 3; index = 12`
Muhammad Babar
1
StringIndexOutOfBoundsException en sí mismo explicativo. Está accediendo a una cadena más allá de su longitud.
Swapnil Kotwal
1
Mis cadenas no fueron reparadas, por lo que las cadenas se generarían en el tiempo de ejecución de la aplicación. He intentado casi todas las respuestas de esta pregunta. Pero solo esta solución funcionó para mí.
Md. Sabbir Ahmed
33

Puede usar Spannablepara aplicar efectos a su TextView:

Aquí está mi ejemplo para colorear solo la primera parte de un TextViewtexto (¡mientras le permite configurar el color dinámicamente en lugar de codificarlo en una cadena como en el ejemplo 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);

En este ejemplo, puede reemplazar 0xFFFF0000 con un getResources().getColor(R.color.red)

Graeme
fuente
1
Si necesita esta mayúscula, simplemente use Mayúsculas () las cadenas.
Graeme
33

He hecho de esta manera:

Consultar referencia

El conjunto de colores de texto por el que pasa de cuerdas y el color :

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

Configure el texto en TextView / Button / EditText, etc. llamando al código siguiente:

Vista de texto:

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

Obtener cadena de color:

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

Establecer texto en TextView de dos cadenas con diferentes colores:

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

Hecho

Hiren Patel
fuente
1
nyc one, pero HTml.fromHtml está en desuso de API 24
Anuraj R
Puede reemplazar llamadas a Html.fromHtml("...")con llamadas aHtml.fromHtml("...", FROM_HTML_MODE_LEGACY)
stkent
31

Utilice 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);
Biswajit Karmakar
fuente
8

Hola chicos, he hecho esto, pruébalo

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)));

Dentro de tu clase TextViewUtils agrega este método

 /***
 *
 * @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;
}
Abdul Rizwan
fuente
Lo actualicé ahora, verifíquelo una vez, está funcionando para mí.
Abdul Rizwan
¿Puede usar Html.fromHtml para usar esta cadena?
Sergey Shustikov
dentro del archivo string.xml He creado una variable y configuré esto, me está funcionando justo ahora que estoy haciendo esto, ¿pueden darme su cadena aquí?
Abdul Rizwan
5

Es mejor usar la cadena en el archivo de cadenas, como tal:

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

Uso:

textView.text=HtmlCompat.fromHtml(getString(R.string.some_text), HtmlCompat.FROM_HTML_MODE_LEGACY)
desarrollador de Android
fuente
4

He escrito un código para otra pregunta que es similar a esta, pero esa pregunta se ha duplicado, así que no puedo responder allí, así que solo pongo mi código aquí si alguien busca el mismo requisito.

No es un código completamente funcional, debe hacer algunos cambios menores para que funcione.

Aquí está el código:

He usado la idea de @Graeme de usar texto que se puede cambiar.

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);

Método de color aleatorio:

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

Prueba esto:

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

Utilice la clase SpannableBuilder en lugar del formato HTML donde sea posible porque es más rápido que el análisis del formato HTML. Vea mi propio punto de referencia "SpannableBuilder vs HTML" en Github ¡Gracias!

Anatoliy Shuba
fuente
1

Respuestas impresionantes! Pude usar Spannable para construir texto de color arcoíris (por lo que esto podría repetirse para cualquier variedad de colores). Aquí está mi método, si ayuda a alguien:

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;
    }

Y luego simplemente configuroText (buildRainboxText (pack_name)); Tenga en cuenta que todas las palabras que paso tienen menos de 15 caracteres y esto solo repite 5 colores 3 veces. ¡Desea ajustar los colores / longitud de la matriz para su uso!

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

para 24 API y más (marca)

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;

Más información

Ahmad Aghazadeh
fuente
1

Desde API 24 tiene FROM_HTML_OPTION_USE_CSS_COLORS para que pueda definir colores en CSS en lugar de repetirlo todo el tiempo con font color=" mucho más claro, cuando tiene algo de HTML y desea resaltar algunas etiquetas predefinidas, solo necesita agregar un fragmento de CSS en la parte superior de su HTML

Filipkowicz
fuente
0

25 de junio de 2020 por @canerkaseler

Me gustaría compartir Kotlin Respuesta :

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
}

Después, llame a la función anterior. Puedes llamar a más de uno:

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

Salida: puede ver subrayado y diferentes colores entre sí.

@canerkaseler

Canerkaseler
fuente