MODE_EDIT_TYPES support monsters and items, with create/delete undo/redo

This commit is contained in:
2025-06-04 08:51:41 -05:00
parent 1842d376e6
commit 756f29bd1b
8 changed files with 304 additions and 188 deletions

View File

@@ -50,7 +50,7 @@ cUndoList undo_list;
short flood_count = 0;
rectangle terrain_rects[256],terrain_rect_base = {0,0,16,16},command_rects[21];
rectangle terrain_rects[16*TYPE_ROWS_EDITING],terrain_rect_base = {0,0,16,16},command_rects[21];
extern rectangle terrain_buttons_rect;
extern short cen_x, cen_y, cur_town;
@@ -121,7 +121,7 @@ void init_screen_locs() {
border_rect[2].top = border_rect[2].bottom - 8;
border_rect[3].left = border_rect[3].right - 8;
for(short i = 0; i < 256; i++) {
for(short i = 0; i < 16 * TYPE_ROWS_EDITING; i++) {
terrain_rects[i] = terrain_rect_base;
terrain_rects[i].offset(3 + (i % 16) * (terrain_rect_base.right + 1),
3 + (i / 16) * (terrain_rect_base.bottom + 1));
@@ -261,13 +261,13 @@ static bool handle_lb_action(int i){
set_up_start_screen();
break;
case LB_EDIT_TER:
start_terrain_editing();
start_type_editing(DRAW_TERRAIN);
break;
case LB_EDIT_MONST:
start_monster_editing(0);
start_type_editing(DRAW_MONST);
break;
case LB_EDIT_ITEM:
start_item_editing(0);
start_type_editing(DRAW_ITEM);
break;
case LB_NEW_TOWN:
if(scenario.towns.size() >= 200) {
@@ -361,62 +361,6 @@ static bool handle_rb_action(location the_point, bool option_hit) {
switch(right_button_status[i + right_top].action) {
case RB_CLEAR:
break;
case RB_MONST:
size_before = scenario.scen_monsters.size();
if(option_hit) {
if(j == size_before - 1 && !scenario.is_monst_used(j))
scenario.scen_monsters.pop_back();
else if(j == size_before) {
scenario.scen_monsters.resize(size_before + 8);
for(; j < scenario.scen_monsters.size(); j++)
scenario.scen_monsters[j].m_name = "New Monster";
} else {
scenario.scen_monsters[j] = cMonster();
scenario.scen_monsters[j].m_name = "Unused Monster";
}
} else {
if(j == size_before) {
scenario.scen_monsters.emplace_back();
scenario.scen_monsters.back().m_name = "New Monster";
}
if(!edit_monst_type(j) && j == size_before && scenario.scen_monsters.back().m_name == "New Monster")
scenario.scen_monsters.pop_back();
}
start_monster_editing(size_before == scenario.scen_monsters.size());
if(size_before > scenario.scen_monsters.size())
pos_before--;
right_sbar->setPosition(pos_before);
break;
case RB_ITEM:
size_before = scenario.scen_items.size();
if(option_hit) {
if(j == size_before - 1 && !scenario.is_item_used(j))
scenario.scen_items.pop_back();
else if(j == size_before) {
scenario.scen_items.resize(size_before + 8);
for(; j < scenario.scen_items.size(); j++) {
scenario.scen_items[j].full_name = "New Item";
scenario.scen_items[j].name = "Item";
}
} else {
scenario.scen_items[j] = cItem();
scenario.scen_items[j].full_name = "Unused Item";
scenario.scen_items[j].name = "Item";
}
} else {
if(j == size_before) {
scenario.scen_items.emplace_back();
scenario.scen_items.back().full_name = "New Item";
scenario.scen_items.back().name = "Item";
}
if(!edit_item_type(j) && j == size_before && scenario.scen_items.back().name == "New Item")
scenario.scen_items.pop_back();
}
start_item_editing(size_before == scenario.scen_items.size());
if(size_before > scenario.scen_items.size())
pos_before--;
right_sbar->setPosition(pos_before);
break;
case RB_SCEN_SPEC:
size_before = scenario.scen_specials.size();
if(option_hit) {
@@ -1261,7 +1205,9 @@ static bool handle_terrain_action(location the_point, bool ctrl_hit) {
}
static bool handle_terpal_action(location cur_point, bool option_hit) {
for(int i = 0; i < 256; i++)
int rows = TYPE_ROWS_DRAWING;
if(overall_mode == MODE_EDIT_TYPES) rows = TYPE_ROWS_EDITING;
for(int i = 0; i < 16 * rows; i++)
if(cur_point.in(terrain_rects[i])) {
int k = pal_sbar->getPosition() * 16 + i;
rectangle temp_rect = terrain_rects[i];
@@ -1292,59 +1238,180 @@ static bool handle_terpal_action(location cur_point, bool option_hit) {
break;
}
}
// MODE_EDIT_TYPES:
else {
short size_before = scenario.ter_types.size(), pos_before = pal_sbar->getPosition();
short pos_before = pos_before = pal_sbar->getPosition();
i += pos_before * 16;
short size_before = scenario.ter_types.size();
if(draw_mode == DRAW_MONST) size_before = scenario.scen_monsters.size(), i++;
else if(draw_mode == DRAW_ITEM) size_before = scenario.scen_items.size();
if(i > size_before) return true;
if(i == 90){
if(draw_mode == DRAW_TERRAIN && i == 90){
showWarning("The pit/barrier terrain cannot be changed.");
return true;
}
if(option_hit) {
// option-click the plus button: create a new row of terrains
// option-click the plus button: create a new row of types
if(i == size_before){
terrain_type_changes_t terrains;
scenario.ter_types.resize(size_before + 16);
for(; i < scenario.ter_types.size(); i++){
scenario.ter_types[i].name = "New Terrain";
terrains.push_back(scenario.ter_types[i]);
}
switch(draw_mode){
case DRAW_TERRAIN:{
terrain_type_changes_t terrains;
scenario.ter_types.resize(size_before + 16);
for(; i < scenario.ter_types.size(); i++){
scenario.ter_types[i].name = "New Terrain";
terrains.push_back(scenario.ter_types[i]);
}
undo_list.add(action_ptr(new aCreateDeleteTerrain(terrains)));
update_edit_menu();
undo_list.add(action_ptr(new aCreateDeleteTerrain(terrains)));
update_edit_menu();
}break;
case DRAW_MONST:{
monst_type_changes_t monsts;
scenario.scen_monsters.resize(size_before + 16);
for(; i < scenario.scen_monsters.size(); i++){
scenario.scen_monsters[i].m_name = "New Monster";
monsts.push_back(scenario.scen_monsters[i]);
}
undo_list.add(action_ptr(new aCreateDeleteMonster(monsts)));
update_edit_menu();
}break;
case DRAW_ITEM:{
item_type_changes_t items;
scenario.scen_items.resize(size_before + 16);
for(; i < scenario.scen_items.size(); i++){
scenario.scen_items[i].full_name = "New Item";
items.push_back(scenario.scen_items[i]);
}
undo_list.add(action_ptr(new aCreateDeleteItem(items)));
update_edit_menu();
}break;
}
}
else{
// option-click the last one and it's safe to delete: delete it
if(i == size_before - 1 && !scenario.is_ter_used(i)){
undo_list.add(action_ptr(new aCreateDeleteTerrain(false, scenario.ter_types.back())));
update_edit_menu();
scenario.ter_types.pop_back();
}
// option-click terrain that can't be deleted (because it would break other terrains' numbers, or is in use somewhere):
// reset type info
else{
scenario.ter_types[i] = cTerrain();
scenario.ter_types[i].name = "Unused Terrain";
switch(draw_mode){
case DRAW_TERRAIN:
// option-click the last one and it's safe to delete: delete it
if(i == size_before - 1 && !scenario.is_ter_used(i)){
undo_list.add(action_ptr(new aCreateDeleteTerrain(false, scenario.ter_types.back())));
update_edit_menu();
scenario.ter_types.pop_back();
}
// option-click type that can't be deleted (because it would break other types' numbers, or is in use somewhere):
// reset type info
else{
scenario.ter_types[i] = cTerrain();
scenario.ter_types[i].name = "Unused Terrain";
}
break;
case DRAW_MONST:
// option-click the last one and it's safe to delete: delete it
if(i == size_before - 1 && !scenario.is_monst_used(i)){
undo_list.add(action_ptr(new aCreateDeleteMonster(false, scenario.scen_monsters.back())));
update_edit_menu();
scenario.scen_monsters.pop_back();
}
// option-click type that can't be deleted (because it would break other types' numbers, or is in use somewhere):
// reset type info
else{
scenario.scen_monsters[i] = cMonster();
scenario.scen_monsters[i].m_name = "Unused Monster";
}
break;
case DRAW_ITEM:
// option-click the last one and it's safe to delete: delete it
if(i == size_before - 1 && !scenario.is_item_used(i)){
undo_list.add(action_ptr(new aCreateDeleteItem(false, scenario.scen_items.back())));
update_edit_menu();
scenario.scen_items.pop_back();
}
// option-click type that can't be deleted (because it would break other types' numbers, or is in use somewhere):
// reset type info
else{
scenario.scen_items[i] = cItem();
scenario.scen_items[i].full_name = "Unused Item";
}
break;
}
}
} else {
// Click the plus button: create a new terrain and edit it immediately
// Click the plus button: create a new type and edit it immediately
if(i == size_before) {
scenario.ter_types.emplace_back();
scenario.ter_types.back().name = "New Terrain";
switch(draw_mode){
case DRAW_TERRAIN:
scenario.ter_types.emplace_back();
scenario.ter_types.back().name = "New Terrain";
break;
case DRAW_MONST:
scenario.scen_monsters.emplace_back();
scenario.scen_monsters.back().m_name = "New Monster";
break;
case DRAW_ITEM:
scenario.scen_items.emplace_back();
scenario.scen_items.back().full_name = "New Item";
break;
}
}
if(!edit_ter_type(i) && i == size_before && scenario.ter_types.back().name == "New Terrain"){
// Canceled:
scenario.ter_types.pop_back();
}else{
undo_list.add(action_ptr(new aCreateDeleteTerrain(true, scenario.ter_types.back())));
update_edit_menu();
switch(draw_mode){
case DRAW_TERRAIN:
if(!edit_ter_type(i)){
// Canceled editing
if(i == size_before){
// Canceled creating new:
scenario.ter_types.pop_back();
}
}
// Created new:
else if(i == size_before){
undo_list.add(action_ptr(new aCreateDeleteTerrain(true, scenario.ter_types.back())));
update_edit_menu();
}else{
// TODO edited existing (if different)
}
break;
case DRAW_MONST:
if(!edit_monst_type(i)){
// Canceled editing
if(i == size_before){
// Canceled creating new:
scenario.scen_monsters.pop_back();
}
}
// Created new:
else if(i == size_before){
undo_list.add(action_ptr(new aCreateDeleteMonster(true, scenario.scen_monsters.back())));
update_edit_menu();
}else{
// TODO edited existing (if different)
}
break;
case DRAW_ITEM:
if(!edit_item_type(i)){
// Canceled editing
if(i == size_before){
// Canceled creating new:
scenario.scen_items.pop_back();
}
}
// Created new:
else if(i == size_before){
undo_list.add(action_ptr(new aCreateDeleteItem(true, scenario.scen_items.back())));
update_edit_menu();
}else{
// TODO edited existing (if different)
}
break;
}
}
if(size_before / 16 > scenario.ter_types.size() / 16)
pos_before--;
short size_after = scenario.ter_types.size();
if(draw_mode == DRAW_MONST) size_after = scenario.scen_monsters.size(), i++;
else if(draw_mode == DRAW_ITEM) size_after = scenario.scen_items.size();
pos_before += (size_after / 16 - size_before / 16);
pal_sbar->setMaximum(max(pos_before, pal_sbar->getMaximum()));
pal_sbar->setPosition(pos_before);
set_up_terrain_buttons(false);
set_up_type_buttons(false);
change_made = true;
}
place_location();
@@ -1621,15 +1688,15 @@ static bool handle_toolpal_action(location cur_point2) {
break;
case PAL_TERRAIN: // Terrain palette
draw_mode = DRAW_TERRAIN;
set_up_terrain_buttons(true);
set_up_type_buttons(true);
break;
case PAL_ITEM: // Item palette
draw_mode = DRAW_ITEM;
set_up_terrain_buttons(true);
set_up_type_buttons(true);
break;
case PAL_MONST: // Monster palette
draw_mode = DRAW_MONST;
set_up_terrain_buttons(true);
set_up_type_buttons(true);
break;
case PAL_BOAT:
set_string("Place/edit boat","Select boat location");
@@ -2732,7 +2799,7 @@ void start_town_edit() {
scenario.editor_state.editing_town = editing_town = true;
scenario.editor_state.drawing = true;
restore_current_town_state();
set_up_terrain_buttons(true);
set_up_type_buttons(true);
shut_down_menus(4);
shut_down_menus(2);
right_sbar->hide();
@@ -2779,7 +2846,7 @@ void start_out_edit() {
scenario.editor_state.editing_town = editing_town = false;
scenario.editor_state.drawing = true;
restore_current_out_state();
set_up_terrain_buttons(true);
set_up_type_buttons(true);
right_sbar->hide();
pal_sbar->show();
shut_down_menus(4);
@@ -2797,68 +2864,19 @@ void start_out_edit() {
redraw_screen();
}
void start_terrain_editing() {
void start_type_editing(eDrawMode mode) {
right_sbar->hide();
pal_sbar->show();
overall_mode = MODE_EDIT_TYPES;
draw_mode = DRAW_TERRAIN;
set_up_terrain_buttons(true);
draw_mode = mode;
set_up_type_buttons(true);
place_location();
set_lb(NLS - 3,LB_TEXT,LB_NO_ACTION,"Alt-click to delete/clear",true);
set_lb(NLS - 2,LB_TEXT,LB_NO_ACTION,"Alt-click '+' to add many",true);
update_mouse_spot(translate_mouse_coordinates(sf::Mouse::getPosition(mainPtr())));
}
void start_monster_editing(bool just_redo_text) {
int num_options = scenario.scen_monsters.size() + 1;
if(!just_redo_text) {
handle_close_terrain_view(MODE_MAIN_SCREEN);
right_sbar->show();
pal_sbar->hide();
right_sbar->setPosition(0);
reset_rb();
right_sbar->setMaximum(num_options - 1 - NRSONPAGE);
}
for(short i = 1; i < num_options; i++) {
std::string title;
if(i == scenario.scen_monsters.size())
title = "Create New Monster";
else title = scenario.scen_monsters[i].m_name;
title = std::to_string(i) + " - " + title;
set_rb(i - 1,RB_MONST, i, title);
}
set_lb(NLS - 3,LB_TEXT,LB_NO_ACTION,"Alt-click to delete",true);
update_mouse_spot(translate_mouse_coordinates(sf::Mouse::getPosition(mainPtr())));
redraw_screen();
}
void start_item_editing(bool just_redo_text) {
int num_options = scenario.scen_items.size() + 1;
if(!just_redo_text) {
handle_close_terrain_view(MODE_MAIN_SCREEN);
right_sbar->show();
pal_sbar->hide();
right_sbar->setPosition(0);
reset_rb();
right_sbar->setMaximum(num_options - NRSONPAGE);
}
for(short i = 0; i < num_options; i++) {
std::string title;
if(i == scenario.scen_items.size())
title = "Create New Item";
else title = scenario.scen_items[i].full_name;
title = std::to_string(i) + " - " + title;
set_rb(i,RB_ITEM, i, title);
}
set_lb(NLS - 3,LB_TEXT,LB_NO_ACTION,"Alt-click to delete",true);
update_mouse_spot(translate_mouse_coordinates(sf::Mouse::getPosition(mainPtr())));
redraw_screen();
}
void start_special_item_editing(bool just_redo_text) {
int num_options = scenario.special_items.size() + 1;

View File

@@ -35,9 +35,7 @@ void set_up_start_screen();
void set_up_main_screen();
void start_town_edit();
void start_out_edit();
void start_terrain_editing();
void start_monster_editing(bool just_redo_text);
void start_item_editing(bool just_redo_text);
void start_type_editing(eDrawMode mode);
void start_special_item_editing(bool just_redo_text);
void start_quest_editing(bool just_redo_text);
void start_shops_editing(bool just_redo_text);

View File

@@ -22,8 +22,6 @@ enum eLBAction {
enum eRBAction {
RB_CLEAR = 0,
RB_MONST = 2,
RB_ITEM = 3,
RB_SCEN_SPEC = 4,
RB_OUT_SPEC = 5,
RB_TOWN_SPEC = 6,

View File

@@ -22,6 +22,10 @@ const int TER_RECT_UL_Y = 19;
const int UI_LAYER_DEFAULT = 1000;
const int UI_LAYER_MENUBAR = 1200;
// When editing types, several more rows can fit because the tool palette isn't there
const int TYPE_ROWS_DRAWING = 16;
const int TYPE_ROWS_EDITING = 23;
enum eScenMode {
MODE_DRAWING = 0,
MODE_TOGGLE_ROAD = 1,

View File

@@ -83,12 +83,13 @@ extern rectangle palette_buttons[10][6];
extern ePalBtn town_buttons[6][10], out_buttons[6][10];
rectangle palette_button_base = {0,0,18,26};
rectangle terrain_buttons_rect = {0,0,410,294};
rectangle terrain_buttons_rect_editing = {0,0,610,294};
extern rectangle left_buttons[NLS][2]; // 0 - whole, 1 - blue button
rectangle left_button_base = {5,5,21,280};
rectangle right_button_base = {RIGHT_AREA_UL_Y,RIGHT_AREA_UL_X,17,RIGHT_AREA_UL_Y};
rectangle terrain_rect = {0,0,340,272};
std::string current_string[2];
extern rectangle terrain_rects[256];
extern rectangle terrain_rects[16*TYPE_ROWS_EDITING];
unsigned char small_what_drawn[64][64];
extern bool small_any_drawn;
@@ -331,6 +332,7 @@ static std::vector<short> get_small_icons(location at, ter_num_t t_to_draw) {
void Set_up_win() {
terrain_rect.offset(TER_RECT_UL_X, TER_RECT_UL_Y);
terrain_buttons_rect.offset(RIGHT_AREA_UL_X, RIGHT_AREA_UL_Y);
terrain_buttons_rect_editing.offset(RIGHT_AREA_UL_X, RIGHT_AREA_UL_Y);
palette_button_base.offset(RIGHT_AREA_UL_X, RIGHT_AREA_UL_Y);
for(short i = 0; i < 10; i++)
@@ -442,7 +444,7 @@ void draw_main_screen() {
// draw terrain palette
if((overall_mode < MODE_MAIN_SCREEN) || (overall_mode == MODE_EDIT_TYPES)) {
place_location();
set_up_terrain_buttons(false);
set_up_type_buttons(false);
TextStyle style;
win_draw_string(mainPtr(), search_field_text_rect, "Search:", eTextMode::WRAP, style);
palette_search_field->show();
@@ -528,27 +530,33 @@ void draw_rb_slot (short which,short mode) {
win_draw_string(mainPtr(),text_rect,right_button_status[which].label,eTextMode::LEFT_TOP,style);
}
void set_up_terrain_buttons(bool reset) {
void set_up_type_buttons(bool reset) {
short pic,small_i;
rectangle ter_from,ter_from_base = {0,0,36,28}, ter_plus_from = {148,235,164,251};
rectangle tiny_from,tiny_to;
rectangle palette_from,palette_to = palette_button_base;
int max;
int rows = TYPE_ROWS_DRAWING;
switch(draw_mode) {
case DRAW_TERRAIN: max = scenario.ter_types.size(); break;
case DRAW_ITEM: max = scenario.scen_items.size(); break;
case DRAW_MONST: max = scenario.scen_monsters.size(); max--; break;
case DRAW_MONST: max = scenario.scen_monsters.size(); max--; break; // I think this is because monsters have no number 0
default: return;
}
if(overall_mode == MODE_EDIT_TYPES) max++;
if(overall_mode == MODE_EDIT_TYPES){
max++; // The plus button
rows = TYPE_ROWS_EDITING;
}
if(reset) pal_sbar->setPosition(0);
pal_sbar->setMaximum((max - 241) / 16);
int rows_overflow = ceil(max / 16.0) - rows;
pal_sbar->setMaximum(rows_overflow);
int first = pal_sbar->getPosition() * 16;
if(draw_mode == DRAW_MONST) first++, max++;
int end = min(first + 256, max);
if(draw_mode == DRAW_MONST) first++, max++; // Monsters have no number 0
int end = min(first + 16 * rows, max);
std::string search_query = palette_search_field->getText();
boost::algorithm::to_lower(search_query);
@@ -566,6 +574,7 @@ void set_up_terrain_buttons(bool reset) {
draw_rect.offset(RIGHT_AREA_UL_X, RIGHT_AREA_UL_Y);
switch(draw_mode){
case DRAW_TERRAIN:{
// Plus button
if(i == scenario.ter_types.size()) {
rect_draw_some_item(editor_mixed, ter_plus_from, mainPtr(), draw_rect);
break;
@@ -609,6 +618,11 @@ void set_up_terrain_buttons(bool reset) {
rect_draw_some_item(editor_mixed, tiny_from, mainPtr(), tiny_to, sf::BlendAlpha, colour);
}break;
case DRAW_MONST:{
// Plus button
if(i == scenario.scen_monsters.size()) {
rect_draw_some_item(editor_mixed, ter_plus_from, mainPtr(), draw_rect);
break;
}
const cMonster& monst = scenario.scen_monsters[i];
std::string name = monst.m_name;
@@ -718,6 +732,11 @@ void set_up_terrain_buttons(bool reset) {
}
}break;
case DRAW_ITEM:{
// Plus button
if(i == scenario.scen_items.size()) {
rect_draw_some_item(editor_mixed, ter_plus_from, mainPtr(), draw_rect);
break;
}
const cItem& item = scenario.scen_items[i];
pic = item.graphic_num;
@@ -1421,16 +1440,23 @@ void place_location() {
frame_rect(mainPtr(), terrain_buttons_rect, sf::Color::Black);
location mouse = translate_mouse_coordinates(sf::Mouse::getPosition(mainPtr()));
location moveTo(5, terrain_rects[255].top + 18);
location moveTo(5, terrain_rects[16 * TYPE_ROWS_DRAWING - 1].top + 18);
if(overall_mode == MODE_EDIT_TYPES) moveTo.y = terrain_rects[16 * TYPE_ROWS_EDITING -1].top + 18;
draw_rect = text_rect;
draw_rect.offset(moveTo);
if(overall_mode < MODE_MAIN_SCREEN) {
// std::cout << "Mouse: " << mouse << " Buttons: " << terrain_buttons_rect << " Terrain: " << terrain_rect << std::endl;
if(mouse.in(terrain_buttons_rect)) {
// Drawing modes and type editing mode, show tooltips for the type buttons
if(overall_mode < MODE_MAIN_SCREEN || overall_mode == MODE_EDIT_TYPES) {
rectangle buttons_rect = terrain_buttons_rect;
int rows = TYPE_ROWS_DRAWING;
if(overall_mode == MODE_EDIT_TYPES){
buttons_rect = terrain_buttons_rect_editing;
rows = TYPE_ROWS_EDITING;
}
if(mouse.in(buttons_rect)) {
location rel_mouse = mouse;
rel_mouse.x -= RIGHT_AREA_UL_X;
rel_mouse.y -= RIGHT_AREA_UL_Y;
for(int i = 0; i < 256; i++) {
for(int i = 0; i < 16 * rows; i++) {
if(rel_mouse.in(terrain_rects[i])) {
int first = pal_sbar->getPosition() * 16;
switch(draw_mode) {
@@ -1452,26 +1478,35 @@ void place_location() {
break;
}
}
} else if(mouse.in(terrain_rect) && mouse_spot.x >= 0)
sout << "Under mouse: x = " << (cen_x - 4 + mouse_spot.x)
<< ", y = " << (cen_y - 4 + mouse_spot.y);
if(sout.str().empty())
sout << "Center: x = " << cen_x << ", y = " << cen_y;
} else {
moveTo.y += 13; // TODO: Not sure how important this is.
sout << "Click terrain to edit. ";
}
}
// Edit types, when none are hovered
if(sout.str().empty() && overall_mode == MODE_EDIT_TYPES){
moveTo.y += 13;
std::string type = "terrain";
if(draw_mode == DRAW_MONST) type = "monster";
else if(draw_mode == DRAW_ITEM) type = "item";
sout << "Click " << type << " to edit.";
}
// Modes showing the terrain map, show the highlighted spot coords or screen center coords
if(sout.str().empty() && mouse.in(terrain_rect) && mouse_spot.x >= 0)
sout << "Under mouse: x = " << (cen_x - 4 + mouse_spot.x)
<< ", y = " << (cen_y - 4 + mouse_spot.y);
if(sout.str().empty())
sout << "Center: x = " << cen_x << ", y = " << cen_y;
TextStyle style;
style.lineHeight = 12;
win_draw_string(mainPtr(), draw_rect, sout.str(), eTextMode::LEFT_TOP, style);
clear_sstr(sout);
moveTo = location(260 ,terrain_rects[255].top + 18);
draw_rect = text_rect;
draw_rect.offset(moveTo);
sout << current_terrain_type;
win_draw_string(mainPtr(), draw_rect, sout.str(), eTextMode::LEFT_TOP, style);
clear_sstr(sout);
if(overall_mode != MODE_EDIT_TYPES){
moveTo = location(260, terrain_rects[255].top + 18);
draw_rect = text_rect;
draw_rect.offset(moveTo);
sout << current_terrain_type;
win_draw_string(mainPtr(), draw_rect, sout.str(), eTextMode::LEFT_TOP, style);
clear_sstr(sout);
}
if(overall_mode < MODE_MAIN_SCREEN) {
moveTo = location(5,terrain_rects[255].bottom + 121);

View File

@@ -12,7 +12,7 @@ void draw_lb();
void draw_lb_slot (short which,short mode) ;
void draw_rb();
void draw_rb_slot (short which,short mode) ;
void set_up_terrain_buttons(bool reset);
void set_up_type_buttons(bool reset);
rectangle visible_bounds();
void draw_terrain();
void draw_monsts();

View File

@@ -110,6 +110,38 @@ bool aCreateDeleteTerrain::redo_me() {
return true;
}
bool aCreateDeleteMonster::undo_me() {
// TODO if not in MODE_EDIT_TYPES, show it
for(cMonster monst : monsters){
scenario.scen_monsters.pop_back();
}
return true;
}
bool aCreateDeleteMonster::redo_me() {
// TODO if not in MODE_EDIT_TYPES, show it
for(cMonster monst : monsters){
scenario.scen_monsters.push_back(monst);
}
return true;
}
bool aCreateDeleteItem::undo_me() {
// TODO if not in MODE_EDIT_TYPES, show it
for(cItem item : items){
scenario.scen_items.pop_back();
}
return true;
}
bool aCreateDeleteItem::redo_me() {
// TODO if not in MODE_EDIT_TYPES, show it
for(cItem item : items){
scenario.scen_items.push_back(item);
}
return true;
}
bool aDrawTerrain::undo_me() {
cArea* cur_area = get_current_area();
for(auto change : changes){

View File

@@ -5,6 +5,8 @@
#include "tools/undo.hpp"
#include "scenario/town.hpp"
#include "scenario/scenario.hpp"
#include "scenario/item.hpp"
#include "scenario/monster.hpp"
extern cScenario scenario;
@@ -25,6 +27,8 @@ typedef std::map<location,ter_change_t,loc_compare> stroke_ter_changes_t;
typedef std::map<size_t, cTown::cItem> item_changes_t;
typedef std::map<size_t, cTownperson> creature_changes_t;
typedef std::vector<cTerrain> terrain_type_changes_t;
typedef std::vector<cMonster> monst_type_changes_t;
typedef std::vector<class cItem> item_type_changes_t;
// Action that modified something in town or outdoor terrain, so we should show the modified area when undoing or redoing
class cTerrainAction : public cAction {
@@ -112,5 +116,32 @@ public:
terrains(terrains) {}
};
/// Action which adds new monster type(s) to the end of the list, or deletes from the end of the list
class aCreateDeleteMonster : public cAction {
monst_type_changes_t monsters;
bool undo_me() override;
bool redo_me() override;
public:
aCreateDeleteMonster(bool create, cMonster monst) :
cAction(create ? "Create Monster Type" : "Delete Monster Type", !create),
monsters({monst}) {}
aCreateDeleteMonster(monst_type_changes_t monsts) :
cAction("Create Monster Types", false),
monsters(monsts) {}
};
/// Action which adds new item type(s) to the end of the list, or deletes from the end of the list
class aCreateDeleteItem : public cAction {
item_type_changes_t items;
bool undo_me() override;
bool redo_me() override;
public:
aCreateDeleteItem(bool create, class cItem item) :
cAction(create ? "Create Item Type" : "Delete Item Type", !create),
items({item}) {}
aCreateDeleteItem(item_type_changes_t items) :
cAction("Create Item Types", false),
items(items) {}
};
#endif