【问题标题】:Drag and drop with custom type identifier doesn't work使用自定义类型标识符拖放不起作用
【发布时间】:2020-04-15 09:13:03
【问题描述】:

我正在尝试使用自定义类型标识符在 macOS 上实现拖放以避免冲突,但它似乎不起作用。首先,这是一个带有 public 和已知标识符的工作示例:

struct ReleaseView: View {
    let id: Int

    var body: some View {
        GeometryReader { _ in
            VStack(spacing: 16) {
                Image(nsImage: NSImage(named: NSImage.networkName)!)
                    .contentShape(Rectangle())
                    .onDrag {
                        return NSItemProvider(item: "\(self.id)" as NSString, typeIdentifier: NSPasteboard.PasteboardType.string.rawValue)
                    }

                DropZone()
            }
        }
    }
}

struct DropZone: View {
    @State var isDragging = false

    var body: some View {
        RoundedRectangle(cornerRadius: 16)
            .stroke(style: StrokeStyle(lineWidth: 4, dash: [8, 8]))
            .background(isDragging ? Color.secondary : Color.clear)
            .frame(width: 100, height: 100)
            .onDrop(of: [NSPasteboard.PasteboardType.string.rawValue], isTargeted: self.$isDragging) { itemProvider in
                print(itemProvider)
                return true
            }
    }
}

在此示例中,您可以将上面的图像拖到拖放区中,它将打印出提供程序。现在,仅仅更改typeIdentifier 就会破坏一切。

static let sharedTypeIdentifier = "com.procrastin8.plzwork"

struct ReleaseView: View {
    // skipping the unchanged bits

                    .onDrag {
                        return NSItemProvider(item: "\(self.id)" as NSString, typeIdentifier: sharedTypeIdentifier)
                    }
}

struct DropZone: View {
    // skipping the unchanged bits

           .onDrop(of: [sharedTypeIdentifier], isTargeted: self.$isDragging) { itemProvider in
                print(itemProvider)
                return true
            }
}

现在这不起作用。在这里使用相同的常量,所以它不是字符串不匹配。又一个 SwiftUI 错误?

【问题讨论】:

    标签: macos swiftui


    【解决方案1】:

    上面的typeIdentifier 不仅仅是一个唯一的字符串,它必须是UTI

    如果你想使用一些自定义应用程序特定的UTI(如果你真的需要它,请三思而后行),那么你必须根据Apple规则注册一个,从

    开始
    <key>UTExportedTypeDeclarations</key>
            <array>
                <dict>
                    <key>UTTypeIdentifier</key>
                    <string>com.procrastin8.plzwork</string>
                    ...
    

    在应用程序中Info.plist

    详情见Declaring New Uniform Type Identifiers

    并在Technical Q&A QA1796广泛收藏

    【讨论】:

      【解决方案2】:

      现在,您可以通过目标项目添加类型标识符,它会自动在 Info.plist 上添加 UTI 字符串,如 Raywenderlich article 中所述。


      演练

      1. 在 Project Navigator 中选择项目
      2. 在“目标”部分选择项目目标
      3. 选择“信息”标签
      4. 展开“导出的类型标识符”
      5. 点击 + 添加新的 UTI
      6. 为描述字段输入描述
      7. 在 Identifier 字段中输入与您在代码中使用的值相同的标识符
      8. 在符合条件下输入 public.data

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-03-20
        • 1970-01-01
        • 2020-12-09
        • 2013-01-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多