意図した通りに音が鳴らない

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

意図した通りに音が鳴らない

#1

投稿記事 by ノダッシー » 10年前

指定した時間になったら

コード:

PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
を使い音が出るタイマーを作っているのですが
ビルドエラーにはならないのですが、処理が重くパソコンからカリカリ音がなりフリーズ一歩手前位の状態になり、音が鳴らなくて困っています。
何故

コード:

PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
で音が出ないのか
どうすれば指定した時間に効果音を鳴らせられるかを教えて下さい

test.wavは30.5 MBあります
Cはポインタ以外の基礎は一通り新C言語入門スーパービギナー編で学び、C言語ゲームプログラミングの館の3.1までやりました
使っている開発環境はMicrosoft Visual Studio Express 2013です
Windows7 32ビット Core i3 CPU 530 @ 2.93GHz メモリ4.00GB
宜しくお願いします

コード:

#pragma warning(disable : 4819)
#include "DxLib.h"

// プログラムは WinMain から始まります
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
	LPSTR lpCmdLine, int nCmdShow)
{
	//int SetAlwaysRunFlag(TRUE);//ウインドウが非アクティブの状態でも処理し続ける
	int StartTime; //起動時の時間を格納する変数
	int hour, minute, second; //表示する時間
	int set_hour, set_minute, set_second; //セットする時間

	SetOutApplicationLogValidFlag(FALSE); //ログ出力をするか否か
	ChangeWindowMode(FALSE); // ウインドウモードかフルスクリーンか
	SetGraphMode(640, 480, 16); //画面サイズを設定します

	if (DxLib_Init() == -1) // DXライブラリ初期化処理
	{
		return -1; // エラーが起きたら直ちに終了
	}

	SetBackgroundColor(0x00, 0x00, 0x00); //背景の色を設定します

	set_hour = KeyInputNumber(50, 50, 99, 0, TRUE); //セットする時間数を入力
	set_minute = KeyInputNumber(70, 50, 59, 0, TRUE); //セットする分数を入力
	set_second = KeyInputNumber(90, 50, 59, 0, TRUE); //セットする秒数を入力

	set_hour %= 100; //ESCが押されたときに0にする
	set_minute %= 60;
	set_second %= 60;

	if (set_second == 0 && set_minute == 0 && set_hour == 0)
		set_minute = 3;    //0時間0分0秒なら3分に合わせる

	DATEDATA Date;

	int A = 640; //最大の値
	int B = 0; //最小の値
	int C = 0;
	int D = 0; //カウントダウン
	int E = 0; //表示用
	int X1 = 0;
	int X2 = 640;
	int Y1 = 50;
	int Y2 = 50;
	int g_Lagefont = CreateFontToHandle("メイリオ", 50, -1, DX_FONTTYPE_ANTIALIASING);
	int jikann;
	int gogo;
	int Handle;//データハンドル格納用変数

	A = set_hour * 360 + set_minute * 60 + set_second;
	B = 0;
	D = set_minute;
	E = set_minute;
	

	StartTime = GetNowCount(); //起動時の時間を取得

	while (1){
		if (ProcessMessage() == -1)break; //ウインドウのメッセージを処理する
		GetDateTime(&Date);

		second = (GetNowCount() - StartTime) / 1000; //秒に変換

		minute = second / 60; //分に変換
		second %= 60;

		hour = minute / 6; //時間に変換
		minute %= 6;

		SetDrawScreen(DX_SCREEN_BACK); //描画する画面を設定します
		ClearDrawScreen(); //画面に描画されている内容を消します


		

		//時間に合わせてメッセージが変わる
		const char* messages[18] = {
			"",
			" ",
			" ",
			" ",
			" ",
			" ", // 5
			" ",
			" ",
			"おはようございます",
			"おはようございます",
			"今日も一日頑張りましょう!", // 10
			"もうすぐお昼休みだ!",
			"休憩時間です!",
			"午後も頑張りましょう",
			"こんにちは",
			"こんにちは", // 15
			"もうすぐで終わりです",
			"お疲れ様でした"
		};

		if (Date.Hour >= 13){
			jikann = Date.Hour - 12;
			gogo = 1;
		}else{
			jikann = Date.Hour;
			gogo = 0;
		}

		//壁紙
		Handle = LoadGraph("sora.jpg"); // 画像をロード
		DrawGraph(0, 0, Handle, TRUE); // データハンドルを使って画像を描画

		DrawFormatStringToHandle(40, 180, GetColor(255, 174, 201), g_Lagefont, "経過時間"); //説明
		DrawFormatStringToHandle(350, 180, GetColor(11, 166, 50), g_Lagefont, "残り時間"); //説明
		DrawFormatStringToHandle(70, 250, GetColor(255,174, 201),g_Lagefont, "%d分", minute); //経過時間を描画します
		DrawFormatStringToHandle(230, 250, GetColor(255, 255, 255), g_Lagefont, "/%d分/", E); //全体の時間を描画します
		DrawFormatStringToHandle(450, 250, GetColor(11, 166, 50),g_Lagefont, "%d分", D); //残り時間
		DrawFormatStringToHandle(0, 300, GetColor(255, 0, 0), g_Lagefont, "デバッグ用⇒%d:%d", Date.Hour, Date.Min);

	if (Date.Hour == 10 && Date.Min == 0){
			//10時の時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 10 && Date.Min == 5){
		//10時5分に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 11 && Date.Min == 0){
		//11時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 11 && Date.Min == 5){
		//11時5分に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 12 && Date.Min == 0){
		//12時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 13 && Date.Min == 0){
		//13時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 14 && Date.Min == 0){
		//14時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 14 && Date.Min == 5){
		//14時5分に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 15 && Date.Min == 0){
		//15時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 15 && Date.Min == 5){
		//15時5分に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}
	if (Date.Hour == 16 && Date.Min == 0){
		//16時に音を鳴らす
		PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			}

		if (gogo = 0){
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午前%d時%d分", jikann, Date.Min);
		}
		else{
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午後%d時%d分", jikann, Date.Min);
		}

		if (1 <= Date.Hour && Date.Hour <= 17) {
			DrawFormatStringToHandle(0, 0, GetColor(255, 255, 255), g_Lagefont, messages[Date.Hour], D); //メッセージを表示
		}
		//ゲージの描画
		DrawBox(0, 50, 640, 150, GetColor(255, 174, 201), TRUE);
		C = A - (hour * 360 + minute * 60 + second);
		if (C < B) C = B;
		DrawBox(X1, Y1, X1 + (X2 - X1)*(C - B) / (A - B), 150, GetColor(11, 166, 50), TRUE);

		//Dに残り時間[分]を設定
		D = C / 60 + 1;

		ScreenFlip(); //DX_SCREEN_BACKに描画した画像を表示します

		if (set_hour * 360 + set_minute * 60 + set_second <= hour * 360 + minute * 60 + second){
			//DrawFormatString(200, 350, GetColor(255, 255, 255), "時間になりました"); //時間になったら表示する
			// test.wavのノーマル再生
			PlaySoundFile("test.wav", DX_PLAYTYPE_NORMAL);

			//音を鳴らす処理
		}


	}

	DxLib_End(); // DXライブラリ使用の終了処理

	return 0; // ソフトの終了 
}

ノダッシー

Re: 意図した通りに音が鳴らない

#2

投稿記事 by ノダッシー » 10年前

申し訳ないです

コード:

if (Date.Hour == 9 && Date.Min == 0 && Date.Sec == 0){
			//9時に音を鳴らす
		PlaySoundMem(Handle_wav, DX_PLAYTYPE_BACK);
			}
とすることで無事に音がなりました。

アバター
softya(ソフト屋)
副管理人
記事: 11677
登録日時: 14年前
住所: 東海地方
連絡を取る:

Re: 意図した通りに音が鳴らない

#3

投稿記事 by softya(ソフト屋) » 10年前

動いたかもしれませんが、そのガードでは秒間60フレームの場合PlaySoundMemが一秒間に60回呼び出されるのをガードできていません。
気づかないだけで60個音が鳴っているでしょう。
1回しかならないように工夫が必要です。
by softya(ソフト屋) 方針:私は仕組み・考え方を理解して欲しいので直接的なコードを回答することはまれですので、すぐコードがほしい方はその旨をご明記下さい。私以外の方と交代したいと思います(代わりの方がいる保証は出来かねます)。

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

Re: 意図した通りに音が鳴らない

#4

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

ノダッシー さんが書きました:何故

コード:

PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
で音が出ないのか
多分画像のハンドルをPlaySoundMemに入れても音は鳴らないと思います。
ノダッシー さんが書きました:どうすれば指定した時間に効果音を鳴らせられるかを教えて下さい
まず、「指定した時間になり、効果音を鳴らしたか」のフラグを用意(OFFで初期化)します。
そして、指定した時間になり、かつ「指定した時間になり、効果音を鳴らしたか」のフラグがOFFだったら、
効果音をバックグラウンド再生し、「指定した時間になり、効果音を鳴らしたか」のフラグをONにするといいと思います。

タイムアウト時の処理には成功しているので、この「指定した時間」は10時0分などのことですね?
でしたら、各if文の中それぞれにこの処理を書くのではなく、
ここのif文に入る前に「効果音を鳴らすべきか」というフラグをOFFにし、
指定した時間になっていたら「効果音を鳴らすべきか」というフラグをONにするといいでしょう。
ここで、いずれの指定した時間にもなっていなかったら、「指定した時間になり、効果音を鳴らしたか」のフラグをOFFにします。
そして、if文に入った後に「効果音を鳴らすべきか」というフラグがONになっていたら、
効果音を鳴らす処理を行います。
これを踏まえてソースコードを改造すると、このような感じになるでしょう。

コード:

#pragma warning(disable : 4819)
#include "DxLib.h"

// プログラムは WinMain から始まります
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
	LPSTR lpCmdLine, int nCmdShow)
{
	//int SetAlwaysRunFlag(TRUE);//ウインドウが非アクティブの状態でも処理し続ける
	int StartTime; //起動時の時間を格納する変数
	int hour, minute, second; //表示する時間
	int set_hour, set_minute, set_second; //セットする時間

	SetOutApplicationLogValidFlag(FALSE); //ログ出力をするか否か
	ChangeWindowMode(FALSE); // ウインドウモードかフルスクリーンか
	SetGraphMode(640, 480, 16); //画面サイズを設定します

	if (DxLib_Init() == -1) // DXライブラリ初期化処理
	{
		return -1; // エラーが起きたら直ちに終了
	}

	SetBackgroundColor(0x00, 0x00, 0x00); //背景の色を設定します

	set_hour = KeyInputNumber(50, 50, 99, 0, TRUE); //セットする時間数を入力
	set_minute = KeyInputNumber(70, 50, 59, 0, TRUE); //セットする分数を入力
	set_second = KeyInputNumber(90, 50, 59, 0, TRUE); //セットする秒数を入力

	set_hour %= 100; //ESCが押されたときに0にする
	set_minute %= 60;
	set_second %= 60;

	if (set_second == 0 && set_minute == 0 && set_hour == 0)
		set_minute = 3;    //0時間0分0秒なら3分に合わせる

	DATEDATA Date;

	int A = 640; //最大の値
	int B = 0; //最小の値
	int C = 0;
	int D = 0; //カウントダウン
	int E = 0; //表示用
	int X1 = 0;
	int X2 = 640;
	int Y1 = 50;
	int Y2 = 50;
	int g_Lagefont = CreateFontToHandle("メイリオ", 50, -1, DX_FONTTYPE_ANTIALIASING);
	int jikann;
	int gogo;
	int Handle;//データハンドル格納用変数

	bool SiteiSitaZikanNiNariKoukaonWoNarasita = false;

	A = set_hour * 360 + set_minute * 60 + set_second;
	B = 0;
	D = set_minute;
	E = set_minute;
	

	StartTime = GetNowCount(); //起動時の時間を取得

	while (1){
		if (ProcessMessage() == -1)break; //ウインドウのメッセージを処理する
		GetDateTime(&Date);

		second = (GetNowCount() - StartTime) / 1000; //秒に変換

		minute = second / 60; //分に変換
		second %= 60;

		hour = minute / 6; //時間に変換
		minute %= 6;

		SetDrawScreen(DX_SCREEN_BACK); //描画する画面を設定します
		ClearDrawScreen(); //画面に描画されている内容を消します


		

		//時間に合わせてメッセージが変わる
		const char* messages[18] = {
			"",
			" ",
			" ",
			" ",
			" ",
			" ", // 5
			" ",
			" ",
			"おはようございます",
			"おはようございます",
			"今日も一日頑張りましょう!", // 10
			"もうすぐお昼休みだ!",
			"休憩時間です!",
			"午後も頑張りましょう",
			"こんにちは",
			"こんにちは", // 15
			"もうすぐで終わりです",
			"お疲れ様でした"
		};

		if (Date.Hour >= 13){
			jikann = Date.Hour - 12;
			gogo = 1;
		}else{
			jikann = Date.Hour;
			gogo = 0;
		}

		//壁紙
		Handle = LoadGraph("sora.jpg"); // 画像をロード
		DrawGraph(0, 0, Handle, TRUE); // データハンドルを使って画像を描画

		DrawFormatStringToHandle(40, 180, GetColor(255, 174, 201), g_Lagefont, "経過時間"); //説明
		DrawFormatStringToHandle(350, 180, GetColor(11, 166, 50), g_Lagefont, "残り時間"); //説明
		DrawFormatStringToHandle(70, 250, GetColor(255,174, 201),g_Lagefont, "%d分", minute); //経過時間を描画します
		DrawFormatStringToHandle(230, 250, GetColor(255, 255, 255), g_Lagefont, "/%d分/", E); //全体の時間を描画します
		DrawFormatStringToHandle(450, 250, GetColor(11, 166, 50),g_Lagefont, "%d分", D); //残り時間
		DrawFormatStringToHandle(0, 300, GetColor(255, 0, 0), g_Lagefont, "デバッグ用⇒%d:%d", Date.Hour, Date.Min);

	bool OtoWoNarasuBeki = false;
	if (Date.Hour == 10 && Date.Min == 0){
			//10時の時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 10 && Date.Min == 5){
		//10時5分に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 11 && Date.Min == 0){
		//11時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 11 && Date.Min == 5){
		//11時5分に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 12 && Date.Min == 0){
		//12時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 13 && Date.Min == 0){
		//13時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 14 && Date.Min == 0){
		//14時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 14 && Date.Min == 5){
		//14時5分に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 15 && Date.Min == 0){
		//15時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 15 && Date.Min == 5){
		//15時5分に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (Date.Hour == 16 && Date.Min == 0){
		//16時に音を鳴らす
		//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
		OtoWoNarasuBeki = true;
			}
	if (OtoWoNarasuBeki) {
		if (!SiteiSitaZikanNiNariKoukaonWoNarasita) {
			SiteiSitaZikanNiNariKoukaonWoNarasita = true;
			PlaySoundFile("test.wav", DX_PLAYTYPE_BACK);
		}
	} else {
		SiteiSitaZikanNiNariKoukaonWoNarasita = false;
	}


		if (gogo = 0){
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午前%d時%d分", jikann, Date.Min);
		}
		else{
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午後%d時%d分", jikann, Date.Min);
		}

		if (1 <= Date.Hour && Date.Hour <= 17) {
			DrawFormatStringToHandle(0, 0, GetColor(255, 255, 255), g_Lagefont, messages[Date.Hour], D); //メッセージを表示
		}
		//ゲージの描画
		DrawBox(0, 50, 640, 150, GetColor(255, 174, 201), TRUE);
		C = A - (hour * 360 + minute * 60 + second);
		if (C < B) C = B;
		DrawBox(X1, Y1, X1 + (X2 - X1)*(C - B) / (A - B), 150, GetColor(11, 166, 50), TRUE);

		//Dに残り時間[分]を設定
		D = C / 60 + 1;

		ScreenFlip(); //DX_SCREEN_BACKに描画した画像を表示します

		if (set_hour * 360 + set_minute * 60 + set_second <= hour * 360 + minute * 60 + second){
			//DrawFormatString(200, 350, GetColor(255, 255, 255), "時間になりました"); //時間になったら表示する
			// test.wavのノーマル再生
			PlaySoundFile("test.wav", DX_PLAYTYPE_NORMAL);

			//音を鳴らす処理
		}


	}

	DxLib_End(); // DXライブラリ使用の終了処理

	return 0; // ソフトの終了 
}
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

