FileManager/本地文件增删改查, Cache/图像缓存处理 的操作

1. FileManager 本地文件管理器,增删改查文件

1.1 实现

Swift 复制代码
// 本地文件管理器
class LocalFileManager{
    // 单例模式
    static let instance = LocalFileManager()
    let folderName = "MyApp_Images"
    
    init() {
        createFolderIfNeeded()
    }
    
    // 创建特定应用的文件夹
    func createFolderIfNeeded(){
        // 创建文件夹路径
        guard let path = FileManager
            .default
            .urls(for: .cachesDirectory, in: .userDomainMask)
            .first?
            .appendingPathComponent(folderName)
            .path else {
            return
        }
        
        // 判断文件夹是否存在,不存在,则创建文件夹路径
        if !FileManager.default.fileExists(atPath: path){
            do {
                try FileManager.default.createDirectory(atPath: path, withIntermediateDirectories: true)
                print("Success create folder.")
            } catch let error {
                print("Error creating folder. \(error)")
            }
        }
    }
    
    // 删除特定应用的文件夹
    func deleteFolder(){
        // 创建文件夹路径
        guard let path = FileManager
            .default
            .urls(for: .cachesDirectory, in: .userDomainMask)
            .first?
            .appendingPathComponent(folderName)
            .path else {
            return
        }
        
        do {
            try FileManager.default.removeItem(atPath: path)
            print("Success deleting filder.")
        } catch let error {
            print("Error deleting folder. \(error)")
        }
    }
    
    // 保存图片
    func saveImage(image: UIImage, name: String) -> String{
        // 压缩图片质量
        //image.jpegData(compressionQuality: 1.0)
        // 获取数据和文件路径
        guard
            let data =  image.pngData(),
            let path = getPathForImage(name: name)
        else{
            return "Error getting data."
        }
        
        do{
            // 文件写入数据
            try data.write(to: path)
            return "Success saving."
        }catch let error{
            return "Error saving: \(error.localizedDescription)"
        }
    }
    
    // 获取图片
    func getImage(name: String) -> UIImage?{
        // 获取文件路径 absoluteString,并检查文件是否存在
        guard let path = getPathForImage(name: name)?.path,
              FileManager.default.fileExists(atPath: path) else{
            print("Error getting path.")
            return nil
        }
        return UIImage(contentsOfFile: path)
    }
    
    // 删除图片
    func deleteImage(name: String) -> String{
        // 获取文件路径,并检查文件是否存在
        guard let path = getPathForImage(name: name)?.path,
              FileManager.default.fileExists(atPath: path) else{
            return "Error getting path."
        }
        do {
            // 删除文件
            try FileManager.default.removeItem(atPath: path)
            return "Successfully deleted."
        } catch let error {
            return "Error deleting image: \(error)"
        }
    }
    
    // 获取文件路径
    func getPathForImage(name: String) -> URL?{
        // 文档目录
        //let directory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)
        // 缓存目录
        //let directory2 = FileManager.default.urls(for: .cachesDirectory, in: .userDomainMask).first
        // 临时目录
        //let directory3 = FileManager.default.temporaryDirectory
        // 拼接路径
        //let path = directory2?.appendingPathComponent("\(name).png")
        guard
            let path = FileManager
                .default
                .urls(for: .cachesDirectory, in: .userDomainMask)
                .first?
                .appendingPathComponent(folderName)
                .appendingPathComponent("\(name).png") else {
            print("Error getting data.")
            return nil
            
        }
        print(path)
        return path
    }
}

class FileManagerViewModel: ObservableObject{
    @Published var image: UIImage? = nil
    let imageName: String = "steve-jobs"
    let localManager  = LocalFileManager.instance
    @Published var infoMessage: String  = ""
    
    init() {
        getImageFromAssetsFoler()
        //getImageFromFileManager()
    }
    // 获取图片,在资源目录
    func getImageFromAssetsFoler(){
        image = UIImage(named: imageName)
    }
    // 获取图像,文件管理器
    func getImageFromFileManager(){
        image = localManager.getImage(name: imageName)
    }
    // 保存图像
    func saveImage(){
        guard let image = image else { return }
        infoMessage = localManager.saveImage(image: image, name: imageName)
    }
    // 删除图像
    func deleteImage(){
        infoMessage = localManager.deleteImage(name: imageName)
        localManager.deleteFolder()
    }
}

/// 文件管理器
struct FileManagerBootcamp: View {
    @StateObject var viewModel = FileManagerViewModel()
    
    var body: some View {
        NavigationView {
            VStack {
                if let image = viewModel.image {
                    Image(uiImage: image)
                        .resizable()
                        .scaledToFill()
                        .frame(width: 200, height: 200)
                        .clipped()
                        .cornerRadius(10)
                }
                
                HStack {
                    Button {
                        viewModel.saveImage()
                    } label: {
                        Text("Save to Fm")
                            .font(.headline)
                            .foregroundColor(.white)
                            .padding()
                            .padding(.horizontal)
                            .background(Color.accentColor)
                            .cornerRadius(10)
                    }
                    
                    Button {
                        viewModel.deleteImage()
                    } label: {
                        Text("Delete from Fm")
                            .font(.headline)
                            .foregroundColor(.white)
                            .padding()
                            .padding(.horizontal)
                            .background(Color.red)
                            .cornerRadius(10)
                    }
                }
                
                Text(viewModel.infoMessage)
                    .font(.largeTitle)
                    .fontWeight(.semibold)
                    .foregroundColor(.purple)
                //.padding(.top, 20)
    
                Spacer()
            }
            .navigationTitle("File Manager")
        }
    }
}

