androidアプリで困っています。ご教授ください

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
mi_l

androidアプリで困っています。ご教授ください

#1

投稿記事 by mi_l » 12年前

イライラ棒をつくり、ステージを自分なりにアレンジして、次は画像を使おうと思いました。

そこで、まずは難しそうなことは避けて、四角い(正方形)当たったらアウトな範囲を作りその上におなじ大きさに切り取った適当な画像をのせれば、画像に当たった=アウトの範囲に当たったになり、正常に動作すると思いました。

そこで自分なりにコードを書いてみましたのでご指摘お願いします

まずはイライラ棒の今回の質問で最低限必要だと思ったものを載せます。
Barricade.java

コード:

package net.dixq.irairabar;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PointF;

public class Barricade extends Task
{
	//障害物のタイプ
	public enum eType
	{
		OUT,//あたるとアウトになる
		GOAL//あたるとゴールになる
	}

	protected PointF  _center = new PointF(0,0);		//図形の中心点
	protected PointF  _pt[];							//図形の頂点
	protected Paint   _paint = new Paint();				//ペイント
	protected eType   _type = eType.OUT;				//タイプ(上にある障害物のタイプ)
	protected float   _rotaSpeed = 0;					//回転スピード

	//コンストラクタ, type=タイプ, n=頂点の数 , conf=設定情報
	//コンストラクタで、何角形であるかという数値が渡される
	public Barricade(int n, BConf conf)
	{
		if( conf != null )
		{
			_rotaSpeed 	= conf.speed;	//回転スピード
			_type 		= conf.type;	//物体のタイプ
		}
		switch(_type)
		{
			case OUT:	//接触してダメ(アウト)なもの
				_paint.setColor(Color.GREEN);//緑に
				break;
			case GOAL:	//�接触してゴールなもの
				_paint.setColor(Color.YELLOW);//黄色に
				break;
		}
		_pt = new PointF[n];	//頂点配列を作る
		for( int i=0; i<n; i++ )
		{
			_pt[i] = new PointF();	//頂点を作る
		}
		_paint.setAntiAlias(true);
	}

	//更新する
	public boolean onUpdate()
	{
		//
		if( _rotaSpeed != 0 )
		{
			//頂点リスト(_pt)を_centerを中心に回転する
			DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed );
		}
		return true;
	}

	//接触しているか、円cirが接触していれば接触した線分をvecに格納し、
	//物体のタイプを返す、接触していなければNOを返す
	public Def.eHitCode isHit( final Circle cir, Vec vec )
	{
		if( DiagramCalcr.isHit( _pt, cir, vec ) == true )
		{
			switch(_type)
			{
				case OUT:
					return Def.eHitCode.OUT;//ダメ
				case GOAL:
					return Def.eHitCode.GOAL;//ゴール
			}
		}
		return Def.eHitCode.NO;//NOを返す
	}

	//描画する
	public void onDraw(Canvas c)
	{
		//頂点が1未満の図形なんてないので
		if( _pt.length < 1 )
		{
			return;//返す
		}
		Path path = new Path();//パス
		path.moveTo(_pt[0].x, _pt[0].y);	//パスの初期位置をセット
		for( int i=0; i<_pt.length; i++ )
		{
			path.lineTo(_pt[i].x, _pt[i].y);	//頂点の位置へラインを引いていく(軌跡を描いていく)
		}
		c.drawPath(path, _paint);	//引いたラインを描画する

	}
}
最終的に書き込むGameMgr.java

コード:

package net.dixq.irairabar;

import java.util.ArrayList;
import java.util.LinkedList;

import net.dixq.irairabar.Barricade.eType;

import android.annotation.SuppressLint;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;

public class GameMgr
{

private enum eStatus
{
NORMAL,//普通
GAMEOVER,//ゲームオーヴァー
GAMECLEAR//ゲームクリア
};

private static final float PI = (float) Math.PI;
private ArrayList<Barricade> _barrList = new ArrayList<Barricade>();//障害物リスト
private LinkedList<Task> _taskList = new LinkedList<Task>();//タスクのリスト
private eStatus _status = eStatus.NORMAL;//状態
private Player _player;

GameMgr()
{
//↓動かない棒

//画面4隅に四角形を配置
_barrList.add(new BarricadeSquare( 0, 0,540, 20, null));
_barrList.add(new BarricadeSquare( 0, 0, 20,960, null));//コンフィグを特に設定しない時はnullを渡すとデフォルト設定になる
_barrList.add(new BarricadeSquare(520, 0, 20,960, null));
_barrList.add(new BarricadeSquare( 0,940,540, 20, null));

//途中の縦壁
_barrList.add(new BarricadeSquare(170, 300, 10, 640, null));//壁1
_barrList.add(new BarricadeSquare(360, 0, 10, 870, null));//壁2

//横壁(1つ目の通路)
_barrList.add(new BarricadeSquare(0, 820, 100, 20, null));//壁1
_barrList.add(new BarricadeSquare(80, 700, 90, 20, null));//壁2
_barrList.add(new BarricadeSquare(0, 370, 50, 200, null));//壁3
_barrList.add(new BarricadeSquare(100, 350, 70, 250, null));//壁4

//2つ目の通路
//	_barrList.add(new BarricadeSquare(180, 850, 120, 90, null));//壁5

//3つ目の通路
//横壁
_barrList.add(new BarricadeSquare(370, 520, 105, 5, null));//壁6
_barrList.add(new BarricadeSquare(410, 290, 110, 5, null));//壁7

_barrList.add(new BarricadeSquare(370, 250, 90, 5, null));//壁7
_barrList.add(new BarricadeSquare(490, 250, 30, 5, null));//壁7

_barrList.add(new BarricadeSquare(370, 210, 30, 5, null));//壁7
_barrList.add(new BarricadeSquare(430, 210, 120, 5, null));//壁7

_barrList.add(new BarricadeSquare(370, 170, 60, 5, null));//壁7
_barrList.add(new BarricadeSquare(460, 170, 80, 5, null));//壁7


//縦壁
_barrList.add(new BarricadeSquare(470, 350, 5, 170, null));//壁6
_barrList.add(new BarricadeSquare(430, 290, 5, 200, null));//壁6


//回転バー
_barrList.add(new BarricadeSquare( 285, 10, 150, 15, new BConf(-PI / 180)));// 回転バー1
_barrList.add(new BarricadeSquare( 430, 770, 250, 15, new BConf(PI / 150)));// 回転バー2
_barrList.add(new BarricadeSquare( 370, 650, 240, 15, new BConf(-PI / 130)));// 回転バー3

//回転三角形
_barrList.add(new BarricadeTriangle( 170, 150, 150, new BConf(+PI / 270)));// 三角形

//回転星
_barrList.add(new BarricadeStar(270, 480, 30, 100, new BConf(+PI / 270)));//星1
_barrList.add(new BarricadeStar(270, 660, 10, 100, new BConf(-PI / 360)));//星2

_barrList.add(new BarricadeStar(240, 850, 40, 70, new BConf(+PI / 30)));//星3
_barrList.add(new BarricadeStar(240, 850, 20, 70, new BConf(-PI / 30)));//星4

_barrList.add(new BarricadeStar(470, 100, 20, 30, new BConf(+PI / 17)));//星3

/*
//_barrList.add(new BarricadeTriangle( 100, 100, 100, new BConf(+PI / 150)));// 三角形
_barrList.add(new BarricadeTriangle( 300, 600, 180, new BConf(+PI / 150)));// 三角形2

_barrList.add(new BarricadeStar(200, 190, 50, 150, new BConf(+PI / 360)));//星1
_barrList.add(new BarricadeStar(200, 190, 15, 100, new BConf(+PI / 180)));//星2(細くて遅い)

//	_barrList.add(new BarricadeSquare(0, 480, 240, 20, new BConf(+PI / 360)));//

_barrList.add(new BarricadeSquare( 100, 500, 170, 20, new BConf(-PI / 360)));// 回転バー
_barrList.add(new BarricadeSquare( 400, 100, 20, 100, new BConf(+PI / 360)));// 回転バー2
//_barrList.add(new BarricadeSquare(185, 600, 55, 20, new BConf(+PI / 360)));//

_barrList.add(new BarricadeSquare(450, 650, 30, 20, null));//壁3
*/
_barrList.add(new BarricadeSquare(480, 20, 40, 40, new BConf(eType.GOAL)));//ごーる!!

for (Barricade bar : _barrList)
{
//タスクリストに障害物を追加
_taskList.add(bar);
}

_player = new Player();
_taskList.add(_player);//プレイヤー
_taskList.add(new FpsController());//fpsのやつ
}
//総突判定
private boolean Collision()
{
Vec vec = new Vec();
final Circle cir = _player.getPt();//プレイヤーの中心円を取得

//障害物の数だけループ
for(Barricade barr : _barrList)
{
//接触判定
Def.eHitCode code = barr.isHit(cir, vec);
switch(code)
{
case OUT://アウトなら・・・
_status = eStatus.GAMEOVER;
return true;
case GOAL:
_status = eStatus.GAMECLEAR;
return true;
}
}
return false;
}

public boolean onUpdate()
{
//ゲームの状態が通常でないなら計算しない
if( _status != eStatus.NORMAL )
{
return true;
}

//衝突判定 衝突したならメソッドを抜ける
if( Collision() )
{
return true;
}
for (int i = 0; i < _taskList.size(); i++)
{
//更新失敗なら・・・
if (_taskList.get(i).onUpdate() == false)
{
//そのタスクを消す
_taskList.remove(i);
i--;
}
}
return true;
}

//状態を表示する
private void drawStatus(Canvas c)
{
switch( _status )
{
case GAMEOVER:
{
Paint paint = new Paint();
paint.setTextSize(80);
paint.setColor(Color.BLACK);
c.drawText("ざんね~ん!!", 70, 300, paint);
}
break;
case GAMECLEAR:
{
Paint paint = new Paint();
paint.setTextSize(80);
paint.setColor(Color.BLACK);
c.drawText("おめでとう!!", 70, 300, paint);
}
break;
}
}

@SuppressLint("WrongCall")
public void onDraw(Canvas c)
{
//白く塗りつぶす
c.drawColor(Color.WHITE);
for (Task task : _taskList)
{
//描画
task.onDraw(c);
}
drawStatus(c);
}

}

そして今回画像の下に配置される当たってはダメな領域(四角形)

コード:

package net.dixq.irairabar;

//障害物(四角形)
public class BarricadeSquare extends Barricade
{

	public BarricadeSquare( float x, float y, float w, float h, BConf conf )
	{
		super(4,conf);
		//4つの頂点座標(x , y)
		_pt[0].x  = x;		_pt[0].y = y;
		_pt[1].x  = x+w;	_pt[1].y = y;
		_pt[2].x  = x+w;	_pt[2].y = y+h;
		_pt[3].x  = x;		_pt[3].y = y+h;
		//中心座標(x , y)
		_center.x = x+w/2;
		_center.y = y+h/2;
	}

}
そして今回私が新たに作成したファイル

コード:

package net.dixq.irairabar;

//画像
public class BarricadeImage extends Barricade
{
	public BarricadeImage(float x, float y, float w,float h,BConf conf )
	{
		super(4 , conf);
		//4つの頂点座標(x , y)
				_pt[0].x  = x;		_pt[0].y = y;
				_pt[1].x  = x+w;	_pt[1].y = y;
				_pt[2].x  = x+w;	_pt[2].y = y+h;
				_pt[3].x  = x;		_pt[3].y = y+h;
				//中心座標(x , y)
				_center.x = x+w/2;
				_center.y = y+h/2;
	}

}
まったくと言っていいほど四角形と同じですが・・・

引数の最後のconfは四角形でもそうですが回転するか否かのものです。
私は最終的にはGameMgr.javaに四角形みたいな形
(_barrList.add(new BarricadeSquare(370, 520, 105, 5, null));//壁6)
で書き込むような環境にしたいと思っています。
そして最後にBarricade.javaの93行目のしたにBitmapの描画命令を書けばいいと思っています。

しかし、私の作ったファイルですと画像の座標、(幅、高さ←要るのかいらないのかわからない)は大丈夫ですが、画像の読み込み(登録)と当然1枚ではないのでが配列を用意しなければなりません・・・ここまではわかっているつもりなのですが、これらのことを何処にどのように書けばいいのかわかりません・・・
(ここでは画像の回転、範囲の回転は考えません)

私の考え方、この質問を見て気づいたことなどご教授ください。
また、どのように考えればよいか、教えてください。

よろしくお願いします。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#2

投稿記事 by ISLe » 12年前

BarricadeクラスにImageを設定できるようにして、onDrawメソッドでCanvas#drawPathの代わりにイメージを描画すれば良いと思います。
そうすれば適切な画像を設定するだけですべての図形に同時に対応できるかと。

Imageが設定されていなければ従来通りとすれば動作確認もしやすいのではないでしょうか。

画像の読み込みはGameMgrのコンストラクタで、Barricadeの派生クラスを構築する前。
コンストラクタでBarricadeの派生クラスにImageへの参照を渡せば、Imageの配列は必要ありません。

mi_l

Re: androidアプリで困っています。ご教授ください

#3

投稿記事 by mi_l » 12年前

ISLe さんが書きました:BarricadeクラスにImageを設定できるようにして、onDrawメソッドでCanvas#drawPathの代わりにイメージを描画すれば良いと思います。
そうすれば適切な画像を設定するだけですべての図形に同時に対応できるかと。

Imageが設定されていなければ従来通りとすれば動作確認もしやすいのではないでしょうか。

画像の読み込みはGameMgrのコンストラクタで、Barricadeの派生クラスを構築する前。
コンストラクタでBarricadeの派生クラスにImageへの参照を渡せば、Imageの配列は必要ありません。
返信遅れました、

自分なりにまず「BarricadeクラスにImageを設定できるようにして、onDrawメソッドでCanvas#drawPathの代わりにイメージを描画すれば良いと思います。」

というところだけ試してみましたがうまくいきません。

ソースを載せますのでご指摘お願いします。

コード:

package net.dixq.irairabar;

import android.content.Context;//追加
import android.content.res.Resources;//追加
import android.view.View;//追加
import android.graphics.Bitmap;//追加
import android.graphics.BitmapFactory;//追加
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PointF;

public class Barricade extends Task
{
	//障害物のタイプ
	public enum eType
	{
		OUT,//あたるとアウトになる
		GOAL//あたるとゴールになる
	}

	protected PointF  _center = new PointF(0,0);		//図形の中心点
	protected PointF  _pt[];							//図形の頂点
	protected Paint   _paint = new Paint();				//ペイント
	protected eType   _type = eType.OUT;				//タイプ(上にある障害物のタイプ)
	protected float   _rotaSpeed = 0;					//回転スピード

	//コンストラクタ, type=タイプ, n=頂点の数 , conf=設定情報
	//コンストラクタで、何角形であるかという数値が渡される
	public Barricade(int n, BConf conf)
	{
		if( conf != null )
		{
			_rotaSpeed 	= conf.speed;	//回転スピード
			_type 		= conf.type;	//物体のタイプ
		}
		switch(_type)
		{
			case OUT:	//接触してダメ(アウト)なもの
				_paint.setColor(Color.GREEN);//緑に
				break;
			case GOAL:	//�接触してゴールなもの
				_paint.setColor(Color.YELLOW);//黄色に
				break;
		}
		_pt = new PointF[n];	//頂点配列を作る
		for( int i=0; i<n; i++ )
		{
			_pt[i] = new PointF();	//頂点を作る
		}
		_paint.setAntiAlias(true);
	}

	//更新する
	public boolean onUpdate()
	{
		//
		if( _rotaSpeed != 0 )
		{
			//頂点リスト(_pt)を_centerを中心に回転する
			DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed );
		}
		return true;
	}

	//接触しているか、円cirが接触していれば接触した線分をvecに格納し、
	//物体のタイプを返す、接触していなければNOを返す
	public Def.eHitCode isHit( final Circle cir, Vec vec )
	{
		if( DiagramCalcr.isHit( _pt, cir, vec ) == true )
		{
			switch(_type)
			{
				case OUT:
					return Def.eHitCode.OUT;//ダメ
				case GOAL:
					return Def.eHitCode.GOAL;//ゴール
			}
		}
		return Def.eHitCode.NO;//NOを返す
	}

	//追記ーーーーーーーーーーーーーーーーーーーーーーーーーーーー
	 // Viewクラスを継承して、自分で作成したGraphicsView
    private class GraphicsView extends View 
    {
        // ↓これはeclipseが自動的に「記載をしろ!」と警告を出してくる。
        // 警告にそって記載する。
        public GraphicsView(Context context)
        {
            super(context);
            // TODO 自動生成されたコンストラクター・スタブ
        }
	//--------------------------------------------------------------

		//描画する
		public void onDraw(Canvas c)
		{
	
			//画像の取得(追加)
			Resources res = this.getContext().getResources();
	
			Bitmap img01 = BitmapFactory.decodeResource(res, R.drawable.aaa);//追加
	
			//頂点が1未満の図形なんてないので
			if( _pt.length < 1 )
			{
				return;//返す
			}
			Path path = new Path();//パス
			path.moveTo(_pt[0].x, _pt[0].y);	//パスの初期位置をセット
			for( int i=0; i<_pt.length; i++ )
			{
				path.lineTo(_pt[i].x, _pt[i].y);	//頂点の位置へラインを引いていく(軌跡を描いていく)
			}
			//c.drawPath(path, _paint);	//引いたラインを描画する
			c.drawBitmap(img01, 0,0,paint());//追加
	
		}
    }
}
「追加」なり「追記」と書かれているところが自分なりにやったところです。

ご指摘お願いします

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#4

投稿記事 by ISLe » 12年前

画像を読み込むのはBarricadeの仕事ではありません。
BarricadeはBarricadeのままで、見た目だけを変えるのですよ。
  1. BarricadeにImageの参照を保持するインスタンス変数を追加してください。
  2. BarricadeのコンストラクタにImageへの参照を受け取る引数を追加して、1.の変数に記録してください。
  3. BarricadeのonDrawメソッドに1.の変数に記録してあるImageへの参照を使ってイメージを描画する処理を追加してください。
    Imageへの参照がnullであれば従来どおりの処理となるようにしておくとデバッグに便利です。
  4. Barricadeの派生クラスにもコンストラクタにImageへの参照を受け取る引数を追加して、Barricadeのコンストラクタに渡すようにしてください。
  5. GameMgrのコンストラクタで画像を読み込んでBarricadeの派生クラスのコンストラクタにImageへの参照を渡すようにしてください。
    コンテキストはGameMgrのコンストラクタの引数で渡すようにするのが良いと思います。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#5

投稿記事 by ISLe » 12年前

コンストラクタにImageの引数を追加する際、以下のようにすると既存のコードを一括で置き換えずに済みます。

コード:

public class Barricade extends Task
{
    public Barricade(int n, BConf conf) {
        this(n, conf, null);
        // 既存の構築はImageをnullとする。
    }
    public Barricade(int n, BConf conf, Image image) {
        // コンストラクタ引数にImageを追加
    }
}

mi_l

Re: androidアプリで困っています。ご教授ください

#6

投稿記事 by mi_l » 12年前

ISLe さんが書きました:画像を読み込むのはBarricadeの仕事ではありません。
BarricadeはBarricadeのままで、見た目だけを変えるのですよ。
  1. BarricadeにImageの参照を保持するインスタンス変数を追加してください。
  2. BarricadeのコンストラクタにImageへの参照を受け取る引数を追加して、1.の変数に記録してください。
  3. BarricadeのonDrawメソッドに1.の変数に記録してあるImageへの参照を使ってイメージを描画する処理を追加してください。
    Imageへの参照がnullであれば従来どおりの処理となるようにしておくとデバッグに便利です。
  4. Barricadeの派生クラスにもコンストラクタにImageへの参照を受け取る引数を追加して、Barricadeのコンストラクタに渡すようにしてください。
  5. GameMgrのコンストラクタで画像を読み込んでBarricadeの派生クラスのコンストラクタにImageへの参照を渡すようにしてください。
    コンテキストはGameMgrのコンストラクタの引数で渡すようにするのが良いと思います。

とりあえず、1、2だけやってみましたがわからないところもたくさんあります。

変更、付け足しは23行目、28行目、49~52行目です。
何が足りないのか、どこがおかしいのかご指摘お願いします。



Barricade.java

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PointF;


public class Barricade extends Task {
	public enum eType{
		OUT,
		GOAL
	}

	protected PointF  _center = new PointF(0,0);		//図形の中心点
	protected PointF  _pt[];							//図形の頂点
	protected Paint   _paint = new Paint();				//ペイント
	protected eType   _type = eType.OUT;				//タイプ(当たるとアウトな壁、ゴールの壁、等)
	protected float   _rotaSpeed = 0;					//回転スピード
	protected Bitmap bit;
	
	protected int images;//参照を保持するインスタンス変数(何型の変数?)*

	//コンストラクタ。 type=タイプ、 n=頂点の数、 conf=設定情報
	public Barricade(int n, BConf conf)
	{
		this(n , conf , null);//ここでエラーが出てます
		
		
		if( conf != null ){
			_rotaSpeed 	= conf.speed;	//回転スピード
			_type 		= conf.type;	//物体のタイプ
		}
		switch(_type){
		case OUT:	//接触してアウトな物
			_paint.setColor(Color.RED);
			break;
		case GOAL:	//接触してゴールな物
			_paint.setColor(Color.GREEN);
			break;
		}
		_pt = new PointF[n];	//頂点配列を作る
		for( int i=0; i<n; i++ ){
			_pt[i] = new PointF();	//頂点を作る
		}
		_paint.setAntiAlias(true);
	}
	public Barricade(int n , BConf conf , Image image)//「Image」でエラーが出てますImage型というのはあるのでしょうか?*
	{
		images = image;//格納(記録)*
	}

	//更新する
	public boolean onUpdate(){
		if( _rotaSpeed != 0 ){	//回転するなら
			DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed );	//頂点リスト(_pt)を_centerを中心に回転する
		}
		return true;
	}

	//接触しているかを問う。円cirが線分vecと接触していれば接触した物体のタイプを返す。接触していなければNOを返す
	public Def.eHitCode isHit( final Circle cir, Vec vec ){
		if( DiagramCalcr.isHit( _pt, cir, vec ) == true ){
			switch(_type){
			case OUT:
				return Def.eHitCode.OUT;
			case GOAL:
				return Def.eHitCode.GOAL;
			}
		}
		return Def.eHitCode.NO;
	}

	//描画する
	public void onDraw(Canvas c){

		c.drawBitmap(bit, _pt[0], _pt[0]);
	}
}

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#7

投稿記事 by ISLe » 12年前

ああごめんなさい。
AndroidはBitmapでしたね。
ImageはBitmapと読み替えてください。

21行目のメンバが描画に使うBitmapへの参照ということで良いと思います。

引数にBitmapを追加するのは、既存のコンストラクタのほうです。
そして既存と同じ引数並びのコンストラクタを追加して既存の呼び出しコードに対応します。

描画コードも既存のものはすべて残しておいてください。
画像をセットしないものが描画されなくなってしまいます。

とりあえず3.の描画コードの追加は後回しにして、4.5.を先にしてください。
描画コードを書いたらすぐに画面に出るほうが良いと思うので。

mi_l

Re: androidアプリで困っています。ご教授ください

#8

投稿記事 by mi_l » 12年前

返信で指摘されたことをまた自分なりにやってみました。

1,2に関係あるBarricade.java↓

変更箇所
(27行目の既存コンストラクタに画像の引数(img)を追加)
(30行目で変数bitに引数imgを格納(記録))
(51~54行目は
ISLe さんが書きました:コンストラクタにImageの引数を追加する際、以下のようにすると既存のコードを一括で置き換えずに済みます。
ので指摘されたようにコンストラクタを作り、既存と引数並びが同じコンストラクタ(ここではthis?)を用意しました)←ここがいまいち理解できません・・・

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;//追加
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;//追加
import android.graphics.PointF;


public class Barricade extends Task {
	public enum eType{
		OUT,
		GOAL
	}

	protected PointF  _center = new PointF(0,0);		//図形の中心点
	protected PointF  _pt[];							//図形の頂点
	protected Paint   _paint = new Paint();				//ペイント
	protected eType   _type = eType.OUT;				//タイプ(当たるとアウトな壁、ゴールの壁、等)
	protected float   _rotaSpeed = 0;					//回転スピード
	protected Bitmap bit;

	//protected int images;//参照を保持するインスタンス変数(何型の変数?)

	//コンストラクタ。 type=タイプ、 n=頂点の数、 conf=設定情報
	public Barricade(int n, BConf conf,Bitmap img)
	{

		bit = img;//格納(記録);


		if( conf != null ){
			_rotaSpeed 	= conf.speed;	//回転スピード
			_type 		= conf.type;	//物体のタイプ
		}
		switch(_type){
		case OUT:	//接触してアウトな物
			_paint.setColor(Color.RED);
			break;
		case GOAL:	//接触してゴールな物
			_paint.setColor(Color.GREEN);
			break;
		}
		_pt = new PointF[n];	//頂点配列を作る
		for( int i=0; i<n; i++ ){
			_pt[i] = new PointF();	//頂点を作る
		}
		_paint.setAntiAlias(true);
	}
	public Barricade(int n , BConf conf)
	{
		this(n , conf , null);
	}

	//更新する
	public boolean onUpdate(){
		if( _rotaSpeed != 0 ){	//回転するなら
			DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed );	//頂点リスト(_pt)を_centerを中心に回転する
		}
		return true;
	}

	//接触しているかを問う。円cirが線分vecと接触していれば接触した物体のタイプを返す。接触していなければNOを返す
	public Def.eHitCode isHit( final Circle cir, Vec vec ){
		if( DiagramCalcr.isHit( _pt, cir, vec ) == true ){
			switch(_type){
			case OUT:
				return Def.eHitCode.OUT;
			case GOAL:
				return Def.eHitCode.GOAL;
			}
		}
		return Def.eHitCode.NO;
	}

	//描画する
    public void onDraw(Canvas c)
    {
        //頂点が1未満の図形なんてないので
        if( _pt.length < 1 )
        {
            return;//返す
        }
        Path path = new Path();//パス
        path.moveTo(_pt[0].x, _pt[0].y);    //パスの初期位置をセット
        for( int i=0; i<_pt.length; i++ )
        {
            path.lineTo(_pt[i].x, _pt[i].y);    //頂点の位置へラインを引いていく(軌跡を描いていく)
        }
        c.drawPath(path, _paint);   //引いたラインを描画する

    }
}
次に4に関するBarricade.javaの派生クラスである星、四角、三角とあるのですが、代表として多く使うであろう四角のクラスを載せます

変更箇所
(8行目に画像の引数imgを追加)
(superで四つ角の座標、conf(回転の有無)、ここにimgも追加してBarricade.javaのコンストラクタに渡すようにした)

(superの4とは、四角の四つ角の座標(座標のx、y座標はコンストラクタ内で定義しているのもわかります)、confは別で定義した回転の有無、そしてimgは画像の表示の有無、そこで、17行目の文なのですが、要るのかいらないのかわかりません・・エラーは出ないのですが入れることでなにが起こるのか、入れないことで何が起こるのか知りたいです・・)

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;


