Sticker management v2 - Implement multi-select.

This commit is contained in:
Jeffrey Starke
2025-04-30 15:06:20 -04:00
committed by Cody Henthorne
parent 030678b029
commit c8bfc88bed
5 changed files with 291 additions and 92 deletions

View File

@@ -10,6 +10,21 @@ import android.view.animation.AnimationUtils
import android.widget.ImageView
import android.widget.LinearLayout
import android.widget.TextView
import androidx.compose.animation.AnimatedVisibility
import androidx.compose.animation.core.FastOutSlowInEasing
import androidx.compose.animation.core.tween
import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut
import androidx.compose.animation.slideInVertically
import androidx.compose.animation.slideOutVertically
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.wrapContentHeight
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.unit.dp
import androidx.compose.ui.viewinterop.AndroidView
import androidx.interpolator.view.animation.FastOutSlowInInterpolator
import org.thoughtcrime.securesms.R
import org.thoughtcrime.securesms.util.ViewUtil
@@ -20,7 +35,7 @@ import org.thoughtcrime.securesms.util.ViewUtil
*
* Overflow items are rendered in a [SignalContextMenu].
*/
class SignalBottomActionBar(context: Context, attributeSet: AttributeSet) : LinearLayout(context, attributeSet) {
class SignalBottomActionBar(context: Context, attributeSet: AttributeSet?) : LinearLayout(context, attributeSet) {
val items: MutableList<ActionItem> = mutableListOf()
@@ -118,3 +133,46 @@ class SignalBottomActionBar(context: Context, attributeSet: AttributeSet) : Line
view.setOnClickListener { item.action.run() }
}
}
@Composable
fun SignalBottomActionBar(
visible: Boolean = true,
items: List<ActionItem>,
modifier: Modifier = Modifier
) {
val slideAnimationOffset = with(LocalDensity.current) { 40.dp.roundToPx() }
val enterAnimation = slideInVertically(
animationSpec = tween(durationMillis = 250, easing = FastOutSlowInEasing),
initialOffsetY = { slideAnimationOffset }
) + fadeIn(
animationSpec = tween(durationMillis = 250, easing = FastOutSlowInEasing)
)
val exitAnimation = slideOutVertically(
animationSpec = tween(durationMillis = 250, easing = FastOutSlowInEasing),
targetOffsetY = { slideAnimationOffset }
) + fadeOut(
animationSpec = tween(durationMillis = 250, easing = FastOutSlowInEasing)
)
AnimatedVisibility(
visible = visible,
enter = enterAnimation,
exit = exitAnimation,
modifier = modifier
.fillMaxWidth()
.padding(horizontal = 20.dp, vertical = 16.dp)
.wrapContentHeight()
) {
AndroidView(
factory = { context ->
SignalBottomActionBar(context, null)
.apply { setItems(items) }
},
update = { view ->
view.setItems(items)
}
)
}
}