modifier = Modifier.padding(
bottom = 8.dp
),
text = when(viewmodel.state) {
State.SignUpSuccess -> “Some text 1”
State.LoadAmbassadorCodeAndReferralNameSuccess -> “Some text 2”
State.SignUpError -> “Some text 3”
}
)
Вы читали официальную документацию по Jetpack Compose?
Странный вопрос Что имеено ?
Ну, в принципе можно, но особо нужно. То есть, какие-то действия пользователя транслируются в VM. VM что-то там делает с этим и присылает измененный стейт в LiveData, Composable функция слушает эти апдейты, тригерится на обновление и рендерит экран с измененными данными
Ну, в принципе можно, но особо нужно. - Вы хотели сказать “Особо не нужно” ? 🙂
Да, в смысле "особо не нужно"
Для полного понимания ситуации Вот к примеру я меняю текст и видимость, если стейт во вьюмодели меняется на LoadAmbassadorCodeAndReferralNameSuccess Мне во вью модели нужно создать 2 mutableState переменные: signUpReferralProgramInvitationTitleText и signUpReferralProgramInvitationRootVisibility И напрямую прописывать их в Compose компоненте А если у меня в одном блоке меняется 20 значений разных в вьюх, а не только текст и видимость. Я получается должен создавать 20 mutableState переменных во вью модели только для одного этого условия А если таких условий у меня 10 Это же дикий ад будет потом во вьюмодели))
data class ScreenState( val signUpReferralProgramInvitationTitleText: String? // ну или какой там тип подойдет ... // все другие 20 значений для отображения. Возможно сгруппированные по еще каким-то структурам ) потом где-то в composable-функции @Composable fun Screen(viewmodel: SignupViewModel) { val state by viewmodel.state.observeAsState() state.signUpReferralProgramInvitationTitleText?.let { Text( value = stringResource(R.string.blah_blah, it) ) } }
А, ну и в самой VM class SignupViewModel(...) : ViewModel() { val state: LivaData<ScreenState> = ... }
как же трудно перепиской все обьяснить 😂 у меня не дата класс, a sealed выше него а c sealed классом получается нужно через expression смотреть какой именно сейчас state у вьюмодели и отталкиваясь от него уже сетить свое значение то, что я предложил, а вы сказали, что так не нужно)
Ну data class может быть внутри sealed class. Вот там на скриншоте выше много наследников sealed class, что они обозначают?
Они нужны для того, чтобы для каждый такой наследник имел свой блок с условиями sealed class State { data class A (val someVar: String ….) object B object C etc. } А во вьюмодели например в конце загрузки данных присваиваю state (она же LiveData) значение наследника A и в активити так как это все тригерится - уже выполняю что находится в блоке A viewmodel.state.observe(this) { when(it) { A -> { textinput.text = “Change some text” progressBar = visible etc } } }
Нене, я имею в виду, какой у них смысл? Вот есть экран, насколько я понял, регистрации. Что конкретно каждый наследник значит?
SignUpSuccess - регистрация успешно заверщшена LoadAmbassadorCodeAndReferralNameSuccess - подгрузилась дата по реферальной программе SignUpError - ошибка при решистрации
Я тогда вообще не понимаю, в чем проблема
Ну то есть в том стейте должны быть все необходимые данные для рендеринга экрана. Под каждый экран своя структура с описанием стейта.
Под каждый экран своя структура с описанием стейта - Что вы имели ввиду ?
Подскажите тогда, если знаете
так я не понял, в чем вообще проблема.... мысль размазана по нескольким сообщениям и смысл ускользает
Я имею в виду, что для каждого экрана существует свой data/sealed class со всеми необходимыми данными. На основе этой структуры composable функция рендерит все что надо.
Мне это нужно использовать в Compose функции
Все равно не понимаю У меня во вьюмодели есть набор готовых data classes and objects Если обзервить в активити эти стейты, то как потом менять что-то в самой composable функции с активити / фрагмента? Нужно значит тригерить это внутри Composable функции, чтобы напрямую иметь доступ ко вью Вижу решение как и писал выше - если текст может меняться во вьюхе в при 3 разных стейтах, тогда пишем так Text( modifier = Modifier.padding( bottom = 8.dp ), text = when(viewmodel.state) { State.SignUpSuccess -> “Some text 1” State.LoadAmbassadorCodeAndReferralNameSuccess -> “Some text 2” State.SignUpError -> “Some text 3” } ) ну и так далее с другими параметрами у компонентов если нужен доступ к активити - передает колбеком в активити обратно
все равно не понимаю, в чем проблема... понятно, что подход, что применялся в UI с вьюхами для композа не совсем подходит. надо переосмысливать и переделывать. про вызов другой активити - у меня или дежавю, или это уже обсуждали.
Руками тригерить ничего не надо. При изменении state который вот этот стейт наступает рекомпозиция. А чтобы был этот стейт нужно вызвать livedata.observeAsState()
да, вчера говорили за это
Мне просто хочется понять пример как это применить в своем случае Я про эти стейты уже все вдоль и поперек прочитал и кучу видео пересмотрел) как мне правильно вот это вот к примеру реализовать с compose ?
это какой то «неправильный» стейт, имхо. для композа по крайней мере. для композа я п пересмотрел подход. в UiState завел бы поле extraInfo: String/Int, и назначал бы его в vm в зависимости от того, что там произошло в юзкейсе SignUp-а
Что такое UIState ?
стейт экрана для композа
Не понимаю Что этот стейт хранит ? Откуда он берется ?
😔 нельзя просто взять старую логику(vm) из классических вьюх и втащить ее в композ. т.к получится знатный винегрет. могу ошибаться, конечно. поправьте если что.
Я хочу перетащить логику из классичекого vm Я хочу понять как это работает на простом примере
Стейт хранит все динамические данные. Есть мокап экрана, который должен быть на выходе?
что там нельзя? Все там можно
Обсуждают сегодня