Skip to content
This repository has been archived by the owner on Mar 18, 2024. It is now read-only.

Commit

Permalink
Improve color picker
Browse files Browse the repository at this point in the history
  • Loading branch information
AnkitSuda committed Nov 25, 2022
1 parent dc17f13 commit e8adf45
Show file tree
Hide file tree
Showing 7 changed files with 215 additions and 61 deletions.
30 changes: 23 additions & 7 deletions app/src/main/java/com/ankitsuda/rebound/ui/main/MainScreen.kt
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import androidx.compose.material.icons.outlined.*
import androidx.compose.runtime.*
import androidx.compose.runtime.livedata.observeAsState
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.vector.ImageVector
Expand All @@ -31,6 +32,8 @@ import androidx.compose.ui.res.stringResource
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.unit.dp
import androidx.compose.ui.window.Dialog
import androidx.compose.ui.window.DialogProperties
import androidx.hilt.navigation.compose.hiltViewModel
import androidx.navigation.NavDestination.Companion.hierarchy
import androidx.navigation.NavGraph.Companion.findStartDestination
Expand Down Expand Up @@ -88,7 +91,10 @@ fun MainScreen(
)
}

@OptIn(ExperimentalMaterialApi::class, ExperimentalMaterialNavigationApi::class)
@OptIn(
ExperimentalMaterialApi::class, ExperimentalMaterialNavigationApi::class,
ExperimentalComposeUiApi::class
)
@Composable
private fun MainLayout(
navController: NavHostController,
Expand Down Expand Up @@ -233,12 +239,22 @@ private fun MainLayout(
}

if (dialogVisible) {
AlertDialog(onDismissRequest = {
dialogVisible = false
},
buttons = {
dialogContent()
})
Dialog(
properties = DialogProperties(usePlatformDefaultWidth = false),
onDismissRequest = {
dialogVisible = false
},
content = {
Surface(
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 32.dp),
color = ReboundTheme.colors.background,
shape = ReboundTheme.shapes.large,
content = dialogContent
)
}
)
}
}
}
Expand Down
12 changes: 11 additions & 1 deletion buildSrc/src/main/java/com/ankitsuda/rebound/buildSrc/Deps.kt
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,8 @@ object Deps {
const val materialDesignIcons = "androidx.compose.material:material-icons-core:$version"
const val materialDesignIconsExtended =
"androidx.compose.material:material-icons-extended:$version"
const val constraintLayout = "androidx.constraintlayout:constraintlayout-compose:1.1.0-alpha04"
const val constraintLayout =
"androidx.constraintlayout:constraintlayout-compose:1.1.0-alpha04"
const val liveData = "androidx.compose.runtime:runtime-livedata:$version"
const val activity = "androidx.activity:activity-compose:$activityVersion"
const val viewModels = "androidx.lifecycle:lifecycle-viewmodel-compose:2.4.0"
Expand Down Expand Up @@ -132,6 +133,15 @@ object Deps {
const val common = "androidx.paging:paging-common-ktx:$version"
const val runtime = "androidx.paging:paging-runtime-ktx:$version"
}

object ColorPicker {
private const val version = "0.5.1"
const val composeColorPicker =
"com.godaddy.android.colorpicker:compose-color-picker:$version"
const val composeColorPickerAndroid =
"com.godaddy.android.colorpicker:compose-color-picker-android:$version"

}
}

