Android - 以编程方式检查互联网连接并在未连接时显示对话框

Posted

技术标签:

【中文标题】Android - 以编程方式检查互联网连接并在未连接时显示对话框【英文标题】:Android - Programmatically check internet connection and display dialog if notConnected 【发布时间】:2013-07-26 15:51:12 【问题描述】:

我正在做一个实时项目。当用户点击应用程序时。欢迎屏幕出现(该屏幕上有一个网络视图)。如果未连接互联网,则应用程序崩溃。基本上,我的问题是以编程方式检查移动设备是否连接到互联网。如果没有,则不要从 web 服务获取数据到 webview 并显示一个对话框,显示“检查您的互联网连接”

在进行研究时,我发现了很多东西,并且我已经尝试实施。但是,它不能满足我的要求

我的代码是,

public boolean isOnline() 
    ConnectivityManager cm =
        (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
    NetworkInfo netInfo = cm.getActiveNetworkInfo();
    if (netInfo != null && netInfo.isConnectedOrConnecting()) 
        return true;
    
    else
    
        Description.setVisibility(View.INVISIBLE);
        new AlertDialog.Builder(WelcomePage.this)
        .setTitle(getResources().getString(R.string.app_name))
        .setMessage(
                getResources().getString(
                        R.string.internet_error))
        .setPositiveButton("OK", null).show();
    
    return false;

我在doInBackground()AsyncTask 中调用这个函数

请帮忙!

【问题讨论】:

这是否检查互联网连接或 wifi 连接。我怀疑是后者,而互联网连接只能通过 ping 来验证? 【参考方案1】:

你可以查看这个库:

https://github.com/novoda/merlin

您只需implement Connectable,当网络出现故障或恢复时,您都会收到回调。

因此,您可以在这种情况下显示您的对话框。

你也可以查询库的当前状态,选择不做你的网络任务

创建 Merlin(使用 Merlin.Builder())

merlin = new Merlin.Builder().withConnectableCallbacks().build(context);

在您的活动中绑定和取消绑定服务

@Override
protected void onResume() 
    super.onResume();
    merlin.bind();


@Override
protected void onPause() 
    super.onPause();
    merlin.unbind();

注册回调

merlin.registerConnectable(new Connectable() 
        @Override
        public void onConnect() 
            // Do something!
        
);

演示中的MerlinActivity 展示了一种将 Merlin 从主应用程序代码中整理出来的简单方法。

【讨论】:

如果您转到github.com/novoda/merlin 并向下滚动,请阅读自述文件,它的解释非常简单 每次我使用 merlin 完成第二个活动时,merlin 都会不断泄漏(第一次也是在使用它)(我在 onPause 和 onDestroy 中有 merlin.unbind 和 merlin == null) @KrzysztofDziuba 如果您在 GH 回购github.com/novoda/merlin/issues 上打开问题,我们将很乐意帮助您处理 Merlin 问题。【参考方案2】:

终于,我得到了答案。

ConnectivityManager conMgr =  (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo netInfo = conMgr.getActiveNetworkInfo();
if (netInfo == null)
    Description.setVisibility(View.INVISIBLE);
    new AlertDialog.Builder(WelcomePage.this)
        .setTitle(getResources().getString(R.string.app_name))
        .setMessage(getResources().getString(R.string.internet_error))
        .setPositiveButton("OK", null).show();
else
    dialog = ProgressDialog.show(WelcomePage.this, "", "Loading...", true,false);
    new Welcome_Page().execute();

【讨论】:

这不应该是预期的答案,因为您自己问如何检查 Internet 连接而不是网络连接,而上面的答案显示了后一部分 如果设备已连接到网络但没有数据(互联网)余额可供使用,这将执行 Welcome_Page() 您必须小心,因为 Internet 连接与网络连接不同。我强烈建议你使用像***.com/a/17880697/245638 这样可靠的东西,或者查看源代码【参考方案3】:

NetworkInfo 类在 API 29 (android 10.0) 中被弃用,更多详情请参见此处:

This class was deprecated in API level 29. Use ConnectivityManager#getNetworkCapabilities or ConnectivityManager#getLinkProperties to get information synchronously

更新代码(使用 Kotlin)

var isConnected = false
val connectivityManager = getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) 
    val networkCapabilities = connectivityManager.activeNetwork ?: return false
    val activeNetwork = connectivityManager.getNetworkCapabilities(networkCapabilities) ?: return false
    isConnected = when 
        activeNetwork.hasTransport(NetworkCapabilities.TRANSPORT_WIFI) -> true
        activeNetwork.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR) -> true
        activeNetwork.hasTransport(NetworkCapabilities.TRANSPORT_ETHERNET) -> true
        else -> false
    
 else 
    connectivityManager.run 
        activeNetworkInfo?.run 
            isConnected = when (type) 
                ConnectivityManager.TYPE_WIFI -> true
                ConnectivityManager.TYPE_MOBILE -> true
                ConnectivityManager.TYPE_ETHERNET -> true
                else -> false
            
        
    

【讨论】:

【参考方案4】:

检查互联网连接

 ConnectivityManager mgr = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
 NetworkInfo netInfo = mgr.getActiveNetworkInfo();

        if (netInfo != null) 
            if (netInfo.isConnected()) 
                // Internet Available
            else 
               //No internet
            
         else 
            //No internet
        

【讨论】:

【参考方案5】:

这是检查您的互联网连接的简单功能。如果已连接,则返回 true,否则返回 false。

 public boolean isInternetOn() 

        // get Connectivity Manager object to check connection
        ConnectivityManager connec =
                (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);

        // Check for network connections
        if (connec.getNetworkInfo(0).getState() == android.net.NetworkInfo.State.CONNECTED ||
                connec.getNetworkInfo(0).getState() == android.net.NetworkInfo.State.CONNECTING ||
                connec.getNetworkInfo(1).getState() == android.net.NetworkInfo.State.CONNECTING ||
                connec.getNetworkInfo(1).getState() == android.net.NetworkInfo.State.CONNECTED) 


            return true;

         else if (
                connec.getNetworkInfo(0).getState() == android.net.NetworkInfo.State.DISCONNECTED ||
                        connec.getNetworkInfo(1).getState() == android.net.NetworkInfo.State.DISCONNECTED) 


            return false;
        
        return false;
    

这是一个检查互联网连接并检查有效或包含在服务器 this 中的 URL 的项目。

【讨论】:

【参考方案6】:
if (InternetConnection.checkConnection(context)) 
    // Internet Available...
 else 
    // Internet Not Available...

只复制下面的类

public class InternetConnection 

    /** CHECK WHETHER INTERNET CONNECTION IS AVAILABLE OR NOT */
    public static boolean checkConnection(Context context) 
        final ConnectivityManager connMgr = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);

        NetworkInfo activeNetworkInfo = connMgr.getActiveNetworkInfo();

        if (activeNetworkInfo != null)  // connected to the internet
            Toast.makeText(context, activeNetworkInfo.getTypeName(), Toast.LENGTH_SHORT).show();

            if (activeNetworkInfo.getType() == ConnectivityManager.TYPE_WIFI) 
                // connected to wifi
                return true;
             else if (activeNetworkInfo.getType() == ConnectivityManager.TYPE_MOBILE) 
                // connected to the mobile provider's data plan
                return true;
            
        
        return false;
    

授予以下权限以显示

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />

【讨论】:

【参考方案7】:

我尝试了上述不同的方法,除此之外,我在某些情况下被抓到了。所以最后,我使用下面的代码 sn-p 进行网络调用...

try 
    InetAddress address = InetAddress.getByName("www.***.com");
    //Connected to working internet connection
 catch (UnknownHostException e) 
    e.printStackTrace();
    //Internet not available

这在许多方面都很有用。如果这种方法有问题,请告诉我。

【讨论】:

这可行,但必须在工作线程中执行。上面的代码给出了 Network on main thread 异常。 同意@SkyTreasure,这取决于我们如何使用这个sn-p ;) @SkyTreasure 能否给出在主线程中使用它的代码?【参考方案8】:
 public boolean isOnline() 
        NetworkInfo activeNetworkInfo = ((ConnectivityManager) 
        getSystemService(CONNECTIVITY_SERVICE)).getActiveNetworkInfo();
        return activeNetworkInfo != null && 
        activeNetworkInfo.isConnectedOrConnecting();
    

