welcome: please sign in
location: "ピースを動かす"の差分
4と41のリビジョン間の差分 (その間の編集: 37回)
2009-12-15 12:40:54時点のリビジョン4
サイズ: 1192
編集者: masahiko
コメント:
2012-01-12 07:00:55時点のリビジョン41
サイズ: 3868
編集者: masahiko
コメント:
削除された箇所はこのように表示されます。 追加された箇所はこのように表示されます。
行 1: 行 1:
#acl All:
行 3: 行 2:
ピースを1つ取り除いてできた空白部分を使って
ピースを1つ取り除いてできた空白の箇所を使って
行 5: 行 5:
{{{#!java
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
行 10: 行 6:
public class Game14 extends JPanel implements MouseListener
{
 int haba;
 int yoko, tate;
 String fname;
 Image img;
 int[][] ban;
 int spx, spy;
 
 Game14()
 {
  addMouseListener(this);
 }
 public void mousePressed(MouseEvent e)
 {
  int x, y, dx, dy;
----
=== 空白の箇所の表現 ===
行 27: 行 9:
  x = e.getX() / haba;
  y = e.getY() / haba;
  dx = (x<spx) ? -1 : (x>spx) ? 1 : 0;
  dy = (y<spy) ? -1 : (y>spy) ? 1 : 0;
// if(x < spx)
// dx = -1;
// else if(x > spx)
// dx = 1;
// else
// dx = 0;
// if(y < spy)
// dy = -1;
// else if(y > spy)
// dy = 1;
// else
// dy = 0;
  if(dx != 0 && dy != 0)
   return;
  while (x != spx || y != spy)
  {
   ban[spx][spy] = ban[spx+dx][spy+dy];
   spx = spx + dx;
   spy = spy + dy;
  };
  repaint();
 }
 
 public void mouseEntered(MouseEvent e) { }
 public void mouseExited(MouseEvent e) { }
 public void mouseReleased(MouseEvent e) { }
 public void mouseClicked(MouseEvent e) { }
}}}
どこに空白があるかを表すために、インスタンス変数を使います。

 * spxで空白の横方向の位置を、0~3の値で表すものとします。

 * spyで空白の縦方向の位置を、0~3の値で表すものとします。

例えば、spx=0, spy=2 のときは
上から3番目の左端が空白。

=== 初期化 ===

最初は右下隅のピースを取り除いた位置です。
したがって値は
 . spx = 3
 . spy = 3
空白箇所は右下のピースを取り除いたものですから、
配列要素の値は右下のピースの値としておきます。
 . ban[spx][spy] = 15

----
=== 空白箇所の表示 ===
paintComponent内に記述。

spx,spyで表された場所は空白であることを示すため、
1色で塗りつぶします。

クリック時の処理の演習ではcx,cyで示された位置を塗りつぶしていましたが、
spx,spyが示す箇所を塗りつぶすように修正します。

塗りつぶしの色は好みのものを指定してください。
----
=== ボタンが押されたときの処理 ===
mousePressed内に記述。

クリック時の処理の演習では
クリックされた座標x,yから対応する位置cx,cyを求めました。

 . cx,cyはmousePressedメソッド内でしか使わないので、(インスタンス変数ではなく)メソッド内の変数として宣言します。

このcx,cyとspx,spyの値を比較し、
クリックされた位置のピースが移動可能かどうか判定し、
可能な場合は移動する処理を記述します。

==== 移動可能かどうかの判定 ====

空白箇所の上下左右のとなりにあるピースの上でクリックされたときは、
そのピースをスライドして移動できる。

例えば丸で示した位置が空白のとき
 . {{attachment:idou1.png}}
クリックされた位置がA,B,C,Dのどれかであればよい。

空白の位置はspx,spyで、クリックされた位置はcx,cyで表されているので、
これを用いて判定を行う。

例えば、丸の位置が空白部分でAの位置でボタンが押された場合、変数の値は次のようになっています。
 . spx は 1
 . spy は 2
 . cx は 2
 . cy は 2

==== ピースを移動する処理 ====

丸の位置が空白部分で、そのすぐ右のAの位置でボタンが押された場合を考えます。

次の処理を順に行ないます。
 . 1)Aの位置にあるピースをすぐ左の空白位置に移動します。
 . 2)空白位置をAの位置に変更します。
 . 3)新しい空白位置に対応する値を代入します。
