依赖

  package_info_plus: ^7.0.0
  path_provider: ^2.1.2 #查找文件 获取文件存储路径
  open_file: ^3.3.2 # 打开文件插件
  permission_handler: ^11.3.1 #检测 Apk 是否拥有权限

配置权限

  <!-- 在 Android 6(Marshmallow)之前的版本中,明确声明网络权限 -->
 <uses-permission android:name="android.permission.INTERNET" /> 
    <!-- 添加存储权限声明 -->
   <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    <!-- 允许应用程序读取外部存储器上的文件。如果你的应用需要读取设备上的文件 -->
  <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
  <!-- 应用有权请求安装其他应用程序的权限 -->
   <uses-permission android:name="android.permission.REQUEST_INSTALL_PACKAGES"/>

代码

//下载app
class UpdateApp extends StatefulWidget {
  const UpdateApp({super.key});

  @override
  State<UpdateApp> createState() => _UpdateAppState();
}

class _UpdateAppState extends State<UpdateApp> {
  @override
  void initState() {
    // TODO: implement initState
    super.initState();
    this._getPackageInfo(); //获取版本号
    this._getAppPath(); //获取路径
  }

  void _showDialog() async {
    await showDialog(
        context: context,
        builder: (context) {
          return AlertDialog(
            title: const Text("更新APP提示!"),
            content: const Text("发现新的版本,新版本修复了如下bug 是否更新!"),
            actions: <Widget>[
              ElevatedButton(
                child: const Text("否"),
                onPressed: () {
                  Navigator.pop(context, 'Cancle');
                },
              ),
              ElevatedButton(
                child: const Text("是"),
                onPressed: () {
                  _downLoad();
                  Navigator.pop(context, 'Ok');
                },
              )
            ],
          );
        });
  }

  //获取版本号
  _getPackageInfo() async {
    PackageInfo packageInfo = await PackageInfo.fromPlatform();
    String appName = packageInfo.appName; // 获取应用程序的名称
    String packageName = packageInfo.packageName; // 获取应用程序的包名
    String version = packageInfo.version; // 获取应用程序的版本号
    String buildNumber = packageInfo.buildNumber; // 获取应用程序的构建号

    print("appName:$appName");
    print("packageName:$packageName");
    print("version:$version");
    print("buildNumber:$buildNumber");
  }

  //获取路径
  _getAppPath() async {
    // 获取应用程序的临时目录
    Directory tempDir = await getTemporaryDirectory();
    String tempPath = tempDir.path;

    // 获取应用程序的文档目录
    Directory appDocDir = await getApplicationDocumentsDirectory();
    String appDocPath = appDocDir.path;

    // 获取外部存储目录
    Directory? directory = await getExternalStorageDirectory();
    String storageDirectory = directory!.path;

    print("tempPath:$tempPath");
    print("appDocDir:$appDocPath");
    print("StorageDirectory:$storageDirectory");
  }

  //检查权限
// _checkPermission 方法用于检查并请求存储权限(仅限于 Android 平台)
  Future<bool> _checkPermission() async {
    await Permission.storage.request();
    // 检查当前主题平台是否为 Android
    if (Theme.of(context).platform == TargetPlatform.android) {
      // 获取存储权限的当前状态
      final status = await Permission.storage.status;

      final status1 = await Permission.requestInstallPackages.status;

      // 如果权限尚未被授予,则向用户请求权限
      if (status != PermissionStatus.granted &&
          status1 != PermissionStatus.granted) {
        final result = await Permission.storage.request();
        // 请求安装应用权限
        final requestInstallPackages =
            await Permission.requestInstallPackages.request();
        // 如果权限请求成功,则返回 true
        if (result == PermissionStatus.granted &&
            requestInstallPackages == PermissionStatus.granted) {
          return true;
        }
      }
      // 如果权限已经被授予,则直接返回 true
      else {
        return true;
      }
    }
    // 如果当前平台不是 Android,则直接返回 false
    return false;
  }

  //下载打开文件
  _downLoad() async {
    // 检查并获取存储权限
    var permission = await this._checkPermission();
//
    // await OpenFile.open("/storage/emulated/0/Android/data/com.example.kid_app/files/aaa.apk");

    // 如果权限已经被授予
    if (permission) {
      // 获取外部存储目录
      final directory = await getExternalStorageDirectory();
      String localPath = directory!.path;

      // 设置 APK 文件的保存路径和名称
      String appName = "aaa.apk";
      // String appName = "aaa.png";
      String savePath = "$localPath/$appName";

      // 设置 APK 文件的网络下载地址
      String apkUrl =
          "https://dashanjiaoyu.oss-cn-shanghai.aliyuncs.com/apk/app-release.apk";
      // 使用 Dio 库进行文件下载,并显示下载进度
      Dio dio = Dio();
      await dio.download(apkUrl, savePath,
          onReceiveProgress: (received, total) {
        if (total != -1) {
          // 打印当前下载进度百分比
          print((received / total * 100).toStringAsFixed(0) + "%");
        }
      });

      // 打印 APK 文件的保存路径
      print(savePath);
      print(
          "------------------------------------------打印 APK 文件的保存路径------------------------------------------");
      try {
        await OpenFile.open(
            "/storage/emulated/0/Android/data/com.example.kid_app/files/aaa.apk",
            type: "application/vnd.android.package-archive");
        //  await OpenFile.open(savePath);
      } catch (e) {
        print("Error opening file: $e");
      }
      // final result = await OpenFile.open(savePath);
    }
    // 如果权限未被授予
    else {
      print("没有权限");
    }
  }

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
        onTap: () async {

          // 点击图标后执行的操作
          _showDialog();
        },
        child: SettingIcon(textLeft: 'Update App', textRight: "1.1.1"));
  }
}

 

 
posted on 2024-04-12 22:36  鲤斌  阅读(49)  评论(0编辑  收藏  举报