80年代の画面表示技術
目次
ビットマップ
ファミコン・SG-1000・MSX には、ビットマップ画面はありません。
しかし、話を分かりやすくするために、パソコンなどにはついていたグラフィック(ビットマップ)画面の話をします。
グラフィック画面では、画面の全情報を記録できるような大量のメモリを用意して、1ドットごとの色情報を記録しておきます。
これを、走査線の速度に合わせて読み出し、色に応じてビームを強弱させると…画面に絵を出すことが出来ます。
単純に言えば、画面を作る方法と言うのは、これで終わり。
でも、この方法には問題があります。メモリを大量に用意する必要があるのです。
たとえば、同じ 1983年発売の PC-8801mkII では、640x200、8色の画面を作ることが出来ました。
8色と言うのは、光の3原色である赤・青・緑が、それぞれ「ある」「ない」の2つしか選べない、ということ。
(PC-8801mkII は、1981年発売の PC-8801 とほぼ同等の機能の廉価版です。以下、PC-8801 と表記します)
640x200 で、1色分の表示は 1bit なので…計算すれば、1色分は 16Kbyte のメモリが必要、となります。3色分で 48Kbyte。
1983年ごろの RAM は 16Kbyte で5千円程度だったようです。PC-8801はグラフィック RAM だけでファミコンと同程度の価格になってしまいます。
これでは、「おもちゃ」であるゲーム機として売り出すことはできません。
グラフィック用は赤・青・緑用に 16Kbyte づつ分割され、周辺回路にアクセスすることで、メインメモリの一部と交換できるようになっていました。
このような、同じアドレスでも違うメモリにアクセスする手法を「バンク切り替え」と呼びます。重要なキーワードです。
なお、メモリには大雑把に分けて DRAM と SRAM がありますが、16K 5千円は DRAM の値段です。
8801 のグラフィックRAM、ファミコンのRAMともDRAM ですが、後にファミコンのカートリッジに入れられた「バックアップメモリ」などは SRAM で、DRAM よりも高価でした。
PC-8801 のようなグラフィック表示では、16x16 のキャラクターを少し動かすたびに、
・キャラクターに消されてしまっていた背景 256ドット分(96byte)を描画
・新たな場所にキャラクター 256ドット分(96byte)を描画
という処理を繰り返していました。1キャラを動かすのに、192byte も書き換えが必要なのです。
当時は CPU がそれほど高速でなかったこともあり、この処理方法でゲームを作るには高度なプログラム技術が必要でした。
テキスト画面
当時…よりちょっと古いですが、1982年発売のパソコン MZ-700 などでは、少ないメモリで画面出力を行うためにグラフィック画面は持ちませんでした。
グラフィック画面を持っていないのはそのせいもあり、1982年ごろのマシンはグラフィックを持たなかった、と言うわけではありません。
ではどうするかと言えば、テキスト画面を持つことになります。
特定の1バイトに 65 という数字を入れれば、画面には A という文字が表示されます。
つづいて 66、67 と入れれば、 B、C と表示されます。
(65 は A のアスキーコード。同様に 66、67 は B、C となる。MZ-700 は厳密に言えばアスキーコードとは違う値を書き込むのだが、テキスト画面の説明は MZ-700 に限った話ではないのでアスキーコードで説明する。)
文字は 8x8 ドットで構成されたため、たった1バイトで 64ドットを表示できたことになります。
メモリの削減効率としては、なかなかいいものでしょう?
ただし、表示するための方法は少し複雑になります。
1)走査線の番号を8で割る。商を n 、余りを m とする。
文字の高さは8ドットなので、「上から n 行目目」の文字の「上から m ライン目」を表示することになります。
2)n 行目の文字コードを取り出す。
全部の文字を取り出すわけではなく、1文字分づつ処理します。
3)文字コードに応じた「フォントデータ」(大抵は ROM に用意されている)を読み出す。
1文字分のフォントは 8byte です。
文字コードを c として、c*8 番目からフォントデータが始まります。
上から mライン目のデータなので、 c*8+m 番目のデータを読み出すことになります。
m が 0 なら、赤丸のついたデータが読み出されることになる。
同様に、m が 1、2、3なら、同じ文字のデータを読み出すのでも、緑、青、黄と読み出すデータが変わる。
4)横8ドットのデータを表示。
取り出したデータは「1バイト」なので、8bit あります。これを出力すれば、8ドットの表示が完成します。
5) 2 に戻り、次の文字を処理。
行の終わりまで(走査線が右端に達するまで)処理します。
1文字毎に読み出されたフォント画像のデータは、走査線に乗って送り出され、横方向に並べられる。
m が 0 のときに読み出されたデータなら、赤丸で示された走査線で送り出される。
m が 1、2、3のときも、先ほどと同様に緑、青、黄の走査線で送り出される。
6) 1 に戻り、次の走査線を処理。
画面の終わり(走査線が下端に達するまで)処理します。
実際に走査線にデータを送り出すのは 4 の部分だけですが、その前処理となる 2~3 ではややこしい処理が必要になります。
走査線は待ってくれませんから、実際にこんな方法で処理していては間に合いません。
そこで、実際の走査線よりも「少し先」の文字表示のためのデータを先に作っておき、そのデータを基に走査線を処理します。
この方法なら、今出力中のデータがなくなる前に次のデータが用意できれば良いので、少し時間の余裕が生まれます。
通常は、フォントデータは ROM に置かれており、書き換えできません。
詳細は後で書きますが、ファミコンでもこれと類似の方法で画面が作られています。
テキスト画面(ファミコンでは BG 画面と呼びます)は、その方式上8ドット単位でしかキャラクターを配置できません。
ゲームの背景などに使用し、そのうえで動くゲームのキャラクター(マリオやソルバルウ)などは、後述するスプライトで描くことになります。
フォントのデータはモノクロだが、出力時に1文字単位で色指定ができたためだ。
そう、先にグラフィック画面を説明した PC-8801 は、テキスト画面も持っていた。
そしてなんと、グラフィックとテキストは「重ね合わせて」表示できた。
当時はテキストとグラフィックはモードを切り替える場合が多く、重ね合わせはすごいことだった。
余談ついでに書いてしまえば、1982 年発売の FM-7 は、テキスト画面を持たずにグラフィックに統一してしまった。
当時の CPU では、文字をグラフィックに描くのは遅かったため、メインとグラフィック用に2つの CPU を搭載するという贅沢なマシンだった。
MSX の場合、フォントの段階で色を付けることはできたが、出力時の変更はできない。
モードによって、フォントはモノクロだったり、多色使えたりする。
ファミコンでは、フォントに相当するものがモノクロではないし、出力時の変更も可能。
ただし、1文字単位での変更はできない。
テキスト画面にもいろいろあるのである。