简体   繁体   English

如何去除Android的textview上的上下空间

[英]How to remove the top and bottom space on textview of Android

When I include the below XML to layout file, I can see the below image.当我将以下XML布局文件时,我可以看到下图。 If you see it, you could realize that the TextView has top and bottom space.如果你看到它,你就会意识到TextView有顶部和底部空间。

<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="E1"
android:background="#ff00ff00"/>

在此处输入图像描述

I wish to remove the space.我想删除空间。 How to remove it?如何删除它? What is it called?这叫什么? If anyone has clue.. please let me know.如果有人有线索..请告诉我。 Thanks in advance.提前致谢。

Try android:includeFontPadding="false" to see if it helps.尝试android:includeFontPadding="false"看看是否有帮助。 In my experience that will help a little bit, but there's no way of reducing the TextView dimensions to the exact pixel-perfect text size.根据我的经验,这会有所帮助,但无法将 TextView 尺寸减小到精确的像素完美文本大小。

The only alternative, which may or may not give better results, is to cheat a bit and hard-wire the dimensions to match the text size, eg "24sp" instead of "wrap_content" for the height.唯一的选择,可能会或可能不会提供更好的结果,是作弊并硬连接尺寸以匹配文本大小,例如"24sp"而不是"wrap_content"作为高度。

I had the same problem.我有同样的问题。 Attribute android:includeFontPadding="false" does not work for me.属性android:includeFontPadding="false"对我不起作用。 I've solved this problem in this way:我以这种方式解决了这个问题:

public class TextViewWithoutPaddings extends TextView {

    private final Paint mPaint = new Paint();

    private final Rect mBounds = new Rect();

    public TextViewWithoutPaddings(Context context) {
        super(context);
    }

    public TextViewWithoutPaddings(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public TextViewWithoutPaddings(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @Override
    protected void onDraw(@NonNull Canvas canvas) {
        final String text = calculateTextParams();

        final int left = mBounds.left;
        final int bottom = mBounds.bottom;
        mBounds.offset(-mBounds.left, -mBounds.top);
        mPaint.setAntiAlias(true);
        mPaint.setColor(getCurrentTextColor());
        canvas.drawText(text, -left, mBounds.bottom - bottom, mPaint);
    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        calculateTextParams();
        setMeasuredDimension(mBounds.width() + 1, -mBounds.top + 1);
    }

    private String calculateTextParams() {
        final String text = getText().toString();
        final int textLength = text.length();
        mPaint.setTextSize(getTextSize());
        mPaint.getTextBounds(text, 0, textLength, mBounds);
        if (textLength == 0) {
            mBounds.right = mBounds.left;
        }
        return text;
    }
}

android:includeFontPadding="false" is pretty good but it does not get it precisely. android:includeFontPadding="false"非常好,但不能准确地得到它。 sometimes you want border line accuracy so you can figure it out yourself by applying negative margins:有时你想要边界线的准确性,所以你可以通过应用负边距自己弄清楚:

try setting your bottom and top margins to a negative value.尝试将底部和顶部边距设置为负值。

something like this:是这样的:

android:layout_marginTop="-5dp"
android:layout_marginBottom="-5dp"

adjust the values accordingly.相应地调整值。

This is the code that saved our day.这是拯救我们一天的代码。 It was adapted using mono C# code from maksimko :它是使用来自maksimko的 mono C# 代码改编的:

public class TopAlignedTextView extends TextView {

    public TopAlignedTextView(Context context) {
        super(context);
    }

    /*This is where the magic happens*/
    @Override
    protected void onDraw(Canvas canvas){

        float offset = getTextSize() - getLineHeight();
        canvas.translate(0, offset);
        super.onDraw(canvas);
    }
}

Still had to play around with textView.setIncludeFontPadding(false) because we were aligning TextViews with different font sizes.仍然需要使用textView.setIncludeFontPadding(false) ,因为我们要将TextViews与不同的字体大小对齐。

I faced the same problem.我遇到了同样的问题。 Here's a good answer: How to align the text to top of TextView?这是一个很好的答案: How to align the text to top of TextView?

But code is little unfinished and don't support all font sizes.但代码还未完成,并不支持所有字体大小。 Change the line换线

int additionalPadding = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 5, getContext().getResources().getDisplayMetrics());

to

int additionalPadding = getTextSize() - getLineHeight();

Complete C# code (mono) removes top offset:完整的 C# 代码(单声道)删除顶部偏移:

public class TextControl : TextView {
    public TextControl (Context context) : base (context)
    {
        SetIncludeFontPadding (false);
        Gravity = GravityFlags.Top;
    }

