起源

图片和文字混合展示,比如这么个需求,需要在每段文字的左边要有一个小圆点,(小圆点符号在android系统中并不支持)。
先用TextView的setDrawableLeft,

嗯,达到要求,那么换个行看看。

喔,糟糕,这个setDrawableLeft是为整个TextView服务的,而不只是为其中某一行准备的哟。

SpannableStringBuilder

为了满足上面说到的需求,使用SpannableStringBuilder的setSpan方法可以将一串文字中的指定字符替换为图片。我先继承SpannableStringBuilder利用setSpan封装出一个appendSpan方法出来。

public class MTSpannableStringBuilder extends SpannableStringBuilder {public MTSpannableStringBuilder appendSpan(String text, Object what, int flags) {int start = length();append(text);setSpan(what, start, length(), flags);return this;}
}
Drawable drawable = getResources().getDrawable(R.drawable.train_round);drawable.setBounds(0, 0, drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight());//要让图片替代指定的文字就要用ImageSpanImageSpan span = new ImageSpan(drawable,ImageSpan.ALIGN_BASELINE);MTSpannableStringBuilder builder = new MTSpannableStringBuilder();builder.appendSpan("ha",span, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);TextView tt = (TextView) findViewById(R.id.spanableText);builder.append("hahahahahahahhahahahahahahahahahahahahahahahahahaahhahahahahlasjljfljasdfasdfsdfadfasdfasdffsfsfsf");tt.setText(builder);

最终的结果是:

哈哈,似乎快要接近了,但是圆点并不能垂直方向居中。希望能够将图片居中,需要经历:
* 将图片”拔高”到居中位置,
* 居中位置怎么计算

因为这里ImageSpan是”替换”TextView中文字内容,所以其理应和文字内容的位置保持对齐。请参考下篇:
【Android UI】TextView的垂直方向概念之top,bottom,ascent,descent,baseline

如下代码中onDraw先将图片和文字内容的bottom对齐,然后再将图片和文字内容居中对齐,对齐的方式就是通过减去[(fontAscent-fontDecent) - drawableHeight]/2。

public class CenteredImageSpan extends ImageSpan {private WeakReference<Drawable> mDrawableRef;public CenteredImageSpan(Context context, final int drawableRes) {super(context, drawableRes);}@Overridepublic int getSize(Paint paint, CharSequence text,int start, int end,Paint.FontMetricsInt fm) {Drawable d = getCachedDrawable();Rect rect = d.getBounds();if (fm != null) {Paint.FontMetricsInt pfm = paint.getFontMetricsInt();// keep it the same as paint's fmfm.ascent = pfm.ascent;fm.descent = pfm.descent;fm.top = pfm.top;fm.bottom = pfm.bottom;}return rect.right;}@Overridepublic void draw(@NonNull Canvas canvas, CharSequence text,int start, int end, float x,int top, int y, int bottom, @NonNull Paint paint) {Drawable b = getCachedDrawable();canvas.save();int drawableHeight = b.getIntrinsicHeight();int fontAscent = paint.getFontMetricsInt().ascent;int fontDescent = paint.getFontMetricsInt().descent;int transY = bottom - b.getBounds().bottom +  // align bottom to bottom(drawableHeight - fontDescent + fontAscent) / 2;  // align center to centercanvas.translate(x, transY);b.draw(canvas);canvas.restore();}// Redefined locally because it is a private member from DynamicDrawableSpanprivate Drawable getCachedDrawable() {WeakReference<Drawable> wr = mDrawableRef;Drawable d = null;if (wr != null) {d = wr.get();}if (d == null) {d = getDrawable();mDrawableRef = new WeakReference<>(d);}return d;}
}

然后得到如下令人满意的结果:

【Android UI】图片 + 文字展示by SpannableStringBuilder相关推荐

  1. android动态设置文本居中显示图片,Android DrawableTextView图片文字居中显示实例

    在我们开发中,TextView设置Android:drawableLeft一定使用的非常多,但Drawable和Text同时居中显示可能不好控制,有没有好的办法解决呢? 小编的方案是通过自定义Text ...

  2. android自定义图片+文字控件四种实现方法,Android自定义“图片+文字”控件四种实现方法之 二--------个人最推荐的一种...

