こんにちはゲストさん。会員登録(無料)して質問・回答してみよう!

締切り済みの質問

msgが定義されていない

Visual Studio2019でwindowsアプリケーションでゲームを作っているんですが、
どうやってもmsgが定義されていないが直りません。
#include <windows.h>

LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wp, LPARAM lp);

//WinMain関数
int WINAPI WinMain(HINSTANCE hCurInst, HINSTANCE hPrevInst,
LPSTR lpsCmdLine, int nCmdShow)
{
//ウィンドウクラスの登録
//メインウィンドウの生成
//メッセージループ
return (int)msg.wParam;

}

//ウィンドウプロシージャ
LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp)
{
switch (msg) {
//メッセージごとにやりたいことを記述する
}

return 0;


}
ご教示お願いします。

投稿日時 - 2020-04-26 21:35:51

QNo.9740696

困ってます

このQ&Aは役に立ちましたか?

0人が「このQ&Aが役に立った」と投票しています

回答(2)

ANo.2

>msgが定義されていない

定義されていませんねえ。

msg 変数がグローバルでない限り、WinMain 関数の中でまず、msgがどういう型の変数(または構造体・オブジェクト)なのか宣言しなければ、使えません。
グローバルであるならば、関数宣言の外側に msg の定義がなければ使えません。
(includeするファイル内で、グローバル変数宣言されてるとかなら使えますが)

WndProc 関数の方では、引数のところで UINT 型で渡されると定義されているので、使えますが。

--

きっとサンプルプログラムでは、WinMain関数本体の冒頭に、

HWND hwnd; //HWND型(構造体)の変数 hwnd を用意する
MSG msg; //MSG型(構造体)の変数 msg を用意する

というような宣言があったはずです。
これは省略してはいけないのです。

C言語(C++・C#)では、VBAなどと違って、使用する変数名やオブジェクトは、全て、宣言してからでなければ使えません。
iやsといった単純な変数でさえも、使用前に「int i;」「char s[100];」のように、この変数はどういう型であると明記しなければ、コンパイル時に「そんな変数は知らない(定義されていない)」と言われてしまいます。

C言語はそのように、人間的な融通のきかない言語ですので、一から十までやりたい事を教えこんで(記述して)やる必要があります。

投稿日時 - 2020-04-27 03:11:22

お礼

回答ありがとうございます。
なるほど、人の社会と当てはめれば確かにそうですね。
まぁ自分なりに、(趣味の範囲でも)これからも勉強していきます。

投稿日時 - 2020-04-27 09:37:18

//WinMain関数
int WINAPI WinMain(HINSTANCE hCurInst, HINSTANCE hPrevInst,
LPSTR lpsCmdLine, int nCmdShow)
{
//ウィンドウクラスの登録
//メインウィンドウの生成
//メッセージループ
return (int)msg.wParam; ←こいつの、出どころはどこ?

}
さらに言えば、ドットでつないでいるが、そもそもの型はなに?
ってのが、エラーとして出ているのではないかと。

投稿日時 - 2020-04-26 22:42:56

お礼

回答ありがとうございます。
猫でも解るゲームプログラミングの本を見て打ち込んでいたのですが、
よく見たらこれは、Windowsアプリケーションの骨格と書いてあります。
なのでこれだけでは動かないようですね。
CDドライブが壊れていて、サンプルを見れなかったのですが、
今見れて解決しました。
ソースだけ記述しておきます
// win01.cpp

#include <windows.h>

LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
ATOM InitApp(HINSTANCE);
BOOL InitInstance(HINSTANCE, int);

char szClassName[] = "win01";//ウィンドウクラス


int WINAPI WinMain(HINSTANCE hCurInst, HINSTANCE hPrevInst,
LPSTR lpsCmdLine, int nCmdShow)
{
MSG msg;
BOOL bRet;

if (!InitApp(hCurInst))
return FALSE;
if (!InitInstance(hCurInst, nCmdShow))
return FALSE;
while ((bRet = GetMessage(&msg, NULL, 0, 0)) != 0) {
if (bRet == -1) {
break;
} else {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int)msg.wParam;
}

//ウィンドウ・クラスの登録

ATOM InitApp(HINSTANCE hInst)
{
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)
{
HWND hWnd;

hWnd = CreateWindow(szClassName,
"猫でもわかるGameプログラミング", //タイトルバーにこの名前が表示されます
WS_OVERLAPPEDWINDOW, //ウィンドウの種類
CW_USEDEFAULT,//X座標
CW_USEDEFAULT,//Y座標
CW_USEDEFAULT,//幅
CW_USEDEFAULT,//高さ
NULL, //親ウィンドウのハンドル、親を作るときはNULL
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)
{
switch (msg) {
case WM_CLOSE:
DestroyWindow(hWnd);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return (DefWindowProc(hWnd, msg, wp, lp));
}
return 0;
}

ありがとうございました。

投稿日時 - 2020-04-26 23:19:14

あなたにオススメの質問