1)Aの位置どのピースがあるかはban[cx][cy]の値として記憶しており、
この値を空白位置である(spx,spy)に移すには
 . ban[spx][spy] = ban[cx][cy]
を行えばよい。

2)spx,spyの値を新しい空白位置の値であるcx,cyに修正します。
 . spx = cx
 . spy = cy

3)空白位置に対応する値(15)を代入します。
 . ban[spx][spy] = 15

以上をまとめると次のようになります。
 . ban[spx][spy] = ban[cx][cy];
 . spx = cx;
 . spy = cy;
 . ban[spx][spy] = 15;
空白の右隣のAの位置で考えましたが、
B,C,Dの位置でもこの命令でよいことを理解しておくこと。
----
=== プログラム ===
 {{{#!java
 }}}
----
=== 演習 ===

ボタンが押された位置が空白箇所の隣であるかを判定する条件を
?
の位置に記述しプログラムを完成させなさい。

ピースを動かす

ピースを1つ取り除いてできた空白の箇所を使って 移動するための処理を記述します。


空白の箇所の表現

どこに空白があるかを表すために、インスタンス変数を使います。

  • spxで空白の横方向の位置を、0~3の値で表すものとします。
  • spyで空白の縦方向の位置を、0~3の値で表すものとします。

例えば、spx=0, spy=2 のときは 上から3番目の左端が空白。

初期化

最初は右下隅のピースを取り除いた位置です。 したがって値は

  • spx = 3
  • spy = 3

空白箇所は右下のピースを取り除いたものですから、 配列要素の値は右下のピースの値としておきます。

  • ban[spx][spy] = 15


空白箇所の表示

paintComponent内に記述。

spx,spyで表された場所は空白であることを示すため、 1色で塗りつぶします。

クリック時の処理の演習ではcx,cyで示された位置を塗りつぶしていましたが、 spx,spyが示す箇所を塗りつぶすように修正します。

塗りつぶしの色は好みのものを指定してください。


ボタンが押されたときの処理

mousePressed内に記述。

クリック時の処理の演習では クリックされた座標x,yから対応する位置cx,cyを求めました。

  • cx,cyはmousePressedメソッド内でしか使わないので、(インスタンス変数ではなく)メソッド内の変数として宣言します。

このcx,cyとspx,spyの値を比較し、 クリックされた位置のピースが移動可能かどうか判定し、 可能な場合は移動する処理を記述します。

移動可能かどうかの判定

空白箇所の上下左右のとなりにあるピースの上でクリックされたときは、 そのピースをスライドして移動できる。

例えば丸で示した位置が空白のとき

  • idou1.png

クリックされた位置がA,B,C,Dのどれかであればよい。

空白の位置はspx,spyで、クリックされた位置はcx,cyで表されているので、 これを用いて判定を行う。

例えば、丸の位置が空白部分でAの位置でボタンが押された場合、変数の値は次のようになっています。

  • spx は 1
  • spy は 2
  • cx は 2
  • cy は 2

ピースを移動する処理

丸の位置が空白部分で、そのすぐ右のAの位置でボタンが押された場合を考えます。

次の処理を順に行ないます。

  • 1)Aの位置にあるピースをすぐ左の空白位置に移動します。
  • 2)空白位置をAの位置に変更します。
  • 3)新しい空白位置に対応する値を代入します。

1)Aの位置どのピースがあるかはban[cx][cy]の値として記憶しており、 この値を空白位置である(spx,spy)に移すには

  • ban[spx][spy] = ban[cx][cy]

を行えばよい。

2)spx,spyの値を新しい空白位置の値であるcx,cyに修正します。

  • spx = cx
  • spy = cy

3)空白位置に対応する値(15)を代入します。

  • ban[spx][spy] = 15

以上をまとめると次のようになります。

  • ban[spx][spy] = ban[cx][cy];
  • spx = cx;
  • spy = cy;
  • ban[spx][spy] = 15;

空白の右隣のAの位置で考えましたが、 B,C,Dの位置でもこの命令でよいことを理解しておくこと。


プログラム

  •    1 
    


演習

ボタンが押された位置が空白箇所の隣であるかを判定する条件を ? の位置に記述しプログラムを完成させなさい。

ピースを動かす (最終更新日時 2012-01-12 07:09:21 更新者 masahiko)