Swift 4粘贴板到Finder

时间:2017-10-26 14:15:32

标签: swift swift4

Finder在MacOS 10.12上接受哪些粘贴板类型? 下面的代码让我拖到其他应用程序(如终端和Sublime),但Finder不接受它。这是PasteboardType的问题,还是我错过了其他什么?

override func viewDidLoad() {
    super.viewDidLoad()
    mediaInUseTableView.setDraggingSourceOperationMask(NSDragOperation.every, forLocal: false)
}
func tableView(_ tableView: NSTableView, writeRowsWith rowIndexes: IndexSet, to pboard: NSPasteboard) -> Bool {
    var urls = [NSURL]()
    var types = [NSPasteboard.PasteboardType]()
//        types.append(NSPasteboard.PasteboardType(kUTTypeURL as String))
//        types.append(NSPasteboard.PasteboardType("NSURLPboardType"))
    types.append(NSPasteboard.PasteboardType("NSFilenamesPboardType"))
//        types.append(NSPasteboard.PasteboardType.string)
    for row in rowIndexes{
        urls.append(self.mediaInUses[row].url.absoluteURL as NSURL)
//            types.append(NSPasteboard.PasteboardType.fileNameType(forPathExtension: self.mediaInUses[row].url.pathExtension))
    }
    pboard.declareTypes(types, owner: nil)
    pboard.writeObjects(urls)
    return true
}

我的环境似乎无法使用一些更多的promesing类型:

NSFilenamesPboardType
'NSFilenamesPboardType' is unavailable in Swift: use 'PasteboardType.fileURL'
NSPasteboard.PasteboardType.fileURL
'fileURL' is only available on OS X 10.13 or newer

1 个答案:

答案 0 :(得分:1)

我花了几个小时分析Finder自己的拖拽数据,这些数据被删除到我的应用程序,并在.declareTypes,.setPropertyList和.setData中尝试了无数的对象变体。我有一次工作(!),然后再次打破相同的代码。 我也绝望地转向Swift 3.2。今天,我意识到 .writeObjects应该根据其输入自动执行上述所有操作,并测试了一个最小的实现,这对其他应用程序运行良好。当这在Finder中不起作用时,我确信问题不得不放在其他地方。

假设:由于尝试无效,Finder将我的申请列入黑名单。

解决方案:重新启动计算机,突然Finder接受了拖动!

我昨天也进行了几次重启,但那时我可能执行得不好。

最低限度实施(Swift 3/4)

// Enable drag to other applications:
tableView.setDraggingSourceOperationMask(NSDragOperation.every, forLocal: false)
// Serve data for dragged table rows:
func tableView(_ tableView: NSTableView, writeRowsWith rowIndexes: IndexSet, to pboard: NSPasteboard) -> Bool {
    // Prepeare data:
    var arrayOfNSURLs = [NSURL]()
    for rowIndex in rowIndexes{
        arrayOfNSURLs.append(self.mediaFiles[rowIndex].url.absoluteURL as NSURL)
    }
    // Let API write objects automatically:
    pboard.writeObjects(arrayOfNSURLs)
    return true
}

以下是我的完整实施(Swift 3/4)

override func viewDidLoad() {
    super.viewDidLoad()
    // Enable global drag (to other applications)
    mediaFilesTableView.setDraggingSourceOperationMask(NSDragOperation.every, forLocal: false)
    sourceClipsTableView.setDraggingSourceOperationMask(NSDragOperation.every, forLocal: false)
}
func tableView(_ tableView: NSTableView, writeRowsWith rowIndexes: IndexSet, to pboard: NSPasteboard) -> Bool {
    if tableView == self.mediaFilesTableView {
        var arrayOfNSURLs = [NSURL]()
        for row in rowIndexes{
            arrayOfNSURLs.append(self.mediaFiles[row].url.absoluteURL as NSURL)
        }
        pboard.writeObjects(arrayOfNSURLs)
        return true
    }
    if tableView == self.sourceClipsTableView {
        var names = [NSString]()
        var info = ""
        for row in rowIndexes{
            info = "\(self.sourceClips[row].mediaFiles.count)"
            if info == "0"{
                info = "MISSING"
            }
            names.append(self.sourceClips[row].name.padding(toLength: 30, withPad: " ", startingAt: 0) + info as NSString)
        }
        pboard.writeObjects(names)
        return true
    }
    return false
}
编辑:切换回Swift 4,这些行似乎与Swift 3相同。