import 'dart:io'; import 'package:dio/dio.dart'; import 'package:flutter/material.dart'; import 'package:flutterappfuyou/code/base/YSTools.dart'; import 'package:open_file/open_file.dart'; import 'package:package_info/package_info.dart'; import 'package:path_provider/path_provider.dart'; import 'package:permission_handler/permission_handler.dart'; import 'package:url_launcher/url_launcher_string.dart'; class YSVersionView extends StatefulWidget { final String content; final String url; final String buildNumber; final bool isMust; const YSVersionView({Key key, this.content = '', this.url = '', this.buildNumber, this.isMust=false}) : super(key: key); @override YSVersionViewState createState() => YSVersionViewState(); } class YSVersionViewState extends State { int _progress = 0; bool _isTap = false; @override Widget build(BuildContext context) { return WillPopScope( onWillPop: () async{ return false; }, child: Center(child: Container( height: 390, width: ysWidth(context)-100, decoration: const BoxDecoration( color: Colors.white, borderRadius: BorderRadius.all(Radius.circular(5)) // image: DecorationImage(image: AssetImage('images/组version.png',),fit: BoxFit.fill) ), padding: EdgeInsets.all(10), child: Column( crossAxisAlignment: CrossAxisAlignment.end, children: [ Container( height: 40, child: centerAlertText('发现新版本', size: 16,color: Colors.black,isBold: true), alignment: Alignment.center, ), Container( margin: EdgeInsets.only(top: 10), height: 320, child: Column( children: [ Container( height: 230, alignment: Alignment.topLeft, padding: const EdgeInsets.all(0), child: SingleChildScrollView( padding: EdgeInsets.all(5), child: centerAlertText('新版本更新说明\n${widget.content}', size: 15, color: const Color(0xFFAFAFAF),line: 100), ), ), GestureDetector( onTap: () async{ if(_isTap)return; if(Platform.isAndroid==true){ bool isPer = await _checkPermission(); if(isPer==true){ _isTap = true; _installApk(widget.url); } }else if(Platform.isIOS==true){ launchUrlString(widget.url); } }, behavior: HitTestBehavior.opaque, child: Container( height: 40, margin: EdgeInsets.only(left: 20,right: 20,top: widget.isMust?30:10,bottom: 10), decoration: const BoxDecoration( color: Colors.pinkAccent, borderRadius: BorderRadius.all(Radius.circular(3)) ), alignment: Alignment.center, child: centerAlertText('立即升级${_progress==0||_progress==100?'':' $_progress%'}', color: Colors.white, size: 15,), ), ), if(widget.isMust==false)GestureDetector( onTap: (){Navigator.pop(context);}, behavior: HitTestBehavior.opaque, child: Container( height: 30, margin: EdgeInsets.only(left: 20,right: 20), alignment: Alignment.center, child: centerAlertText('稍后升级',color: const Color(0xFFAFAFAF), size: 15,), ), ) ], ), ) ], ), )), ); } Future _checkPermission() async { if(Platform.isAndroid==true){ if (await Permission.requestInstallPackages.request().isDenied) { Map statuses = await [ Permission.requestInstallPackages, ].request(); if(statuses[Permission.requestInstallPackages].isDenied){ return false; } } } return true; } Future _downloadAndroid(String url) async { PackageInfo packageInfo = await PackageInfo.fromPlatform(); /// 创建存储文件 Directory storageDir = await getExternalStorageDirectory(); String storagePath = storageDir.path; File file = File('$storagePath/${packageInfo.appName}v' '${packageInfo.buildNumber}.apk'); if (!file.existsSync()) { file.createSync(); } try { LogUtil.d(url); /// 发起下载请求 Response response = await Dio().get( url, onReceiveProgress: showDownloadProgress, options: Options(responseType: ResponseType.bytes,followRedirects: true,) ); file.writeAsBytesSync(response.data); return file; } catch (e) { LogUtil.d(e); return null; } } /// 安装apk Future _installApk(String url) async { File apkFile = await _downloadAndroid(url); String apkFilePath = apkFile.path; if (apkFilePath.isEmpty) { return; } OpenFile.open(apkFilePath); } /// 展示下载进度 void showDownloadProgress(num received, num total) { if (total != -1) { _progress = int.parse('${(received / total~/0.01)}'); setState(() {}); if(_progress==100){ _isTap = false; } } } } centerAlertText(String text,{Color color = Colors.white,double size,bool isBold = false,int line = 1}) { return Text(text,style: TextStyle(fontSize: size,color: color,decoration: TextDecoration.none, fontWeight: isBold?FontWeight.bold:FontWeight.normal,),maxLines: line,overflow: TextOverflow.ellipsis,); }