    protected override void OnDraw (Android.Graphics.Canvas canvas)
    {
        if (base.Layout == null)
            return;

        Paint.Color = new Android.Graphics.Color (CurrentTextColor);
        Paint.DrawableState = GetDrawableState ();

        canvas.Save ();

        var offset = TextSize - LineHeight;
        canvas.Translate (0, offset);

        base.Layout.Draw (canvas);

        canvas.Restore ();
    }
}

Just wanted to add to DynamicMind 's answer that the reason why you see spacing around your TextViews is padding in 9-patch backgrounds they use by default.只是想在DynamicMind的回答中补充一点,您在 TextView 周围看到间距的原因是在它们默认使用的9 补丁背景中进行填充

9-patch technology allows you to specify a content area which is, effectively, padding. 9-patch 技术允许您指定一个有效填充的内容区域 That padding is used unless you set the view's padding explicitly.除非您明确设置视图的填充,否则将使用该填充。 Eg, when you programmatically set a 9-patch background to a view which had paddings set, they are overridden.例如,当您以编程方式将 9 补丁背景设置为已设置填充的视图时,它们将被覆盖。 And vise-versa, if you set paddings they override what was set by 9-patch background.反之亦然,如果您设置填充,它们会覆盖 9 补丁背景设置的内容。

Unfortunately, in the XML layout it's not possible to determine the order of these operations.不幸的是,在 XML 布局中,无法确定这些操作的顺序。 I think just removing the background from your TextViews would help:我认为仅从 TextViews 中删除背景会有所帮助:

android:background="@null"
public class TopAlignedTextView extends TextView {

    public TopAlignedTextView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public TopAlignedTextView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs);
        setIncludeFontPadding(false); //remove the font padding
        setGravity(getGravity() | Gravity.TOP);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        TextPaint textPaint = getPaint();
        textPaint.setColor(getCurrentTextColor());
        textPaint.drawableState = getDrawableState();
        canvas.save();

        //remove extra font padding
        int yOffset = getHeight() - getBaseline();
        canvas.translate(0, - yOffset / 2);

        if (getLayout() != null) {
            getLayout().draw(canvas);
        }
        canvas.restore();
    }
}

Modified this answer a little bit to use kotlin class and extend AppCompatTextView , trimming vertical padding.稍微修改答案以使用 kotlin class 并扩展AppCompatTextView ,修剪垂直填充。

It allows setting android:fontFamily .它允许设置android:fontFamily Method calculateTextParams() moved from onDraw() for performance.为提高性能,方法calculateTextParams()onDraw() ) 移出。 Not tested for multiple lines of text:未测试多行文本:

import android.content.Context
import android.graphics.Canvas
import android.graphics.Rect
import android.util.AttributeSet
import androidx.appcompat.widget.AppCompatTextView

class NoPaddingTextView : AppCompatTextView
{
  private val boundsRect = Rect()
  private val textParams = calculateTextParams()

  constructor(context : Context?)
  : super(context)

  constructor(context : Context?, attrs : AttributeSet?)
  : super(context, attrs)

  constructor(context : Context?, attrs : AttributeSet?, defStyleAttr : Int)
  : super(context, attrs, defStyleAttr)

  override fun onDraw(canvas : Canvas)
  {
    with(boundsRect) {
      paint.isAntiAlias = true
      paint.color = currentTextColor
      canvas.drawText(textParams,
                      -left.toFloat(),
                      (-top - bottom).toFloat(),
                      paint)
    }
  }

  override fun onMeasure(widthMeasureSpec : Int, heightMeasureSpec : Int)
  {
    super.onMeasure(widthMeasureSpec, heightMeasureSpec)
    calculateTextParams()
    setMeasuredDimension(boundsRect.width() + 1, -boundsRect.top + 1)
  }

  private fun calculateTextParams() : String
  {
    return text.toString()
    .also {text ->
      text.length.let {textLength ->
        paint.textSize = textSize
        paint.getTextBounds(text, 0, textLength, boundsRect)
        if(textLength == 0) boundsRect.right = boundsRect.left
      }
    }
  }
}

Have you defined a layout margin?您是否定义了布局边距? For example:例如:

android:layout_marginTop="5dp"

Otherwise, if your text view is wrapped inside a LinearLayout or other container, then that cold have either padding or a margin too.否则,如果您的文本视图被包裹在 LinearLayout 或其他容器中,那么冷视图也有填充或边距。

Inside a LinearLayout the default padding might be an issue.在 LinearLayout 内部,默认填充可能是个问题。 Try setting it to 0dp.尝试将其设置为 0dp。 It worked for me.它对我有用。

The answer of TopAlignedTextView code: TopAlignedTextView@GitHub TopAlignedTextView代码的答案TopAlignedTextView@GitHub

use it by layout:通过布局使用它:

<com.github.captain_miao.view.TopAlignedTextView
    android:id="@+id/text_a"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:text="@string/text_demo_a"
/>

在此处输入图像描述

My way for fixing this is pretty hacky, but I managed to get the text to sit where I wanted by setting the height of the text view as static and fiddling with it until it just barely fit the text.我解决这个问题的方法很老套,但我设法让文本位于我想要的位置,方法是将文本视图的高度设置为 static 并摆弄它直到它刚好适合文本。 In my case, the font style I was using had a height of 64sp so I set the height of my textview to 50sp and it worked okay.在我的例子中,我使用的字体样式的高度为 64sp,所以我将 textview 的高度设置为 50sp,它工作正常。 I also had to set foreground_gravity to bottom.我还必须将 foreground_gravity 设置为底部。

android:background="@android:drawable/editbox_background"

use it according to you change it that you want editbox_background.根据您的需要使用它,将其更改为您想要的 editbox_background。 because android provide some build in background like above code choose according to your requirement.因为 android 提供了一些像上面代码一样的后台构建,请根据您的要求选择。 May be it is help full to you.可能对你有帮助。

android:includeFontPadding="false"

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM