This is what I had for my Tetris clode I was working on.
#include <WINDOWS.H>#include <STDLIB.H>#include <STDIO.H>struct BOARD{ CHAR umBoard[ 14 ][ 21 ]; CHAR uLines;};struct BLOCK{ CHAR umBlock[ 4 ][ 4 ]; CHAR uX; CHAR uY;};const CHAR g_mmBlockI[ 4 ][ 4 ] = { { 0, 1, 0, 0 }, { 0, 1, 0, 0 }, { 0, 1, 0, 0 }, { 0, 1, 0, 0 }, };const CHAR g_mmBlockJ[ 4 ][ 4 ] = { { 0, 1, 0, 0 }, { 0, 1, 0, 0 }, { 1, 1, 0, 0 }, { 0, 0, 0, 0 }, };const CHAR g_mmBlockL[ 4 ][ 4 ] = { { 1, 0, 0, 0 }, { 1, 0, 0, 0 }, { 1, 1, 0, 0 }, { 0, 0, 0, 0 }, };const CHAR g_mmBlockO[ 4 ][ 4 ] = { { 1, 1, 0, 0 }, { 1, 1, 0, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, };const CHAR g_mmBlockS[ 4 ][ 4 ] = { { 0, 1, 1, 0 }, { 1, 1, 0, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, };const CHAR g_mmBlockT[ 4 ][ 4 ] = { { 1, 1, 1, 0 }, { 0, 1, 0, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, };const CHAR g_mmBlockZ[ 4 ][ 4 ] = { { 1, 1, 0, 0 }, { 0, 1, 1, 0 }, { 0, 0, 0, 0 }, { 0, 0, 0, 0 }, };double g_fLastTime = 0.0;HBRUSH g_hbrBlock = CreateSolidBrush( RGB( 100, 100, 120 ) );HBRUSH g_hbrSpace = CreateSolidBrush( RGB( 0, 0, 0 ) );BOARD g_Board = { 0 };BLOCK g_Block = { 0 };BOOL g_bDoUpdate = FALSE;//-----------------------------------------------------------------------------// Reset the game board//VOID ResetGameBoard( ){ for ( int i = 0; i < 21; ++i ) for ( int j = 0; j < 14; ++j ) if ( i == 20 || j == 0 || j == 13 ) g_Board.umBoard[ j ][ i ] = 1; else g_Board.umBoard[ j ][ i ] = 0; g_Board.uLines = 0;}//-----------------------------------------------------------------------------// Generate a new random figure//VOID GenerateRandomBlock( ){ CHAR uBlock = ( rand( ) % 7 ) + 1; switch ( uBlock ) { case 1: memcpy( g_Block.umBlock, g_mmBlockI, 16 ); break; case 2: memcpy( g_Block.umBlock, g_mmBlockJ, 16 ); break; case 3: memcpy( g_Block.umBlock, g_mmBlockL, 16 ); break; case 4: memcpy( g_Block.umBlock, g_mmBlockO, 16 ); break; case 5: memcpy( g_Block.umBlock, g_mmBlockS, 16 ); break; case 6: memcpy( g_Block.umBlock, g_mmBlockT, 16 ); break; case 7: memcpy( g_Block.umBlock, g_mmBlockZ, 16 ); break; } g_Block.uX = 6; g_Block.uY = 0;}//-----------------------------------------------------------------------------// Check for a collision on the board//BOOL CheckCollision ( CHAR umBlock[ 4 ][ 4 ] ){ for ( int i = 0; i < 4; ++i ) for ( int j = 0; j < 4; ++j ) if ( umBlock[ j ][ i ] == 0 ) break; else if ( g_Board.umBoard[ j + g_Block.uX ][ i + g_Block.uY ] + umBlock[ j ][ i ] != umBlock[ j ][ i ] ) return TRUE; return FALSE;}//-----------------------------------------------------------------------------// Move a block//BOOL MoveBlock( int nDX, int nDY ){ int nTempX, nTempY; nTempX = g_Block.uX; nTempY = g_Block.uY; g_Block.uX += nDX; g_Block.uY += nDY; if ( TRUE == CheckCollision( g_Block.umBlock ) ) { g_Block.uX = nTempX; g_Block.uY = nTempY; return TRUE; } return FALSE;}//-----------------------------------------------------------------------------// Rotate a block 90 degrees//VOID RotateBlock( ){ CHAR i, j, umFig[ 4 ][ 4 ]; for ( i = 0; i < 4; ++i ) for ( j = 0; j < 4; ++j ) umFig[ j ][ i ] = g_Block.umBlock[ 4 - i ][ j ]; if ( TRUE == CheckCollision( umFig ) ) return; for ( i = 0; i < 4; ++i ) for ( j = 0; j < 4; ++j ) umFig[ j ][ i ] = g_Block.umBlock[ j ][ i ];}//-----------------------------------------------------------------------------// Insert a block//VOID InsertBlock( ){ for ( int i = 0; i < 4; ++i ) for ( int j = 0; j < 4; ++j ) if ( g_Block.umBlock[ j ][ i ] != 0 ) g_Board.umBoard[ g_Block.uX + j ][ g_Block.uY + i ] = g_Block.umBlock[ j ][ i ];}//-----------------------------------------------------------------------------// Remove completed lines//VOID RemoveLine( UINT uIndex ){ for ( int i = uIndex; i > 0; --i ) for ( int j = 1; j < 13; ++j ) g_Board.umBoard[ j ][ i ] = g_Board.umBoard[ j ][ i - 1 ];}//-----------------------------------------------------------------------------// Search for completed lines//VOID SearchLines( ){ CHAR uNumBlocks = 0; for ( int i = 0; i < 21; ++i ) for ( int j = 1; j < 13; ++j ) if ( g_Board.umBoard[ j ][ i ] == 0 ) { uNumBlocks = 0; break; } else { ++uNumBlocks; if ( uNumBlocks >= 12 ) { RemoveLine( i ); ++g_Board.uLines; --i; } }}//-----------------------------------------------------------------------------// Paint the scene//VOID PaintScene( HWND hWnd ){ CHAR cvBuffer[ 80 ]; RECT rcBlock; HDC hDC; int i, j; hDC = GetDC( hWnd ); for ( i = 0; i < 20; ++i ) for ( j = 1; j < 13; ++j ) { rcBlock.top = ( i * 16 ) + 4; rcBlock.left = ( j * 16 ) + 4; rcBlock.bottom = rcBlock.top + 16; rcBlock.right = rcBlock.left + 16; if ( g_Board.umBoard[ j ][ i ] == 0 ) FillRect( hDC, &rcBlock, g_hbrSpace ); else FillRect( hDC, &rcBlock, g_hbrBlock ); } for ( i = 0; i < 4; ++i ) for ( j = 0; j < 4; ++j ) if ( g_Block.umBlock[ j ][ i ] == 0 ) break; else { rcBlock.top = ( ( g_Block.uY + i ) * 16 ) + 4; rcBlock.left = ( ( g_Block.uX + j ) * 16 ) + 4; rcBlock.bottom = rcBlock.top + 16; rcBlock.right = rcBlock.left + 16; if ( g_Block.umBlock[ j ][ i ] != 0 ) FillRect( hDC, &rcBlock, g_hbrBlock ); } SetBkColor( hDC, RGB( 100, 120, 100 ) ); SetTextColor( hDC, RGB( 255, 240, 50 ) ); sprintf( cvBuffer, "Level: %i", ( g_Board.uLines / 15 ) ); TextOut( hDC, 210, 100, cvBuffer, ( int )strlen( cvBuffer ) ); sprintf( cvBuffer, "Lines: %i", g_Board.uLines ); TextOut( hDC, 210, 135, cvBuffer, ( int )strlen( cvBuffer ) ); ReleaseDC( hWnd, hDC );}//-----------------------------------------------------------------------------// Process Win32 application messages//LRESULT CALLBACK WindowProc ( HWND hWnd, UINT uMessage, WPARAM wParam, LPARAM lParam ){ switch ( uMessage ) { case WM_LBUTTONDOWN: SendMessage( hWnd, WM_NCLBUTTONDOWN, HTCAPTION, lParam ); return 0L; case WM_KEYDOWN: switch ( LOWORD( wParam ) ) { case VK_ESCAPE: PostQuitMessage( 0 ); break; case VK_LEFT: MoveBlock( -1, 0 ); g_bDoUpdate = TRUE; break; case VK_RIGHT: MoveBlock( 1, 0 ); g_bDoUpdate = TRUE; break; case VK_DOWN: MoveBlock( 0, 1 ); g_bDoUpdate = TRUE; break; case VK_SPACE: RotateBlock( ); g_bDoUpdate = TRUE; break; } return 0L; case WM_DESTROY: PostQuitMessage( 0 ); return 0L; } return DefWindowProc( hWnd, uMessage, wParam, lParam );}//-----------------------------------------------------------------------------// Application entry point//int WINAPI WinMain ( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd ){ WNDCLASS sWC; HWND hWnd; MSG sMsg; memset( &sWC, 0, sizeof( WNDCLASS ) ); sWC.hbrBackground = CreateSolidBrush( RGB( 100, 120, 100 ) ); sWC.hCursor = LoadCursor( NULL, IDC_ARROW ); sWC.hIcon = LoadIcon( NULL, IDI_WINLOGO ); sWC.hInstance = hInstance; sWC.lpfnWndProc = WindowProc; sWC.lpszClassName = "DEMO"; RegisterClass( &sWC ); hWnd = CreateWindow( "DEMO", "Demo", WS_CAPTION | WS_SYSMENU | WS_MINIMIZEBOX | WS_VISIBLE, CW_USEDEFAULT, CW_USEDEFAULT, 270, 400, NULL, NULL, hInstance, NULL ); ResetGameBoard( ); GenerateRandomBlock( ); PeekMessage( &sMsg, NULL, 0U, 0U, PM_NOREMOVE ); while ( WM_QUIT != sMsg.message ) if ( PeekMessage( &sMsg, NULL, 0U, 0U, PM_REMOVE ) ) { TranslateMessage( &sMsg ); DispatchMessage( &sMsg ); } else { double fTime = GetTickCount( ) * 0.001; if ( fTime - g_fLastTime > ( 1.0 - ( ( g_Board.uLines / 15 ) * 0.1 ) ) ) { g_fLastTime = fTime; if ( MoveBlock( 0, 1 ) ) { InsertBlock( ); SearchLines( ); GenerateRandomBlock( ); } g_bDoUpdate = TRUE; } if ( TRUE == g_bDoUpdate ) { PaintScene( hWnd ); g_bDoUpdate = FALSE; } } return ( int )sMsg.wParam;}