Как я могу создать SwiftUI TextView, который будет обновлять привязку при создании нового представления

Я попытался использовать класс Coordinator для создания TextView, но, похоже, он всегда сохраняет привязку к исходному объекту.

Если я использую это в представлении SwiftUI, как это, то если я использую DocView в расположении мастер / подробности и передаю новый объект Doc, тогда TextView всегда будет удерживать привязку к первому документу.

Итак, если есть список документов или элементов, тогда, когда выбран второй или третий документ и для этого документа создается DocView, любые изменения в TextView обновят сведения о первых документах.

Таким образом, похоже, что Координатор или что-то еще сохраняет исходную привязку, а не обновляет, чтобы отразить последний экземпляр переменной doc DocView.

Я неправильно понял, как должен работать Координатор, и если да, то как я могу убедиться, что при создании нового DocView (doc: newdocobject) привязка будет обновлена.

На практике TextView будет отображать детали newdocobject, но каждый раз, когда выполняется какое-либо редактирование, цель все еще остается исходным объектом.

РЕДАКТИРОВАТЬ: образец приложения https://duncangroenewald.com/files/SampleApps/TextView.zip

Лучшая иллюстрация проблемы https://duncangroenewald.com/files/SampleApps/TextView2.zip

      struct DocView: View {
   @ObservedObject var doc: Doc

   var body: some View {

      TextView(attributedText: $doc.details)

   }
}

class Doc: NSObject, ObservableObject {
   var name: String
   
   var details: NSAttributedString

   init(name: String) {
      self.name = name
      self.details = NSAttributedString(string:"New doc details")
   }

}


    //
    //  TextView.swift
    //  DocApp
    //
    //  Created by Duncan Groenewald on 11/12/21.
    //  Copyright © 2021 Apple. All rights reserved.
    //
    
    import Foundation
    import SwiftUI
    
    #if !os(macOS)
     
    struct TextView: UIViewRepresentable {
     
        @Binding var attributedText: NSAttributedString
        
        func makeUIView(context: Context) -> OSTextView {
            let textView = OSTextView()
            textView.delegate = context.coordinator
     
            return textView
        }
     
        func updateUIView(_ uiView: OSTextView, context: Context) {
            uiView.attributedText = attributedText
        }
        
        func makeCoordinator() -> Coordinator {
            Coordinator($attributedText)
        }
         
        class Coordinator: NSObject, UITextViewDelegate {
            var text: Binding<NSAttributedString>
         
            init(_ text: Binding<NSAttributedString>) {
                self.text = text
            }
         
            func textViewDidChange(_ textView: UITextView) {
                self.text.wrappedValue = textView.attributedText
            }
        }
    }
    
    #endif
    
    #if os(macOS)
     
    struct TextView: NSViewRepresentable {
     
        @Binding var attributedText: NSAttributedString
        
        func makeNSView(context: Context) -> OSTextView {
            let textView = OSTextView(frame: .zero)
            textView.delegate = context.coordinator
            return textView
        }
     
        func updateNSView(_ nsView: OSTextView, context: Context) {
            nsView.textStorage?.setAttributedString(attributedText)
        }
        
        func makeCoordinator() -> Coordinator {
            return Coordinator($attributedText)
        }
         
        class Coordinator: NSObject, NSTextViewDelegate {
            var text: Binding<NSAttributedString>
         
            init(_ text: Binding<NSAttributedString>) {
                self.text = text
                super.init()
            }
         
            func textDidChange(_ notification: Notification) {
                if let textView = notification.object as? NSTextView {
                    self.text.wrappedValue = textView.attributedString()
                }
            }
        }
    }
    
    #endif

0 ответов

Другие вопросы по тегам