android textview 显示html方法解析
程序员文章站
2023-12-09 15:29:15
现在网络的繁盛时代,光文字是不能满足人们的胃口的,图片,flash,音频,视频就成为浏览网页的主流显示,在手机上也一样。在手机上显示从网络端获取的数据显示,大家很自然的想起...
现在网络的繁盛时代,光文字是不能满足人们的胃口的,图片,flash,音频,视频就成为浏览网页的主流显示,在手机上也一样。在手机上显示从网络端获取的数据显示,大家很自然的想起两种方式,一种就是webview,一种就是textview。当然webview直接显示html页面就行了,我主要说的textview显示html内容。
首先,说下textview到底支持那些标签呢,通过对源码的查看,发现textview可以解析一部分html标签,如:
<a href="...">
<b>
<big>
<blockquote>
<br>
<cite>
<dfn>
<div align="...">
<em>
<font size="..." color="..." face="...">
<h1>
<h2>
<h3>
<h4>
<h5>
<h6>
<i>
<img src="...">
<p>
<small>
<strike>
<strong>
<sub>
<sup>
<tt>
<u>
大家想究其根本可以查看android.text.html源码,其中有一段这样写:
private void handlestarttag(string tag, attributes attributes) {
if (tag.equalsignorecase("br")) {
// we don't need to handle this. tagsoup will ensure that there's a </br> for each <br>
// so we can safely emite the linebreaks when we handle the close tag.
} else if (tag.equalsignorecase("p")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("div")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("em")) {
start(mspannablestringbuilder, new bold());
} else if (tag.equalsignorecase("b")) {
start(mspannablestringbuilder, new bold());
} else if (tag.equalsignorecase("strong")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("cite")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("dfn")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("i")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("big")) {
start(mspannablestringbuilder, new big());
} else if (tag.equalsignorecase("small")) {
start(mspannablestringbuilder, new small());
} else if (tag.equalsignorecase("font")) {
startfont(mspannablestringbuilder, attributes);
} else if (tag.equalsignorecase("blockquote")) {
handlep(mspannablestringbuilder);
start(mspannablestringbuilder, new blockquote());
} else if (tag.equalsignorecase("tt")) {
start(mspannablestringbuilder, new monospace());
} else if (tag.equalsignorecase("a")) {
starta(mspannablestringbuilder, attributes);
} else if (tag.equalsignorecase("u")) {
start(mspannablestringbuilder, new underline());
} else if (tag.equalsignorecase("sup")) {
start(mspannablestringbuilder, new super());
} else if (tag.equalsignorecase("sub")) {
start(mspannablestringbuilder, new sub());
} else if (tag.length() == 2 &&
character.tolowercase(tag.charat(0)) == 'h' &&
tag.charat(1) >= '1' && tag.charat(1) <= '6') {
handlep(mspannablestringbuilder);
start(mspannablestringbuilder, new header(tag.charat(1) - '1'));
} else if (tag.equalsignorecase("img")) {
startimg(mspannablestringbuilder, attributes, mimagegetter);
} else if (mtaghandler != null) {
mtaghandler.handletag(true, tag, mspannablestringbuilder, mreader);
}
}
private void handleendtag(string tag) {
if (tag.equalsignorecase("br")) {
handlebr(mspannablestringbuilder);
} else if (tag.equalsignorecase("p")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("div")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("em")) {
end(mspannablestringbuilder, bold.class, new stylespan(typeface.bold));
} else if (tag.equalsignorecase("b")) {
end(mspannablestringbuilder, bold.class, new stylespan(typeface.bold));
} else if (tag.equalsignorecase("strong")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("cite")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("dfn")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("i")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("big")) {
end(mspannablestringbuilder, big.class, new relativesizespan(1.25f));
} else if (tag.equalsignorecase("small")) {
end(mspannablestringbuilder, small.class, new relativesizespan(0.8f));
} else if (tag.equalsignorecase("font")) {
endfont(mspannablestringbuilder);
} else if (tag.equalsignorecase("blockquote")) {
handlep(mspannablestringbuilder);
end(mspannablestringbuilder, blockquote.class, new quotespan());
} else if (tag.equalsignorecase("tt")) {
end(mspannablestringbuilder, monospace.class,
new typefacespan("monospace"));
} else if (tag.equalsignorecase("a")) {
enda(mspannablestringbuilder);
} else if (tag.equalsignorecase("u")) {
end(mspannablestringbuilder, underline.class, new underlinespan());
} else if (tag.equalsignorecase("sup")) {
end(mspannablestringbuilder, super.class, new superscriptspan());
} else if (tag.equalsignorecase("sub")) {
end(mspannablestringbuilder, sub.class, new subscriptspan());
} else if (tag.length() == 2 &&
character.tolowercase(tag.charat(0)) == 'h' &&
tag.charat(1) >= '1' && tag.charat(1) <= '6') {
handlep(mspannablestringbuilder);
endheader(mspannablestringbuilder);
} else if (mtaghandler != null) {
mtaghandler.handletag(false, tag, mspannablestringbuilder, mreader);
}
}
通过源码可以看到,除了默认的一些标签,其还支持自定义标签;看下面代码:
else if (mtaghandler != null) {
mtaghandler.handletag(false, tag, mspannablestringbuilder, mreader);
}
系统会调用mtaghandler的handletag方法。所以,我们可以实现此接口,来解析自己定义的标签类型。
具体的,自己可以看一下下面实例:
package com.mxgsa.tvimg;
import org.xml.sax.xmlreader;
import android.content.context;
import android.content.intent;
import android.text.editable;
import android.text.html.taghandler;
import android.text.spanned;
import android.text.style.clickablespan;
import android.view.view;
import android.view.view.onclicklistener;
public class mxgsataghandler implements taghandler{
private int sindex = 0;
private int eindex=0;
private final context mcontext;
public mxgsataghandler(context context){
mcontext=context;
}
public void handletag(boolean opening, string tag, editable output, xmlreader xmlreader) {
// todo auto-generated method stub
if (tag.tolowercase().equals("mxgsa")) {
if (opening) {
sindex=output.length();
}else {
eindex=output.length();
output.setspan(new mxgsaspan(), sindex, eindex, spanned.span_exclusive_exclusive);
}
}
}
private class mxgsaspan extends clickablespan implements onclicklistener{
@override
public void onclick(view widget) {
// todo auto-generated method stub
//具体代码,可以是跳转页面,可以是弹出对话框,下面是跳转页面
mcontext.startactivity(new intent(mcontext,mainactivity.class));
}
}
}
调用页面:
package com.mxgsa.tvimg;
import android.app.activity;
import android.os.bundle;
import android.text.html;
import android.text.method.linkmovementmethod;
import android.widget.textview;
public class mxgsaactivity extends activity{
private textview tview;
@override
public void oncreate(bundle savedinstancestate) {
super.oncreate(savedinstancestate);
setcontentview(r.layout.mxgsa_activity);
findcontrol();
setdata();
}
private void findcontrol() {
tview = (textview) findviewbyid(r.id.tvimage);
}
private void setdata() {
// todo auto-generated method stub
final string stext = "测试自定义标签:<br><h1><mxgsa>测试自定义标签</mxgsa></h1>";
tview.settext(html.fromhtml(stext, null, new mxgsataghandler(this)));
tview.setclickable(true);
tview.setmovementmethod(linkmovementmethod.getinstance());
}
}
下篇将会讲带图片的html文本显示!待续 。。。。。
首先,说下textview到底支持那些标签呢,通过对源码的查看,发现textview可以解析一部分html标签,如:
复制代码 代码如下:
<a href="...">
<b>
<big>
<blockquote>
<br>
<cite>
<dfn>
<div align="...">
<em>
<font size="..." color="..." face="...">
<h1>
<h2>
<h3>
<h4>
<h5>
<h6>
<i>
<img src="...">
<p>
<small>
<strike>
<strong>
<sub>
<sup>
<tt>
<u>
大家想究其根本可以查看android.text.html源码,其中有一段这样写:
复制代码 代码如下:
private void handlestarttag(string tag, attributes attributes) {
if (tag.equalsignorecase("br")) {
// we don't need to handle this. tagsoup will ensure that there's a </br> for each <br>
// so we can safely emite the linebreaks when we handle the close tag.
} else if (tag.equalsignorecase("p")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("div")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("em")) {
start(mspannablestringbuilder, new bold());
} else if (tag.equalsignorecase("b")) {
start(mspannablestringbuilder, new bold());
} else if (tag.equalsignorecase("strong")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("cite")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("dfn")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("i")) {
start(mspannablestringbuilder, new italic());
} else if (tag.equalsignorecase("big")) {
start(mspannablestringbuilder, new big());
} else if (tag.equalsignorecase("small")) {
start(mspannablestringbuilder, new small());
} else if (tag.equalsignorecase("font")) {
startfont(mspannablestringbuilder, attributes);
} else if (tag.equalsignorecase("blockquote")) {
handlep(mspannablestringbuilder);
start(mspannablestringbuilder, new blockquote());
} else if (tag.equalsignorecase("tt")) {
start(mspannablestringbuilder, new monospace());
} else if (tag.equalsignorecase("a")) {
starta(mspannablestringbuilder, attributes);
} else if (tag.equalsignorecase("u")) {
start(mspannablestringbuilder, new underline());
} else if (tag.equalsignorecase("sup")) {
start(mspannablestringbuilder, new super());
} else if (tag.equalsignorecase("sub")) {
start(mspannablestringbuilder, new sub());
} else if (tag.length() == 2 &&
character.tolowercase(tag.charat(0)) == 'h' &&
tag.charat(1) >= '1' && tag.charat(1) <= '6') {
handlep(mspannablestringbuilder);
start(mspannablestringbuilder, new header(tag.charat(1) - '1'));
} else if (tag.equalsignorecase("img")) {
startimg(mspannablestringbuilder, attributes, mimagegetter);
} else if (mtaghandler != null) {
mtaghandler.handletag(true, tag, mspannablestringbuilder, mreader);
}
}
private void handleendtag(string tag) {
if (tag.equalsignorecase("br")) {
handlebr(mspannablestringbuilder);
} else if (tag.equalsignorecase("p")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("div")) {
handlep(mspannablestringbuilder);
} else if (tag.equalsignorecase("em")) {
end(mspannablestringbuilder, bold.class, new stylespan(typeface.bold));
} else if (tag.equalsignorecase("b")) {
end(mspannablestringbuilder, bold.class, new stylespan(typeface.bold));
} else if (tag.equalsignorecase("strong")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("cite")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("dfn")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("i")) {
end(mspannablestringbuilder, italic.class, new stylespan(typeface.italic));
} else if (tag.equalsignorecase("big")) {
end(mspannablestringbuilder, big.class, new relativesizespan(1.25f));
} else if (tag.equalsignorecase("small")) {
end(mspannablestringbuilder, small.class, new relativesizespan(0.8f));
} else if (tag.equalsignorecase("font")) {
endfont(mspannablestringbuilder);
} else if (tag.equalsignorecase("blockquote")) {
handlep(mspannablestringbuilder);
end(mspannablestringbuilder, blockquote.class, new quotespan());
} else if (tag.equalsignorecase("tt")) {
end(mspannablestringbuilder, monospace.class,
new typefacespan("monospace"));
} else if (tag.equalsignorecase("a")) {
enda(mspannablestringbuilder);
} else if (tag.equalsignorecase("u")) {
end(mspannablestringbuilder, underline.class, new underlinespan());
} else if (tag.equalsignorecase("sup")) {
end(mspannablestringbuilder, super.class, new superscriptspan());
} else if (tag.equalsignorecase("sub")) {
end(mspannablestringbuilder, sub.class, new subscriptspan());
} else if (tag.length() == 2 &&
character.tolowercase(tag.charat(0)) == 'h' &&
tag.charat(1) >= '1' && tag.charat(1) <= '6') {
handlep(mspannablestringbuilder);
endheader(mspannablestringbuilder);
} else if (mtaghandler != null) {
mtaghandler.handletag(false, tag, mspannablestringbuilder, mreader);
}
}
通过源码可以看到,除了默认的一些标签,其还支持自定义标签;看下面代码:
else if (mtaghandler != null) {
mtaghandler.handletag(false, tag, mspannablestringbuilder, mreader);
}
系统会调用mtaghandler的handletag方法。所以,我们可以实现此接口,来解析自己定义的标签类型。
具体的,自己可以看一下下面实例:
复制代码 代码如下:
package com.mxgsa.tvimg;
import org.xml.sax.xmlreader;
import android.content.context;
import android.content.intent;
import android.text.editable;
import android.text.html.taghandler;
import android.text.spanned;
import android.text.style.clickablespan;
import android.view.view;
import android.view.view.onclicklistener;
public class mxgsataghandler implements taghandler{
private int sindex = 0;
private int eindex=0;
private final context mcontext;
public mxgsataghandler(context context){
mcontext=context;
}
public void handletag(boolean opening, string tag, editable output, xmlreader xmlreader) {
// todo auto-generated method stub
if (tag.tolowercase().equals("mxgsa")) {
if (opening) {
sindex=output.length();
}else {
eindex=output.length();
output.setspan(new mxgsaspan(), sindex, eindex, spanned.span_exclusive_exclusive);
}
}
}
private class mxgsaspan extends clickablespan implements onclicklistener{
@override
public void onclick(view widget) {
// todo auto-generated method stub
//具体代码,可以是跳转页面,可以是弹出对话框,下面是跳转页面
mcontext.startactivity(new intent(mcontext,mainactivity.class));
}
}
}
调用页面:
复制代码 代码如下:
package com.mxgsa.tvimg;
import android.app.activity;
import android.os.bundle;
import android.text.html;
import android.text.method.linkmovementmethod;
import android.widget.textview;
public class mxgsaactivity extends activity{
private textview tview;
@override
public void oncreate(bundle savedinstancestate) {
super.oncreate(savedinstancestate);
setcontentview(r.layout.mxgsa_activity);
findcontrol();
setdata();
}
private void findcontrol() {
tview = (textview) findviewbyid(r.id.tvimage);
}
private void setdata() {
// todo auto-generated method stub
final string stext = "测试自定义标签:<br><h1><mxgsa>测试自定义标签</mxgsa></h1>";
tview.settext(html.fromhtml(stext, null, new mxgsataghandler(this)));
tview.setclickable(true);
tview.setmovementmethod(linkmovementmethod.getinstance());
}
}
下篇将会讲带图片的html文本显示!待续 。。。。。
推荐阅读
-
android textview 显示html方法解析
-
android+json+php+mysql实现用户反馈功能方法解析
-
Android编程实现压缩图片并加载显示的方法
-
Android中执行java命令的方法及java代码执行并解析shell命令
-
Android编程实现Gallery中每次滑动只显示一页的方法
-
Android 使用Pull方法解析XML文件的方法
-
Android自定义View设定到FrameLayout布局中实现多组件显示的方法 分享
-
Android编程简单解析JSON格式数据的方法示例
-
Android编程简易实现XML解析的方法详解
-
HTML5里的placeholder属性使用实例和美化显示效果的方法