object Utils {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@

package com.ankitsuda.rebound.ui.components.settings.color_pickers

import androidx.compose.animation.AnimatedContent
import androidx.compose.animation.ExperimentalAnimationApi
import androidx.compose.foundation.layout.*
import androidx.compose.material.Text
import androidx.compose.material.TextButton
Expand All @@ -27,8 +29,10 @@ import com.ankitsuda.common.compose.LocalDialog
import com.ankitsuda.rebound.ui.components.color_picker.ColorPicker1
import com.ankitsuda.rebound.ui.components.color_picker.ColorPickerPresets
import com.ankitsuda.common.compose.R
import com.ankitsuda.rebound.ui.components.color_picker.ColorPicker2


@OptIn(ExperimentalAnimationApi::class)
@Composable
fun ColorPickerDialog1(
defaultColor: Color = Color.Red,
Expand All @@ -43,48 +47,52 @@ fun ColorPickerDialog1(
mutableStateOf(defaultColor)
}

val screenHeight = (LocalConfiguration.current.screenHeightDp / 1.0).dp
// val screenHeight = (LocalConfiguration.current.screenHeightDp / 1.0).dp

Column(
modifier = Modifier
.fillMaxWidth()
.height(screenHeight)
// .height(screenHeight)
) {
if (isPresetLayout) {
ColorPickerPresets(
modifier = Modifier
.fillMaxWidth()
.height(300.dp),
onColorPicked = {
selectedColor = it
},
)
AnimatedContent(targetState = isPresetLayout) {
if (it) {
ColorPickerPresets(
modifier = Modifier
.fillMaxWidth()
.padding(16.dp),
// .height(300.dp),
onColorPicked = { newColor ->
selectedColor = newColor
},
)

} else {
ColorPicker1(
modifier = Modifier
.fillMaxWidth()
.height(600.dp),
colorSelected = {
selectedColor = it
},
defaultColor = defaultColor
)
} else {
ColorPicker2(
modifier = Modifier
.fillMaxWidth()
.padding(16.dp),
colorSelected = { newColor ->
selectedColor = newColor
},
defaultColor = defaultColor
)

}
}


Spacer(Modifier.height(16.dp))

Row(
horizontalArrangement = Arrangement.SpaceBetween,
modifier = Modifier.fillMaxWidth()
modifier = Modifier
.fillMaxWidth()
.padding(bottom = 8.dp, start = 16.dp, end = 16.dp)
) {
TextButton(onClick = {
isPresetLayout = !isPresetLayout
}) {
Text(
text = if (isPresetLayout) stringResource(id = R.string.custom) else stringResource(id = R.string.presets)
text = if (isPresetLayout) stringResource(id = R.string.custom) else stringResource(
id = R.string.presets
)
)
}
TextButton(onClick = with(LocalDialog.current) {
Expand Down
4 changes: 4 additions & 0 deletions modules/common-ui-components/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,11 @@ dependencies {
api project(":modules:common-ui-icons")
api project(":modules:navigation")
api project(":modules:domain")

api Deps.Android.Compose.collapsingToolbar
api Deps.Android.ColorPicker.composeColorPicker
api Deps.Android.ColorPicker.composeColorPickerAndroid

kapt Deps.Dagger.hiltCompiler
coreLibraryDesugaring Deps.Android.desugaring

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
/*
* Copyright (c) 2022 Ankit Suda.
*
* Licensed under the GNU General Public License v3
*
* This is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU General Public License for more details.
*/

package com.ankitsuda.rebound.ui.components.color_picker

import androidx.compose.runtime.*
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.res.stringResource
import com.ankitsuda.base.util.toHexString
import com.ankitsuda.rebound.ui.components.AppTextField
import com.ankitsuda.rebound.ui.components.R

@Composable
fun ColorHexInfo(
modifier: Modifier = Modifier,
selectedColor: Color,
onHexEdited: (Color) -> Unit
) {
val mSelectedColor by remember(selectedColor) {
mutableStateOf(selectedColor)
}
var text by remember(selectedColor) {
mutableStateOf("#" + mSelectedColor.toHexString().uppercase()/*.drop(2)*/)
}

AppTextField(modifier = modifier, value = text, placeholderValue = stringResource(id = R.string.hex), onValueChange = {
text = it
try {
onHexEdited(Color(android.graphics.Color.parseColor(it)))
} catch (e: Exception) {
e.printStackTrace()
}
})
}
Original file line number Diff line number Diff line change
Expand Up @@ -112,33 +112,6 @@ fun ColorPicker1(
}
}


@Composable
private fun ColorHexInfo(
modifier: Modifier = Modifier,
selectedColor: Color,
onHexEdited: (Color) -> Unit
) {
var mSelectedColor by remember {
mutableStateOf(selectedColor)
}
var text by remember {
mutableStateOf("#" + mSelectedColor.toHexString().uppercase().drop(2))
}
if (selectedColor != mSelectedColor) {
mSelectedColor = selectedColor
text = "#" + mSelectedColor.toHexString().uppercase().drop(2)
}
AppTextField(modifier = modifier, value = text, placeholderValue = stringResource(id = R.string.hex), onValueChange = {
text = it
try {
onHexEdited(Color(android.graphics.Color.parseColor(it)))
} catch (e: Exception) {
e.printStackTrace()
}
})
}

private fun Color.toHexString(): String {
val alphaString = (alpha * 255).toInt().toString(16).let { if (it.length == 1) "0$it" else it }
val redString = (red * 255).toInt().toString(16).let { if (it.length == 1) "0$it" else it }
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
/*
* Copyright (c) 2022 Ankit Suda.
*
* Licensed under the GNU General Public License v3
*
* This is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU General Public License for more details.
*/

package com.ankitsuda.rebound.ui.components.color_picker

import androidx.compose.foundation.background
import androidx.compose.foundation.layout.*
import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.layout.onGloballyPositioned
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.unit.dp
import com.godaddy.android.colorpicker.ClassicColorPicker
import com.godaddy.android.colorpicker.HsvColor

@Composable
fun ColorPicker2(
modifier: Modifier = Modifier,
defaultColor: Color = Color.Red,
colorSelected: (Color) -> Unit
) {
var mColorFromHex by remember(key1 = defaultColor) {
mutableStateOf(defaultColor)
}

var mColor by remember(key1 = defaultColor) {
mutableStateOf(defaultColor)
}

LaunchedEffect(key1 = mColorFromHex, block = {
mColor = mColorFromHex
})

var colorHexInfoHeight by remember {
mutableStateOf(30.dp)
}

BoxWithConstraints(
modifier = modifier
) {
val minWidth = this.minWidth
Column(
modifier = Modifier.fillMaxWidth(),
verticalArrangement = Arrangement.spacedBy(8.dp)
) {
key(mColorFromHex) {
ClassicColorPicker(
modifier = Modifier
.fillMaxWidth()
.height(minWidth),
color = mColorFromHex,
onColorChanged = { color: HsvColor ->
mColor = color.toColor()
colorSelected(color.toColor())
}
)
}

Row(
verticalAlignment = Alignment.CenterVertically
) {
Box(
Modifier
.height(colorHexInfoHeight)
.width(colorHexInfoHeight)
.background(mColor)
)
Spacer(modifier = Modifier.width(16.dp))
ColorHexInfo(
modifier = with(LocalDensity.current) {
Modifier.onGloballyPositioned {
colorHexInfoHeight = it.size.height.toDp()
}
},
selectedColor = mColor,
onHexEdited = {
mColorFromHex = it
colorSelected(it)
}
)
}
}
}
}

0 comments on commit e8adf45

Please sign in to comment.