| 情報処理2z(Java version) 課題10:オリジナルゲームへ向けて |
できた所までを班担当SAに見せてチェックしてもらってから帰ってください。
5時45分より早くに帰るのは御遠慮下さい。
できたところまでのプログラムをレポートシステム(Subject:2z10)に提出してください。
Java で使う画像、音声ファイルを自作するには、そのためのペイントソフトや サウンドクリエイトソフトを使う必要があります。 窓の杜等から 気に入ったソフトをダウンロードしてきて作ってみましょう。
自作が難しかったらインターネット上から自分が欲しい画像、音声を頂いてきて Java で使用可能なファイル形式に変換する方法が良いでしょう。 このための変換ソフトも同じく窓の杜にいくつか置いてあります。
ただ窓の杜にあるファイルのうち約半分はシェアウェアです。 フリーウェアは無料で使用することができるソフトですが、 シェアウェアは何らかの形で代金を求められているソフトです。 形態は様々ですが、例えば無料で使っているうちは機能が制限されていて、 送金すると引き換えにパスワードがもらえ、 そのパスワードを入力すると全ての機能が使えるようになります。 もし使ったソフトが気に入ったら作者に代金を送金しましょう。 バージョンアップなど様々なメリットもあります。
私は変換ソフトとして 『IrfanView』(画像変換)、『GoldWave』(音声変換) を 使っています。参考までに。また、少ない数なら変換もします。 フロッピーに落として持ってきて下さい。
基本的に Java アプレットではファイルへの読み書きは禁止となっています。 ただ、アプレットで禁止なだけであって CGI を使って出来ないことはありません。 この説明をするには CGI の説明など新たな事があまりに多く、 とても大変なので『おまじない』的に簡単に使える様なものを 現在作成中です。もう少し待ってて下さい。完成したらウェブページに載せます。
シミュレーションゲームやロールプレイングゲームなどを作ろうとする場合(!?)、 メインの画面(アプレット)の他にウィンドウを作成し、 両方とも表示に使えるようにすると画面構成がすっきりします。
サンプルプログラムを載せて簡単に説明します。
import java.awt.*;
import java.awt.image.*;
public class win extends java.applet.Applet
{
MyWindow w = null;
public void init()
{
w = new MyWindow(100,100);
}
public boolean keyDown( Event ev , int c )
{
if( w == null ) return true;
if( c == 'h' ) w.moveRect(-4,0);
if( c == 'l' ) w.moveRect(4,0);
if( c == 'j' ) w.moveRect(0,4);
if( c == 'k' ) w.moveRect(0,-4);
if( c == 'c' ) w.hide();
if( c == 's' ) w.show();
return true;
}
}
class MyWindow extends Frame
{
Image offscr;
Graphics offscr_g;
int xsize = 100 , ysize = 100;
int rectx = 0 , recty = 50;
MyWindow(int x,int y)
{
super("mywindow");
xsize = x;
ysize = y;
show(); /* Windowsでは、resizeよりも前にshowする必要がある。 */
resize( xsize,ysize);
show(); /* UNIXでは、resizeよりも後ろにshowする必要がある。 */
/* createImageするより先にshowがある必要がある。 */
offscr = createImage( xsize , ysize );
offscr_g = offscr.getGraphics();
}
public void moveRect( int xdif, int ydif )
{
rectx += xdif; /* rectx = rectx + xdif; と同じ */
recty += ydif;
repaint();
}
public void update( Graphics g )
{
paint( g );
}
public void paint( Graphics g )
{
/* Windowsではshowする時点でpaintが呼ばれるので以下のコードが必要。 */
if( offscr_g == null ) return;
offscr_g.setColor( Color.white );
offscr_g.fillRect( 0 , 0 , xsize , ysize );
offscr_g.setColor( Color.black );
offscr_g.fillRect( rectx , recty , 10, 10 );
g.drawImage( offscr , 0 , 0 , null );
}
public boolean keyDown( Event ev , int c )
{
hide(); /* mywindow を消す */
return true;
}
}
|
ここで初めて2つ目のクラスを宣言しています。 このクラスは Frame クラスを extends して、 mywindow に対する描画処理は全てこの新たなクラス MyWindow で行っています。
win クラスの中で、w がこの MyWindow を操作する変数というように宣言します。 同時にサイズも (100, 100) にしていますね。
そして keyDown メソッドで、対応するキーが押されたら MyWindow クラスの moveRect や show, hide を呼び出します。show はウィンドウを作成する命令、 hide はウィンドウを消去する命令です。
あとは仮想画面など、今までの描画命令を普通に使うことができます。
おまけ。
☆いきなりゲームが始まるのもなんですから、
sキーを押したらゲームが始まるようにしたい場合。
(※色々方法はあると思いますが、あくまでも一つの例です)
待機中なのかゲーム中なのかを示す変数を用意し、その変数の値によって、
描画するものや動かす物体の内容を切り替えます。
具体的には……
int gamemode; /* 0:待機中 1:ゲーム中 */
という「今なにをしているのかを表わす変数」を作って、
initメソッドの中で gamemode=0;/* 待機中 */ とやっておいて、
printメソッドは
/* gamemodeの値によって描くものを切り替える */
if(gamemode==0){ 「sを押してください」と表示 ;}
if(gamemode==1){ 通常の描画;}
として、
keyDownメソッドの中に
case 's': /* s が押されるとゲームが始まる */
if(gamemode==0){
ボールやバーの座標の初期化;
gamemode=1;
}
break;
を追加して、
runメソッドの中身を
while(true){
時間調節(sleep);
if(gamemode==1){
バーの移動やボールの移動やはね返り判定;
if(ボールを逃した){gamemode=0;/* 待機中の状態に */}
}
else {
ゲームが始まる前に何かが動く演出を入れたいならこの辺に;
特にないならelseは必要ないでしょう。;
}
repaint();
}
こうしてやれば、
sを押すまでは「sを押せ!」と表示されて、
sを押すとテニスゲームが始まり、
ゲームが終わると「sを押せ!」という表示に戻ります。
この状態でsを押すと再びテニスゲームが始まる、と。
ゲームオーバーの表示等を入れたい人は各自工夫してください。
gamemode==2(ゲーム終了後)という状態を作るとか、gamemode==0の時に
座標などの変数の値から判断して「ゲームオーバー」と表示させるとか。
同様にゲームクリアー時にも演出等が入れられます。