首页 > 解决方案 > SwiftUI TextEditor - 编辑完成后保存状态

问题描述

问题概述

我正在构建一个笔记应用程序,并且有一个笔记编辑视图,其中一些 TextEditor 用于收听用户的输入。现在一个环境对象被传递给这个笔记编辑视图,我设计了一个保存按钮来保存更改。它运行良好,只是用户必须单击保存按钮才能更新模型。

预期行为

编辑完成后,文本编辑器应更新 EnvironmentObject 实例的值。不一定要单击保存按钮来保存更改。

下面是视图的示例代码

struct NoteDetails: View {

    @EnvironmentObject var UserData: Notes
    @Binding var selectedNote: SingleNote?
    @Binding var selectedFolder: String?
    @Binding var noteEditingMode: Bool

    @State var title:String = ""
    @State var updatedDate:Date = Date()
    @State var content: String = ""
    
    var id: Int?
    var label: String?
    
    @State private var wordCount: Int = 0

 var body: some View {

VStack(alignment: .leading) {
                TextEditor(text: $title)
                    .font(.title2)
                    .padding(.top)
                    .padding(.horizontal)
                    .frame(width: UIScreen.main.bounds.width, height: 50, alignment: /*@START_MENU_TOKEN@*/.center/*@END_MENU_TOKEN@*/)
                   
                    
                
                                        
                Text(updatedDate, style: .date)
                    .font(.subheadline)
                    .padding(.horizontal)
                
                Divider()
                
                TextEditor(text: $content)
                    .font(.body)
                    .lineSpacing(15)
                    .padding(.horizontal)
                    
                    .frame(maxHeight:.infinity)
                    

                Spacer()
                
            }
}
}

下面是 EnvironmentObject 的编辑函数的示例代码

UserData.editPost(label: label!, id: id!, data: SingleNote(updateDate: Date(), title: title, body: content))

我尝试过的方法

在互联网上没有找到合理的解决方案,所以在这里提出这个问题。提前感谢您的建议!

标签: swiftuitext-editor

解决方案


编辑完成后,我不知道您要保存的确切含义。这是我发现的两种可能的方法。

注意:在下面的演示中,蓝色背景的文本显示保存的文本。

1.当用户关闭键盘时保存

解决方案:添加一个轻击手势,让用户在TextEditor. 同时打电话save()

代码:

struct ContentView: View {
    
    @State private var text: String = ""
    @State private var savedText: String = ""
    
    
    var body: some View {
        VStack(spacing: 20) {
            Text(savedText)
                .frame(width: 300, height: 200, alignment: .topLeading)
                .background(Color.blue)
            
            TextEditor(text: $text)
                .frame(width: 300, height: 200)
                .border(Color.black, width: 1)
                .onTapGesture {}
        }
        .onTapGesture { hideKeyboardAndSave() }
    }
    
    
    private func hideKeyboardAndSave() {
        UIApplication.shared.sendAction(#selector(UIResponder.resignFirstResponder), to: nil, from: nil, for: nil)
        save()
    }
    
    
    private func save() {
        savedText = text
    }
}

2. x 秒无更改后保存

解决方案:只有在没有进一步事件的情况下经过几秒钟后才使用Combinewith发布和观察。.debouncex

我已经设置x为 3。

代码:

struct ContentView: View {
    
    @State private var text: String = ""
    @State private var savedText: String = ""
    
    let detector = PassthroughSubject<Void, Never>()
    let publisher: AnyPublisher<Void, Never>
    
    init() {
        publisher = detector
            .debounce(for: .seconds(3), scheduler: DispatchQueue.main)
            .eraseToAnyPublisher()
    }
    
    
    var body: some View {
        VStack(spacing: 20) {
            Text(savedText)
                .frame(width: 300, height: 200, alignment: .topLeading)
                .background(Color.blue)
            
            TextEditor(text: $text)
                .frame(width: 300, height: 200)
                .border(Color.black, width: 1)
                .onChange(of: text) { _ in detector.send() }
                .onReceive(publisher) { save() }
        }
    }
    
    
    private func save() {
        savedText = text
    }
}

推荐阅读