for文を使ったセーブ機能について

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
白雪
記事: 5
登録日時: 1年前

for文を使ったセーブ機能について

#1

投稿記事 by 白雪 » 1年前

セーブ機能を追加したくてスクリプトプレーヤーにあるセーブ機能を参考にコードを書きました。
横3マス分、縦4マス分に区切り、任意の場所をクリックするとその場所に応じてそれぞれセーブされる仕組みです。

現在12マス分すべて反応しますが、セーブは1番左上のみされる状況です。他の所はクリック判定されていますが更新はされません。予想ですがセーブ場所決定をするfor文が原因かと思います。

コード:

//セーブ画面作成
for (y = SAVE_PAGE * 4; y < SAVE_PAGE * 4 + 4; y++) {
	for (z = 0; z < 3; z++) {
		SetDrawBlendMode(DX_BLENDMODE_ALPHA, 128);
		DrawGraph(10 + (z % 3) * 416, 30 + (y % 4) * 169, SAVE_BG_D, TRUE);
		SetDrawBlendMode(DX_BLENDMODE_NOBLEND, 0);
	}
}

//画面上でのセーブ場所決定
for (y = SAVE_PAGE * 4; y < SAVE_PAGE * 4 + 4; y++) {//セーブ場所決定 X座標 横方向
	x = 0;
	for (z = 0; z < 3; z++) {//セーブ場所決定 Y座標 縦方向
	DrawFormatStringToHandle(10 + ((z % 3) * 416), 30 + ((y % 4) * 169), GetColor(0, 0, 0), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
	if (Mouse_X > 10 + ((z % 3) * 416) && Mouse_X < 426 + ((z % 3) * 416) && Mouse_Y>30 + ((y % 4) * 169) && Mouse_Y < 199 + ((y % 4) * 169)) {//クリック判定設定
			DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(255, 255, 255), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
		if (Mouse_CL != 0) {
				x = (3 * (y % 4)) + (z % 3);//セーブするファイルナンバー
				Game_Save(x = (3 * (y % 4)) + (z % 3)); }//セーブ処理
		}
		else
		{
			DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(192, 192, 192), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
		}
		}
	}

/*
yで縦何行目かの指定、zで横何行目かの指定をしています。
z0のy3なら11のセーブ場所にセーブされる。

  ↓  ↓  ↓
   Z0  Z1  Z2
  	 0  1  2  Y0←
  	 3  4  5  Y1←
  	 6  7  8  Y2←
  	 9  10   11    Y3←
  	 
  セーブ処理のGame_Save(x = (3 * (y % 4)) + (z % 3)); が11になり、それでファイルを決定している。
  	 
*/

Visualstudio2019  c++ DXライブラリ

質問は、なぜ1番左上のみセーブされるか、どこに問題があるか。
また、このコードの場合for文ではなく別のコードの方がいいのか。
それが知りたいです。

ぶっきらぼうな書き方になってしまいすみません。よろしくお願いします。
添付ファイル
スクリーンショット 2022-06-25 182233.png
実際のセーブ画面になります。

アバター
みけCAT
記事: 6734
登録日時: 13年前
住所: 千葉県
連絡を取る:

Re: for文を使ったセーブ機能について

#2

投稿記事 by みけCAT » 1年前

適当にコードを補って動かしてみた結果、Game_Save関数にはクリックした場所に対応する番号が渡されていました。
よって、Game_Save関数もしくはその他の未公開の部分にバグがあると推測できます。

コード:

#include <DxLib.h>
#include <vector>

struct Date_s {
	int Year, Mon, Day, Hour, Min, Sec;
	Date_s() : Year(0), Mon(0), Day(0), Hour(0), Min(0), Sec(0) {}
};

void Game_Save(int x) {
	printfDx("saved %d\n", x);
}

int WINAPI WinMain(HINSTANCE /* hInstance */, HINSTANCE /* hPrevInstance */, LPSTR /* lpCmdLine */, int /* nCmdShow */) {
	if (ChangeWindowMode(TRUE) != DX_CHANGESCREEN_OK || DxLib_Init() != 0) return 1;
	int SAVE_BG_D = MakeScreen(128, 128, FALSE);
	SetDrawScreen(SAVE_BG_D);
	DrawBox(0, 0, 128, 128, GetColor(255, 128, 128), TRUE);
	DrawBox(10, 10, 118, 118, GetColor(128, 64, 64), TRUE);

	SetDrawScreen(DX_SCREEN_BACK);

	const int SAVE_PAGE = 0;
	int FontHandle_L = CreateFontToHandle(NULL, -1, -1, -1);
	std::vector<Date_s> Date(100);

	int pMouseButton = 0, cMouseButton;
	while (ScreenFlip() == 0 && ClearDrawScreen() == 0 && ProcessMessage() == 0) {
		int x, y, z;
		int Mouse_X, Mouse_Y, Mouse_CL;
		GetMousePoint(&Mouse_X, &Mouse_Y);
		cMouseButton = GetMouseInput();
		Mouse_CL = (cMouseButton & MOUSE_INPUT_LEFT) && !(pMouseButton & MOUSE_INPUT_LEFT);
		pMouseButton = cMouseButton;

		//セーブ画面作成
		for (y = SAVE_PAGE * 4; y < SAVE_PAGE * 4 + 4; y++) {
			for (z = 0; z < 3; z++) {
				SetDrawBlendMode(DX_BLENDMODE_ALPHA, 128);
				DrawGraph(10 + (z % 3) * 416, 30 + (y % 4) * 169, SAVE_BG_D, TRUE);
				SetDrawBlendMode(DX_BLENDMODE_NOBLEND, 0);
			}
		}

		//画面上でのセーブ場所決定
		for (y = SAVE_PAGE * 4; y < SAVE_PAGE * 4 + 4; y++) {//セーブ場所決定 X座標 横方向
			x = 0;
			for (z = 0; z < 3; z++) {//セーブ場所決定 Y座標 縦方向
			DrawFormatStringToHandle(10 + ((z % 3) * 416), 30 + ((y % 4) * 169), GetColor(0, 0, 0), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
			if (Mouse_X > 10 + ((z % 3) * 416) && Mouse_X < 426 + ((z % 3) * 416) && Mouse_Y>30 + ((y % 4) * 169) && Mouse_Y < 199 + ((y % 4) * 169)) {//クリック判定設定
					DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(255, 255, 255), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
				if (Mouse_CL != 0) {
						x = (3 * (y % 4)) + (z % 3);//セーブするファイルナンバー
						Game_Save(x = (3 * (y % 4)) + (z % 3)); }//セーブ処理
				}
				else
				{
					DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(192, 192, 192), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
				}
			}
		}

	}

	DxLib_End();
	return 0;
}
test1_ss1.png
test1_ss1.png (15.72 KiB) 閲覧数: 3190 回
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

アバター
みけCAT
記事: 6734
登録日時: 13年前
住所: 千葉県
連絡を取る:

Re: for文を使ったセーブ機能について

#3

投稿記事 by みけCAT » 1年前

ところで、Dateの内容を表示する時、「描画する位置に応じた要素」ではなく
「0番目または今回のループでGame_Save関数に渡した場所の要素」を使用しているのはなぜでしょうか?
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

白雪
記事: 5
登録日時: 1年前

Re: for文を使ったセーブ機能について

#4

投稿記事 by 白雪 » 1年前

検証ありがとうございます。
本来自分でコードを書いて確かめるべきでしたが、頭から抜けていました。すみません。
Game_Save関数にはクリックした場所に対応する番号が渡されてたのですね。私の方でも1度しっかりと確認してみます。
みけCAT さんが書きました:
1年前
ところで、Dateの内容を表示する時、「描画する位置に応じた要素」ではなく
「0番目または今回のループでGame_Save関数に渡した場所の要素」を使用しているのはなぜでしょうか?
読解力なくてすみません。

コード:

	DrawFormatStringToHandle(10 + ((z % 3) * 416), 30 + ((y % 4) * 169), GetColor(0, 0, 0), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);//日付け表示
これの『10 + ((z % 3) * 416), 30 + ((y % 4) * 169)』この部分のことでしょうか?この部分なのであれば、特に深い意味はありません。ただたんに参考元がこのような感じだったのでとりあえずこう書いた感じです。

アバター
みけCAT
記事: 6734
登録日時: 13年前
住所: 千葉県
連絡を取る:

Re: for文を使ったセーブ機能について

#5

投稿記事 by みけCAT » 1年前

白雪 さんが書きました:
1年前
これの『10 + ((z % 3) * 416), 30 + ((y % 4) * 169)』この部分のことでしょうか?
いいえ。
どの要素を表示するかを決めるxを、Mouse_CL != 0 の時しか更新していないのが気になった、ということです。
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

白雪
記事: 5
登録日時: 1年前

Re: for文を使ったセーブ機能について

#6

投稿記事 by 白雪 » 1年前

みけCAT さんが書きました:
1年前
いいえ。
どの要素を表示するかを決めるxを、Mouse_CL != 0 の時しか更新していないのが気になった、ということです。
すみません。完全にこちらのミスでした。
見直した結果、Mouse_CL != 0 よりも前に書かなければなりませんでした。指摘していただきありがとうございます。
またそれに伴って要素を表示するxの数式に問題があることがわかりました。

xの更新のタイミングと数式を試行錯誤した結果、それぞれの場所でセーブでき、尚且つ日付がしっかり別々になるようになりました。質問に答えていただきありがとうございました。
最終的に望んだとおりに動いたコードの修正部分を載せておきます。

コード:

//画面上でのセーブ場所決定
for (y = SAVE_PAGE * 4; y < SAVE_PAGE * 4 + 4; y++) {//セーブ場所決定
	for (z = 0; z < 3; z++) {
		x = (3 * (y % 4)) + (z % 3)+ SAVE_PAGE * 12;//質問時より位置と数式の変更を行いました。
		DrawFormatStringToHandle(10 + ((z % 3) * 416), 30 + ((y % 4) * 169), GetColor(0, 0, 0), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);
		if (Mouse_X > 10 + ((z % 3) * 416) && Mouse_X < 426 + ((z % 3) * 416) && Mouse_Y>30 + ((y % 4) * 169) && Mouse_Y < 199 + ((y % 4) * 169)) {
			DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(255, 255, 255), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);
		if (Mouse_CL != 0) {
				Game_Save(x); 
					}//セーブ処理
		}
		else
		{						
			DrawFormatStringToHandle(9 + ((z % 3) * 416), 29 + ((y % 4) * 169), GetColor(192, 192, 192), FontHandle_L, "%d/%d/%d/%d/%d/%d", Date[x].Year, Date[x].Mon, Date[x].Day, Date[x].Hour, Date[x].Min, Date[x].Sec);
		}
	}
}
添付ファイル
スクリーンショット 2022-06-26 073304.png

返信

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