[英]Checking if the internet connection is lost at runtime
美好的一天。 我知道如何檢查是否有可用的Internet連接,我的問題是我想向用戶顯示一個AlertDialog,該警報對話框將阻止操作,除非在連接丟失或停用時再次嘗試。 我不知道如何只編寫一次代碼,所以我不需要在所有活動中手動復制它。
我嘗試使用觀察者模式,並在SplashActivity(Launcher Activity)中對其進行了初始化。
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_home);
ObservedObject observedObject = new ObservedObject();
observedObject.addObserver(new ObserverInternetConnection());
}
public class ObservedObject extends Observable {
private boolean isConnected;
public boolean isConnected() {
return isConnected;
}
public void setConnected(boolean connected) {
isConnected = connected;
setChanged();
notifyObservers();
}
public class ObserverInternetConnection implements Observer {
@Override
public void update(Observable observable, Object o) {
if (observable instanceof ObservedObject) {
if (observable.hasChanged())
//alert is a method to show toast message
alert("connection changed");
if (((ObservedObject) observable).isConnected)
alert("connected");
else
alert("disconnected");
}
}
}
當我手動設置observedObject連接時,它起作用了。 但我想避免這樣做。 有沒有一種方法可以自動執行此操作? 我當時在考慮使用另一個線程,但是我該怎么做呢? 另一個問題是,我檢查Internet連接的方式是使用ConnectivityManager,但它需要我傳遞上下文,並且上下文可以(並且將會)在整個應用程序中發生變化,我該如何克服呢? 還有其他解決方法嗎?
我建議在初始化連接更改偵聽器(在您的情況下為Observer)的地方創建BaseActivity
,並使用Splash,Main和其他正在使用的活動擴展此活動。
這樣,您將避免代碼重復。
當活動被破壞時,也不要忘記注銷監聽器。
另外,您不需要使用其他線程。 這是如何在Activity中監聽連接性變化的示例:
首先注冊接收者:
@Override
public void register(Context context) {
initReceiver();
final IntentFilter intentFilter = new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION);
context.registerReceiver(receiver, intentFilter);
}
接收器
receiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
if (isOnline()) {
hideNoConnectionError();
} else {
showNoConnectionError();
}
}
};
和isOnline()
val isOnline: Boolean
get() {
return try {
val connectivityManager = context.getSystemService(
Context.CONNECTIVITY_SERVICE) as ConnectivityManager
connectivityManager.activeNetworkInfo != null &&
connectivityManager.activeNetworkInfo.isConnected
} catch (exception: Exception) {
false
}
}
抱歉,最后一種方法是用Kotlin編寫的,但是我認為這完全可以理解
如果您的最低SDK版本> = N(24),另一種方法是在Application
類中訂閱ConectivityManager
。 為了防止用戶進行交互,請在頂部啟動透明活動,並用一些陰影背景說明該連接已丟失。 這不是理想的方法,但是您無需堅持繼承。
TestApplication.java
public class TestApplication extends android.app.Application {
private static final String TAG = "TestApplication";
@Override
public void onCreate() {
super.onCreate();
ConnectivityManager m = (ConnectivityManager) getSystemService(Service.CONNECTIVITY_SERVICE);
m.registerDefaultNetworkCallback(new ConnectivityManager.NetworkCallback() {
@Override
public void onAvailable(Network network) {
Log.e(TAG, "onAvailable: ");
startActivity(ConnectionLostScreen.createIntentHideSplashOnNetworkRecovery(TestApplication.this));
}
@Override
public void onLost(Network network) {
Log.e(TAG, "onLost: ");
startActivity(ConnectionLostScreen.createShowSplashOnNetworkFailure(TestApplication.this));
}
});
}
}
ConnectionLostScreen.java
public class ConnectionLostScreen extends AppCompatActivity {
private final static int SHOW = 1;
private final static int HIDE = 2;
private final static String EXTRA_NAME = "ACTION";
public static Intent createShowSplashOnNetworkFailure(Context app) {
Intent intent = new Intent(app, ConnectionLostScreen.class);
intent.putExtra(EXTRA_NAME, SHOW);
intent.addFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT| Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NO_ANIMATION);
return intent;
}
public static Intent createIntentHideSplashOnNetworkRecovery(Context app) {
Intent intent = new Intent(app, ConnectionLostScreen.class);
intent.putExtra(EXTRA_NAME, HIDE);
intent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
return intent;
}
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_splash_screen);
if (getIntent() != null) handleIntent(getIntent());
}
@Override
public void onBackPressed() {
//disabled so user would not be able to close this activity.
}
@Override
protected void onNewIntent(Intent intent) {
super.onNewIntent(intent);
if (intent != null) handleIntent(intent);
}
void handleIntent(Intent intent) {
int value = intent.getIntExtra(EXTRA_NAME, 0);
if (value == 0 || value == HIDE) {
finish();
return;
}
}
}
ConnectionLostScreen的主題為。
<style name="Theme.Transparent" parent="AppTheme">
<item name="android:windowIsTranslucent">true</item>
<item name="android:windowBackground">@android:color/transparent</item>
<item name="android:windowContentOverlay">@null</item>
<item name="android:windowNoTitle">true</item>
<item name="android:backgroundDimEnabled">false</item>
</style>
優點:
ConnectionLostScreen
時, ConnectionLostScreen
將關閉。 缺點:
ConnectionLostScreen
活動流管理(使其變為singleTop等)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.