Android Activity运行期间网络断开未触发无网络弹窗的问题咨询
Hey there! The issue you're facing makes total sense—your current code only checks the network state once when the Activity is created in onCreate(). So when you launch the app with a network connection and then turn off mobile data later, the app never re-checks the network status, hence no popup appears.
Let's fix this by setting up a network state listener that triggers whenever the network connectivity changes. Here are two reliable approaches:
Approach 1: Use ConnectivityManager.NetworkCallback (Recommended for API 21+)
This is the modern, system-recommended way to listen for network changes, especially since Android 8.0 (API 26) restricted implicit broadcast receivers.
Step 1: Update your Activity code
public class YourActivity extends AppCompatActivity { private ConnectivityManager.NetworkCallback networkCallback; private Dialog networkDialog; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.your_activity_layout); // Initialize network callback to listen for connectivity changes networkCallback = new ConnectivityManager.NetworkCallback() { @Override public void onAvailable(Network network) { super.onAvailable(network); // Network restored—dismiss popup if it's visible runOnUiThread(() -> { if (networkDialog != null && networkDialog.isShowing()) { networkDialog.dismiss(); } }); } @Override public void onLost(Network network) { super.onLost(network); // Network lost—show offline popup runOnUiThread(() -> showOfflineDialog()); } }; // Register the callback when the Activity starts registerNetworkCallback(); // Check initial network state and show popup if needed checkInitialNetworkState(); } private void registerNetworkCallback() { ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); if (cm != null) { NetworkRequest networkRequest = new NetworkRequest.Builder() .addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET) .addTransportType(NetworkCapabilities.TRANSPORT_WIFI) .addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR) .build(); cm.registerNetworkCallback(networkRequest, networkCallback); } } private void checkInitialNetworkState() { ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo activeNetwork = cm.getActiveNetworkInfo(); boolean isConnected = activeNetwork != null && activeNetwork.isConnectedOrConnecting(); if (!isConnected) { showOfflineDialog(); } } private void showOfflineDialog() { // Prevent duplicate dialogs if (networkDialog != null && networkDialog.isShowing()) { return; } networkDialog = new Dialog(this); networkDialog.setContentView(R.layout.networkalert); networkDialog.setCancelable(false); networkDialog.getWindow().setLayout(WindowManager.LayoutParams.WRAP_CONTENT, WindowManager.LayoutParams.WRAP_CONTENT); networkDialog.getWindow().getAttributes().windowAnimations = android.R.style.Animation_Dialog; Button retrybtn = networkDialog.findViewById(R.id.retrybtn); retrybtn.setOnClickListener(v -> recreate()); networkDialog.show(); } @Override protected void onDestroy() { super.onDestroy(); // Unregister callback to avoid memory leaks ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); if (cm != null && networkCallback != null) { cm.unregisterNetworkCallback(networkCallback); } } }
Approach 2: Broadcast Receiver (Legacy, for older Android versions)
If you need to support devices below API 21, you can use a broadcast receiver. Note that for Android 8.0+, you must register it dynamically (not in the manifest).
Step 1: Create the Broadcast Receiver
public class NetworkChangeReceiver extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo activeNetwork = cm.getActiveNetworkInfo(); boolean isConnected = activeNetwork != null && activeNetwork.isConnectedOrConnecting(); if (!isConnected && context instanceof YourActivity) { ((YourActivity) context).showOfflineDialog(); } else if (isConnected && context instanceof YourActivity) { Dialog dialog = ((YourActivity) context).networkDialog; if (dialog != null && dialog.isShowing()) { dialog.dismiss(); } } } }
Step 2: Register/Unregister in your Activity
public class YourActivity extends AppCompatActivity { private NetworkChangeReceiver networkReceiver; private Dialog networkDialog; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.your_activity_layout); networkReceiver = new NetworkChangeReceiver(); // Register receiver dynamically IntentFilter filter = new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION); registerReceiver(networkReceiver, filter); // Check initial network state checkInitialNetworkState(); } private void checkInitialNetworkState() { ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo activeNetwork = cm.getActiveNetworkInfo(); boolean isConnected = activeNetwork != null && activeNetwork.isConnectedOrConnecting(); if (!isConnected) { showOfflineDialog(); } } public void showOfflineDialog() { if (networkDialog != null && networkDialog.isShowing()) { return; } // Same dialog creation code as your original networkDialog = new Dialog(this); networkDialog.setContentView(R.layout.networkalert); networkDialog.setCancelable(false); networkDialog.getWindow().setLayout(WindowManager.LayoutParams.WRAP_CONTENT, WindowManager.LayoutParams.WRAP_CONTENT); networkDialog.getWindow().getAttributes().windowAnimations = android.R.style.Animation_Dialog; Button retrybtn = networkDialog.findViewById(R.id.retrybtn); retrybtn.setOnClickListener(v -> recreate()); networkDialog.show(); } @Override protected void onDestroy() { super.onDestroy(); // Unregister receiver to avoid memory leaks unregisterReceiver(networkReceiver); } }
Key Notes:
- Always run UI operations (like showing/dismissing dialogs) on the main thread—we use
runOnUiThread()in the NetworkCallback to ensure this. - Avoid creating duplicate dialogs by checking if one is already visible before creating a new instance.
- Unregister listeners/receivers in
onDestroy()to prevent memory leaks.
内容的提问来源于stack exchange,提问作者Shreyas patne