ノダッシー

Re: 意図した通りに音が鳴らない

#5

投稿記事 by ノダッシー » 10年前

soft屋さん、みけCATさん
ガードの問題ご指摘ありがとうございました
1秒間に60回も呼びだれていたとは…重くなるのは当然ですね^^;

今回は時計のプログラムの仕様変更をしまして実装したい事が4つあります

1.以下の指定した時間に音が鳴るようにする →解決済み

2.残り時間と連動してゲージが減っていくようにする。例えば9:55分になったら残り時間が5分になりゲージもそれに合わせて減少していく → 未解決
試したこと→ 音をならすタイミングで、残り時間を D = 5; に設定してみたがダメでした

3.時間により表示メッセージが変動する →解決済み

4.立ち上げた瞬間から自動的に残り時間と経過時間が連動して動くようにしたい
→現状何故か設定してないのにゲージが減っていく
試したこと式を弄ってみたが訳がわかりません


9:00-9:55
10:00-10:55
11:00-12:00
12:40-13:40
13:45-14:50
14:55-16:00


どうかよろしくお願いします

コード:

#pragma warning(disable : 4819)
#include "DxLib.h"

// プログラムは WinMain から始まります
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
	LPSTR lpCmdLine, int nCmdShow)
{
	//int SetAlwaysRunFlag(TRUE);//ウインドウが非アクティブの状態でも処理し続ける
	int StartTime; //起動時の時間を格納する変数
	int hour, minute, second; //表示する時間
	int set_hour = 0, set_minute = 0, set_second = 0; //セットする時間

	SetOutApplicationLogValidFlag(FALSE); //ログ出力をするか否か
	ChangeWindowMode(TRUE); // ウインドウモードかフルスクリーンか
	SetGraphMode(640, 480, 16); //画面サイズを設定します

	if (DxLib_Init() == -1) // DXライブラリ初期化処理
	{
		return -1; // エラーが起きたら直ちに終了
	}

	SetBackgroundColor(0x00, 0x00, 0x00); //背景の色を設定します


	DATEDATA Date;

	int A = 640; //最大の値
	int B = 0; //最小の値
	int C = 0;//???
	int D = 0; //カウントダウン
	int E = 0; //表示用
	int X1 = 0;
	int X2 = 640;
	int Y1 = 50;
	int Y2 = 50;
	int g_Lagefont = CreateFontToHandle("メイリオ", 50, -1, DX_FONTTYPE_ANTIALIASING);
	int jikann;
	int gogo;
	int Handle;//背景画像描画用
	int Handle_wav;

	bool SiteiSitaZikanNiNariKoukaonWoNarasita = false;

	Handle_wav = LoadSoundMem("test.wav"); // サウンド/up.wavをロードし、識別番号をHandleに格納

	StartTime = GetNowCount(); //起動時の時間を取得

	while (1){
		if (ProcessMessage() == -1)break; //ウインドウのメッセージを処理する
		GetDateTime(&Date);

		second = (GetNowCount() - StartTime) / 1000; //秒に変換

		minute = second / 60; //分に変換
		second %= 60;

		hour = minute / 6; //時間に変換
		minute %= 6;



		SetDrawScreen(DX_SCREEN_BACK); //描画する画面を設定します
		ClearDrawScreen(); //画面に描画されている内容を消します




		//時間に合わせてメッセージが変わる
		const char* messages[18] = {
			"",
			" ",
			" ",
			" ",
			" ",
			" ", // 5
			" ",
			" ",
			"おはようございます",
			"おはようございます",
			"今日も一日頑張りましょう!", // 10
			"もうすぐお昼休みだ!",
			"休憩時間です!",
			"午後も頑張りましょう",
			"こんにちは",
			"こんにちは", // 15
			"もうすぐで終わりです",
			"お疲れ様でした"
		};

		if (Date.Hour >= 13){
			jikann = Date.Hour - 12;
			gogo = 1;
		}
		else{
			jikann = Date.Hour;
			gogo = 0;
		}

		//壁紙
		//Handle = LoadGraph("sora.jpg"); // 画像をロード
		//DrawGraph(0, 0, Handle, TRUE); // データハンドルを使って画像を描画

		DrawFormatStringToHandle(40, 180, GetColor(255, 174, 201), g_Lagefont, "経過時間"); //説明
		DrawFormatStringToHandle(350, 180, GetColor(11, 166, 50), g_Lagefont, "残り時間"); //説明
		DrawFormatStringToHandle(70, 250, GetColor(255, 174, 201), g_Lagefont, "%d分", minute); //経過時間を描画します
		DrawFormatStringToHandle(230, 250, GetColor(255, 255, 255), g_Lagefont, "/%d分/", E); //全体の時間を描画します
		DrawFormatStringToHandle(450, 250, GetColor(11, 166, 50), g_Lagefont, "%d分", D); //残り時間

		bool OtoWoNarasuBeki = false;
		if (Date.Hour == 9 && Date.Min == 0){
			//9時の時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 9 && Date.Min == 55){
			//9時55分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 10 && Date.Min == 55){
			//10時55に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 11 && Date.Min == 0){
			//11時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 12 && Date.Min == 0){
			//12時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 12 && Date.Min == 40){
			//12時40に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 13 && Date.Min == 40){
			//13時40に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 13 && Date.Min == 45){
			//13時45分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 50){
			//14時50に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 55){
			//14時55分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 55){
			//14時55に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 16 && Date.Min == 0){
			//16時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (OtoWoNarasuBeki) {
			if (!SiteiSitaZikanNiNariKoukaonWoNarasita) {
				SiteiSitaZikanNiNariKoukaonWoNarasita = true;
				PlaySoundFile("test.wav", DX_PLAYTYPE_BACK);
			}
		}
		else {
			SiteiSitaZikanNiNariKoukaonWoNarasita = false;
		}

		if (gogo = 0){
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午前%d時%d分", jikann, Date.Min);
		}
		else{
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午後%d時%d分", jikann, Date.Min);
		}

		if (1 <= Date.Hour && Date.Hour <= 17) {
			DrawFormatStringToHandle(0, 0, GetColor(255, 255, 255), g_Lagefont, messages[Date.Hour], D); //メッセージを表示
		}
		//ゲージの描画
		DrawBox(0, 50, 640, 150, GetColor(255, 174, 201), TRUE);
		C = A - (hour * 360 + minute * 60 + second);
		if (C < B) C = B;
		//      0   50  0    640    0       0    640  0
		DrawBox(X1, Y1, X1 + (X2 - X1)*(C - B) / (A - B), 150, GetColor(11, 166, 50), TRUE);

		//Dに残り時間[分]を設定
		//D = C / 60;
		ScreenFlip(); //DX_SCREEN_BACKに描画した画像を表示します


	}

	DxLib_End(); // DXライブラリ使用の終了処理

	return 0; // ソフトの終了 
}

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

Re: 意図した通りに音が鳴らない

#6

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

ノダッシー さんが書きました:2.残り時間と連動してゲージが減っていくようにする。例えば9:55分になったら残り時間が5分になりゲージもそれに合わせて減少していく → 未解決
試したこと→ 音をならすタイミングで、残り時間を D = 5; に設定してみたがダメでした
仕様をもう少し詳しく教えてほしいです。
「例えば9:55分になったら残り時間が5分になり」とありますが、他の例はありますか?
「残り時間」は特定の時刻までのものですか?それても残り時間を設定する時刻と設定する残り時間の組が与えられますか?
ノダッシー さんが書きました:4.立ち上げた瞬間から自動的に残り時間と経過時間が連動して動くようにしたい
→現状何故か設定してないのにゲージが減っていく
試したこと式を弄ってみたが訳がわかりません
前述のとおり「残り時間」の仕様がよくわからないですが、
残り時間=測りたい時間-経過時間 というように計算すれば連動して動くと思います。
ゲージが動くのは、1 [hour] + 4 [minuts] + 40 [second]の時間についてカウントダウンしているからであり、仕様です。
ノダッシー さんが書きました:9:00-9:55
10:00-10:55
11:00-12:00
12:40-13:40
13:45-14:50
14:55-16:00
このデータはどういう意味ですか?
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

