SwipeToDismissBox
कॉम्पोनेंट की मदद से, उपयोगकर्ता किसी आइटम को बाईं या दाईं ओर स्वाइप करके उसे खारिज या अपडेट कर सकता है.
एपीआई का प्लैटफ़ॉर्म
स्वाइप जेस्चर से ट्रिगर होने वाली कार्रवाइयां लागू करने के लिए, SwipeToDismissBox
कॉम्पोज़ेबल का इस्तेमाल करें. मुख्य पैरामीटर में ये शामिल हैं:
state
: स्वाइप आइटम पर कैलकुलेशन से जनरेट हुई वैल्यू को सेव करने के लिए बनाई गईSwipeToDismissBoxState
स्थिति, जो जनरेट होने पर इवेंट ट्रिगर करती है.backgroundContent
: आइटम के कॉन्टेंट के पीछे दिखने वाला कंपोज़ेबल, जिसे अपनी पसंद के मुताबिक बनाया जा सकता है. यह कॉन्टेंट स्वाइप करने पर दिखता है.
बुनियादी उदाहरण: स्वाइप करके अपडेट करना या खारिज करना
इस उदाहरण में स्निपेट, स्वाइप करने की सुविधा को दिखाते हैं. इस सुविधा के तहत, स्क्रीन पर मौजूद आइटम को शुरू से आखिर तक स्वाइप करने पर, वह अपडेट हो जाता है. वहीं, आखिर से शुरू तक स्वाइप करने पर, वह आइटम हट जाता है.
data class TodoItem( val itemDescription: String, var isItemDone: Boolean = false )
@Composable fun TodoListItem( todoItem: TodoItem, onToggleDone: (TodoItem) -> Unit, onRemove: (TodoItem) -> Unit, modifier: Modifier = Modifier, ) { val swipeToDismissBoxState = rememberSwipeToDismissBoxState( confirmValueChange = { if (it == StartToEnd) onToggleDone(todoItem) else if (it == EndToStart) onRemove(todoItem) // Reset item when toggling done status it != StartToEnd } ) SwipeToDismissBox( state = swipeToDismissBoxState, modifier = modifier.fillMaxSize(), backgroundContent = { when (swipeToDismissBoxState.dismissDirection) { StartToEnd -> { Icon( if (todoItem.isItemDone) Icons.Default.CheckBox else Icons.Default.CheckBoxOutlineBlank, contentDescription = if (todoItem.isItemDone) "Done" else "Not done", modifier = Modifier .fillMaxSize() .background(Color.Blue) .wrapContentSize(Alignment.CenterStart) .padding(12.dp), tint = Color.White ) } EndToStart -> { Icon( imageVector = Icons.Default.Delete, contentDescription = "Remove item", modifier = Modifier .fillMaxSize() .background(Color.Red) .wrapContentSize(Alignment.CenterEnd) .padding(12.dp), tint = Color.White ) } Settled -> {} } } ) { ListItem( headlineContent = { Text(todoItem.itemDescription) }, supportingContent = { Text("swipe me to update or remove.") } ) } }
कोड के बारे में अहम जानकारी
swipeToDismissBoxState
, कॉम्पोनेंट की स्थिति को मैनेज करता है. आइटम के साथ इंटरैक्शन होने के बाद, यहconfirmValueChange
कॉलबैक को ट्रिगर करता है. कॉलबैक बॉडी, अलग-अलग संभावित कार्रवाइयों को मैनेज करता है. कॉलबैक एक बोलियन वैल्यू दिखाता है. इससे कॉम्पोनेंट को पता चलता है कि उसे खारिज करने वाला ऐनिमेशन दिखाना है या नहीं. इस मामले में:- अगर आइटम को शुरू से आखिर तक स्वाइप किया जाता है, तो यह
onToggleDone
लैम्ब्डा को कॉल करता है और मौजूदाtodoItem
को पास करता है. यह, 'क्या-क्या करें' आइटम को अपडेट करने से जुड़ा है. - अगर आइटम को आखिर से शुरू तक स्वाइप किया जाता है, तो यह
onRemove
lambda को कॉल करता है और मौजूदाtodoItem
को पास करता है. यह, 'क्या-क्या करें' सूची में मौजूद आइटम को मिटाने के बराबर है. it != StartToEnd
: अगर स्वाइप की दिशाStartToEnd
नहीं है, तो यह लाइनtrue
दिखाती है. अगर दिशाStartToEnd
है, तो यहfalse
दिखाती है.false
को वापस लाने से, "टॉगल हो गया" स्वाइप करने के बाद,SwipeToDismissBox
तुरंत नहीं दिखता. इससे विज़ुअल की पुष्टि करने या ऐनिमेशन दिखाने में मदद मिलती है.
- अगर आइटम को शुरू से आखिर तक स्वाइप किया जाता है, तो यह
SwipeToDismissBox
, हर आइटम पर हॉरिज़ॉन्टल स्वाइप इंटरैक्शन की सुविधा चालू करता है. विश्राम की स्थिति में, यह कॉम्पोनेंट का अंदरूनी कॉन्टेंट दिखाता है. हालांकि, जब कोई उपयोगकर्ता स्वाइप करना शुरू करता है, तो कॉन्टेंट हट जाता है औरbackgroundContent
दिखता है. सामान्य कॉन्टेंट औरbackgroundContent
, दोनों को पैरंट कंटेनर की सभी पाबंदियां मिलती हैं, ताकि वे खुद को रेंडर कर सकें.content
कोbackgroundContent
के ऊपर ड्रॉ किया गया है. इस मामले में:backgroundContent
कोIcon
के तौर पर लागू किया गया है. इसका बैकग्राउंड रंग,SwipeToDismissBoxValue
पर आधारित है:Blue
स्वाइप करते समयStartToEnd
— किसी टास्क को टॉगल करना.Red
EndToStart
को स्वाइप करते समय — 'क्या-क्या करें' सूची में मौजूद किसी आइटम को मिटाना.Settled
के लिए बैकग्राउंड में कुछ नहीं दिखता — जब आइटम को स्वाइप नहीं किया जा रहा है, तो बैकग्राउंड में कुछ नहीं दिखता.- इसी तरह, स्वाइप करने की दिशा के हिसाब से
Icon
दिखता है: StartToEnd
,CheckBox
आइकॉन तब दिखाता है, जब 'क्या-क्या करें' सूची में मौजूद कोई आइटम पूरा हो जाता है. अगर आइटम पूरा नहीं होता है, तोCheckBoxOutlineBlank
आइकॉन दिखता है.EndToStart
,Delete
आइकॉन दिखाता है.
@Composable private fun SwipeItemExample() { val todoItems = remember { mutableStateListOf( TodoItem("Pay bills"), TodoItem("Buy groceries"), TodoItem("Go to gym"), TodoItem("Get dinner") ) } LazyColumn { items( items = todoItems, key = { it.itemDescription } ) { todoItem -> TodoListItem( todoItem = todoItem, onToggleDone = { todoItem -> todoItem.isItemDone = !todoItem.isItemDone }, onRemove = { todoItem -> todoItems -= todoItem }, modifier = Modifier.animateItem() ) } } }
कोड के बारे में अहम जानकारी
mutableStateListOf(...)
, निगरानी की जा सकने वाली ऐसी सूची बनाता है जिसमेंTodoItem
ऑब्जेक्ट हो सकते हैं. जब इस सूची में कोई आइटम जोड़ा या हटाया जाता है, तो Compose उन यूज़र इंटरफ़ेस (यूआई) के हिस्सों को फिर से कॉम्पोज़ करता है जो इस सूची पर निर्भर होते हैं.mutableStateListOf()
में, चारTodoItem
ऑब्जेक्ट को उनके ब्यौरे के साथ शुरू किया जाता है: "बिल भरना", "राशन खरीदना", "जिम जाना", और "डिनर पाना".
LazyColumn
,todoItems
की वर्टिकल स्क्रोलिंग सूची दिखाता है.onToggleDone = { todoItem -> ... }
एक कॉलबैक फ़ंक्शन है, जिसेTodoListItem
में से शुरू किया जाता है. ऐसा तब होता है, जब उपयोगकर्ता किसी ऑब्जेक्ट को 'हो गया' के तौर पर मार्क करता है. यहtodoItem
कीisItemDone
प्रॉपर्टी को अपडेट करता है.todoItems
एकmutableStateListOf
है, इसलिए यह बदलाव यूज़र इंटरफ़ेस (यूआई) को अपडेट करते हुए, फिर से कॉम्पोज़ करने की प्रोसेस को ट्रिगर करता है.onRemove = { todoItem -> ... }
एक कॉलबैक फ़ंक्शन है, जो उपयोगकर्ता के आइटम हटाने पर ट्रिगर होता है. इससेtodoItems
सूची से कोईtodoItem
हट जाता है. इससे, फिर से कॉम्पोज़िशन भी होता है और आइटम को दिखाई गई सूची से हटा दिया जाता है.- हर
TodoListItem
परanimateItem
मॉडिफ़ायर लागू किया जाता है, ताकि आइटम खारिज होने पर मॉडिफ़ायर काplacementSpec
कॉल किया जा सके. इससे, आइटम को हटाने के साथ-साथ सूची में मौजूद अन्य आइटम का क्रम बदलने की जानकारी ऐनिमेशन के ज़रिए दी जाती है.
नतीजा
नीचे दिए गए वीडियो में, पिछले स्निपेट में मौजूद, स्वाइप करके हटाने की बुनियादी सुविधा के बारे में बताया गया है:
सैंपल कोड का पूरा ब्यौरा देखने के लिए, GitHub की सोर्स फ़ाइल देखें.
बेहतर उदाहरण: स्वाइप करने पर बैकग्राउंड के रंग में ऐनिमेशन जोड़ना
नीचे दिए गए स्निपेट में, स्वाइप करने पर किसी आइटम के बैकग्राउंड के रंग को ऐनिमेट करने के लिए, पोज़िशनल थ्रेशोल्ड को शामिल करने का तरीका बताया गया है.
data class TodoItem( val itemDescription: String, var isItemDone: Boolean = false )
@Composable fun TodoListItemWithAnimation( todoItem: TodoItem, onToggleDone: (TodoItem) -> Unit, onRemove: (TodoItem) -> Unit, modifier: Modifier = Modifier, ) { val swipeToDismissBoxState = rememberSwipeToDismissBoxState( confirmValueChange = { if (it == StartToEnd) onToggleDone(todoItem) else if (it == EndToStart) onRemove(todoItem) // Reset item when toggling done status it != StartToEnd } ) SwipeToDismissBox( state = swipeToDismissBoxState, modifier = modifier.fillMaxSize(), backgroundContent = { when (swipeToDismissBoxState.dismissDirection) { StartToEnd -> { Icon( if (todoItem.isItemDone) Icons.Default.CheckBox else Icons.Default.CheckBoxOutlineBlank, contentDescription = if (todoItem.isItemDone) "Done" else "Not done", modifier = Modifier .fillMaxSize() .drawBehind { drawRect(lerp(Color.LightGray, Color.Blue, swipeToDismissBoxState.progress)) } .wrapContentSize(Alignment.CenterStart) .padding(12.dp), tint = Color.White ) } EndToStart -> { Icon( imageVector = Icons.Default.Delete, contentDescription = "Remove item", modifier = Modifier .fillMaxSize() .background(lerp(Color.LightGray, Color.Red, swipeToDismissBoxState.progress)) .wrapContentSize(Alignment.CenterEnd) .padding(12.dp), tint = Color.White ) } Settled -> {} } } ) { OutlinedCard(shape = RectangleShape) { ListItem( headlineContent = { Text(todoItem.itemDescription) }, supportingContent = { Text("swipe me to update or remove.") } ) } } }
कोड के बारे में अहम जानकारी
drawBehind
,Icon
composable के कॉन्टेंट के पीछे सीधे कैनवस में ड्रॉ करता है.drawRect()
, कैनवस पर एक रेक्टैंगल बनाता है और ड्रॉइंग के दायरे के पूरे बॉर्डर को तय किए गएColor
से भरता है.
- स्वाइप करने पर, आइटम के बैकग्राउंड का रंग
lerp
का इस्तेमाल करके आसानी से बदल जाता है.StartToEnd
से स्वाइप करने पर, बैकग्राउंड का रंग धीरे-धीरे हल्के स्लेटी से नीले में बदलता है.EndToStart
से स्वाइप करने पर, बैकग्राउंड का रंग धीरे-धीरे हल्के स्लेटी से लाल में बदल जाता है.- एक रंग से दूसरे रंग में ट्रांज़िशन की रफ़्तार,
swipeToDismissBoxState.progress
से तय होती है.
OutlinedCard
, सूची के आइटम के बीच थोड़ा सा विज़ुअल सेपरेशन जोड़ता है.
@Composable private fun SwipeItemWithAnimationExample() { val todoItems = remember { mutableStateListOf( TodoItem("Pay bills"), TodoItem("Buy groceries"), TodoItem("Go to gym"), TodoItem("Get dinner") ) } LazyColumn { items( items = todoItems, key = { it.itemDescription } ) { todoItem -> TodoListItemWithAnimation( todoItem = todoItem, onToggleDone = { todoItem -> todoItem.isItemDone = !todoItem.isItemDone }, onRemove = { todoItem -> todoItems -= todoItem }, modifier = Modifier.animateItem() ) } } }
कोड के बारे में अहम जानकारी
- इस कोड के बारे में अहम बातें जानने के लिए, पिछले सेक्शन में मौजूद अहम बातें देखें. इसमें एक जैसे कोड स्निपेट के बारे में बताया गया है.
नतीजा
इस वीडियो में, ऐनिमेशन वाले बैकग्राउंड रंग के साथ बेहतर सुविधाओं को दिखाया गया है:
सैंपल कोड का पूरा ब्यौरा देखने के लिए, GitHub की सोर्स फ़ाइल देखें.