I. Introduction▲
Code d'un démineur en pure Windows API.
II. Code complet▲
Sélectionnez
#include <windows.h>
#include <time.h>
#include <stdio.h>
#define LARG 32
#define NBC_X 16
#define NBC_Y 12
#define NB_MINE 20
/* ID de menu */
#define IDM_QUIT 1
#define IDM_NEW 2
#define IDM_ABOUT 3
#define GET_X_LPARAM(lp) ((int)(short)LOWORD(lp))
#define GET_Y_LPARAM(lp) ((int)(short)HIWORD(lp))
HINSTANCE hinst;
LRESULT CALLBACK MainWndProc
(
HWND, UINT, WPARAM, LPARAM);
int
Demine
(
int
tab[NBC_Y][NBC_X], int
y, int
x);
int
WINAPI WinMain
(
HINSTANCE hinstance, HINSTANCE hPrevInstance,
LPSTR lpCmdLine, int
nCmdShow)
{
HWND hwnd;
MSG msg;
WNDCLASS wc;
HMENU hMenu, hSousMenu;
RECT winRect;
hinst =
hinstance;
wc.style =
0
;
wc.lpfnWndProc =
MainWndProc;
wc.cbClsExtra =
0
;
wc.cbWndExtra =
0
;
wc.hInstance =
hinstance;
wc.hIcon =
LoadIcon
(
NULL
, IDI_APPLICATION);
wc.hCursor =
LoadCursor
(
NULL
, IDC_ARROW);
wc.hbrBackground =
(
HBRUSH)(
COLOR_WINDOW+
1
);
wc.lpszMenuName =
NULL
;
wc.lpszClassName =
"
MaWinClass
"
;
if
(!
RegisterClass
(&
wc)) return
FALSE;
hSousMenu =
CreateMenu
(
);
AppendMenu
(
hSousMenu, MF_STRING, IDM_NEW, "
Nouvelle partie
"
);
AppendMenu
(
hSousMenu, MF_MENUBREAK, -
1
, NULL
);
AppendMenu
(
hSousMenu, MF_STRING, IDM_ABOUT, "
A propos
"
);
AppendMenu
(
hSousMenu, MF_STRING, IDM_QUIT, "
Quitter
"
);
hMenu =
CreateMenu
(
);
AppendMenu
(
hMenu,MF_POPUP,(
UINT)hSousMenu,"
Fichier
"
);
SetRect
(&
winRect, 0
, 0
, LARG*
NBC_X, LARG*
NBC_Y);
AdjustWindowRect
(&
winRect, WS_CAPTION, TRUE);
hwnd =
CreateWindow
(
"
MaWinClass
"
, "
DMine
"
,
WS_SYSMENU |
WS_CAPTION |
WS_MINIMIZEBOX, CW_USEDEFAULT, CW_USEDEFAULT,
winRect.right-
winRect.left, winRect.bottom-
winRect.top,
NULL
, hMenu, hinstance, NULL
);
if
(!
hwnd) return
FALSE;
ShowWindow
(
hwnd, nCmdShow);
UpdateWindow
(
hwnd);
while
(
GetMessage
(&
msg, NULL
, 0
, 0
))
{
TranslateMessage
(&
msg);
DispatchMessage
(&
msg);
}
return
msg.wParam;
}
/**
***************************************************************************
*/
int
Demine
(
int
tab[NBC_Y][NBC_X], int
y, int
x)
{
if
(
tab[y][x]&
0x00010000
) tab[y][x]=
tab[y][x]&
0xFFFEFFFF
;
else
return
0
;
if
(
tab[y][x]&
0x100
) return
1
; /* Si mine --> Perdu */
if
(
tab[y][x]&
0x0000000F
) return
0
; /* case comporte un nb */
if
(
y!=
0
&&
x!=
0
) Demine
(
tab, y-
1
, x-
1
); /* traitement des cases adjacentes */
if
(
y!=
0
) Demine
(
tab, y-
1
, x);
if
(
y!=
0
&&
x!=
NBC_X-
1
) Demine
(
tab, y-
1
, x+
1
);
if
(
x!=
0
) Demine
(
tab, y, x-
1
);
if
(
x!=
NBC_X-
1
) Demine
(
tab, y, x+
1
);
if
(
y!=
NBC_Y-
1
&&
x!=
0
) Demine
(
tab, y+
1
, x-
1
);
if
(
y!=
NBC_Y-
1
) Demine
(
tab, y+
1
, x);
if
(
y!=
NBC_Y-
1
&&
x!=
NBC_X-
1
) Demine
(
tab, y+
1
, x+
1
);
return
0
;
}
/**
***************************************************************************
*/
void
Showtab
(
int
tab[NBC_Y][NBC_X])
{
int
x, y;
for
(
y=
0
; y<
NBC_Y; y++
)
for
(
x=
0
; x<
NBC_X; x++
)
{
tab[y][x]=
tab[y][x]&
0xFFFEFFFF
;
}
}
/**
***************************************************************************
*/
int
Test
(
int
tab[NBC_Y][NBC_X])
{
int
x, y;
int
result =
1
;
for
(
y=
0
; y<
NBC_Y; y++
)
for
(
x=
0
; x<
NBC_X; x++
)
{
if
(
tab[y][x]&
0x00010000
&&
!(
tab[y][x]&
0x00000100
)) result=
0
;
}
return
result;
}
/**
***************************************************************************
*/
void
Init
(
int
tab[NBC_Y][NBC_X])
{
int
x, y;
for
(
x=
0
; x<
NB_MINE; x++
) /* Pose les mines */
{
int
mineX, mineY;
mineX =
rand
(
)%
NBC_X;
mineY =
rand
(
)%
NBC_Y;
if
(
tab[mineY][mineX]&
0x100
) x--
;
else
tab[mineY][mineX] =
0x100
;
}
for
(
y=
0
; y<
NBC_Y; y++
) /* Init les cases */
for
(
x=
0
; x<
NBC_X; x++
)
{
if
(
tab[y][x]&
0x100
)
{
if
(
y!=
0
&&
x!=
0
) tab[y-
1
][x-
1
]++
;
if
(
y!=
0
) tab[y-
1
][x]++
;
if
(
y!=
0
&&
x!=
NBC_X-
1
) tab[y-
1
][x+
1
]++
;
if
(
x!=
0
) tab[y][x-
1
]++
;
if
(
x!=
NBC_X-
1
) tab[y][x+
1
]++
;
if
(
y!=
NBC_Y-
1
&&
x!=
0
) tab[y+
1
][x-
1
]++
;
if
(
y!=
NBC_Y-
1
) tab[y+
1
][x]++
;
if
(
y!=
NBC_Y-
1
&&
x!=
NBC_X-
1
) tab[y+
1
][x+
1
]++
;
}
tab[y][x]=
tab[y][x]|
0x00010000
;
}
}
/**
***************************************************************************
*/
LRESULT CALLBACK MainWndProc
(
HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
static
int
tab[NBC_Y][NBC_X];
static
int
end;
switch
(
uMsg)
{
case
WM_CREATE:
srand
((
unsigned
int
)time
(
0
));
Init
(
tab);
return
0
;
case
WM_COMMAND:
if
(
LOWORD
(
wParam) ==
IDM_QUIT) PostMessage
(
hwnd, WM_CLOSE,0
,0
);
if
(
LOWORD
(
wParam) ==
IDM_ABOUT)
MessageBox
(
NULL
, "
Démineur code de CGi !
"
, "
A Propos !
"
, MB_OK);
if
(
LOWORD
(
wParam) ==
IDM_NEW)
{
ZeroMemory
(
tab, sizeof
(
tab));
Init
(
tab);
end=
0
;
InvalidateRect
(
hwnd, NULL
, FALSE);
}
return
0
;
case
WM_LBUTTONUP:
{
int
x, y;
int
xPos =
GET_X_LPARAM
(
lParam);
int
yPos =
GET_Y_LPARAM
(
lParam);
if
(
end) return
0
;
x =
xPos/
LARG;
y =
yPos/
LARG;
InvalidateRect
(
hwnd, NULL
, FALSE);
if
(
y<
NBC_Y &&
x<
NBC_X &&
Demine
(
tab, y, x))
{
Showtab
(
tab);
MessageBox
(
NULL
, "
Désolé ! Vous avez Perdu !
"
, "
DMine
"
, MB_OK);
end=
1
;
}
else
if
(
Test
(
tab))
{
MessageBox
(
NULL
, "
Bravo ! Vous avez Gagné !
"
, "
DMine
"
, MB_OK);
end=
1
;
}
return
0
;
}
case
WM_PAINT:
{
int
i, j;
HPEN hpen;
HDC hdc, hdcDB;
HBITMAP bmDB;
HGDIOBJ hobjold;
PAINTSTRUCT ps;
RECT rect, caserect;
HBRUSH hbcase =
CreateSolidBrush
(
0x00FF8080
);
hpen =
CreatePen
(
PS_SOLID, 1
, 0x00AFAFAF
);
GetClientRect
(
hwnd, &
rect);
hdc =
BeginPaint
(
hwnd, &
ps);
hdcDB =
CreateCompatibleDC
(
hdc);
bmDB =
CreateCompatibleBitmap
(
hdc, rect.right, rect.bottom);
hobjold =
SelectObject
(
hdcDB, bmDB);
SelectObject
(
hdcDB,hpen);
FillRect
(
hdcDB, &
rect, (
HBRUSH)(
COLOR_3DFACE+
1
));
for
(
j=
0
; j<
NBC_Y; j++
)
for
(
i=
0
; i<
NBC_X; i++
)
{
int
value =
tab[j][i];
caserect.left =
i*
LARG+
1
;
caserect.right =
i*
LARG+
LARG;
caserect.top =
j*
LARG+
1
;
caserect.bottom =
j*
LARG+
LARG;
Rectangle
(
hdcDB, i*
LARG+
0
, j*
LARG+
0
,
i*
LARG+
LARG+
1
, j*
LARG+
LARG+
1
);
SetTextColor
(
hdcDB,0x00000000
);
if
(
value&
0x100
) /* mine */
DrawText
(
hdcDB,"
M
"
,1
,&
caserect,
DT_CENTER |
DT_VCENTER |
DT_SINGLELINE);
if
(
value>
0
&&
value<
9
) /* les nombres */
{
char
st[16
];
sprintf
(
st, "
%i
"
, value);
if
(
value==
1
) SetTextColor
(
hdcDB,0x00FF0000
);
if
(
value==
2
) SetTextColor
(
hdcDB,0x00008F00
);
if
(
value==
3
) SetTextColor
(
hdcDB,0x000000FF
);
if
(
value>=
4
) SetTextColor
(
hdcDB,0x00FF00FF
);
DrawText
(
hdcDB, st, 1
, &
caserect,
DT_CENTER |
DT_VCENTER |
DT_SINGLELINE);
}
if
(
value&
0x00010000
) /* cache les cases */
{
caserect.left++
;
caserect.right--
;
caserect.top++
;
caserect.bottom--
;
FillRect
(
hdcDB, &
caserect, hbcase);
}
}
BitBlt
(
hdc, 0
, 0
, rect.right, rect.bottom, hdcDB, 0
, 0
, SRCCOPY);
DeleteDC
(
hdcDB);
DeleteObject
(
bmDB);
EndPaint
(
hwnd, &
ps);
DeleteObject
(
hbcase);
DeleteObject
(
hpen);
return
0
;
}
case
WM_DESTROY:
PostQuitMessage
(
0
);
return
0
;
default
:
return
DefWindowProc
(
hwnd, uMsg, wParam, lParam);
}
}
À vos compilateurs.