如何在TextInputLayout中更改EditText提示的大小

时间:2016-10-21 20:13:09

标签: android android-textinputlayout

我正在尝试更改TextInputLayout中的提示大小,但它没有按预期工作。这就是我想要实现的目标:

Desired result

styles.xml

<style name="TextLabel" parent="TextAppearance.Design.Hint">
    <item name="android:textSize">44sp</item>
</style>

fragment.xml

<android.support.design.widget.TextInputLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:hintTextAppearance="@style/TextLabel"
    android:hint="Password">

    <android.support.design.widget.TextInputEditText
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:textSize="24sp"/>

</android.support.design.widget.TextInputLayout>

EditText不为空时,此代码仅适用于浮动标签,但我想更改EditText本身的提示大小,当它为空时。

2 个答案:

答案 0 :(得分:1)

在通胀/初始化期间将常规提示文本的大小添加到EditText时,常规提示文本的大小将设置为TextInputLayout的文本大小。此值最终在TextInputLayout中的私有帮助程序类上设置,并且没有公开的方法或字段来更改它。

但是,我们可以通过继承TextInputLayout来拦截添加EditText的文本大小。添加EditText后,我们缓存其文本大小,将所需的提示大小设置为文本大小,允许超类添加它并初始化提示,最后设置EditText的文本尺寸回到原来的值。

例如:

public class CustomTextInputLayout extends TextInputLayout {

    private float mainHintTextSize;
    private float editTextSize;

    public CustomTextInputLayout(Context context) {
        this(context, null);
    }

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

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

        TypedArray a = context.obtainStyledAttributes(
            attrs, R.styleable.CustomTextInputLayout);

        mainHintTextSize = a.getDimensionPixelSize(
            R.styleable.CustomTextInputLayout_mainHintTextSize, 0);

        a.recycle();
    }

    @Override
    public void addView(View child, int index, ViewGroup.LayoutParams params) {
        final boolean b = child instanceof EditText && mainHintTextSize > 0;

        if (b) {
            final EditText e = (EditText) child;
            editTextSize = e.getTextSize();
            e.setTextSize(TypedValue.COMPLEX_UNIT_PX, mainHintTextSize);
        }

        super.addView(child, index, params);

        if (b) {
            getEditText().setTextSize(TypedValue.COMPLEX_UNIT_PX, editTextSize);
        }
    }

    // Units are pixels.

    public float getMainHintTextSize() {
        return mainHintTextSize;
    }

    // This optional method allows for dynamic instantiation of this class and
    // its EditText, but it cannot be used after the EditText has been added.
    // Units are scaled pixels.

    public void setMainHintTextSize(float size) {
        if (getEditText() != null) {
            throw new IllegalStateException(
                "Hint text size must be set before EditText is added");
        }

        mainHintTextSize = TypedValue.applyDimension(
            TypedValue.COMPLEX_UNIT_SP, size, getResources().getDisplayMetrics());
    }
}

要使用自定义mainHintTextSize属性,我们需要<resources>中的以下内容,我们只需将以下文件放在res/values/文件夹中,或添加到那个已经存在的那个。

attrs.xml

<resources>
    <declare-styleable name="CustomTextInputLayout" >
        <attr name="mainHintTextSize" format="dimension" />
    </declare-styleable>
</resources>

如果您不关心使用自定义属性,则可以跳过此文件,并删除上面第三个构造函数中的TypedArray处理。

此自定义类是TextInputLayout的替代品,可以像使用它一样使用。例如:

<com.mycompany.myapp.CustomTextInputLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:hint="Password"
    app:hintTextAppearance="@style/TextLabel"
    app:mainHintTextSize="12sp">

    <android.support.design.widget.TextInputEditText
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:textSize="24sp"
        android:text="qwerty123" />

</com.mycompany.myapp.CustomTextInputLayout>

screenshot

不幸的是,使用此方法后,添加EditText后无法更改提示文本大小。这需要反思,如果需要,我可以提供这样的解决方案。

答案 1 :(得分:0)

如果您希望提示在展开和折叠状态下具有相同的大小。您可以编写自己的自定义TextInputLayout

package android.support.design.widget

import android.annotation.SuppressLint
import android.content.Context
import android.util.AttributeSet
import android.view.View
import android.view.ViewGroup
import android.widget.EditText

class ConstantHintSizeTextInputLayout : TextInputLayout {
    constructor(context: Context?) : super(context)
    constructor(context: Context?, attrs: AttributeSet?) : super(context, attrs)
    constructor(context: Context?, attrs: AttributeSet?, defStyleAttr: Int) : super(context, attrs, defStyleAttr)

    @SuppressLint("RestrictedApi")
    override fun addView(child: View?, index: Int, params: ViewGroup.LayoutParams?) {
        super.addView(child, index, params)
        if (child is EditText) {
            collapsingTextHelper.expandedTextSize = collapsingTextHelper.collapsedTextSize
        }
    }
}

重要提示::程序包名称应与android.support.design.widget完全相同,因为此解决方案使用访问程序包专用字段的方式,但不涉及反射,因此速度很快

相关问题