https://kotlinlang.org logo
Title
s

Spikey Sanju

09/14/2021, 10:48 AM
Hello all, I’ve been working on new task manager app with jetpack compose app. I’m facing
huge performance issues
when I’m
navigating
from
all task composable
👉
add task composable
.
Add task composable
screen is having multiple
OutlineTextField
. Is there any workaround solution for this? Here’s the sample video 👇 . See more details in thread below.
Add Task Composable 👇
@Composable
fun AddTaskScreen(viewModel: MainViewModel, actions: MainActions) { // component state val bottomSheetState = rememberModalBottomSheetState(ModalBottomSheetValue.Hidden) val listState = rememberLazyListState() val scope = rememberCoroutineScope() val context = LocalContext.current // task value state var titleState by rememberSaveable { mutableStateOf(“”) } var descriptionState by rememberSaveable { mutableStateOf(“”) } var categoryState by rememberSaveable { mutableStateOf(“”) } var emojiState by rememberSaveable { mutableStateOf(“”) } var urgencyState by rememberSaveable { mutableStateOf(0F) } var importanceState by rememberSaveable { mutableStateOf(0F) } var priorityState by rememberSaveable { mutableStateOf(Priority.IMPORTANT) } val isCompletedState by rememberSaveable { mutableStateOf(false) } val dueState by rememberSaveable { mutableStateOf(“18/12/1998”) } val stepCount by rememberSaveable { mutableStateOf(5) } val result = viewModel.emoji.collectAsState().value ModalBottomSheetLayout( sheetState = bottomSheetState, sheetContent = { BottomSheetTitle() LazyVerticalGrid( cells = GridCells.Adaptive(minSize = 60.dp) ) { // get all emoji viewModel.getAllEmoji(context) // parse emoji into ViewStates when (result) { EmojiViewState.Empty -> { item { AnimationViewState( title = stringResource(R.string.text_error_title), description = stringResource(R.string.text_error_description), callToAction = stringResource(R.string.text_error_description), screenState = ScreenState.ERROR, actions = { scope.launch { bottomSheetState.hide() } } ) } } is EmojiViewState.Error -> { item { AnimationViewState( title = stringResource(R.string.text_error_title).plus(“, “) .plus(result.exception), description = stringResource(R.string.text_error_description), callToAction = stringResource(R.string.text_error_description), screenState = ScreenState.ERROR, actions = { scope.launch { bottomSheetState.hide() } } ) } } EmojiViewState.Loading -> { item { AnimationViewState( title = stringResource(R.string.text_error_title), description = stringResource(R.string.text_error_description), callToAction = stringResource(R.string.text_error_description), screenState = ScreenState.LOADING, actions = { scope.launch { bottomSheetState.hide() } } ) } } is EmojiViewState.Success -> { items(result.emojiItem) { emoji -> EmojiPlaceHolderBottomSheet( emoji = emoji.emoji, onSelect = { scope.launch { emojiState = it bottomSheetState.hide() } } ) } } } } } ) { Scaffold( topBar = { TopAppBar( title = { Text( text = stringResource(id = R.string.text_addTask), style = typography.h6, textAlign = TextAlign.Start, color = einsenColors.black, modifier = Modifier.padding(start = 16.dp) ) }, navigationIcon = { IconButton(onClick = { actions.upPress.invoke() }) { Icon( painter = painterResource(id = R.drawable.ic_back), contentDescription = stringResource(R.string.back_button), tint = einsenColors.black ) } }, backgroundColor = einsenColors.background, elevation = 0.dp ) } ) { LazyColumn(state = listState, contentPadding = PaddingValues(bottom = 24.dp)) { // Emoji item { Spacer(modifier = Modifier.height(24.dp)) Box( modifier = Modifier.fillMaxWidth(), contentAlignment = Alignment.Center ) { EmojiPlaceHolder( emoji = emojiState, onSelect = { scope.launch { bottomSheetState.show() } } ) } } // Title item { Spacer(modifier = Modifier.height(24.dp)) EinsenInputTextField( title = stringResource(R.string.text_title), value = titleState ) { titleState = it } } // Description item { Spacer(modifier = Modifier.height(24.dp)) EinsenInputTextField( title = stringResource(R.string.text_description), value = descriptionState ) { descriptionState = it } } // Category item { Spacer(modifier = Modifier.height(24.dp)) EinsenInputTextField( title = stringResource(R.string.text_category), value = categoryState ) { categoryState = it } } val titleStyle = TextStyle( fontSize = 16.sp, fontFamily = Avenir, fontWeight = FontWeight.Bold ) // Urgency item { Spacer(modifier = Modifier.height(24.dp)) Column(modifier = Modifier.padding(start = 24.dp, end = 24.dp)) { Text( text = stringResource(R.string.text_urgency), style = titleStyle, color = MaterialTheme.colors.onPrimary ) Spacer(modifier = Modifier.height(12.dp)) StepSlider(stepCount = stepCount, value = urgencyState) { urgencyState = it } } } // Importance item { Spacer(modifier = Modifier.height(24.dp)) Column(modifier = Modifier.padding(start = 24.dp, end = 24.dp)) { Text( text = stringResource(R.string.text_importance), style = titleStyle, color = MaterialTheme.colors.onPrimary ) Spacer(modifier = Modifier.height(12.dp)) StepSlider(stepCount = stepCount, value = importanceState) { importanceState = it } } } // Save Task CTA item { Spacer(modifier = Modifier.height(36.dp)) PrimaryButton(title = stringResource(R.string.text_save_task)) { // calculate the average value by adding urgency + priority / 2 val priorityAverage = urgencyState + importanceState / 2 priorityState = calculatePriority(priorityAverage) val task = task { title = titleState description = descriptionState category = categoryState emoji = emojiState urgency = urgencyState importance = importanceState priority = priorityState due = dueState isCompleted = isCompletedState } when { titleState.isEmpty() && descriptionState.isEmpty() || categoryState.isEmpty() -> { showToast(context, “Please fill all the fields & save the task”) } else -> { viewModel.insertTask(task).run { showToast(context, “Task added successfully!“) actions.upPress.invoke() } } } } } } } } } @Composable private fun BottomSheetTitle() { Text( modifier = Modifier.padding(start = 16.dp, top = 16.dp, bottom = 24.dp), text = stringResource(R.string.tetxt_choose_emoji), style = typography.h5, textAlign = TextAlign.Start, color = einsenColors.black ) }
a

adjpd

09/14/2021, 2:55 PM
Are you testing this on a release build with R8? If not, I'd suggest you do, and then report back.
s

Shakil Karim

09/14/2021, 6:34 PM
I think you need to merge all these state variables to a single State
c

Colton Idle

09/15/2021, 12:51 AM
File a bug with a minimal repro project and they will help you! (they helped with my perf issue I filed)
s

Spikey Sanju

09/27/2021, 7:11 AM
@Colton Idle @Shakil Karim @adjpd I figured out the issue. It’s not because of Compose. I’ve been doing memory intensive process by parsing the huge
Emoji's json
file with
Kotlin Serialization
(ie.
22,000 lines
approx). So i’m facing this
800 - 1200 ms
Lag when navigating to
Add task screen
. In some
high end
devices it is working perfectly fine. Thanks you all!!