Che*_*eng 5 unicode android android-edittext
我们注意到,在targetSdkVersion 28期间EditText,当输入非英语unicode(如中文,日语,...)时,输入后将趋于“稍微下推”该行。
当代码为targetSdkVersion 27或更低版本时,不会发生这种情况。
targetSdkVersion27,在模拟器API 28上运行(在输入非英语unicode之前)
(输入非英文unicode后)
(确认间距确定)
targetSdkVersion28,在模拟器API 28上运行(在输入非英语unicode之前)
(输入非英文unicode后)
(确认间距是有问题的。按下输入后的行)
这是我们使用的XML和代码。我们从继承androidx.appcompat.widget.AppCompatEditText,画线,使问题更加明显。
<com.yocto.wenote.note.LinedEditText
android:id="@+id/body_edit_text"
android:gravity="top"
android:paddingLeft="16dp"
android:paddingRight="16dp"
android:layout_marginBottom="12dp"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/transparent"
android:scrollbars="vertical"
android:textSize="18sp"
android:singleLine="false"
android:lineSpacingMultiplier="1.4"
android:inputType="textMultiLine|textCapSentences"
android:textCursorDrawable="?attr/shorterCursor" />
Run Code Online (Sandbox Code Playgroud)
LinedEditText.java
package com.yocto.wenote.note;
import android.content.Context;
import android.content.res.Resources;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.util.TypedValue;
import com.yocto.wenote.R;
/**
* Created by yccheok on 24/3/2018.
*/
public class LinedEditText extends androidx.appcompat.widget.AppCompatEditText {
private final Paint mPaint = new Paint();
private int noteLineColor;
private static final float DEFAULT_LINE_SPACING_EXTRA = 0.0f;
private static final float DEFAULT_LINE_SPACING_MULTIPLIER = 1.4f;
private void initResource() {
Context context = getContext();
TypedValue typedValue = new TypedValue();
Resources.Theme theme = context.getTheme();
theme.resolveAttribute(R.attr.noteLineColor, typedValue, true);
noteLineColor = typedValue.data;
}
public LinedEditText(Context context) {
super(context);
initResource();
initPaint();
}
public void setNoteLineColor(int noteLineColor) {
this.noteLineColor = noteLineColor;
}
public LinedEditText(Context context, AttributeSet attrs) {
super(context, attrs);
initResource();
initPaint();
}
public LinedEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
initResource();
initPaint();
}
private void initPaint() {
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setColor(noteLineColor);
mPaint.setStrokeWidth(1);
}
@Override
protected void onDraw(Canvas canvas) {
int left = getLeft();
int right = getRight();
int paddingTop = getPaddingTop();
int paddingBottom = getPaddingBottom();
int paddingLeft = getPaddingLeft();
int paddingRight = getPaddingRight();
final int heightWithScrollY = getHeight() + getScrollY();
int lineHeight = getLineHeight();
int count = (heightWithScrollY-paddingTop-paddingBottom) / lineHeight;
mPaint.setColor(noteLineColor);
mPaint.setTypeface(this.getTypeface());
final float originalLineHeight;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN) {
originalLineHeight = lineHeight / getLineSpacingMultiplier();
} else {
originalLineHeight = lineHeight / DEFAULT_LINE_SPACING_MULTIPLIER;
}
for (int i = 0; i < count; i++) {
float baseline = lineHeight * (i + 1) + paddingTop - mPaint.descent() - (lineHeight - originalLineHeight);
canvas.drawLine(
left + paddingLeft,
baseline,
right - paddingRight,
baseline,
mPaint
);
}
super.onDraw(canvas);
}
// /sf/ask/3462730561/
@Override
protected void onTextChanged(CharSequence text, int start, int lengthBefore, int lengthAfter) {
super.onTextChanged(text, start, lengthBefore, lengthAfter);
if (lengthBefore != lengthAfter) {
float add;
float mul;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN) {
add = getLineSpacingExtra();
mul = getLineSpacingMultiplier();
} else {
add = DEFAULT_LINE_SPACING_EXTRA;
mul = DEFAULT_LINE_SPACING_MULTIPLIER;
}
setLineSpacing(0f, 1f);
setLineSpacing(add, mul);
}
}
}
Run Code Online (Sandbox Code Playgroud)
请注意,如果您使用targetSdkVersion28,但在仿真器API 27上运行,也不会发生此问题。
关于解决方法有什么建议吗?
p / s我在https://issuetracker.google.com/issues/131284662提出了问题
您必须查询每个现有行的基线才能在正确的位置绘制线条。我简化了你的代码,这个版本将解决你的问题,我在Android P和Android Q上进行了测试:
@Override
protected void onDraw(Canvas canvas) {
int left = getLeft();
int right = getRight();
int paddingLeft = getPaddingLeft();
int paddingRight = getPaddingRight();
mPaint.setColor(noteLineColor);
mPaint.setTypeface(this.getTypeface());
Layout layout = getLayout();
// 1. Draw line for existing rows
for (int i = 0; i < layout.getLineCount(); i++) {
int baseline = layout.getLineBaseline(i);
canvas.drawLine(
left + paddingLeft,
baseline,
right - paddingRight,
baseline,
mPaint
);
}
// 2. Draw line for non-existing rows
final int heightWithScrollY = getHeight() + getScrollY();
int lineHeight = getLineHeight();
int nextBaseline = layout.getHeight() + lineHeight;
while(nextBaseline < heightWithScrollY){
canvas.drawLine(
left + paddingLeft,
nextBaseline,
right - paddingRight,
nextBaseline,
mPaint
);
nextBaseline += lineHeight;
}
super.onDraw(canvas);
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
366 次 |
| 最近记录: |