さて、2ボタンしかない日本のファミコンミニにSNES入れてどうすんだといわれそうですが、
まぁ海外モデルでは複数ボタンもあるしどうにかなるんじゃね、ということで試していたSNESエミュレータがぼちぼち動きそうなので少しまとめておきます。
とりあえず、retroPiとかにも持っていかれる元のsnes9xを選定してみました。
GitHub - domaemon/snes9x-sdl: Snes9x - Portable Super Nintendo Entertainment System (TM) emulator
ここからcloneしてコンパイルします。
まず、ファミコンミニに非常に近いA33上で動かしてみることにします。
このA33にはLCDをつけていて、X11とかはちゃんと動いていますが、
適当にコンパイルした状態だと色がきちんと出ないうえに、
横に二つ並んで表示される、という困った状態になりました。
で、ここまでは来るわけだ。hackchi化したカーネルのコマンドラインから動かせてるのでほぼこれで動きそう。ただ、例によって画面の変更がきかないのでこうなってるっぽいな。やっぱり最終フレームバッファを720pでとってやらないと、ということか。 pic.twitter.com/XjLUsjiZtS
— ひろみつ(85.1kg) (@bakueikozo) 2017年2月6日
何となく推測すると、フレームバッファの色解像度と
出力されているLCDの解像度が合わない、ということのようです。
ここで早めに「きれいに2つ並んでるんだから、元が16bitで32bitディスプレイなんだな」と気づけばよかったんですが、そこに気付くまでには結構時間がかかりましたw
これは、結構早い段階でファミコンミニでも再現できていたため、
A33上で同じ現象が出る、ということはファミコンミニでも直すのに役立ちました。
↓のはpcDuinoでコンパイルした奴をファミコンミニに持って行ったものです。
結構前から動かせそうで動かせてなかったんですよね。
一応動きそうなんだが、いろいろ変。このボードの構成では、かなり決め打ちされた構成でのHDMI出力しか出ないので、SDLとかの最終出力解像度をそれに合わせてレンダリングしてもらえばいいような気はするが。ドライバ周りを工夫するか、プログラムのほうで拡大させれば動くのかなぁ…? pic.twitter.com/ICxpmysqRi
— ひろみつ(85.1kg) (@bakueikozo) 2017年1月18日
で、いろいろ調べてみたところ、ファミコンミニのフレームバッファとHDMI出力は
「1280x720 32bit」にすればきれいに出る、ということがわかりました。
ここで、snes9xのSDLポートはどうなっているかというと、
見事に16bit固定のようです。さらに、
のように、内部レンダリングも16bit固定になっていました。
もしかして、ここを変えればいいんじゃね?と思いましたが
ここに指定できるのは、結局16bitカラーのみのようです。
エミュレーションの都合上仕方がないようなので、作成されたバッファを32bitに転送することで色変換を実現しました。
内部バッファと一緒にスクリーンは別途作って
フリップ時にいったん経由して描画する
そんな感じなのと、SDL1.2に依存しているので拡大縮小が出来ず、最大パフォーマンスが出ていませんが、SDL2に移行できればSDL_BlitScaledが使えて、
そうすると内部バッファとの関係でもう少しパフォーマンスが上がるかもしれません。
で、今のところはとりあえずこんなもんです。
ファミコンに持ってきたがダメだ、ちょっと重すぎ 描画最適化しないとダメそう。 pic.twitter.com/OzXueO1P2B
— ひろみつ(85.1kg) (@bakueikozo) 2017年2月6日
上から下に移動してる青線はフレーム描画のテスト用に書いてるものです。
ちょっとまだ遅いし、画面解像度の1280x800を使い切れていない(小さめで書いてる)ので、ぼちぼち調整して、あとはパッド対応をしたらどうにかなるかな。