You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

387 lines
14 KiB
Dart

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

import 'dart:async';
import 'dart:io';
///https://blog.csdn.net/zcylyzhi4/article/details/108002879
///1、导入相关包
import 'dart:isolate';
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:flutter_downloader/flutter_downloader.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:hyzp_ybqx04_changning/components/dioFun.dart';
import 'package:open_file/open_file.dart';
import 'package:path_provider/path_provider.dart';
import 'package:progress_dialog/progress_dialog.dart';
import '../../../components/commonFun.dart';
///版本更新类
class MyUpdatedNew {
MyUpdatedNew(
{this.ver,
this.date,
this.theContext,
this.bStartUpdated = false,
this.bShowNoNewVersion = false}) {
initState();
}
String ver = '1.0.0';
String date = '';
BuildContext theContext;
bool bStartUpdated;
bool bShowNoNewVersion;
//2、声明变量
int _stampAppCompile = -1;
String _dateNewver = '';
Map _mapVer = {};
String serviceVersionCode = '';
String appId = '';
ProgressDialog pr;
String apkName = '';
String appPath = '';
ReceivePort _port = ReceivePort();
void initState() {
// 0、初始化FlutterDownLoader。版本更新初始化放在这里会报错初始化失败
// WidgetsFlutterBinding.ensureInitialized();
if (!bFlutterDownloader_initialize) {
FlutterDownloader.initialize(debug: true).then((value) {
registerCallback(first: true);
});
} else {
registerCallback();
}
}
registerCallback({bool first = false}) {
//3、在initState中初始化
/*
D/DownloadWorker( 4745): Update too frequently!!!!, this should be dropped
E/flutter ( 4745): [ERROR:flutter/lib/ui/ui_dart_state.cc(177)] Unhandled Exception: NoSuchMethodError: The method 'update' was called on null.
E/flutter ( 4745): Receiver: null
E/flutter ( 4745): Tried calling: update(message: "下载中,请稍后…", progress: 0.0)
E/flutter ( 4745): #0 Object.noSuchMethod (dart:core-patch/object_patch.dart:51:5)
E/flutter ( 4745): #1 MyUpdatedNew._updateDownLoadInfo (package:hyzp_ybqx04_changning/pages/MyMsics/05_updated/MyUpdatedNew.dart:251:10)
E/flutter ( 4745): #2 _rootRunUnary (dart:async/zone.dart:1206:13)
E/flutter ( 4745): #3 _CustomZone.runUnary (dart:async/zone.dart:1100:19)
E/flutter ( 4745): #4 _CustomZone.runUnaryGuarded (dart:async/zone.dart:1005:7)
E/flutter ( 4745): #5 _BufferingStreamSubscription._sendData (dart:async/stream_impl.dart:357:11)
E/flutter ( 4745): #6 _BufferingStreamSubscription._add (dart:async/stream_impl.dart:285:7)
E/flutter ( 4745): #7 _SyncStreamControllerDispatch._sendData (dart:async/stream_controller.dart:808:19)
E/flutter ( 4745): #8 _StreamController._add (dart:async/stream_controller.dart:682:7)
E/flutter ( 4745): #9 _StreamController.add (dart:async/stream_controller.dart:624:5)
E/flutter ( 4745): #10 _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:168:12)
E/flutter ( 4745):
*/
if (!first) {
// 解决2次进入报错无法下载的问题-OK
// 如果以前注册过必须先移除否则报错无法下载DownloadWorker( 4745): Update too frequently!!!!, this should be dropped
IsolateNameServer.removePortNameMapping('downloader_send_port');
// FlutterDownloader.cancelAll();
// FlutterDownloader.remove(taskId: null);
}
IsolateNameServer.registerPortWithName(_port.sendPort, 'downloader_send_port');
_port.listen(_updateDownLoadInfo);
FlutterDownloader.registerCallback(_downLoadCallback);
getNewverUrl().then((value) {
_mapVer = value;
print('_mapVer = ${_mapVer}');
//I/flutter (12498): _mapVer = {id: 1, ver: 1.0.0, miaos: 版本说明,
// downurl: http://www.sctastech.com/download/hyzp_20210425.apk, updatetime: 1620632231}
print('oldVer = ${ver}');
//_mapVer['ver'] = '1.3.1';
print('newVer = ${_mapVer['ver']}');
// I/flutter ( 1872): oldVer = 1.3.0
// I/flutter ( 1872): newVer = 1.3.1
if (first) {
bFlutterDownloader_initialize = true;
}
startUpdated();
});
}
///开始更新过程
Future startUpdated() async {
// 如果是android则执行热更新
if (Platform.isAndroid) {
verCompare(newVer: _mapVer['ver'], oldVer: ver).then((value) {
if (value) {
print('value = $value');
//_getNewVersionAPP(context);
//appId = res.data['id'];
//_checkVersionCode();
bNewVer = true; //发现新版本
if (bStartUpdated) {
serviceVersionCode = _mapVer['ver'];
_showNewVersionAppDialog();
}
} else if (bShowNoNewVersion) {
// 没有发现新版本
_showNoNewVersionAppDialog();
}
});
}
}
/// 没有发现新版本
Future<void> _showNoNewVersionAppDialog() async {
return showDialog<void>(
context: theContext,
barrierDismissible: false,
builder: (BuildContext context) {
return AlertDialog(
title: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[Text("没有发现新版本")],
),
content: Container(
//padding: EdgeInsets.only(bottom: ScreenUtil().setHeight(18)),
height: ScreenUtil().setHeight(230),
decoration: BoxDecoration(
border: Border.all(color: Colors.blueAccent, width: 1.0),
borderRadius: BorderRadius.circular(5),
),
alignment: Alignment.center,
child: RichText(
textAlign: TextAlign.center,
text: TextSpan(children: [
TextSpan(text: 'NewVer: ', style: TextStyle(fontSize: 17, color: Colors.black)),
TextSpan(
text: '暂无新版本',
style: TextStyle(
fontSize: 17, color: Colors.black, fontWeight: FontWeight.bold)),
]),
),
),
actions: <Widget>[
new FlatButton(
child: new Text('确定'),
onPressed: () {
Navigator.of(context).pop();
},
),
],
);
});
}
/// 版本更新提示对话框
Future<void> _showNewVersionAppDialog() async {
String content1 = "注意:";
String content2 = "新版本下载成功后,将弹出“安装未知应用程序”界面,请";
String content3 = "授权“允许此来源”";
String content4 = ";然后";
String content5 = "稍等几秒钟";
String content6 = ",再";
String content7 = "点击“返回”按钮(一般位于左上角)";
String content8 = ",按照提示即可完成升级过程。若";
String content9 = "升级过程意外中断";
String content10 = "可重启App再次升级即可。";
return showDialog<void>(
context: theContext,
barrierDismissible: false,
builder: (BuildContext context) {
return AlertDialog(
insetPadding: EdgeInsets.symmetric(horizontal: 20.0, vertical: 24.0),
buttonPadding: EdgeInsets.only(bottom: 15, right: 20),
title: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[Text("发现新版本")],
),
content: Container(
padding: EdgeInsets.only(
left: ScreenUtil().setHeight(25), right: ScreenUtil().setHeight(10)),
height: ScreenUtil().setHeight(620),
decoration: BoxDecoration(
border: Border.all(color: Colors.blueAccent, width: 1.0),
borderRadius: BorderRadius.circular(5),
),
alignment: Alignment.center,
child: Column(
children: [
RichText(
textAlign: TextAlign.center,
text: TextSpan(children: [
TextSpan(
text: '\nNewVer: ',
style: TextStyle(fontSize: 17, color: Colors.redAccent)),
TextSpan(
text: serviceVersionCode,
style: TextStyle(
fontSize: 17, color: Colors.redAccent, fontWeight: FontWeight.bold)),
]),
),
RichText(
textAlign: TextAlign.justify,
text: TextSpan(children: [
getTextSpan('\n' + content1, color: Colors.blueAccent),
getTextSpan(content2),
getTextSpan(content3, color: Colors.redAccent),
getTextSpan(content4),
getTextSpan(content5, color: Colors.redAccent),
getTextSpan(content6),
getTextSpan(content7, color: Colors.redAccent),
getTextSpan(content8),
getTextSpan(content9, color: Colors.blueAccent),
getTextSpan(content10),
]),
),
],
),
),
actions: <Widget>[
new FlatButton(
child: new Text('立即更新'),
onPressed: () {
/// 执行更新操作
Navigator.pop(context);
_executeDownload(context);
},
),
new FlatButton(
child: new Text('下次再说'),
onPressed: () {
Navigator.of(context).pop();
},
),
],
);
});
}
TextSpan getTextSpan(String _text, {Color color = Colors.black, double fontSize = 15}) {
return TextSpan(text: _text, style: TextStyle(fontSize: fontSize, color: color));
}
/// 下载最新apk包
Future<void> _executeDownload(BuildContext context) async {
pr = new ProgressDialog(
context,
type: ProgressDialogType.Download,
isDismissible: true,
showLogs: true,
);
pr.style(message: '准备下载...');
if (!pr.isShowing()) {
pr.show();
}
final path = await _apkLocalPath;
apkName = getFileName(_mapVer['downurl']);
await FlutterDownloader.enqueue(
//url: 'http://update.rwworks.com:8088/appManager/monitor/app/appload/' + appId + '',
url: _mapVer['downurl'],
savedDir: path,
fileName: apkName,
showNotification: true,
openFileFromNotification: true);
}
/// 下载进度回调函数
static void _downLoadCallback(String id, DownloadTaskStatus status, int progress) {
final SendPort send = IsolateNameServer.lookupPortByName('downloader_send_port');
send.send([id, status, progress]);
}
/// 更新下载进度框
_updateDownLoadInfo(dynamic data) {
DownloadTaskStatus status = data[1];
int progress = data[2];
if (status == DownloadTaskStatus.running) {
pr.update(progress: double.parse(progress.toString()), message: "下载中,请稍后…");
}
if (status == DownloadTaskStatus.failed) {
if (pr.isShowing()) {
pr.hide();
}
}
if (status == DownloadTaskStatus.complete) {
if (pr.isShowing()) {
pr.hide();
}
_installApk();
}
}
/// 安装apk
Future<Null> _installApk() async {
await OpenFile.open(appPath + '/' + apkName);
}
/// 获取apk存储位置
Future<String> get _apkLocalPath async {
final directory = await getExternalStorageDirectory();
String path = directory.path + Platform.pathSeparator + 'Download';
;
final savedDir = Directory(path);
bool hasExisted = await savedDir.exists();
if (!hasExisted) {
await savedDir.create();
}
appPath = path;
// this.setState(() {
// appPath = path;
// });
return path;
}
//4、判断自动更新
// 版本比较
//R:\FlutterProject\FlutterProject33\hyzp_ybqx\lib\pages\MyMsics\05_updated\MyUpdatedNew.dart line 343
Future verCompare({String newVer, String oldVer}) async {
//解决newVer中不包含字符“+”号报错失败问题
if (newVer.indexOf('+') > -1) {
//解决App.Car_Ver.Getver接口返回值变化后1.3.11+20210729字符串转换为数字报错问题
print('newVer = $newVer');
newVer = newVer.substring(0, newVer.indexOf('+')); // substring是含头不含尾
print('newVer2 = $newVer');
}
List listNewVer = await tran2int(newVer.split('.'));
List listOldVer = await tran2int(oldVer.split('.'));
int len = listNewVer.length;
for (int i = 0; i < len; i++) {
if (listNewVer[i] > listOldVer[i]) {
return true;
}
}
return false;
}
Future tran2int(List _list) async {
List listRet = [];
int len = _list.length;
for (int i = 0; i < len; i++) {
listRet.add(int.parse(_list[i].trim()));
}
return listRet;
}
///https://blog.csdn.net/zcylyzhi4/article/details/108002879
//5、自动更新代码
/// 执行版本更新的网络请求
/// 检查当前版本是否为最新,若不是,则更新
// void _checkVersionCode() {
// PackageInfo.fromPlatform().then((PackageInfo packageInfo) {
// var currentVersionCode = packageInfo.version;
// if (double.parse(serviceVersionCode.substring(0, 3)) >
// double.parse(currentVersionCode.substring(0, 3))) {
// _showNewVersionAppDialog();
// }
// });
// }
}