character can move around

This commit is contained in:
John Bintz 2024-02-15 21:18:15 -05:00
parent d52426a877
commit 5dd033eeb9
9 changed files with 208 additions and 28 deletions

2
.gitignore vendored
View File

@ -4,3 +4,5 @@
*.EXE *.EXE
.ccls-cache/ .ccls-cache/
*.LNK *.LNK
*.o
*.exe

View File

@ -25,5 +25,6 @@ struct BMPImage {
int readBMPIntoMemory(FILE *, struct BMPImage *); int readBMPIntoMemory(FILE *, struct BMPImage *);
int readBMPIntoNewMemory(FILE *, struct BMPImage *); int readBMPIntoNewMemory(FILE *, struct BMPImage *);
void bmp256ColorPaletteToVGAColorPalette(struct BMPImage*, struct VGAColor[]); void bmp256ColorPaletteToVGAColorPalette(struct BMPImage*, struct VGAColor[]);
void freeBMP(struct BMPImage *);
#endif #endif

195
game.c
View File

@ -10,6 +10,171 @@ struct BMPImage spritesheetImage;
struct VGAColor vgaColors[256]; struct VGAColor vgaColors[256];
struct SpriteRender arenaWallTop, arenaWallSide, arenaFloor; struct SpriteRender arenaWallTop, arenaWallSide, arenaFloor;
struct SpriteRender rabbit;
void setupWallSprites() {
buildSpriteFromSpritesheet(
&spritesheetImage,
&arenaWallTop,
0, 0, 20, 20
);
buildSpriteFromSpritesheet(
&spritesheetImage,
&arenaWallSide,
20, 0, 20, 20
);
buildSpriteFromSpritesheet(
&spritesheetImage,
&arenaFloor,
40, 0, 20, 20
);
}
void setupRabbitSprites() {
buildSpriteFromSpritesheet(
&spritesheetImage,
&rabbit,
0, 20, 16, 16
);
}
char arenaLayout[10][10] = {
{ 1, 1, 1, 1, 0, 0, 1, 1, 1, 1 },
{ 1, 2, 2, 2, 0, 0, 2, 2, 2, 1 },
{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
{ 2, 0, 0, 0, 0, 0, 0, 0, 0, 2 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
{ 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 },
{ 1, 1, 1, 1, 0, 0, 1, 1, 1, 1 }
};
void renderArenaTile(int x, int y) {
char tile;
struct SpriteRender *target;
tile = arenaLayout[y][x];
switch (tile) {
case 0:
target = &arenaFloor;
break;
case 1:
target = &arenaWallTop;
break;
case 2:
target = &arenaWallSide;
break;
}
target->x = x * 20;
target->y = y * 20;
drawSprite(target);
}
void buildArena() {
int x, y;
for (y = 0; y < 10; ++y) {
for (x = 0; x < 10; ++x) {
renderArenaTile(x, y);
}
}
}
int rabbitPosition[2] = { 60, 60 };
int rabbitLimits[2][2] = {
{ 20, 20 },
{ 180, 180 }
};
#define RABBIT_MOTION_DRAG (2)
#define RABBIT_MOTION_ACCELERATION (5)
#define RABBIT_MOTION_MAX_SPEED (12)
signed char rabbitVelocity[2] = { 0, 0 };
void renderRabbit() {
rabbit.x = rabbitPosition[0];
rabbit.y = rabbitPosition[1];
drawSprite(&rabbit);
}
void handleRabbitMovement() {
int i;
if (keyboardKeydownState.KEY_W) {
rabbitVelocity[1] -= RABBIT_MOTION_ACCELERATION;
if (rabbitVelocity[1] < -RABBIT_MOTION_MAX_SPEED) {
rabbitVelocity[1] = -RABBIT_MOTION_MAX_SPEED;
}
}
if (keyboardKeydownState.KEY_S) {
rabbitVelocity[1] += RABBIT_MOTION_ACCELERATION;
if (rabbitVelocity[1] > RABBIT_MOTION_MAX_SPEED) {
rabbitVelocity[1] = RABBIT_MOTION_MAX_SPEED;
}
}
if (keyboardKeydownState.KEY_A) {
rabbitVelocity[0] -= RABBIT_MOTION_ACCELERATION;
if (rabbitVelocity[0] < -RABBIT_MOTION_MAX_SPEED) {
rabbitVelocity[0] = -RABBIT_MOTION_MAX_SPEED;
}
}
if (keyboardKeydownState.KEY_D) {
rabbitVelocity[0] += RABBIT_MOTION_ACCELERATION;
if (rabbitVelocity[0] > RABBIT_MOTION_MAX_SPEED) {
rabbitVelocity[0] = RABBIT_MOTION_MAX_SPEED;
}
}
for (i = 0; i < 2; ++i) {
rabbitPosition[i] += (rabbitVelocity[i] / 5);
if (rabbitPosition[i] < rabbitLimits[0][i]) {
rabbitPosition[i] = rabbitLimits[0][i];
}
if (rabbitPosition[i] >= rabbitLimits[1][i]) {
rabbitPosition[i] = rabbitLimits[1][i];
}
if (rabbitVelocity[i] < 0) {
rabbitVelocity[i] += RABBIT_MOTION_DRAG;
if (rabbitVelocity[i] > 0) rabbitVelocity[i] = 0;
}
if (rabbitVelocity[i] > 0) {
rabbitVelocity[i] -= RABBIT_MOTION_DRAG;
if (rabbitVelocity[i] < 0) rabbitVelocity[i] = 0;
}
}
}
void drawOnlyRabbitArena() {
int rabbitLeftTileX, rabbitRightTileX,
rabbitTopTileY, rabbitBottomTileY;
rabbitLeftTileX = rabbitPosition[0] / 20;
rabbitRightTileX = (rabbitPosition[0] + 16) / 20;
rabbitTopTileY = rabbitPosition[1] / 20;
rabbitBottomTileY = (rabbitPosition[1] + 16) / 20;
renderArenaTile(rabbitLeftTileX, rabbitTopTileY);
if (rabbitLeftTileX != rabbitRightTileX) {
renderArenaTile(rabbitRightTileX, rabbitTopTileY);
if (rabbitTopTileY != rabbitBottomTileY) {
renderArenaTile(rabbitRightTileX, rabbitBottomTileY);
}
}
if (rabbitTopTileY != rabbitBottomTileY) {
renderArenaTile(rabbitLeftTileX, rabbitBottomTileY);
}
}
int main(void) { int main(void) {
FILE *fh; FILE *fh;
@ -24,32 +189,33 @@ int main(void) {
if (readBMPIntoNewMemory(fh, &spritesheetImage)) return 1; if (readBMPIntoNewMemory(fh, &spritesheetImage)) return 1;
fclose(fh); fclose(fh);
return 0;
spritesheetImage.transparentColor = 0; spritesheetImage.transparentColor = 0;
buildSpriteFromSpritesheet( setupWallSprites();
&spritesheetImage, setupRabbitSprites();
&arenaWallTop,
0, 0, 20, 20
);
setVideoMode(VIDEO_MODE_VGA_256); setVideoMode(VIDEO_MODE_VGA_256);
bmp256ColorPaletteToVGAColorPalette(&spritesheetImage, vgaColors); bmp256ColorPaletteToVGAColorPalette(&spritesheetImage, vgaColors);
setVGAColors(vgaColors, 256); setVGAColors(vgaColors, 256);
while (keepRunning) { buildArena();
arenaWallTop.x = 0;
arenaWallTop.y = 0;
drawSprite(&arenaWallTop); while (keepRunning) {
readMouse(&mouseStatus);
populateKeyboardKeydownState();
handleRabbitMovement();
waitStartVbl(); waitStartVbl();
drawOnlyRabbitArena();
renderRabbit();
copyDrawBufferToDisplay(); copyDrawBufferToDisplay();
waitEndVbl(); waitEndVbl();
if (mouseStatus.leftButtonDown) { keepRunning = 0; }
} }
// states: // states:
// * main menu // * main menu
// * play // * play
@ -70,6 +236,13 @@ int main(void) {
// * check for bullets hitting the edges of the screen and remove // * check for bullets hitting the edges of the screen and remove
// * // *
// //
freeBMP(&spritesheetImage);
setVideoMode(VIDEO_MODE_80x25_TEXT);
uninstallKeyboardHandler();
fprintf(stderr, "meow\n");
return 0; return 0;
} }

2
game.lnk Normal file
View File

@ -0,0 +1,2 @@
NAME game.exe
FILE game.o

View File

@ -1,13 +1,7 @@
.c.obj obj = game.o bmpload.o mouse_io.o pc_stuff.o vga.o keyboard.o
wcc386 -q $<
game.exe: bmpload.obj mouse_io.obj pc_stuff.obj vga.obj keyboard.obj game.obj .c.o:
%write game.lnk NAME $@ wcc386 -q -bt=dos -q $<
%write game.lnk SYSTEM DOS4G
%write game.lnk FILE bmpload.obj game.exe: $(obj)
%write game.lnk FILE mouse_io.obj wcl386 -q -bt=dos -l=dos4g $(obj)
%write game.lnk FILE pc_stuff.obj
%write game.lnk FILE vga.obj
%write game.lnk FILE keyboard.obj
%write game.lnk FILE game.obj
wlink @game.lnk

View File

@ -1,8 +1,11 @@
#include <dos.h> #include <dos.h>
#include <conio.h> #include <conio.h>
#include <i86.h>
#include "mouse_io.h" #include "mouse_io.h"
struct MouseStatus *_status;
int activateMouse(struct MouseStatus *status) { int activateMouse(struct MouseStatus *status) {
union REGS regs; union REGS regs;
int mouseActivated; int mouseActivated;
@ -28,10 +31,12 @@ int activateMouse(struct MouseStatus *status) {
int386(MOUSE_DRIVER_INTERRUPT, &regs, &regs); int386(MOUSE_DRIVER_INTERRUPT, &regs, &regs);
} }
_status = status;
return mouseActivated; return mouseActivated;
} }
void readMouse(struct MouseStatus *status) { void readMouse() {
union REGS regs; union REGS regs;
int buttonStatus; int buttonStatus;
@ -39,10 +44,10 @@ void readMouse(struct MouseStatus *status) {
int386(MOUSE_DRIVER_INTERRUPT, &regs, &regs); int386(MOUSE_DRIVER_INTERRUPT, &regs, &regs);
buttonStatus = regs.w.bx; buttonStatus = regs.w.bx;
status->xPosition = regs.w.cx; _status->xPosition = regs.w.cx;
status->yPosition = regs.w.dx; _status->yPosition = regs.w.dx;
status->leftButtonDown = buttonStatus & 1; _status->leftButtonDown = buttonStatus & 1;
status->rightButtonDown = (buttonStatus >> 1) & 1; _status->rightButtonDown = (buttonStatus >> 1) & 1;
} }

3
setup.sh Normal file
View File

@ -0,0 +1,3 @@
export WATCOM=~/Applications/open-watcom-v2/rel
export INCLUDE=$WATCOM/h
export PATH=$WATCOM/binl64:$WATCOM/binl:$PATH

Binary file not shown.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 39 KiB

After

Width:  |  Height:  |  Size: 39 KiB