[ATARI LYNX] 画面の上下反転機能LYNXにはハードウェアで画面の上下反転機能が搭載されている。なぜそのよ うな機能が搭載されているかというと、欧米の人は左利きの人が多いらしく、 それらの人向け用に、本体を逆さまにして使用できるようにした結果そうなっ たらしい。なかなか面白い理由だと思った。確かにLYNXは上下対称の形をしていて、ど ちらで持っても同じように使えるんだな。 持ち方については、GBASPの縦持ちにも一考の余地がある。![]()
どのように持っても左手で十字キー操作なので、その点でLYNXとは話が違う けど……。 持ち方自体は、どちらとも違和感無く持てて、操作感も特に変わらなかった。 だから操作系に関しては好きなようにすればいいとして、問題なのは画面だ。 液晶が左に来るのと、右に来るのとでは印象が大きく違う。 個人的には左に来た方がしっくりくるけど、これは人によって違う気もする。 右脳と左脳が関係する気もする。しない気もする。どうだろ。分からん。
http://membres.lycos.fr/advdbg/ これはなかなかいい。 プロジェクトを作る必要があるようなのでまだソースレベルデバッグは試し てないけど、ELFを食わせて出来る範囲で触ってみたところ… 例えばDMA転送のログが取れたり(DMA): DMA0 Transfert from [0x020026D4] to [0x07000200], Size=32 (128 bytes), Mode=32bits (DMA): DMA0 Transfert from [0x020030D4] to [0x07000000], Size=256 (1024 bytes), Mode=32bits (DMA): DMA0 Transfert from [0x020036D4] to [0x07000200], Size=32 (128 bytes), Mode=32bits (DMA): DMA0 Transfert from [0x020038D4] to [0x07000000], Size=24 (96 bytes), Mode=32bits (VCOUNT割り込みでOAMにDMA転送をセットしている様子が見られる)画面モードのログが取れたり########## Changing Display Mode ########## Video mode: 0 Display Frame Select: 0x06000000 H-Blank Interval Free: 1 OBJ VRAM Mapping: 1D Forced Blank: -- Screen Display BG0: On Screen Display BG1: -- Screen Display BG2: -- Screen Display BG3: -- Window 0 Display : -- Window 1 Display : -- OBJ Window Display: -- (タイルモード時はここでマップベース・キャラベースアドレスも分かると いいんだけどなあ)と、GBAに特化したデバグが出来るので、活用すればもの凄く便利だと思う。 エミュレータ込みの環境しか用意されていないので、他のエミュレータを使 え無いのが難点か。エミュレーション精度が問題となるけど、説明書にある ようにウインドウとモザイクがサポートされてない点を除けば、そこそこの 完成度のように思った。スプライトダブラも余裕で動いているし。 追々、適当なベンチで詳しく検証してみようと思う。
走|召連身|寸 | 68|K タイトル画面が収まらない。 BGMをMIDIにコンバートして音色の録音。音色番号が同じで中身の違う音色が 多いのでメモ取り重要。曲側の手直しが面倒だけど、一から作る労力に比べ たら数万倍楽か。ループポイントの設定、スプリットを別けて音は完成。 あとはBGマップを出せば絵・音両方の素材が一段落着くかな。もう移植作業 に入れる段階だけど、どうしようか迷う。このまま突っ走るべきか?
90度回転させてみたところ……うおーっ! これは! ついさっきまで、横スクロールを取り入れればなんとかなるだろうと思って いて(実際、横スクロールする縦シューの殆どは仮想画面がだいたい正方形 になっているし)GBAの 160x240 をスクロールして 256x240、上下8ドット くらいは諦めてもらうかなどと妄想していたのだけど……。 いざ表示してみると妄想以上に厳しい。上画像のボスを画面中央に置いてみ ると、翼部分の弾射出位置が見えない! そもそもの問題なんだけど、超連射の敵配置は自機を左右に忙しく振るよう に配慮されていて……。例えば右側の敵に専念している間に、左の見えない 位置で敵が生まれて、そして見えない場所から弾を撃ってきて、そして死に いたるという恐ろしい事態が至る所で待ち受けているのだ。 まあ、そこらへんは最初から折り込み済みで、結局のところ指がパターンを 覚えてるから構わないという話もあるにはあるんだけど。
要するに歯抜けで転送すればいいのだけど、そうするとDMA に頼れないので 他の転送手段を考える必要がある。で、LDM/STMの出番なのであった。これで歯抜け転送が出来た。しかしまだ優先度が崩れる。これはもう真面目 に優先度について考えるしかないかも分からんね。u32 *obj = (u32 *)&sp_buf[array_select][next_part].spr[0]; u32 *oam = (next_part & 0x01) ? OAM_EVEN : OAM_ODD; num = (num + 1) & ~1; asm ( "1: \n" "ldmia %0!, {r0-r1} \n" "stmia %1!, {r0-r1} \n" "add %1, %1, #8 \n" "ldmia %0!, {r0-r1} \n" "stmia %1!, {r0-r1} \n" "subs %2, %2, #2 \n" "add %1, %1, #8 \n" "bpl 1b \n" /* out */ : /* in */ : "r"(obj), "r"(oam), "r"(num) /* destroyed */ : "r0", "r1" );
ノートでやってもいいんだけど、使えるコントローラが限られるので、とい うかUSB のジョイパッドしか選択肢が無いので、要するに入力遅延が激しく 気になるので、やはり遅延の無い環境でやりたいと思うのが人の常であると ころの俺。 というわけで、PCG キャッシュを16x16 専用に作り変えたり、XSP と同等の 機能をおおよそ満たすようにダブラを弄ったりして、きたる日に備えるので あった。XSP_Test.zip それで思ったんだけど、超思ったんだけど、XSP には優先度破綻軽減モード があるわけで、しかし今回のプログラムにはそれがついてないわけで、爆発 アニメなどで破綻が顕著に分かってしまうのだ。 そもそもXSP はスプライト全体をスプライト番号の奇数・偶数で別けて、ブ ロック毎に飛び飛びで転送をしているので、優先度破綻軽減モードを使わな くてもある程度の保護は為されているのだ。 一方こちらは、スプライトを番号の前半・後半に別けてDMA で一括転送して いるため、ラスタブロックの境にあるスプライトの優先度は簡単に破綻して しまう。 CPUパワーを駆使したいところだけど、水平帰線期間が短いのでなかなか…。
さて、実はこのソースなのだけど、エミュレータでは増やしたスプライトが ちゃんと表示されているけど、色々弄っているうちに、実機に持っていくと 表示されないという症状が出てしまった。実機で正常に動いていた頃のソー スを紛失してしまった(バージョン管理ソフトを使うべき)のでどこで何を 間違えたのか分からんのだ。 とりあえず、DMA転送が実行されていないような気配なので、そうなる状況 を考えてみると、配列が奇数アドレスに配置されてるのではないかと思った 次第。 で、調べてみる。mapファイルを見てもいいけど、必要な情報が点在していて 分かりづらい。そこでnmを使うのだ。するとアドレス順にソートされたシン ボル情報が出力されるので、メモリがどのように使われているのかを見ると きに便利なのであった。 02001634 d sp_buf あれれ?ちゃんと偶数アドレスに配置されてるよ?(;´Д`)コマル
ここしばらくBulletGBA作者のtekezoさんとのスプライトダブラ談義に花を 咲かせていて、そのときの話の流れでスプライトダブラの仕組みを解説した ページを見せて頂いたのだけど、俺だけが見るのじゃ勿体無いと思っていた のと、それにスプライトダブラについて(XSP などの公開されているソース はあっても)文面で解説したものは無かったので、今回の公開は有意義だよ な!と思った。 GBA で学ぶ古典的プログラミング (スプライトダブラ) ハイ、ここまで宣伝です。 氏のソースは C++ で書かれているわけで、それに対して C は圧倒的に無力 であり、何故 extern "C++" が C に無いのかと枕を涙で濡らしつつ、ドモホ ルンリンクルでお肌を濡らし、折角だから C で書かれた俺版のソースを公開 することにした。 でも中途半端なテストプログラムの状態なまま、長い間腐らせてあったもの だから、このまま使えると思っちゃいかんよ。 doubler_test.zip
ファイルを焼いたDVD-Rは、読めなくなると非常にダメージがでかいという ことを体で理解した。つまり念入りに、執拗に、注意深く、小動物を追い詰 めたライオンのように、そして時にはエレガントに、ベリファイをするよう 心がけるべきだと思った。 話を総合すると、ライオンはDVD-Rをエレガントに焼く。
webarchive: 基礎から学ぶGBAプログラミング GBAKiso.zip webarchive: libpgba libpgba-1.0.tar.gz それぞれサイトが消えてしまっているようなので転載しておきます。 マズいようでしたら消しますので、コメントかメールにてご連絡ください。 If you wish to delete archives, comment or email me please.
Forthcoming devkitARM release 18 devkitARMの新版は4.1と4.0.3のどっちがいい?という投票をやってるよ! もちろん俺は3.4.3に票を投ずるがね。hehehe... ってオイ……ねえよ!3.4.3がねえよ!どうすりゃいいんだよ俺は……。
簡単なクラスを書いて確かめてみた。CODE_IN_IWRAM を付けたり外したりしながらコンパイルしてみる。 (CODE_IN_IWRAM有り) 0x03000020 Tester::WaitVBlank() 0x03000044 Tester::MainLoop() (CODE_IN_IWRAM無し) 0x08000594 Tester::WaitVBlank() 0x080005b8 Tester::MainLoop() ああ。 これはもうオブジェクト指向に移行するかも分からんね。#ifndef DEBUG # define CODE_IN_IWRAM __attribute__ ((section (".iwram"), long_call)) #else # define CODE_IN_IWRAM #endif class Test { public: Test() {} ~Test() {} CODE_IN_IWRAM void MainLoop(void); private: CODE_IN_IWRAM void WaitVBlank(void); static u32 fcount; }; u32 Test::fcount = 0; CODE_IN_IWRAM void Test::MainLoop(void) { while (1) { WaitVBlank(); fcount++; print_num(map0, fcount); } } CODE_IN_IWRAM void Test::WaitVBlank(void) { while (REG_VCOUNT != 159) {} while (REG_VCOUNT == 159) {} }
BulletGBA 「GBA の縦持ち+スプライトダブラ」と、あまりにも自分の方向性と被って い(た|る)ので驚いているわけですが、ソースを見てまた驚いた。 というのは明示的にIRAMへ関数を配置しているわけでも無さそうなのに処理 速度が速い。スクリプトの内容にもよるけど、300発くらい弾を出しても平 気でフルフレーム出ている。こ、これはっ…!IRAMに関数置きまくりな自分 のプログラムが150発程度で処理落ちを始めている事実と比較してただただ 愕然とするばかりであった。 というか、そもそもクラスのメソッドがどこに配置されるのか俺的に謎であ り、コンパイルオプションの-mthumbが潰されているので、ひょっとしたら 全てメモリ上に置かれているのかとも思うのだけど……。 mapファイルを見てしまえば一目瞭然なのでmakeしようとしたら、msysでは make出来なかった。ううう。