swiftnsattributedstringswift-concurrencynstextattachmentswift6

Swift 6 concurrency issue with `NSTextAttachmentViewProvider`


I completely stuck with subclass NSTextAttachmentViewProvider in swift 6 concurrency.

So lets say I have a simple custom NSTextAttachmentViewProvider:

final shapeViewProvider: NSTextAttachmentViewProvider {

   override func loadView() {
      let view = UIView()
      view.background = .red

      self.view = view
   }

}

This will not compile with the following error:

Call to main actor-isolated initializer 'init()' in a synchronous nonisolated context

annotating the class or the method with @MainActor will not work:

Main actor-isolated instance method 'loadView()' has different actor isolation from nonisolated overridden declaration


Solution

  • This is currently just a limitation of Swift unfortunately. This issue is being discussed on this Swift Forums thread.

    Right now, you can work around this by wrapping MainActor.assumeIsolated around the code that needs to be on the main actor.

    class SomeProvider: NSTextAttachmentViewProvider {
        override func loadView() {
            self.view = MainActor.assumeIsolated {
                let view = UIView()
                view.backgroundColor = .red
                return view
            }
        }
    }
    

    This will crash if loadView is not called on the main actor. This assumption should be true if you are using TextKit correctly.