diff --git a/data/background.bmp b/data/background.bmp deleted file mode 100644 index aaec3b0..0000000 Binary files a/data/background.bmp and /dev/null differ diff --git a/data/hero_head_front.bmp b/data/hero_head_front.bmp deleted file mode 100644 index e7bd369..0000000 Binary files a/data/hero_head_front.bmp and /dev/null differ diff --git a/data/structured_art.bmp b/data/structured_art.bmp new file mode 100644 index 0000000..2ecd9ec Binary files /dev/null and b/data/structured_art.bmp differ diff --git a/data/test.bmp b/data/test.bmp deleted file mode 100644 index 73f4167..0000000 Binary files a/data/test.bmp and /dev/null differ diff --git a/data/test_background.bmp b/data/test_background.bmp new file mode 100644 index 0000000..c09af67 Binary files /dev/null and b/data/test_background.bmp differ diff --git a/data/test_hero_back_cape.bmp b/data/test_hero_back_cape.bmp new file mode 100644 index 0000000..7452e25 Binary files /dev/null and b/data/test_hero_back_cape.bmp differ diff --git a/data/test_hero_back_head.bmp b/data/test_hero_back_head.bmp new file mode 100644 index 0000000..9b39e95 Binary files /dev/null and b/data/test_hero_back_head.bmp differ diff --git a/data/test_hero_back_torso.bmp b/data/test_hero_back_torso.bmp new file mode 100644 index 0000000..2f0f5a9 Binary files /dev/null and b/data/test_hero_back_torso.bmp differ diff --git a/data/test_hero_front_cape.bmp b/data/test_hero_front_cape.bmp new file mode 100644 index 0000000..1bb2a88 Binary files /dev/null and b/data/test_hero_front_cape.bmp differ diff --git a/data/test_hero_front_head.bmp b/data/test_hero_front_head.bmp new file mode 100644 index 0000000..293f995 Binary files /dev/null and b/data/test_hero_front_head.bmp differ diff --git a/data/test_hero_front_torso.bmp b/data/test_hero_front_torso.bmp new file mode 100644 index 0000000..316fe7a Binary files /dev/null and b/data/test_hero_front_torso.bmp differ diff --git a/data/test_hero_left_cape.bmp b/data/test_hero_left_cape.bmp new file mode 100644 index 0000000..042b5ee Binary files /dev/null and b/data/test_hero_left_cape.bmp differ diff --git a/data/test_hero_left_head.bmp b/data/test_hero_left_head.bmp new file mode 100644 index 0000000..1b5e6c0 Binary files /dev/null and b/data/test_hero_left_head.bmp differ diff --git a/data/test_hero_left_torso.bmp b/data/test_hero_left_torso.bmp new file mode 100644 index 0000000..0799221 Binary files /dev/null and b/data/test_hero_left_torso.bmp differ diff --git a/data/test_hero_right_cape.bmp b/data/test_hero_right_cape.bmp new file mode 100644 index 0000000..42be29e Binary files /dev/null and b/data/test_hero_right_cape.bmp differ diff --git a/data/test_hero_right_head.bmp b/data/test_hero_right_head.bmp new file mode 100644 index 0000000..0778279 Binary files /dev/null and b/data/test_hero_right_head.bmp differ diff --git a/data/test_hero_right_torso.bmp b/data/test_hero_right_torso.bmp new file mode 100644 index 0000000..993462d Binary files /dev/null and b/data/test_hero_right_torso.bmp differ diff --git a/data/test_hero_shadow.bmp b/data/test_hero_shadow.bmp new file mode 100644 index 0000000..7a77795 Binary files /dev/null and b/data/test_hero_shadow.bmp differ diff --git a/data/test_scene_layer_00.bmp b/data/test_scene_layer_00.bmp new file mode 100644 index 0000000..e083086 Binary files /dev/null and b/data/test_scene_layer_00.bmp differ diff --git a/data/test_scene_layer_01.bmp b/data/test_scene_layer_01.bmp new file mode 100644 index 0000000..eef9e77 Binary files /dev/null and b/data/test_scene_layer_01.bmp differ diff --git a/data/test_scene_layer_02.bmp b/data/test_scene_layer_02.bmp new file mode 100644 index 0000000..8948459 Binary files /dev/null and b/data/test_scene_layer_02.bmp differ diff --git a/data/test_scene_layer_03.bmp b/data/test_scene_layer_03.bmp new file mode 100644 index 0000000..4b93a9a Binary files /dev/null and b/data/test_scene_layer_03.bmp differ diff --git a/data/test_scene_layer_04.bmp b/data/test_scene_layer_04.bmp new file mode 100644 index 0000000..78e503d Binary files /dev/null and b/data/test_scene_layer_04.bmp differ diff --git a/handmade.c b/handmade.c index f45e985..aec1e27 100644 --- a/handmade.c +++ b/handmade.c @@ -84,8 +84,11 @@ static void DrawRectangle(game_offscreen_buffer *Buffer, F32 RealMinX, F32 RealM } } -static void DrawBitmap(game_offscreen_buffer *Buffer, loaded_bitmap *Bitmap, F32 RelX, F32 RelY) +static void DrawBitmap(game_offscreen_buffer *Buffer, loaded_bitmap *Bitmap, F32 RelX, F32 RelY, S32 AlignX, S32 AlignY) { + RelX -= (F32)AlignX; + RelY -= (F32)AlignY; + S32 MinX = RoundF32toS32(RelX); S32 MinY = RoundF32toS32(RelY); S32 MaxX = RoundF32toS32(RelX + (F32)Bitmap->Width); @@ -112,12 +115,12 @@ static void DrawBitmap(game_offscreen_buffer *Buffer, loaded_bitmap *Bitmap, F32 for(S32 X = MinX; X < MaxX; X++) { F32 A = (F32)((*Source >> 24) & 0xFF) / 255.0f; F32 SR = (F32)((*Source >> 16) & 0xFF); - F32 SG = (F32)((*Source >> 8) & 0xFF); - F32 SB = (F32)((*Source >> 0) & 0xFF); + F32 SG = (F32)((*Source >> 8) & 0xFF); + F32 SB = (F32)((*Source >> 0) & 0xFF); F32 DR = (F32)((*Dest >> 16) & 0xFF); - F32 DG = (F32)((*Dest >> 8) & 0xFF); - F32 DB = (F32)((*Dest >> 0) & 0xFF); + F32 DG = (F32)((*Dest >> 8) & 0xFF); + F32 DB = (F32)((*Dest >> 0) & 0xFF); // TODO: This should be replaced by premultiplied alpha. F32 R = (1.0f-A)*DR + A*SR; @@ -186,7 +189,7 @@ static loaded_bitmap DEBUGLoadBMP(thread_context *Thread, debug_read_file_result bit_scan_result GreenShift = FindLeastSignificantSetBit(GreenMask); bit_scan_result BlueShift = FindLeastSignificantSetBit(BlueMask); bit_scan_result AlphaShift = FindLeastSignificantSetBit(AlphaMask); - + ASSERT(RedShift.Found); ASSERT(GreenShift.Found); ASSERT(BlueShift.Found); @@ -200,7 +203,8 @@ static loaded_bitmap DEBUGLoadBMP(thread_context *Thread, debug_read_file_result *SourceDest = ((((C >> AlphaShift.Index) & 0xFF) << 24) | (((C >> RedShift.Index ) & 0xFF) << 16) | (((C >> GreenShift.Index) & 0xFF) << 8) | - (((C >> BlueShift.Index ) & 0xFF) << 8)); + (((C >> BlueShift.Index ) & 0xFF) << 0)); + SourceDest++; } } } @@ -224,10 +228,40 @@ void UpdateAndRender(thread_context *Thread, game_memory *Memory, game_input *In GameState = (game_state *)Memory->PermanentStorage; if(!Memory->IsInitialized) { - GameState->Backdrop = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/background.bmp"); - GameState->HeroHead = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/hero_head_front.bmp");; - GameState->HeroCape = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/hero_cape_front.bmp");; - GameState->HeroTorso = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/hero_torso_front.bmp");; + GameState->Backdrop = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_background.bmp"); + + hero_bitmaps *Bitmap; + + Bitmap = &GameState->HeroBitmaps[0]; + Bitmap->AlignX = 72; + Bitmap->AlignY = 182; + Bitmap->Head = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_right_head.bmp"); + Bitmap->Cape = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_right_cape.bmp"); + Bitmap->Torso = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_right_torso.bmp"); + Bitmap++; + + Bitmap->AlignX = 72; + Bitmap->AlignY = 182; + Bitmap->Head = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_back_head.bmp"); + Bitmap->Cape = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_back_cape.bmp"); + Bitmap->Torso = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_back_torso.bmp"); + Bitmap++; + + Bitmap->AlignX = 72; + Bitmap->AlignY = 182; + Bitmap->Head = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_left_head.bmp"); + Bitmap->Cape = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_left_cape.bmp"); + Bitmap->Torso = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_left_torso.bmp"); + Bitmap++; + + Bitmap->AlignX = 72; + Bitmap->AlignY = 182; + Bitmap->Head = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_front_head.bmp"); + Bitmap->Cape = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_front_cape.bmp"); + Bitmap->Torso = DEBUGLoadBMP(Thread, Memory->DEBUGPlatformReadEntireFile, "data/test_hero_front_torso.bmp"); + + GameState->CameraP.AbsTileX = 17 / 2; + GameState->CameraP.AbsTileY = 9 / 2; GameState->PlayerP.AbsTileX = 2; GameState->PlayerP.AbsTileY = 3; @@ -376,15 +410,19 @@ void UpdateAndRender(thread_context *Thread, game_memory *Memory, game_input *In if(Controller->MoveUp.EndedDown) { dPlayerY = 1.0f; + GameState->FacingDirection = 1; } if(Controller->MoveDown.EndedDown) { dPlayerY = -1.0f; + GameState->FacingDirection = 3; } if(Controller->MoveLeft.EndedDown) { dPlayerX = -1.0f; + GameState->FacingDirection = 2; } if(Controller->MoveRight.EndedDown) { dPlayerX = 1.0f; + GameState->FacingDirection = 0; } F32 PlayerSpeed = 2.0f; @@ -428,17 +466,17 @@ void UpdateAndRender(thread_context *Thread, game_memory *Memory, game_input *In DrawRectangle(Buffer, 0.0f, 0.0f, (F32)Buffer->Width, (F32)Buffer->Height, 0.0f, 1.0f, 0.0f); - DrawBitmap(Buffer, &GameState->Backdrop, 0.0f, 0.0f); + DrawBitmap(Buffer, &GameState->Backdrop, 0.0f, 0.0f, 0, 0); F32 ScreenCenterX = 0.5f * (F32)Buffer->Width; F32 ScreenCenterY = 0.5f * (F32)Buffer->Height; for(S32 RelRow = -10; RelRow < 10; RelRow++) { for(S32 RelColumn = -20; RelColumn < 20; RelColumn++) { - U32 Column = GameState->PlayerP.AbsTileX + RelColumn; - U32 Row = GameState->PlayerP.AbsTileY + RelRow; + U32 Column = GameState->CameraP.AbsTileX + RelColumn; + U32 Row = GameState->CameraP.AbsTileY + RelRow; - U32 TileID = GetTileValue(TileMap, Column, Row, GameState->PlayerP.AbsTileZ); + U32 TileID = GetTileValue(TileMap, Column, Row, GameState->CameraP.AbsTileZ); if(TileID > 1) { F32 Gray = 0.5f; @@ -450,13 +488,13 @@ void UpdateAndRender(thread_context *Thread, game_memory *Memory, game_input *In Gray = 0.25f; } - if((Column == GameState->PlayerP.AbsTileX) && (Row == GameState->PlayerP.AbsTileY)) { + if((Column == GameState->CameraP.AbsTileX) && (Row == GameState->CameraP.AbsTileY)) { Gray = 0.0f; } - F32 CenterX = ScreenCenterX - MetersToPixels*GameState->PlayerP.OffsetX + (F32)RelColumn*(F32)TileSideInPixels; - F32 CenterY = ScreenCenterY + MetersToPixels*GameState->PlayerP.OffsetY - (F32)RelRow*(F32)TileSideInPixels; + F32 CenterX = ScreenCenterX - MetersToPixels*GameState->CameraP.OffsetX + (F32)RelColumn*(F32)TileSideInPixels; + F32 CenterY = ScreenCenterY + MetersToPixels*GameState->CameraP.OffsetY - (F32)RelRow*(F32)TileSideInPixels; F32 MinX = CenterX - 0.5f*(F32)TileSideInPixels; F32 MinY = CenterY - 0.5f*(F32)TileSideInPixels; F32 MaxX = CenterX + 0.5f*(F32)TileSideInPixels; @@ -466,13 +504,21 @@ void UpdateAndRender(thread_context *Thread, game_memory *Memory, game_input *In } } + tile_map_difference Diff = SubtractInF32(TileMap, &GameState->PlayerP, &GameState->CameraP); + F32 PlayerR = 1.0f; F32 PlayerG = 0.0f; F32 PlayerB = 0.0f; - F32 PlayerLeft = ScreenCenterX - 0.5f * MetersToPixels*PlayerWidth; - F32 PlayerTop = ScreenCenterY - MetersToPixels*PlayerHeight; + F32 PlayerGroundPointX = ScreenCenterX + MetersToPixels*Diff.dX; + F32 PlayerGroundPointY = ScreenCenterY + MetersToPixels*Diff.dY; + F32 PlayerLeft = PlayerGroundPointX - 0.5f * MetersToPixels*PlayerWidth; + F32 PlayerTop = PlayerGroundPointY - MetersToPixels*PlayerHeight; DrawRectangle(Buffer, PlayerLeft, PlayerTop, PlayerLeft + MetersToPixels*PlayerWidth, PlayerTop + MetersToPixels*PlayerHeight, PlayerR, PlayerG, PlayerB); - DrawBitmap(Buffer, &GameState->HeroHead, PlayerLeft, PlayerTop); + + hero_bitmaps *Bitmap = &GameState->HeroBitmaps[GameState->FacingDirection]; + DrawBitmap(Buffer, &Bitmap->Torso, PlayerGroundPointX, PlayerGroundPointY, Bitmap->AlignX, Bitmap->AlignY); + DrawBitmap(Buffer, &Bitmap->Cape, PlayerGroundPointX, PlayerGroundPointY, Bitmap->AlignX, Bitmap->AlignY); + DrawBitmap(Buffer, &Bitmap->Head, PlayerGroundPointX, PlayerGroundPointY, Bitmap->AlignX, Bitmap->AlignY); GameOutputSound(GameState, SoundBuffer, 400); } diff --git a/handmade.h b/handmade.h index 64c6ed9..766ff8b 100644 --- a/handmade.h +++ b/handmade.h @@ -18,11 +18,8 @@ typedef struct debug_read_file_result { void *Contents; } debug_read_file_result; -debug_read_file_result DEBUGPlatformReadEntireFile(thread_context *Thread, - const char *Filename); -B32 DEBUGPlatformWriteEntireFile(thread_context *Thread, - const char *Filename, U32 MemorySize, - void *Memory); +debug_read_file_result DEBUGPlatformReadEntireFile(thread_context *Thread, const char *Filename); +B32 DEBUGPlatformWriteEntireFile(thread_context *Thread, const char *Filename, U32 MemorySize, void *Memory); void DEBUGPlatformFreeFileMemory(thread_context *Thread, void *Memory); #endif @@ -171,17 +168,26 @@ typedef struct loaded_bitmap { U32 *Pixels; } loaded_bitmap; +typedef struct hero_bitmaps { + S32 AlignX; + S32 AlignY; + + loaded_bitmap Head; + loaded_bitmap Cape; + loaded_bitmap Torso; +} hero_bitmaps; + typedef struct game_state { memory_arena WorldArena; world *World; + tile_map_position CameraP; tile_map_position PlayerP; loaded_bitmap Backdrop; - loaded_bitmap HeroHead; - loaded_bitmap HeroCape; - loaded_bitmap HeroTorso; + U32 FacingDirection; + hero_bitmaps HeroBitmaps[4]; } game_state; #endif diff --git a/handmade_tile.c b/handmade_tile.c index 54c6e8b..d5f277e 100644 --- a/handmade_tile.c +++ b/handmade_tile.c @@ -135,3 +135,20 @@ static B32 AreOnSameTile(tile_map_position *A, tile_map_position *B) B32 Result = ((A->AbsTileX == B->AbsTileX) && (A->AbsTileY == B->AbsTileY) && (A->AbsTileZ == B->AbsTileZ)); return Result; } + +static tile_map_difference SubtractInF32(tile_map *TileMap, tile_map_position *A, tile_map_position *B) +{ + tile_map_difference Result; + + F32 dTileX = (F32)A->AbsTileX - (F32)B->AbsTileY; + F32 dTileY = (F32)A->AbsTileX - (F32)B->AbsTileY; + F32 dTileZ = (F32)A->AbsTileX - (F32)B->AbsTileY; + + Result.dX = TileMap->TileSideInMeters*dTileX + (A->OffsetX - B->OffsetX); + Result.dY = TileMap->TileSideInMeters*dTileY + (A->OffsetY - B->OffsetY); + + // TODO: Incomplete . . . + Result.dZ = TileMap->TileSideInMeters*dTileZ; + + return Result; +} diff --git a/handmade_tile.h b/handmade_tile.h index 0d0d345..ca94cf2 100644 --- a/handmade_tile.h +++ b/handmade_tile.h @@ -1,6 +1,12 @@ #ifndef HANDMADE_TILE_H_SENTRY #define HANDMADE_TILE_H_SENTRY +typedef struct tile_map_difference { + F32 dX; + F32 dY; + F32 dZ; +} tile_map_difference; + typedef struct tile_map_position { U32 AbsTileX; U32 AbsTileY;