    http://blog.csdn.net/yanzi1225627/article/details/8633872 第二种方法也要新建一个图片+文字的xml布局文件,然后写一个类继承自LinearLa ...

  3. android 按钮 图片文字居中显示,[Android]Android 布局中如何让图片和文字居中显示?...

    图片文字居中显示 **①组件TextView的属性 drawableTop ``` 块内或者行内图片与文字居中对齐最靠谱的方式! 做图片与文字在一行的按钮时候最常用到,总结了一个靠谱的方法,终于可以完 ...

  4. dp和px,那些不得不吐槽的故事——Android平台图片文字元素单位浅析 (转)

    一个优秀的手机软件,不仅要有精巧的功能,流畅的速度,让人赏心悦目的UI也往往是用户选择的重要理由.作为移动产品的PM,也需要了解一些在UI设计中的基本知识. 1. px和pt,一对好伙伴 在视觉设计中 ...

  5. android 图片文字布局,Android自定义控件图片+文字布局

    本来想用Tabrow来布局一组上面是图片下面是文字说明的控件,可是发现Tabrow不像想象的那样简易,并且这几组之间的控件距离很差把握,在网上找了两种方法以供参照.html 方法1.利用RadioBu ...

  6. Android自定义控件图片+文字布局

    原本想用Tabrow来布局一组上面是图片下面是文字说明的控件,但是发现Tabrow不像想象的那样简易,而且这几组之间的控件距离不好把握,在网上找了两种方法以供参照. 方法一.利用RadioButton ...

  7. unity调用 Android 分享图片文字 方法 不需要第三方sdk 兼容android7.0+

    直接说方法把,在Android Studio中 新建一个工程,新建时选择Add No Activity,包名跟unity中设置的一样比如这里用 come.demo.share 在res目录下新建个文件 ...

  8. [Android]使用ViewPager实现图片滑动展示

    在淘宝等电商的APP首页经常能看到大幅的广告位,通常有多幅经常更新的图片用于展示促销信息,如下图所示: 通常会自动滚动,也可以根据手势滑动.我没有研究过人家的APP是通过什么实现的,可能有第三方已经封 ...

  9. Android 图片文字识别DEMO(基于百度OCR)

    前言   OCR 是 Optical Character Recognition 的缩写,翻译为光学字符识别,指的是针对印刷体字符,采用光学的方式将纸质文档中的文字转换成为黑白点阵的图像文件,通过识别 ...

最新文章

  1. python多功能电子钟_python gui - PyQt4 精彩实例分析之电子钟
  2. NET使用了UpdatePanel后如何弹出对话框!
  3. 深度学习用于图片的分类和检测总结
  4. hspice2016安装教程
  5. pythonfor输入多个数字_我一天学会了python最基础的编程
  6. 如何让智能客服成为企业的生产力工具?
  7. debian常用工具所在的包
  8. 第三次学JAVA再学不好就吃翔(part82)--泛型
  9. Fiddler 十分钟最全使用介绍
  10. 算法前戏 递归 二分查找 列表查找
  11. 安装php 端口被占用,安装phpstudy,APMServ启动服务提示80端口被占用
  12. kesioncms ajax分页,改进KesionCMS V9.0x SQL标签分页支持嵌套
  13. VC++6遇到的问题(持续更新)
  14. java - day006 - 构造方法
  15. 安卓自定义控件,自行绘制文字
  16. 基于STM32C8T6F103实现串口通信
  17. 如何制作 Windows 系统主题?
  18. python烤地瓜实例(深入理解面向对象编程)
  19. pycharm破解补丁激活
  20. 一对一直播,一对一脚本开发行业的下一个风口将在5G普及后到来!

热门文章

  1. vue入门总结(3)
  2. mac下常用快捷键整理
  3. Redis工具类的封装
  4. st2045 漏洞反弹root shell
  5. BIO与NIO、AIO的区别(这个容易理解)
  6. OssImport系列之四——最佳实践
  7. 響應式設計中百分比 % 的問題
  8. Oracle获取LOB长度的两种方法效率对比
  9. 推荐12个Android开发源码(包括应用、游戏、效果等等)
  10. 上班族漫画(转收藏)