1. <ul id="0c1fb"></ul>

      <noscript id="0c1fb"><video id="0c1fb"></video></noscript>
      <noscript id="0c1fb"><listing id="0c1fb"><thead id="0c1fb"></thead></listing></noscript>

      99热在线精品一区二区三区_国产伦精品一区二区三区女破破_亚洲一区二区三区无码_精品国产欧美日韩另类一区

      RELATEED CONSULTING
      相關(guān)咨詢
      選擇下列產(chǎn)品馬上在線溝通
      服務(wù)時(shí)間:8:30-17:00
      你可能遇到了下面的問(wèn)題
      關(guān)閉右側(cè)工具欄

      新聞中心

      這里有您想知道的互聯(lián)網(wǎng)營(yíng)銷解決方案
      如何在Android中使用CanvasdrawText屬性實(shí)現(xiàn)文字居中

      這篇文章主要為大家詳細(xì)介紹了如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,發(fā)現(xiàn)的小伙伴們可以參考一下:

      思南網(wǎng)站建設(shè)公司創(chuàng)新互聯(lián),思南網(wǎng)站設(shè)計(jì)制作,有大型網(wǎng)站制作公司豐富經(jīng)驗(yàn)。已為思南近千家提供企業(yè)網(wǎng)站建設(shè)服務(wù)。企業(yè)網(wǎng)站搭建\成都外貿(mào)網(wǎng)站建設(shè)公司要多少錢(qián),請(qǐng)找那個(gè)售后服務(wù)好的思南做網(wǎng)站的公司定做!

      Android是什么

      Android是一種基于Linux內(nèi)核的自由及開(kāi)放源代碼的操作系統(tǒng),主要使用于移動(dòng)設(shè)備,如智能手機(jī)和平板電腦,由美國(guó)Google公司和開(kāi)放手機(jī)聯(lián)盟領(lǐng)導(dǎo)及開(kāi)發(fā)。

      首先把坐標(biāo)原點(diǎn)移動(dòng)到控件中心(默認(rèn)坐標(biāo)原點(diǎn)在屏幕左上角),這樣看起來(lái)比較直觀一些,然后繪制x、y軸,此時(shí)原點(diǎn)向上y為負(fù),向下y為正,向左x為負(fù),向右x為正,以(0,0)坐標(biāo)開(kāi)始繪制一段文本:

      @Override
      public void draw(Canvas canvas) {
       super.draw(canvas);
       // 將坐標(biāo)原點(diǎn)移到控件中心
       canvas.translate(getWidth() / 2, getHeight() / 2);
       // x軸
       canvas.drawLine(-getWidth() / 2, 0, getWidth() / 2, 0, paint);
       // y軸
       canvas.drawLine(0, -getHeight() / 2, 0, getHeight() / 2, paint);
      
       // 繪制文字
       paint.setTextSize(sp2px(50));
       canvas.drawText("YangLe", 0, 0, paint);
      }

      看下繪制的文本:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      繪制文本

      咦,為什么繪制的文本在第一象限,y坐標(biāo)不是指定的0嗎,為什么文本沒(méi)有在x軸的上面或下面,而是穿過(guò)了x軸,帶著這些疑問(wèn)繼續(xù)往下看:

      首先看一個(gè)重要的類:

      public static class FontMetrics {
       /**
       * The maximum distance above the baseline for the tallest glyph in
       * the font at a given text size.
       */
       public float top;
       /**
       * The recommended distance above the baseline for singled spaced text.
       */
       public float ascent;
       /**
       * The recommended distance below the baseline for singled spaced text.
       */
       public float descent;
       /**
       * The maximum distance below the baseline for the lowest glyph in
       * the font at a given text size.
       */
       public float bottom;
       /**
       * The recommended additional space to add between lines of text.
       */
       public float leading;
      }

      FontMetrics類是Paint的一個(gè)內(nèi)部類,主要定義了繪制文本時(shí)的一些關(guān)鍵坐標(biāo)位置,看下這些值都代表什么:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      關(guān)鍵坐標(biāo)

      看圖說(shuō)話:

      • top:從基線(x軸)向上繪制區(qū)域的最高點(diǎn),此值為負(fù)值

      • ascent:?jiǎn)涡形谋荆瑥幕€(x軸)向上繪制的推薦最高點(diǎn),此值為負(fù)值

      • baseline:基線,此值為0

      • descent:?jiǎn)涡形谋荆瑥幕€(x軸)向下繪制的推薦最低點(diǎn),此值為正值

      • bottom:從基線(x軸)向下繪制區(qū)域的最低點(diǎn),此值為正值

      • leading:推薦的額外行距,一般為0

      下面再來(lái)看看drawText這個(gè)方法:

      /**
       * Draw the text, with origin at (x,y), using the specified paint. The origin is interpreted
       * based on the Align setting in the paint.
       *
       * @param text The text to be drawn
       * @param x The x-coordinate of the origin of the text being drawn
       * @param y The y-coordinate of the baseline of the text being drawn
       * @param paint The paint used for the text (e.g. color, size, style)
       */
      public void drawText(@NonNull String text, float x, float y, @NonNull Paint paint) {
       super.drawText(text, x, y, paint);
      }

      重點(diǎn)看下x、y參數(shù)的含義:

      • x:繪制文本的起始x坐標(biāo)

      • y:繪制文本的baseline在y軸方向的位置

      有點(diǎn)難理解,舉個(gè)栗子,上文中的x、y參數(shù)傳的是(0,0),此時(shí)的baseline正好是坐標(biāo)系中x軸,就相當(dāng)于從y軸開(kāi)始向右繪制,以x軸作為文本的baseline進(jìn)行繪制。

      如果參數(shù)傳(0,10),此時(shí)繪制文本的baseline從x軸開(kāi)始向下移動(dòng)10px,也就是以y10作為文本的baseline進(jìn)行繪制,y10就是繪制文本的baseline在y軸方向的位置。

      注意:baseline是繪制文本的基線,相對(duì)于繪制文本區(qū)域來(lái)說(shuō),相當(dāng)于x軸,向上為負(fù)(top、ascent),向下為正(descent、bottom),但是這個(gè)x軸并不是控件的x軸,切記切記!!!

      還記得我們?cè)谏衔闹刑岢龅囊蓡?wèn)嗎,這下可以解釋了:

      為什么繪制的文本在第一象限?

      因?yàn)槲覀儼炎鴺?biāo)原點(diǎn)移到了控件中心,文本的baseline正好為x軸,top、ascent值為負(fù),所以繪制的文本在第一象限。

      y坐標(biāo)不是指定的0嗎,為什么文本沒(méi)有在x軸的上面或下面,而是穿過(guò)了x軸?

      drawText方法默認(rèn)x軸方向是從左到右繪制的,y軸方向是從baseline為基準(zhǔn)繪制的,文中的baseline正好為x軸,以baseline為基準(zhǔn)繪制文本向下還有一段距離,所以文本穿過(guò)了x軸。

      3.繪制居中的文本

      在上文中,我們學(xué)習(xí)了如何繪制一段文本,以及其中參數(shù)和坐標(biāo)的含義,接下來(lái)進(jìn)入正題,看下如何才能繪制居中的文本。

      首先看一張圖,此時(shí)文本的baseline正好為x軸,如果想要文本居中顯示的話,就需要先計(jì)算文本的寬度和高度:

      • 寬度:調(diào)用Paint的measureText方法就可以獲得文本的寬度

      • 高度:文本的高度就是實(shí)際繪制區(qū)域的高度,可以用(fontMetrics.descent - fontMetrics.ascent)獲取,因?yàn)閍scent為負(fù)數(shù),所以最終算出來(lái)的是兩者的和

      現(xiàn)在有了寬度,把繪制文本的x坐標(biāo)向左移動(dòng)(寬度 / 2)就可以水平居中,但是垂直方向就不能這么干了,我們要將文本向下移動(dòng)baseline到文本中心的距離,也就是(高度 / 2 - fontMetrics.descent),如下圖所示:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      計(jì)算baseLineY

      現(xiàn)在的公式為:

      float baseLineY
      = (fontMetrics.descent - fontMetrics.ascent) / 2 - fontMetrics.descent;
      = -fontMetrics.ascent / 2 - fontMetrics.descent / 2;
      = -(fontMetrics.ascent + fontMetrics.descent) / 2;
      = Math.abs(fontMetrics.ascent + fontMetrics.descent) / 2;

      Paint中也有獲取ascent和descent值的方法,所以公式最終為:

      float baseLineY = Math.abs(paint.ascent() + paint.descent()) / 2;

      注意:此公式是相對(duì)于坐標(biāo)原點(diǎn)在控件中心來(lái)計(jì)算的,如果坐標(biāo)原點(diǎn)在左上角,baseLineY需要加上控件高度的一半。

      float baseLineY = height / 2 + Math.abs(paint.ascent() + paint.descent()) / 2;

      看下代碼:

      @Override
      public void draw(Canvas canvas) {
       super.draw(canvas);
       // 將坐標(biāo)原點(diǎn)移到控件中心
       canvas.translate(getWidth() / 2, getHeight() / 2);
       // x軸
       canvas.drawLine(-getWidth() / 2, 0, getWidth() / 2, 0, paint);
       // y軸
       canvas.drawLine(0, -getHeight() / 2, 0, getHeight() / 2, paint);
      
       // 繪制居中文字
       paint.setTextSize(sp2px(50));
       paint.setColor(Color.GRAY);
       // 文字寬
       float textWidth = paint.measureText("YangLe'Blog");
       // 文字baseline在y軸方向的位置
       float baseLineY = Math.abs(paint.ascent() + paint.descent()) / 2;
       canvas.drawText("YangLe'Blog", -textWidth / 2, baseLineY, paint);
      }

      看下居中了嗎:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      繪制居中文本

      大功告成!

      4.繪制多行居中的文本

      注意:drawText方法不支持繪制多行文本

      4.1 方式一

      使用支持自動(dòng)換行的StaticLayout:

      /**
       * 繪制多行居中文本(方式1)
       *
       * @param canvas 畫(huà)布
       */
      private void drawCenterMultiText1(Canvas canvas) {
       String text = "ABC";
      
       // 畫(huà)筆
       TextPaint textPaint = new TextPaint();
       textPaint.setAntiAlias(true);
       textPaint.setColor(Color.GRAY);
      
       // 設(shè)置寬度超過(guò)50dp時(shí)換行
       StaticLayout staticLayout = new StaticLayout(text, textPaint, dp2px(50),
        Layout.Alignment.ALIGN_CENTER, 1f, 0f, false);
       canvas.save();
       // StaticLayout默認(rèn)從(0,0)點(diǎn)開(kāi)始繪制
       // 如果需要調(diào)整位置,只能在繪制之前移動(dòng)Canvas的起始坐標(biāo)
       canvas.translate(-staticLayout.getWidth() / 2, -staticLayout.getHeight() / 2);
       staticLayout.draw(canvas);
       canvas.restore();
      }

      看下StaticLayout的構(gòu)造方法參數(shù)含義:

      public StaticLayout(CharSequence source, TextPaint paint, int width, Alignment align, 
         float spacingmult, float spacingadd, boolean includepad) {
       this(source, 0, source.length(), paint, width, align, spacingmult, spacingadd, includepad);
      }
      • source:需要分行的文本

      • paint:畫(huà)筆對(duì)象

      • width:layout的寬度,文本超出寬度時(shí)自動(dòng)換行

      • align:layout的對(duì)其方式

      • spacingmult:相對(duì)行間距,相對(duì)字體大小,1f表示行間距為1倍的字體高度

      • spacingadd:基礎(chǔ)行距偏移值,實(shí)際行間距等于(spacingmult + spacingadd)

      • includepad:參數(shù)未知

      看下效果:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      StaticLayout

      使用StaticLayout,每行設(shè)置的寬度是相同的,當(dāng)需求為每行顯示不同長(zhǎng)度的文本時(shí),這種方式就不能使用了,別擔(dān)心,接著來(lái)看下第二種方式。

      4.2 方式二

      使用循環(huán)drawText的方式進(jìn)行繪制,看圖說(shuō)話:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      計(jì)算baseLineY

      現(xiàn)在需要繪制A、B、C三行文本,紅色A代表每行文本默認(rèn)的繪制位置,綠色的線代表每行文本的baseline,x軸為紅色A的baseline,現(xiàn)在分為三種情況:

      • 文本在x軸上方:紅色A的baseline向上移動(dòng)a距離,總高度的/2 - 文本的top值(絕對(duì)值)

      • 文本在x軸中間:紅色A的baseline向下移動(dòng)b距離,計(jì)算公式請(qǐng)參考單行文本居中公式

      • 文本在x軸下方:紅色A的baseline向下移動(dòng)c距離,總高度的/2 - 文本的bottom值(絕對(duì)值)

      看下代碼:

      /**
       * 繪制多行居中文本(方式2)
       *
       * @param canvas 畫(huà)布
       */
      private void drawCenterMultiText2(Canvas canvas) {
       String[] texts = {"A", "B", "C"};
      
       Paint.FontMetrics fontMetrics = paint.getFontMetrics();
       // top絕對(duì)值
       float top = Math.abs(fontMetrics.top);
       // ascent絕對(duì)值
       float ascent = Math.abs(fontMetrics.ascent);
       // descent,正值
       float descent = fontMetrics.descent;
       // bottom,正值
       float bottom = fontMetrics.bottom;
       // 行數(shù)
       int textLines = texts.length;
       // 文本高度
       float textHeight = top + bottom;
       // 文本總高度
       float textTotalHeight = textHeight * textLines;
       // 基數(shù)
       float basePosition = (textLines - 1) / 2f;
      
       for (int i = 0; i < textLines; i++) {
        // 文本寬度
        float textWidth = paint.measureText(texts[i]);
        // 文本baseline在y軸方向的位置
        float baselineY;
      
        if (i < basePosition) {
         // x軸上,值為負(fù)
         // 總高度的/2 - 已繪制的文本高度 - 文本的top值(絕對(duì)值)
         baselineY = -(textTotalHeight / 2 - textHeight * i - top);
      
        } else if (i > basePosition) {
         // x軸下,值為正
         // 總高度的/2 - 未繪制的文本高度 - 文本的bottom值(絕對(duì)值)
         baselineY = textTotalHeight / 2 - textHeight * (textLines - i - 1) - bottom;
      
        } else {
         // x軸中,值為正
         // 計(jì)算公式請(qǐng)參考單行文本居中公式
         baselineY = (ascent - descent) / 2;
        }
      
        canvas.drawText(texts[i], -textWidth / 2, baselineY, paint);
       }
      }

      對(duì)照上圖再看代碼就很好理解了,覺(jué)得代碼中的公式還有可以優(yōu)化的地方,如果你有好的方法,可以留言告訴我哈。
      再看下中文版的多行文本:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      多行居中文本

      TextAlign

      Paint的TextAlign屬性決定了繪制文本相對(duì)于drawText方法中x參數(shù)的相對(duì)位置。
      舉個(gè)栗子:

      • Paint.Align.LEFT:默認(rèn)屬性,x坐標(biāo)為繪制文本的最左側(cè)坐標(biāo)

      • Paint.Align.CENTER:x坐標(biāo)為繪制文本的水平中心坐標(biāo)

      • Paint.Align.RIGHT:x坐標(biāo)為繪制文本的最右側(cè)坐標(biāo)

      看圖理解下:

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中

      Paint.Align.LEFT

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中
      Paint.Align.CENTER

      如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中
      Paint.Align.RIGHT

      文本居中的公式

      坐標(biāo)原點(diǎn)在控件中心:

      float baseLineY = Math.abs(paint.ascent() + paint.descent()) / 2;

      坐標(biāo)原點(diǎn)在控件左上角:

      float baseLineY = height / 2 + Math.abs(paint.ascent() + paint.descent()) / 2;

      以上就是創(chuàng)新互聯(lián)小編為大家收集整理的如何在Android中使用Canvas drawText屬性實(shí)現(xiàn)文字居中,如何覺(jué)得創(chuàng)新互聯(lián)網(wǎng)站的內(nèi)容還不錯(cuò),歡迎將創(chuàng)新互聯(lián)網(wǎng)站推薦給身邊好友。


      文章名稱:如何在Android中使用CanvasdrawText屬性實(shí)現(xiàn)文字居中
      網(wǎng)站URL:http://ef60e0e.cn/article/gsjgog.html
      99热在线精品一区二区三区_国产伦精品一区二区三区女破破_亚洲一区二区三区无码_精品国产欧美日韩另类一区
      1. <ul id="0c1fb"></ul>

        <noscript id="0c1fb"><video id="0c1fb"></video></noscript>
        <noscript id="0c1fb"><listing id="0c1fb"><thead id="0c1fb"></thead></listing></noscript>

        蒙阴县| 浑源县| 黄陵县| 禹城市| 玉屏| 凤山市| 定南县| 神农架林区| 招远市| 淳安县| 灌阳县| 威信县| 斗六市| 文山县| 修文县| 翁牛特旗| 三亚市| 武城县| 离岛区| 宣恩县| 乡宁县| 会宁县| 芜湖市| 许昌市| 张北县| 建昌县| 剑阁县| 普洱| 长岛县| 安岳县| 华容县| 浙江省| 渭源县| 德惠市| 陆丰市| 平利县| 霍城县| 西贡区| 赤城县| 高雄县| 孝义市|