android10 TF卡的ZIP压缩和解压

1.android10想要操作tf卡或者内部存储,还是需要先使用SAF获取存储权限.本文需先了解SAF框架和kotlin.

        val sm =
            getSystemService(Context.STORAGE_SERVICE) as StorageManager
        val volume = sm.storageVolumes
        val size = volume.size
        for (i in 1 until size) {
            val storageVolume = volume[i]
            val intent = storageVolume.createOpenDocumentTreeIntent()
            startActivityForResult(intent, REQUEST_REQUEST_CODE)
        }

在onActivityResult中将权限uri保存起来,方便后来使用.

    override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
        val uri = data!!.getData()
        val takeFlags: Int = (data.getFlags()
                and (Intent.FLAG_GRANT_READ_URI_PERMISSION
                or Intent.FLAG_GRANT_WRITE_URI_PERMISSION))
        contentResolver.takePersistableUriPermission(uri!!, takeFlags)
        PreferencesUtil(context!!).saveValue("uri", uri.toString())
        super.onActivityResult(requestCode, resultCode, data)
    }

我们已经获取到了外部存储的根uri权限

2.想要解压tf卡压缩文件其实很简单,首先通过tf的根uri找到我们需要的zip文件.这里我们的压缩文件是/zipFiles/res.zip

            val uri = PreferencesUtil(applicationContext).getString("uri", "asdsa")
            val tFPath = DocumentFile.fromTreeUri(this, Uri.parse(uri))
            var zipFiles = tFPath!!.findFile("zipFiles")
            if (!zipFiles!!.exists()) {
                zipFiles = tFPath.createDirectory("zipFiles")
            }
            val findFile = zipFiles!!.findFile("res.zip")

然后将其转换成zipInputStream,zipInputStream.nextEntry方法可以获取压缩包中每个压缩文件的实体,将其写出到想要的位置就可以了.

            val inputStream = contentResolver.openInputStream(findFile!!.uri)
            val zipInputStream = ZipInputStream(BufferedInputStream(inputStream!!))
            var entry: ZipEntry
            val buf = ByteArray(1024)
            while (null != zipInputStream.nextEntry.also { entry = it }) {
                val createFile = zipFiles.createFile("image/jpg", entry.getName())
                val outputStream = contentResolver.openOutputStream(createFile!!.uri)
                var readLen = 0
                while (-1 != zipInputStream.read(buf, 0, 1024).also({ readLen = it })) {
                    outputStream!!.write(buf, 0, readLen)
                }
                outputStream!!.close()
            }
            inputStream.close()
            zipInputStream.close()

3.压缩的方法就是解压的你过程,先通过uri创建压缩文件

            val uri = PreferencesUtil(applicationContext).getString("uri", "asdsa")
            val tFPath: DocumentFile = DocumentFile.fromTreeUri(this, Uri.parse(uri))!!
            var zipFiles: DocumentFile = tFPath.findFile("zipFiles")!!
            if (!zipFiles.exists()) {
                zipFiles = tFPath.createDirectory("zipFiles")!!
            }
            val createFile: DocumentFile = tFPath.createFile("application/zip",             
            "test.zip")!!

zip类型的压缩文件的mini格式为"application/zip",通过压缩文件创建压缩文件里的压缩文件.在将需要压缩的文件数据写入.

            val outputStream = contentResolver.openOutputStream(createFile.uri)
            val zipOutputStream = ZipOutputStream(BufferedOutputStream(outputStream!!))
            zip(zipOutputStream, "", zipFiles)
            zipOutputStream.flush()
            zipOutputStream.close()
private fun zip(zipOutputStream: ZipOutputStream, zipName: String, zipFiles: DocumentFile) {
        if (zipFiles.isDirectory) {
            val listFiles = zipFiles.listFiles()
            var path = zipFiles.uri.path!!
            for (file in listFiles) {
                val name = file.name!!
                zip(zipOutputStream,  name, file)
            }
        } else {
            val entry: ZipEntry = ZipEntry(zipName)
            zipOutputStream.putNextEntry(entry)
            val input = contentResolver.openInputStream(zipFiles.uri)!!
            val buf = ByteArray(1024)
            var len = -1
            while (input.read(buf).also { len = it } != -1) {
                zipOutputStream.write(buf, 0, len)
            }
            zipOutputStream.flush()
            zipOutputStream.closeEntry()
            input.close()
        }
    }

to be continued

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值