نمای کلی LiveData بخشی از Android Jetpack .
LiveData
یک کلاس دارنده داده قابل مشاهده است. برخلاف یک قابل مشاهده معمولی، LiveData از چرخه حیات آگاه است، به این معنی که به چرخه حیات سایر اجزای برنامه، مانند فعالیتها، قطعات یا خدمات احترام میگذارد. این آگاهی تضمین می کند که LiveData فقط ناظران مؤلفه برنامه را که در حالت چرخه حیات فعال هستند به روز می کند.
LiveData ناظری را که توسط کلاس Observer
نشان داده می شود، در حالت فعال در نظر می گیرد اگر چرخه حیات آن در حالت STARTED
یا RESUMED
باشد. LiveData فقط به ناظران فعال در مورد به روز رسانی ها اطلاع می دهد. ناظران غیرفعال که برای تماشای اشیاء LiveData
ثبت نام کردهاند، از تغییرات مطلع نمیشوند.
شما می توانید یک مشاهده گر جفت شده با یک شی که رابط LifecycleOwner
را پیاده سازی می کند، ثبت کنید. این رابطه به ناظر اجازه می دهد تا زمانی که وضعیت شی Lifecycle
مربوطه به DESTROYED
تغییر می کند، حذف شود. این به ویژه برای فعالیتها و قطعات مفید است، زیرا آنها میتوانند با خیال راحت اشیاء LiveData
را مشاهده کنند و نگران نشت اطلاعات نباشند—فعالیتها و قطعهها بلافاصله پس از از بین رفتن چرخه حیات آنها لغو اشتراک میشوند.
برای اطلاعات بیشتر در مورد نحوه استفاده از LiveData، به کار با اشیاء LiveData مراجعه کنید.
مزایای استفاده از LiveData
استفاده از LiveData مزایای زیر را به همراه دارد:
- اطمینان حاصل می کند که رابط کاربری شما با وضعیت داده شما مطابقت دارد
- LiveData از الگوی ناظر پیروی می کند. LiveData هنگام تغییر داده های اساسی به اشیاء
Observer
اطلاع می دهد. می توانید کد خود را برای به روز رسانی UI در این اشیاءObserver
ادغام کنید. به این ترتیب، لازم نیست هر بار که داده های برنامه تغییر می کند، رابط کاربری را به روز کنید زیرا ناظر این کار را برای شما انجام می دهد. - بدون نشت حافظه
- ناظران به اشیاء
Lifecycle
متصل می شوند و زمانی که چرخه حیات مرتبط با آنها از بین رفت، پس از خود پاکسازی می کنند. - بدون خرابی به دلیل فعالیت های متوقف شده
- اگر چرخه حیات ناظر غیرفعال باشد، مثلاً در مورد یک فعالیت در پشته پشتی، هیچ رویداد LiveData را دریافت نمی کند.
- دیگر نیازی به دست زدن به چرخه عمر دستی نیست
- اجزای UI فقط داده های مربوطه را مشاهده می کنند و مشاهده را متوقف نمی کنند یا از سر نمی گیرند. LiveData به طور خودکار همه اینها را مدیریت می کند زیرا از تغییرات وضعیت چرخه عمر مربوطه هنگام مشاهده آگاه است.
- داده های همیشه به روز
- اگر یک چرخه حیات غیرفعال شود، پس از فعال شدن مجدد، آخرین داده ها را دریافت می کند. برای مثال، فعالیتی که در پسزمینه بود، آخرین دادهها را بلافاصله پس از بازگشت به پیشزمینه دریافت میکند.
- تغییرات پیکربندی مناسب
- اگر یک فعالیت یا قطعه به دلیل تغییر پیکربندی، مانند چرخش دستگاه، دوباره ایجاد شود، بلافاصله آخرین داده های موجود را دریافت می کند.
- به اشتراک گذاری منابع
- میتوانید یک شی
LiveData
با استفاده از الگوی singleton گسترش دهید تا سرویسهای سیستم را بپیچانید تا بتوانند در برنامه شما به اشتراک گذاشته شوند. شیLiveData
یک بار به سرویس سیستم متصل می شود و سپس هر ناظری که به منبع نیاز دارد می تواند فقط شیLiveData
را تماشا کند. برای اطلاعات بیشتر، به Extend LiveData مراجعه کنید.
با اشیاء LiveData کار کنید
برای کار با اشیاء LiveData
مراحل زیر را دنبال کنید:
- یک نمونه از
LiveData
برای نگهداری نوع خاصی از داده ایجاد کنید. این معمولا در کلاسViewModel
شما انجام می شود. - یک شی
Observer
ایجاد کنید که متدonChanged()
تعریف می کند، که کنترل می کند چه اتفاقی می افتد زمانی که داده های نگهداری شدهLiveData
تغییر می کند. شما معمولاً یک شیObserver
را در یک کنترلر UI ایجاد می کنید، مانند یک فعالیت یا قطعه. شی
Observer
را با استفاده از متدobserve()
به شیLiveData
متصل کنید.observe()
یک شیLifecycleOwner
می گیرد. این شیءObserver
را در شیءLiveData
مشترک می کند تا از تغییرات مطلع شود. شما معمولاً شیObserver
را در یک کنترلر UI، مانند یک فعالیت یا قطعه، متصل می کنید.
وقتی مقدار ذخیره شده در شی LiveData
را به روز می کنید، تا زمانی که LifecycleOwner
پیوست شده در حالت فعال باشد، همه ناظران ثبت شده را فعال می کند.
LiveData به ناظران کنترلر رابط کاربری اجازه می دهد تا در به روز رسانی ها مشترک شوند. هنگامی که داده های نگهداری شده توسط شی LiveData
تغییر می کند، UI به طور خودکار در پاسخ به روز می شود.
اشیاء LiveData را ایجاد کنید
LiveData پوششی است که می تواند با هر داده ای، از جمله اشیایی که Collections
پیاده سازی می کنند، مانند List
استفاده شود. یک شی LiveData
معمولاً در یک شی ViewModel
ذخیره می شود و از طریق یک متد getter قابل دسترسی است، همانطور که در مثال زیر نشان داده شده است:
کاتلین
class NameViewModel : ViewModel() { // Create a LiveData with a String val currentName: MutableLiveData<String> by lazy { MutableLiveData<String>() } // Rest of the ViewModel... }
جاوا
public class NameViewModel extends ViewModel { // Create a LiveData with a String private MutableLiveData<String> currentName; public MutableLiveData<String> getCurrentName() { if (currentName == null) { currentName = new MutableLiveData<String>(); } return currentName; } // Rest of the ViewModel... }
در ابتدا، داده ها در یک شی LiveData
تنظیم نشده اند.
میتوانید در راهنمای ViewModel درباره مزایا و استفاده از کلاس ViewModel
اطلاعات بیشتری کسب کنید.
اشیاء LiveData را مشاهده کنید
در بیشتر موارد، متد onCreate()
یک جزء برنامه به دلایل زیر مکان مناسبی برای شروع مشاهده یک شی LiveData
است:
- برای اطمینان از اینکه سیستم از روش
onResume()
یک اکتیویتی یا قطعه فراخوانی اضافی نمیکند. - برای اطمینان از اینکه فعالیت یا قطعه دارای داده هایی است که می تواند به محض فعال شدن نمایش داده شود. به محض اینکه یک جزء برنامه در حالت
STARTED
قرار می گیرد، جدیدترین مقدار را از اشیاءLiveData
که مشاهده می کند دریافت می کند. این تنها در صورتی اتفاق می افتد که شیLiveData
که باید مشاهده شود تنظیم شده باشد.
به طور کلی، LiveData بهروزرسانیها را تنها زمانی که دادهها تغییر میکند و فقط به ناظران فعال ارائه میدهد. یک استثنا در این رفتار این است که ناظران نیز هنگامی که از حالت غیرفعال به حالت فعال تغییر می کنند، به روز رسانی دریافت می کنند. علاوه بر این، اگر مشاهدهگر برای بار دوم از غیرفعال به فعال تغییر کند، فقط در صورتی بهروزرسانی دریافت میکند که مقدار از آخرین باری که فعال شده است تغییر کرده باشد.
کد نمونه زیر نحوه شروع مشاهده یک شی LiveData
را نشان می دهد:
کاتلین
class NameActivity : AppCompatActivity() { // Use the 'by viewModels()' Kotlin property delegate // from the activity-ktx artifact private val model: NameViewModel by viewModels() override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) // Other code to setup the activity... // Create the observer which updates the UI. val nameObserver = Observer<String> { newName -> // Update the UI, in this case, a TextView. nameTextView.text = newName } // Observe the LiveData, passing in this activity as the LifecycleOwner and the observer. model.currentName.observe(this, nameObserver) } }
جاوا
public class NameActivity extends AppCompatActivity { private NameViewModel model; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); // Other code to setup the activity... // Get the ViewModel. model = new ViewModelProvider(this).get(NameViewModel.class); // Create the observer which updates the UI. final Observer<String> nameObserver = new Observer<String>() { @Override public void onChanged(@Nullable final String newName) { // Update the UI, in this case, a TextView. nameTextView.setText(newName); } }; // Observe the LiveData, passing in this activity as the LifecycleOwner and the observer. model.getCurrentName().observe(this, nameObserver); } }
پس از observe()
با nameObserver
به عنوان پارامتر، onChanged()
بلافاصله فراخوانی می شود و آخرین مقدار ذخیره شده در mCurrentName
را ارائه می دهد. اگر شی LiveData
مقداری را در mCurrentName
تنظیم نکرده باشد، onChanged()
فراخوانی نمی شود.
اشیاء LiveData را به روز کنید
LiveData هیچ روش در دسترس عمومی برای به روز رسانی داده های ذخیره شده ندارد. کلاس MutableLiveData
متدهای setValue(T)
و postValue(T)
را به صورت عمومی نشان می دهد و اگر نیاز به ویرایش مقدار ذخیره شده در یک شی LiveData
دارید، باید از آنها استفاده کنید. معمولاً MutableLiveData
در ViewModel
استفاده می شود و سپس ViewModel
فقط اشیاء LiveData
تغییرناپذیر را در معرض دید ناظران قرار می دهد.
پس از تنظیم رابطه مشاهدهگر، سپس می توانید مقدار شی LiveData
را به روز کنید، همانطور که در مثال زیر نشان داده شده است، که وقتی کاربر روی دکمه ای ضربه می زند، همه ناظران را فعال می کند:
کاتلین
button.setOnClickListener { val anotherName = "John Doe" model.currentName.setValue(anotherName) }
جاوا
button.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { String anotherName = "John Doe"; model.getCurrentName().setValue(anotherName); } });
فراخوانی setValue(T)
در مثال باعث میشود ناظران متدهای onChanged()
خود را با مقدار John Doe
فراخوانی کنند. مثال فشار دادن دکمه را نشان می دهد، اما setValue()
یا postValue()
می تواند برای به روز رسانی mName
به دلایل مختلفی فراخوانی شود، از جمله در پاسخ به درخواست شبکه یا بارگذاری پایگاه داده تکمیل می شود. در همه موارد، فراخوانی به setValue()
یا postValue()
ناظران را فعال می کند و UI را به روز می کند.
از LiveData با Room استفاده کنید
کتابخانه تداوم اتاق از پرس و جوهای قابل مشاهده پشتیبانی می کند که اشیاء LiveData
را برمی گرداند. پرس و جوهای قابل مشاهده به عنوان بخشی از یک شی دسترسی به پایگاه داده (DAO) نوشته می شوند.
اتاق تمام کدهای لازم برای به روز رسانی شی LiveData
هنگام به روز رسانی پایگاه داده تولید می کند. کد تولید شده در صورت نیاز پرس و جو را به صورت ناهمزمان بر روی یک رشته پس زمینه اجرا می کند. این الگو برای همگام نگه داشتن داده های نمایش داده شده در رابط کاربری با داده های ذخیره شده در پایگاه داده مفید است. میتوانید در راهنمای کتابخانه دائمی اتاق درباره اتاق و DAO اطلاعات بیشتری کسب کنید.
از کوروتین ها با LiveData استفاده کنید
LiveData
شامل پشتیبانی از کوروتین های Kotlin است. برای اطلاعات بیشتر، استفاده از کوروتین های Kotlin با اجزای معماری Android را ببینید.
LiveData در معماری یک برنامه
LiveData
از چرخه حیات آگاه است و از چرخه حیات موجودیت هایی مانند فعالیت ها و قطعات پیروی می کند. از LiveData
برای برقراری ارتباط بین مالکان چرخه حیات و سایر اشیاء با طول عمر متفاوت مانند اشیاء ViewModel
استفاده کنید. مسئولیت اصلی ViewModel
بارگذاری و مدیریت داده های مرتبط با رابط کاربری است که آن را به یک نامزد عالی برای نگهداری اشیاء LiveData
تبدیل می کند. اشیاء LiveData
را در ViewModel
ایجاد کنید و از آنها برای نمایش وضعیت در لایه UI استفاده کنید.
فعالیتها و قطعات نباید نمونههای LiveData
را نگه دارند زیرا نقش آنها نمایش دادهها است نه حالت نگهداشتن. همچنین، دور نگه داشتن فعالیت ها و قطعات از نگهداری داده ها، نوشتن تست های واحد را آسان تر می کند.
ممکن است کار کردن با اشیاء LiveData
در کلاس لایه داده وسوسه انگیز باشد، اما LiveData
برای مدیریت جریان های ناهمزمان داده طراحی نشده است. حتی اگر میتوانید از تبدیلهای LiveData
و MediatorLiveData
برای رسیدن به این هدف استفاده کنید، این رویکرد دارای اشکالاتی است: قابلیت ترکیب جریانهای داده بسیار محدود است و تمام اشیاء LiveData
(از جمله مواردی که از طریق تبدیلها ایجاد میشوند) در رشته اصلی مشاهده میشوند. کد زیر نمونه ای از نحوه نگهداری LiveData
در Repository
است که می تواند رشته اصلی را مسدود کند:
کاتلین
class UserRepository { // DON'T DO THIS! LiveData objects should not live in the repository. fun getUsers(): LiveData<List<User>> { ... } fun getNewPremiumUsers(): LiveData<List<User>> { return getUsers().map { users -> // This is an expensive call being made on the main thread and may // cause noticeable jank in the UI! users .filter { user -> user.isPremium } .filter { user -> val lastSyncedTime = dao.getLastSyncedTime() user.timeCreated > lastSyncedTime } } }
جاوا
class UserRepository { // DON'T DO THIS! LiveData objects should not live in the repository. LiveData<List<User>> getUsers() { ... } LiveData<List<User>> getNewPremiumUsers() { return Transformations.map(getUsers(), // This is an expensive call being made on the main thread and may cause // noticeable jank in the UI! users -> users.stream() .filter(User::isPremium) .filter(user -> user.getTimeCreated() > dao.getLastSyncedTime()) .collect(Collectors.toList())); } }
اگر نیاز به استفاده از جریانهای داده در لایههای دیگر برنامه خود دارید، از Kotlin Flow استفاده کنید و سپس با استفاده از asLiveData()
آنها را به LiveData
در ViewModel
تبدیل کنید. در مورد استفاده از Kotlin Flow
با LiveData
در این Codelab بیشتر بیاموزید. برای پایگاههای کد ساخته شده با جاوا، استفاده از Executors را همراه با callbacks یا RxJava
در نظر بگیرید.
LiveData را گسترش دهید
LiveData یک ناظر را در حالت فعال در نظر می گیرد اگر چرخه زندگی ناظر در حالت STARTED
یا RESUMED
باشد. کد نمونه زیر نحوه گسترش کلاس LiveData
را نشان می دهد:
کاتلین
class StockLiveData(symbol: String) : LiveData<BigDecimal>() { private val stockManager = StockManager(symbol) private val listener = { price: BigDecimal -> value = price } override fun onActive() { stockManager.requestPriceUpdates(listener) } override fun onInactive() { stockManager.removeUpdates(listener) } }
جاوا
public class StockLiveData extends LiveData<BigDecimal> { private StockManager stockManager; private SimplePriceListener listener = new SimplePriceListener() { @Override public void onPriceChanged(BigDecimal price) { setValue(price); } }; public StockLiveData(String symbol) { stockManager = new StockManager(symbol); } @Override protected void onActive() { stockManager.requestPriceUpdates(listener); } @Override protected void onInactive() { stockManager.removeUpdates(listener); } }
پیاده سازی قیمت شنونده در این مثال شامل روش های مهم زیر است:
- متد
onActive()
زمانی فراخوانی می شود که شیLiveData
یک ناظر فعال داشته باشد. این بدان معناست که باید از این روش شروع به مشاهده به روز رسانی قیمت سهام کنید. - متد
onInactive()
زمانی فراخوانی می شود که شیLiveData
هیچ ناظر فعالی نداشته باشد. از آنجایی که هیچ ناظری گوش نمی دهد، دلیلی برای اتصال به سرویسStockManager
وجود ندارد. - متد
setValue(T)
مقدار نمونهLiveData
را به روز می کند و هر ناظر فعال را در مورد تغییر مطلع می کند.
می توانید از کلاس StockLiveData
به صورت زیر استفاده کنید:
کاتلین
public class MyFragment : Fragment() { override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) val myPriceListener: LiveData<BigDecimal> = ... myPriceListener.observe(viewLifecycleOwner, Observer<BigDecimal> { price: BigDecimal? -> // Update the UI. }) } }
جاوا
public class MyFragment extends Fragment { @Override public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); LiveData<BigDecimal> myPriceListener = ...; myPriceListener.observe(getViewLifecycleOwner(), price -> { // Update the UI. }); } }
متد observe()
LifecycleOwner
مرتبط با نمای قطعه را به عنوان اولین آرگومان ارسال می کند. انجام این کار نشان می دهد که این ناظر به شی Lifecycle
مرتبط با مالک متصل است، به این معنی:
- اگر شی
Lifecycle
در حالت فعال نباشد، مشاهده گر فراخوانی نمی شود حتی اگر مقدار تغییر کند. - پس از از بین رفتن شی
Lifecycle
، ناظر به طور خودکار حذف می شود.
این واقعیت که اشیاء LiveData
از چرخه حیات آگاه هستند به این معنی است که شما می توانید آنها را بین چندین فعالیت، قطعات و خدمات به اشتراک بگذارید. برای ساده نگه داشتن مثال، می توانید کلاس LiveData
را به صورت تکی به صورت زیر پیاده سازی کنید:
کاتلین
class StockLiveData(symbol: String) : LiveData<BigDecimal>() { private val stockManager: StockManager = StockManager(symbol) private val listener = { price: BigDecimal -> value = price } override fun onActive() { stockManager.requestPriceUpdates(listener) } override fun onInactive() { stockManager.removeUpdates(listener) } companion object { private lateinit var sInstance: StockLiveData @MainThread fun get(symbol: String): StockLiveData { sInstance = if (::sInstance.isInitialized) sInstance else StockLiveData(symbol) return sInstance } } }
جاوا
public class StockLiveData extends LiveData<BigDecimal> { private static StockLiveData sInstance; private StockManager stockManager; private SimplePriceListener listener = new SimplePriceListener() { @Override public void onPriceChanged(BigDecimal price) { setValue(price); } }; @MainThread public static StockLiveData get(String symbol) { if (sInstance == null) { sInstance = new StockLiveData(symbol); } return sInstance; } private StockLiveData(String symbol) { stockManager = new StockManager(symbol); } @Override protected void onActive() { stockManager.requestPriceUpdates(listener); } @Override protected void onInactive() { stockManager.removeUpdates(listener); } }
و می توانید از آن در قطعه به صورت زیر استفاده کنید:
کاتلین
class MyFragment : Fragment() { override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) StockLiveData.get(symbol).observe(viewLifecycleOwner, Observer<BigDecimal> { price: BigDecimal? -> // Update the UI. }) }
جاوا
public class MyFragment extends Fragment { @Override public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) { super.onViewCreated(view, savedInstanceState); StockLiveData.get(symbol).observe(getViewLifecycleOwner(), price -> { // Update the UI. }); } }
قطعات و فعالیت های متعدد می توانند نمونه MyPriceListener
را مشاهده کنند. LiveData تنها در صورتی به سرویس سیستم متصل می شود که یک یا چند مورد از آنها قابل مشاهده و فعال باشند.
تبدیل LiveData
ممکن است بخواهید تغییراتی در مقدار ذخیره شده در یک شی LiveData
قبل از ارسال آن به ناظران ایجاد کنید، یا ممکن است لازم باشد یک نمونه LiveData
متفاوت را بر اساس مقدار مورد دیگر برگردانید. بسته Lifecycle
کلاس Transformations
ارائه می دهد که شامل متدهای کمکی است که از این سناریوها پشتیبانی می کنند.
-
Transformations.map()
- تابعی را روی مقدار ذخیره شده در شی
LiveData
اعمال می کند و نتیجه را در پایین دست منتشر می کند.
کاتلین
val userLiveData: LiveData<User> = UserLiveData() val userName: LiveData<String> = userLiveData.map { user -> "${user.name} ${user.lastName}" }
جاوا
LiveData<User> userLiveData = ...; LiveData<String> userName = Transformations.map(userLiveData, user -> { user.name + " " + user.lastName });
-
Transformations.switchMap()
- مشابه
map()
، تابعی را برای مقدار ذخیره شده در شیLiveData
اعمال می کند و نتیجه را باز می کند و به پایین دست ارسال می کند. تابع ارسال شده بهswitchMap()
باید یک شیLiveData
را برگرداند، همانطور که در مثال زیر نشان داده شده است:
کاتلین
private fun getUser(id: String): LiveData<User> { ... } val userId: LiveData<String> = ... val user = userId.switchMap { id -> getUser(id) }
جاوا
private LiveData<User> getUser(String id) { ...; } LiveData<String> userId = ...; LiveData<User> user = Transformations.switchMap(userId, id -> getUser(id) );
شما می توانید از روش های تبدیل برای انتقال اطلاعات در طول چرخه حیات ناظر استفاده کنید. تبدیل ها محاسبه نمی شوند مگر اینکه یک ناظر در حال تماشای شی LiveData
برگشتی باشد. از آنجایی که تبدیل ها به صورت تنبل محاسبه می شوند، رفتارهای مرتبط با چرخه عمر به طور ضمنی بدون نیاز به فراخوانی یا وابستگی های صریح اضافی منتقل می شوند.
اگر فکر می کنید که به یک شی Lifecycle
در داخل یک شی ViewModel
نیاز دارید، احتمالاً یک تبدیل راه حل بهتری است. به عنوان مثال، فرض کنید یک مؤلفه رابط کاربری دارید که یک آدرس را میپذیرد و کد پستی آن آدرس را برمیگرداند. همانطور که در کد نمونه زیر نشان داده شده است، میتوانید ViewModel
سادهلوح را برای این مؤلفه پیادهسازی کنید:
کاتلین
class MyViewModel(private val repository: PostalCodeRepository) : ViewModel() { private fun getPostalCode(address: String): LiveData<String> { // DON'T DO THIS return repository.getPostCode(address) } }
جاوا
class MyViewModel extends ViewModel { private final PostalCodeRepository repository; public MyViewModel(PostalCodeRepository repository) { this.repository = repository; } private LiveData<String> getPostalCode(String address) { // DON'T DO THIS return repository.getPostCode(address); } }
سپس مؤلفه UI باید هر بار که getPostalCode()
را فراخوانی می کند، از شی قبلی LiveData
لغو ثبت نام کرده و در نمونه جدید ثبت شود. علاوه بر این، اگر مؤلفه UI دوباره ایجاد شود، به جای استفاده از نتیجه تماس قبلی، فراخوانی دیگری را با متد repository.getPostCode()
راه اندازی می کند.
در عوض، میتوانید جستجوی کد پستی را بهعنوان تبدیل ورودی آدرس پیادهسازی کنید، همانطور که در مثال زیر نشان داده شده است:
کاتلین
class MyViewModel(private val repository: PostalCodeRepository) : ViewModel() { private val addressInput = MutableLiveData<String>() val postalCode: LiveData<String> = addressInput.switchMap { address -> repository.getPostCode(address) } private fun setInput(address: String) { addressInput.value = address } }
جاوا
class MyViewModel extends ViewModel { private final PostalCodeRepository repository; private final MutableLiveData<String> addressInput = new MutableLiveData(); public final LiveData<String> postalCode = Transformations.switchMap(addressInput, (address) -> { return repository.getPostCode(address); }); public MyViewModel(PostalCodeRepository repository) { this.repository = repository } private void setInput(String address) { addressInput.setValue(address); } }
در این مورد، قسمت postalCode
به عنوان تبدیل addressInput
تعریف می شود. تا زمانی که برنامه شما یک ناظر فعال مرتبط با فیلد postalCode
داشته باشد، مقدار فیلد هر زمان که addressInput
تغییر کند دوباره محاسبه و بازیابی میشود.
این مکانیسم به سطوح پایینتر برنامه اجازه میدهد تا اشیاء LiveData
را ایجاد کند که بهطور تنبلی در صورت تقاضا محاسبه میشوند. یک شی ViewModel
می تواند به راحتی ارجاعاتی به اشیاء LiveData
بدست آورد و سپس قوانین تبدیل را در بالای آنها تعریف کند.
تحولات جدید ایجاد کنید
ده ها تغییر خاص مختلف وجود دارد که ممکن است در برنامه شما مفید باشد، اما به طور پیش فرض ارائه نشده اند. برای پیاده سازی تغییر شکل خود می توانید از کلاس MediatorLiveData
استفاده کنید که به دیگر اشیاء LiveData
گوش می دهد و رویدادهای منتشر شده توسط آنها را پردازش می کند. MediatorLiveData
وضعیت خود را به درستی به شی منبع LiveData
منتشر می کند. برای آشنایی بیشتر با این الگو، به مستندات مرجع کلاس Transformations
مراجعه کنید.
چندین منبع LiveData را ادغام کنید
MediatorLiveData
یک زیر کلاس از LiveData
است که به شما امکان می دهد چندین منبع LiveData را ادغام کنید. ناظرهای اشیاء MediatorLiveData
سپس هر زمان که هر یک از اشیاء منبع اصلی LiveData تغییر کند فعال می شوند.
به عنوان مثال، اگر یک شی LiveData
در رابط کاربری خود دارید که می تواند از یک پایگاه داده محلی یا یک شبکه به روز شود، می توانید منابع زیر را به شی MediatorLiveData
اضافه کنید:
- یک شی
LiveData
مرتبط با داده های ذخیره شده در پایگاه داده. - یک شی
LiveData
مرتبط با داده های قابل دسترسی از شبکه.
فعالیت شما فقط باید شی MediatorLiveData
را مشاهده کند تا بهروزرسانیها را از هر دو منبع دریافت کند. برای مثالی دقیق، بخش Addendum: exposuring network status در راهنمای معماری برنامه را ببینید.
منابع اضافی
برای کسب اطلاعات بیشتر در مورد کلاس LiveData
، به منابع زیر مراجعه کنید.
نمونه ها
- Sunflower ، یک برنامه آزمایشی که بهترین روشها را با اجزای معماری نشان میدهد
- نمونه اولیه اجزای معماری اندروید
Codelabs
- اتاق اندروید با منظره (جاوا) (کاتلین)
- با Kotlin Flow و LiveData روال های پیشرفته را بیاموزید
وبلاگ ها
- ViewModels و LiveData: Patterns + Anti Patterns
- LiveData فراتر از ViewModel - الگوهای واکنشی با استفاده از Transformations و MediatorLiveData
- LiveData با SnackBar، Navigation و رویدادهای دیگر (مورد SingleLiveEvent)
ویدیوها
{% کلمه به کلمه %}برای شما توصیه می شود
- توجه: متن پیوند زمانی که جاوا اسکریپت خاموش است نمایش داده می شود
- از کوروتین های کاتلین با اجزای آگاه از چرخه حیات استفاده کنید
- مدیریت چرخه زندگی با اجزای مربوط به چرخه حیات
- پیاده سازی Paging خود را تست کنید