如何删除Android的textview上的顶部和底部空间

时间:2011-07-06 09:00:00

标签: android textview

当我将以下XML添加到布局文件时,我可以看到下图。如果你看到它,你会发现TextView有顶部和底部空间。

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

enter image description here

我希望删除这个空间。如何删除它?这叫什么? 如果有人有线索...请告诉我。提前谢谢。

14 个答案:

答案 0 :(得分:86)

尝试android:includeFontPadding="false"看看它是否有帮助。根据我的经验,这将有所帮助,但没有办法将TextView尺寸缩小到精确的像素完美文本大小。

唯一可能会或可能不会产生更好结果的替代方案是作弊并硬连接尺寸以匹配文字大小,例如: <{1}}而不是"24sp"的高度。

答案 1 :(得分:19)

尝试将您的底部和顶部边距设置为负数。

类似的东西:

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

相应地调整值。

答案 2 :(得分:19)

我遇到了同样的问题。属性android:includeFontPadding="false"对我不起作用。我用这种方式解决了这个问题:

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;
    }
}

答案 3 :(得分:4)

我遇到了同样的问题。 这是一个很好的答案:How to align the text to top of TextView?

但是代码很少未完成,并且不支持所有字体大小。改变行

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

int additionalPadding = getTextSize() - getLineHeight();

完整的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 ();
    }
}

答案 4 :(得分:4)

这是拯救我们一天的代码。它使用来自maksimko的单声道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);
    }
}

仍然需要使用textView.setIncludeFontPadding(false),因为我们将TextViews与不同的字体大小对齐。

答案 5 :(得分:3)

只是想添加到DynamicMind's answer,你在TextViews周围看到间距的原因是他们默认使用 9-patch背景中的填充

9-patch技术允许您指定内容区域,实际上是填充。除非您明确设置视图的填充,否则将使用该填充。例如,当您以编程方式将9补丁背景设置为设置了填充的视图时,它们将被覆盖。反之亦然,如果你设置填充,它们会覆盖9补丁背景设置的内容。

不幸的是,在XML布局中,无法确定这些操作的顺序。我想从TextView中删除背景会有所帮助:

android:background="@null"

答案 6 :(得分:2)

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();
    }
}

答案 7 :(得分:1)

您是否定义了布局边距? 例如:

android:layout_marginTop="5dp"

否则,如果你的文本视图被包装在LinearLayout或其他容器中,那么那个冷也有填充或边距。

答案 8 :(得分:0)

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

根据你想要的改变它使用它editbox_background。 因为android提供了一些背景,如上面的代码根据你的要求选择。 可能对你有帮助。

答案 9 :(得分:0)

在LinearLayout内部,默认填充可能是个问题。尝试将其设置为0dp。它对我有用。

答案 10 :(得分:0)

TopAlignedTextView代码answerTopAlignedTextView@GitHub

按布局使用它:

<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"
/>

enter image description here

答案 11 :(得分:0)

我修复此问题的方法非常糟糕,但我设法将文本设置为我想要的位置,将文本视图的高度设置为静态并摆弄它直到它几乎不适合文本。在我的情况下,我使用的字体样式的高度为64sp,所以我将textview的高度设置为50sp,它工作正常。我还必须将foreground_gravity设置为bottom。

答案 12 :(得分:0)

android:includeFontPadding =“ false”

答案 13 :(得分:0)

经过修改的this回答了一点,以使用kotlin类并扩展AppCompatTextView,以修剪垂直填充。

它允许设置android:fontFamily。方法calculateTextParams()onDraw()移至性能。未测试多行文本:

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
      }
    }
  }
}