Html.fromHtml, Android N'de kullanımdan kaldırıldı


300

Bir Html.fromHtmlhtml görüntülemek için kullanıyorum TextView.

Spanned result = Html.fromHtml(mNews.getTitle());
...
...
mNewsTitle.setText(result);

Fakat Html.fromHtml şimdi Android N + 'da kullanımdan kaldırıldı

Bunu yapmanın yeni yolunu ne / nasıl bulurum?

Yanıtlar:


617

güncelleme : @Andy'nin belirttiği gibi , HtmlCompataşağıdaki yöntem yerine kullanılabilecek Google oluşturdu . Bu bağımlılığı implementation 'androidx.core:core:1.0.1 uygulamanızın build.gradle dosyasına ekleyin. Sitesinin en son sürümünü kullandığınızdan emin olun.androidx.core:core .

Bu aşağıdakileri kullanmanıza izin verir:

HtmlCompat.fromHtml(html, HtmlCompat.FROM_HTML_MODE_LEGACY);

HtmlCompat belgelerinde farklı bayraklar hakkında daha fazla bilgi edinebilirsiniz

orijinal cevap: Android N'de yeni bir Html.fromHtmlyöntem tanıttılar . Html.fromHtmlşimdi bayraklar adı verilen ek bir parametre gerekiyor. Bu bayrak, HTML'nizin nasıl görüntüleneceği konusunda size daha fazla kontrol sağlar.

Android N ve üzeri sürümlerde bu yeni yöntemi kullanmalısınız. Eski yöntem kullanımdan kaldırılmıştır ve gelecekteki Android sürümlerinde kaldırılabilir.

Eski sürümlerde eski yöntemi ve Android N ve üzeri sürümlerde daha yeni yöntemi kullanacak olan kendi Util yönteminizi oluşturabilirsiniz. Bir sürüm eklemezseniz, uygulamanızın daha düşük Android sürümlerinde bozulacağını kontrol edin. Bu yöntemi Util sınıfınızda kullanabilirsiniz.

@SuppressWarnings("deprecation")
public static Spanned fromHtml(String html){
    if(html == null){
        // return an empty spannable if the html is null
        return new SpannableString("");
    }else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
        // FROM_HTML_MODE_LEGACY is the behaviour that was used for versions below android N
        // we are using this flag to give a consistent behaviour
        return Html.fromHtml(html, Html.FROM_HTML_MODE_LEGACY);
    } else {
        return Html.fromHtml(html);
    }
}

İsterseniz HTML.FROM_HTML_MODE_LEGACYek bir parametreye dönüştürebilirsiniz . Bu, hangi bayrağı kullanacağınız konusunda size daha fazla kontrol sağlar.

Html sınıfı belgelerinde farklı bayraklar hakkında daha fazla bilgi edinebilirsiniz


2
Sıfır hangi bayrağı temsil eder?
ban-geoengineering

4
Html.FROM_HTML_MODE_LEGACY
ban-geoengineering

14
ah, HtmlCompat gibi bir şeyin görünmesini bekliyorum
vanomart

12
Tüy bırakmayan uyarılardan kaçınmak için //noinspection deprecationhemen altına bir yorum eklemek de yararlıdır else.
Ted Hopp

1
Bu bayrakların her birinin bu blog gönderisinde ne yaptığını görebilirsiniz: medium.com/@yair.kukielka/…
Yair Kukielka

95

Bu uyarıların bir sürü vardı ve her zaman FROM_HTML_MODE_LEGACY kullanın, bu yüzden HtmlCompat adlı aşağıdakileri içeren bir yardımcı sınıf yaptım:

   @SuppressWarnings("deprecation")
   public static Spanned fromHtml(String source) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            return Html.fromHtml(source, Html.FROM_HTML_MODE_LEGACY);
        } else {
            return Html.fromHtml(source);
        }
    }

2
Kabul edilen cevapla aynı etki, ancak SuppressWarnings ek açıklaması nedeniyle +1
Stoycho Andreev

Bu mod hakkında küçük bir açıklama yapabilir misiniz?
Ranjith Kumar

Tüm HTMLCompact git göbek üzerinde olabilir sağlayabilir serin görünüyor
Shareef'ten

@shareef ama bu sadece bu tek yöntem ile sıkıcı bir yardımcı sınıf ....
k2col

61

FromHtml () öğelerinin bayraklarını karşılaştırın.

<p style="color: blue;">This is a paragraph with a style</p>

<h4>Heading H4</h4>

<ul>
   <li style="color: yellow;">
      <font color=\'#FF8000\'>li orange element</font>
   </li>
   <li>li #2 element</li>
</ul>

<blockquote>This is a blockquote</blockquote>

Text after blockquote
Text before div

<div>This is a div</div>

Text after div

FROM_HTML BAYRAKLAR


Giriş HTML'sini de paylaşır mısınız? Bu, dönüşümü daha iyi anlamaya yardımcı olur.
Kalpesh Patel

Stil niteliklerinin uygulanmadığını görüyorum, bunları uygulamanın bir yolu var mı?
Christine


25

Kotlin'de gelişecek kadar şanslıysanız, sadece bir uzantı işlevi oluşturun:

fun String.toSpanned(): Spanned {
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
        return Html.fromHtml(this, Html.FROM_HTML_MODE_LEGACY)
    } else {
        @Suppress("DEPRECATION")
        return Html.fromHtml(this)
    }
}

Ve sonra her yerde kullanmak çok tatlı:

yourTextView.text = anyString.toSpanned()

5
yazımları kaldırarak kaydedebilir Spannedvereturn
Minami

14

fromHtml

Bu yöntem edildi kaldırılmış olarak API seviyesi 24 .

FROM_HTML_MODE_LEGACY kullanmalısınız

Blok düzeyinde öğeleri, aralarında boş satırlar (iki yeni satır karakteri) ile ayırın. Bu, N'den önceki eski davranıştır.

kod

if (Build.VERSION.SDK_INT >= 24)
        {
            etOBJ.setText(Html.fromHtml("Intellij \n Amiyo",Html.FROM_HTML_MODE_LEGACY));

         }
 else
        {
           etOBJ.setText(Html.fromHtml("Intellij \n Amiyo"));
        }

Kotlin için

fun setTextHTML(html: String): Spanned
    {
        val result: Spanned = if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.N) {
            Html.fromHtml(html, Html.FROM_HTML_MODE_LEGACY)
        } else {
            Html.fromHtml(html)
        }
        return result
    }

Aramak

 txt_OBJ.text  = setTextHTML("IIT Amiyo")

Bu mod hakkında küçük bir açıklama yapabilir misiniz?
Ranjith Kumar

SDK'nın sürüm kontrollerini işlemesini istiyorsanız, şunu kullanın: HtmlCompat.fromHtml("textWithHtmlTags", HtmlCompat.FROM_HTML_MODE_LEGACY)
Wajid Ali

8

Resmi doc'dan:

fromHtml(String)yöntem API düzeyi 24'te kullanımdan kaldırıldı fromHtml(String, int) .

  1. TO_HTML_PARAGRAPH_LINES_CONSECUTIVESeçenek toHtml(Spanned, int): '\n'İç <p> elemanlar tarafından sınırlandırılmış ardışık metin satırlarını kaydırın .

  2. TO_HTML_PARAGRAPH_LINES_INDIVIDUALSeçenek toHtml(Spanned, int): '\n'a <p>veya <li> öğenin içinde ayrılmış metin satırlarını kaydırın .

https://developer.android.com/reference/android/text/Html.html


8

Kotlin kullanıyorsanız , bunu bir Kotlin uzantısı kullanarak başardım:

fun TextView.htmlText(text: String){
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
        setText(Html.fromHtml(text, Html.FROM_HTML_MODE_LEGACY))
    } else {
        setText(Html.fromHtml(text))
    }
}

Sonra şöyle deyin:

textView.htmlText(yourHtmlText)

5

@Rockney ve @ k2col'ün cevabını genişletmek için geliştirilmiş kod şöyle görünebilir:

@NonNull
public static Spanned fromHtml(@NonNull String html) {
    if (CompatUtils.isApiNonLowerThan(VERSION_CODES.N)) {
        return Html.fromHtml(html, Html.FROM_HTML_MODE_LEGACY);
    } else {
        //noinspection deprecation
        return Html.fromHtml(html);
    }
}

Nerede CompatUtils.isApiNonLowerThan:

public static boolean isApiNonLowerThan(int versionCode) {
    return Build.VERSION.SDK_INT >= versionCode;
}

Aradaki fark, fazladan yerel değişken olmaması ve kullanımdan kaldırmanın sadece elsebranşta olmasıdır. Yani bu tek dal hariç tüm yöntemi bastırmayacaktır.

Google'ın Android'in gelecekteki bazı sürümlerinde fromHtml(String source, int flags)yöntemi bile kullanımdan kaldırmaya ne zaman karar vereceği yardımcı olabilir .


4

Kullanabilirsiniz

//noinspection deprecation
return Html.fromHtml(source);

sadece tek bir açıklama için teftişi bastırmak, ancak tüm yöntemi değil.


2

Çerçeve sınıfı, fromHtml()satır sonlarının nasıl işleneceğini bildirmek için bir işaret gerektirecek şekilde değiştirildi . Bu Nougat'a eklendi ve sadece Android sürümleri arasında bu sınıfın uyumsuzluklarına meydan okuyor.

Sınıfı standartlaştırmak ve backport etmek ve öğeler ve stil için daha fazla geri arama eklemek için bir uyumluluk kütüphanesi yayınladım:

https://github.com/Pixplicity/HtmlCompat

Çerçevenin Html sınıfına benzer olsa da, daha fazla geri çağrıya izin vermek için bazı imza değişiklikleri gerekiyordu. GitHub sayfasından örnek:

Spanned fromHtml = HtmlCompat.fromHtml(context, source, 0);
// You may want to provide an ImageGetter, TagHandler and SpanCallback:
//Spanned fromHtml = HtmlCompat.fromHtml(context, source, 0,
//        imageGetter, tagHandler, spanCallback);
textView.setMovementMethod(LinkMovementMethod.getInstance());
textView.setText(fromHtml);

Kitaplığınızı kullanan bir uygulamada kullandığımda minSdkVersion 15ve değerler-v24.xmltargetSdkVersion 23 için bir derleme hatası aldığımda : Error:(3) Error retrieving parent for item: No resource found that matches the given name 'android:TextAppearance.Material.Widget.Button.Borderless.Colored'.Kitaplığınız açıkça API düzey 25'i hedefliyor. Hala nasıl kullanabilirim?
JJD

2

İşte benim çözümüm.

 if (Build.VERSION.SDK_INT >= 24) {
        holder.notificationTitle.setText(Html.fromHtml(notificationSucces.getMessage(), Html.FROM_HTML_MODE_LEGACY));
    } else {
        holder.notificationTitle.setText(Html.fromHtml(notificationSucces.getMessage()));

    }

1

sadece bir işlev yapın:

public Spanned fromHtml(String str){
  return Build.VERSION.SDK_INT >= 24 ? Html.fromHtml(str, Html.FROM_HTML_MODE_LEGACY) : Html.fromHtml(str);
}

0

Bu küçük kod satırını deneyin

HtmlCompat.fromHtml("Your html text",HtmlCompat.FROM_HTML_MODE_LEGACY)

-2

Ul ol li etiketleri dahil temel html etiketlerini desteklemek için aşağıdakileri deneyin. Aşağıda gösterildiği gibi bir Etiket işleyici oluşturun

import org.xml.sax.XMLReader;

import android.app.Activity;
import android.os.Bundle;
import android.text.Editable;
import android.text.Html;
import android.text.Html.TagHandler;
import android.util.Log;

public class MyTagHandler implements TagHandler {
    boolean first= true;
    String parent=null;
    int index=1;
    @Override
    public void handleTag(boolean opening, String tag, Editable output,
                          XMLReader xmlReader) {

        if(tag.equals("ul")) parent="ul";
        else if(tag.equals("ol")) parent="ol";
        if(tag.equals("li")){
            if(parent.equals("ul")){
                if(first){
                    output.append("\n\t•");
                    first= false;
                }else{
                    first = true;
                }
            }
            else{
                if(first){
                    output.append("\n\t"+index+". ");
                    first= false;
                    index++;
                }else{
                    first = true;
                }
            }
        }
    }
}

Etkinlik'teki metni aşağıda gösterildiği gibi ayarlayın

@SuppressWarnings("deprecation")
    public void init(){
        try {
            TextView help = (TextView) findViewById(R.id.help);
            if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.N) {
                help.setText(Html.fromHtml(getString(R.string.help_html),Html.FROM_HTML_MODE_LEGACY, null, new MyTagHandler()));
            } else {
                help.setText(Html.fromHtml(getString(R.string.help_html), null, new MyTagHandler()));
            }
        } catch (Exception e) {
            e.printStackTrace();
        }

    }

Kaynak dize dosyalarındaki html metni

<! [CDATA [... ham html verileri ...]]>

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.