如何解决我想减少基本相同的方法中的代码并传入参数但不知道从哪里开始?
我有一个 spriteKit 项目,其中包含多个场景中的多个角色。
作为初学者,我只是为每个场景单独构建了一个 - 这会产生大量额外的代码。
我知道我可以用“构建角色类”或类似的东西来清理它...
我只是不确定从哪里开始。
这是一个场景中两个角色的代码……但想象一下每个场景有 5-10 个角色吗?
//BEAR
func buildBear() {
let bearanimatedAtlas = SKTextureAtlas(named: "Bear")
var bearFrames: [SKTexture] = []
let numImages = bearanimatedAtlas.textureNames.count
for i in 1...numImages {
let bearTextureName = "bear\(i)"
bearFrames.append(bearanimatedAtlas.textureNamed(bearTextureName))
}
animatedBear = bearFrames
let firstFrameTexture = animatedBear[0]
bear = SKSpriteNode(texture: firstFrameTexture)
bear.size.height = 370
bear.size.width = 370
bear.position = CGPoint(x: 295,y: 25)
bear.zPosition = 1
bear.name = "bear"
isUserInteractionEnabled = true
addChild(bear)
}
//CAT
func buildCat() {
let catanimatedAtlas = SKTextureAtlas(named: "Cat")
var catFrames: [SKTexture] = []
let numImages = catanimatedAtlas.textureNames.count
for i in 1...numImages {
let catTextureName = "cat\(i)"
catFrames.append(catanimatedAtlas.textureNamed(catTextureName))
}
animatedCat = catFrames
let firstFrameTexture = animatedCat[0]
cat = SKSpriteNode(texture: firstFrameTexture)
cat.size.height = 240
cat.size.width = 240
cat.position = CGPoint(x: 134,y: -38)
cat.zPosition = 2
cat.name = "cat"
isUserInteractionEnabled = true
addChild(cat)
}
我怎么能清理这样的东西 - 我需要每个场景不同的位置/大小,但我想我可以覆盖每个场景?
我知道我知道怎么做! - 只是不知道从哪里开始?
请轻推一下!
解决方法
关于存在这么多语言的一个令人困惑的事情是它们都有自己的行话和约定。然而,问题的根源与 Swift 或 Sprite Kit 无关。当我阅读您的问题时,我看到可以使用某些抽象数据类型的代码。在 Java 中,您将创建一个接口,在 C++ 中,您将创建一个“纯虚拟”类。好吧,任何其他名字的玫瑰仍然可以完成工作。我建议创建一个协议,可能称为 Spritable
,以定义您打算构建到精灵中的对象类型。可能就这么简单:
protocol Spritable {
var species: String { get }
var height: Int { get }
var width: Int { get }
}
您的两个功能之间唯一不同的地方似乎是起始位置。由于这不是 Spritable
对象的含义所固有的,因此我将单独打包该数据。元组应该可以完成这项工作。通过这些修订,您的两个功能可以合二为一:
func buildSprite(of creature: Spritable,at position: (x: Int,y: Int,z: Int)) {
let spriteAnimatedAtlas = SKTextureAtlas(named: creature.species)
var spriteFrames: [SKTexture] = []
let numImages = spriteAnimatedAtlas.textureNames.count
for i in 1...numImages {
let spriteTextureName = "\(creature.species.lowercased())\(i)"
spriteFrames.append(spriteAnimatedAtlas.textureNamed(spriteTextureName))
}
animatedSprite = spriteFrames
let firstFrameTexture = animatedSprite[0]
sprite = SKSpriteNode(texture: firstFrameTexture)
sprite.size.height = creature.height
sprite.size.width = creature.width
sprite.position = CGPoint(x: position.x,y: position.y)
sprite.zPosition = position.z
sprite.name = creature.species
isUserInteractionEnabled = true
addChild(sprite)
}
要建造一只熊,除了工作室之外,您还需要定义一个实现 Spritable
的结构:
struct Bear: Spritable {
var species: String { return "Bear" }
var height: Int
var width: Int
init(height: Int,width: Int) {
self.height = height
self.width = width
}
}
那么这里就是你的函数调用:
buildSprite(of: Bear(height: 370,width: 370),at: (295,25,1))
这是一个非常简单的例子,可以用一些比这更简单的方法来解决。但是,我发现项目越大,围绕抽象数据类型组织代码的好处就越大,因此即使在这样的简单案例中,也值得采用这种方法。
,我最终没有使用协议。
我只是构建了一种构造精灵的方法 - 类似于@TallChuck 建议的方法。
func buildCharacter(name:String,height: CGFloat,width: CGFloat,position: CGPoint,zPosition: CGFloat) {
let animatedAtlas = SKTextureAtlas(named: name)
var animationFrames: [SKTexture] = []
let numImages = animatedAtlas.textureNames.count
for i in 1...numImages {
let textureName = "\(name)\(i)"
animationFrames.append(animatedAtlas.textureNamed(textureName))
}
animatedCharacter = animationFrames
let firstFrameTexture = animatedCharacter[0]
builtCharacter = SKSpriteNode(texture: firstFrameTexture)
builtCharacter.size.height = height
builtCharacter.size.width = width
builtCharacter.position = position
builtCharacter.zPosition = zPosition
builtCharacter.name = name
isUserInteractionEnabled = true
addChild(builtCharacter)
}
它非常适合构建和添加到场景中 - 在访问节点名称以进行触摸检测时遇到一些问题,但对其进行了排序。现在试图弄清楚如何在节点上调用操作 - 它与正常方式完全不同。所以我接下来会问这个问题。但总体上减少了大量的重复代码!感谢您的帮助。
,这一切都不必在代码中完成。使用 Sprite Kit,您可以通过 sprite kit 编辑器创建您的熊和猫,然后使用按文件名加载的构造函数加载 sks 文件。
这与游戏对象在统一中的工作方式类似。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。