The reachability class can only differentiate between WiFi and Wwan types, but cannot differentiate between 2G and 3G networks.
There are some methods on the Internet, but there are bugs.
After searching online for data and testing, the following methods are basically summed up:
1. How to use the Navigation bar: (Private API)
Code:
typedef enum { Networktype_none = 0, networktype_wifi, networktype_2g, networktype_3g,} networktype ;
UIApplication *application = [UIApplication sharedapplication]; Nsarray *subviews = [[[Application Valueforkey:@ "StatusBar"] valueforkey:@ "Foregroundview"]subviews]; NSNumber *datanetworkitemview = nil;for (id subView in subviews) {if ([SubView iskindofclass:[nsclassfromstring (@ "UIStat Usbardatanetworkitemview ") class]) {Datanetworkitemview = SubView; Break }} networktype Networktype = Networktype_none; switch ([[Datanetworkitemview valueforkey:@ "Datanetworktype"] integervalue] {case 0:nslog (@ "No WiFi o R Cellular "); Networktype = Networktype_none; Break Case 1:nslog (@ "2G"); Networktype = networktype_2g; Break Case 2:nslog (@ "3G"); Networktype = networktype_3g; Break Default:nslog (@ "Wifi"); Networktype = Networktype_wifi; Break }
return networktype;
Use this method to make sure that the navigation bar is not hidden and that the navigation bar is hidden and the value is not taken. In addition, the method has a bug, through the Reachability class, when the network type changes, and then execute the code, the obtained network type data is not updated. If the program enters the background and then goes to the foreground, re-executing the code allows you to retrieve the latest network type data. So the user experience is not good, when the user in the mobile, the network type changes, unable to obtain the latest network type, the page data can not be updated. (PS: If any big God knows, what method can refresh the data value, look at the liberal enlighten, thanks! )
2, through the Scnetworkreachability class
Code:
struct sockaddr_in zeroaddress; Bzero (&zeroaddress, sizeof (zeroaddress)); Zeroaddress.sin_len = sizeof (zeroaddress); zeroaddress.sin_family = af_inet; Scnetworkreachabilityref defaultroutereachability = scnetworkreachabilitycreatewithaddress (NULL, struct sockaddr *) &zeroaddress); To create a reference to a test connection: scnetworkreachabilityflags flags; Scnetworkreachabilitygetflags (defaultroutereachability, &flags); if ((Flags & kscnetworkreachabilityflagsreachable) = = 0) {return networktype_none; } networktype retVal = Networktype_none; if ((Flags & kscnetworkreachabilityflagsconnectionrequired) = = 0) {retVal = Networktype_wifi; } if (((Flags & kscnetworkreachabilityflagsconnectionondemand)! = 0) | | (Flags & kscnetworkreachabilityflagsconnectionontraffic)! = 0)) {if (Flags & KSCNETWORKREACHABILITYFLA gsinterventionrequired) = = 0) {retVal = Networktype_wifi; } } if ((Flags & kscnetworkreachabilityflagsiswwan) = = Kscnetworkreachabilityflagsiswwan) {if (Flags & KSC networkreachabilityflagsreachable) = = kscnetworkreachabilityflagsreachable) {if (Flags & Kscnetworkreacha bilityflagstransientconnection) = = kscnetworkreachabilityflagstransientconnection) {RetVal = NetWorkType_3 G if ((Flags & kscnetworkreachabilityflagsconnectionrequired) = = kscnetworkreachabilityflagsconnectionrequired) { RetVal = networktype_2g; }}}} return retVal;
This method is the same as the Reachability method, can not distinguish between 2G and 3g network, but the online test can be differentiated, if someone knows the reason, I hope to correct, thank you!
3. Using Softwareupdateservice.framework (Private API)
Preparatory work:
Export a header file declaration that generates a private API
Using private or non-exposed APIs, you first need to export their corresponding header files, which have declarations of related functions in the header file.
Tools:
Class-dump
Class-dump can extract the corresponding data structure and function declaration from the compiled objective-c binary file.
How to use:
In order to use the Class-dump command in any directory, it is recommended that you copy the Class-dump file to the/user/local/bin/directory, and then execute the following command in any directory:
class-dump/developer/platforms/iphonesimulator.platform/developer/sdks/iphonesimulator3.0.sdk/system/library/ frameworks/softwareupdateservices.framework/>sukit.h
But bulidsetting set the framework's search path to set the true private library path, because we want to use its executable file, only the header file is not.
Code:
NSBundle *b = [NSBundle bundlewithpath:@ "/system/library/privateframeworks/softwareupdateservices.framework"]; if ([b load]) {//load Class from STRING sunetworkmonitor *networkmonitor = [Sunetworkmonitor sharedinstance] ; int netType = [Networkmonitor currentnetworktype]; Networktype networktype = Networktype_none; Switch (netType) {case 0:nslog (@ "No WiFi or cellular"); Networktype = Networktype_none; Break Case 1:nslog (@ "WIFI"); Networktype = Networktype_wifi; Break Case 2:nslog (@ "2G"); Networktype = networktype_2g; Break Case 3:nslog (@ "3G"); Networktype = networktype_3g; Break Default:break; }
return networktype; } return Networktype_none;
This method can obtain the network type and, when the network type changes, gets the latest network type. No bugs have been found yet, just the preparation phase of the work is more troublesome.
4, the last method is to use the IOS7 system comes with the API to get. Only, the system version below IOS7 requires the above method to get the network type.
Four ways to get the network type for iOS