NetInfoModule
向JS端提供了當前設備的網絡狀態信息,API方法如下:
- getCurrentConnectivity 異步返回網絡狀態network_info
- isConnectionMetered 返回手機流量是否被計量
實現分析如下。
NetInfoModule
創建時會獲取系統服務:
mConnectivityManager = (ConnectivityManager) reactContext.getSystemService(Context.CONNECTIVITY_SERVICE);
JS端獲取手機網絡狀態信息的方式有兩種,一種是調用異步方法主動拉取,另一種是當手機狀態改變的時候Native主動通知JS端。
通過getCurrentConnectivity方法,JS端可以主動拉取到當前設備的網絡狀態:
public void getCurrentConnectivity(Promise promise) {
if (mNoNetworkPermission) {
promise.reject(ERROR_MISSING_PERMISSION, MISSING_PERMISSION_MESSAGE, null);
return;
}
promise.resolve(createConnectivityEventMap());
}
private WritableMap createConnectivityEventMap() {
WritableMap event = new WritableNativeMap();
event.putString("network_info", mConnectivity);
return event;
}
成員變量mConnectivity
保存了當前網絡狀態。
NetInfoModule
注冊了網絡狀態改變廣播的監聽:
private void registerReceiver() {
IntentFilter filter = new IntentFilter();
filter.addAction(ConnectivityManager.CONNECTIVITY_ACTION);
getReactApplicationContext().registerReceiver(mConnectivityBroadcastReceiver, filter);
mConnectivityBroadcastReceiver.setRegistered(true);
}
private void unregisterReceiver() {
if (mConnectivityBroadcastReceiver.isRegistered()) {
getReactApplicationContext().unregisterReceiver(mConnectivityBroadcastReceiver);
mConnectivityBroadcastReceiver.setRegistered(false);
}
}
當收到網絡狀態發生改變的系統廣播后,一方面更新成員變量mConnectivity
,一方面主動通知JS端:
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(ConnectivityManager.CONNECTIVITY_ACTION)) {
updateAndSendConnectionType();
}
}
private void updateAndSendConnectionType() {
String currentConnectivity = getCurrentConnectionType();
if (!currentConnectivity.equalsIgnoreCase(mConnectivity)) {
mConnectivity = currentConnectivity;
sendConnectivityChangedEvent();
}
}
當用戶處于非WIFI環境下時,往往會比較在意網絡流量問題。isConnectionMetered相當于返回了當前用戶是否在意流量的耗費:
public void isConnectionMetered(Promise promise) {
if (mNoNetworkPermission) {
promise.reject(ERROR_MISSING_PERMISSION, MISSING_PERMISSION_MESSAGE, null);
return;
}
promise.resolve(ConnectivityManagerCompat.isActiveNetworkMetered(mConnectivityManager));
}
為了便于使用,JS端對NetInfoModule模塊進行了封裝,可以直接使用NetInfo類獲取網絡信息。