Android UI 之居中绘制文本内容的正确方法——实现自定义一个TextView

本文介绍了在Android中自定义TextView实现文本水平和垂直居中的方法,涉及到Canvas、Paint和FontMetrics的使用。通过计算文本与控件的尺寸关系,确保文本在控件内正确居中显示,同时提供了代码示例和实际效果对比。
摘要由CSDN通过智能技术生成

    我们在自定义一个控件的时候,有时候会需要自己来绘制一些文本内容,这样就自然而然遇到确定文本的方位的问题,比如文本需要水平居中,垂直居中,居左,居右,左上。。。等等很多情况。其中最常见的就是文本位于控件的正中央了。

    既然是文本居中,那就要让文本水平居中,并且同时垂直居中,我们分开来做。

    水平居中的思路很简单,一种是得到控件的宽度A,使得文本的中心位置x坐标=A/2就可以了。还有一种思路是我们得到控件的宽度A,然后测量出要绘制的文本的宽度B,然后使得文本的左端x坐标=(A-B)/2。

    相对复杂一点的实现文本垂直居中,我们需要用到FontMetrics,这里涉及到几个概念,分别是文本的top,bottom,ascent,descent,baseline。看下面的图:


    我们在画布中绘制文本的时候,会调用Canvas.drawText(String text, float x, float y, Paint paint)这个方法,其中y的坐标就是上图中baseline的y坐标,所以,如果我们只是简单地把drawText方法中的y设置为控件高度的1/2是不准确的,如果这样做的话会发现文本整体是位于画布的上半部分的,因为baseline下面的文本部分是很小的。

    正确的做法是通过一些合理的换算使得文本的y坐标(baseline的y坐标)位于控件的下半部分区域。下面是我自己通过计算和测试得到的准确换算关系:

float textCenterVerticalBaselineY = viewHeight / 2 - fm.descent + (fm.bottom - fm.top) / 2;
    textCenterVerticalBaselineY就是绘制文本时候的y坐标,viewHeight是控件的高度。其实这个换算关系也不难理解,viewHeight/2-fm.descent的意思是将整个文字区域抬高到控件的1/2,然后我们再加上(fm.bottom - fm.top) / 2的意思就是将文本下沉文本top到bottom长度的一半,从而实现文本垂直居中的目的。

    有的人或许会问,为什么最后加上的是bottom到top距离的一半而不是descent到ascent的一半呢?其实这个是我测试的结果,我发现如果用bottom到top距离的一半来设置文本垂直居中,和系统控件TextView的文本居中效果是一样的,我们来看下面的效果:

    首先是我们使用(fm.bottom - fm.top) / 2:


    然后是使用(fm.descent - fm.ascent) / 2:

  • 7
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值