Spritekit | SWIFT 3 | - 无法将Void类型的值(又名'())转换为预期的参数类型'unsafeRawPointer'

时间:2016-09-22 09:47:28

标签: ios sprite-kit swift3

无法将Void类型的值(又名'())转换为预期的参数类型'unsafeRawPointer'

该代码允许我通过触摸在屏幕上绘制线条。我正在使用字典允许多个用户同时绘制多行。

当我尝试将指针存储在NSValue键中时。

在我开始升级到Swift 3之前,这在Objective C中运行良好。

var lines: NSMutableDictionary! 

override func didMove(to view: SKView) {
    lines = NSMutableDictionary.init(capacity: 4)
}

 override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {        
    for t in touches {
        let location: CGPoint = t.location(in: self)
        // Create a mutable path
        let path: UIBezierPath = UIBezierPath()
        path.move(to: location)
        // Create a shape node using the path
        lineNode = SKShapeNode(path: path.cgPath)
        lineNode.name = "sprite\(i)"
        self.addChild(lineNode)

        // Use touch pointer as the dictionary key. Since the dictionary key must conform to
        // NSCopying, box the touch pointer in an NSValue
        var key = NSValue(pointer: (t as! Void))  -- **ERROR HERE**
        lines[key] = lineNode 
    }
}

override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
    for t in touches {
        let location = t.location(in: self)

         // Retrieve the shape node that corresponds to touch
         let key = NSValue(pointer: (touches as! Void))  -- **ERROR HERE**
         lineNode = (lines[key] as! String)

        if lineNode != nil {
            // Create and initial a mutable path with the lineNode's path
            let path = UIBezierPath(cgPath: lineNode.path!)
            // Add a line to the current touch point
            path.addLine(to: location)
            // Update lineNode
            lineNode.path = path.cgPath
            lineNode.physicsBody = SKPhysicsBody(edgeChainFrom: path.cgPath)
            lineNode.name = lineNodeCategoryName
        }
    }
}

有人知道我为什么会这样做以及如何解决错误?

1 个答案:

答案 0 :(得分:1)

也许你在Objective-C中混淆了(void *)...,在Swift中混淆了as! Void。它们完全不同。

由于UITouchHashable,您可以将其用作Swift的密钥Dictionary。 尝试使用它:

var lines: [UITouch: SKShapeNode] = [:]

override func didMove(to view: SKView) {
    lines = Dictionary(minimumCapacity: 4)
}

override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
    for t in touches {
        let location: CGPoint = t.location(in: self)
        // Create a mutable path
        let path: UIBezierPath = UIBezierPath()
        path.move(to: location)
        // Create a shape node using the path
        let lineNode = SKShapeNode(path: path.cgPath)
        lineNode.name = "sprite\(i)"
        self.addChild(lineNode)

        lines[t] = lineNode
    }
}

override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
    for t in touches {
        let location = t.location(in: self)

        // Retrieve the shape node that corresponds to touch
        if let lineNode = lines[t] {
            // Create and initial a mutable path with the lineNode's path
            let path = UIBezierPath(cgPath: lineNode.path!)
            // Add a line to the current touch point
            path.addLine(to: location)
            // Update lineNode
            lineNode.path = path.cgPath
            lineNode.physicsBody = SKPhysicsBody(edgeChainFrom: path.cgPath)
            lineNode.name = lineNodeCategoryName
        }
    }
}

我不知道UITouch的这种用法,但正如您所说,使用NSValue的Objective-C版本确实有效,我上面的代码应该有效。