NSArray在被枚举时发生了变异

时间:2017-01-18 03:36:31

标签: swift sprite-kit

我正在创建一个关卡,通过展示新场景来加载每个关卡。在物理设备上打开项目时,一半时间会说NSArray在枚举时发生变异。我认为它与我的animationManger类有关,它将多个SKTextureAtlases加载到集合中,然后使SKActions为场景中的每个节点设置动画。我将动画管理器放在GameViewController中,因此每次出现新级别时都不必加载纹理。有人可以给我一些关于做什么的建议

import UIKit
import SpriteKit
import GameplayKit

class GameViewController: UIViewController {

    var AnimManager:AnimationManager?
    var LvlManager:LevelManager?
    var sceneView:SKView = SKView()


    override func viewDidLoad() {
        super.viewDidLoad()

       //Load these 2
       AnimManager = AnimationManager(sets: ["Launcher","Button","Launch"])
       LvlManager = LevelManager(levels: 46)

       NotificationCenter.default.addObserver(self, selector: #selector(self.createScene), name: NSNotification.Name(rawValue: "CreateScene"), object: nil)

       //Create the SceneView
       sceneView = self.view as! SKView
       //Scene View Properties
       sceneView.ignoresSiblingOrder = true
       sceneView.showsFPS = true
       sceneView.showsNodeCount = true
       sceneView.showsPhysics = true
   }  

   func createScene() {

       //Create the new Scene
       let scene = PilScene(Size: UIScreen.main.bounds.size, DataFile: "Levels", levelManager: LvlManager!, animationManager: AnimManager!)
       //Present the Scene
       print("presenting scene")
       sceneView.presentScene(scene)
   }

   override var shouldAutorotate: Bool {
       return true
   }

   override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
       if UIDevice.current.userInterfaceIdiom == .phone {
           return .allButUpsideDown
       } else {
           return .all
       }
   }

   override func didReceiveMemoryWarning() {
       super.didReceiveMemoryWarning()
       // Release any cached data, images, etc that aren't in use.
   }

   override var prefersStatusBarHidden: Bool {
       return true
   }
}

下面是为每个场景中的节点创建所有动画动作的类

 class AnimationManager {

//Tuple contains Name of FrameSet, Forward Animation Action, and Backward Animation Action
var actions:[(String, SKAction, SKAction)] = []

//Starts loading the atlases when the manager is initialized
init(sets: [String]) {
    loadAtlases(setNames: sets)
}

//Creates the atlases and preloads them immediately
func loadAtlases(setNames: [String]) {

    for name in setNames {

        let atlas = SKTextureAtlas(named: name)

        atlas.preload {
            self.createFrameSetAction(atlas: atlas, atlasName: name)
            if name == setNames[setNames.count - 1] {
                print("Game Finished Loading")
                NotificationCenter.default.post(name: NSNotification.Name(rawValue: "CreateScene"), object: nil)
            }
        }
    }
}

//Takes in the atlases and creates collections of sktextures
func createFrameSetAction(atlas: SKTextureAtlas, atlasName: String) {

    var frameCollection:[SKTexture] = []

    var loop = 0

    while loop <= atlas.textureNames.count - 1 {
        if loop < 10 {
            frameCollection.append(atlas.textureNamed("Frames_0000\(loop)"))
        }else if loop < 100{
            frameCollection.append(atlas.textureNamed("Frames_000\(loop)"))
        }else if loop > 99 && loop < 110 {
            frameCollection.append(atlas.textureNamed("Frames_00\(loop)"))
        }else{
            frameCollection.append(atlas.textureNamed("Frames_00\(loop)"))
        }
        loop += 1
    }

    let animate = SKAction.animate(with: frameCollection, timePerFrame: 1/30)
    let reverseAnimate = animate.reversed()
    actions.append((atlasName, animate,reverseAnimate))
}

//Returns a collection of frames for a texture set by its name
func getAnimation(name: String) -> SKAction {

    for action in actions { 
        if name == action.0 { 
            return action.1 
        }
    }

    return SKAction.animate(with: [SKTexture(imageNamed: name)], timePerFrame: 1/30)
    }
}

以下是控制台中的内容:

    2017-01-18 12:50:23.226 PilaTesting[7289:186676] *** Terminating app      due to uncaught exception 'NSGenericException', reason: '***     Collection <__NSArrayM: 0x610000646750> was mutated while being enumerated.'
*** First throw call stack:
(
    0   CoreFoundation                      0x00000001076ccd4b  __exceptionPreprocess + 171
1   libobjc.A.dylib                     0x000000010712e21e objc_exception_throw + 48
2   CoreFoundation                      0x0000000107735f6c __NSFastEnumerationMutationHandler + 124
3   SpriteKit                           0x0000000108247b6d -[SKNode _processSearchTokens:visited:usingBlock:stopPointer:] + 2440
4   SpriteKit                           0x0000000108247082 -[SKNode _enumerateChildNodesWithName:usingBlock:stopPointer:] + 1127
5   SpriteKit                           0x000000010824695a -[SKNode enumerateChildNodesWithName:usingBlock:] + 58
6   SpriteKit                           0x0000000108246868 -[SKNode childNodeWithName:] + 148
7   PilaTesting                         0x0000000106afe470 _TFC11PilaTesting9PilaScene6updatefSdT_ + 112
8   PilaTesting                         0x0000000106afe65c _TToFC11PilaTesting9PilaScene6updatefSdT_ + 44
9   SpriteKit                           0x000000010820fe37 -[SKScene _update:] + 365
10  SpriteKit                           0x000000010822ee19 -[SKView _update:] + 950
11  SpriteKit                           0x000000010822b682 __51-[SKView _vsyncRenderForTime:preRender:postRender:]_block_invoke.322 + 285
12  SpriteKit                           0x000000010822aa4a -[SKView _vsyncRenderForTime:preRender:postRender:] + 611
13  SpriteKit                           0x000000010822c2b6 __29-[SKView setUpRenderCallback]_block_invoke + 211
14  SpriteKit                           0x0000000108263e73 -[SKDisplayLink _callbackForNextFrame:] + 335
15  QuartzCore                          0x000000010e68b895 _ZN2CA7Display15DisplayLinkItem8dispatchEy + 57
16  QuartzCore                          0x000000010e68b755 _ZN2CA7Display11DisplayLink14dispatch_itemsEyyy + 449
17  CoreFoundation                      0x000000010765edb4 __CFRUNLOOP_IS_CALLING_OUT_TO_A_TIMER_CALLBACK_FUNCTION__ + 20
18  CoreFoundation                      0x000000010765ea43 __CFRunLoopDoTimer + 1075
19  CoreFoundation                      0x000000010765e5ca __CFRunLoopDoTimers + 250
20  CoreFoundation                      0x00000001076562f1 __CFRunLoopRun + 2065
21  CoreFoundation                      0x0000000107655884 CFRunLoopRunSpecific + 420
22  GraphicsServices                    0x000000010edc9a6f GSEventRunModal + 161
23  UIKit                               0x000000010842fc68 UIApplicationMain + 159
24  PilaTesting                         0x0000000106b029ff main + 111
25  libdyld.dylib                       0x000000010b78068d start + 1
26  ???                                 0x0000000000000001 0x0 + 1
)
libc++abi.dylib: terminating with uncaught exception of type NSException

0 个答案:

没有答案