簡體   English   中英

在 Jetpack Compose 中單擊時更改表面項目的背景顏色

[英]Change background color of surface item when click in jetpack compose

當用戶 select 是Surface上的項目時,我想更改背景顏色。 我在我的父母中使用Column ,所以我不能制作LazyColumn 所以我正在使用Foreach來制作視圖列表。 默認情況下不會選擇任何視圖,當用戶單擊項目時我想更改顏色。 注意:一次只有一項將是 select。

掃描設備列表

@Composable
fun ColumnScope.ScanDeviceList(
    scanDeviceList: List<ScanResult>,
    modifier: Modifier = Modifier,
    pairSelectedDevice: () -> Unit
) {
    Spacer()
    AnimatedVisibility() {
        Column {
            Text()
            Spacer()
            scanDeviceList.forEachIndexed { index, scanResult ->
                ClickableItemContainer(
                    rippleColor = AquaLightOpacity10,
                    content = {
                        ScanDeviceItem(index, scanResult, scanDeviceList)
                    }
                ){}
            }
            AvailableWarningText()
            PairSelectedDevice(pairSelectedDevice)
        }
    }
}

掃描設備項

@Composable
fun ScanDeviceItem(
    index: Int,
    scanResult: ScanResult,
    scanDeviceList: List<ScanResult>
) {
    Column {
        if (index == 0) {
            Divider(color = Cloudy, thickness = 1.dp)
        }
        Text(
            text = scanResult.device.name,
            modifier = Modifier.padding(vertical = 10.dp)
        )
        if (index <= scanDeviceList.lastIndex) {
            Divider(color = Cloudy, thickness = 1.dp)
        }
    }
}

可點擊項目容器

@OptIn(ExperimentalMaterialApi::class)
@Composable
fun ClickableItemContainer(
    rippleColor: Color = TealLight,
    content: @Composable (MutableInteractionSource) -> Unit,
    clickAction: () -> Unit
) {
    val interactionSource = remember { MutableInteractionSource() }
    CompositionLocalProvider(
        LocalRippleTheme provides AbcRippleTheme(rippleColor),
        content = {
            Surface(
                onClick = { clickAction() },
                interactionSource = interactionSource,
                color = White
            ) {
                content(interactionSource)
            }
        }
    )
}

我想要這樣的東西

在此處輸入圖像描述

現在上面的解決方案只適用於漣漪效應,現在我想一次將我的 function 擴展到 select 一個項目。 非常感謝

您可以存儲選定的索引,並在用戶單擊每個項目時使用clickAction更新其值。

就像是:

@Composable
fun MyList(

      var selectedIndex by remember { mutableStateOf(-1) }

      Column() {
          itemsList.forEachIndexed() { index, item ->
              MyItem(
                  selected = selectedIndex == index,
                  clickAction = { selectedIndex = index }
              )
      }
}

@Composable
fun MyItem(
    selected : Boolean = false,
    clickAction: () -> Unit
){
     Surface(
        onClick = { clickAction() },
        color = if (selected) Color.Red else Color.Yellow
     ) {
         Text("Item...")
     }
}

要一次只選擇項目,您可以遵循類似的行為。 您將所選項目保存在 mutableState 變量中,例如:

var itemSelected by remember { mutableState(ScanDeviceResult()) }

之后,當您單擊該項目時,您會更新 itemSelected,例如:

ClickableItemContainer(
                    rippleColor = AquaLightOpacity10,
                    content = {
                        ScanDeviceItem(index, scanResult, scanDeviceList)
                    }
                ){ newItemSelected ->
itemSelected = newItemSelected
}

現在,每個 ClickableItemContainer 都需要有一個關聯的 ScanResult。

    @OptIn(ExperimentalMaterialApi::class)
@Composable
fun ClickableItemContainer(
itemSelected: ScanResult,
scanResult: ScanResult,
    rippleColor: Color = TealLight,
    content: @Composable (MutableInteractionSource) -> Unit,
    clickAction: (ScanResult) -> Unit
) {
    val interactionSource = remember { MutableInteractionSource() }
    CompositionLocalProvider(
        LocalRippleTheme provides AbcRippleTheme(rippleColor),
        content = {
            Surface(
                onClick = { clickAction.invoke(scanResult) },
                interactionSource = interactionSource,
                color = if (itemSelected == scanResult) YOUR_BACKGROUND-SELECTED_COLOR else White
            ) {
                content(interactionSource)
            }
        }
    )
}

現在,在您的 ScanDeviceList 方法上:

    @Composable
    fun ColumnScope.ScanDeviceList(
        itemSelected: MutableState<ScanResult>,
        scanDeviceList: List<ScanResult>,
        modifier: Modifier = Modifier,
        pairSelectedDevice: () -> Unit
    ) {
        Spacer()
        AnimatedVisibility() {
            Column {
                Text()
                Spacer()
                scanDeviceList.forEachIndexed { index, scanResult ->
                    ClickableItemContainer(
                        itemSelected = itemSelected,
                        scanResult = scanResult,
                        rippleColor = AquaLightOpacity10,
                        content = {
                            ScanDeviceItem(index, scanResult, scanDeviceList)
                        }
                    ){ scanResultToSelect ->
               itemSelected = scanResultToSelect
}
                }
                AvailableWarningText()
                PairSelectedDevice(pairSelectedDevice)
            }
        }
    }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM