it-swarm.com.de

Wie füge ich ein Bild in einem TextView-Text hinzu?

Ich habe bei Google herumgesucht und bin auf diese Seite gestoßen, auf der ich eine ähnliche Frage wie meine gefunden habe, in der ein Bild in einen TextView-Text eingefügt wird, zum Beispiel "Hallo, mein Name ist [Bild]" und das Antwort war folgende:

ImageSpan is = new ImageSpan(context, resId);
text.setSpan(is, index, index + strLength, 0);

Ich würde gerne in diesem Code wissen,

  1. Was soll ich im Kontext eingeben oder tun?
  2. Soll ich etwas zur text.setSpan() tun wie Import oder Referenz oder den Text hinterlassen?

Wenn jemand das für mich reißen kann, wäre das sehr dankbar.

69
Cranosaur

Versuche dies ..

    txtview.setCompoundDrawablesWithIntrinsicBounds(
                    R.drawable.image, 0, 0, 0);

Siehe auch .. http://developer.Android.com/reference/Android/widget/TextView.html

Versuchen Sie dies in einer XML-Datei 

    <TextView
        Android:id="@+id/txtStatus"
        Android:layout_width="wrap_content"
        Android:layout_height="wrap_content"
        Android:layout_gravity="center"
        Android:drawableLeft="@drawable/image"
        Android:drawablePadding="5dp"
        Android:singleLine="true"
        Android:text="@string/name"/>
175
Umesh Lakhani

com/xyz/customandroid/TextViewWithImages.Java:

import Java.util.regex.Matcher;
import Java.util.regex.Pattern;

import Android.content.Context;
import Android.text.Spannable;
import Android.text.style.ImageSpan;
import Android.util.AttributeSet;
import Android.util.Log;
import Android.widget.TextView;

public class TextViewWithImages extends TextView {

    public TextViewWithImages(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }
    public TextViewWithImages(Context context, AttributeSet attrs) {
        super(context, attrs);
    }
    public TextViewWithImages(Context context) {
        super(context);
    }
    @Override
    public void setText(CharSequence text, BufferType type) {
        Spannable s = getTextWithImages(getContext(), text);
        super.setText(s, BufferType.SPANNABLE);
    }

    private static final Spannable.Factory spannableFactory = Spannable.Factory.getInstance();

    private static boolean addImages(Context context, Spannable spannable) {
        Pattern refImg = Pattern.compile("\\Q[img src=\\E([a-zA-Z0-9_]+?)\\Q/]\\E");
        boolean hasChanges = false;

        Matcher matcher = refImg.matcher(spannable);
    while (matcher.find()) {
        boolean set = true;
        for (ImageSpan span : spannable.getSpans(matcher.start(), matcher.end(), ImageSpan.class)) {
            if (spannable.getSpanStart(span) >= matcher.start()
             && spannable.getSpanEnd(span) <= matcher.end()
               ) {
                spannable.removeSpan(span);
            } else {
                set = false;
                break;
            }
        }
        String resname = spannable.subSequence(matcher.start(1), matcher.end(1)).toString().trim();
        int id = context.getResources().getIdentifier(resname, "drawable", context.getPackageName());
        if (set) {
            hasChanges = true;
            spannable.setSpan(  new ImageSpan(context, id),
                                matcher.start(),
                                matcher.end(),
                                Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
                             );
        }
    }

        return hasChanges;
    }
    private static Spannable getTextWithImages(Context context, CharSequence text) {
        Spannable spannable = spannableFactory.newSpannable(text);
        addImages(context, spannable);
        return spannable;
    }
}

Benutzen:

in res/layout/mylayout.xml:

            <com.xyz.customandroid.TextViewWithImages
                Android:layout_width="wrap_content"
                Android:layout_height="wrap_content"
                Android:textColor="#FFFFFF00"
                Android:text="@string/can_try_again"
                Android:textSize="12dip"
                style=...
                />

Wenn Sie TextViewWithImages.Java an einem anderen Ort als com/xyz/customandroid/ platzieren, müssen Sie auch den Paketnamen com.xyz.customandroid oben ändern.

in res/values ​​/ strings.xml:

<string name="can_try_again">Press [img src=ok16/] to accept or [img src=retry16/] to retry</string>

dabei sind ok16.png und retry16.png Symbole im Ordner res/drawable/

67

Diese Antwort basiert auf dieser hervorragenden Antwort by 18446744073709551615 . Ihre Lösung ist zwar hilfreich, ändert jedoch nicht das Bildsymbol mit dem umgebenden Text. Außerdem wird die Symbolfarbe nicht auf die Farbe des umgebenden Texts festgelegt. 

Bei der folgenden Lösung wird ein weißes, quadratisches Symbol verwendet, das die Größe und Farbe des umgebenden Textes berücksichtigt.

public class TextViewWithImages extends TextView {

    private static final String DRAWABLE = "drawable";
    /**
     * Regex pattern that looks for embedded images of the format: [img src=imageName/]
     */
    public static final String PATTERN = "\\Q[img src=\\E([a-zA-Z0-9_]+?)\\Q/]\\E";

    public TextViewWithImages(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }

