固定小数点で動かす
座標と速度に小数部を持たせて、1ピクセル未満の細かさでキャラクターを動かします。
なぜ小数部が必要か
座標を整数のピクセル単位だけで持つと、速度は「1フレームに1ピクセル」「2ピクセル」のように飛び飛びになります。ゆっくり加速する、重力で少しずつ落ちる、といった動きを作るには、1ピクセルより細かい単位(サブピクセル)が必要です。
ここでは、1ピクセルを256分割した単位を使います。
| 変数 | 大きさ | 内容 |
|---|---|---|
| $10 | 1バイト | X座標の小数部(1/256ピクセル単位) |
| $11・$12 | 2バイト | X座標の整数部(ピクセル) |
| $14・$15 | 2バイト | X方向の速度(符号付き、1/256ピクセル単位) |
$10~$12 を、1/256ピクセル単位の24ビットの値として扱います。
速度を座標に加える
速度は符号付きの16ビットなので、24ビットの座標に加えるときは、上位バイトを符号で埋めて(符号拡張して)加えます。
; X座標に速度を加える
REP #$20
CLC
LDA $10
ADC $14 ; 座標の下位16ビット + 速度
STA $10
SEP #$20
LDA.b #$00
BIT $15 ; 速度の符号(ビット7)を調べる
BPL .plus
DEC A ; 負の速度なら上位バイトは$FF
.plus
ADC $12 ; 繰り上がりと符号拡張した上位バイトを加える
STA $12
LDA命令・BIT命令・DEC命令はキャリーフラグを変えないので、最初のADC命令の繰り上がりがそのまま最後のADC命令に渡ります。
加速と重力
速度にも小さな値を毎フレーム加えることで、加速や重力を表現します。
; Y方向の速度($18・$19)に重力を加え、最大の落下速度で止める
REP #$20
LDA $18
CLC
ADC.w #$0040 ; 1フレームに 0.25 ピクセル/フレーム ずつ加速
BMI .store ; 上昇中(負の速度)ならそのまま
CMP.w #$0400 ; 最大の落下速度 4ピクセル/フレーム
BCC .store
LDA.w #$0400
.store
STA $18
画面に表示する
スプライトのOAMに書くのは、整数部だけです。
SEP #$20
LDA $11
SEC
SBC $40 ; カメラのX座標を引いて、画面上の座標にする
STA $0200 ; OAMの写しのX座標