使用纹理图集的SpriteKit SKAction animateWithTextures

时间:2013-09-19 16:34:31

标签: sprite-kit

使用纹理图集,SpriteKit SKAction animateWithTextures无法第一次正确渲染。

我有一个初始化精灵并在其上运行一个动作的场景,当我不使用纹理贴图时,它可以正常工作。现在的问题是,当场景第一次加载时,它会绘制精灵帧大小和它的纹理大小相同,因此精灵被拉伸拉伸。我有一个后退按钮,所以当我退出并重新进入场景时,它会正常加载。它不会影响纹理图集中的任何其他精灵纹理,只影响动画纹理,并且奇怪的是它只在首次渲染时才会发生。

注意:我正在使用一个单例,它有一个存储在ViewController.m文件中生成的所有动画的数组。

** ADDED **

好的,我已经做了很多实验,我得出的结论是自动图谱生成器解释我的文件名的方式一定有问题,我认为这与“@ 2x有关“特别是标签。

我已经尝试通过删除名称的“.atlas”部分来重命名地图册文件夹并且图像渲染完美,当然这不是理想的解决方案,因为它意味着更多的绘制调用。

我命名图像的方式如下......

主题-NAME数字解析-DEVICE-PNG

例如,图像将被称为“SPOOKY_tree_0@2x~iphone.png”

然后我使用辅助方法将其加载到缓存单例中,因为......

- (SKAction *)animationWithFile:(NSString *)name theme:(NSString *)theme frameCount:       (int)frameCount delay:(float)delay {

// Load the animation frames as textures and create the sprite frames
NSMutableArray *frames = [NSMutableArray arrayWithCapacity:frameCount];

for (int i = 0; i < frameCount; i++) {

    NSString *retina;
    if ([GLOBAL _hd]) {

        retina = @"@2x";

    } else { retina = @""; }

    NSString *deviceType;
    if ([GLOBAL _ipad]) {

        deviceType = @"~ipad";

    } else { deviceType = @"~iphone"; }

    // Create the file name
    NSString *file = [NSString stringWithFormat:@"%@%@_%d%@%@", theme, name, i, retina, deviceType];

    // Create the texture/frame
    SKTexture *frame = [SKTexture textureWithImageNamed:file];

    [frames addObject:frame];
}

// Return the animation object from all the sprite animation frames
return [SKAction animateWithTextures:frames timePerFrame:delay];
}

// Return the animation object from all the sprite animation frames
return [SKAction animateWithTextures:frames timePerFrame:delay];

然后使用“name”变量将其存储在键下的 NSMutableDictionary 中,如此...

- (void)loadPegAnimations {

    NSString *newName;
    SKAction *newAnimation;
    int newFrameCount;
    CGFloat fps = 1.0/20.0;

    newName = kP1_DEPLOYING_PEG;
    newFrameCount = 9;
    newAnimation = [self animationWithFile:newName theme:pegTheme frameCount:newFrameCount delay:fps];
    [self addAnimation:newAnimation byName:newName];

    newName = kP1_LOSING_PEG;
    newFrameCount = 22;
    newAnimation = [self animationWithFile:newName theme:pegTheme frameCount:newFrameCount delay:fps];
    [self addAnimation:newAnimation byName:newName];

    newName = kP2_DEPLOYING_PEG;
    newFrameCount = 9;
    newAnimation = [self animationWithFile:newName theme:pegTheme frameCount:newFrameCount delay:fps];
    [self addAnimation:newAnimation byName:newName];

    newName = kP2_LOSING_PEG;
    newFrameCount = 22;
    newAnimation = [self animationWithFile:newName theme:pegTheme frameCount:newFrameCount delay:fps];
    [self addAnimation:newAnimation byName:newName];

}

当我想使用该动画时,我使用“[[PEGOGraphicLoader sharedGraphicLoader] frameByName:kP1_DEPLOYING_PEG]]行来调用单例缓存;”返回SKAction *。

我想不知何故,当它回调动画的图像时,它会重新将@ 2x应用于图像并尝试将它们压缩到精灵帧中,但我不确定。此外,这仍然无法解释动画在第一次播放后正常渲染的事实。

我已经尝试将分辨率元素和设备元素从-textureWithImageNamed:方法中删除,但是纹理图集并没有找到图像,只是显示为巨大的X.我想我会在没有启用纹理图集的情况下工作,直到我知道它绝对不是纹理图集生成器的错误。

与此同时,我正在考虑使用hack类型命名约定,因此我可以根据设备类型等以编程方式决定加载哪些纹理,并为每种设备类型设置不同的atlas文件夹。

如果有人遇到过类似的问题,或者想知道我做错了什么,那么我想知道。我还没有在实际设备上测试游戏,所以它可能是模拟器的一个问题。

2 个答案:

答案 0 :(得分:2)

我发现自己与使用TextureAtlas的精灵有同样的问题。我玩了不同的设置,发现设置调整大小:是恢复:是布尔选项纠正了我的错误大小的精灵动画。希望这有帮助

答案 1 :(得分:1)

我以为SpriteKit会自动处理Retina。尝试删除更改字符串@ 2x的代码行,同时尝试删除设备类型,看看是否也没有为您处理。

我还注意到,如果你使用animateWithTextures,如果设置resize有帮助:NO并恢复:NO