    public TextViewWithImages(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public TextViewWithImages(Context context) {
        super(context);
    }

    @Override
    public void setText(CharSequence text, BufferType type) {
        final Spannable spannable = getTextWithImages(getContext(), text, getLineHeight(), getCurrentTextColor());
        super.setText(spannable, BufferType.SPANNABLE);
    }

    private static Spannable getTextWithImages(Context context, CharSequence text, int lineHeight, int colour) {
        final Spannable spannable = Spannable.Factory.getInstance().newSpannable(text);
        addImages(context, spannable, lineHeight, colour);
        return spannable;
    }

    private static boolean addImages(Context context, Spannable spannable, int lineHeight, int colour) {
        final Pattern refImg = Pattern.compile(PATTERN);
        boolean hasChanges = false;

        final Matcher matcher = refImg.matcher(spannable);
        while (matcher.find()) {
            boolean set = true;
            for (ImageSpan span : spannable.getSpans(matcher.start(), matcher.end(), ImageSpan.class)) {
                if (spannable.getSpanStart(span) >= matcher.start()
                        && spannable.getSpanEnd(span) <= matcher.end()) {
                    spannable.removeSpan(span);
                } else {
                    set = false;
                    break;
                }
            }
            final String resName = spannable.subSequence(matcher.start(1), matcher.end(1)).toString().trim();
            final int id = context.getResources().getIdentifier(resName, DRAWABLE, context.getPackageName());
            if (set) {
                hasChanges = true;
                spannable.setSpan(makeImageSpan(context, id, lineHeight, colour),
                        matcher.start(),
                        matcher.end(),
                        Spannable.SPAN_EXCLUSIVE_EXCLUSIVE
                );
            }
        }
        return hasChanges;
    }

    /**
     * Create an ImageSpan for the given icon drawable. This also sets the image size and colour.
     * Works best with a white, square icon because of the colouring and resizing.
     *
     * @param context       The Android Context.
     * @param drawableResId A drawable resource Id.
     * @param size          The desired size (i.e. width and height) of the image icon in pixels.
     *                      Use the lineHeight of the TextView to make the image inline with the
     *                      surrounding text.
     * @param colour        The colour (careful: NOT a resource Id) to apply to the image.
     * @return An ImageSpan, aligned with the bottom of the text.
     */
    private static ImageSpan makeImageSpan(Context context, int drawableResId, int size, int colour) {
        final Drawable drawable = context.getResources().getDrawable(drawableResId);
        drawable.mutate();
        drawable.setColorFilter(colour, PorterDuff.Mode.MULTIPLY);
        drawable.setBounds(0, 0, size, size);
        return new ImageSpan(drawable, ImageSpan.ALIGN_BOTTOM);
    }

}

Wie benutzt man:

Betten Sie einfach Verweise auf die gewünschten Symbole in den Text ein. Es ist egal, ob der Text programmgesteuert durch textView.setText(R.string.string_resource); oder in xml gesetzt wird.

Um ein Zeichen-Icon mit dem Namen example.png einzubetten, fügen Sie die folgende Zeichenfolge in den Text ein: [img src=example/].

Eine String-Ressource könnte beispielsweise so aussehen:

<string name="string_resource">This [img src=example/] is an icon.</string>
10
A Boschman

Ich habe viele verschiedene Lösungen ausprobiert und dies war für mich die beste:

SpannableStringBuilder ssb = new SpannableStringBuilder(" Hello world!");
ssb.setSpan(new ImageSpan(context, R.drawable.image), 0, 1, Spannable.SPAN_INCLUSIVE_INCLUSIVE);
tv_text.setText(ssb, TextView.BufferType.SPANNABLE);

Dieser Code benötigt ein Minimum an Speicher.

9
Pavel Kataykin

Dies basiert teilweise auf dieser früheren Antwort von @A Boschman . Bei dieser Lösung habe ich festgestellt, dass die Eingangsgröße des Bildes die Fähigkeit von makeImageSpan(), das Bild richtig zu zentrieren, stark beeinflusste. Außerdem habe ich festgestellt, dass die Lösung den Textabstand beeinflusst hat, indem unnötige Zeilenabstände erstellt wurden. 

Ich habe BaseImageSpan (aus der Fresco-Bibliothek von Facebook) gefunden, um diese Aufgabe besonders gut zu erledigen:

 /**
 * Create an ImageSpan for the given icon drawable. This also sets the image size. Works best
 * with a square icon because of the sizing
 *
 * @param context       The Android Context.
 * @param drawableResId A drawable resource Id.
 * @param size          The desired size (i.e. width and height) of the image icon in pixels.
 *                      Use the lineHeight of the TextView to make the image inline with the
 *                      surrounding text.
 * @return An ImageSpan, aligned with the bottom of the text.
 */
private static BetterImageSpan makeImageSpan(Context context, int drawableResId, int size) {
    final Drawable drawable = context.getResources().getDrawable(drawableResId);
    drawable.mutate();
    drawable.setBounds(0, 0, size, size);
    return new BetterImageSpan(drawable, BetterImageSpan.ALIGN_CENTER);
}

Übergeben Sie dann wie üblich Ihre betterImageSpan-Instanz an spannable.setSpan()

0
kip2