Draw gun in character previews

This commit is contained in:
Cong
2021-06-12 16:53:05 +10:00
parent ccc249c5d7
commit 5ea4fd61b5
12 changed files with 49 additions and 37 deletions

View File

@@ -819,7 +819,7 @@ static void DrawPlayerSummary(
DisplayCharacterAndName(
svec2i_add(pos, svec2i(size.x / 4, size.y / 2)), &data->Pd->Char,
DIRECTION_DOWN, data->Pd->name, colorWhite);
DIRECTION_DOWN, data->Pd->name, colorWhite, data->Pd->guns[0]);
if (data->Pd->survived)
{

View File

@@ -164,7 +164,7 @@ ActorPics GetCharacterPicsFromActor(TActor *a)
static const Pic *GetBodyPic(
PicManager *pm, const CharSprites *cs, const direction_e dir,
const ActorAnimation anim, const int frame, const int numBarrels,
const CharColors *colors);
const int grips, const CharColors *colors);
static const Pic *GetLegsPic(
PicManager *pm, const CharSprites *cs, const direction_e dir,
const ActorAnimation anim, const int frame, const CharColors *colors);
@@ -240,6 +240,7 @@ ActorPics GetCharacterPics(
break;
}
}
const int grips = gun == NULL ? 0 : gun->Grips;
pics.Head = GetHeadPic(c->Class, headDir, grimace, colors);
pics.HeadOffset = GetActorDrawOffset(
pics.Head, BODY_PART_HEAD, c->Class->Sprites, anim, frame, dir,
@@ -269,7 +270,7 @@ ActorPics GetCharacterPics(
// Body
pics.Body = GetBodyPic(
&gPicManager, c->Class->Sprites, dir, anim, frame, numBarrels, colors);
&gPicManager, c->Class->Sprites, dir, anim, frame, numBarrels, grips, colors);
pics.BodyOffset = GetActorDrawOffset(
pics.Body, BODY_PART_BODY, c->Class->Sprites, anim, frame, dir,
GUNSTATE_READY);
@@ -480,7 +481,7 @@ const Pic *GetHairPic(
static const Pic *GetBodyPic(
PicManager *pm, const CharSprites *cs, const direction_e dir,
const ActorAnimation anim, const int frame, const int numBarrels,
const CharColors *colors)
const int grips, const CharColors *colors)
{
const int stride = anim == ACTORANIMATION_WALKING ? 8 : 1;
const int col = frame % stride;
@@ -488,13 +489,10 @@ static const Pic *GetBodyPic(
const int idx = col + row * stride;
char buf[CDOGS_PATH_MAX];
CASSERT(numBarrels <= 2, "up to 2 barrels supported");
const char *upperPose = "";
const NamedSprites *ns = NULL;
if (numBarrels == 1)
{
upperPose = "_handgun";
}
else if (numBarrels == 2)
const char *upperPose = "_handgun";
// TODO: 2 grip firing pic
if (numBarrels == 2 || grips == 2)
{
upperPose = "_dualgun";
}
@@ -507,7 +505,7 @@ static const Pic *GetBodyPic(
// Get or generate masked sprites
ns = PicManagerGetCharSprites(pm, buf, colors);
// TODO: provide dualgun sprites for all body types
if (ns == NULL && numBarrels == 2)
if (ns == NULL && strcmp(upperPose, "_dualgun") == 0)
{
upperPose = "_handgun";
continue;
@@ -552,11 +550,11 @@ static const Pic *GetDeathPic(PicManager *pm, const int frame)
void DrawCharacterSimple(
const Character *c, const struct vec2i pos, const direction_e d,
const bool hilite, const bool showGun)
const bool hilite, const bool showGun, const WeaponClass *gun)
{
const gunstate_e barrelStates[MAX_BARRELS] = { GUNSTATE_READY, GUNSTATE_READY };
ActorPics pics = GetCharacterPics(
c, d, d, ACTORANIMATION_IDLE, 0, NULL, barrelStates, false,
c, d, d, ACTORANIMATION_IDLE, 0, gun, barrelStates, false,
colorBlack, NULL, NULL, 0);
DrawActorPics(&pics, pos, Rect2iZero());
if (hilite)

View File

@@ -77,7 +77,7 @@ typedef struct
void DrawCharacterSimple(
const Character *c, const struct vec2i pos, const direction_e d,
const bool hilite, const bool showGun);
const bool hilite, const bool showGun, const WeaponClass *gun);
void DrawHead(
SDL_Renderer *renderer, const Character *c, const direction_e dir,
const struct vec2i pos);

View File

@@ -161,6 +161,8 @@ static void LoadGunDescription(
}
CFREE(tmp);
}
wc->Grips = 1;
LoadInt(&wc->Grips, node, "Grips");
LoadBool(&wc->IsGrenade, node, "IsGrenade");

View File

@@ -67,6 +67,7 @@ typedef struct
{
char *Sprites;
const Pic *Icon;
int Grips;
bool IsGrenade;
char *name;
char *Description;

View File

@@ -412,10 +412,11 @@ static void MissionDrawEnemy(
}
const CharacterStore *store = &data->co->Setting.characters;
const int charIndex = *(int *)CArrayGet(&store->baddieIds, data->index);
const Character *ch = CArrayGet(&store->OtherChars, charIndex);
DrawCharacterSimple(
CArrayGet(&store->OtherChars, charIndex),
ch,
svec2i_add(svec2i_add(pos, o->Pos), svec2i_scale_divide(o->Size, 2)),
DIRECTION_DOWN, UIObjectIsHighlighted(o), true);
DIRECTION_DOWN, UIObjectIsHighlighted(o), true, ch->Gun);
}
static void MissionDrawSpecialChar(
UIObject *o, GraphicsDevice *g, struct vec2i pos, void *vData)
@@ -431,10 +432,11 @@ static void MissionDrawSpecialChar(
}
const CharacterStore *store = &data->co->Setting.characters;
const int charIndex = CharacterStoreGetSpecialId(store, data->index);
const Character *ch = CArrayGet(&store->OtherChars, charIndex);
DrawCharacterSimple(
CArrayGet(&store->OtherChars, charIndex),
ch,
svec2i_add(svec2i_add(pos, o->Pos), svec2i_scale_divide(o->Size, 2)),
DIRECTION_DOWN, UIObjectIsHighlighted(o), true);
DIRECTION_DOWN, UIObjectIsHighlighted(o), true, ch->Gun);
}
static void MissionDrawMapItem(
UIObject *o, GraphicsDevice *g, struct vec2i pos, void *vData)

View File

@@ -490,11 +490,11 @@ static void MissionDrawKillObjective(
CharacterStore *store = &data->co->Setting.characters;
if (store->specialIds.size > 0)
{
Character *c = CArrayGet(
const Character *c = CArrayGet(
&store->OtherChars, CharacterStoreGetSpecialId(store, 0));
const struct vec2i drawPos = svec2i_add(
svec2i_add(pos, o->Pos), svec2i_scale_divide(o->Size, 2));
DrawCharacterSimple(c, drawPos, DIRECTION_DOWN, false, true);
DrawCharacterSimple(c, drawPos, DIRECTION_DOWN, false, true, c->Gun);
}
}
static void MissionDrawCollectObjective(
@@ -551,11 +551,11 @@ static void MissionDrawRescueObjective(
CharacterStore *store = &data->co->Setting.characters;
if (store->prisonerIds.size > 0)
{
Character *c = CArrayGet(
const Character *c = CArrayGet(
&store->OtherChars, CharacterStoreGetPrisonerId(store, 0));
const struct vec2i drawPos = svec2i_add(
svec2i_add(pos, o->Pos), svec2i_scale_divide(o->Size, 2));
DrawCharacterSimple(c, drawPos, DIRECTION_DOWN, false, true);
DrawCharacterSimple(c, drawPos, DIRECTION_DOWN, false, true, c->Gun);
}
}

View File

@@ -132,11 +132,11 @@ static void DrawCharacter(
UNUSED(g);
EditorBrushAndCampaign *data = vData;
CharacterStore *store = &data->Campaign->Setting.characters;
Character *c = CArrayGet(&store->OtherChars, data->Brush.u.ItemIndex);
const Character *c = CArrayGet(&store->OtherChars, data->Brush.u.ItemIndex);
DrawCharacterSimple(
c,
svec2i_add(svec2i_add(pos, o->Pos), svec2i_scale_divide(o->Size, 2)),
DIRECTION_DOWN, false, false);
DIRECTION_DOWN, false, false, c->Gun);
}
static void DrawObjective(
UIObject *o, GraphicsDevice *g, struct vec2i pos, void *vData)
@@ -154,17 +154,17 @@ static void DrawObjective(
switch (obj->Type)
{
case OBJECTIVE_KILL: {
Character *c = CArrayGet(
const Character *c = CArrayGet(
&store->OtherChars,
CharacterStoreGetSpecialId(store, data->Brush.Index2));
DrawCharacterSimple(c, pos, DIRECTION_DOWN, false, false);
DrawCharacterSimple(c, pos, DIRECTION_DOWN, false, false, c->Gun);
}
break;
case OBJECTIVE_RESCUE: {
Character *c = CArrayGet(
const Character *c = CArrayGet(
&store->OtherChars,
CharacterStoreGetPrisonerId(store, data->Brush.Index2));
DrawCharacterSimple(c, pos, DIRECTION_DOWN, false, false);
DrawCharacterSimple(c, pos, DIRECTION_DOWN, false, false, c->Gun);
}
break;
case OBJECTIVE_COLLECT: {

View File

@@ -39,13 +39,13 @@
// centered around the target position
void DisplayCharacterAndName(
struct vec2i pos, const Character *c, const direction_e d,
const char *name, const color_t color)
const char *name, const color_t color, const WeaponClass *gun)
{
// Move the point down a bit since the default character draw point is at
// its feet
pos.y += 8;
struct vec2i namePos = svec2i_add(pos, svec2i(-FontStrW(name) / 2, -30));
DrawCharacterSimple(c, pos, d, false, false);
DrawCharacterSimple(c, pos, d, false, false, gun);
FontStrMask(name, namePos, color);
}
@@ -72,8 +72,13 @@ void MenuDisplayPlayer(
{
strcpy(s, pData->name);
}
const WeaponClass *gun = NULL;
if (d->GunIdx >= 0)
{
gun = pData->guns[d->GunIdx];
}
DisplayCharacterAndName(playerPos, &pData->Char, d->Dir, s, colorWhite);
DisplayCharacterAndName(playerPos, &pData->Char, d->Dir, s, colorWhite, gun);
}
void MenuDisplayPlayerControls(

View File

@@ -2,7 +2,7 @@
C-Dogs SDL
A port of the legendary (and fun) action/arcade cdogs.
Copyright (c) 2013-2016, Cong Xu
Copyright (c) 2013-2016, 2021 Cong Xu
All rights reserved.
Redistribution and use in source and binary forms, with or without
@@ -37,6 +37,7 @@ typedef struct
int PlayerUID;
menu_t **currentMenu;
direction_e Dir;
int GunIdx;
} MenuDisplayPlayerData;
void MenuDisplayPlayer(
const menu_t *menu, GraphicsDevice *g,
@@ -49,4 +50,4 @@ void MenuDisplayPlayerControls(
void DisplayCharacterAndName(
struct vec2i pos, const Character *c, const direction_e d,
const char *name, const color_t color);
const char *name, const color_t color, const WeaponClass *gun);

View File

@@ -232,7 +232,7 @@ static void PlayerListCustomDraw(
// Draw the players offset on alternate rows
DisplayCharacterAndName(
svec2i(x + (i & 1) * 16, y + 4), &p->Char, DIRECTION_DOWN, p->name,
textColor);
textColor, p->guns[0]);
// Draw score
x += 100;

View File

@@ -92,10 +92,10 @@ static void DisplayGunIcon(
const struct vec2i size, const void *data);
static void AddEquippedMenuItem(
menu_t *menu, const PlayerData *p, const int slot, const bool enabled);
static void PostInputRotatePlayer(menu_t *menu, int cmd, void *data)
static void PostInputEquipMenu(menu_t *menu, int cmd, void *data)
{
UNUSED(menu);
MenuDisplayPlayerData *d = data;
// Rotate player using left/right keys
const int dx = (cmd & CMD_LEFT) ? 1 : ((cmd & CMD_RIGHT) ? -1 : 0);
if (dx != 0)
@@ -107,6 +107,9 @@ static void PostInputRotatePlayer(menu_t *menu, int cmd, void *data)
sprintf(buf, "footsteps/%s", p->Char.Class->Footsteps);
SoundPlay(&gSoundDevice, StrSound(buf));
}
// Display gun based on menu index
d->GunIdx = MIN(menu->u.normal.index, MAX_WEAPONS);
}
static void CreateEquippedWeaponsMenu(
MenuSystem *ms, EventHandlers *handlers, GraphicsDevice *g,
@@ -156,7 +159,7 @@ static void CreateEquippedWeaponsMenu(
ms->root, MenuCreateNormal(END_MENU_LABEL, "", MENU_TYPE_NORMAL, 0));
MenuSetCustomDisplay(ms->root, DisplayGunIcon, NULL);
MenuSetPostInputFunc(ms->root, PostInputRotatePlayer, display);
MenuSetPostInputFunc(ms->root, PostInputEquipMenu, display);
// Pre-select the End menu
ms->root->u.normal.index = (int)(ms->root->u.normal.subMenus.size - 1);