美文网首页Android-阅读器系列
Androidの自定义TextView解决中文排版混乱,未满一行

Androidの自定义TextView解决中文排版混乱,未满一行

作者: SteamPY | 来源:发表于2021-05-24 12:22 被阅读0次

    TextView 文本并不会整齐地排列,遇到文字中带有中英文时,给我换行了,网上百度后,解决方式很多。最后采用github上的JustifyTextView,需要进行自定义TextView.

    GitHub地址:

    https://github.com/ufo22940268/android-justifiedtextview

    目前先借鉴使用此类,用来解决问题,先做个笔记,方便查看。

    package com.steampy.app.widget.textview;
    
    import android.content.Context;
    import android.graphics.Canvas;
    import android.graphics.Paint;
    import android.text.Layout;
    import android.text.StaticLayout;
    import android.text.TextPaint;
    import android.util.AttributeSet;
    
    public class JustifyTextView extends androidx.appcompat.widget.AppCompatTextView {
    
        private int mLineY;
        private int mViewWidth;
        public static final String TWO_CHINESE_BLANK = "  ";
    
        public JustifyTextView(Context context, AttributeSet attrs) {
            super(context, attrs);
        }
    
        @Override
        protected void onLayout(boolean changed, int left, int top, int right,
                                int bottom) {
            super.onLayout(changed, left, top, right, bottom);
        }
    
        @Override
        protected void onDraw(Canvas canvas) {
            TextPaint paint = getPaint();
            paint.setColor(getCurrentTextColor());
            paint.drawableState = getDrawableState();
            mViewWidth = getMeasuredWidth();
            String text = getText().toString();
            mLineY = 0;
            mLineY += getTextSize();
            Layout layout = getLayout();
    
            // layout.getLayout()在4.4.3出现NullPointerException
            if (layout == null) {
                return;
            }
    
            Paint.FontMetrics fm = paint.getFontMetrics();
    
            int textHeight = (int) (Math.ceil(fm.descent - fm.ascent));
            textHeight = (int) (textHeight * layout.getSpacingMultiplier() + layout
                    .getSpacingAdd());
            //解决了最后一行文字间距过大的问题
            for (int i = 0; i < layout.getLineCount(); i++) {
                int lineStart = layout.getLineStart(i);
                int lineEnd = layout.getLineEnd(i);
                float width = StaticLayout.getDesiredWidth(text, lineStart,
                        lineEnd, getPaint());
                String line = text.substring(lineStart, lineEnd);
    
                if(i < layout.getLineCount() - 1) {
                    if (needScale(line)) {
                        drawScaledText(canvas, lineStart, line, width);
                    } else {
                        canvas.drawText(line, 0, mLineY, paint);
                    }
                } else {
                    canvas.drawText(line, 0, mLineY, paint);
                }
                mLineY += textHeight;
            }
        }
    
        private void drawScaledText(Canvas canvas, int lineStart, String line,
                                    float lineWidth) {
            float x = 0;
            if (isFirstLineOfParagraph(lineStart, line)) {
                String blanks = "  ";
                canvas.drawText(blanks, x, mLineY, getPaint());
                float bw = StaticLayout.getDesiredWidth(blanks, getPaint());
                x += bw;
    
                line = line.substring(3);
            }
    
            int gapCount = line.length() - 1;
            int i = 0;
            if (line.length() > 2 && line.charAt(0) == 12288
                    && line.charAt(1) == 12288) {
                String substring = line.substring(0, 2);
                float cw = StaticLayout.getDesiredWidth(substring, getPaint());
                canvas.drawText(substring, x, mLineY, getPaint());
                x += cw;
                i += 2;
            }
    
            float d = (mViewWidth - lineWidth) / gapCount;
            for (; i < line.length(); i++) {
                String c = String.valueOf(line.charAt(i));
                float cw = StaticLayout.getDesiredWidth(c, getPaint());
                canvas.drawText(c, x, mLineY, getPaint());
                x += cw + d;
            }
        }
    
        private boolean isFirstLineOfParagraph(int lineStart, String line) {
            return line.length() > 3 && line.charAt(0) == ' '
                    && line.charAt(1) == ' ';
        }
    
        private boolean needScale(String line) {
            if (line == null || line.length() == 0) {
                return false;
            } else {
                return line.charAt(line.length() - 1) != '\n';
            }
        }
    
    }
    

    相关文章

      网友评论

        本文标题:Androidの自定义TextView解决中文排版混乱,未满一行

        本文链接:https://www.haomeiwen.com/subject/yklxsltx.html