0

In my swift App for macOS, I want to implement a QLPreviewingController. Methods for iOS are very documented, but I can't find examples of previewing for macOS.

I made a NSViewController which has the protocol QLPreviewingController, but I don't understand what I have to do to implement the method preparePreviewOfFile, as I don't understand how to make the controller calling this method.

Ken White
  • 123,280
  • 14
  • 225
  • 444
  • Are you trying to preview files within your app using Quick Look, or add a custom preview extension to the system that can be used by other apps (like Finder, for example)? – adeasismont Apr 06 '22 at 20:52
  • I'm trying to use Quick Look. Otherwise I know howto open the application corresponding to the file, but I want the user to have a quick look at the file – Patrice Rapaport Apr 07 '22 at 03:22

2 Answers2

0

The QLPreviewingController protocol is for implementing preview extensions that add custom previews to the system.

If you want to show previews from your own AppKit app, you should use QLPreviewPanel or QLPreviewView from the QuickLookUI framework.

https://developer.apple.com/documentation/quicklookui

adeasismont
  • 245
  • 1
  • 8
  • Thank's, I didn't understood I had to use a QLPreviewPanel. But now I have another problem: when I pass a URL representing a PDF File, for example, the panel just shows the title of the file and an icon (which is not the icon of a pdf File) – Patrice Rapaport Apr 08 '22 at 05:27
  • You can't preview any URL on the disk, since your app is sandboxed. You can only preview URLs you have access to. In "Signing & Capabilities" in your target settings, you can enable file access for different default folders, but if you want to go beyond that, the user need to grant you access by manually opening the file in your app first. – adeasismont Apr 08 '22 at 08:01
  • I just tried a small project here where I attempted to preview a pdf in ~/Downloads, and I only saw a file icon (and it logged a sandbox error in the console). When I enabled Read Only access to the Downloads folder, I could preview the file correctly. – adeasismont Apr 08 '22 at 08:01
  • I will continue searching. My App is sandboxed, I have read write access to the Downloads folder (I need to write to the folder in another class, and it works) but I still have the problem. I noticed that previewPanel(_ panel: QLPreviewPanel!, previewItemAt index: Int) -> QLPreviewItem! is called twice – Patrice Rapaport Apr 08 '22 at 08:50
  • I think this question has been answered (QLPreviewPanel and QLPreviewView are the ways to show Quick Look in AppKit). Would you mind accepting the answer and opening a new one re: your file access problems? (And please share as much relevant code as possible then too!) – adeasismont Apr 08 '22 at 11:33
  • Yes of course, but what do you mean by opening a new one? do you mean I have to post a new question with subject your file access problem? – Patrice Rapaport Apr 08 '22 at 15:54
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/243727/discussion-between-adeasismont-and-patrice-rapaport). – adeasismont Apr 08 '22 at 18:57
0

I solved my problem, according to macOS Swift QuickLook Warning: setDelegate and setDataSource called while the panel has no controller.

first of all, to start opening the file, I had

@objc func previewFile(_ sender: Any) {
     let panel = QLPreviewPanel.shared()
      panel?.dataSource = self
      panel?.delegate = self
      panel?.makeKeyAndOrderFront(nil)
}

The panel dataSource and delegate dont't have to be implemented there, but in the following functions:

override func beginPreviewPanelControl(_ panel: QLPreviewPanel!) {
    print("beginPreviewPanelController \(panel)")
    panel.dataSource = self
    panel.delegate = self
}

override func endPreviewPanelControl(_ panel: QLPreviewPanel!) {
    print("endPreviewPanelController \(panel)")
    panel.dataSource = nil
    panel.delegate = nil
}

after that, I used an URL by calling URL(string: ...). That was the reason of the problem. I had to use URL(fileURLWithPath: ...)

hoping this will help