public class BarricadeSquare extends Barricade {

	public BarricadeSquare( float x, float y, float w, float h, BConf conf, Bitmap img ){
		super(4,conf, img);
		_pt[0].x  = x;		_pt[0].y = y;
		_pt[1].x  = x+w;	_pt[1].y = y;
		_pt[2].x  = x+w;	_pt[2].y = y+h;
		_pt[3].x  = x;		_pt[3].y = y+h;
		_center.x = x+w/2;
		_center.y = y+h/2;
		
		bit = img;//これはエラーはでない(不要?)
	}

}
そして5に関するGameMgr.java

変更箇所
(12~15行目に追記)
(31行目に追記)
(33行目に引数を追加、35,36行目はとあるサイトでみたやり方でやりました(色々なサイトでやり方が違っていたので困惑していますが)、そしてgrtContextのところでエラーが出ます、エラー内容は「getContext は解決できないか、フィールドではありません」です。)

コード:

package net.dixq.irairabar;

import java.util.ArrayList;
import java.util.LinkedList;

import net.dixq.irairabar.Barricade.eType;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.content.res.Resources;
import android.content.Context;


public class GameMgr {

	private enum eStatus{
		NORMAL,
		GAMEOVER,
		GAMECLEAR
	};

	private static final float PI = (float) Math.PI;
	private ArrayList<Barricade> _barrList = new ArrayList<Barricade>();//障害物リスト
	private LinkedList<Task> _taskList = new LinkedList<Task>();// タスクリスト
	private eStatus _status = eStatus.NORMAL;
	private Player _player;
	private Bitmap bits[];//追加

	GameMgr(Context con) {

		Resources res = this.getContext.getResources();
		bits[0] = BitmapFactory.decodeResource(res, R.drawable.ic_launcher);



/*
		_barrList.add(new BarricadeSquare(  0,  0,480, 20, null));// 画面4隅に四角形を配置
		_barrList.add(new BarricadeSquare(  0,  0, 20,800, null));
		_barrList.add(new BarricadeSquare(460,  0, 20,800, null));
		_barrList.add(new BarricadeSquare(  0,780,480, 20, null));

		_barrList.add(new BarricadeTriangle(  0, 0, 200, new BConf(+PI / 150)));// 左上回転する三角形
		_barrList.add(new BarricadeTriangle(480, 0, 180, new BConf(+PI / 150)));// 右上回転する三角形

		_barrList.add(new BarricadeStar(240, 240, 50, 200, new BConf(-PI / 360)));// 中央に回転する星
		_barrList.add(new BarricadeStar(240, 240, 20,  80, new BConf(+PI / 360)));// 中央に回転する星

		_barrList.add(new BarricadeSquare(300, 440, 200, 20, null));//右下の固定通路
		_barrList.add(new BarricadeSquare(250, 520, 130, 20, null));//
		_barrList.add(new BarricadeSquare(330, 620, 130, 20, null));//

		_barrList.add(new BarricadeSquare(230, 390, 20, 350, null));//中央区切り線

		_barrList.add(new BarricadeSquare(0, 480, 240, 20, new BConf(+PI / 360)));// 左下回転するバー

		_barrList.add(new BarricadeSquare( 20, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(130, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(185, 600,  55, 20, new BConf(+PI / 360)));// 左下回転するバー

*/
	//	_barrList.add(new BarricadeSquare(20, 680,  80, 20, null));// ゴールに接触したバー

	//	_barrList.add(new BarricadeSquare(20, 700,  80, 80, new BConf(eType.GOAL)));// ゴール

		for (Barricade bar : _barrList) {
			_taskList.add(bar);	//タスクリストに障害物を追加
		}

		_player = new Player();
		_taskList.add(_player);
		_taskList.add(new FpsController());
	}

	private boolean Collision(){
		Vec vec = new Vec();
		final Circle cir = _player.getPt();
		for(Barricade barr : _barrList){
			Def.eHitCode code = barr.isHit(cir, vec);
			switch(code){
			case OUT:
				_status = eStatus.GAMEOVER;
				return true;
			case GOAL:
				_status = eStatus.GAMECLEAR;
				return true;
			}
		}
		return false;
	}

	public boolean onUpdate() {
		if( _status != eStatus.NORMAL ){
			return true;
		}
		if( Collision() ){
			return true;
		}
		for (int i = 0; i < _taskList.size(); i++) {
			if (_taskList.get(i).onUpdate() == false) { // 更新失敗なら
				_taskList.remove(i); // そのタスクを消す
				i--;
			}
		}
		return true;
	}

	private void drawStatus(Canvas c){
		switch( _status ){
		case GAMEOVER:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameOver", 40, 100, paint);
			}
			break;
		case GAMECLEAR:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameClear", 40, 100, paint);
			}
			break;
		}
	}

	public void onDraw(Canvas c) {
		c.drawColor(Color.WHITE); // 白で塗りつぶす
		for (Task task : _taskList) {
			task.onDraw(c);// 描画
		}

		drawStatus(c);
	}

}
長文になりましたが返信に対する自分なりの考え(コード)を載せました。
ご指摘お願します。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#9

投稿記事 by ISLe » 12年前

mi_l さんが書きました:ので指摘されたようにコンストラクタを作り、既存と引数並びが同じコンストラクタ(ここではthis?)を用意しました)←ここがいまいち理解できません・・・
既存の呼び出し側のコードは引数を追加する前のBarricadeのコンストラクタを呼び出しています。
引数を追加すると呼び出し側のコードは引数が足らなくなるためコンパイルエラーになってしまいます。
それらのコードがエラーにならないように、Bitmapをnullで引数を追加したコンストラクタを呼び出すように差し替えます。
既存のコードを書き換えずに済ますためのテクニックです。
本来はコンストラクタで引数を省略できるように見せるものですが。
mi_l さんが書きました:(superの4とは、四角の四つ角の座標(座標のx、y座標はコンストラクタ内で定義しているのもわかります)、confは別で定義した回転の有無、そしてimgは画像の表示の有無、そこで、17行目の文なのですが、要るのかいらないのかわかりません・・エラーは出ないのですが入れることでなにが起こるのか、入れないことで何が起こるのか知りたいです・・)
Barricadeのインスタンス変数bitはprotectedなので、継承したクラスから直接アクセスできます。
効果としてはBarricadeのコンストラクタに追加したものと同じです。
同じなので派生先のクラスで特に必要はありません。
mi_l さんが書きました:(33行目に引数を追加、35,36行目はとあるサイトでみたやり方でやりました(色々なサイトでやり方が違っていたので困惑していますが)、そしてgrtContextのところでエラーが出ます、エラー内容は「getContext は解決できないか、フィールドではありません」です。)
getResourcesメソッドはコンストラクタの引数で受け取ったContextのものを使ってください。
GameMgrのインスタンスを作成しているところがエラーになったと思いますがどうしました?
Activity内でthisを渡したのではないでしょうか。
それだとリークの可能性があるので、getApplicationContext()の戻り値を与えるようにしてください。

読み込んだビットマップはそのままBarricadeに渡すので、ローカル変数でかまいません。
配列にしたりメンバ変数を用意する必要はありません。


概ね問題ありません。
Context周りは注意してください。

コンパイルできたらいったん動かしてみてください。
変更する前とまったく変わらなければうまくいってます。

mi_l

Re: androidアプリで困っています。ご教授ください

#10

投稿記事 by mi_l » 12年前

返信ありがとうございます。

とりあえず、理解できた(多分・・・)ところから直していきます
ISLe さんが書きました: getResourcesメソッドはコンストラクタの引数で受け取ったContextのものを使ってください。

読み込んだビットマップはそのままBarricadeに渡すので、ローカル変数でかまいません。
配列にしたりメンバ変数を用意する必要はありません。
というところは直しました。

(31、35、36行目を変更)
GameMgr.java

コード:

package net.dixq.irairabar;

import java.util.ArrayList;
import java.util.LinkedList;

import net.dixq.irairabar.Barricade.eType;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.content.res.Resources;
import android.content.Context;


public class GameMgr {

	private enum eStatus{
		NORMAL,
		GAMEOVER,
		GAMECLEAR
	};

	private static final float PI = (float) Math.PI;
	private ArrayList<Barricade> _barrList = new ArrayList<Barricade>();//障害物リスト
	private LinkedList<Task> _taskList = new LinkedList<Task>();// タスクリスト
	private eStatus _status = eStatus.NORMAL;
	private Player _player;
	Bitmap bits;//追加

