Android自定义TextView实现文字图片居中显示的方法
作者:布丁西西 发布时间:2023-07-21 12:46:00
最近有个需求是这样的,人民币的符号“¥”因为安卓手机系统的不一致导致符号不是完全一样,所以用美工的给的图片代替,考虑到用的地方比较多,所以想着写一个继承于线性布局的组合控件,后来一想,安卓中不是有TextView吗,这个自带图片的控件,后来写了个demo,因为我是用的MatchParent,导致问题出现,人民币符号不是和文字一样的居中,因此才有了这篇博文,让我们来自定义TextView吧,这个场景用的比较多。
分析下TextView的源码
我们先来分析下TextView的源码,因为TextView有上下左右四个方向的图片,上下咱就先不考虑了,因为一般来说图片垂直居中是没有问题的,我们就只处理这个left,和right方向上的图片, 我们直接看TextView的ondraw方法,因为TextView 也是继承自View,所有的绘制都将会在这里操作
<span style="font-size:18px;">int vspace = bottom - top - compoundPaddingBottom - compoundPaddingTop;
int hspace = right - left - compoundPaddingRight - compoundPaddingLeft;
// IMPORTANT: The coordinates computed are also used in invalidateDrawable()
// Make sure to update invalidateDrawable() when changing this code.
if (dr.mShowing[Drawables.LEFT] != null) {
canvas.save();
canvas.translate(scrollX + mPaddingLeft + leftOffset,
scrollY + compoundPaddingTop +
(vspace - dr.mDrawableHeightLeft) / 2);
dr.mShowing[Drawables.LEFT].draw(canvas);
canvas.restore();
}
// IMPORTANT: The coordinates computed are also used in invalidateDrawable()
// Make sure to update invalidateDrawable() when changing this code.
if (dr.mShowing[Drawables.RIGHT] != null) {
canvas.save();
canvas.translate(scrollX + right - left - mPaddingRight
- dr.mDrawableSizeRight - rightOffset,
scrollY + compoundPaddingTop + (vspace - dr.mDrawableHeightRight) / 2);
dr.mShowing[Drawables.RIGHT].draw(canvas);
canvas.restore();
}</span>
从上面可以看到有个canvas.translate方法,大概意思是,save后,将画布向X轴和Y轴分别平移了scrollX ..和scrollY,平移后,将left方向的图片绘制上去,最后restore还原到上个画布中,Right同理。
那这样,咱基本上就明白原理,TextView的四个方向都是通过Canvas的translate来绘制到文字的上下左右了,那咱们就只改这个scrollX 和 scrollY就可以实现咱的需求了吧。
具体实现
1.下面写有注释,不是特别麻烦,适配drawableLeft 和 drawableRight图片,PS,xml中不要设置Gravity,这样就可以居中了,代码如下:
<span style="font-size:18px;">package com.chaoxing.email.view;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.view.Gravity;
import android.widget.TextView;
/**
* use in xml
* use in code
*/
public class EmailCenterTextView extends TextView {
public EmailCenterTextView(Context context) {
super(context);
}
public EmailCenterTextView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public EmailCenterTextView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
@Override
protected void onDraw(Canvas canvas) {
Drawable[] drawables = getCompoundDrawables();
if (null != drawables) {
Drawable drawableLeft = drawables[0];
Drawable drawableRight = drawables[2];
float textWidth = getPaint().measureText(getText().toString());
if (null != drawableLeft) {
setGravity(Gravity.START | Gravity.CENTER_VERTICAL);
float contentWidth = textWidth + getCompoundDrawablePadding() + drawableLeft.getIntrinsicWidth();
if (getWidth() - contentWidth > 0) {
canvas.translate((getWidth() - contentWidth - getPaddingRight() - getPaddingLeft()) / 2, 0);
}
}
if (null != drawableRight) {
setGravity(Gravity.END | Gravity.CENTER_VERTICAL);
float contentWidth = textWidth + getCompoundDrawablePadding() + drawableRight.getIntrinsicWidth();
if (getWidth() - contentWidth > 0) {
canvas.translate(-(getWidth() - contentWidth - getPaddingRight() - getPaddingLeft()) / 2, 0);
}
}
if (null == drawableRight && null == drawableLeft) {
setGravity(Gravity.CENTER);
}
}
super.onDraw(canvas);
}
}</span>
更新效果图(因为之前有看到网友回复,最近又用到了再更新下这个博客)
title是用的就是EmailCenterTextView,那个箭头上下的就是设置的drawableRight,演示的未读和垃圾箱EmailCenterTextView没有设置图片
来源:http://blog.csdn.net/shenshibaoma/article/details/53405524


猜你喜欢
- 文章来源:csdn 作者:wangfengsdu经常听到回调函数(callback function)这个概念, 所谓回调函数,就是指这个函
- 对于服务器端开发人员而言,调用第三方接口获取数据,将其“代理”转化并返给客户端几乎是家常便
- Java怎么自动添加重写的toString方法,这里我们将给大家介绍详细的解决方法。首先,添加一个任意的类,具体的类型没有要求,然后在主程序
- /* * 绘制0°到360°的正弦曲线 * 分两种情形,y>0和y<=0进行绘制 * 每种情形中要
- IOS与网页JS交互随着移动APP的快速迭代开发趋势,越来越多的APP中嵌入了html网页,但在一些大中型APP中,尤其是电商类
- 我们经常用简单数据类型,比如int作为泛型Dictionary<TKey,TValue>的key,但有时候我们希望自定义数据类型
- 日志是非常重要的,虽然他不会以需求功能提来,但也不会体现在产品方案中。但是,它在系统项目中却占有巨大的地位。为了保证服务的高可用,发现问题一
- SpringCloud feign无法注入接口接口:package cn.mn.app.service;import org.springf
- 一、概要线程是操作系统中独立的个体,但这些个体如果不经过特殊的处理就不能成为一个整体,线程间的通信就是成为整体的必用方案之一。可以说,使线程
- 目录QR二维码QR二维码格式QR二维码结构APIQRCodeDetector类结构检测QR二维码识别QR二维码检测并识别QR二维码操作结果源
- 环境配置Jdk1.8 + Tomcat8.5 + mysql + Eclispe(IntelliJ IDEA,Eclispe,MyEclis
- 本文实例为大家分享了Spring MVC接口防数据篡改和重复提交的具体代码,供大家参考,具体内容如下一、自定义一个注解,此注解可以使用在方法
- 引言青蛙见了蜈蚣,好奇地问:"蜈蚣大哥,我很好奇,你那么多条腿,走路的时候先迈哪一条啊?"蜈蚣听后说:"青蛙老
- 本文实例为大家分享了Java文件操作的具体代码,供大家参考,具体内容如下简介本程序主要采用了FileInputStream和FileOutp
- 1 需求描述我们现在要干一个什么事情呢,我们要在浏览器输入一个请求地址,然后我们的后端就给我返回一个User对象即可,并且我希望以Json的
- 本文实例为大家分享了Android实现悬浮窗效果的具体代码,供大家参考,具体内容如下一、权限:<uses-permission and
- 服务器端代码:import java.io.BufferedReader; import java.io.InputStreamR
- 本文实例主要进行java Timer(定时调用、固定时间执行)测试,具体实现代码如下。测试1当任务执行时间小于重复执行的间隔时间代码:pub
- 如下所示:1 需要在project structure中的Artifacts下的项目classes文件夹下添加Directory Conte
- 前言Android 从 4.0 开始就提供了手机录屏方法,但是需要 root 权限,比较麻烦不容易实现。但是从 5.0 开始,系统提供给了