在画布上绘制曲线文本,在android中使用不同长度的文本

时间:2017-04-18 05:54:47

标签: android canvas

我需要实现在画布上的圆形路径上绘制文本的弯曲文本。

使用

绘制圆形路径
 canvas.drawTextOnPath(QUOTE, circle, 485, 20, tPaint);

但它不适用于不同长度的文本。

以下是我的班级在canavs上绘制圆形文字。

 public class CircularTextVie extends View {
        private  String QUOTE = "";
        private Path circle;
        private Paint cPaint;
        private Paint tPaint;

        public CircularTextVie(Context context) {
            super(context);
            circle = new Path();
            cPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
            cPaint.setStyle(Paint.Style.STROKE);
            cPaint.setColor(Color.LTGRAY);
            cPaint.setStrokeWidth(3);
            tPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
            tPaint.setStyle(Paint.Style.FILL_AND_STROKE);
            tPaint.setColor(Color.BLACK);
        }


        @Override
        protected void onDraw(Canvas canvas) {
            canvas.restore();
            int xPos =  (canvas.getWidth() /3);
            int yPos = (int) ((canvas.getHeight() / 3) - ((tPaint.descent() + tPaint.ascent()) / 3)) ;
            circle.addCircle(xPos, yPos, 150, Path.Direction.CW);


      canvas.drawTextOnPath(QUOTE, circle, 485, 20, tPaint);
            QUOTE="";

        }


    public void SetText(String text) {
       this.QUOTE = text;

    }

    public void SetTypeFace(Typeface face) {
       cPaint.setTypeface(face);
      tPaint.setTypeface(face);
    }


    public void SetColor(int color) {
        cPaint.setColor(color);
       tPaint.setColor(color);

    }

}

感谢。

1 个答案:

答案 0 :(得分:2)

这可以通过根据文本宽度改变x和y位置来完成

定义变量

private Rect textBounds;
private int mTextWidth, mTextHeight,centerX,centerY;

在customview

的构造函数中添加以下内容
textBounds = new Rect();

tPaint.getTextBounds(QUOTE, 0, QUOTE.length(), textBounds);
mTextWidth = Math.round(tPaint.measureText(QUOTE.toString())); // Use measureText to calculate width
mTextHeight = textBounds.height(); // Use height from getTextBounds()

然后在onDraw

canvas.drawCircle(centerX,centerY,150,mCirlcePaint);
circle.addCircle(centerX, centerY, 150, Path.Direction.CW); 
// Note the 0 that's y offset. textdraw at circumference of the circle. Changing y you probably need to change the radius as well i guess.
canvas.drawTextOnPath(QUOTE, circle, (centerX)-(mTextWidth / 2f), 0, tPaint);

centerX,centerY是圆圈的中心,即canvaswidht / 2和canvasHeight / 2。我画了一个圆圈供参考

你好的结果

enter image description here

更大文字的结果

enter image description here

对于数字 enter image description here

编辑:评论中的问题

所涉及的数学是使用文本长度计算半圆         radius = (float) ((mTextWidth) / (Math.PI))。如果文字长度大于画布,则需要缩小文字大小或使用整圆radius = (float) ((mTextWidth) / (2*(Math.PI)))。您可以考虑使用其他边缘情况来正确绘制文本。

公共类GraphicsView扩展了View {

private String QUOTE = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
private Path circle;
private Paint mCirlcePaint;
private Paint tPaint;
private Rect textBounds;
private int mTextWidth, mTextHeight, centerX, centerY;

private float radius;

public GraphicsView(Context context) {
    super(context);
    circle = new Path();

    tPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
    tPaint.setStyle(Paint.Style.FILL_AND_STROKE);
    tPaint.setColor(Color.BLACK);
    tPaint.setTextSize(100f);
    textBounds = new Rect();

    tPaint.getTextBounds(QUOTE, 0, QUOTE.length(), textBounds);
    mTextWidth = Math.round(tPaint.measureText(QUOTE.toString())); // Use measureText to calculate width
    mTextHeight = textBounds.height(); // Use height from getTextBounds()

    mCirlcePaint = new Paint();
    mCirlcePaint.setStyle(Paint.Style.FILL);
    mCirlcePaint.setColor(Color.GREEN);

    radius = (float) ((mTextWidth) / (Math.PI));

}

@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
    super.onSizeChanged(w, h, oldw, oldh);
    centerX = w / 2;
    centerY = h / 2;

}

@Override
protected void onDraw(Canvas canvas) {

    canvas.rotate(180, getWidth() / 2, getHeight() / 2);
    canvas.drawCircle(centerX, centerY, radius, mCirlcePaint);
    circle.addCircle(centerX, centerY, radius, Path.Direction.CW);
    canvas.drawTextOnPath(QUOTE, circle, 0, 0, tPaint);

   }

}