Skip to content

Commit 79ab40a

Browse files
authored
Diggers and Special diggers configurable (#3209)
- who is an imp now? - I know I am but what are you? Also, new script command: 'SET_DIGGER([player],(creature])`
1 parent 95824bf commit 79ab40a

27 files changed

+179
-171
lines changed

config/creatrs/imp.cfg

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -113,7 +113,8 @@ SpellImmunity = 0
113113
; FLYING - creature normally isn't touching ground when moving and can move up and down.
114114
; SEE_INVISIBLE - creature has natural ability which works like Sight spell.
115115
; PASS_LOCKED_DOORS - creature can move through locked doors and won't fight with doors.
116-
; SPECIAL_DIGGER - creature can dig and perform other dungeon tasks.
116+
; SPECIAL_DIGGER - creature is different from 'real' creatures can dig and perform other dungeon tasks. Like an Imp.
117+
; DIGGING_CREATURE - creature is a 'real' creature but can also dig and perform other dungeon task. Like a Tunneller.
117118
; ARACHNID - creature is kind of spider.
118119
; DIPTERA - creature is kind of fly.
119120
; LORD - creature is lord of the land, usually arrives to level as final boss, and at arrival you can hear "beware, the lord of the land approaches".

config/creatrs/tunneller.cfg

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ DamageToBoulder = 20
3030
; Creature thing size - XY and Z, one cube is 256x256.
3131
ThingSize = 240 400
3232
LairObject = LAIR_TUNLR
33-
Properties = BLEEDS HUMANOID_SKELETON SPECIAL_DIGGER
33+
Properties = BLEEDS HUMANOID_SKELETON DIGGING_CREATURE
3434

3535
[attraction]
3636
EntranceRoom = NULL NULL NULL

src/config_creature.c

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2005,6 +2005,11 @@ TbBool set_creature_available(PlayerNumber plyr_idx, ThingModel crtr_model, long
20052005

20062006
ThingModel get_players_special_digger_model(PlayerNumber plyr_idx)
20072007
{
2008+
struct PlayerInfo* player = get_player(plyr_idx);
2009+
2010+
if(player->special_digger != 0)
2011+
return player->special_digger;
2012+
20082013
ThingModel crmodel;
20092014

20102015
if (player_is_roaming(plyr_idx))
@@ -2198,9 +2203,9 @@ CreatureJob get_job_for_subtile(const struct Thing *creatng, MapSubtlCoord stl_x
21982203
}
21992204
if (creatng->owner == slabmap_owner(slb))
22002205
{
2201-
if (thing_is_creature_special_digger(creatng))
2206+
if (thing_is_creature_digger(creatng))
22022207
{
2203-
if (creatng->model == get_players_special_digger_model(creatng->owner))
2208+
if (creature_is_for_dungeon_diggers_list(creatng))
22042209
{
22052210
required_kind_flags |= JoKF_OwnedDiggers;
22062211
}
@@ -2223,7 +2228,7 @@ CreatureJob get_job_for_subtile(const struct Thing *creatng, MapSubtlCoord stl_x
22232228
}
22242229
} else
22252230
{
2226-
if (creatng->model == get_players_special_digger_model(creatng->owner)) {
2231+
if (creature_is_for_dungeon_diggers_list(creatng)) {
22272232
required_kind_flags |= JoKF_EnemyDiggers;
22282233
} else {
22292234
required_kind_flags |= JoKF_EnemyCreatures;

src/config_creature.h

Lines changed: 21 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -41,26 +41,27 @@ extern "C" {
4141
#define CREATURE_PROPERTY_INCREASE_ON_EXP 35
4242
/******************************************************************************/
4343
enum CreatureModelFlags {
44-
CMF_IsSpecDigger = 0x000001, // Imp and Tunneller.
45-
CMF_IsArachnid = 0x000002, // Simply, Spider.
46-
CMF_IsDiptera = 0x000004, // Simply, Fly.
47-
CMF_IsLordOfLand = 0x000008, // Simply, Knight and Avatar.
48-
CMF_IsSpectator = 0x000010, // Simply, Floating Spirit.
49-
CMF_IsEvil = 0x000020, // All evil creatures.
50-
CMF_ImmuneToBoulder = 0x000040, // Boulder traps are destroyed at the moment they touch the creature.
51-
CMF_NoCorpseRotting = 0x000080, // Corpse cannot rot in graveyard.
52-
CMF_NoEnmHeartAttack = 0x000100, // Creature will not attack enemy heart on sight.
53-
CMF_Trembling = 0x000200, // Creature causes ground to tremble when dropped.
54-
CMF_Fat = 0x000400, // Creature too fat to walk a full animation.
55-
CMF_Female = 0x000800, // Creature is female.
56-
CMF_Insect = 0x001000, // Creature is kind of insect.
57-
CMF_OneOfKind = 0x002000, // Only one creature of that kind may exist on one level. Unit name is type name.
58-
CMF_NoImprisonment = 0x004000, // Creature will not faint.
59-
CMF_NoResurrect = 0x008000, // Creature will not resurrect.
60-
CMF_NoTransfer = 0x010000, // Creature cannot be transferred.
61-
CMF_NoStealHero = 0x020000, // Prevent the creature from being stolen with the Steal Hero special.
62-
CMF_PreferSteal = 0x040000, // The creature can be generated from Steal Hero special if there's nothing to steal.
63-
CMF_EventfulDeath = 0x080000, // The LAST_DEATH_EVENT[] script location is updated on death.
44+
CMF_IsSpecDigger = 0x000001, // is a dedicated digger that doesn't do things normal units do (like imp)
45+
CMF_IsArachnid = 0x000002, // Simply, Spider.
46+
CMF_IsDiptera = 0x000004, // Simply, Fly.
47+
CMF_IsLordOfLand = 0x000008, // Simply, Knight and Avatar.
48+
CMF_IsSpectator = 0x000010, // Simply, Floating Spirit.
49+
CMF_IsEvil = 0x000020, // All evil creatures.
50+
CMF_ImmuneToBoulder = 0x000040, // Boulder traps are destroyed at the moment they touch the creature.
51+
CMF_NoCorpseRotting = 0x000080, // Corpse cannot rot in graveyard.
52+
CMF_NoEnmHeartAttack = 0x000100, // Creature will not attack enemy heart on sight.
53+
CMF_Trembling = 0x000200, // Creature causes ground to tremble when dropped.
54+
CMF_Fat = 0x000400, // Creature too fat to walk a full animation.
55+
CMF_Female = 0x000800, // Creature is female.
56+
CMF_Insect = 0x001000, // Creature is kind of insect.
57+
CMF_OneOfKind = 0x002000, // Only one creature of that kind may exist on one level. Unit name is type name.
58+
CMF_NoImprisonment = 0x004000, // Creature will not faint.
59+
CMF_NoResurrect = 0x008000, // Creature will not resurrect.
60+
CMF_NoTransfer = 0x010000, // Creature cannot be transferred.
61+
CMF_NoStealHero = 0x020000, // Prevent the creature from being stolen with the Steal Hero special.
62+
CMF_PreferSteal = 0x040000, // The creature can be generated from Steal Hero special if there's nothing to steal.
63+
CMF_EventfulDeath = 0x080000, // The LAST_DEATH_EVENT[] script location is updated on death.
64+
CMF_IsDiggingCreature = 0x100000, // unit still counts as a regular creature but can also do digger tasks (like tunneler)
6465
};
6566

6667
// Before C23 standard, we cannot specify the underlaying type (in this case we want 64bit int) of enum.

src/config_crtrmodel.c

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,7 @@ const struct NamedCommand creatmodel_properties_commands[] = {
126126
{"NO_STEAL_HERO", 32},
127127
{"PREFER_STEAL", 33},
128128
{"EVENTFUL_DEATH", 34},
129+
{"DIGGING_CREATURE", 35},
129130
{NULL, 0},
130131
};
131132

@@ -748,6 +749,10 @@ TbBool parse_creaturemodel_attributes_blocks(long crtr_model,char *buf,long len,
748749
crconf->model_flags |= CMF_EventfulDeath;
749750
n++;
750751
break;
752+
case 35: // DIGGING_CREATURE
753+
crconf->model_flags |= CMF_IsDiggingCreature;
754+
n++;
755+
break;
751756
default:
752757
CONFWRNLOG("Incorrect value of \"%s\" parameter \"%s\" in [%s] block of %s %s file.",
753758
COMMAND_TEXT(cmd_num),word_buf,block_buf, creature_code_name(crtr_model), config_textname);
@@ -904,7 +909,7 @@ TbBool parse_creaturemodel_attributes_blocks(long crtr_model,char *buf,long len,
904909
}
905910
#undef COMMAND_TEXT
906911
// If the creature is a special breed, then update an attribute in CreatureConfig struct
907-
if ((crconf->model_flags & CMF_IsSpecDigger) != 0)
912+
if ((crconf->model_flags & (CMF_IsSpecDigger|CMF_IsDiggingCreature)) != 0)
908913
{
909914
if ((crconf->model_flags & CMF_IsEvil) != 0) {
910915
game.conf.crtr_conf.special_digger_evil = crtr_model;
@@ -917,7 +922,7 @@ TbBool parse_creaturemodel_attributes_blocks(long crtr_model,char *buf,long len,
917922
game.conf.crtr_conf.spectator_breed = crtr_model;
918923
}
919924
// Set creature start states based on the flags
920-
if ((crconf->model_flags & CMF_IsSpecDigger) != 0)
925+
if ((crconf->model_flags & (CMF_IsSpecDigger|CMF_IsDiggingCreature)) != 0)
921926
{
922927
crstat->evil_start_state = CrSt_ImpDoingNothing;
923928
crstat->good_start_state = CrSt_TunnellerDoingNothing;

src/creature_groups.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -324,7 +324,7 @@ TbBool remove_creature_from_group_without_leader_consideration(struct Thing *cre
324324
static short creature_could_be_lead_digger(struct Thing* creatng, struct CreatureControl* cctrl)
325325
{
326326
short potential_leader = 0;
327-
if (thing_is_creature_special_digger(creatng))
327+
if (thing_is_creature_digger(creatng))
328328
{
329329
if (cctrl->party_objective != CHeroTsk_DefendParty)
330330
{
@@ -406,7 +406,7 @@ struct Thing* get_best_creature_to_lead_group(struct Thing* grptng)
406406
TRACE_THING(ctng);
407407
if (has_digger > 0)
408408
{
409-
is_digger = thing_is_creature_special_digger(ctng);
409+
is_digger = thing_is_creature_digger(ctng);
410410
}
411411
cctrl = creature_control_get_from_thing(ctng);
412412
struct CreatureControl* bcctrl = creature_control_get_from_thing(best_creatng);

src/creature_jobs.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -496,7 +496,7 @@ TbBool is_correct_owner_to_perform_job(const struct Thing *creatng, PlayerNumber
496496
// We need to check for it later in upper function, because lack of related room may generate message for the player
497497
if (creatng->owner == plyr_idx)
498498
{
499-
if (creatng->model == get_players_special_digger_model(creatng->owner)) {
499+
if (creature_is_for_dungeon_diggers_list(creatng)) {
500500
if ((get_flags_for_job(new_job) & JoKF_OwnedDiggers) == 0)
501501
return false;
502502
} else {
@@ -505,7 +505,7 @@ TbBool is_correct_owner_to_perform_job(const struct Thing *creatng, PlayerNumber
505505
}
506506
} else
507507
{
508-
if (creatng->model == get_players_special_digger_model(creatng->owner)) {
508+
if (creature_is_for_dungeon_diggers_list(creatng)) {
509509
if ((get_flags_for_job(new_job) & JoKF_EnemyDiggers) == 0)
510510
return false;
511511
} else {
@@ -995,7 +995,7 @@ TbBool attempt_job_work_in_room_near_pos(struct Thing *creatng, MapSubtlCoord st
995995
}
996996
creatng->continue_state = get_arrive_at_state_for_job(new_job);
997997
cctrl->target_room_id = room->index;
998-
if (thing_is_creature_special_digger(creatng))
998+
if (thing_is_creature_digger(creatng))
999999
{
10001000
cctrl->digger.task_repeats = 0;
10011001
cctrl->job_assigned = new_job;
@@ -1020,7 +1020,7 @@ TbBool attempt_job_work_in_room_and_cure_near_pos(struct Thing *creatng, MapSubt
10201020
creatng->continue_state = get_arrive_at_state_for_job(new_job);
10211021
cctrl->target_room_id = room->index;
10221022
process_temple_cure(creatng);
1023-
if (thing_is_creature_special_digger(creatng))
1023+
if (thing_is_creature_digger(creatng))
10241024
{
10251025
cctrl->digger.task_repeats = 0;
10261026
cctrl->job_assigned = new_job;

src/creature_states.c

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -479,8 +479,8 @@ struct StateInfo states[CREATURE_STATES_COUNT] = {
479479
* - 1: Working.
480480
* - 2: Fighting.
481481
*/
482-
long const state_type_to_gui_state[] = {
483-
0, 1, 0, 0, 0, 2, 0, 0, 1, 0, 0, 2, 2, 1, 1, 0,
482+
long const state_type_to_gui_state[STATE_TYPES_COUNT] = {
483+
0, 1, 0, 0, 0, 2, 0, 0, 1, 0, 0, 2, 2, 1, 1,
484484
};
485485

486486
/******************************************************************************/
@@ -1539,7 +1539,7 @@ short creature_being_dropped(struct Thing *creatng)
15391539
if (!creature_under_spell_effect(creatng, CSAfF_Chicken))
15401540
{
15411541
// Special tasks for diggers
1542-
if ((get_creature_model_flags(creatng) & CMF_IsSpecDigger) != 0)
1542+
if (thing_is_creature_digger(creatng))
15431543
{
15441544
if ((slabmap_owner(slb) == creatng->owner) || (slabmap_owner(slb) == game.neutral_player_num))
15451545
{
@@ -3728,7 +3728,7 @@ CrCheckRet move_check_persuade(struct Thing *creatng)
37283728
!thing_is_invalid(i);
37293729
i = thing_get(i->next_on_mapblk) )
37303730
{
3731-
if (i->owner != creatng->owner || !thing_is_creature(i) || i == creatng || i->model == get_players_special_digger_model(creatng->owner))
3731+
if (i->owner != creatng->owner || !thing_is_creature(i) || i == creatng || creature_is_for_dungeon_diggers_list(i))
37323732
continue;
37333733
i_leader = get_group_leader(i);
37343734
if (i_leader)
@@ -4825,7 +4825,7 @@ short set_start_state_f(struct Thing *thing,const char *func_name)
48254825
if (player->victory_state == VicS_LostLevel)
48264826
{
48274827
// TODO: Correctly deal with possession of creatures not owned by the player
4828-
if (thing->model != get_players_special_digger_model(player->id_number))
4828+
if (!creature_is_for_dungeon_diggers_list(thing))
48294829
{
48304830
cleanup_current_thing_state(thing);
48314831
initialise_thing_state(thing, CrSt_LeavesBecauseOwnerLost);

src/creature_states.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,12 @@
2121

2222
#include "bflib_basics.h"
2323
#include "globals.h"
24-
#include "dungeon_data.h"
2524

2625
/** Count of creature states, originally 147. */
2726
#define CREATURE_STATES_COUNT CrSt_ListEnd
2827

2928
#define FIGHT_FEAR_DELAY 160
29+
#define STATE_TYPES_COUNT CrStTyp_ListEnd
3030

3131
#ifdef __cplusplus
3232
extern "C" {

src/creature_states_combt.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,7 @@ TbBool creature_is_being_attacked_by_enemy_creature_not_digger(struct Thing *fig
130130
for (oppn_idx = 0; oppn_idx < COMBAT_MELEE_OPPONENTS_LIMIT; oppn_idx++)
131131
{
132132
struct Thing* enmtng = thing_get(figctrl->opponents_melee[oppn_idx]);
133-
if (!thing_is_invalid(enmtng) && !thing_is_creature_special_digger(enmtng))
133+
if (!thing_is_invalid(enmtng) && !thing_is_creature_digger(enmtng))
134134
{
135135
if (players_are_enemies(fightng->owner,enmtng->owner)) {
136136
return true;
@@ -141,7 +141,7 @@ TbBool creature_is_being_attacked_by_enemy_creature_not_digger(struct Thing *fig
141141
for (oppn_idx = 0; oppn_idx < COMBAT_RANGED_OPPONENTS_LIMIT; oppn_idx++)
142142
{
143143
struct Thing* enmtng = thing_get(figctrl->opponents_ranged[oppn_idx]);
144-
if (!thing_is_invalid(enmtng) && !thing_is_creature_special_digger(enmtng))
144+
if (!thing_is_invalid(enmtng) && !thing_is_creature_digger(enmtng))
145145
{
146146
if (players_are_enemies(fightng->owner,enmtng->owner)) {
147147
return true;

0 commit comments

Comments
 (0)