	GameMgr(Context con) {

		Resources res = con.getResources();
		bits = BitmapFactory.decodeResource(res, R.drawable.ic_launcher);



/*
		_barrList.add(new BarricadeSquare(  0,  0,480, 20, null));// 画面4隅に四角形を配置
		_barrList.add(new BarricadeSquare(  0,  0, 20,800, null));
		_barrList.add(new BarricadeSquare(460,  0, 20,800, null));
		_barrList.add(new BarricadeSquare(  0,780,480, 20, null));

		_barrList.add(new BarricadeTriangle(  0, 0, 200, new BConf(+PI / 150)));// 左上回転する三角形
		_barrList.add(new BarricadeTriangle(480, 0, 180, new BConf(+PI / 150)));// 右上回転する三角形

		_barrList.add(new BarricadeStar(240, 240, 50, 200, new BConf(-PI / 360)));// 中央に回転する星
		_barrList.add(new BarricadeStar(240, 240, 20,  80, new BConf(+PI / 360)));// 中央に回転する星

		_barrList.add(new BarricadeSquare(300, 440, 200, 20, null));//右下の固定通路
		_barrList.add(new BarricadeSquare(250, 520, 130, 20, null));//
		_barrList.add(new BarricadeSquare(330, 620, 130, 20, null));//

		_barrList.add(new BarricadeSquare(230, 390, 20, 350, null));//中央区切り線

		_barrList.add(new BarricadeSquare(0, 480, 240, 20, new BConf(+PI / 360)));// 左下回転するバー

		_barrList.add(new BarricadeSquare( 20, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(130, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(185, 600,  55, 20, new BConf(+PI / 360)));// 左下回転するバー

*/
	//	_barrList.add(new BarricadeSquare(20, 680,  80, 20, null));// ゴールに接触したバー

	//	_barrList.add(new BarricadeSquare(20, 700,  80, 80, new BConf(eType.GOAL)));// ゴール

		for (Barricade bar : _barrList) {
			_taskList.add(bar);	//タスクリストに障害物を追加
		}

		_player = new Player();
		_taskList.add(_player);
		_taskList.add(new FpsController());
	}

	private boolean Collision(){
		Vec vec = new Vec();
		final Circle cir = _player.getPt();
		for(Barricade barr : _barrList){
			Def.eHitCode code = barr.isHit(cir, vec);
			switch(code){
			case OUT:
				_status = eStatus.GAMEOVER;
				return true;
			case GOAL:
				_status = eStatus.GAMECLEAR;
				return true;
			}
		}
		return false;
	}

	public boolean onUpdate() {
		if( _status != eStatus.NORMAL ){
			return true;
		}
		if( Collision() ){
			return true;
		}
		for (int i = 0; i < _taskList.size(); i++) {
			if (_taskList.get(i).onUpdate() == false) { // 更新失敗なら
				_taskList.remove(i); // そのタスクを消す
				i--;
			}
		}
		return true;
	}

	private void drawStatus(Canvas c){
		switch( _status ){
		case GAMEOVER:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameOver", 40, 100, paint);
			}
			break;
		case GAMECLEAR:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameClear", 40, 100, paint);
			}
			break;
		}
	}

	public void onDraw(Canvas c) {
		c.drawColor(Color.WHITE); // 白で塗りつぶす
		for (Task task : _taskList) {
			task.onDraw(c);// 描画
		}

		drawStatus(c);
	}

}
教える方からすれば多少面倒になるかもしれませんが一つずつ理解していきたいので、まず、上記の変更はご指摘した意図と合っているか教えてください。

よろしくおねがいします。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#11

投稿記事 by ISLe » 12年前

ローカル変数で良いので、31行目は不要です。

36行目を
Bitmap bits = ~
と宣言してください。

mi_l

Re: androidアプリで困っています。ご教授ください

#12

投稿記事 by mi_l » 12年前

ご指摘ありがとうございます。

残るのはあと、
ISLe さんが書きました: GameMgrのインスタンスを作成しているところがエラーになったと思いますがどうしました?
Activity内でthisを渡したのではないでしょうか。
それだとリークの可能性があるので、getApplicationContext()の戻り値を与えるようにしてください。

概ね問題ありません。
Context周りは注意してください。

コンパイルできたらいったん動かしてみてください。
変更する前とまったく変わらなければうまくいってます。
と指摘された個所です。
最初の「GameMgrのインスタンスを作成しているところがエラーになったと思いますがどうしました?」
というご指摘ではまさにその通りでGameSurfaceView.javaのGameMgrのインスタンスを作成してるところにエラーがつきました・・・
(9行目)
コンストラクタと合わせるために「null」を入れたら38行目(正確には onDraw(getHolder());のあと)と44行目の「unlock」のところにエラーがつきました

GameSurfaceView.java

コード:

package net.dixq.irairabar;

import android.content.Context;
import android.graphics.Canvas;
import android.view.SurfaceHolder;
import android.view.SurfaceView;

class GameSurfaceView extends SurfaceView implements SurfaceHolder.Callback, Runnable {
	private GameMgr _gameMgr = new GameMgr();
	private Thread _thread;

	public GameSurfaceView(Context context) {
		super(context);
		getHolder().addCallback(this);
	}

	@Override
	public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
		//解像度情報変更通知
	}

	@Override
	public void surfaceCreated(SurfaceHolder holder) {
		_thread = new Thread(this);		//別スレッドでメインループを作る
		_thread.start();
	}

	@Override
	public void surfaceDestroyed(SurfaceHolder holder) {
		_thread = null;
	}

	@Override
	public void run() {
		while (_thread!=null) {	//メインループ
			_gameMgr.onUpdate();
			onDraw(getHolder());
		}
	}

	private void onDraw(SurfaceHolder holder) {
		Canvas c = holder.lockCanvas();
		_gameMgr.onDraw(c);
		holder.unlockCanvasAndPost(c);
	}
}

また、次の指摘(前の指摘の延長)であった「Activity内でthisを渡したのではないでしょうか。
それだとリークの可能性があるので、getApplicationContext()の戻り値を与えるようにしてください。」

という個所で「getApplicationContext()」を詳しく知らないので調べました

http://individualmemo.blog104.fc2.com/b ... ry-41.html

そして、軽くですが理解しました。
(ActivityのContext、(This)はライフサイクルがとても重要視される、よってそのサイクル内で完結できないような場合はリークが起こる
、また、Activityが破棄されるとき、Contextオブジェクトも同様に何度でも破棄されて何度でも作られるという弱み(特徴)もある・・・(ってことですかね・・))

(逆にApplicationのContext、(getApplicationContext())はアプリケーションのライフサイクルに関わらず同じContextオブジェクトとなっていることが強み(特徴)である。)

そこで、IrairaBarActivity.javaでActivityのContext、いわゆる(this)が使われているのは22、24、42行目でありました

これをgetApplicationContext()に変えろという指摘なのでしょうか?

コード:

package net.dixq.irairabar;

import android.app.Activity;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.Window;
import android.view.WindowManager;

public class IrairaBarActivity extends Activity {

	GameSurfaceView _view;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);

		getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
		requestWindowFeature(Window.FEATURE_NO_TITLE);

        getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);//画面のタイムアウト防止

		_view = new GameSurfaceView(this);
		setContentView(_view);
		AcSensor.Inst().onCreate(this); // センサー初期化
	}

	@Override
	protected void onResume() { // アクティビティが動き始める時呼ばれる
		super.onResume();
		AcSensor.Inst().onResume();// 開始時にセンサーを動かし始める
	}

	@Override
	protected void onPause() { // アクティビティの動きが止まる時呼ばれる
		super.onPause();
		AcSensor.Inst().onPause();// 中断時にセンサーを止める
	}

	@Override
	public boolean onKeyDown(int keyCode, KeyEvent event) {
		if (keyCode == KeyEvent.KEYCODE_BACK) {
			_view = new GameSurfaceView(this);
			setContentView(_view); // 処理の実体はGameSurfaceView内のGameMgr
			return false;
		} else {
			return super.onKeyDown(keyCode, event);
		}
	}
}
またリークする理由がいまいち理解できていません・・・
最後でいいので教えてください・・・・


よろしくお願いします。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#13

投稿記事 by ISLe » 12年前

mi_l さんが書きました:最初の「GameMgrのインスタンスを作成しているところがエラーになったと思いますがどうしました?」
というご指摘ではまさにその通りでGameSurfaceView.javaのGameMgrのインスタンスを作成してるところにエラーがつきました・・・
(9行目)
コンストラクタと合わせるために「null」を入れたら38行目(正確には onDraw(getHolder());のあと)と44行目の「unlock」のところにエラーがつきました
9行目で宣言といっしょにインスタンスを作成していますが、これだとコンテキストを渡せませんので、ここでは変数の宣言だけにしてください。
GameMgrのインスタンスの作成と変数への代入をGameSurfaceViewのコンストラクタで行なってください。
GameSurfaceViewのコンストラクタの引数にContextがあるので、これを使ってgetApplicationContextを呼び出してください。

38行目と44行目のエラーはGameMgrの変更で_gameMgr変数の宣言が無効になって影響が出ているのだと思います。
変数の宣言とインスタンスの作成が正しく行われればそちらのエラーは自動的に消えます。
mi_l さんが書きました:そこで、IrairaBarActivity.javaでActivityのContext、いわゆる(this)が使われているのは22、24、42行目でありました
これをgetApplicationContext()に変えろという指摘なのでしょうか?
GameMgrを構築するときのContextについてお話していますので、それらは関係ありません。
#もしかしたらgetApplicationContextに変えるべきかもしれませんが、ここでは関知しません。
イライラ棒のプロジェクト全体を見ておらず、GameMgrはActivity内で構築されていると思っていました。
GameSurfaceViewで構築されていると分かりましたので上に書いたようにしてください。

