Files
prosperon/anim2d.cm
2026-02-24 21:08:46 -06:00

96 lines
1.9 KiB
Plaintext

var film2d = use('film2d')
var graphics = use('graphics')
var anim_proto = {
type: 'sprite',
play: function(name) {
var anim = name ? this._anims[name] : this._anims
if (!anim || !anim.frames) return this
this._anim = anim
this._frame = 0
this._elapsed = 0
this._playing = true
this.image = anim.frames[0].image
return this
},
stop: function() {
this._playing = false
return this
},
resume: function() {
this._playing = true
return this
},
update: function(dt) {
if (!this._playing || !this._anim) return
var frames = this._anim.frames
this._elapsed += dt
while (this._elapsed >= frames[this._frame].time) {
this._elapsed -= frames[this._frame].time
this._frame++
if (this._frame >= length(frames)) {
if (this._anim.loop) {
this._frame = 0
} else {
this._frame = length(frames) - 1
this._playing = false
break
}
}
}
this.image = frames[this._frame].image
},
destroy: function() {
film2d.unregister(this._id)
}
}
return function(props) {
var img = props.image || props.anim
var anims = graphics.texture(img)
var defaults = {
type: 'sprite',
pos: {x: 0, y: 0},
width: null,
height: null,
anchor_x: 0.5,
anchor_y: 0.5,
rotation: 0,
color: {r: 1, g: 1, b: 1, a: 1},
opacity: 1,
tint: {r: 1, g: 1, b: 1, a: 1},
filter: 'nearest',
plane: 'default',
layer: 0,
groups: [],
visible: true
}
var data = object(defaults, props)
data._anims = anims
data._anim = null
data._frame = 0
data._elapsed = 0
data._playing = false
data.image = null
var s = meme(anim_proto, data)
// Auto-play: if anims is a single animation, start it
if (anims && anims.frames) {
s._anim = anims
s._frame = 0
s._playing = true
s.image = anims.frames[0].image
}
film2d.register(s)
return s
}