/*   ブロック崩し>ボールの移動処理 1999/ 3/27 宍戸 輝光 */ #include LRESULT CALLBACK WndProc (HWND, UINT, WPARAM, LPARAM); void draw(void); LPBYTE lpBuf,lpScreen,lpChr[5]; LPBITMAPINFO lpDIB; LPRGBQUAD lpRGB; HDC hdcWin; HWND hwMain; BYTE map[16][16]; DWORD dwTime,dwPreTime; int iX=7,iY=1,iBx=7,iBy=3,iDBx=1,iDBy=1; int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR szCmdLine, int iCmdShow){ MSG msg; WNDCLASSEX wndclass ; int i,j; wndclass.cbSize = sizeof(wndclass); wndclass.style = CS_HREDRAW | CS_VREDRAW; wndclass.lpfnWndProc = WndProc; wndclass.cbClsExtra = 0; wndclass.cbWndExtra = 0; wndclass.hInstance = hInstance; wndclass.hIcon = NULL; wndclass.hCursor = LoadCursor(NULL,IDC_ARROW); wndclass.hbrBackground = (HBRUSH)GetStockObject(LTGRAY_BRUSH); wndclass.lpszMenuName = NULL; wndclass.lpszClassName = "CWindow"; wndclass.hIconSm = NULL; RegisterClassEx (&wndclass); hwMain=CreateWindow ("CWindow",NULL, WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,CW_USEDEFAULT,600,560, NULL,NULL,hInstance,NULL); lpBuf=(LPBYTE)GlobalAlloc /* バッファ用メモリ確保 */ (GPTR,sizeof(BITMAPINFO)+255*sizeof(RGBQUAD)+512*512+32*32*5); lpDIB=(LPBITMAPINFO)lpBuf; /* バッファ用メモリを分配 */ lpRGB=(RGBQUAD*)(lpBuf+sizeof(BITMAPINFOHEADER)); lpScreen=lpBuf+sizeof(BITMAPINFO)+255*sizeof(RGBQUAD); for (i=0;i<5;i++) /* キャラクタ用ビットマップ配列 */ lpChr[i]=lpScreen+512*512+32*32*i; lpDIB->bmiHeader.biSize=sizeof(BITMAPINFOHEADER); /* BITMAPINFO構造体 */ lpDIB->bmiHeader.biWidth=512; lpDIB->bmiHeader.biHeight=512; lpDIB->bmiHeader.biPlanes=1; lpDIB->bmiHeader.biBitCount=8; lpDIB->bmiHeader.biCompression=BI_RGB; lpDIB->bmiHeader.biSizeImage=0; lpDIB->bmiHeader.biXPelsPerMeter=0; lpDIB->bmiHeader.biYPelsPerMeter=0; lpDIB->bmiHeader.biClrUsed=0; lpDIB->bmiHeader.biClrImportant=0; lpDIB->bmiColors[0]=lpRGB[0]; /* カラーテーブルの先頭 */ lpRGB[0].rgbRed=0; lpRGB[0].rgbGreen=0; lpRGB[0].rgbBlue=0; lpRGB[1].rgbRed=128; lpRGB[1].rgbGreen=128; lpRGB[1].rgbBlue=128; lpRGB[2].rgbRed=192; lpRGB[2].rgbGreen=192; lpRGB[2].rgbBlue=192; lpRGB[3].rgbRed=240; lpRGB[3].rgbGreen=240; lpRGB[3].rgbBlue=255; lpRGB[4].rgbRed=160; lpRGB[4].rgbGreen=128; lpRGB[4].rgbBlue=255; lpRGB[5].rgbRed=192; lpRGB[5].rgbGreen=255; lpRGB[5].rgbBlue=240; lpRGB[6].rgbRed=255; lpRGB[6].rgbGreen=128; lpRGB[6].rgbBlue=128; FillMemory(lpChr[0],1024,1); /* キャラクター0(タイル) */ for(i=0;i<4;i++) FillMemory(lpChr[0]+i*256,32,0); for (i=0;i<8;i++) { *(lpChr[0]+i*32+4)=0; *(lpChr[0]+i*32+20)=0; *(lpChr[0]+(i+16)*32+4)=0; *(lpChr[0]+(i+16)*32+20)=0; *(lpChr[0]+(i+8)*32+12)=0; *(lpChr[0]+(i+8)*32+28)=0; *(lpChr[0]+(i+24)*32+12)=0; *(lpChr[0]+(i+24)*32+28)=0; } FillMemory(lpChr[1],1024,2); /* キャラクター1(ブロック) */ for (i=1;i<31;i++) FillMemory(lpChr[1]+i*32+1,30,4); FillMemory(lpChr[2],1024,3); /* キャラクター2(壁) */ FillMemory(lpChr[3],1024,0); /* キャラクター3(自機) */ for (i=1;i<31;i++) FillMemory(lpChr[3]+i*32+1,30,5); CopyMemory(lpChr[4],lpChr[0],32*32); for (i=2;i<16;i++) /* キャラクター4(ボール)*/ FillMemory(lpChr[4]+i*32+16-i,i*2,6); for (i=16;i<30;i++) FillMemory(lpChr[4]+i*32+(i-14),32-(i-14)*2,6); ShowWindow (hwMain,iCmdShow); // ウインドウを表示 UpdateWindow (hwMain); /* 画面情報配列初期化 */ FillMemory(map[0],256,2); /* 全体を壁で塗りつぶす */ for (i=1;i<15;i++) /* ブロックとタイル配置 */ for (j=1;j<15;j++) if (i<9) map[j][i]=0; else map[j][i]=1; map[iX][iY]=3; /* 自機の初期位置 */ map[iBx][iBy]=4; /* ボールの初期位置 */ dwTime=GetTickCount(); while (1) { /* メインループ */ if (PeekMessage (&msg,NULL,0,0,PM_NOREMOVE)) { if (!GetMessage (&msg,NULL,0,0)) // メッセージ処理 return msg.wParam ; TranslateMessage(&msg); DispatchMessage(&msg); } else draw(); // 描画処理 } } void draw(void) { int i,j,k; if (GetTickCount()>dwTime+80) dwTime=GetTickCount(); else /* 前回の処理から80ms 以上経ってなければ戻る */ return; for (i=0;i<16;i++) /* マップ情報で画面作成 */ for (j=0;j<16;j++) for (k=0;k<32;k++) CopyMemory(lpScreen+j*32+(k+i*32)*512,lpChr[map[j][i]]+k*32,32); /* 自機の移動 */ if (GetAsyncKeyState(VK_RIGHT)<0 && map[iX+1][iY]==0) { /* 右方向 */ map[iX][iY]=0; /* 現在の座標をクリア */ map[++iX][iY]=3; /* 新しい座標を設定 */ } if (GetAsyncKeyState(VK_LEFT)<0 && map[iX-1][iY]==0) { /* 左方向 */ map[iX][iY]=0; /* 現在の座標をクリア */ map[--iX][iY]=3; /* 新しい座標を設定 */ } if (map[iBx+iDBx][iBy]==1) { /* 水平方向のブロック壁判定 */ map[iBx+iDBx][iBy]=0; iDBx=-iDBx; } else if (map[iBx][iBy+iDBy]==1) { /* 垂直方向のブロック壁判定 */ map[iBx][iBy+iDBy]=0; iDBy=-iDBy; } else if (map[iBx+iDBx][iBy+iDBy]==1) { /* ブロックの角判定 */ map[iBx+iDBx][iBy+iDBy]=0; iDBx=-iDBx; iDBy=-iDBy; } if (map[iBx+iDBx][iBy]>1 && map[iBx][iBy+iDBy]==0) { /* 自機・壁判定 */ iDBx=-iDBx; } else if (map[iBx][iBy+iDBy]>1 && map[iBx+iDBx][iBy]==0) { iDBy=-iDBy; } else if (map[iBx+iDBx][iBy+iDBy]>1) { iDBx=-iDBx; iDBy=-iDBy; } if (map[iBx+iDBx][iBy+iDBy]<2) { map[iBx][iBy]=0; iBx+=iDBx; iBy+=iDBy; map[iBx][iBy]=4; } InvalidateRect(hwMain,NULL,FALSE); UpdateWindow (hwMain); // 再描画 } LRESULT CALLBACK WndProc (HWND hwnd, UINT iMsg, WPARAM wParam, LPARAM lParam) { HDC hdc; PAINTSTRUCT ps; switch (iMsg) { case WM_PAINT: hdc=BeginPaint(hwnd,&ps); StretchDIBits(hdc,8,8,512,512, 0,0,512,512,lpScreen,lpDIB, DIB_RGB_COLORS,SRCCOPY); /* DIBを画面に描画 */ EndPaint(hwnd,&ps); break; case WM_DESTROY : // 終了処理 GlobalFree(lpBuf); PostQuitMessage(0); return 0; } return DefWindowProc (hwnd, iMsg, wParam, lParam) ; }