mi_l さんが書きました:またリークする理由がいまいち理解できていません・・・
最後でいいので教えてください・・・・
ホームボタンを押して待機状態になったりなどいろいろな場面で、Activityは作成し直されることがあります。
ActivityをContextとして渡すと、そのActivityがロックされてしまうので古いActivityがいつまでもメモリに残ってしまいます。
getApplicationContextの戻り値は特定のインスタンスに結び付いていないのでロックされるActivityもないというわけです。
Activityと寿命を共にするオブジェクトにはActivity自身への参照を渡しても問題ありません。

実はGameSurfaceViewが使われている箇所を見ると今回Contextをそのまま渡して問題ないパターンなのですが、GameMgrというクラスの意味合い的にgetApplicationContextの戻り値を渡すべきだと考えます。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#14

投稿記事 by ISLe » 12年前

BarricadeSquareにもBarricadeと同じようにコンストラクタを追加して、Barricadeの派生クラスのインスタンスを作成している箇所を変更せずにエラーが出ないようにしてください。
そこでいったん変更する前とまったく変わらず動くかどうか確認してください。

mi_l

Re: androidアプリで困っています。ご教授ください

#15

投稿記事 by mi_l » 12年前

ご指摘にありました通り、自分なりにやってみました(ですがまだエラーはでましたのでまたご教授お願いします)
ISLe さんが書きました: 9行目で宣言といっしょにインスタンスを作成していますが、これだとコンテキストを渡せませんので、ここでは変数の宣言だけにしてください。
GameMgrのインスタンスの作成と変数への代入をGameSurfaceViewのコンストラクタで行なってください。
GameSurfaceViewのコンストラクタの引数にContextがあるので、これを使ってgetApplicationContextを呼び出してください。

38行目と44行目のエラーはGameMgrの変更で_gameMgr変数の宣言が無効になって影響が出ているのだと思います。
変数の宣言とインスタンスの作成が正しく行われればそちらのエラーは自動的に消えます。
というところなのですが、

変更箇所
(9行目、宣言だけに変更)
(16行目、インスタンス作成)
そして「GameSurfaceViewのコンストラクタの引数にContextがあるので、これを使ってgetApplicationContextを呼び出してください」
との指摘に対する自分の考えも16行目なのですが・・・あっているのでしょうか?
もしあっているのであれば、先ほどもありましたが、39行目の onDraw(getHolder());の後と、46行目のunlockにエラーがついてしまいます、その理由が知りたいです。
(間違っているのであればそれはそれなのですが・・)
()
GameSurfaceView.java

コード:

package net.dixq.irairabar;

import android.content.Context;
import android.graphics.Canvas;
import android.view.SurfaceHolder;
import android.view.SurfaceView;

class GameSurfaceView extends SurfaceView implements SurfaceHolder.Callback, Runnable {
	private GameMgr _gameMgr;
	private Thread _thread;

	public GameSurfaceView(Context context) {
		super(context);
		getHolder().addCallback(this);

		_gameMgr = new GameMgr(context.getApplicationContext());
	}

	@Override
	public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
		//解像度情報変更通知
	}

	@Override
	public void surfaceCreated(SurfaceHolder holder) {
		_thread = new Thread(this);		//別スレッドでメインループを作る
		_thread.start();
	}

	@Override
	public void surfaceDestroyed(SurfaceHolder holder) {
		_thread = null;
	}

	@Override
	public void run() {
		while (_thread!=null) {	//メインループ
			_gameMgr.onUpdate();
			onDraw(getHolder());
		}
	}

	private void onDraw(SurfaceHolder holder) {
		Canvas c = holder.lockCanvas();
		_gameMgr.onDraw(c);
		holder.unlockCanvasAndPost(c);
	}
}

また、
ISLe さんが書きました:BarricadeSquareにもBarricadeと同じようにコンストラクタを追加して、Barricadeの派生クラスのインスタンスを作成している箇所を変更せずにエラーが出ないようにしてください。
そこでいったん変更する前とまったく変わらず動くかどうか確認してください。
に対しては、19~23行目に追加しました

そうすると、GameMgr.javaでは「_barrList.add(new BarricadeSquare( 0, 0,480, 20, null , bits))」とやっても「_barrList.add(new BarricadeSquare( 0, 0,480, 20, null ))」とやってもエラーが出ませんでした。(これは指摘の意図にあっていたということでしょうか?)
BarradeSquare.java

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;


public class BarricadeSquare extends Barricade {

	public BarricadeSquare( float x, float y, float w, float h, BConf conf, Bitmap img ){
		super(4,conf, img);
		_pt[0].x  = x;		_pt[0].y = y;
		_pt[1].x  = x+w;	_pt[1].y = y;
		_pt[2].x  = x+w;	_pt[2].y = y+h;
		_pt[3].x  = x;		_pt[3].y = y+h;
		_center.x = x+w/2;
		_center.y = y+h/2;


	}
	public BarricadeSquare( float x, float y, float w, float h, BConf conf)
	{
		super(4 ,conf , null);

	}

}

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#16

投稿記事 by ISLe » 12年前

mi_l さんが書きました:変更箇所
(9行目、宣言だけに変更)
(16行目、インスタンス作成)
そして「GameSurfaceViewのコンストラクタの引数にContextがあるので、これを使ってgetApplicationContextを呼び出してください」
との指摘に対する自分の考えも16行目なのですが・・・あっているのでしょうか?
もしあっているのであれば、先ほどもありましたが、39行目の onDraw(getHolder());の後と、46行目のunlockにエラーがついてしまいます、その理由が知りたいです。
(間違っているのであればそれはそれなのですが・・)
GameSurfaceViewはこれで問題ないはずです。

エラーについては詳しく教えていただけないでしょうか。
Eclipseで開発しているのであればエラー箇所にカーソルを合わせればエラーメッセージがポップアップ表示されますし、『問題』ウィンドウにエラーメッセージが一覧表示されるはずです。

エラーがここだけじゃなく、GameMgrにもエラーがあるのならGameMgrに関係するすべての箇所にエラーは出ますが。
mi_l さんが書きました:そうすると、GameMgr.javaでは「_barrList.add(new BarricadeSquare( 0, 0,480, 20, null , bits))」とやっても「_barrList.add(new BarricadeSquare( 0, 0,480, 20, null ))」とやってもエラーが出ませんでした。(これは指摘の意図にあっていたということでしょうか?)
それは以前Barricadeクラスのところで説明しました。
既存のコードをエラーにしないためにコンストラクタの呼び出しを差し替えています。

ですがBarricadeSquareのコンストラクタは意図に合っていません。
追加した部分が何もしないコンストラクタになっています。
this(~)構文を使って、引数を追加したコンストラクタを呼び出すようにしてください。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#17

投稿記事 by ISLe » 12年前

エラーをとても気にしていらっしゃいますが、コンパイルエラーは次に作業すべき箇所を示す貴重な情報です。

GameMgrのコンストラクタに引数を追加した際に実引数をnullにしたようなその場しのぎは絶対にしないでください。

貴重な情報を失うだけでなく、さらにそれは実行時のバグとなり、はるかに多くの、数時間・数日といった単位で人生の貴重な時間が奪われていくことになります。

コンパイルエラーがあるというのはまだやるべきことがあるということです。
その場しのぎから生まれたバグを潰す作業は完全に無駄なことです。

少なくとも現時点でコンパイルエラーがあるのは作業が進んでいる証拠で、正常です。
むしろコンパイルエラーがあってくれないとおかしいですし次に何をやれば良いか分からなくなるのでなくなると困ります。
こちらは実際に作業していないので気付かないこともあるはずなので。

mi_l

Re: androidアプリで困っています。ご教授ください

#18

投稿記事 by mi_l » 12年前

ご指摘ありがとうございます。

返信が遅くなりました。

コンストラクタは自分なりに直してみました。

変更箇所
(21行目)

BarricadeSquare.java

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;


public class BarricadeSquare extends Barricade {

	public BarricadeSquare( float x, float y, float w, float h, BConf conf, Bitmap img ){
		super(4,conf, img);
		_pt[0].x  = x;		_pt[0].y = y;
		_pt[1].x  = x+w;	_pt[1].y = y;
		_pt[2].x  = x+w;	_pt[2].y = y+h;
		_pt[3].x  = x;		_pt[3].y = y+h;
		_center.x = x+w/2;
		_center.y = y+h/2;


	}
	public BarricadeSquare( float x, float y, float w, float h, BConf conf)
	{
		this(x, y ,w, h, conf, null);

	}

}
そして、GameMgr.javaでもエラーがなくなったかと思ったのですが、最後に一つありました

