win32api複数のタイマーを同時に処理する方法とは?

このQ&Aのポイント
  • win32apiを使用して複数のタイマーを同時に処理する方法について教えてください。
  • タイマーを使ったアニメーションを実装している際に、SetTimer関数を使って複数のタイマーを同時に処理したいのですが、片方のタイマーしか処理されません。
  • タイマーの処理を同時に行うための解決方法を教えてください。
回答を見る
  • ベストアンサー

win32api複数のタイマーを同時に処理するには

いつもお世話になっています。 いま、タイマーを使ったアニメーションをやっているのですが、 SetTimer(VisualWnd,ID_YOKOUGOKI,200,NULL); SetTimer(VisualWnd,ID_MOJIOKURI,20,NULL); ようにすると、下のID_MOJIOKURIの部分しか処理されません。 case WM_TIMER: switch(wParam){ case ID_YOKOUGOKI: if(syouninkaiwa<13){ if(playeryoko==1){ playeryoko=2; }else if(playeryoko==2){ playeryoko=3; }else if(playeryoko==3){ playeryoko=4; }else if(playeryoko==4){ playeryoko=1; } if(syouninyoko==1){ syouninyoko=2; }else if(syouninyoko==2){ syouninyoko=3; }else if(syouninyoko==3){ syouninyoko=4; }else if(syouninyoko==4){ syouninyoko=1; } } break; case ID_MOJIOKURI: if(syouninkaiwa==1){ mojiokuri+=1; } break; } InvalidateRect(VisualWnd,NULL,FALSE); return 0; また描画処理は if(playeryoko==1){ BitBlt(hdcv, 250,132, 34, 32, memdc[50], 0, 0, SRCCOPY); }else if(playeryoko==2){ BitBlt(hdcv, 249,130, 34, 32, memdc[55], 0, 0, SRCCOPY); }else if(playeryoko==3){ BitBlt(hdcv, 250,132, 34, 32, memdc[50], 0, 0, SRCCOPY); }else if(playeryoko==4){ BitBlt(hdcv, 249,130, 34, 32, memdc[56], 0, 0, SRCCOPY); } if(syouninyoko==1){ BitBlt(hdcv, 220,130, 29, 32, memdc[51], 0, 0, SRCCOPY); }else if(syouninyoko==2){ BitBlt(hdcv, 220,130, 29, 32, memdc[57], 0, 0, SRCCOPY); }else if(syouninyoko==3){ BitBlt(hdcv, 220,130, 29, 32, memdc[51], 0, 0, SRCCOPY); }else if(syouninyoko==4){ BitBlt(hdcv, 220,130, 29, 32, memdc[58], 0, 0, SRCCOPY); } }else{ BitBlt(hdcv, 250,130, 34, 32, memdc[50], 0, 0, SRCCOPY); BitBlt(hdcv, 220,130, 29, 32, memdc[51], 0, 0, SRCCOPY); } SetTimer(VisualWnd,ID_YOKOUGOKI,200,NULL); SetTimer(VisualWnd,ID_MOJIOKURI,20,NULL); if(syouninkaiwa == 0){ TextOut(hdcv,350,350,TEXT("push Enter"),lstrlen(TEXT("push Enter"))); }else if(syouninkaiwa == 1){ if(mojiokuri==1){ wsprintf(TEXT1,L"○"); }else if(mojiokuri==2){ wsprintf(TEXT1,L"○○"); }else if(mojiokuri==3){ wsprintf(TEXT1,L"○○○"); }else if(mojiokuri==4){ wsprintf(TEXT1,L"○○○○"); }else if(mojiokuri==5){ wsprintf(TEXT1,L"○○○○○"); }else if(mojiokuri==6){ wsprintf(TEXT1,L"○○○○○○"); }else if(mojiokuri==7){ wsprintf(TEXT1,L"○○○○○○○"); }else if(mojiokuri==8){ wsprintf(TEXT1,L"近頃、冒険者が多"); } ・・・・・・・・・・・・・・・・・・・・ TextOut(hdcv,20,240,TEXT1,lstrlen(TEXT1));   というふうです。 どちらが悪いのか分かりません。 ちなみに、タイマーの時間を同じにしたら、同時にできましたが、両方の処理が遅くなりました。   どのように解決したらよいのか教えてください。お願いします。

質問者が選んだベストアンサー

  • ベストアンサー
  • axsies
  • ベストアンサー率64% (38/59)
回答No.1

コードから推察するに、原因は描画コード内のSetTimer関数の呼び出しだと思われます。 > SetTimer(VisualWnd,ID_YOKOUGOKI,200,NULL); > SetTimer(VisualWnd,ID_MOJIOKURI,20,NULL); まず、SetTimer関数(およびメッセージタイマー全体)の仕様を確認してください。 MSDN - SetTimer関数 http://msdn.microsoft.com/ja-jp/library/cc411200.aspx SetTimer関数を呼び出すとuElapse引数で与えられた間隔で、WM_TIMERイベントを送り続ける仕様です。 nIDEventで識別されるタイマーが既に設定されていた場合、タイマーはリセットされます。 描画コードがWM_PAINTメッセージで処理されると仮定すると、 WM_TIMER→InavlidateRect()→WM_PAINT送出→SetTimer()が呼び出され、どちらのタイマもリセットされる。 ID_MOJIOKURIのタイマの方がID_YOKOUGOKIより高頻度なため、 高確率でID_MOJIOKURIが処理されているように見える…のではないかと思います。 提示されたコードからの推測ですので、確証はありませんが。 コードを見る限り、描画コード中のSetTimer関数呼び出しは不要に思えます。 ひとまず、描画コード中のSetTimer関数呼び出しは削除し、 タイマが不要になったらKillTimer関数を呼び出すように変更してみてはいかがでしょうか。 また、蛇足ですがメッセージタイマは55ms程度の精度しかありません。 ID_MOJIOKURIで20msを指定されていますが、実際にはその間隔での処理は期待できません。 文字送りですので、特に問題ないと思いますけど。

crashbeen
質問者

お礼

回答ありがとうございました。 SetTimerをWM_CREATEでやったらできました。 詳しいご説明、本当にありがとうございました。

関連するQ&A

  • win32api 画面のちらつき

    win32api ビットマップを描画したとき、タイマーで少しずつ動かしているのですが、 画面がかなりちらつきます。   調べても、イマイチわからなくてどうすればいいかわかりません。 是非、わかりやすく教えていただきたいです。   タイマーの中身です。 ugokuはタイマーがあるかないかを判断するためにいれました。 なかなかいい方法が見つからなかったので。 playermukiはそのままです。 case WM_TIMER:  ugoku=1; if(playermuki==1){ playerX-=3; InvalidateRect(VisualWnd,NULL,TRUE); }else if(playermuki==2){ playerX+=3; InvalidateRect(VisualWnd,NULL,TRUE); }else if(playermuki==3){ playerY+=3; InvalidateRect(VisualWnd,NULL,TRUE); }else if(playermuki==4){ playerY-=3; InvalidateRect(VisualWnd,NULL,TRUE); } break; また、タイマーをセットするとき case WM_KEYDOWN: if(wParam==VK_RIGHT){ playermuki=1; if(ugoku==0){ SetTimer(VisualWnd,ID_T_UGOKI,50,NULL); } }else if(wParam==VK_LEFT){ playermuki=2; if(ugoku==0){ SetTimer(VisualWnd,ID_T_UGOKI,50,NULL); } }else if(wParam==VK_UP){ playermuki=3; if(ugoku==0){ SetTimer(VisualWnd,ID_T_UGOKI,50,NULL); } }else if(wParam==VK_DOWN){ playermuki=4; if(ugoku==0){ SetTimer(VisualWnd,ID_T_UGOKI,50,NULL); } } return 0; タイマーを切るとき case WM_KEYUP: if(wParam==VK_RIGHT){ KillTimer(VisualWnd,ID_T_UGOKI); ugoku=0; }else if(wParam==VK_LEFT){ KillTimer(VisualWnd,ID_T_UGOKI); ugoku=0; }else if(wParam==VK_UP){ KillTimer(VisualWnd,ID_T_UGOKI); ugoku=0; }else if(wParam==VK_DOWN){ KillTimer(VisualWnd,ID_T_UGOKI); ugoku=0; } return 0;

  • C言語で文字列バッファを消去する方法

    今、C言語とWin32 APIを使ってプログラミングをしています。 wsprintf(str,TEXT("プレイヤーの攻撃!")); TextOut(hdc,0,520,bstr,lstrlen(str)); if(ehp <= 0) {    wsprintf(str,TEXT("敵を倒しました"));    TextOut(hdc,0,520,bstr,lstrlen(str)); } このコードを実行すると、2回目のTextOutのところで 「敵をたおしました撃!」と出てしまいます。 きっとstrに以前の文字列が残っているからだと思いますが、 この保存した文字列を消去するにはどうしたらよいのでしょうか? for文でstr[0]から'\0'までナル文字を代入し続けたり、いろいろと試したのですが駄目でした。どうかこんな自分にご助力お願いできないでしょうか? どうかお願い致します。

  • BitBlt関数について

    お世話になっております。   またまた質問ですが、   画像を表示したいので、BitBlt関数を使ってみたんですが、   エラーもなく、実行できました。   しかし、画像が表示されません。   サイトや本を何回も見て、間違いがないか見たんですけど、間違いがまったく見当たりません。   LRESULT CALLBACK VisualProc ( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) { switch(uMsg) { case WM_CREATE: memdc = CreateCompatibleDC( NULL ); hBitmap = ( HBITMAP )LoadImage( NULL , TEXT("player.bmp") , IMAGE_BITMAP , 0 , 0 , LR_LOADFROMFILE | LR_CREATEDIBSECTION ); SelectObject(memdc, hBitmap); return 0; case WM_PAINT: hdc = BeginPaint(VisualWnd,&ps); BitBlt(hdc, 30,30, 34, 32, memdc, 0, 0, SRCCOPY); EndPaint(VisualWnd,&ps); return 0; .............................................................................. 画像は、リソースで追加→既存の項目→ピクチャ でやりました。 それで、ピクチャからプロジェクトのファイルに移動させました。   それでもできません。     一体どのようにやればいいのでしょうか。 わかりやすく教えてください。

  • Win32APIでアイコンファイルを表示したいのですが。

    いつもお世話になっております。 小生、只今WindowsXPSP3上でC言語とWin32APIを使い、BCC5.5.1でコンパイルしながらWindowsプログラミングを勉強しています。 度々の質問で申し訳ございませんが、 今回、アイコンをビットマップと同じ様にクライアント領域に描画しようと思っているのですが、うまく行きません。。。 コードは以下の様になっております。 #include <windows.h> #define BUFSIZ 1024 LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); ATOM InitApp(HINSTANCE, LPCSTR); BOOL InitInstance(HINSTANCE, int, LPCSTR); int WINAPI WinMain( HINSTANCE hCurInst, HINSTANCE hPrevInst, LPSTR lpsCmdLine, int nCmdShow) { MSG msg; BOOL bRet; LPCSTR szClassName = "アイコンを読み込む"; if(!InitApp(hCurInst, szClassName)){ return FALSE; } if(!InitInstance(hCurInst, nCmdShow, szClassName)){ return FALSE; } while((bRet = GetMessage(&msg, NULL, 0, 0)) != 0){ if(bRet == -1){ MessageBox(NULL, "GetMessage Error", "Error", MB_OK); break; } else{ TranslateMessage(&msg); DispatchMessage(&msg); } } return (int)msg.wParam; } //ウィンドウクラスの登録 ATOM InitApp(HINSTANCE hInst, LPCSTR szClassName) { WNDCLASSEX wc; wc.cbSize = sizeof(WNDCLASSEX); wc.style = CS_HREDRAW | CS_VREDRAW; wc.lpfnWndProc = WndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInst; wc.hIcon = (HICON)LoadImage( NULL, MAKEINTRESOURCE(IDI_APPLICATION), IMAGE_ICON, 0, 0, LR_DEFAULTSIZE | LR_SHARED); wc.hCursor = (HCURSOR)LoadImage( NULL, MAKEINTRESOURCE(IDC_ARROW), IMAGE_CURSOR, 0, 0, LR_DEFAULTSIZE | LR_SHARED); wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH); wc.lpszMenuName = NULL; wc.lpszClassName = (LPCSTR)szClassName; wc.hIconSm = (HICON)LoadImage( NULL, MAKEINTRESOURCE(IDI_APPLICATION), IMAGE_ICON, 0, 0, LR_DEFAULTSIZE | LR_SHARED); return (RegisterClassEx(&wc)); } //ウィンドウの生成 BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName) { HWND hWnd; hWnd = CreateWindow( szClassName, "Window", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, NULL, hInst, NULL); if(!hWnd){ return FALSE; } ShowWindow(hWnd, nCmdShow); UpdateWindow(hWnd); return TRUE; } //ウィンドウプロシージャ LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp) { //デバイスコンテキスト HDC hdc; //メモリデバイスコンテキスト static HDC memDC; //画像(アイコン)を扱う変数 static HICON hIcon; //画像情報(アイコン)を扱う変数 static BITMAP bmp; static ICONINFO ici = {TRUE}; //アイコンの幅、高さを格納する変数、バッファ static int x, y; //描画情報を格納する構造体 PAINTSTRUCT ps; switch(msg){ case WM_CREATE: memDC = CreateCompatibleDC(NULL); hIcon = (HICON)LoadImage( NULL, "Linux.ico", IMAGE_ICON, 0, 0, LR_LOADFROMFILE); if(hIcon == NULL){ MessageBox(hWnd, "It failed in reading the icon file.", "Error", MB_OK | MB_ICONWARNING); return 0; } GetIconInfo(hIcon, &ici); GetObject(ici.hbmColor, sizeof(bmp), &bmp); x = bmp.bmWidth; y = bmp.bmHeight; SelectObject(memDC, hIcon); break; case WM_PAINT: hdc = BeginPaint(hWnd, &ps); BitBlt(hdc, 0, 0, x, y, memDC, 0, 0, SRCCOPY); EndPaint(hWnd, &ps); break; case WM_DESTROY: DeleteDC(memDC); DeleteObject(hIcon); PostQuitMessage(0); break; default: return (DefWindowProc(hWnd, msg, wp, lp)); } return 0; } 以上です。 本当に度々の質問で申し訳ございませんが、 お忙しい中、申し訳ございませんが、 先輩方、アドバイス宜しくお願いします。

  • 猫でもわかるWindowsプログラミングの5.2タイピングソフトのプログラムについて

    猫でもわかるWindowsプログラミング第3版の5.2タイピングソフトのプログラムなのですが、 本のプログラムをそのまま書くと、タイプミス!の分岐にはいらないんですが、これは本が間違ってるんでしょうか? 付属のCD-ROMのプログラム(本の方とは少し違う)は正しく動いているようですが、 本に書いてある方がなぜ上手くいかないのかが理解できません。 もし本が間違えているなら、どこが間違っているのか教えていただけると助かります。 下のコードは本に書いてあった方のウィンドウプロージャ部を写したものです。 LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp) { HDC hdc; PAINTSTRUCT ps; MMTIME mm; switch (msg) { case WM_CREATE: srand((unsigned)time(NULL)); break; case WM_PAINT: hdc = BeginPaint(hWnd, &ps); TextOut(hdc, 0, 0, szMondai, lstrlen(szMondai)); TextOut(hdc, 0, 40, szInput, lstrlen(szInput)); if(bSeikai) SetTextColor(hdc, RGB(0,0,0)); else SetTextColor(hdc, RGB(255,0,0)); TextOut(hdc,0,80,szCheck,lstrlen(szCheck)); EndPaint(hWnd, &ps); break; case WM_CHAR: if(wp == VK_SPACE && !bStart) { bStart = TRUE; TypeStart(hWnd); break; } if(bStart == FALSE) return DefWindowProc(hWnd, msg, wp, lp); if(wp == VK_ESCAPE) { lstrcpy(szMondai, TEXT("")); lstrcpy(szInput, TEXT("")); lstrcpy(szCheck, TEXT("")); InvalidateRect(hWnd, NULL, TRUE); bStart = FALSE; break; } wsprintf(szInput, TEXT("あなたの入力=\"%c\""), (int)wp); if(szMondai[6] == szInput[14]) { bSeikai = TRUE; mm.wType = TIME_MS; timeGetSystemTime(&mm, sizeof(MMTIME)); dwEnd = mm.u.ms; wsprintf(szCheck, TEXT("反応時間[%dミリ秒]"), dwEnd - dwStart); TypeStart(hWnd); } else { bSeikai = FALSE; MessageBeep(MB_OK); lstrcpy(szCheck, TEXT("タイプミス!")); } InvalidateRect(hWnd, NULL, TRUE); break; case WM_DESTROY: PostQuitMessage(0); break; default: return (DefWindowProc(hWnd, msg, wp,lp)); } return 0; } int TypeStart(HWND hWnd) { int n; MMTIME mm; n = rand() % 26; wsprintf(szMondai, TEXT("問題=\"%c\""), 'a' + n); mm.wType = TIME_MS; timeGetSystemTime(&mm, sizeof(MMTIME)); dwStart = mm.u.ms; InvalidateRect(hWnd, NULL, TRUE); return 0; }

  • (SHORT)

    ウインドウプロシージャ内ですが、(SHORT)は何のためについているんでしょうか?(どんな効果がありますか) 教えてください。 case WM_MOUSEWHEEL :     wsprintf(str,TEXT("WHEEL %s"),        ((SHORT)HIWORD(wparam))>0 ? TEXT("↑"):TEXT("↓"));     hdc=GetDC(hwnd);     TextOut(hdc,0,0,str,lstrlen(str));

  • ビットマップ表示とSetTimer関数を同居させる方法

    ビットマップ表示とSetTimer関数を同居させる方法 現在、vc++2005を使用して、簡易的なGUIアプリケーションを作成しようとしているのですが、自分では解決ができない問題が発生してしまったので、質問させていただきます。 それはビットマップ表示とSetTimer関数を同居させる方法についてです。 ビットマップを読み込んで表示させる機能を追加してから、SetTimer関数が反応しなくなってしまい困っています。 ちなみにビットマップ表示の機能を追加する前まではSetTimer関数が正常に機能していました。 ウィンドウのハンドルhWndが何か関係しているのかと思ったのですが、解決方法がわからず・・・・・・ ご存知の方がいらっしゃましたら御教授いただけると幸いです。 ↓ ソースの一部です case WM_CREATE: //ビットマップファイル読み込み + 表示の準備 static HBITMAP hbitmap,prebitmap; static HDC hDC, hcomDC;      hbitmap = (HBITMAP)LoadImage(NULL,_T("kouen.bmp"),IMAGE_BITMAP,0,0, LR_LOADFROMFILE); if( hbitmap == NULL ) { MessageBox(hWnd, _T("ビットマップのロードに失敗しました"), _T("エラー"),MB_OK | MB_ICONWARNING); return 0; } hDC =GetDC(hWnd); hcomDC =CreateCompatibleDC(hDC); prebitmap= (HBITMAP)SelectObject(hcomDC,hbitmap);            (中略) break;                     case WM_LBUTTONDOWN: //2連続のシングルクリック防止 EnableWindow(hWnd,FALSE); SetTimer(hWnd, ID_TIMER1, 500, NULL); ← これが機能していない          (中略) break; case WM_PAINT: BitBlt( hDC, 0, 0, 1024, 690, hcomDC, 0, 0, SRCCOPY ); break; case WM_TIMER://機能しなくなってしまった部分 if(wParam==ID_TIMER1){ KillTimer(hWnd,ID_TIMER1); EnableWindow(hWnd,TRUE); }

  • Win32APIによるタイマイベントの種類について。

    小生、只今WindowsXPSP3上でC言語とWin32APIを使用し、BCC5.5.1でコンパイルしながら、Windowsプログラミングを勉強しています。 そこで質問なのですが、 「猫でもわかるWindowsプログラミング第2版」にて、 デジタル時計の実践という章があり、そこで下記のようなコメントの付いたコードがありました。 switch(msg){ case WM_CREATE: //タイマの作成 SetTimer(hWnd, ID_MYTIMER, 500, NULL); break; case WM_TIMER: //関係ないタイマイベントはDefWindowProcに任せる if(wp != ID_MYTIMER){ return (DefWindowProc(hWnd, msg, wp, lp)); } 上記の関係ないタイマイベントとは具体的にどのような種類があるんでしょうか。 お忙しい中、申し訳ございませんが、先輩方アドバイス宜しくお願いします。

  • Win32APIにて、簡易タイピングソフトを作成したのですが、うまく実行されません。

    いつもお世話になっております。 小生、只今、WinXPSP3上でC言語とWin32APIを使用し、BCC5.5.1でコンパイルしながらWindowsプログラミングを勉強しています。 今回、質問させて頂きたいのは、「猫でもわかるWindowsプログラミング第2版」の第5章簡易タイピングソフトを作るの回で、掲載されてあったコードを自分なりに改造して、実行してみたのですが、ウィンドウが起動しても、真っ白の状態でタイピングの問題が出題されないようになってしまいました。 以下にコードを掲載致します。 ※文字数制限にひっかかったので、改造した部分だけを掲載させて頂きます。 #include <windows.h> #include <time.h> #pragma comment(lib, "winmm.lib") LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); ATOM InitApp(HINSTANCE, LPCSTR); BOOL InitInstance(HINSTANCE, int, LPCSTR); DWORD TypeStart(HWND, char*); //ウィンドウの生成 BOOL InitInstance(HINSTANCE hInst, int nCmdShow, LPCSTR szClassName) { HWND hWnd; hWnd = CreateWindow( szClassName, "EasyTyping", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, 200, 200, NULL, NULL, hInst, NULL); if(!hWnd){ return FALSE; } ShowWindow(hWnd, nCmdShow); UpdateWindow(hWnd); return TRUE; } //ウィンドウプロシージャ LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp) { HDC hdc; PAINTSTRUCT ps; MMTIME mm; char szMondai[32] = {0}; char szInput[32] = {0}; char szCheck[32] = {0}; DWORD dwStart, dwEnd; BOOL bStart = FALSE, bSeikai = TRUE; switch(msg){ case WM_CREATE: srand((unsigned)time(NULL)); break; case WM_PAINT: hdc = BeginPaint(hWnd, &ps); TextOut(hdc, 0, 0, szMondai, (int)strlen(szMondai)); TextOut(hdc, 0, 40, szInput, (int)strlen(szInput)); if(bSeikai == TRUE){ SetTextColor(hdc, RGB(0, 0, 0)); } else{ SetTextColor(hdc, RGB(255, 0, 0)); } TextOut(hdc, 0, 80, szCheck, (int)strlen(szCheck)); EndPaint(hWnd, &ps); break; case WM_CHAR: if(wp == VK_SPACE && !bStart){ bStart = TRUE; dwStart = TypeStart(hWnd, szMondai); break; } if(bStart == FALSE){ return DefWindowProc(hWnd, msg, wp, lp); } if(wp == VK_ESCAPE){ strcpy(szMondai, ""); strcpy(szInput, ""); strcpy(szCheck, ""); InvalidateRect(hWnd, NULL, TRUE); bStart = FALSE; break; } wsprintf(szInput, "あなたの入力 = \"%c\"", (int)wp); if(szMondai[6] == szInput[14]){ bSeikai = TRUE; mm.wType = TIME_MS; timeGetSystemTime(&mm, sizeof(MMTIME)); dwEnd = mm.u.ms; wsprintf(szCheck, "反応時間[%dミリ秒]", dwEnd - dwStart); dwStart = TypeStart(hWnd, szMondai); } else{ bSeikai = FALSE; MessageBeep(MB_OK); strcpy(szCheck, "タイプミス!"); } InvalidateRect(hWnd, NULL, TRUE); break; case WM_DESTROY: PostQuitMessage(0); break; default: return DefWindowProc(hWnd, msg, wp, lp); } return 0; } DWORD TypeStart(HWND hWnd, char *p_szMondai) { int n; MMTIME mm; n = rand() % 26; wsprintf(p_szMondai, "問題 = \"%c\"", 'a' + n); mm.wType = TIME_MS; timeGetSystemTime(&mm, sizeof(MMTIME)); InvalidateRect(hWnd, NULL, TRUE); return mm.u.ms; } #endif 以上です。 掲載されているコードは余りにもグローバル変数が多く、 自分自身余り、グローバル変数は好きではないので、関数内で収まるようにと改造したのですが。。。 お忙しい中、申し訳ございませんが、先輩方、アドバイス宜しくお願い致します。

  • C++ 音のリアルタイム処理

    音ゲーを作っているのですが音をリアルタイム(実際には違いますが。)で処理をしたいのにうまくいきません。エラーはないのですが音が出なくて困っています。よろしかったら助けてください。 以下が主要部分です。 波形データを決められた時間ごとに加工して出力するプログラム。 case WM_CREATE:  SetTimer(hWnd, ID_MYTIMER, 500, NULL);  //500msecで更新  フォーマットの宣言 ~ ~ waveOutOpen(&hWaveOut1,WAVE_MAPPER,&wfe1,0,0,CALLBACK_NULL); Wave=(short*)calloc(wfe.nAvgBytesPerSec,10); whdr.lpData=(LPSTR)Wave; whdr.dwBufferLength=wfe.nAvgBytesPerSec * 10; whdr.dwFlags=WHDR_BEGINLOOP | WHDR_ENDLOOP; whdr.dwLoops=1; break; case WM_TIMER: if (wp != ID_MYTIMER) return DefWindowProc(hWnd, msg, wp, lp); if(a<20){//あらかじめ宣言された変数 初期値0 for(int l*X=0;l<X(a+1)*0.5;l++){ //0.5秒ごとに更新 Xサンプリング周波数 Wave[2*l ]=sound[i]*G; Wave[2*l+1]=sound[i]*G;//データ書き込み  a++;  }else{  Wave[2*l ]=0; Wave[2*l+1]=0;//データ書き込み  } waveOutPrepareHeader(hWaveOut,&whdr,sizeof(WAVEHDR)); waveOutWrite(hWaveOut,&whdr,sizeof(WAVEHDR)); InvalidateRect(hWnd, NULL, FALSE); break;