package org.mercury_im.messenger.android.ui.account; import android.app.Application; import androidx.lifecycle.AndroidViewModel; import androidx.lifecycle.LiveData; import androidx.lifecycle.MutableLiveData; import org.mercury_im.messenger.android.MercuryImApplication; import org.mercury_im.messenger.R; import org.mercury_im.messenger.core.account.error.PasswordError; import org.mercury_im.messenger.core.account.error.UsernameError; import org.mercury_im.messenger.android.ui.MercuryAndroidViewModel; import org.mercury_im.messenger.core.util.Optional; import org.mercury_im.messenger.android.util.TextChangedListener; import org.mercury_im.messenger.core.viewmodel.accounts.LoginViewModel; import java.util.logging.Logger; import javax.inject.Inject; import io.reactivex.Observable; public class AndroidLoginViewModel extends AndroidViewModel implements MercuryAndroidViewModel { private static final Logger LOGGER = Logger.getLogger(AndroidLoginViewModel.class.getName()); private final MutableLiveData loginUsernameError = new MutableLiveData<>(); private final MutableLiveData loginPasswordError = new MutableLiveData<>(); private final MutableLiveData loginButtonEnabled = new MutableLiveData<>(true); private final MutableLiveData loginFinished = new MutableLiveData<>(false); @Inject LoginViewModel commonViewModel; @Inject public AndroidLoginViewModel(Application application) { super(application); reset(); } public void reset() { MercuryImApplication.getApplication().getAppComponent().inject(this); commonViewModel.reset(); addDisposable(mapUsernameErrorCodeToMessage(getCommonViewModel().getLoginUsernameError()) .subscribe(e -> loginUsernameError.setValue(e.isPresent() ? e.getItem() : null))); addDisposable(mapPasswordErrorCodeToMessage(getCommonViewModel().getLoginPasswordError()) .subscribe(e -> loginPasswordError.setValue(e.isPresent() ? e.getItem() : null))); addDisposable(getCommonViewModel().isLoginPossible() .subscribe(loginButtonEnabled::setValue)); addDisposable(getCommonViewModel().isLoginSuccessful() .subscribe(loginFinished::setValue)); } private Observable> mapUsernameErrorCodeToMessage(Observable> errorCodeObservable) { return errorCodeObservable.map(optional -> { if (!optional.isPresent()){ return new Optional<>(null); } UsernameError error = optional.getItem(); int resourceId; switch (error) { case emptyUsername: resourceId = R.string.error_field_required; break; case invalidUsername: resourceId = R.string.error_invalid_username; break; case unreachableServer: resourceId = R.string.error_unreachable_server; break; default: resourceId = R.string.error_uknown_error; } return new Optional<>(getApplication().getResources().getString(resourceId)); }); } private Observable> mapPasswordErrorCodeToMessage(Observable> errorCodeObservable) { return errorCodeObservable.map(optional -> { if (!optional.isPresent()){ return new Optional<>(null); } PasswordError error = optional.getItem(); int resourceId; switch (error) { case emptyPassword: resourceId = R.string.error_field_required; break; case incorrectPassword: resourceId = R.string.error_incorrect_password; break; default: resourceId = R.string.error_uknown_error; } return new Optional<>(getApplication().getResources().getString(resourceId)); }); } @Override protected void onCleared() { super.onCleared(); getCommonViewModel().dispose(); } public void onLoginButtonClicked() { getCommonViewModel().login(); } public LiveData getLoginUsernameError() { return loginUsernameError; } public LiveData getLoginPasswordError() { return loginPasswordError; } public LiveData isLoginButtonEnabled() { return loginButtonEnabled; } public LiveData isLoginFinished() { return loginFinished; } @Override public LoginViewModel getCommonViewModel() { return commonViewModel; } public TextChangedListener getUsernameTextChangedListener() { return usernameTextChangedListener; } public TextChangedListener getPasswordTextChangedListener() { return passwordTextChangedListener; } private final TextChangedListener usernameTextChangedListener = new TextChangedListener() { @Override public void onTextChanged(CharSequence s, int start, int before, int count) { getCommonViewModel().onLoginUsernameChanged(s.toString()); } }; private final TextChangedListener passwordTextChangedListener = new TextChangedListener() { @Override public void onTextChanged(CharSequence s, int start, int before, int count) { getCommonViewModel().onLoginPasswordChanged(s.toString()); } }; }