1.2 效果图

2. Cache 图像缓存处理操作

2.1 实现

Swift 复制代码
// 缓存管理器
class CacheManager {
    // 单例模式
    static let instance = CacheManager()
    
    private init() {}
    
    // 计算型属性 图像缓存
    var imageCache: NSCache<NSString, UIImage> = {
        let cache = NSCache<NSString, UIImage>()
        // 容纳最大对象的数量
        cache.countLimit = 100
        // 容纳最大值
        cache.totalCostLimit = 1024 * 1024 * 100 // 100mb
        return cache
    }()
    
    // 添加图像
    func add(image: UIImage, name: String) -> String{
        imageCache.setObject(image, forKey: name as NSString)
        return "Added to cache!"
    }
    
    // 移除图像
    func remove(name: String) -> String{
        imageCache.removeObject(forKey: name as NSString)
        return "Removed from cache"
    }
    
    // 获取图像
    func get(name: String) -> UIImage?{
        return imageCache.object(forKey: name as NSString)
    }
}

// 缓存 ViewModel
class CacheViewModel: ObservableObject{
    @Published var startingImage: UIImage? = nil
    @Published var cachedImage: UIImage? = nil
    @Published var infoMessage: String = ""
    
    let imageName = "steve-jobs"
    let manager = CacheManager.instance
    
    init() {
        getImageFromAssetsFolder()
    }
    
    // 获取资源文件中图像
    func getImageFromAssetsFolder(){
        startingImage = UIImage(named: imageName)
    }
    
    // 保存图像
    func saveToCache(){
        guard let image = startingImage else { return }
        infoMessage = manager.add(image: image, name: imageName)
    }
    
    // 移除图像
    func removeFromCache(){
        infoMessage = manager.remove(name: imageName)
    }
    
    // 获取缓存图像
    func getFromCache(){
        if let returnedImage = manager.get(name: imageName){
            cachedImage = returnedImage
            infoMessage = "Got image from cache"
        }else{
            cachedImage = nil
            infoMessage = "Image not found in cache"
        }
    }
}

// 缓存管理
struct CacheBootcamp: View {
    @StateObject var viewModel = CacheViewModel()
    
    var body: some View {
        NavigationView {
            VStack {
                if let image = viewModel.startingImage{
                    Image(uiImage: image)
                        .resizable()
                        .scaledToFill()
                        .frame(width: 200, height: 200)
                        .clipped()
                        .cornerRadius(10)
                }
                
                Text(viewModel.infoMessage)
                    .font(.largeTitle)
                    .fontWeight(.semibold)
                    .foregroundColor(Color.purple)
                
                HStack {
                    Button {
                        viewModel.saveToCache()
                    } label: {
                        Text("Save to Cache")
                            .font(.headline)
                            .foregroundColor(.white)
                            .padding()
                            .background(Color.accentColor)
                            .cornerRadius(10)
                    }
                    
                    Button {
                        viewModel.removeFromCache()
                    } label: {
                        Text("Delete from Cache")
                            .font(.headline)
                            .foregroundColor(.white)
                            .padding()
                            .background(Color.red)
                            .cornerRadius(10)
                    }
                }
                
                Button {
                    viewModel.getFromCache()
                } label: {
                    Text("Get from Cache")
                        .font(.headline)
                        .foregroundColor(.white)
                        .padding()
                        .background(Color.green)
                        .cornerRadius(10)
                }
                
                if let image = viewModel.cachedImage{
                    Image(uiImage: image)
                        .resizable()
                        .scaledToFill()
                        .frame(width: 200, height: 200)
                        .clipped()
                        .cornerRadius(10)
                }
                
                Spacer()
            }
            .navigationTitle("Cache Bootcamp")
        }
    }
}

2.2 效果图

相关推荐
Daniel_Coder2 小时前
iOS Widget 开发-7:TimelineProvider 机制全解析:构建未来时间线
ios·swift·widget
Swift社区2 小时前
Swift 图论实战:DFS 算法解锁 LeetCode 323 连通分量个数
算法·swift·图论
Daniel_Coder3 小时前
iOS Widget 开发-3:Widget 的种类与尺寸(主屏、锁屏、灵动岛)
ios·swift·widget
前端开发与ui设计的老司机4 小时前
从数据洞察到设计变革:UI前端如何利用数字孪生重塑用户体验?
ui·ux
大熊猫侯佩4 小时前
Swift 6.2:江湖再掀惊涛浪,新功出世震四方
swift·apple·wwdc
前端开发与ui设计的老司机5 小时前
大数据时代UI前端的智能化升级:基于机器学习的用户意图预测
大数据·ui
前端开发与ui设计的老司机14 小时前
从UI设计到数字孪生实战:构建智慧教育的个性化学习平台
学习·ui
前端世界16 小时前
鸿蒙UI开发全解:JS与Java双引擎实战指南
javascript·ui·harmonyos
大熊猫侯佩16 小时前
WWDC 25 风云再起:SwiftUI 7 Charts 心法从 2D 到 3D 的华丽蜕变
swiftui·swift·wwdc
Engandend19 小时前
Flutter与iOS混合开发交互
flutter·ios·程序员