diff --git a/rsrc/dialogs/edit-terrain.xml b/rsrc/dialogs/edit-terrain.xml
index 9e93ba8c..11db7637 100644
--- a/rsrc/dialogs/edit-terrain.xml
+++ b/rsrc/dialogs/edit-terrain.xml
@@ -41,6 +41,7 @@
Transform to what?
+
Ground type:
@@ -81,6 +82,7 @@
*flag1
+
*flag2
@@ -91,10 +93,11 @@
Combat Arena:
+
- Map icon:
-
-
+ Map icon:
+
+
diff --git a/rsrc/dialogs/pick-spec-type.xml b/rsrc/dialogs/pick-spec-type.xml
new file mode 100644
index 00000000..bf8da718
--- /dev/null
+++ b/rsrc/dialogs/pick-spec-type.xml
@@ -0,0 +1,14 @@
+
+
+
\ No newline at end of file
diff --git a/rsrc/strings/ter-flag1.txt b/rsrc/strings/ter-flag1.txt
index 9c831a13..1d73517d 100644
--- a/rsrc/strings/ter-flag1.txt
+++ b/rsrc/strings/ter-flag1.txt
@@ -1,6 +1,6 @@
Small Icon
What to change to?
-Amount of damage done
+Sides per die
Unused
Graphic when occupied
Strength (1-8)
@@ -13,8 +13,8 @@ Unused
Number of special to call
Unused
Unused
-Unused
-Unused
+Number of Dice
+Number of Dice
Direction
Direction
Direction
diff --git a/rsrc/strings/ter-flag2.txt b/rsrc/strings/ter-flag2.txt
index b76c19af..98911f94 100644
--- a/rsrc/strings/ter-flag2.txt
+++ b/rsrc/strings/ter-flag2.txt
@@ -1,16 +1,16 @@
Unused
Number of sound (99 - no sound)
-Damage multiplier
+Number of Dice
Unused
Unused
Percentage chance
Unused
-Strength
+Method
Unused
Difficulty (0-4 L, 5-9 M, 10 I)
Unused
Unused
-Type of special (0 - local, 1 - town/global, 2 - out/global, 3 - global)
+Type of special (0 - global, 1 - local)
Unused
Unused
Unused
@@ -21,4 +21,4 @@ Unused
Unused
Unused
Number of sound (99 - no sound)
-Type of special (0 - local, 1 - town/global, 2 - out/global, 3 - global)
\ No newline at end of file
+Type of special (0 - global, 1 - local)
\ No newline at end of file
diff --git a/rsrc/strings/ter-flag3.txt b/rsrc/strings/ter-flag3.txt
index 24cb6bff..e89aa1e5 100644
--- a/rsrc/strings/ter-flag3.txt
+++ b/rsrc/strings/ter-flag3.txt
@@ -5,7 +5,7 @@ Unused
Unused
Status type
Unused
-Method (1 - Move Mountains, 2 - quickfire, 0 - either)
+Unused
Unused
Can be bashed? (0 - can't, 1 - can)
Unused
diff --git a/src/boe.actions.cpp b/src/boe.actions.cpp
index efd0baa7..2b937c15 100644
--- a/src/boe.actions.cpp
+++ b/src/boe.actions.cpp
@@ -2506,7 +2506,7 @@ void handle_hunting() {
for(int i = 0; i < 6; i++)
if(univ.party[i].is_alive() && univ.party[i].traits[trait] && get_ran(1,0,12) == 5) {
- univ.party.food += get_ran(2,1,6);
+ univ.party.food += get_ran(univ.scenario.ter_types[ter].flag1,1,6);
add_string_to_buf(univ.party[i].name + "hunts.");
put_pc_screen();
}
@@ -2670,11 +2670,11 @@ static eDirection find_waterfall(short x, short y, short mode){
if(mode == 0){
eTerSpec spec = univ.scenario.ter_types[univ.town->terrain(x + dir_x_dif[i],y + dir_y_dif[i])].special;
to_dir[i] = spec == eTerSpec::WATERFALL_CAVE || spec == eTerSpec::WATERFALL_SURFACE;
- if(univ.scenario.ter_types[univ.town->terrain(x + dir_x_dif[i],y + dir_y_dif[i])].flag1.u != i) to_dir[i] = false;
+ if(univ.scenario.ter_types[univ.town->terrain(x + dir_x_dif[i],y + dir_y_dif[i])].flag1 != i) to_dir[i] = false;
}else{
eTerSpec spec = univ.scenario.ter_types[univ.out[x + dir_x_dif[i]][y + dir_y_dif[i]]].special;
to_dir[i] = spec == eTerSpec::WATERFALL_CAVE || spec == eTerSpec::WATERFALL_SURFACE;
- if(univ.scenario.ter_types[univ.out[x + dir_x_dif[i]][y + dir_y_dif[i]]].flag1.u != i) to_dir[i] = false;
+ if(univ.scenario.ter_types[univ.out[x + dir_x_dif[i]][y + dir_y_dif[i]]].flag1 != i) to_dir[i] = false;
}
}
short count = 0;
diff --git a/src/boe.combat.cpp b/src/boe.combat.cpp
index 5eb20548..f2bbae61 100644
--- a/src/boe.combat.cpp
+++ b/src/boe.combat.cpp
@@ -5081,10 +5081,10 @@ void process_fields() {
for(j = r.top + 1; j < r.bottom ; j++)
if(qf[i][j] > 0) {
ter_num_t ter = univ.town->terrain(i,j);
- if(univ.scenario.ter_types[ter].special == eTerSpec::CRUMBLING && univ.scenario.ter_types[ter].flag3.u > 0) {
+ if(univ.scenario.ter_types[ter].special == eTerSpec::CRUMBLING && univ.scenario.ter_types[ter].flag2 > 0) {
// TODO: This seems like the wrong sound
play_sound(60);
- univ.town->terrain(i,j) = univ.scenario.ter_types[ter].flag1.u;
+ univ.town->terrain(i,j) = univ.scenario.ter_types[ter].flag1;
add_string_to_buf(" Quickfire burns through barrier.");
}
univ.town.set_quickfire(i,j,true);
diff --git a/src/boe.graphics.cpp b/src/boe.graphics.cpp
index 6b8862a2..84c89f3c 100644
--- a/src/boe.graphics.cpp
+++ b/src/boe.graphics.cpp
@@ -1254,7 +1254,7 @@ void draw_trim(short q,short r,short which_trim,ter_num_t ground_ter) {
bool extend_road_terrain(ter_num_t ter) {
eTrimType trim = univ.scenario.ter_types[ter].trim_type;
eTerSpec spec = univ.scenario.ter_types[ter].special;
- ter_num_t flag = univ.scenario.ter_types[ter].flag1.u;
+ ter_num_t flag = univ.scenario.ter_types[ter].flag1;
if(trim == eTrimType::ROAD || trim == eTrimType::CITY || trim == eTrimType::WALKWAY)
return true;
if(spec == eTerSpec::BRIDGE)
@@ -1263,7 +1263,7 @@ bool extend_road_terrain(ter_num_t ter) {
return true; // cave entrance, most likely
if(spec == eTerSpec::UNLOCKABLE || spec == eTerSpec::CHANGE_WHEN_STEP_ON)
return true; // closed door, possibly locked; or closed portcullis
- if(spec == eTerSpec::CHANGE_WHEN_USED && univ.scenario.ter_types[flag].special == eTerSpec::CHANGE_WHEN_STEP_ON && univ.scenario.ter_types[flag].flag1.u == ter)
+ if(spec == eTerSpec::CHANGE_WHEN_USED && univ.scenario.ter_types[flag].special == eTerSpec::CHANGE_WHEN_STEP_ON && univ.scenario.ter_types[flag].flag1 == ter)
return true; // open door (I think) TODO: Verify this works
if(spec == eTerSpec::LOCKABLE)
return true; // open portcullis (most likely)
diff --git a/src/boe.graphutil.cpp b/src/boe.graphutil.cpp
index 53d27e8e..4d268885 100644
--- a/src/boe.graphutil.cpp
+++ b/src/boe.graphutil.cpp
@@ -203,7 +203,7 @@ void draw_monsters() {
(univ.scenario.ter_types[ter].special == eTerSpec::BED) && isHumanoid(univ.town.monst[i].m_type)
&& (univ.town.monst[i].active == 1 || univ.town.monst[i].target == 6) &&
width == 1 && height == 1)
- draw_one_terrain_spot((short) where_draw.x,(short) where_draw.y,10000 + univ.scenario.ter_types[ter].flag1.u);
+ draw_one_terrain_spot((short) where_draw.x,(short) where_draw.y,10000 + univ.scenario.ter_types[ter].flag1);
else if(univ.town.monst[i].picture_num >= 1000) {
bool isParty = univ.town.monst[i].picture_num >= 10000;
sf::Texture* src_gw;
@@ -485,7 +485,7 @@ void draw_party_symbol(location center) {
ter = univ.town->terrain(univ.town.p_loc.x,univ.town.p_loc.y);
// now wedge in bed graphic
if(is_town() && univ.scenario.ter_types[ter].special == eTerSpec::BED)
- draw_one_terrain_spot((short) target.x,(short) target.y,10000 + univ.scenario.ter_types[ter].flag1.u);
+ draw_one_terrain_spot((short) target.x,(short) target.y,10000 + univ.scenario.ter_types[ter].flag1);
else Draw_Some_Item(*from_gw, source_rect, terrain_screen_gworld, target, 1, 0);
}
else if(univ.party.in_boat >= 0) {
diff --git a/src/boe.locutils.cpp b/src/boe.locutils.cpp
index a74e7ea3..59ff70c2 100644
--- a/src/boe.locutils.cpp
+++ b/src/boe.locutils.cpp
@@ -583,19 +583,17 @@ void swap_ter(short i,short j,ter_num_t ter1,ter_num_t ter2) {
}
void alter_space(short i,short j,ter_num_t ter) {
- location l;
-
- l.x = i;
- l.y = j;
-
if(is_out()) {
+ location l(i,j);
l = local_to_global(l);
univ.out[l.x][l.y] = ter;
univ.out->terrain[i][j] = ter;
- }
- else {
+ } else {
+ ter_num_t former = univ.town->terrain(i,j);
univ.town->terrain(i,j) = ter;
- if(univ.scenario.ter_types[univ.town->terrain(i,j)].special == eTerSpec::CONVEYOR)
+ if(univ.scenario.ter_types[ter].special == eTerSpec::CONVEYOR)
univ.town.belt_present = true;
+ if(univ.scenario.ter_types[former].light_radius != univ.scenario.ter_types[ter].light_radius)
+ univ.town->set_up_lights();
}
}
diff --git a/src/boe.main.cpp b/src/boe.main.cpp
index 3f178694..0305c38d 100644
--- a/src/boe.main.cpp
+++ b/src/boe.main.cpp
@@ -628,40 +628,38 @@ void change_cursor(location where_curs) {
void move_sound(ter_num_t ter,short step){
static bool on_swamp = false;
- short pic,snd;
+ short pic;
eTerSpec spec;
pic = univ.scenario.ter_types[ter].picture;
spec = univ.scenario.ter_types[ter].special;
- snd = univ.scenario.ter_types[ter].step_sound;
+ eStepSnd snd = univ.scenario.ter_types[ter].step_sound;
// if on swamp don't play squish sound : BoE legacy behavior, can be removed safely
- if(snd == 4 && !flying() && univ.party.in_boat == 0){
- if(on_swamp && get_ran(1,1,100) >= 10)return;
+ if(snd == eStepSnd::SPLASH && !flying() && univ.party.in_boat < 0){
+ if(on_swamp && get_ran(1,1,100) >= 10) return;
on_swamp = true;
- }else on_swamp = false;
+ } else on_swamp = false;
- if(!monsters_going && (overall_mode < MODE_COMBAT) && (univ.party.in_boat >= 0)) {// is on boat ?
+ if(!monsters_going && (overall_mode < MODE_COMBAT) && (univ.party.in_boat >= 0)) {
if(spec == eTerSpec::TOWN_ENTRANCE)
return;
play_sound(48); //play boat sound
- }
- else if(!monsters_going && (overall_mode < MODE_COMBAT) && (univ.party.in_horse >= 0)) {//// is on horse ?
+ } else if(!monsters_going && (overall_mode < MODE_COMBAT) && (univ.party.in_horse >= 0)) {
play_sound(85); //so play horse sound
- }
- else switch(univ.scenario.ter_types[ter].step_sound){
- case 1:
- play_sound(55); //squish
+ } else switch(univ.scenario.ter_types[ter].step_sound){
+ case eStepSnd::SQUISH:
+ play_sound(55);
break;
- case 2:
- play_sound(47); //crunch
+ case eStepSnd::CRUNCH:
+ play_sound(47);
break;
- case 3:
- break; //silence : do nothing
- case 4:
- play_sound(17); // big splash
+ case eStepSnd::NONE:
break;
- default: //safety footsteps valve
+ case eStepSnd::SPLASH:
+ play_sound(17);
+ break;
+ case eStepSnd::STEP:
if(step % 2 == 0) //footsteps alternate sound
play_sound(49);
else play_sound(50);
diff --git a/src/boe.monster.cpp b/src/boe.monster.cpp
index acfd4dcd..9cd761bf 100644
--- a/src/boe.monster.cpp
+++ b/src/boe.monster.cpp
@@ -891,21 +891,21 @@ bool monst_check_special_terrain(location where_check,short mode,short which_mon
bool do_look = false; // If becomes true, terrain changed, so need to update what party sees
cCreature *which_m;
eTerSpec ter_abil;
- unsigned short ter_flag;
+ unsigned short ter_dir;
from_loc = univ.town.monst[which_monst].cur_loc;
ter = univ.town->terrain(where_check.x,where_check.y);
////
which_m = &univ.town.monst[which_monst];
ter_abil = univ.scenario.ter_types[ter].special;
- ter_flag = univ.scenario.ter_types[ter].flag3.u;
+ ter_dir = univ.scenario.ter_types[ter].flag3;
if(mode > 0 && ter_abil == eTerSpec::CONVEYOR) {
if(
- ((ter_flag == DIR_N) && (where_check.y > from_loc.y)) ||
- ((ter_flag == DIR_E) && (where_check.x < from_loc.x)) ||
- ((ter_flag == DIR_S) && (where_check.y < from_loc.y)) ||
- ((ter_flag == DIR_W) && (where_check.x > from_loc.x)) ) {
+ ((ter_dir == DIR_N) && (where_check.y > from_loc.y)) ||
+ ((ter_dir == DIR_E) && (where_check.x < from_loc.x)) ||
+ ((ter_dir == DIR_S) && (where_check.y < from_loc.y)) ||
+ ((ter_dir == DIR_W) && (where_check.x > from_loc.x)) ) {
return false;
}
}
@@ -1023,10 +1023,10 @@ bool monst_check_special_terrain(location where_check,short mode,short which_mon
case eTerSpec::CHANGE_WHEN_STEP_ON:
can_enter = false;
if(!(monster_placid(which_monst))) {
- univ.town->terrain(where_check.x,where_check.y) = univ.scenario.ter_types[ter].flag1.u;
+ univ.town->terrain(where_check.x,where_check.y) = univ.scenario.ter_types[ter].flag1;
do_look = true;
if(point_onscreen(center,where_check))
- play_sound(univ.scenario.ter_types[ter].flag2.u);
+ play_sound(univ.scenario.ter_types[ter].flag2);
}
break;
@@ -1038,7 +1038,7 @@ bool monst_check_special_terrain(location where_check,short mode,short which_mon
break;
case eTerSpec::DAMAGING:
- switch(eDamageType(ter_flag)) {
+ switch(eDamageType(univ.scenario.ter_types[ter].flag3)) {
case eDamageType::FIRE:
return univ.town.monst[which_monst].fire_res == 0;
case eDamageType::COLD:
diff --git a/src/boe.party.cpp b/src/boe.party.cpp
index 58951008..cabd796f 100644
--- a/src/boe.party.cpp
+++ b/src/boe.party.cpp
@@ -1504,16 +1504,16 @@ void cast_town_spell(location where) {
case eSpell::UNLOCK:
// TODO: Is the unlock spell supposed to have a max range?
if(univ.scenario.ter_types[ter].special == eTerSpec::UNLOCKABLE){
- if(univ.scenario.ter_types[ter].flag2.u == 10)
+ if(univ.scenario.ter_types[ter].flag2 == 10)
r1 = 10000;
else{
r1 = get_ran(1,1,100) - 5 * adj + 5 * univ.town.difficulty;
- r1 += univ.scenario.ter_types[ter].flag2.u * 7;
+ r1 += univ.scenario.ter_types[ter].flag2 * 7;
}
if(r1 < (135 - combat_percent[min(19,univ.party[who_cast].level)])) {
add_string_to_buf(" Door unlocked.");
play_sound(9);
- univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[ter].flag1.u;
+ univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[ter].flag1;
}
else {
play_sound(41);
@@ -1577,10 +1577,10 @@ void crumble_wall(location where) {
if(loc_off_act_area(where))
return;
ter = univ.town->terrain(where.x,where.y);
- if(univ.scenario.ter_types[ter].special == eTerSpec::CRUMBLING && univ.scenario.ter_types[ter].flag3.u < 2) {
+ if(univ.scenario.ter_types[ter].special == eTerSpec::CRUMBLING && univ.scenario.ter_types[ter].flag2 < 2) {
// TODO: This seems like the wrong sound
play_sound(60);
- univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[ter].flag1.u;
+ univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[ter].flag1;
add_string_to_buf(" Barrier crumbles.");
}
diff --git a/src/boe.specials.cpp b/src/boe.specials.cpp
index 496c3497..282c44df 100644
--- a/src/boe.specials.cpp
+++ b/src/boe.specials.cpp
@@ -67,7 +67,6 @@ short store_item_spell_level = 10;
// global values for when processing special encounters
iLiving* current_pc_picked_in_spec_enc = nullptr;
extern std::map skill_max;
-location store_special_loc;
bool special_in_progress = false;
// 0 - can't use 1 - combat only 2 - town only 3 - town & combat only 4 - everywhere 5 - outdoor
@@ -113,7 +112,7 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
short r1,i,door_pc,pic_type = 0,ter_pic = 0;
eTerSpec ter_special;
std::string choice;
- ter_flag_t ter_flag1,ter_flag2,ter_flag3;
+ int ter_flag1,ter_flag2,ter_flag3;
eDamageType dam_type = eDamageType::WEAPON;
bool can_enter = true;
location out_where,from_loc,to_loc;
@@ -150,10 +149,10 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
// TODO: Why not support conveyors outdoors, too?
if(mode != eSpecCtx::OUT_MOVE && ter_special == eTerSpec::CONVEYOR) {
if(
- ((ter_flag3.u == DIR_N) && (where_check.y > from_loc.y)) ||
- ((ter_flag3.u == DIR_E) && (where_check.x < from_loc.x)) ||
- ((ter_flag3.u == DIR_S) && (where_check.y < from_loc.y)) ||
- ((ter_flag3.u == DIR_W) && (where_check.x > from_loc.x)) ) {
+ ((ter_flag3 == DIR_N) && (where_check.y > from_loc.y)) ||
+ ((ter_flag3 == DIR_E) && (where_check.x < from_loc.x)) ||
+ ((ter_flag3 == DIR_S) && (where_check.y < from_loc.y)) ||
+ ((ter_flag3 == DIR_W) && (where_check.x > from_loc.x)) ) {
ASB("The moving floor prevents you.");
return false;
}
@@ -289,9 +288,9 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
case eTerSpec::CHANGE_WHEN_USED: case eTerSpec::CALL_SPECIAL_WHEN_USED:
break;
case eTerSpec::CHANGE_WHEN_STEP_ON:
- alter_space(where_check.x,where_check.y,ter_flag1.u);
- if(ter_flag2.u < 200) {
- play_sound(-1 * ter_flag2.u);
+ alter_space(where_check.x,where_check.y,ter_flag1);
+ if(ter_flag2 < 200) {
+ play_sound(-1 * ter_flag2);
}
give_help(47,65);
if(blocksMove(univ.scenario.ter_types[ter].blockage))
@@ -305,10 +304,10 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
break;
if(mode == eSpecCtx::OUT_MOVE && out_boat_there(where_check) < 30)
break;
- if(ter_flag3.u > 0 && ter_flag3.u < 8)
- dam_type = (eDamageType) ter_flag3.u;
+ if(ter_flag3 > 0 && ter_flag3 < 8)
+ dam_type = (eDamageType) ter_flag3;
else dam_type = eDamageType::WEAPON;
- r1 = get_ran(ter_flag2.u,1,ter_flag1.u);
+ r1 = get_ran(ter_flag2,1,ter_flag1);
switch(dam_type){
case eDamageType::FIRE:
add_string_to_buf(" It's hot!");
@@ -366,55 +365,55 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
if(mode == eSpecCtx::COMBAT_MOVE) i = univ.get_target_i(which_pc); else i = 0;
for( ; i < 6; i++)
if(univ.party[i].main_status == eMainStatus::ALIVE) {
- if(get_ran(1,1,100) <= ter_flag2.u) {
- switch((eStatus)ter_flag3.u){
+ if(get_ran(1,1,100) <= ter_flag2) {
+ switch((eStatus)ter_flag3){
case eStatus::POISONED_WEAPON: // TODO: Do something here
if(get_ran(1,1,100) > 60) add_string_to_buf("It's eerie here...");
break;
case eStatus::BLESS_CURSE: // Should say "You feel awkward." / "You feel blessed."?
- univ.party[i].curse(ter_flag1.s);
+ univ.party[i].curse(ter_flag1);
break;
case eStatus::POISON:
- univ.party[i].poison(ter_flag1.u);
+ univ.party[i].poison(ter_flag1);
break;
case eStatus::HASTE_SLOW: // Should say "You feel sluggish." / "You feel speedy."?
- univ.party[i].slow(ter_flag1.s);
+ univ.party[i].slow(ter_flag1);
break;
case eStatus::INVULNERABLE: // Should say "You feel odd." / "You feel protected."?
- univ.party[i].apply_status(eStatus::INVULNERABLE,ter_flag1.u);
+ univ.party[i].apply_status(eStatus::INVULNERABLE,ter_flag1);
break;
case eStatus::MAGIC_RESISTANCE: // Should say "You feel odd." / "You feel protected."?
- univ.party[i].apply_status(eStatus::MAGIC_RESISTANCE,ter_flag1.u);
+ univ.party[i].apply_status(eStatus::MAGIC_RESISTANCE,ter_flag1);
break;
case eStatus::WEBS: // Should say "You feel sticky." / "Your skin tingles."?
- univ.party[i].web(ter_flag1.u);
+ univ.party[i].web(ter_flag1);
break;
case eStatus::DISEASE: // Should say "You feel healthy." / "You feel sick."?
- univ.party[i].disease(ter_flag1.u);
+ univ.party[i].disease(ter_flag1);
break;
case eStatus::INVISIBLE:
- if(ter_flag1.s < 0) add_string_to_buf("You feel obscure.");
+ if(ter_flag1 < 0) add_string_to_buf("You feel obscure.");
else add_string_to_buf("You feel exposed.");
- univ.party[i].apply_status(eStatus::INVISIBLE,ter_flag1.s);
+ univ.party[i].apply_status(eStatus::INVISIBLE,ter_flag1);
break;
case eStatus::DUMB: // Should say "You feel clearheaded." / "You feel confused."?
- univ.party[i].dumbfound(ter_flag1.u);
+ univ.party[i].dumbfound(ter_flag1);
break;
case eStatus::MARTYRS_SHIELD: // Should say "You feel dull." / "You start to glow slightly."?
- univ.party[i].apply_status(eStatus::MARTYRS_SHIELD,ter_flag1.u);
+ univ.party[i].apply_status(eStatus::MARTYRS_SHIELD,ter_flag1);
break;
case eStatus::ASLEEP: // Should say "You feel alert." / "You feel very tired."?
- univ.party[i].sleep(eStatus::ASLEEP,ter_flag1.u,ter_flag1.u / 2);
+ univ.party[i].sleep(eStatus::ASLEEP,ter_flag1,ter_flag1 / 2);
break;
case eStatus::PARALYZED: // Should say "You find it easier to move." / "You feel very stiff."?
- univ.party[i].sleep(eStatus::PARALYZED,ter_flag1.u,ter_flag1.u / 2);
+ univ.party[i].sleep(eStatus::PARALYZED,ter_flag1,ter_flag1 / 2);
break;
case eStatus::ACID: // Should say "Your skin tingles pleasantly." / "Your skin burns!"?
- univ.party[i].acid(ter_flag1.u);
+ univ.party[i].acid(ter_flag1);
break;
case eStatus::FORCECAGE:
if(is_out()) break;
- univ.party[i].sleep(eStatus::FORCECAGE,ter_flag1.u,ter_flag1.u / 2);
+ univ.party[i].sleep(eStatus::FORCECAGE,ter_flag1,ter_flag1 / 2);
// TODO: Do we need to process fields here? Or is it done after returning from this function?
break;
case eStatus::MAIN: case eStatus::CHARM: // These magic values are illegal in this context
@@ -427,15 +426,12 @@ bool check_special_terrain(location where_check,eSpecCtx mode,cPlayer& which_pc,
break;
case eTerSpec::CALL_SPECIAL: {
short spec_type = 0;
- if(ter_flag2.u == 3){
+ if(ter_flag2 == 1){
if(mode == eSpecCtx::TOWN_MOVE || (mode == eSpecCtx::COMBAT_MOVE && which_combat_type == 1))
spec_type = 2;
else spec_type = 1;
- }else if(ter_flag2.u == 2 && (mode == eSpecCtx::OUT_MOVE || (mode == eSpecCtx::COMBAT_MOVE && which_combat_type == 0)))
- spec_type = 1;
- else if(ter_flag2.u == 1 && (mode == eSpecCtx::TOWN_MOVE || (mode == eSpecCtx::COMBAT_MOVE && which_combat_type == 1)))
- spec_type = 2;
- run_special(mode,spec_type,ter_flag1.u,where_check,&s1,&s2,&s3);
+ }
+ run_special(mode,spec_type,ter_flag1,where_check,&s1,&s2,&s3);
if(s1 > 0)
can_enter = false;
break;
@@ -1238,18 +1234,16 @@ bool use_space(location where) {
return false;
}
add_string_to_buf(" OK.");
- alter_space(where.x,where.y,univ.scenario.ter_types[ter].flag1.u);
- play_sound(univ.scenario.ter_types[ter].flag2.u);
+ alter_space(where.x,where.y,univ.scenario.ter_types[ter].flag1);
+ play_sound(univ.scenario.ter_types[ter].flag2);
return true;
} else if(univ.scenario.ter_types[ter].special == eTerSpec::CALL_SPECIAL_WHEN_USED) {
short spec_type = 0;
- if(univ.scenario.ter_types[ter].flag2.u == 3){
- if((is_town() || (is_combat() && which_combat_type == 1))) spec_type = 2; else spec_type = 1;
- }else if(univ.scenario.ter_types[ter].flag2.u == 1 && (is_town() || (is_combat() && which_combat_type == 1)))
- spec_type = 2;
- else if(univ.scenario.ter_types[ter].flag2.u == 2 && (is_out() || (is_combat() && which_combat_type == 1)))
- spec_type = 1;
- run_special(eSpecCtx::USE_SPACE,spec_type,univ.scenario.ter_types[ter].flag1.u,where,&i,&i,&i);
+ if(univ.scenario.ter_types[ter].flag2 == 1){
+ if(is_town() || (is_combat() && which_combat_type == 1)) spec_type = 2;
+ else spec_type = 1;
+ }
+ run_special(eSpecCtx::USE_SPACE,spec_type,univ.scenario.ter_types[ter].flag1,where,&i,&i,&i);
return true;
}
add_string_to_buf(" Nothing to use.");
@@ -1706,7 +1700,7 @@ void push_things() {
if(univ.town.monst[i].active > 0) {
l = univ.town.monst[i].cur_loc;
ter = univ.town->terrain(l.x,l.y);
- switch(univ.scenario.ter_types[ter].flag1.u) { // TODO: Implement the other 4 possible directions
+ switch(univ.scenario.ter_types[ter].flag1) { // TODO: Implement the other 4 possible directions
case DIR_N: l.y--; break;
case DIR_E: l.x++; break;
case DIR_S: l.y++; break;
@@ -1723,7 +1717,7 @@ void push_things() {
if(univ.town.items[i].variety != eItemType::NO_ITEM) {
l = univ.town.items[i].item_loc;
ter = univ.town->terrain(l.x,l.y);
- switch(univ.scenario.ter_types[ter].flag1.u) { // TODO: Implement the other 4 possible directions
+ switch(univ.scenario.ter_types[ter].flag1) { // TODO: Implement the other 4 possible directions
case DIR_N: l.y--; break;
case DIR_E: l.x++; break;
case DIR_S: l.y++; break;
@@ -1740,7 +1734,7 @@ void push_things() {
if(is_town()) {
ter = univ.town->terrain(univ.town.p_loc.x,univ.town.p_loc.y);
l = univ.town.p_loc;
- switch(univ.scenario.ter_types[ter].flag1.u) { // TODO: Implement the other 4 possible directions
+ switch(univ.scenario.ter_types[ter].flag1) { // TODO: Implement the other 4 possible directions
case DIR_N: l.y--; break;
case DIR_E: l.x++; break;
case DIR_S: l.y++; break;
@@ -1779,7 +1773,7 @@ void push_things() {
if(univ.party[i].main_status == eMainStatus::ALIVE) {
ter = univ.town->terrain(univ.party[i].combat_pos.x,univ.party[i].combat_pos.y);
l = univ.party[i].combat_pos;
- switch(univ.scenario.ter_types[ter].flag1.u) { // TODO: Implement the other 4 possible directions
+ switch(univ.scenario.ter_types[ter].flag1) { // TODO: Implement the other 4 possible directions
case DIR_N: l.y--; break;
case DIR_E: l.x++; break;
case DIR_S: l.y++; break;
@@ -1967,7 +1961,6 @@ void run_special(eSpecCtx which_mode,short which_type,short start_spec,location
current_pc_picked_in_spec_enc = &univ.party;
break;
}
- store_special_loc = spec_loc;
if(end_scenario) {
special_in_progress = false;
return;
@@ -2334,24 +2327,19 @@ void general_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
}
break;
case eSpecType::CHANGE_TER:
- set_terrain(loc(spec.ex1a,spec.ex1b),spec.ex2a);
+ alter_space(spec.ex1a,spec.ex1b,spec.ex2a);
*redraw = true;
draw_map(true);
check_mess = true;
break;
case eSpecType::SWAP_TER:
- if(coord_to_ter(spec.ex1a,spec.ex1b) == spec.ex2a){
- set_terrain(loc(spec.ex1a,spec.ex1b),spec.ex2b);
- }
- else if(coord_to_ter(spec.ex1a,spec.ex1b) == spec.ex2b){
- set_terrain(loc(spec.ex1a,spec.ex1b),spec.ex2a);
- }
+ swap_ter(spec.ex1a,spec.ex1b,spec.ex2a,spec.ex2b);
*redraw = 1;
draw_map(true);
check_mess = true;
break;
case eSpecType::TRANS_TER:
- set_terrain(loc(spec.ex1a,spec.ex1b),univ.scenario.ter_types[coord_to_ter(spec.ex1a,spec.ex1b)].trans_to_what);
+ alter_space(spec.ex1a,spec.ex1b,univ.scenario.ter_types[coord_to_ter(spec.ex1a,spec.ex1b)].trans_to_what);
*redraw = 1;
draw_map(true);
check_mess = true;
@@ -3611,22 +3599,6 @@ void ifthen_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
}
}
-void set_terrain(location l, ter_num_t terrain_type) {
- if(terrain_type >= univ.scenario.ter_types.size()) return;
- if(is_out()) {
- univ.out->terrain[l.x][l.y] = terrain_type;
- l = local_to_global(l);
- univ.out[l.x][l.y] = terrain_type;
- } else {
- ter_num_t former = univ.town->terrain(l.x,l.y);
- univ.town->terrain(l.x,l.y) = terrain_type;
- if(univ.scenario.ter_types[terrain_type].special == eTerSpec::CONVEYOR)
- belt_present = true;
- if(univ.scenario.ter_types[former].light_radius != univ.scenario.ter_types[terrain_type].light_radius)
- univ.town->set_up_lights();
- }
-}
-
void townmode_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
short *next_spec,short* /*next_spec_type*/,short *a,short *b,short *redraw) {
static const char*const stairDlogs[8] = {
@@ -3687,13 +3659,13 @@ void townmode_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
case eSpecType::TOWN_LOCK_SPACE:
ter = coord_to_ter(spec.ex1a,spec.ex1b);
if(univ.scenario.ter_types[ter].special == eTerSpec::LOCKABLE)
- set_terrain(l,univ.scenario.ter_types[ter].flag1.u);
+ alter_space(l.x,l.y,univ.scenario.ter_types[ter].flag1);
*redraw = 1;
break;
case eSpecType::TOWN_UNLOCK_SPACE:
ter = coord_to_ter(spec.ex1a,spec.ex1b);
if(univ.scenario.ter_types[ter].special == eTerSpec::UNLOCKABLE)
- set_terrain(l,univ.scenario.ter_types[ter].flag1.u);
+ alter_space(l.x,l.y,univ.scenario.ter_types[ter].flag1);
*redraw = 1;
break;
case eSpecType::TOWN_SFX_BURST:
@@ -3737,7 +3709,7 @@ void townmode_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
*next_spec = -1;
}
else {
- if(handle_lever(store_special_loc) > 0)
+ if(handle_lever(loc(PSD[SDF_SPEC_LOC_X], PSD[SDF_SPEC_LOC_Y])) > 0)
*next_spec = spec.ex1b;
}
break;
@@ -3826,8 +3798,8 @@ void townmode_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
i = custom_choice_dialog(strs, spec.pic, ePicType(spec.pictype), buttons);
if(i == 1) {*next_spec = -1;}
else {
- ter = coord_to_ter(store_special_loc.x,store_special_loc.y);
- set_terrain(store_special_loc,univ.scenario.ter_types[ter].trans_to_what);
+ ter = coord_to_ter(PSD[SDF_SPEC_LOC_X], PSD[SDF_SPEC_LOC_Y]);
+ alter_space(PSD[SDF_SPEC_LOC_X], PSD[SDF_SPEC_LOC_Y],univ.scenario.ter_types[ter].trans_to_what);
*next_spec = spec.ex1b;
}
}
@@ -4214,33 +4186,26 @@ void rect_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
break;
case eSpecType::RECT_CHANGE_TER:
if(get_ran(1,1,100) <= spec.sd2){
- set_terrain(l,spec.sd1);
+ alter_space(l.x,l.y,spec.sd1);
*redraw = true;
draw_map(true);
}
break;
case eSpecType::RECT_SWAP_TER:
- if(coord_to_ter(i,j) == spec.sd1){
- set_terrain(l,spec.sd2);
- *redraw = true;
- draw_map(true);
- }
- else if(coord_to_ter(i,j) == spec.sd2){
- set_terrain(l,spec.sd1);
- *redraw = true;
- draw_map(true);
- }
+ swap_ter(l.x,l.y,spec.sd1,spec.sd2);
+ *redraw = true;
+ draw_map(true);
break;
case eSpecType::RECT_TRANS_TER:
ter = coord_to_ter(i,j);
- set_terrain(l,univ.scenario.ter_types[ter].trans_to_what);
+ alter_space(l.x,l.y,univ.scenario.ter_types[ter].trans_to_what);
*redraw = true;
draw_map(true);
break;
case eSpecType::RECT_LOCK:
ter = coord_to_ter(i,j);
if(univ.scenario.ter_types[ter].special == eTerSpec::LOCKABLE){
- set_terrain(l,univ.scenario.ter_types[ter].flag1.u);
+ alter_space(l.x,l.y,univ.scenario.ter_types[ter].flag1);
*redraw = true;
draw_map(true);
}
@@ -4248,7 +4213,7 @@ void rect_spec(eSpecCtx which_mode,cSpecial cur_node,short cur_spec_type,
case eSpecType::RECT_UNLOCK:
ter = coord_to_ter(i,j);
if(univ.scenario.ter_types[ter].special == eTerSpec::UNLOCKABLE){
- set_terrain(l,univ.scenario.ter_types[ter].flag1.u);
+ alter_space(l.x,l.y,univ.scenario.ter_types[ter].flag1);
*redraw = true;
draw_map(true);
break;
diff --git a/src/boe.specials.h b/src/boe.specials.h
index c803e623..1a1bb0e2 100644
--- a/src/boe.specials.h
+++ b/src/boe.specials.h
@@ -20,7 +20,6 @@ bool run_stone_circle(short which);
void fade_party();
void change_level(short town_num,short x,short y);
void push_things();
-void set_terrain(location l, ter_num_t terrain_type);
void queue_special(eSpecCtx mode, unsigned short which_type, short spec, location spec_loc);
void run_special(eSpecCtx which_mode,short which_type,short start_spec,location spec_loc,short *a,short *b,short *redraw);
void run_special(pending_special_type spec, short* a, short* b, short* redraw);
diff --git a/src/boe.town.cpp b/src/boe.town.cpp
index 2b34a31d..ff657e0a 100644
--- a/src/boe.town.cpp
+++ b/src/boe.town.cpp
@@ -1160,7 +1160,7 @@ void pick_lock(location where,short pc_num) {
add_string_to_buf(" Wrong terrain type.");
return;
}
- unlock_adjust = univ.scenario.ter_types[terrain].flag2.u;
+ unlock_adjust = univ.scenario.ter_types[terrain].flag2;
if((unlock_adjust >= 5) || (r1 > (unlock_adjust * 15 + 30))) {
add_string_to_buf(" Didn't work.");
if(will_break) {
@@ -1174,7 +1174,7 @@ void pick_lock(location where,short pc_num) {
else {
add_string_to_buf(" Door unlocked.");
play_sound(9);
- univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[terrain].flag1.u;
+ univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[terrain].flag1;
}
}
@@ -1190,15 +1190,15 @@ void bash_door(location where,short pc_num) {
return;
}
- unlock_adjust = univ.scenario.ter_types[terrain].flag2.u;
- if(unlock_adjust >= 5 || r1 > (unlock_adjust * 15 + 40) || univ.scenario.ter_types[terrain].flag3.u != 1) {
+ unlock_adjust = univ.scenario.ter_types[terrain].flag2;
+ if(unlock_adjust >= 5 || r1 > (unlock_adjust * 15 + 40) || univ.scenario.ter_types[terrain].flag3 != 1) {
add_string_to_buf(" Didn't work.");
damage_pc(pc_num,get_ran(1,1,4),eDamageType::UNBLOCKABLE,eRace::UNKNOWN,0);
}
else {
add_string_to_buf(" Lock breaks.");
play_sound(9);
- univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[terrain].flag1.u;
+ univ.town->terrain(where.x,where.y) = univ.scenario.ter_types[terrain].flag1;
}
}
@@ -1260,9 +1260,9 @@ void erase_out_specials() {
univ.scenario.ter_types[sector.terrain[sector.exit_locs[k].x][sector.exit_locs[k].y]].special == eTerSpec::TOWN_ENTRANCE &&
(sector.exit_locs[k].x == minmax(0,47,sector.exit_locs[k].x)) &&
(sector.exit_locs[k].y == minmax(0,47,sector.exit_locs[k].y))) {
- if(univ.party.can_find_town[sector.exit_dests[k]] == 0) {
+ if(!univ.party.can_find_town[sector.exit_dests[k]]) {
univ.out[48 * i + sector.exit_locs[k].x][48 * j + sector.exit_locs[k].y] =
- univ.scenario.ter_types[sector.terrain[sector.exit_locs[k].x][sector.exit_locs[k].y]].flag1.u;
+ univ.scenario.ter_types[sector.terrain[sector.exit_locs[k].x][sector.exit_locs[k].y]].flag1;
}
else if(univ.party.can_find_town[sector.exit_dests[k]]) {
univ.out[48 * i + sector.exit_locs[k].x][48 * j + sector.exit_locs[k].y] =
diff --git a/src/boe.townspec.cpp b/src/boe.townspec.cpp
index a390927f..67826715 100644
--- a/src/boe.townspec.cpp
+++ b/src/boe.townspec.cpp
@@ -167,18 +167,11 @@ location get_spec_loc(short which) {
return where;
}
-// 0 if no pull.
-// 1 if pull
-// levers should always start to left.
-short handle_lever(location w) {
+bool handle_lever(location w) {
if(cChoiceDlog("basic-lever",{"pull", "leave"}).show() == "leave")
- return 0;
+ return false;
play_sound(94);
- switch_lever(w);
- return 1;
-}
-
-void switch_lever(location w) {
alter_space(w.x,w.y,univ.scenario.ter_types[univ.town->terrain(w.x,w.y)].trans_to_what);
+ return true;
}
diff --git a/src/boe.townspec.h b/src/boe.townspec.h
index d63f6477..0aba71b2 100644
--- a/src/boe.townspec.h
+++ b/src/boe.townspec.h
@@ -6,5 +6,4 @@ bool special_trap(short trap_type,short dialog_num,short *flip_bit);
bool run_trap(short pc_num,eTrapType trap_type,short trap_level,short diff);
location get_spec_loc(short which);
-void switch_lever(location w);
-short handle_lever(location w);
+bool handle_lever(location w);
diff --git a/src/classes/terrain.cpp b/src/classes/terrain.cpp
index acd84953..4c969793 100644
--- a/src/classes/terrain.cpp
+++ b/src/classes/terrain.cpp
@@ -116,139 +116,135 @@ void cTerrain::append(legacy::terrain_type_type& old){
trim_ter = 0;
}
if(trim_ter == 99) trim_ter = 0;
- flag1.u = old.flag1;
- flag2.u = old.flag2;
+ flag1 = old.flag1;
+ flag2 = old.flag2;
switch(old.special){
case 0:
if(i == 7 || i == 10 || i == 13 || i == 16){
special = eTerSpec::NONE;
- flag1.s = 23;
- flag2.u = flag3.u = 0;
+ flag1 = 23;
+ flag2 = flag3 = 0;
}else if(picture == 215 || (picture >= 218 && picture <= 221)){
picture = 215;
special = eTerSpec::NONE;
- flag1.s = 3;
- flag2.u = flag3.u = 0;
+ flag1 = 3;
+ flag2 = flag3 = 0;
}else if(picture == 216 || (picture >= 222 && picture <= 225)){
picture = 215;
special = eTerSpec::NONE;
- flag1.s = 2;
- flag2.u = flag3.u = 0;
+ flag1 = 2;
+ flag2 = flag3 = 0;
}else if(picture == 143) {
special = eTerSpec::BED;
- flag1.s = 230;
- flag2.u = flag3.u = 0;
+ flag1 = 230;
+ flag2 = flag3 = 0;
}else if((picture >= 61 && picture <= 66) || picture == 961 || picture == 962){
special = eTerSpec::BRIDGE;
- flag1.u = flag2.u = flag3.u = 0;
+ flag1 = flag2 = flag3 = 0;
break;
}else{
special = eTerSpec::NONE;
- flag1.s = -1;
- flag2.u = flag3.u = 0;
+ flag1 = -1;
+ flag2 = flag3 = 0;
}
break;
case 1:
special = eTerSpec::CHANGE_WHEN_STEP_ON;
- flag3.u = 0;
+ flag3 = 0;
break;
case 2:
special = eTerSpec::DAMAGING;
- flag3.u = int(eDamageType::FIRE);
+ flag3 = int(eDamageType::FIRE);
break;
case 3:
special = eTerSpec::DAMAGING;
- flag3.u = int(eDamageType::COLD);
+ flag3 = int(eDamageType::COLD);
break;
case 4:
special = eTerSpec::DAMAGING;
- flag3.u = int(eDamageType::MAGIC);
+ flag3 = int(eDamageType::MAGIC);
break;
case 5:
special = eTerSpec::DANGEROUS;
- flag3.u = (int)eStatus::POISON;
+ flag3 = (int)eStatus::POISON;
break;
case 6:
special = eTerSpec::DANGEROUS;
- flag3.u = (int)eStatus::DISEASE;
+ flag3 = (int)eStatus::DISEASE;
break;
case 7:
special = eTerSpec::CRUMBLING;
- flag2.u = 0; // ???: may change this
- flag3.u = 1; // destroyed by Move Mountains but not by quickfire; 0 = both, 2 = quickfire only
+ flag2 = 1; // destroyed by Move Mountains but not by quickfire; 0 = both, 2 = quickfire only
break;
case 8:
special = eTerSpec::LOCKABLE;
- flag3.u = 0;
+ flag3 = 0;
break;
case 9:
special = eTerSpec::UNLOCKABLE;
- flag3.u = false; // can't bash
+ flag3 = false; // can't bash
break;
case 10:
special = eTerSpec::UNLOCKABLE;
- flag3.u = true; // can bash
+ flag3 = true; // can bash
break;
case 11:
special = eTerSpec::IS_A_SIGN;
- flag3.u = 0;
+ flag3 = 0;
break;
case 12:
special = eTerSpec::CALL_SPECIAL;
- flag2.u = 0; // local special, always (1 would be local if in town, global if outdoors)
- flag3.s = -1;
+ flag2 = 1; // local special
break;
case 13:
special = eTerSpec::CALL_SPECIAL;
- flag2.u = 3; // global special, always (2 would be local if outdoors, global if in town)
- flag3.s = -1;
+ flag2 = 0; // global special
break;
case 14:
special = eTerSpec::IS_A_CONTAINER;
- flag3.u = 0;
+ flag3 = 0;
break;
case 15:
special = eTerSpec::WATERFALL_CAVE;
- flag1.u = DIR_S;
- flag3.u = 0;
+ flag1 = DIR_S;
+ flag3 = 0;
break;
case 16:
special = eTerSpec::CONVEYOR;
- flag1.u = DIR_N;
- flag3.u = 0;
+ flag1 = DIR_N;
+ flag3 = 0;
break;
case 17:
special = eTerSpec::CONVEYOR;
- flag1.u = DIR_E;
- flag3.u = 0;
+ flag1 = DIR_E;
+ flag3 = 0;
break;
case 18:
special = eTerSpec::CONVEYOR;
- flag1.u = DIR_S;
- flag3.u = 0;
+ flag1 = DIR_S;
+ flag3 = 0;
break;
case 19:
special = eTerSpec::CONVEYOR;
- flag1.u = DIR_W;
- flag3.u = 0;
+ flag1 = DIR_W;
+ flag3 = 0;
break;
case 20:
special = eTerSpec::BLOCKED_TO_MONSTERS;
- flag3.u = 0;
+ flag3 = 0;
break;
case 21:
special = eTerSpec::TOWN_ENTRANCE;
- flag3.u = 0;
+ flag3 = 0;
break;
case 22:
special = eTerSpec::CHANGE_WHEN_USED;
- flag2.u = 59;
- flag3.u = 0;
+ flag2 = 59;
+ flag3 = 0;
break;
case 23:
special = eTerSpec::CALL_SPECIAL_WHEN_USED;
- flag2.u = 3; // global special, always (2 would be local if outdoors, global if in town)
- flag3.s = -1;
+ flag2 = 0; // global special
break;
}
trans_to_what = old.trans_to_what;
@@ -257,8 +253,7 @@ void cTerrain::append(legacy::terrain_type_type& old){
if(special == eTerSpec::DANGEROUS) block_horse = false; // because it's now redundant and unhelpful
else block_horse = old.block_horse;
light_radius = old.light_radius;
- step_sound = old.step_sound;
- if(step_sound > 99) step_sound = 99;
+ step_sound = eStepSnd(old.step_sound);
shortcut_key = old.shortcut_key;
switch(picture){
// Rubbles, plus pentagram as a bonus
@@ -475,3 +470,31 @@ std::istream& operator >> (std::istream& in, eTerObstruct& e){
else e = eTerObstruct::CLEAR;
return in;
}
+
+
+std::ostream& operator<< (std::ostream& out, eStepSnd snd) {
+ switch(snd) {
+ case eStepSnd::CRUNCH: out << "crunch"; break;
+ case eStepSnd::NONE: out << "none"; break;
+ case eStepSnd::SPLASH: out << "splash"; break;
+ case eStepSnd::SQUISH: out << "squish"; break;
+ case eStepSnd::STEP: out << "step"; break;
+ }
+ return out;
+}
+
+std::istream& operator >> (std::istream& in, eStepSnd& e){
+ std::string key;
+ in >> key;
+ if(key == "crunch")
+ e = eStepSnd::CRUNCH;
+ else if(key == "none")
+ e = eStepSnd::NONE;
+ else if(key == "splash")
+ e = eStepSnd::SPLASH;
+ else if(key == "squish")
+ e = eStepSnd::SQUISH;
+ else if(key == "step")
+ e = eStepSnd::STEP;
+ return in;
+}
diff --git a/src/classes/terrain.h b/src/classes/terrain.h
index 55c1affe..a681cb07 100644
--- a/src/classes/terrain.h
+++ b/src/classes/terrain.h
@@ -19,24 +19,21 @@
namespace legacy { struct terrain_type_type; };
-// Depending on the special ability, the flags may need to be treated as either signed or unsigned
-union ter_flag_t {signed short s; unsigned short u;};
+enum class eStepSnd {STEP, SQUISH, CRUNCH, NONE, SPLASH};
class cTerrain {
public:
std::string name;
pic_num_t picture;
eTerObstruct blockage;
- ter_flag_t flag1;
- ter_flag_t flag2;
- ter_flag_t flag3; // new additional flag for special properties
+ int flag1, flag2, flag3;
eTerSpec special;
ter_num_t trans_to_what;
bool fly_over;
bool boat_over;
bool block_horse;
unsigned int light_radius;
- snd_num_t step_sound;
+ eStepSnd step_sound;
unsigned char shortcut_key; // for editor use only
unsigned int obj_num = 0; // ditto (formerly res1)
unsigned int ground_type; // ditto (formerly res2)
@@ -58,5 +55,7 @@ std::ostream& operator << (std::ostream& out, eTrimType e);
std::istream& operator >> (std::istream& in, eTrimType& e);
std::ostream& operator << (std::ostream& out, eTerObstruct e);
std::istream& operator >> (std::istream& in, eTerObstruct& e);
+std::ostream& operator << (std::ostream& out, eStepSnd e);
+std::istream& operator >> (std::istream& in, eStepSnd& e);
#endif
diff --git a/src/dialogxml/button.cpp b/src/dialogxml/button.cpp
index cba06b40..deec6386 100644
--- a/src/dialogxml/button.cpp
+++ b/src/dialogxml/button.cpp
@@ -93,8 +93,6 @@ void cButton::draw(){
// Others may need adjustments too, not sure
// TODO: How is it supposed to know it's a default button when this fact is stored in the dialog, not the button?
if(key.spec && key.k == key_enter) drawFrame(2,frameStyle); // frame default button, to provide a visual cue that it's the default
- } else if(parent) {
- tileImage(*inWindow,frame,bg[parent->getBg()]);
}
}
@@ -266,8 +264,6 @@ void cLed::draw(){
to_rect.right = frame.right;
to_rect.left = frame.left + 18; // Possibly could be 20
win_draw_string(*inWindow,to_rect,lbl,eTextMode::LEFT_TOP,style);
- } else if(parent) {
- tileImage(*inWindow,frame,bg[parent->getBg()]);
}
}
diff --git a/src/dialogxml/pict.cpp b/src/dialogxml/pict.cpp
index f0d3047d..34e4944d 100644
--- a/src/dialogxml/pict.cpp
+++ b/src/dialogxml/pict.cpp
@@ -569,11 +569,7 @@ void cPict::draw(){
rectangle rect = frame;
inWindow->setActive();
- if(!visible){ // Erase it
- rect.inset(-3, -3);
- tileImage(*inWindow,rect,bg[parent->getBg()]);
- return;
- }
+ if(!visible) return;
if(picNum == BLANK) { // Just fill with black
fill_rect(*inWindow, rect, sf::Color::Black);
return;
diff --git a/src/scenedit/scen.core.cpp b/src/scenedit/scen.core.cpp
index 750e704e..0e92aaa2 100644
--- a/src/scenedit/scen.core.cpp
+++ b/src/scenedit/scen.core.cpp
@@ -3,6 +3,7 @@
#include
#include
#include
+#include
#include
#include "scen.global.h"
#include "scenario.h"
@@ -42,6 +43,61 @@ const std::set items_no_strength = {
};
static bool save_ter_info(cDialog& me, cTerrain& ter) {
+ eTerSpec prop = eTerSpec(boost::lexical_cast(dynamic_cast(me["prop"]).getSelected().substr(4)));
+ int spec_type = me["flag2"].getTextAsNum();
+ int num_town = (**std::min_element(scenario.towns.begin(), scenario.towns.end(), [](cTown* a,cTown* b){
+ return a->specials.size() < b->specials.size();
+ })).specials.size();
+ int num_out = (**std::min_element(scenario.outdoors.begin(), scenario.outdoors.end(), [](cOutdoors* a,cOutdoors* b){
+ return a->specials.size() < b->specials.size();
+ })).specials.size();
+ int num_loc = std::min(num_town, num_out);
+ int num_glob = scenario.scen_specials.size();
+ switch(prop) {
+ case eTerSpec::CHANGE_WHEN_STEP_ON:
+ case eTerSpec::CHANGE_WHEN_USED:
+ if(!check_range(me, "flag1", true, 0, scenario.ter_types.size() - 1, "Terrain to change to")) return false;
+ if(!check_range(me, "flag2", true, 0, 99, "Sound to play")) return false;
+ break;
+ case eTerSpec::DAMAGING:
+ if(!check_range(me, "flag1", true, 0, 100, "Sides per die")) return false;
+ if(!check_range(me, "flag2", true, 0, 100, "Number of sides")) return false;
+ if(!check_range(me, "flag3", true, 0, 8, "Damage type")) return false;
+ break;
+ case eTerSpec::DANGEROUS:
+ if(!check_range(me, "flag1", true, 0, 8, "Strength")) return false;
+ if(!check_range(me, "flag2", true, 0, 100, "Percentage chance")) return false;
+ if(!check_range(me, "flag3", true, 0, 14, "Status type")) return false;
+ break;
+ case eTerSpec::CRUMBLING:
+ if(!check_range_msg(me, "flag2", true, 0, 2, "Method", "1 - Move Mountains, 2 - quickfire, 0 - either")) return false;
+ if(false) // Prevent next line from executing if it's crumbling
+ case eTerSpec::UNLOCKABLE:
+ if(!check_range(me, "flag2", true, 0, 10, "Difficulty")) return false;
+ case eTerSpec::LOCKABLE:
+ case eTerSpec::TOWN_ENTRANCE:
+ if(!check_range(me, "flag1", true, 0, scenario.ter_types.size() - 1,
+ prop == eTerSpec::TOWN_ENTRANCE ? "Terrain when hidden" : "Terrain to change to"))
+ return false;
+ break;
+ case eTerSpec::WATERFALL_CAVE:
+ case eTerSpec::WATERFALL_SURFACE:
+ case eTerSpec::CONVEYOR:
+ if(!check_range(me, "flag1", true, 0, 7, "Direction")) return false;
+ break;
+ case eTerSpec::CALL_SPECIAL:
+ case eTerSpec::CALL_SPECIAL_WHEN_USED:
+ if(spec_type < 0 || spec_type > 1) {
+ giveError("Special type must be either 0 or 1.", &me);
+ return false;
+ }
+ if(!check_range(me, "flag1", true, 0, (spec_type == 0 ? num_glob : num_loc) - 1, "Special to call")) return false;
+ break;
+ case eTerSpec::BRIDGE: case eTerSpec::BED: case eTerSpec::IS_A_SIGN: case eTerSpec::IS_A_CONTAINER: case eTerSpec::BLOCKED_TO_MONSTERS:
+ case eTerSpec::WILDERNESS_CAVE: case eTerSpec::WILDERNESS_SURFACE: case eTerSpec::NONE:
+ case eTerSpec::UNUSED1: case eTerSpec::UNUSED2: case eTerSpec::UNUSED3:
+ break;
+ }
ter.picture = me["pict"].getTextAsNum();
// TODO: Should somehow verify the pict number is valid
@@ -53,57 +109,24 @@ static bool save_ter_info(cDialog& me, cTerrain& ter) {
else if(blockage == "window") ter.blockage = eTerObstruct::BLOCK_MOVE;
else if(blockage == "obstructed") ter.blockage = eTerObstruct::BLOCK_MOVE_AND_SHOOT;
else if(blockage == "opaque") ter.blockage = eTerObstruct::BLOCK_MOVE_AND_SIGHT;
- ter.special = (eTerSpec) boost::lexical_cast(dynamic_cast(me["prop"]).getSelected().substr(4));
- /*
- i = CDGN(813,6);
- if((store_ter.special < 2) || (store_ter.special > 6)) {
- if(cre(i,0,256,"First special flag must be from 0 to 255.","",813)) return false;
- }
- else if(store_ter.special == eTerSpec::DAMAGING) {
- if(cre(i,0,256,"First special flag must be from 0 to 100.","",813)) return false;
- }
- else if(store_ter.special == eTerSpec::DANGEROUS) {
- if(cre(i,0,256,"First special flag must be from 0 to 8.","",813)) return false;
- }
- */
- if(ter.special == eTerSpec::NONE)
- ter.flag1.s = me["flag1"].getTextAsNum();
- else ter.flag1.u = me["flag1"].getTextAsNum();
- if(false) // flag2 is never signed, apparently; but that could change?
- ter.flag2.s = me["flag2"].getTextAsNum();
- else ter.flag2.u = me["flag2"].getTextAsNum();
- if(ter.special == eTerSpec::CALL_SPECIAL || ter.special == eTerSpec::CALL_SPECIAL_WHEN_USED)
- ter.flag3.s = me["flag3"].getTextAsNum();
- else ter.flag3.u = me["flag3"].getTextAsNum();
+ ter.special = prop;
+ ter.flag1 = me["flag1"].getTextAsNum();
+ ter.flag2 = me["flag2"].getTextAsNum();
+ ter.flag3 = me["flag3"].getTextAsNum();
- /*
- if(store_ter.special == eTerSpec::TOWN_ENTRANCE) {
- if(cre(i,0,256,"Second special flag must be from 0 to 200.","",813)) return false;
- }
- else if(store_ter.special == eTerSpec::DAMAGING || store_ter.special == eTerSpec::DANGEROUS) {
- if(cre(i,0,256,"Second special flag must be from 0 to 100.","",813)) return false;
- }
- */
-
- /*
- if(cre(i,0,255,"Transform To What must be from 0 to 255.","",813)) return false;
- */
ter.trans_to_what = me["trans"].getTextAsNum();
ter.fly_over = dynamic_cast(me["flight"]).getState() == led_red;
ter.boat_over = dynamic_cast(me["boat"]).getState() == led_red;
ter.block_horse = dynamic_cast(me["horse"]).getState();
ter.light_radius = me["light"].getTextAsNum();
- /*
- if(cre(store_ter.light_radius,0,8,"Light radius must be from 0 to 8.","",813)) return false;
- */
std::string sound = dynamic_cast(me["sound"]).getSelected();
- // TODO: Uh, why not use an actual sound number instead of 0...4?
- if(sound == "step") ter.step_sound = 0;
- else if(sound == "squish") ter.step_sound = 1;
- else if(sound == "crunch") ter.step_sound = 2;
- else if(sound == "nosound") ter.step_sound = 3;
- else if(sound == "splash") ter.step_sound = 4;
+ // TODO: Offer the option of a custom sound?
+ if(sound == "step") ter.step_sound = eStepSnd::STEP;
+ else if(sound == "squish") ter.step_sound = eStepSnd::SQUISH;
+ else if(sound == "crunch") ter.step_sound = eStepSnd::CRUNCH;
+ else if(sound == "nosound") ter.step_sound = eStepSnd::NONE;
+ else if(sound == "splash") ter.step_sound = eStepSnd::SPLASH;
std::string shortcut = me["key"].getText();
if(shortcut.length() > 0) ter.shortcut_key = shortcut[0];
@@ -195,7 +218,87 @@ static bool show_help(std::string from_file, cDialog& parent, pic_num_t pic){
return true;
}
-static bool fill_ter_flag_info(cDialog& me, std::string id, bool){
+static bool pick_ter_flag(cDialog& me, std::string id, eKeyMod) {
+ if(id == "editspec") {
+ int which_type = me["flag2"].getTextAsNum();
+ if(which_type == 1) {
+ std::string choice = cChoiceDlog("pick-spec-type", {"town", "out", "cancel"}).show();
+ if(choice == "cancel") return true;
+ else if(choice == "town") which_type = 2;
+ }
+ short spec = me["flag1"].getTextAsNum();
+ if(spec < 0 || spec > 255) {
+ spec = get_fresh_spec(which_type);
+ if(spec < 0) {
+ giveError("You can't create a new special encounter because there are no more free special nodes.",
+ "To free a special node, set its type to No Special and set its Jump To special to -1.", &me);
+ return true;
+ }
+ }
+ if(edit_spec_enc(spec,which_type,&me))
+ me["flag1"].setTextToNum(spec);
+ return true;
+ } else if(id == "picktrans") {
+ int i = me["trans"].getTextAsNum();
+ i = choose_text(STRT_TER, i, &me, "Transform to what terrain?");
+ me["trans"].setTextToNum(i);
+ return true;
+ }
+ int which = id[8] - '0';
+ std::string fld = id.substr(4);
+ int i = me[fld].getTextAsNum();
+ eTerSpec prop;
+ cLedGroup& led_ctrl = dynamic_cast(me["prop"]);
+ std::istringstream sel(led_ctrl.getSelected().substr(4));
+ sel >> prop;
+ switch(prop) {
+ case eTerSpec::NONE:
+ // TODO: Could have a pick graphic dialog for the editor icon, but that requires adding a new graphic type
+ return true;
+ case eTerSpec::CHANGE_WHEN_STEP_ON: case eTerSpec::CHANGE_WHEN_USED:
+ if(which == 1)
+ i = choose_text(STRT_TER, i, &me, "Change to what terrain?");
+ else if(which == 2)
+ i = choose_text(STRT_SND, i, &me, "Select the sound to play when it changes:");
+ else return true;
+ break;
+ case eTerSpec::DAMAGING:
+ if(which == 3)
+ i = choose_damage_type(i, &me);
+ else return true;
+ break;
+ case eTerSpec::DANGEROUS:
+ if(which == 3)
+ i = choose_status_effect(i, false, &me);
+ else return true;
+ break;
+ case eTerSpec::BED:
+ if(which == 1)
+ i = choose_graphic(i, PIC_TER, &me);
+ else return true;
+ break;
+ case eTerSpec::WATERFALL_CAVE: case eTerSpec::WATERFALL_SURFACE: case eTerSpec::CONVEYOR:
+ if(which == 1)
+ i = choose_text(STRT_DIR, i, &me, "Which direction?");
+ else return true;
+ break;
+ case eTerSpec::CRUMBLING: case eTerSpec::LOCKABLE: case eTerSpec::UNLOCKABLE: case eTerSpec::TOWN_ENTRANCE:
+ if(which == 1)
+ i = choose_text(STRT_TER, i, &me, prop == eTerSpec::TOWN_ENTRANCE ? "Terrain type when hidden:" : "Terrain to change to:");
+ else return true;
+ break;
+ case eTerSpec::CALL_SPECIAL: case eTerSpec::CALL_SPECIAL_WHEN_USED:
+ case eTerSpec::UNUSED1: case eTerSpec::UNUSED2: case eTerSpec::UNUSED3:
+ case eTerSpec::WILDERNESS_CAVE: case eTerSpec::WILDERNESS_SURFACE:
+ case eTerSpec::BRIDGE: case eTerSpec::IS_A_SIGN: case eTerSpec::IS_A_CONTAINER: case eTerSpec::BLOCKED_TO_MONSTERS:
+ return true;
+ }
+ me[fld].setTextToNum(i);
+ return true;
+}
+
+static bool fill_ter_flag_info(cDialog& me, std::string id, bool losing){
+ if(losing) return true;
eTerSpec prop;
cLedGroup& led_ctrl = dynamic_cast(me[id]);
std::istringstream sel(led_ctrl.getSelected().substr(4));
@@ -206,12 +309,30 @@ static bool fill_ter_flag_info(cDialog& me, std::string id, bool){
me["pickflag1"].hide();
me["pickflag2"].hide();
me["pickflag3"].hide();
+ me["editspec"].hide();
switch(prop) {
case eTerSpec::NONE:
me["pickflag1"].hide(); // TODO: Could have a pick graphic dialog for the editor icon, but that requires adding a new graphic type
break;
+ case eTerSpec::CHANGE_WHEN_STEP_ON: case eTerSpec::CHANGE_WHEN_USED:
+ me["pickflag1"].show();
+ me["pickflag2"].show();
+ break;
+ case eTerSpec::DAMAGING: case eTerSpec::DANGEROUS:
+ me["pickflag3"].show();
+ break;
+ case eTerSpec::BED: case eTerSpec::WATERFALL_CAVE: case eTerSpec::WATERFALL_SURFACE: case eTerSpec::CONVEYOR:
+ case eTerSpec::CRUMBLING: case eTerSpec::LOCKABLE: case eTerSpec::UNLOCKABLE: case eTerSpec::TOWN_ENTRANCE:
+ me["pickflag1"].show();
+ break;
+ case eTerSpec::CALL_SPECIAL: case eTerSpec::CALL_SPECIAL_WHEN_USED:
+ me["editspec"].show();
+ break;
+ case eTerSpec::UNUSED1: case eTerSpec::UNUSED2: case eTerSpec::UNUSED3:
+ case eTerSpec::WILDERNESS_CAVE: case eTerSpec::WILDERNESS_SURFACE:
+ case eTerSpec::BRIDGE: case eTerSpec::IS_A_SIGN: case eTerSpec::IS_A_CONTAINER: case eTerSpec::BLOCKED_TO_MONSTERS:
+ break;
}
- // TODO: Click handlers for the "choose" buttons as necessary, plus hide/show them as needed
return true;
}
@@ -239,7 +360,9 @@ static void fill_ter_info(cDialog& me, short ter){
}
me["number"].setTextToNum(ter);
me["name"].setText(ter_type.name);
- me["key"].setTextToNum(ter_type.shortcut_key);
+ if(ter_type.shortcut_key > ' ')
+ me["key"].setText(std::string(1, ter_type.shortcut_key));
+ else me["key"].setText("");
me["light"].setTextToNum(ter_type.light_radius);
me["trans"].setTextToNum(ter_type.trans_to_what);
me["ground"].setTextToNum(ter_type.ground_type);
@@ -274,19 +397,19 @@ static void fill_ter_info(cDialog& me, short ter){
}{
cLedGroup& led_ctrl = dynamic_cast(me["sound"]);
switch(ter_type.step_sound){
- case 0:
+ case eStepSnd::STEP:
led_ctrl.setSelected("step");
break;
- case 1:
+ case eStepSnd::SQUISH:
led_ctrl.setSelected("squish");
break;
- case 2:
+ case eStepSnd::CRUNCH:
led_ctrl.setSelected("crunch");
break;
- case 3:
+ case eStepSnd::NONE:
led_ctrl.setSelected("nosound");
break;
- case 4:
+ case eStepSnd::SPLASH:
led_ctrl.setSelected("splash");
break;
}
@@ -303,15 +426,9 @@ static void fill_ter_info(cDialog& me, short ter){
cLed& led_ctrl = dynamic_cast(me["horse"]);
led_ctrl.setState(led_red);
}
- if(ter_type.special == eTerSpec::NONE)
- me["flag1"].setTextToNum(ter_type.flag1.s);
- else me["flag1"].setTextToNum(ter_type.flag1.u);
- if(false) // flag2 is never signed, apparently; but that could change?
- me["flag2"].setTextToNum(ter_type.flag2.s);
- else me["flag2"].setTextToNum(ter_type.flag2.u);
- if(ter_type.special == eTerSpec::CALL_SPECIAL || ter_type.special == eTerSpec::CALL_SPECIAL_WHEN_USED)
- me["flag3"].setTextToNum(ter_type.flag3.s);
- else me["flag3"].setTextToNum(ter_type.flag3.u);
+ me["flag1"].setTextToNum(ter_type.flag1);
+ me["flag2"].setTextToNum(ter_type.flag2);
+ me["flag3"].setTextToNum(ter_type.flag3);
me["arena"].setTextToNum(ter_type.combat_arena);
}
@@ -321,7 +438,6 @@ static bool finish_editing_ter(cDialog& me, std::string id, ter_num_t& which) {
if(!me.toast(true)) return true;
if(id == "left") {
me.untoast();
- // TODO: Use size() once ter_types becomes a vector
if(which == 0)
which = scenario.ter_types.size() - 1;
else which--;
@@ -417,31 +533,37 @@ static bool edit_ter_obj(cDialog& me, ter_num_t which_ter) {
return true;
}
-short edit_ter_type(ter_num_t which) {
+void edit_ter_type(ter_num_t which) {
using namespace std::placeholders;
cDialog ter_dlg("edit-terrain");
// Attach handlers
ter_dlg["pict"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,2999,"terrain graphic"));
ter_dlg["pickpict"].attachClickHandler(std::bind(pick_picture,PIC_TER,_1,"pict","graphic"));
ter_dlg["pickanim"].attachClickHandler(std::bind(pick_picture,PIC_TER_ANIM,_1,"pict","graphic"));
- ter_dlg["light"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,255,"light radius"));
- ter_dlg["trans"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,65535,"\"transform to what?\""));
+ ter_dlg["light"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,8,"light radius"));
+ ter_dlg["trans"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,scenario.ter_types.size() - 1,"\"transform to what?\""));
ter_dlg["ground"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,255,"ground type"));
- ter_dlg["trimter"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,255,"trim terrain"));
+ ter_dlg["trimter"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,scenario.ter_types.size() - 1,"trim terrain"));
ter_dlg["trim"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,18,"trim type"));
ter_dlg["prop"].attachFocusHandler(fill_ter_flag_info);
ter_dlg["cancel"].attachClickHandler(std::bind(&cDialog::toast, &ter_dlg, false));
- ter_dlg["arena"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,299,"ground type"));
+ ter_dlg["arena"].attachFocusHandler(std::bind(check_range,_1,_2,_3,0,999 + scenario.towns.size(),"combat areana"));
// TODO: Add focus handler for key
ter_dlg["object"].attachClickHandler(std::bind(edit_ter_obj, _1, std::ref(which)));
ter_dlg.attachClickHandlers(std::bind(finish_editing_ter,_1,_2,std::ref(which)), {"left", "right", "done"});
ter_dlg["picktrim"].attachClickHandler(std::bind(pick_string,"trim-names", _1, "trim", ""));
ter_dlg["pickarena"].attachClickHandler(std::bind(pick_string,"arena-names", _1, "arena", ""));
ter_dlg["help"].attachClickHandler(std::bind(show_help, "ter-type-help", _1, 16));
+ ter_dlg.attachClickHandlers(pick_ter_flag, {"pickflag1", "pickflag2", "pickflag3", "editspec", "picktrans"});
+ ter_dlg["picktown"].attachClickHandler([](cDialog& me, std::string, eKeyMod) -> bool {
+ int i = me["arena"].getTextAsNum();
+ if(i < 1000) i = -1; else i -= 1000;
+ i = choose_text(STRT_TOWN, i, &me, "Select a town to base the combat arena on:");
+ if(i >= 0) me["arena"].setTextToNum(i + 1000);
+ return true;
+ });
fill_ter_info(ter_dlg,which);
ter_dlg.run();
- // TODO: What should be returned?
- return 0;
}
static void put_monst_info_in_dlog(cDialog& me, cMonster& monst, mon_num_t which) {
diff --git a/src/scenedit/scen.core.h b/src/scenedit/scen.core.h
index bfa8d602..f0823af6 100644
--- a/src/scenedit/scen.core.h
+++ b/src/scenedit/scen.core.h
@@ -2,7 +2,7 @@
class cDialog;
void edit_custom_pics_types();
-short edit_ter_type(ter_num_t which_ter);
+void edit_ter_type(ter_num_t which_ter);
short edit_monst_type(short which_monst);
cMonster edit_monst_abil(cMonster starting_record,short which_monst,cDialog& parent);
short edit_item_type(short which_item);
diff --git a/src/scenedit/scen.fileio.cpp b/src/scenedit/scen.fileio.cpp
index 2091b1ef..afaac252 100644
--- a/src/scenedit/scen.fileio.cpp
+++ b/src/scenedit/scen.fileio.cpp
@@ -263,9 +263,9 @@ static void writeTerrainToXml(ticpp::Printer&& data) {
data.OpenElement("special");
data.PushElement("type", ter.special);
- data.PushElement("flag", ter.flag1.u);
- data.PushElement("flag", ter.flag2.u);
- data.PushElement("flag", ter.flag3.u);
+ data.PushElement("flag", ter.flag1);
+ data.PushElement("flag", ter.flag2);
+ data.PushElement("flag", ter.flag3);
data.CloseElement("special");
data.OpenElement("editor");
diff --git a/src/scenedit/scen.graphics.cpp b/src/scenedit/scen.graphics.cpp
index 86e762fa..5669b2a5 100644
--- a/src/scenedit/scen.graphics.cpp
+++ b/src/scenedit/scen.graphics.cpp
@@ -133,13 +133,13 @@ static short get_small_icon(ter_num_t ter){
short icon = -1;
switch(scenario.ter_types[ter].special){
case eTerSpec::NONE:
- icon = scenario.ter_types[ter].flag1.s;
+ icon = scenario.ter_types[ter].flag1;
break;
case eTerSpec::CHANGE_WHEN_STEP_ON:
icon = 23;
break;
case eTerSpec::DAMAGING:
- switch(eDamageType(scenario.ter_types[ter].flag3.u)) {
+ switch(eDamageType(scenario.ter_types[ter].flag3)) {
case eDamageType::WEAPON:
icon = 40;
break;
@@ -178,7 +178,7 @@ static short get_small_icon(ter_num_t ter){
icon = -1;
break;
case eTerSpec::DANGEROUS:
- switch((eStatus)scenario.ter_types[ter].flag3.u){
+ switch((eStatus)scenario.ter_types[ter].flag3){
case eStatus::POISONED_WEAPON: // TODO: Do something here
break;
case eStatus::BLESS_CURSE: // TODO: Do something here (check flag1 to determine whether bless or curse)
@@ -224,15 +224,15 @@ static short get_small_icon(ter_num_t ter){
icon = 30;
break;
case eTerSpec::UNLOCKABLE:
- if(scenario.ter_types[ter].flag2.u >= 5)
- icon = (scenario.ter_types[ter].flag2.u == 10) ? 32 : 31;
+ if(scenario.ter_types[ter].flag2 >= 5)
+ icon = (scenario.ter_types[ter].flag2 == 10) ? 32 : 31;
else icon = 30;
break;
case eTerSpec::IS_A_SIGN:
icon = 26;
break;
case eTerSpec::CALL_SPECIAL:
- icon = scenario.ter_types[ter].flag3.s;
+ icon = scenario.ter_types[ter].flag3;
break;
case eTerSpec::IS_A_CONTAINER:
icon = 36;
@@ -242,7 +242,7 @@ static short get_small_icon(ter_num_t ter){
icon = -1;
break;
case eTerSpec::CONVEYOR:
- switch(scenario.ter_types[ter].flag1.u){ // TODO: Consider the other four possible directions
+ switch(scenario.ter_types[ter].flag1){ // TODO: Consider the other four possible directions
case DIR_N:
icon = 27;
break;
@@ -267,7 +267,7 @@ static short get_small_icon(ter_num_t ter){
icon = -1;
break;
case eTerSpec::CALL_SPECIAL_WHEN_USED:
- icon = scenario.ter_types[ter].flag3.s;
+ icon = scenario.ter_types[ter].flag3;
break;
default:
icon = -1;
diff --git a/src/scenedit/scen.keydlgs.cpp b/src/scenedit/scen.keydlgs.cpp
index dd65002c..0062cedf 100644
--- a/src/scenedit/scen.keydlgs.cpp
+++ b/src/scenedit/scen.keydlgs.cpp
@@ -316,6 +316,9 @@ short choose_text(eStrType list, unsigned short cur_choice, cDialog* parent, con
case STRT_ENCHANT:
strings = {"+1", "+2", "+3", "Shoot Flames", "Flaming", "+5", "Blessed"};
break;
+ case STRT_DIR:
+ strings = {"North", "Northease", "East", "Southeast", "South", "Southwest", "West", "Northwest", "None"};
+ break;
}
if(cur_choice < 0 || cur_choice >= strings.size())
cur_choice = -1;
diff --git a/src/scenedit/scen.keydlgs.h b/src/scenedit/scen.keydlgs.h
index 7c26f409..1047cb8b 100644
--- a/src/scenedit/scen.keydlgs.h
+++ b/src/scenedit/scen.keydlgs.h
@@ -11,7 +11,7 @@ enum eStrType {
STRT_ATTITUDE, STRT_STAIR, STRT_LIGHT, STRT_CONTEXT,
STRT_SHOP, STRT_COST_ADJ, STRT_STAIR_MODE, STRT_TALK_NODE,
STRT_STATUS, STRT_SPELL_PAT, STRT_SUMMON, STRT_TALK,
- STRT_ENCHANT,
+ STRT_ENCHANT, STRT_DIR,
};
bool cre(short val,short min,short max,std::string text1,std::string text2,cDialog* parent) ;
diff --git a/src/tools/vector2d.hpp b/src/tools/vector2d.hpp
index 48e0441a..9ddaaf24 100644
--- a/src/tools/vector2d.hpp
+++ b/src/tools/vector2d.hpp
@@ -76,6 +76,12 @@ public:
size_t height() const {
return h;
}
+ typename std::vector::iterator begin() {
+ return data.begin();
+ }
+ typename std::vector::iterator end() {
+ return data.end();
+ }
size_t size() const {
return data.size();
}