EditText
にテキストがあるかどうかに関係なく、ラベルを常に展開したままにしておくことができるかどうか疑問に思いました。ソースを調べたところ、変更をアニメーション化するかどうかに関係なく、ValueAnimator
内でcounter
とTextWatcher
を使用しています。たぶん、TextWatcher
内のValueAnimator
にカスタムEditText
を使用してカスタムTextInputLayout
を設定できますか?
TextInputLayout
の現在のバージョンは、特に1つのことを行うために存在します。EditText
にテキストがあるかどうかに応じて、ヘルパーラベルを表示/非表示にします。必要なのは異なる動作であるため、TextInputLayout
とは異なるウィジェットが必要です。このケースは、ニーズに合ったカスタムビューを作成するのに最適な候補です。
とはいえ、カスタムTextWatcher
をEditText
に設定するというアイデアも機能しません。これは、TextInputLayout
が実際にアニメーションを処理する内部を公開しないため、どちらも機能しません。 updateLabelVisibility()
、setEditText()
、仕事などを行う魔法のHandler
。もちろん、このような詳細については、反射パスに行きたくないので、...
MaterialEditText を使用するだけです!それはあなたが望むことを正確に行う次のプロパティを持っています。
met_floatingLabelAlwaysShown:フローティングラベルをアニメーション化するのではなく、常に表示します。デフォルトではFalse。
ライブラリは非常に安定しており(私は2つの異なるプロジェクトで使用しています)、カスタマイズするためのオプションがたくさんあります。それが役に立てば幸い!
サポートデザイン23.3.0を使用している私にとっては、
<Android.support.design.widget.TextInputLayout
Android:layout_width="match_parent"
Android:layout_height="wrap_content"
Android:hint="wow such hint"
app:hintEnabled="true"
app:hintAnimationEnabled="false"
/>
一番の答えにもかかわらず、私はまだJavaリフレクションソリューションを思いついた(com.google.Android.material.textfield.TextInputLayout
からcom.google.Android.material:material:1.0.0
を使用):
/**
* Creation Date: 3/20/19
*
* @author www.flx-apps.com
*/
public class CollapsedHintTextInputLayout extends TextInputLayout {
Method collapseHintMethod;
public CollapsedHintTextInputLayout(Context context) {
super(context);
init();
}
public CollapsedHintTextInputLayout(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
public CollapsedHintTextInputLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init();
}
void init() {
setHintAnimationEnabled(false);
try {
collapseHintMethod = TextInputLayout.class.getDeclaredMethod("collapseHint", boolean.class);
collapseHintMethod.setAccessible(true);
}
catch (Exception ignored) {
ignored.printStackTrace();
}
}
@Override
public void invalidate() {
super.invalidate();
try {
collapseHintMethod.invoke(this, false);
}
catch (Exception e) {
e.printStackTrace();
}
}
}
もちろん、Java Reflectionは決してきれいではありませんが、私の場合は、似たようなウィジェットを作成するよりも便利なソリューションであり、リンクされたライブラリは古くて放棄されているように見えました…:/
使用する場合は、それぞれのProGuardルールを追加することを忘れないでください。
-keepclassmembers class com.google.Android.material.textfield.TextInputLayout {
private void collapseHint;
}
ラベルのヒントをレイアウトに配置し、テキストボックスのヒントを編集テキストに衝突させることなく配置できるようにするためのトリックを次に示します。クラス間の比較を行うため、元の不正な描画が発生するのを防ぎ、縮小/プログアの設定に対処する必要がないため、上記のリフレクションソリューションよりもうまく機能します。
次のようにTextInputEditTextをサブクラス化します。
import Android.content.Context
import Android.text.Editable
import Android.text.SpannableStringBuilder
import Android.util.AttributeSet
import com.google.Android.material.R
import com.google.Android.material.textfield.TextInputEditText
import com.google.Android.material.textfield.TextInputLayout
class MonkeyedTextInputEditText @JvmOverloads constructor(context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = R.attr.editTextStyle) : TextInputEditText(context, attrs, defStyleAttr) {
@Override
override fun getText(): Editable? {
val text = super.getText()
if (!text.isNullOrEmpty())
return text
/* We want this expression in TextInputLayout.Java to be true if there's a hint set:
* final boolean hasText = editText != null && !TextUtils.isEmpty(editText.getText());
* But for everyone else it should return the real value, so we check the caller.
*/
if (!hint.isNullOrEmpty() && Thread.currentThread().stackTrace[3].className == TextInputLayout::class.qualifiedName)
return SpannableStringBuilder(hint)
return text
}
}
次に、レイアウトは次のようになります。
<com.google.Android.material.textfield.TextInputLayout
...
Android:hint="YOUR LABEL TEXT"
...
>
<yourapp.MonkeyedTextInputEditText
...
Android:hint="YOUR PLACEHOLDER TEXT"
...
/>
</com.google.Android.material.textfield.TextInputLayout>