می توانید از کتابخانه های مورد علاقه خود در Compose استفاده کنید. این بخش نحوه ترکیب چند مورد از مفیدترین کتابخانه ها را شرح می دهد.
فعالیت
برای استفاده از Compose در یک اکتیویتی، باید از ComponentActivity
استفاده کنید، یک زیر کلاس از Activity
که LifecycleOwner
و اجزای مناسب را برای Compose ارائه میکند. همچنین API های اضافی را ارائه می کند که کد شما را از روش های نادیده گرفته شده در کلاس فعالیت شما جدا می کند. Activity Compose این APIها را در معرض مواد composable قرار میدهد به طوری که دیگر نیازی به حذف روشهای خارج از composableهای شما یا بازیابی یک نمونه Activity
صریح نیست. علاوه بر این، این APIها تضمین میکنند که فقط یک بار مقداردهی اولیه میشوند، از ترکیب مجدد جان سالم به در میبرند و در صورت حذف شدن ترکیبپذیر از ترکیب، به درستی پاک میشوند.
نتیجه فعالیت
API rememberLauncherForActivityResult()
به شما امکان می دهد از یک فعالیت در composable خود نتیجه بگیرید :
@Composable fun GetContentExample() { var imageUri by remember { mutableStateOf<Uri?>(null) } val launcher = rememberLauncherForActivityResult(ActivityResultContracts.GetContent()) { uri: Uri? -> imageUri = uri } Column { Button(onClick = { launcher.launch("image/*") }) { Text(text = "Load Image") } Image( painter = rememberAsyncImagePainter(imageUri), contentDescription = "My Image" ) } }
این مثال یک قرارداد ساده GetContent()
را نشان می دهد. با ضربه زدن روی دکمه درخواست اجرا می شود. لامبدای انتهایی برای rememberLauncherForActivityResult()
پس از انتخاب تصویر توسط کاربر و بازگشت به فعالیت راهاندازی فراخوانی میشود. این تصویر انتخاب شده را با استفاده از تابع rememberImagePainter()
Coil بارگیری می کند.
هر زیر کلاس ActivityResultContract
را می توان به عنوان اولین آرگومان برای rememberLauncherForActivityResult()
استفاده کرد. این بدان معنی است که شما می توانید از این تکنیک برای درخواست محتوا از چارچوب و سایر الگوهای رایج استفاده کنید. شما همچنین می توانید قراردادهای سفارشی خود را ایجاد کرده و با این تکنیک از آنها استفاده کنید.
درخواست مجوزهای زمان اجرا
از همان Activity Result API و rememberLauncherForActivityResult()
توضیح داده شده در بالا میتوان برای درخواست مجوزهای زمان اجرا با استفاده از قرارداد RequestPermission
برای یک مجوز واحد یا قرارداد RequestMultiplePermissions
برای چندین مجوز استفاده کرد.
کتابخانه Accompanist Permissions همچنین میتواند یک لایه بالای آن APIها برای ترسیم وضعیت اعطا شده فعلی برای مجوزها به حالتی که UI Compose شما میتواند استفاده کند، استفاده شود.
کنترل دکمه بازگشت سیستم
برای ارائه پیمایش برگشت سفارشی و نادیده گرفتن رفتار پیشفرض دکمه بازگشت سیستم از داخل composable خود، composable شما میتواند BackHandler
برای رهگیری آن رویداد استفاده کند:
var backHandlingEnabled by remember { mutableStateOf(true) } BackHandler(backHandlingEnabled) { // Handle back press }
آرگومان اول کنترل می کند که آیا BackHandler
در حال حاضر فعال است یا خیر. شما می توانید از این آرگومان برای غیرفعال کردن موقت کنترلر خود بر اساس وضعیت جزء خود استفاده کنید. اگر کاربر یک رویداد بازگشتی سیستم را راهاندازی کند و BackHandler
در حال حاضر فعال باشد، لامبدای انتهایی فراخوانی میشود.
ViewModel
اگر از کتابخانه ViewModel کامپوننتهای معماری استفاده میکنید، میتوانید با فراخوانی تابع viewModel()
ViewModel
از هر composable دسترسی داشته باشید. وابستگی زیر را به فایل Gradle خود اضافه کنید:
شیار
dependencies { implementation 'androidx.lifecycle:lifecycle-viewmodel-compose:2.8.5' }
کاتلین
dependencies { implementation("androidx.lifecycle:lifecycle-viewmodel-compose:2.8.5") }
سپس می توانید از تابع viewModel()
در کد خود استفاده کنید.
class MyViewModel : ViewModel() { /*...*/ } // import androidx.lifecycle.viewmodel.compose.viewModel @Composable fun MyScreen( viewModel: MyViewModel = viewModel() ) { // use viewModel here }
viewModel()
یک ViewModel
موجود را برمی گرداند یا یک مدل جدید ایجاد می کند. به طور پیشفرض، ViewModel
برگردانده شده در محدوده فعالیت، قطعه یا مقصد ناوبری محصور قرار میگیرد و تا زمانی که محدوده فعال است، حفظ میشود.
به عنوان مثال، اگر composable در یک اکتیویتی استفاده شود، viewModel()
همان نمونه را برمی گرداند تا زمانی که اکتیویتی به پایان برسد یا فرآیند از بین برود.
class MyViewModel : ViewModel() { /*...*/ } // import androidx.lifecycle.viewmodel.compose.viewModel @Composable fun MyScreen( // Returns the same instance as long as the activity is alive, // just as if you grabbed the instance from an Activity or Fragment viewModel: MyViewModel = viewModel() ) { /* ... */ } @Composable fun MyScreen2( viewModel: MyViewModel = viewModel() // Same instance as in MyScreen ) { /* ... */ }
دستورالعمل های استفاده
شما معمولاً به نمونه های ViewModel
در composable های سطح صفحه دسترسی دارید، یعنی نزدیک به یک root composable که از یک فعالیت، قطعه یا مقصد یک نمودار ناوبری فراخوانی می شود. این به این دلیل است که ViewModel
ها به طور پیش فرض به آن اشیاء سطح صفحه نمایش داده می شوند. اطلاعات بیشتر در مورد چرخه حیات ViewModel
و دامنه را در اینجا بخوانید.
سعی کنید از انتقال نمونه های ViewModel
به دیگر composable ها خودداری کنید، زیرا این کار می تواند آزمایش آن ها را دشوارتر کند و پیش نمایش ها را خراب کند. در عوض، فقط داده ها و توابع مورد نیاز آنها را به عنوان پارامتر ارسال کنید.
میتوانید از نمونههای ViewModel
برای مدیریت وضعیت برای ترکیبپذیرهای سطح زیر صفحه استفاده کنید، با این حال، از چرخه حیات و محدوده ViewModel
آگاه باشید. اگر composable مستقل است، ممکن است بخواهید از Hilt برای تزریق ViewModel
استفاده کنید تا مجبور نباشید وابستگیها را از composableهای والد منتقل کنید.
اگر ViewModel
شما وابستگی دارد، viewModel()
یک ViewModelProvider.Factory
اختیاری را به عنوان پارامتر می گیرد.
برای اطلاعات بیشتر درباره ViewModel
در Compose و نحوه استفاده از نمونهها با کتابخانه Navigation Compose یا فعالیتها و قطعات، به اسناد قابلیت همکاری مراجعه کنید.
جریان های داده
Compose همراه با برنامه های افزودنی برای محبوب ترین راه حل های مبتنی بر جریان اندروید ارائه می شود. هر یک از این پسوندها توسط یک مصنوع متفاوت ارائه می شود:
-
LiveData.observeAsState()
موجود در مصنوعandroidx.compose.runtime:runtime-livedata:$composeVersion
. -
Flow.collectAsState()
به وابستگی اضافی نیاز ندارد. -
Observable.subscribeAsState()
موجود در مصنوعandroidx.compose.runtime:runtime-rxjava2:$composeVersion
یاandroidx.compose.runtime:runtime-rxjava3:$composeVersion
.
این مصنوعات به عنوان یک شنونده ثبت می شوند و ارزش ها را به عنوان یک State
نشان می دهند. هر زمان که یک مقدار جدید منتشر می شود، Compose آن قسمت هایی از UI را که در آن state.value
استفاده می شود، دوباره ترکیب می کند. به عنوان مثال، در این کد، ShowData
هر بار که exampleLiveData
یک مقدار جدید منتشر می کند، دوباره ترکیب می کند.
// import androidx.lifecycle.viewmodel.compose.viewModel @Composable fun MyScreen( viewModel: MyViewModel = viewModel() ) { val dataExample = viewModel.exampleLiveData.observeAsState() // Because the state is read here, // MyScreen recomposes whenever dataExample changes. dataExample.value?.let { ShowData(dataExample) } }
عملیات ناهمزمان در Compose
Jetpack Compose به شما امکان می دهد عملیات ناهمزمان را با استفاده از کوروتین ها از داخل اجزای سازنده خود اجرا کنید.
برای اطلاعات بیشتر، APIهای LaunchedEffect
، produceState
و rememberCoroutineScope
را در اسناد عوارض جانبی مشاهده کنید.
ناوبری
مؤلفه Navigation از برنامه های Jetpack Compose پشتیبانی می کند. برای اطلاعات بیشتر به پیمایش با نوشتن و انتقال Jetpack Navigation به Navigation Compose مراجعه کنید.
هیلت
Hilt راه حل پیشنهادی برای تزریق وابستگی در برنامه های اندروید است و با Compose یکپارچه کار می کند.
تابع viewModel()
ذکر شده در بخش ViewModel به طور خودکار از ViewModel استفاده می کند که Hilt با حاشیه نویسی @HiltViewModel
می سازد. ما اسنادی را با اطلاعاتی در مورد ادغام ViewModel Hilt ارائه کردهایم.
@HiltViewModel class MyViewModel @Inject constructor( private val savedStateHandle: SavedStateHandle, private val repository: ExampleRepository ) : ViewModel() { /* ... */ } // import androidx.lifecycle.viewmodel.compose.viewModel @Composable fun MyScreen( viewModel: MyViewModel = viewModel() ) { /* ... */ }
هیلت و ناوبری
Hilt همچنین با کتابخانه Navigation Compose یکپارچه می شود. وابستگی های اضافی زیر را به فایل Gradle خود اضافه کنید:
شیار
dependencies { implementation 'androidx.hilt:hilt-navigation-compose:1.2.0' }
کاتلین
dependencies { implementation("androidx.hilt:hilt-navigation-compose:1.2.0") }
هنگام استفاده از Navigation Compose، همیشه از تابع composable hiltViewModel
برای به دست آوردن یک نمونه از ViewModel
@HiltViewModel
خود استفاده کنید. این با قطعات یا فعالیت هایی که با @AndroidEntryPoint
حاشیه نویسی شده اند کار می کند.
به عنوان مثال، اگر ExampleScreen
یک مقصد در یک نمودار ناوبری است، hiltViewModel()
فراخوانی کنید تا نمونه ای از ExampleViewModel
به مقصد برسد، همانطور که در قطعه کد زیر نشان داده شده است:
// import androidx.hilt.navigation.compose.hiltViewModel @Composable fun MyApp() { val navController = rememberNavController() val startRoute = "example" NavHost(navController, startDestination = startRoute) { composable("example") { backStackEntry -> // Creates a ViewModel from the current BackStackEntry // Available in the androidx.hilt:hilt-navigation-compose artifact val viewModel = hiltViewModel<MyViewModel>() MyScreen(viewModel) } /* ... */ } }
اگر نیاز به بازیابی نمونه ViewModel
با محدوده مسیرهای ناوبری یا نمودار ناوبری دارید، از تابع composable hiltViewModel
استفاده کنید و backStackEntry
مربوطه را به عنوان پارامتر ارسال کنید:
// import androidx.hilt.navigation.compose.hiltViewModel // import androidx.navigation.compose.getBackStackEntry @Composable fun MyApp() { val navController = rememberNavController() val startRoute = "example" val innerStartRoute = "exampleWithRoute" NavHost(navController, startDestination = startRoute) { navigation(startDestination = innerStartRoute, route = "Parent") { // ... composable("exampleWithRoute") { backStackEntry -> val parentEntry = remember(backStackEntry) { navController.getBackStackEntry("Parent") } val parentViewModel = hiltViewModel<ParentViewModel>(parentEntry) ExampleWithRouteScreen(parentViewModel) } } } }
صفحه بندی
کتابخانه Paging بارگیری تدریجی داده ها را برای شما آسان می کند و در Compose پشتیبانی می شود. صفحه انتشار صفحهبندی حاوی اطلاعاتی درباره وابستگی اضافی paging-compose
است که باید به پروژه و نسخه آن اضافه شود.
در اینجا یک نمونه از APIهای Compose کتابخانه Paging آورده شده است:
@Composable fun MyScreen(flow: Flow<PagingData<String>>) { val lazyPagingItems = flow.collectAsLazyPagingItems() LazyColumn { items( lazyPagingItems.itemCount, key = lazyPagingItems.itemKey { it } ) { index -> val item = lazyPagingItems[index] Text("Item is $item") } } }
برای اطلاعات بیشتر در مورد استفاده از صفحهبندی در نوشتن، فهرستها و مستندات شبکهها را بررسی کنید.
نقشه ها
می توانید از کتابخانه Maps Compose برای ارائه Google Maps در برنامه خود استفاده کنید. در اینجا یک مثال استفاده آمده است:
@Composable fun MapsExample() { val singapore = LatLng(1.35, 103.87) val cameraPositionState = rememberCameraPositionState { position = CameraPosition.fromLatLngZoom(singapore, 10f) } GoogleMap( modifier = Modifier.fillMaxSize(), cameraPositionState = cameraPositionState ) { Marker( state = remember { MarkerState(position = singapore) }, title = "Singapore", snippet = "Marker in Singapore" ) } }
برای شما توصیه می شود
- توجه: وقتی جاوا اسکریپت خاموش است، متن پیوند نمایش داده می شود
- عوارض جانبی در Compose
- State و Jetpack Compose
- حالت رابط کاربری را در Compose ذخیره کنید