WinForm桌面应用如何判断当前活跃互联网连接是否为计量连接?
嘿,当然可以搞定这个需求!WinForm桌面应用虽然没有UWP那种直接可用的GetInternetConnectionProfile() API,但我们有两种靠谱的方法来判断当前活跃互联网连接是不是计量连接:
方法一:通过P/Invoke调用Win32原生API(兼容.NET Framework)
这种方法兼容性拉满,不管你用的是老版本的.NET Framework还是新的.NET,都能跑。核心是调用iphlpapi.dll里的GetNetworkConnectionCost函数,它能返回当前网络连接的成本属性,包括是否为计量连接。
先看代码示例:
using System; using System.Runtime.InteropServices; public static class NetworkCostHelper { // 定义网络连接成本的标志位 [Flags] private enum NETCONNECTION_COST_FLAGS { None = 0x0, NETCONNECTION_COST_FLAG_ROAMING = 0x1, NETCONNECTION_COST_FLAG_METERED = 0x2, NETCONNECTION_COST_FLAG_CONGESTED = 0x4, NETCONNECTION_COST_FLAG_APPROACHING_DATA_LIMIT = 0x8, NETCONNECTION_COST_FLAG_OVER_DATA_LIMIT = 0x10 } // 定义存储网络连接成本信息的结构体 [StructLayout(LayoutKind.Sequential)] private struct NETWORK_CONNECTION_COST { public uint Size; public uint Cost; public NETCONNECTION_COST_FLAGS CostFlags; } // 导入Win32函数 [DllImport("iphlpapi.dll", SetLastError = true)] private static extern uint GetNetworkConnectionCost(IntPtr interfaceLuid, out NETWORK_CONNECTION_COST connectionCost); public static bool IsCurrentConnectionMetered() { // 获取当前活跃网络接口的信息,直接传IntPtr.Zero获取默认连接 NETWORK_CONNECTION_COST costInfo = new NETWORK_CONNECTION_COST(); costInfo.Size = (uint)Marshal.SizeOf(typeof(NETWORK_CONNECTION_COST)); uint result = GetNetworkConnectionCost(IntPtr.Zero, out costInfo); // 如果调用成功,检查是否包含计量连接的标志 return result == 0 && (costInfo.CostFlags & NETCONNECTION_COST_FLAG_METERED) != 0; } }
使用的时候直接调用NetworkCostHelper.IsCurrentConnectionMetered()就能得到结果啦。
方法二:调用Windows Runtime API(适合.NET Core 3.0+/NET 5+)
如果你用的是较新版本的.NET(.NET Core 3.0及以上,或者.NET 5+),WinForm应用可以直接调用UWP的WinRT API,写法和UWP里差不多,非常简洁。
步骤如下:
- 确保你的WinForm项目目标框架是Windows专用的(比如
net6.0-windows),项目文件里会有类似配置:
<TargetFramework>net6.0-windows</TargetFramework> <UseWindowsForms>true</UseWindowsForms>
- 添加
using Windows.Networking.Connectivity;命名空间 - 编写判断代码:
using Windows.Networking.Connectivity; public static bool IsMeteredConnection() { var profile = NetworkInformation.GetInternetConnectionProfile(); if (profile == null) { // 没有活跃的互联网连接 return false; } return profile.ConnectionCost.IsMetered; }
这个方法代码更简洁,和UWP的写法几乎一致,非常容易上手。
注意事项
- 方法一的P/Invoke方式兼容性更好,适合所有.NET版本的WinForm应用,包括老的.NET Framework 4.x系列。
- 方法二需要你的项目基于Windows专用的.NET版本,运行环境为Windows 10及以上系统(都支持WinRT API)。
- 不管用哪种方法,默认权限就足够访问网络信息,不需要额外申请特殊权限。
内容的提问来源于stack exchange,提问作者Faraz Azhar
相关产品推荐
相关产品推荐

