Skip to content

SpriteSheet

何波 edited this page Feb 24, 2019 · 9 revisions

SpriteSheet

var data = {
    images: ["sprites.jpg"],
    images: [this.game.load.get('ship')]],
    frames: {width:50, height:50},
    frames: {width:64, height:64, count:20, regX: 32, regY:64, spacing:0, margin:0},
    frames: [
        // x, y, width, height, imageIndex*, regX*, regY*
        [64, 0, 96, 64],
        [0, 0, 64, 64, 1, 32, 32]
        // etc.
    ],
    animations: {
        // start, end, next*, speed*
        run: [0, 8],
        jump: [9, 12, "run", 2]
    },
    animations: {
        stand:0,
        run:[1,5],
        jump:[6,8,"run"]
    },
    animations: {
        walk: {
            frames: [1,2,3,3,2,1]
        },
        shoot: {
            frames: [1,4,5,6],
            next: "walk",
            speed: 0.5
        }
    }

};
var spriteSheet = new createjs.SpriteSheet(data);
var animation = new createjs.Sprite(spriteSheet, "run");

SpriteSheet原点(regX,regY)

在用Animate CC制作一个MovieClip元件时,可以Edit Multiple Frames,再Ctrl+A全选所有帧拖动元件到“+”号位置来改变Movie Clip的中心点(一般我们拖动“+”号到MC中心)。在Libray中,右键选中此Movie Clip从右键菜单中选择“Generate Sprite Sheet”,导出的Data数据会带上regX,regY。

export default class Ship {
  constructor (game) {
    this.game = game
    this.init()
  }

  init () {
    let data = {
      images: [this.game.load.get('ship')],
      frames: [
        // x, y, width, height, imageIndex*, regX*, regY*
        // fly,die,bubble动画所有帧的中心点都在图片的中央,如果用Sprite来设置中心点,是很难分别设各animations的regX,regY的
        [0, 0, 82, 60, 0, 41, 30],
        [0, 60, 130, 130, 0, 65, 65],
        [0, 190, 130, 130, 0, 65, 65],
        [0, 320, 130, 130, 0, 65, 65],
        [0, 450, 170, 170, 0, 86, 88]
      ],
      framerate: 5,
      animations: {
        fly: [0],
        die: [1, 3],
        bubble: [4]
      }
    }
    let spriteSheet = new createjs.SpriteSheet(data)
    this.sprite = new createjs.Sprite(spriteSheet)
    this.game.stage.addChild(this.sprite)
    this.sprite.set({ x: this.game.canvas.width / 2, y: this.game.canvas.height / 2 })
    console.info(this.sprite.regX) // sprite的regX还是为0
    this.sprite.gotoAndPlay('fly')
  }
}

data.framerate或Sprite.framerate

每次tick的时候,Sprite就会执行advance()函数向前执行,设置framerate后,Sprite就会以event.delta

Sprite源码

p.advance = function(time) {
    // 首先看Sprite自身有没有设置framerate,如果没有找spriteSheet.framerate
    // 我们一般把framerate设置在spriteSheet的data上
    var fps = this.framerate || this.spriteSheet.framerate;
    var t = (fps && time != null) ? time/(1000/fps) : 1;
    this._normalizeFrame(t);
};

如果设置了spriteSheet.framerate,sprite帧频还是不变,有可能是因为stage.update没有加参数据event Note that the Sprite framerate will only work if the stage update method is provided with the Ticker/tick:event

createjs.Ticker.addEventListener("tick", handleTick);
function handleTick(event) {
   // 这里一定要加上event,如果不加event在tick的时候缺少很多事件属性,如不会有event.delta。
   // 则spriteSheet的data.framerate不会生效
   stage.update(event);
}

MovieClip.framerate同上

要MovieClip.framerate生效,必须设置Tick后state.update(event)

例如,如果一个帧速率framerate = 10的movieclip被放置在一个以40fps速度更新的阶段上,那么movieclip将大约每4个节拍前进一帧。这并不准确,因为每一次tick之间的时间time在不同的帧之间会略有不同。

framerate好处

因为可以设置Sprite(SpriteSheet)和MovieClip的framerate,我们完全可以用createjs.Ticker.timingMode = createjs.Ticker.RAF。这样可以利动画Ticker为requestAnimationFrame带来60帧频的性能,又能单独设置Sprite和MovieClip的各自帧频。

Clone this wiki locally