Presenter 中同時持有 View 以及 Model 的 Interface 引用,而 View 持有 Presenter 的實例。html
當某個 View 須要展現某些數據時,首先會調用 Presenter 的某個接口,而後 Presenter 會調用 Model 請求數據。android
當 Model 數據加載成功後會調用 Presenter 的回調方法通知 Presenter 數據加載完畢,最後 Presenter 再調用 View 層接口展現加載後數據。算法
不太愛用mvp。mvp無非就是面向接口編程的一個典型。presenter經過view和model接口的引用,來調用具體實現類實現的方法,這麼作的好處是,業務結構清晰,且未來更換實現類超級方便,由於業務結構不用改,就只是實現類摘掉,再換一個就是。雖然明知好處,但仍是不太愛用~數據庫
最後:編程
採用哪一種軟件設計模式都是爲了達到以下目的:設計模式
易於維護網絡
易於測試架構
鬆耦合度app
複用性高ide
健壯穩定
原文鏈接:http://blog.csdn.net/johnny901114/article/details/50706329
MVVM是Model-View-ViewModel的簡寫. 它是有三個部分組成:Model、View、ViewModel。
Model:數據模型層。包含業務邏輯和校驗邏輯。
View:屏幕上顯示的UI界面(layout、views)。
ViewModel:View和Model之間的連接橋樑,處理視圖邏輯。
MVVM架構圖以下:
MVVM架構經過ViewModel隔離了UI層和業務邏輯層,下降程序的耦合度。經過DataBinding實現View和ViewModel之間的綁定。
Android App 中MVC的不足
通常來講,咱們開發Android App是基於MVC,因爲MVC的普及和快速開發的特色,一個app從0開發通常都是基於MVC的。
Activity、Fragment至關於C (Controller), 佈局至關於V(View), 數據層至關於M(Model)
隨着業務的增加,Controller裏的代碼會愈來愈臃腫,由於它不僅要負責業務邏輯,還要控制View的展現。也就是說Activity、Fragment雜糅了Controller和View,耦合變大。並不能算做真正意義上的MVC。
編寫代碼基本的過程是這樣的,在Activity、Fragment中初始化Views,而後拉取數據,成功後把數據填充到View裏。
假若有以下場景
:
咱們基於MVC開發完初版本,而後企業須要迭代2.0版本,而且UI界面變化比較大,業務變更較小,怎麼辦呢?
當2.0的全部東西都已經評審事後。這個時候,新建佈局,而後開始按照新的效果圖,進行UI佈局。而後還要新建Activity、Fragment把相關邏輯和數據填充到新的View上。
若是業務邏輯比較複雜,須要從Activity、Fragment中提取上個版本的全部邏輯,這個時候本身可能就要暈倒了,由於一個複雜的業務,一個Activity幾千行代碼也是很常見的。千辛萬苦作完提取完,可能還會出現不少bug。
MVP架構圖以下:
MVP把視圖層抽象到View接口,邏輯層抽象到Presenter接口,提到了代碼的可讀性。下降了視圖邏輯和業務邏輯的耦合。
可是有MVP的不足:
這個時候MVVM就閃亮登場了。從上面的MVVM功能圖咱們知道:
如今咱們回到上面從app1.0到app2.0迭代的問題,若是用MVVM去實現那就比較簡單,這個時候不須要動Activity、Fragment,
只須要把佈局按照2.0版本的效果實現一遍便可。由於視圖邏輯和數據填充已經在佈局裏了,這就是上面提到的可重用性。
A view component in MVP contains a visual part of the application.
The view binds to observable variables and actions exposed by the view model typically using the data binding framework.
The view is responsible for handling for example:
Menus
Permissions
Event listeners
Showing dialogs, Toasts, Snackbars
Working with Android View
and Widget
Starting activities
All functionality which is related to the Android Context
The view model contains the data required for the view. It is an abstraction of the view and exposes public properties and commands. It uses observable data to notify the view about changes. It also allows to pass events to the model. It is also a value converter from the raw model data to presentation-friendly properties)
The view model has the following responsibilities:
Exposing data
Exposing state (progress, offline, empty, error, etc)
Handling visibility
Input validation
Executing calls to the model
Executing methods in the view
The view model should only know about the application context. the application context can:
Start a service
Bind to a service
Send a broadcast
Register a broadcast receiver
Load resource values
It cannot:
Show a dialog
Start an activity
Inflate a layout
Contains a data provider and the code to fetch and update the data. The data can be retrieved from different sources, for example:
REST API
Realm db
SQLite db
Handles broadcast
Shared Preferences
Firebase
etc.
Basically the same as the model in the MVP.
I have a class the Boolean field gets updated with a private BroadcastReceiver wifiScanReceiver; private boolean isWifiConnected = false; wifiScanReceiver = new BroadcastReceiver() { @Override public void onReceive(Context c, Intent intent) { // Wifi connected/disconnected NetworkInfo nwInfo = intent.getParcelableExtra(WifiManager.EXTRA_NETWORK_INFO); final WifiInfo connectionInfo = wifiManager.getConnectionInfo(); if (nwInfo.getState().equals(NetworkInfo.State.CONNECTED)) { // wifi connect isWifiConnected = true; } else { // wifi disconnected isWifiConnected = false; } } }; context.registerReceiver(wifiScanReceiver, wifiIntentFilter); In my Meaning - having sort of a "listener" to changes of the I know there are tons of ways to do it, from broadcasting an What I am really looking for is sort of data binding with a converter, like you would do in a MVVM project. Is there such a thing in android? |
1 Answer
|
I assume you know about android data binding and you're just asking how to do it for this specific case. If not, here is the android data binding guide. You will need a way to observe the boolean value so the UI can remain updated. The easiest way is to make it an ObservableBoolean field of your model object: public class ViewModel { public final ObservableBoolean isWifiConnected = new ObservableBoolean(); // other things you want to bind to your layout... } When you create the binding, you must also assign the model: public void onCreate(Bundle icicle) { ActivityMainBinding binding = DataBindingUtil.setContentView(this, R.layout.activity_main); this.model = new ViewModel(); binding.setModel(this.model); } And when you receive the broadcast, you update the model: wifiScanReceiver = new BroadcastReceiver() { //... model.isWifiConnected.set(newValue); //... }; And your layout would be something like this: <layout ...> <data> <variable name="model" type="com.example.ViewModel"/> </data> <!-- rest of layout --> <ImageView android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@{model.isWifiConnected ? @drawable/xxx : @drawable/yyy}"/> </layout> You could also avoid the model class if you keep track of the binding and set the variable directly on it. In that case, you'd have a variable: <variable name="isWifiConnected" type="boolean"/> And your broadcast receiver would set the value: binding.setIsWifiConnected(newValue); |