(ですが、これはエラー部分に破線が出てきたわけではなく、equlipse下部の問題の部分を見ても理解ができませんでした・・・

135行目のonDrawについてでした。
エラー内容は、
「Suspicious method call; should probably call "draw" rather than "onDraw”」

とありました。

コード:

package net.dixq.irairabar;

import java.util.ArrayList;
import java.util.LinkedList;

import net.dixq.irairabar.Barricade.eType;

import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;

import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.content.res.Resources;
import android.content.Context;


public class GameMgr {

	private enum eStatus{
		NORMAL,
		GAMEOVER,
		GAMECLEAR
	};

	private static final float PI = (float) Math.PI;
	private ArrayList<Barricade> _barrList = new ArrayList<Barricade>();//障害物リスト
	private LinkedList<Task> _taskList = new LinkedList<Task>();// タスクリスト
	private eStatus _status = eStatus.NORMAL;
	private Player _player;

	GameMgr(Context con) {

		Resources res = con.getResources();
		Bitmap bits = BitmapFactory.decodeResource(res, R.drawable.ic_launcher);



		_barrList.add(new BarricadeSquare(  0,  0,480, 20, null , bits));// 画面4隅に四角形を配置

		_barrList.add(new BarricadeSquare(  0,  0, 700,800, null));
		/*
		_barrList.add(new BarricadeSquare(460,  0, 20,800, null));
		_barrList.add(new BarricadeSquare(  0,780,480, 20, null));

		_barrList.add(new BarricadeTriangle(  0, 0, 200, new BConf(+PI / 150),));// 左上回転する三角形
		_barrList.add(new BarricadeTriangle(480, 0, 180, new BConf(+PI / 150)));// 右上回転する三角形

		_barrList.add(new BarricadeStar(240, 240, 50, 200, new BConf(-PI / 360)));// 中央に回転する星
		_barrList.add(new BarricadeStar(240, 240, 20,  80, new BConf(+PI / 360)));// 中央に回転する星

		_barrList.add(new BarricadeSquare(300, 440, 200, 20, null));//右下の固定通路
		_barrList.add(new BarricadeSquare(250, 520, 130, 20, null));//
		_barrList.add(new BarricadeSquare(330, 620, 130, 20, null));//

		_barrList.add(new BarricadeSquare(230, 390, 20, 350, null));//中央区切り線

		_barrList.add(new BarricadeSquare(0, 480, 240, 20, new BConf(+PI / 360)));// 左下回転するバー

		_barrList.add(new BarricadeSquare( 20, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(130, 600, 110, 20, new BConf(+PI / 360)));// 左下回転するバー
		_barrList.add(new BarricadeSquare(185, 600,  55, 20, new BConf(+PI / 360)));// 左下回転するバー

*/
	//	_barrList.add(new BarricadeSquare(20, 680,  80, 20, null));// ゴールに接触したバー

	//	_barrList.add(new BarricadeSquare(20, 700,  80, 80, new BConf(eType.GOAL)));// ゴール

		for (Barricade bar : _barrList) {
			_taskList.add(bar);	//タスクリストに障害物を追加
		}

		_player = new Player();
		_taskList.add(_player);
		_taskList.add(new FpsController());
	}

	private boolean Collision(){
		Vec vec = new Vec();
		final Circle cir = _player.getPt();
		for(Barricade barr : _barrList){
			Def.eHitCode code = barr.isHit(cir, vec);
			switch(code){
			case OUT:
				_status = eStatus.GAMEOVER;
				return true;
			case GOAL:
				_status = eStatus.GAMECLEAR;
				return true;
			}
		}
		return false;
	}

	public boolean onUpdate() {
		if( _status != eStatus.NORMAL ){
			return true;
		}
		if( Collision() ){
			return true;
		}
		for (int i = 0; i < _taskList.size(); i++) {
			if (_taskList.get(i).onUpdate() == false) { // 更新失敗なら
				_taskList.remove(i); // そのタスクを消す
				i--;
			}
		}
		return true;
	}

	private void drawStatus(Canvas c){
		switch( _status ){
		case GAMEOVER:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameOver", 40, 100, paint);
			}
			break;
		case GAMECLEAR:
			{
				Paint paint = new Paint();
				paint.setTextSize(80);
				paint.setColor(Color.BLACK);
				c.drawText("GameClear", 40, 100, paint);
			}
			break;
		}
	}

	public void onDraw(Canvas c) {
		c.drawColor(Color.WHITE); // 白で塗りつぶす
		for (Task task : _taskList) {
			task.onDraw(c);// 描画
		}

		drawStatus(c);
	}

}

どういうことか教えてください。
お願いします。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#19

投稿記事 by ISLe » 12年前

BarricadeSquareのコンストラクタはOKです。
mi_l さんが書きました:135行目のonDrawについてでした。
エラー内容は、
「Suspicious method call; should probably call "draw" rather than "onDraw”」
とありました。
これはAndroid Lintが出力しているエラーです。
Lintとは、バグの原因となりそうな危険なコーディングをチェックしてくれる機能です。
イライラ棒のプロジェクトが作られたときには、まだADTプラグインにこの機能が無かったようですね。

onDrawというメソッドの名前(on~)はシステムからコールバックされるイベントメソッドに付けられる名前で紛らわしいので、自ら呼び出すメソッドにはonDrawではなくdrawという名前を付けなさいということのようです。

とりあえずメソッドの宣言の直前に
@SuppressLint("WrongCall")
と記述することで黙らせることができます。
#スレの最初の投稿で付けてありますね。

今回は既存のプロジェクトを利用しているので黙らせますが、Lint機能を止めたりメッセージを無視するのは本来は危険なことです。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#20

投稿記事 by ISLe » 12年前

GameMgrの障害物リストに障害物を登録しているコードを(BarricadeSquare以外もすべて)元に戻してください。
エラーが出なければ元と同じに動くかどうか確認してください。

元と同じに動くことが確認できたら、画像を描画するコードを加えます。

mi_l

Re: androidアプリで困っています。ご教授ください

#21

投稿記事 by mi_l » 12年前

返信ありがとうございます。

ご指摘いただいた通り、既存のプロジェクトを使っているから助かった部分がとても多いです(まだ全然未熟さを感じます)

ですが、やっとここまで来れました
(No6での返信でいただいた手順の1,2、4、5が終わり、今の段階で実行してもしっかり壁は出ます、あとは描画の部分だけなのですが・・・)

91行目のDrawPathの代わりにDrawBitmapを使うのだと指摘をいただきましたが、DrawBitmapでもたくさん種類がありました。
またDrawPathを使わないなら上の数行(85~90)もいらないですよね

c.drawBitmap(bitmap, left, top, paint)の形では「 c.drawBitmap(bits , )まではわかるのですが表示画像左上の座標はどのように表せばいいのでしょうか?またpaintの部分は?」という状況です・・・


考え方など教えてください。

Barricade.java

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;//追加
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;//追加
import android.graphics.PointF;


public class Barricade extends Task {
    public enum eType{
        OUT,
        GOAL
    }

    protected PointF  _center = new PointF(0,0);        //図形の中心点
    protected PointF  _pt[];                            //図形の頂点
    protected Paint   _paint = new Paint();             //ペイント
    protected eType   _type = eType.OUT;                //タイプ(当たるとアウトな壁、ゴールの壁、等)
    protected float   _rotaSpeed = 0;                   //回転スピード
    protected Bitmap bit;

    //protected int images;//参照を保持するインスタンス変数(何型の変数?)

    //コンストラクタ。 type=タイプ、 n=頂点の数、 conf=設定情報
    public Barricade(int n, BConf conf,Bitmap img)
    {

        bit = img;//格納(記録);


        if( conf != null ){
            _rotaSpeed  = conf.speed;   //回転スピード
            _type       = conf.type;    //物体のタイプ
        }
        switch(_type){
        case OUT:   //接触してアウトな物
            _paint.setColor(Color.RED);
            break;
        case GOAL:  //接触してゴールな物
            _paint.setColor(Color.GREEN);
            break;
        }
        _pt = new PointF[n];    //頂点配列を作る
        for( int i=0; i<n; i++ ){
            _pt[i] = new PointF();  //頂点を作る
        }
        _paint.setAntiAlias(true);
    }
    public Barricade(int n , BConf conf)
    {
        this(n , conf , null);
    }

    //更新する
    public boolean onUpdate(){
        if( _rotaSpeed != 0 ){  //回転するなら
            DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed ); //頂点リスト(_pt)を_centerを中心に回転する
        }
        return true;
    }

    //接触しているかを問う。円cirが線分vecと接触していれば接触した物体のタイプを返す。接触していなければNOを返す
    public Def.eHitCode isHit( final Circle cir, Vec vec ){
        if( DiagramCalcr.isHit( _pt, cir, vec ) == true ){
            switch(_type){
            case OUT:
                return Def.eHitCode.OUT;
            case GOAL:
                return Def.eHitCode.GOAL;
            }
        }
        return Def.eHitCode.NO;
    }

    //描画する
    public void onDraw(Canvas c)
    {
        //頂点が1未満の図形なんてないので
        if( _pt.length < 1 )
        {
            return;//返す
        }
        Path path = new Path();//パス
        path.moveTo(_pt[0].x, _pt[0].y);    //パスの初期位置をセット
        for( int i=0; i<_pt.length; i++ )
        {
            path.lineTo(_pt[i].x, _pt[i].y);    //頂点の位置へラインを引いていく(軌跡を描いていく)
        }
        c.drawPath(path, _paint);   //引いたラインを描画する

    }
}

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#22

投稿記事 by ISLe » 12年前

