gpt4 book ai didi

android - 你能解释一下 TextView + Gravity + SingleLine 和 Canvas 的行为吗?

转载 作者:塔克拉玛干 更新时间:2023-11-02 09:03:46 26 4
gpt4 key购买 nike

我有一个自定义 TextView,它的 onDraw 方法被覆盖以在 TextView 周围绘制红色边框。

当我将重力设置为左侧以外的其他值时 AND singleLine=true :不绘制边框。

  • 有什么理由吗?
  • 有什么解决方法吗?

以下屏幕截图说明了问题:第二个 textView 没有边框 enter image description here

TL 表示 TOP|LEFT ; C 表示 CENTER ; SL表示单线; T 表示真实; F 表示错误

这是代码(可以复制/粘贴并运行 - 不需要布局文件)

import android.app.Activity;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.os.Bundle;
import android.view.Gravity;
import android.widget.RelativeLayout;
import android.widget.TextView;


public class MyActivity extends Activity {

private final int TEXT_VIEW_WIDTH_PX = 400;
private final int TEXT_VIEW_HEIGHT_PX = 60;
private Paint borderPaint = new Paint();

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
RelativeLayout rootView = new RelativeLayout(this);
getWindow().setContentView(rootView);

borderPaint.setColor(Color.RED);

MyTextView text1 = makeTextView("Grav=TL ; SL=F",100);
rootView.addView(text1);

MyTextView text2 = makeTextView("Grav=C ; SL=T",200);
//combination of the 2 following attributes cause the issue
text2.setSingleLine(true);
text2.setGravity(Gravity.CENTER);
rootView.addView(text2);

MyTextView text3 = makeTextView("Grav=C ; SL=F",300);
text3.setGravity(Gravity.CENTER);
rootView.addView(text3);

MyTextView text4 = makeTextView("Grav=TL ; SL=T",400);
text4.setSingleLine(true);
rootView.addView(text4);
}

/**
* Custom TextView with red border
*/
private class MyTextView extends TextView {

private MyTextView(Context context) {
super(context);
}

@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
canvas.drawLine(1,1,1,TEXT_VIEW_HEIGHT_PX-1,borderPaint);
canvas.drawLine(1,1,TEXT_VIEW_WIDTH_PX-1,1,borderPaint);
canvas.drawLine(TEXT_VIEW_WIDTH_PX-1,1,TEXT_VIEW_WIDTH_PX-1,TEXT_VIEW_HEIGHT_PX-1,borderPaint);
canvas.drawLine(1,TEXT_VIEW_HEIGHT_PX-1,TEXT_VIEW_WIDTH_PX-1,TEXT_VIEW_HEIGHT_PX-1,borderPaint);
}
}


/**
* create a MyTextView with 'text' context and located at x=50 ; y=marginTop
* (nothing relevant for the issue here)
*/
private MyTextView makeTextView(String text, int marginTop){
MyTextView textView = new MyTextView(this);
textView.setText(text);
RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(TEXT_VIEW_WIDTH_PX,TEXT_VIEW_HEIGHT_PX);
lp.topMargin = marginTop;
lp.leftMargin = 50;
textView.setLayoutParams(lp);
return textView;
}

}

最佳答案

感谢 pskink 的深入研究(来自对我的另一个答案的评论):

If you want to know why custom onDraw doesn't draw anything, just Log.d the value of canvas.getMatrix().

[It] seems that canvas is translated/horizontally scrolled (at least in my case) 8159 pixels to the left, so calling canvas.translate(8159, 0) fixes the issue, of course 8159 is not a magic number and can vary.

I found it, see VERY_WIDE constant in TextView, it is set to 16384 (2**14), in my case TextView has width of 66 and now (16384-66)/2 == 8159, voila!

...but VERY_WIDE is private so you cannot access it :-(

从这里开始,我想知道是否可以通过编程方式检索偏移量,并且确实可以通过 getScrollX() 轻松检索。这种方法通过取消水平滚动来平移 Canvas 而不是“破解”单行。单线显示更自然。

在自定义 TextView 中:

@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);

// translate the canvas before drawing onto it, fixing the position
canvas.translate(getScrollX(), 0);

canvas.drawLine(1, 1, 1, TEXT_VIEW_HEIGHT_PX - 1, borderPaint);
canvas.drawLine(1, 1, TEXT_VIEW_WIDTH_PX - 1, 1, borderPaint);
canvas.drawLine(TEXT_VIEW_WIDTH_PX - 1, 1, TEXT_VIEW_WIDTH_PX - 1,
TEXT_VIEW_HEIGHT_PX - 1, borderPaint);
canvas.drawLine(1, TEXT_VIEW_HEIGHT_PX - 1, TEXT_VIEW_WIDTH_PX - 1,
TEXT_VIEW_HEIGHT_PX - 1, borderPaint);
}

此代码尚未针对所有情况进行彻底测试。我只确认了OP提供的4个案例

关于android - 你能解释一下 TextView + Gravity + SingleLine 和 Canvas 的行为吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25501185/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com