【讨论】:

【参考方案9】:

您的设备具有网络连接并不意味着您可以访问互联网。它可以是没有互联网的 wifi,也可以是没有数据包的数据 SIM。 从 API 23 开始,您可以使用下面的方法来检查它。您可以在 UI 上执行此操作。或者在广播接收器中。

ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
Network currentnetwork = cm.getActiveNetwork();
if (currentnetwork != null) 
        if (cm.getNetworkCapabilities(currentnetwork).hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET) && cm.getNetworkCapabilities(currentnetwork).hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED)) 
            
            // do your stuff. We have internet.
     else 
            // We have no internet connection.
        

    else 
       // We have no internet connection.
   

【讨论】:

【参考方案10】:
private boolean isOnline() 
        ConnectivityManager connMgr = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
        NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();
        return (networkInfo != null && networkInfo.isConnected());
    

这是官方的方式,谷歌也使用同样的方式来检查安卓设备的互联网连接。你可以在这里查看 - link。 这是一个非常完美的方法,它实际上检查互联网是否正常工作。

现在你的具体问题,使用一个计时器类,然后在 if(isOnline) 然后 toast 中放一个 toast。

【讨论】:

【参考方案11】:

doInBackground 在与主 UI 不同的线程上运行,因此您无法在此处创建显示对话框。相反,在您的 AsyncTask 中覆盖 onPreExecute,并在那里进行测试。

【讨论】:

@Java_Android 它对我来说看起来不错 - 它只需要移动到不同的方法(在 UI 线程中运行的方法)。 @Java_Android 请阅读我的回答。您需要在 onPreExecute 中执行此操作,您可以在 AsyncTask 中覆盖它。按照提供的链接获得更多帮助。 @Phil..Buddy,我也试过了......它既不能在主线程的“onCreate”中工作,也不能在“AsyncTask”的“onPreExecute”中工作【参考方案12】:

关于如何检查互联网连接的更新 Kotlin 和 Android 29 版本(getNetworkInfo 在 SDK 29 中已弃用)适用于 minSDK >= 23:

fun hasInternet(): Boolean 
    val connectivityManager = appContainer.contextProvider.currentAppContext()
        .getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
    val network = connectivityManager.activeNetwork

    val capabilities = connectivityManager.getNetworkCapabilities(network)
    var hasInternet = false
    capabilities?.let 
        hasInternet = it.hasCapability(NET_CAPABILITY_INTERNET)
    
    return hasInternet

【讨论】:

【参考方案13】:

这组代码可帮助您检查从 API 级别 16 到 30 的互联网连接是否可用

@SuppressWarnings("deprecation")
public static boolean isInternetAvailable(Activity activity) 
    ConnectivityManager conMgr = (ConnectivityManager) activity.getSystemService(Context.CONNECTIVITY_SERVICE);

    if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) 
        Network network = conMgr.getActiveNetwork();
        NetworkCapabilities networkCapabilities = conMgr.getNetworkCapabilities(network);
        if (networkCapabilities != null) 
            return networkCapabilities.hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET);
         else return false;
     else 
        // below API Level 23
        return conMgr.getActiveNetworkInfo() != null
                && conMgr.getActiveNetworkInfo().isAvailable()
                && conMgr.getActiveNetworkInfo().isConnected();
    

【讨论】:

【参考方案14】:

Internet 连接也可以在onCreate()onResume() 方法中检查。无需在 AsyncTask 内部调用。

或者你可以在调用AsyncTask execute()方法之前调用

if(isOnline)

   MyAsyncTask task=new MyAMyAsyncTask();
   task.execute();



else

// no internet connection

【讨论】:

以上是关于Android - 以编程方式检查互联网连接并在未连接时显示对话框的主要内容,如果未能解决你的问题,请参考以下文章

检查 ufw 状态并在未激活时发送 Prometheus 警报

如何在 iOS 和 Android 的 React Native 应用程序中检查互联网连接?

如何以编程方式在 Android Q 中打开设置面板?

如何以编程方式连接到 ***?

如何在应用程序运行时连续检查互联网连接

Wordpress:如何以编程方式创建帖子并在之前检查重复项