ノダッシー

Re: 意図した通りに音が鳴らない

#7

投稿記事 by ノダッシー » 10年前

説明不足で申し訳ないです
添付した画像の通りに動くタイマーを制作したいのですが
残り時間とは全体の時間から経過時間を引いた時間で
全体の時間とは
1回目55分
2回目5分
3回目55分
4回目5分
5回目60分
6回目5分
7回目65分
8回目5分
9回目65分
の事です


9:00時に音を鳴らし、全体の時間を55分と設定して、9:55分になったら再度音を鳴らし全体の時間を5分に設定します
次は10:00時なったら音を鳴らし全体の時間を55分にします、
ゲージはその時間と連動して動く仕組みに作りたいです


9:00-9:55
10:00-10:55
11:00-12:00
12:40-13:40
13:45-14:50
14:55-16:00

ノダッシー

Re: 意図した通りに音が鳴らない

#8

投稿記事 by ノダッシー » 10年前

画像
画像貼り忘れました申し訳ないです

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

Re: 意図した通りに音が鳴らない

#9

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

仕様に合うようにプログラムを改造してみました。

コード:

#pragma warning(disable : 4819)
#include "DxLib.h"

// プログラムは WinMain から始まります
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
	LPSTR lpCmdLine, int nCmdShow)
{
	//int SetAlwaysRunFlag(TRUE);//ウインドウが非アクティブの状態でも処理し続ける
	//int StartTime; //起動時の時間を格納する変数
	//int hour, minute, second; //表示する時間
	//int set_hour = 0, set_minute = 0, set_second = 0; //セットする時間
	int minute;

	SetOutApplicationLogValidFlag(FALSE); //ログ出力をするか否か
	ChangeWindowMode(TRUE); // ウインドウモードかフルスクリーンか
	SetGraphMode(640, 480, 16); //画面サイズを設定します

	if (DxLib_Init() == -1) // DXライブラリ初期化処理
	{
		return -1; // エラーが起きたら直ちに終了
	}

	SetBackgroundColor(0xFF, 0xFF, 0xFF); //背景の色を設定します

	int moziNoIro = GetColor(0, 0, 0);
	int keikaZikanNoIro = GetColor(217, 150, 148);
	int nokoriZikanNoIro = GetColor(0, 176, 80);
	int geeziNoKyoukaiSenNoIro = GetColor(56, 93, 138);
	int migiNoSenNoIro = GetColor(106 ,106, 106);
	int hidariNoSenNoIro = GetColor(63, 93, 141);

	DATEDATA Date;

	int A = 640; //最大の値
	int B = 0; //最小の値
	int C = 0;//???
	int D = 0; //カウントダウン
	int E = 0; //表示用
	int X1 = 0;
	int X2 = 640;
	int Y1 = 50;
	//int Y2 = 50;
	int g_Lagefont = CreateFontToHandle("メイリオ", 50, -1, DX_FONTTYPE_ANTIALIASING);
	int jikann;
	int gogo;
	//int Handle;//背景画像描画用
	//int Handle_wav;

	//bool SiteiSitaZikanNiNariKoukaonWoNarasita = false;
	int maeNiOtoWoNarasitaZikantai = -1;
	bool saisyoNoFureemuDeAru = true;

	//Handle_wav = LoadSoundMem("test.wav"); // サウンド/up.wavをロードし、識別番号をHandleに格納

	//StartTime = GetNowCount(); //起動時の時間を取得

	while (1){
		if (ProcessMessage() == -1)break; //ウインドウのメッセージを処理する
		GetDateTime(&Date);

		/*
		second = (GetNowCount() - StartTime) / 1000; //秒に変換

		minute = second / 60; //分に変換
		second %= 60;

		hour = minute / 6; //時間に変換
		minute %= 6;
		*/

		/*
		// テスト用
		// 時刻を60倍の速さで進ませる
		Date.Hour = Date.Min % 24;
		Date.Min = Date.Sec;
		Date.Sec= 0;
		//*/

		SetDrawScreen(DX_SCREEN_BACK); //描画する画面を設定します
		ClearDrawScreen(); //画面に描画されている内容を消します




		//時間に合わせてメッセージが変わる
		const char* messages[18] = {
			"",
			" ",
			" ",
			" ",
			" ",
			" ", // 5
			" ",
			" ",
			"おはようございます",
			"おはようございます",
			"今日も一日頑張りましょう!", // 10
			"もうすぐお昼休みだ!",
			"休憩時間です!",
			"午後も頑張りましょう",
			"こんにちは",
			"こんにちは", // 15
			"もうすぐで終わりです",
			"お疲れ様でした"
		};
		// 基準時刻
		int kizyunZikoku[12][2] = {
			{ 9,  0}, { 9, 55},
			{10,  0}, {10, 55},
			{11,  0}, {12,  0},
			{12, 40}, {13, 40},
			{13, 45}, {14, 50},
			{14, 55}, {16,  0}
		};
		// その基準時刻と次の基準時刻の間でゲージを動かすか
		bool zikanWoHyouziSuru[12] = {
			true, true,
			true, true,
			true, false,
			false, true,
			true, true,
			true, false
		};

		// 今の時刻がどこに該当するかを計算する
		int imaNoZikoku = 60 * (60 * Date.Hour + Date.Min) + Date.Sec;
		int maeNoKizyunZikoku = 0;
		int tugiNoKizyunZikoku = 0;
		int imaNoZikantai = -1;
		for (int i = 0; i < 12; i++) {
			int miteiruKizyunZikoku = 60 * (60 * kizyunZikoku[i][0] + kizyunZikoku[i][1]);
			if (imaNoZikoku < miteiruKizyunZikoku) {
				if (i > 0) {
					imaNoZikantai = i - 1;
					maeNoKizyunZikoku = 60 * (60 * kizyunZikoku[i - 1][0] + kizyunZikoku[i - 1][1]);
					tugiNoKizyunZikoku = 60 * (60 * kizyunZikoku[i][0] + kizyunZikoku[i][1]);
				}
				break;
			}
		}
		if (saisyoNoFureemuDeAru) {
			maeNiOtoWoNarasitaZikantai = imaNoZikantai;
			saisyoNoFureemuDeAru = false;
		}

		// 経過時間と残り時間を計算し、ゲージのパラメータを設定する
		if(imaNoZikantai >= 0 && zikanWoHyouziSuru[imaNoZikantai]) {
			// 表示する時間
			minute = (imaNoZikoku - maeNoKizyunZikoku) / 60;
			E = (tugiNoKizyunZikoku - maeNoKizyunZikoku) / 60;
			D = (tugiNoKizyunZikoku - imaNoZikoku) / 60;
			// ゲージのパラメータ
			A = tugiNoKizyunZikoku;
			B = maeNoKizyunZikoku;
			C = imaNoZikoku;
		} else {
			// 表示する時間
			minute = 99;
			E = 99;
			D = 99;
			// ゲージのパラメータ
			A = 640;
			B = 0;
			C = 0;
		}

		// 午前と午後を分ける
		if (Date.Hour >= 13){
			jikann = Date.Hour - 12;
			gogo = 1;
		}
		else{
			jikann = Date.Hour;
			gogo = 0;
		}

		//壁紙
		//Handle = LoadGraph("sora.jpg"); // 画像をロード
		//DrawGraph(0, 0, Handle, TRUE); // データハンドルを使って画像を描画

		DrawFormatStringToHandle(40, 180, keikaZikanNoIro, g_Lagefont, "経過時間"); //説明
		DrawFormatStringToHandle(350, 180, nokoriZikanNoIro, g_Lagefont, "残り時間"); //説明
		DrawFormatStringToHandle(70, 250, keikaZikanNoIro, g_Lagefont, "%d分", minute); //経過時間を描画します
		DrawFormatStringToHandle(230, 250, moziNoIro, g_Lagefont, "/%d分/", E); //全体の時間を描画します
		DrawFormatStringToHandle(450, 250, nokoriZikanNoIro, g_Lagefont, "%d分", D); //残り時間

		/*
		bool OtoWoNarasuBeki = false;
		if (Date.Hour == 9 && Date.Min == 0){
			//9時の時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 9 && Date.Min == 55){
			//9時55分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 10 && Date.Min == 55){
			//10時55に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 11 && Date.Min == 0){
			//11時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 12 && Date.Min == 0){
			//12時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 12 && Date.Min == 40){
			//12時40に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 13 && Date.Min == 40){
			//13時40に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 13 && Date.Min == 45){
			//13時45分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 50){
			//14時50に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 55){
			//14時55分に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 14 && Date.Min == 55){
			//14時55に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		if (Date.Hour == 16 && Date.Min == 0){
			//16時に音を鳴らす
			//PlaySoundMem(Handle, DX_PLAYTYPE_BACK);
			OtoWoNarasuBeki = true;
		}
		*/
		if (maeNiOtoWoNarasitaZikantai != imaNoZikantai) {
			maeNiOtoWoNarasitaZikantai = imaNoZikantai;
		//if (imaNoZikoku == maeNoKizyunZikoku) {
			//if (!SiteiSitaZikanNiNariKoukaonWoNarasita) {
				//SiteiSitaZikanNiNariKoukaonWoNarasita = true;
			PlaySoundFile("test.wav", DX_PLAYTYPE_BACK);
			//}
		}
		//else {
		//	SiteiSitaZikanNiNariKoukaonWoNarasita = false;
		//}

		DrawFormatStringToHandle(150, 400, moziNoIro, g_Lagefont, "%s%d時%d分", gogo ? "午後" : "午前", jikann, Date.Min);
		/*
		if (gogo = 0){
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午前%d時%d分", jikann, Date.Min);
		}
		else{
			DrawFormatStringToHandle(150, 400, GetColor(255, 255, 255), g_Lagefont, "午後%d時%d分", jikann, Date.Min);
		}
		*/

		if (1 <= Date.Hour && Date.Hour <= 17) {
			DrawFormatStringToHandle(0, 0, moziNoIro, g_Lagefont, messages[Date.Hour], D); //メッセージを表示
		}
		//ゲージの描画
		DrawBox(0, 50, 640, 150, nokoriZikanNoIro, TRUE);
		int geeziNoKawarime = X1 + (X2 - X1)*(C - B) / (A - B);
		//C = A - (hour * 360 + minute * 60 + second);
		//if (C < B) C = B;
		//      0   50  0    640    0       0    640  0
		DrawBox(X1, Y1, geeziNoKawarime, 150, keikaZikanNoIro, TRUE);
		DrawLine(0, Y1    , X2, Y1    , geeziNoKyoukaiSenNoIro);
		DrawLine(0, Y1 - 1, X2, Y1 - 1, geeziNoKyoukaiSenNoIro);
		DrawLine(0, Y1 + 1, X2, Y1 + 1, geeziNoKyoukaiSenNoIro);
		DrawLine(0, 150    , X2, 150    , geeziNoKyoukaiSenNoIro);
		DrawLine(0, 150 - 1, X2, 150 - 1, geeziNoKyoukaiSenNoIro);
		DrawLine(0, 150 + 1, X2, 150 + 1, geeziNoKyoukaiSenNoIro);
		DrawLine(geeziNoKawarime    , Y1, geeziNoKawarime    , 150, geeziNoKyoukaiSenNoIro);
		DrawLine(geeziNoKawarime - 1, Y1, geeziNoKawarime - 1, 150, geeziNoKyoukaiSenNoIro);
		DrawLine(geeziNoKawarime + 1, Y1, geeziNoKawarime + 1, 150, geeziNoKyoukaiSenNoIro);
		DrawLine(0    , Y1, 0    , 150, hidariNoSenNoIro);
		DrawLine(0 + 1, Y1, 0 + 1, 150, hidariNoSenNoIro);
		DrawLine(0 + 2, Y1, 0 + 2, 150, hidariNoSenNoIro);

		// 画面右の線の描画
		DrawLine(640 - 3, 0, 640 - 3, 480, migiNoSenNoIro);
		DrawLine(640 - 2, 0, 640 - 2, 480, migiNoSenNoIro);
		DrawLine(640 - 1, 0, 640 - 1, 480, migiNoSenNoIro);

		//Dに残り時間[分]を設定
		//D = C / 60;
		ScreenFlip(); //DX_SCREEN_BACKに描画した画像を表示します


	}

	DxLib_End(); // DXライブラリ使用の終了処理

	return 0; // ソフトの終了 
}
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

ノダッシー

Re: 意図した通りに音が鳴らない

#10

投稿記事 by ノダッシー » 10年前

みけCATさんありがとうございました!
仕様通りに動かす事ができましたが、自分の頭で理解する為にソースの解読をし勉強したいと思います

閉鎖

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