0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

【Android】リアルタイムバリデーション機能付きのパスワード入力欄を作る

Last updated at Posted at 2022-02-20

はじめに

こんな感じでバリデーションエラーの時は赤く、それ以外の時は白くなるパスワード入力欄ありますよね。
Androidでこれを実装したかったのですが、レイアウトを出し分けるやり方がなかなか見つからず苦労しました。
なので今回はその備忘録を記したいと思います。

validation_test.gif

実行環境

項目 情報
PC MacBook Pro (14-inch,2021)
CPU Apple M1 Pro 10-core
GPU Apple M1 Pro 16-core
OS macOS Monterey (12.0.1)
Android Studio Arctic Fox 2020.3.1 Patch4

作成手順

  1. 背景用のdrawableを2つ作成(エラー用、標準時用)
  2. ViewModelでバリデーションエラーメソッドの実装
  3. レイアウトファイル内のEditTextに1と2を適用
  4. ActivityでレイアウトとViewModelの結合

今回は8文字以下ならEditTextを赤くしてエラーを示すという形で作っていきます。

1. 背景用のdrawableを2つ作成(エラー用、標準時用)

EditTextの背景に適用させる角丸のdrawableを2つ(エラー用、標準時用)作っておきます。
shapeやstrokeなどはお好みでどうぞ。

edittext_error.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <shape android:shape="rectangle">
            <corners android:radius="10dp" />
            <solid android:color="#FFE4E1" />
            <stroke android:width="1dp" android:color="#FF0000" />
        </shape>
    </item>
</selector>
edittext_normal.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <shape android:shape="rectangle">
            <corners android:radius="10dp" />
            <solid android:color="#f5f5f5" />
            <stroke android:width="1dp" android:color="#808080" />
        </shape>
    </item>
</selector>

2. ViewModelでバリデーションエラーメソッドの実装

「入力された文字列が8文字以下ならエラー」というメソッドを具体的に記述していきます。
ここを変えればもっと複雑なバリデーションもかけられるようになります。

MainViewModel.kt
class MainViewModel() : ViewModel() {

    // エラーかどうか判定する変数を置いておく
    val isError: MutableLiveData<Boolean> = MutableLiveData()

    // 入力された文字列が8文字以下ならisErrorをtrueにする
    fun checkError(editable: Editable){
        if (editable.length < 8){
            isError.value = true
        }else{
            isError.value = false
        }
    }
}

3. レイアウトファイル内のEditTextに1と2を適用

とりあえずシンプルにEditTextを1つだけ配置します。

activity_main.xml
<layout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools">

    <data>

        <variable
            name="viewModel"
            type="com.example.firstapplication.MainViewModel" />
    </data>

    <EditText
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_margin="30dp"
        android:afterTextChanged="@{viewModel::checkError}"
        android:background="@{viewModel.isError ?@drawable/edittext_error : @drawable/edittext_normal}"
        android:padding="10dp" />
</layout>

まず、android:afterTextChangedに関数を設定し、入力した文字列をMainViewModel内のeditableで受け取っています。

そうしてバリデーションが通ったか否かを判定し、android:backgroundで背景を適用させます。
ここでは三項演算子を使用し、isErrorがtrueなら@drawable/edittext_errorを、falseなら@drawable/edittext_normalを適用させるようにしています。

4. ActivityでレイアウトとViewModelの結合

MainActivity.kt
class MainActivity : AppCompatActivity() {

    var binding: ActivityMainBinding? = null
    val viewModel = MainViewModel()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        setContentView(R.layout.activity_main)
        binding = DataBindingUtil.setContentView(this,R.layout.activity_main)
        binding?.apply {
            lifecycleOwner = this@MainActivity
            viewModel = this@MainActivity.viewModel
        }
    }
}

MainActivityではレイアウトを作成し、その上でレイアウトファイルのlifecycleOwnerとviewModelをそれぞれ設定しています。
この辺りの書き方は色々流派があると思いますが、いずれにせよbinding?.apply内の記述がないとうまく動かず私みたいにハマる羽目になるので、最後まで気を抜かずに確認しましょう。参考

ここまで書けば一通り完成です!

ハマりポイント

カスタムビュー上だと見た目が変化しない

今回はxmlで<EditText>を使っていますが、ここを独自に作成したカスタムビューにするというケースは往々にしてあると思います。
ですが私が試した限りですと、ここをカスタムビューにしてしまうとうまく動きませんでした。

三項演算子でdrawableを設定しようとすると補完が効かない

xmlのEditTextタグ内で android:background="@{viewModel.isError ?@drawable/edittext_error : @drawable/edittext_normal}"とやっている部分も注意が必要です。
結構長い記述なのですが、ここだけなぜか補完が効きません。
そのため、書いた後は一旦drawableファイル名の上でcmd+B(windowsの場合はctrl+B)を押し、該当のファイルに飛べるかどうか確認してください。
これで飛べれば正常に書けている証拠です。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?