我有一个网络调用要执行。但在此之前,我需要检查设备是否有互联网连接。
这是我目前为止所做的:
var connectivityResult = new Connectivity().checkConnectivity();// User defined class
if (connectivityResult == ConnectivityResult.mobile ||
connectivityResult == ConnectivityResult.wifi) {*/
this.getData();
} else {
neverSatisfied();
}
上述方法行不通。
对我来说,我只是在Firebase中创建一个数据,并使用未来构建器来等待数据。在这里,就像这样,你可以检查连接是否太慢,所以数据将被加载:
FutureBuilder(
future: _getImage(context),
builder: (context, snapshot) {
switch (snapshot.connectionState) {
case ConnectionState.none:
return Text('Press button to start.');
case ConnectionState.active:
case ConnectionState.waiting:
return Container(
height:
MediaQuery.of(context).size.height / 1.25,
width:
MediaQuery.of(context).size.width / 1.25,
child: Loading());
case ConnectionState.done:
if (snapshot.hasData) {
return snapshot.data;
} else {
return FlatButton(
onPressed: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) =>
ProfilePage()));
},
child: Icon(
Icons.add_a_photo,
size: 50,
),
);
}
// You can reach your snapshot.data['url'] in here
}
return null;
},
),
我发现仅仅使用连接包不足以判断互联网是否可用。在安卓系统中,它只会检查是否有WIFI或移动数据是否打开,而不会检查是否有实际的互联网连接。在我的测试中,即使没有移动信号ConnectivityResult。Mobile将返回true。
在IOS系统中,我的测试发现,连接插件在手机没有信号的情况下能够正确地检测出是否有网络连接,而Android系统中才存在这个问题。
我找到的解决方案是使用data_connection_checker包以及连接性包。这只是通过向几个可靠的地址发出请求来确保有一个互联网连接,检查的默认超时时间大约是10秒。
我完成的isInternet函数看起来有点像这样:
Future<bool> isInternet() async {
var connectivityResult = await (Connectivity().checkConnectivity());
if (connectivityResult == ConnectivityResult.mobile) {
// I am connected to a mobile network, make sure there is actually a net connection.
if (await DataConnectionChecker().hasConnection) {
// Mobile data detected & internet connection confirmed.
return true;
} else {
// Mobile data detected but no internet connection found.
return false;
}
} else if (connectivityResult == ConnectivityResult.wifi) {
// I am connected to a WIFI network, make sure there is actually a net connection.
if (await DataConnectionChecker().hasConnection) {
// Wifi detected & internet connection confirmed.
return true;
} else {
// Wifi detected but no internet connection found.
return false;
}
} else {
// Neither mobile data or WIFI detected, not internet connection found.
return false;
}
}
if (await DataConnectionChecker(). hasconnection)部分对于移动连接和wifi连接都是一样的,可能应该移动到一个单独的函数。我在这里没有这样做是为了让它更易于阅读。
import 'dart:async';
import 'dart:io';
import 'package:flutter/material.dart';
import 'package:app_settings/app_settings.dart';
import 'package:connectivity/connectivity.dart';
class InternetConnect extends StatefulWidget {
@override
InternetConnectState createState() => InternetConnectState();
}
class InternetConnectState extends State<InternetConnect> {
ConnectivityResult previous;
bool dialogshown = false;
StreamSubscription connectivitySubscription;
Future<bool> checkinternet() async {
try {
final result = await InternetAddress.lookup('google.com');
if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
return Future.value(true);
}
} on SocketException catch (_) {
return Future.value(false);
}
}
void checkInternetConnect(BuildContext context) {
connectivitySubscription = Connectivity()
.onConnectivityChanged
.listen((ConnectivityResult connresult) {
if (connresult == ConnectivityResult.none) {
dialogshown = true;
showDialog(
context: context, barrierDismissible: false, child: alertDialog());
} else if (previous == ConnectivityResult.none) {
checkinternet().then((result) {
if (result == true) {
if (dialogshown == true) {
dialogshown = false;
Navigator.pop(context);
}
}
});
}
previous = connresult;
});
}
AlertDialog alertDialog() {
return AlertDialog(
title: Text('ERROR'),
content: Text("No Internet Detected."),
actions: <Widget>[
FlatButton(
// method to exit application programitacally
onPressed: () {
AppSettings.openWIFISettings();
},
child: Text("Settings"),
),
],
);
}
@override
Widget build(BuildContext context) {
return Container();
}
}
and you can use this method in init of any class
@override
void initState() {
// TODO: implement initState
InternetConnectState().checkInternetConnect(context);
super.initState();
}
这是我的解决方案,它检查互联网连接以及数据连接,我希望你喜欢它。
First of all add dependencies in your pubsec.yaml
dependencies:
data_connection_checker:
And Here Is The main.dart Of My Solution
import 'dart:async';
import 'package:data_connection_checker/data_connection_checker.dart';
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: "Data Connection Checker",
home: HomePage(),
);
}
}
class HomePage extends StatefulWidget {
@override
_HomePageState createState() => _HomePageState();
}
class _HomePageState extends State<HomePage> {
StreamSubscription<DataConnectionStatus> listener;
var Internetstatus = "Unknown";
@override
void initState() {
// TODO: implement initState
super.initState();
// _updateConnectionStatus();
CheckInternet();
}
@override
void dispose() {
// TODO: implement dispose
listener.cancel();
super.dispose();
}
CheckInternet() async {
// Simple check to see if we have internet
print("The statement 'this machine is connected to the Internet' is: ");
print(await DataConnectionChecker().hasConnection);
// returns a bool
// We can also get an enum instead of a bool
print("Current status: ${await DataConnectionChecker().connectionStatus}");
// prints either DataConnectionStatus.connected
// or DataConnectionStatus.disconnected
// This returns the last results from the last call
// to either hasConnection or connectionStatus
print("Last results: ${DataConnectionChecker().lastTryResults}");
// actively listen for status updates
listener = DataConnectionChecker().onStatusChange.listen((status) {
switch (status) {
case DataConnectionStatus.connected:
Internetstatus="Connectd TO THe Internet";
print('Data connection is available.');
setState(() {
});
break;
case DataConnectionStatus.disconnected:
Internetstatus="No Data Connection";
print('You are disconnected from the internet.');
setState(() {
});
break;
}
});
// close listener after 30 seconds, so the program doesn't run forever
// await Future.delayed(Duration(seconds: 30));
// await listener.cancel();
return await await DataConnectionChecker().connectionStatus;
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Data Connection Checker"),
),
body: Container(
child: Center(
child: Text("$Internetstatus"),
),
),
);
}
}
连接插件在其文档中声明,它只在有网络连接的情况下提供信息,但不包括网络连接到Internet的情况
请注意,在Android上,这并不保证连接到互联网。例如,应用程序可能有wifi接入,但它可能是一个VPN或酒店wifi,没有接入。
你可以使用
import 'dart:io';
...
try {
final result = await InternetAddress.lookup('example.com');
if (result.isNotEmpty && result[0].rawAddress.isNotEmpty) {
print('connected');
}
} on SocketException catch (_) {
print('not connected');
}
更新
不建议使用连接包。请使用官方的Flutter Community connectivity_plus包。