mi_l さんが書きました:91行目のDrawPathの代わりにDrawBitmapを使うのだと指摘をいただきましたが、DrawBitmapでもたくさん種類がありました。
またDrawPathを使わないなら上の数行(85~90)もいらないですよね
既存の描画コードを削除してしまうとBitmapをセットしない障害物が表示されなくなってしまいます。
最初に説明しましたが、追加した機能を使わないときは従来どおりに動くほうが作業を少しずつ進めることができますしデバッグにも便利です。

bitsがnullかどうかで振り分けてください。
mi_l さんが書きました: c.drawBitmap(bitmap, left, top, paint)の形では「 c.drawBitmap(bits , )まではわかるのですが表示画像左上の座標はどのように表せばいいのでしょうか?またpaintの部分は?」という状況です・・・
とりあえずBarricadeSquareに限定して考えます。
BarricadeSquareは傾きのない四角形なので、_pt配列の4つの要素を頂点としてそれに合わせて画像を描画します。

Canvas#drawBitmap(Bitmap bitmap, Rect src, RectF dst, Paint paint)
が使えます。
srcはnullを指定すると画像全体が使用されます。
dstに_pt配列の4つの要素を元にしてRectFに適切に値をセットして与えてください。

paintは既に用意されているメンバを使えば良いでしょう。
こちらも必要であればコンストラクタでbitsがnullかどうかで画像を描画する場合の設定をするように振り分けてください。

mi_l

Re: androidアプリで困っています。ご教授ください

#23

投稿記事 by mi_l » 12年前

返信ありがとうございます。

返信である、
ISLe さんが書きました:
既存の描画コードを削除してしまうとBitmapをセットしない障害物が表示されなくなってしまいます。
最初に説明しましたが、追加した機能を使わないときは従来どおりに動くほうが作業を少しずつ進めることができますしデバッグにも便利です。

bitsがnullかどうかで振り分けてください。

とりあえずBarricadeSquareに限定して考えます。
BarricadeSquareは傾きのない四角形なので、_pt配列の4つの要素を頂点としてそれに合わせて画像を描画します。

Canvas#drawBitmap(Bitmap bitmap, Rect src, RectF dst, Paint paint)
が使えます。
srcはnullを指定すると画像全体が使用されます。
dstに_pt配列の4つの要素を元にしてRectFに適切に値をセットして与えてください。

paintは既に用意されているメンバを使えば良いでしょう。
こちらも必要であればコンストラクタでbitsがnullかどうかで画像を描画する場合の設定をするように振り分けてください。
の個所についての自分の考えを載せます

BarricadeSquare.java
(変更点なし)

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;


public class BarricadeSquare extends Barricade {

    public BarricadeSquare( float x, float y, float w, float h, BConf conf, Bitmap img ){
        super(4,conf, img);
        _pt[0].x  = x;      _pt[0].y = y;
        _pt[1].x  = x+w;    _pt[1].y = y;
        _pt[2].x  = x+w;    _pt[2].y = y+h;
        _pt[3].x  = x;      _pt[3].y = y+h;
        _center.x = x+w/2;
        _center.y = y+h/2;


    }
    public BarricadeSquare( float x, float y, float w, float h, BConf conf)
    {
        this(x, y ,w, h, conf, null);

    }

}
そして、Barricade.java
変更点
(9行目に追加)
(92~100行目)

コード:

package net.dixq.irairabar;

import android.graphics.Bitmap;//追加
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;//追加
import android.graphics.PointF;
import android.graphics.RectF;//追加


public class Barricade extends Task {
    public enum eType{
        OUT,
        GOAL
    }

    protected PointF  _center = new PointF(0,0);        //図形の中心点
    protected PointF  _pt[];                            //図形の頂点
    protected Paint   _paint = new Paint();             //ペイント
    protected eType   _type = eType.OUT;                //タイプ(当たるとアウトな壁、ゴールの壁、等)
    protected float   _rotaSpeed = 0;                   //回転スピード
    protected Bitmap bit;

    //protected int images;//参照を保持するインスタンス変数(何型の変数?)

    //コンストラクタ。 type=タイプ、 n=頂点の数、 conf=設定情報
    public Barricade(int n, BConf conf,Bitmap img)
    {

        bit = img;//格納(記録);


        if( conf != null ){
            _rotaSpeed  = conf.speed;   //回転スピード
            _type       = conf.type;    //物体のタイプ
        }
        switch(_type){
        case OUT:   //接触してアウトな物
            _paint.setColor(Color.RED);
            break;
        case GOAL:  //接触してゴールな物
            _paint.setColor(Color.GREEN);
            break;
        }
        _pt = new PointF[n];    //頂点配列を作る
        for( int i=0; i<n; i++ ){
            _pt[i] = new PointF();  //頂点を作る
        }
        _paint.setAntiAlias(true);
    }
    public Barricade(int n , BConf conf)
    {
        this(n , conf , null);
    }

    //更新する
    public boolean onUpdate(){
        if( _rotaSpeed != 0 ){  //回転するなら
            DiagramCalcr.RotateDiagram( _pt, _center, _rotaSpeed ); //頂点リスト(_pt)を_centerを中心に回転する
        }
        return true;
    }

    //接触しているかを問う。円cirが線分vecと接触していれば接触した物体のタイプを返す。接触していなければNOを返す
    public Def.eHitCode isHit( final Circle cir, Vec vec ){
        if( DiagramCalcr.isHit( _pt, cir, vec ) == true ){
            switch(_type){
            case OUT:
                return Def.eHitCode.OUT;
            case GOAL:
                return Def.eHitCode.GOAL;
            }
        }
        return Def.eHitCode.NO;
    }

    //描画する
    public void onDraw(Canvas c)
    {
        //頂点が1未満の図形なんてないので
        if( _pt.length < 1 )
        {
            return;//返す
        }
        Path path = new Path();//パス
        path.moveTo(_pt[0].x, _pt[0].y);    //パスの初期位置をセット
        for( int i=0; i<_pt.length; i++ )
        {
            path.lineTo(_pt[i].x, _pt[i].y);    //頂点の位置へラインを引いていく(軌跡を描いていく)
        }
        if( bit == null )
        {
        c.drawPath(path, _paint);   //引いたラインを描画する
        }
        else
        {
        //画像は全体を使うと仮定
        c.drawBitmap(bit, null, new RectF(_pt[0].x , _pt[0].y , _pt[2].x , _pt[2].y ), null);
        }

    }
}

ご指摘お願いします。

mi_l

Re: androidアプリで困っています。ご教授ください

#24

投稿記事 by mi_l » 12年前

追記、

実機で実行しましたら、無事に画像が出ました!

微調整(表示画像の)も終わり、私のこのトピックの質問に対する答えが形になりました。


が、一つ前の私の考えに対するご指摘、アドバイスなどあれば、書いていただきたいです

ですので、一応まだ「解決」はつけないでおきます。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#25

投稿記事 by ISLe » 12年前

Barricadeの描画処理は、画像を描画する場合は、Pathのインスタンスを作成するところから分岐してください。
画像を描画するときPathは不要です。

インデントにも注意してください。

全体としては特に問題ないと思います。

ISLe
記事: 2650
登録日時: 15年前
連絡を取る:

Re: androidアプリで困っています。ご教授ください

#26

投稿記事 by ISLe » 12年前

mi_l さんが書きました:ご指摘いただいた通り、既存のプロジェクトを使っているから助かった部分がとても多いです(まだ全然未熟さを感じます)
既存のものを使うことと未熟かどうかは関係ありません。

誰でも既存の言語を使い、既存の開発環境を使い、既存のプラットフォームを使い、既存のハードウェアを使います。
すべてをゼロから作ることのできるひとなど、ひとにぎりどころかほんのひとつまみもいません。

未熟というのは、その場しのぎや思い込みで貴重な情報を無駄にすることです。
そのせいで自ら無駄で余計な作業を増やして本来やるべき仕事が遅くなります。

ソースコードを読むことやマニュアルを読むときにも、ただ書いてあることを読むだけでなく、あらゆる情報を読み取ることが重要です。

そのひとつは癖です。
これを書いた人はこういうふうに書く傾向があるということを読み取れば、どこに対象があるか、どういうキーワードで情報にヒットするかといったことを素早く判断できます。

描画先の矩形を指定する引数があるはずだと考えてリファレンスを見れば
Canvas#drawBitmap(Bitmap bitmap, Rect src, RectF dst, Paint paint)
を見付けるのに5秒もかかりません。
ひとつずつ文章に書かれた機能の説明を読んでいったら数十分とか下手したら数時間かかります。
それだけで一日が終わってしまいます。

mi_l

Re: androidアプリで困っています。ご教授ください

#27

投稿記事 by mi_l » 12年前

最後までご指摘、ご教授いただきありがとうございます。

No、25での指摘に対するコードの訂正はしました。

アドバイスもいただき感謝いたします。


自分の納得いかないところ、今一つ理解できてないところは、我儘に訊きました(もちろん調べてからですけど・・・)

その質問に対する返信も丁寧にしてくださり、とても助かりました。


では、これにてこのトピックは解決とさせていただきます。

閉鎖

“C言語何でも質問掲示板” へ戻る