Cut and paste functionality added in the editor
This commit is contained in:
parent
0c3c4054f4
commit
2fa19dc876
5 changed files with 105 additions and 11 deletions
|
@ -122,6 +122,30 @@ alt=no
|
|||
shift=no
|
||||
[/hotkey]
|
||||
|
||||
[hotkey]
|
||||
command="editcut"
|
||||
key="x"
|
||||
ctrl=yes
|
||||
alt=no
|
||||
shift=no
|
||||
[/hotkey]
|
||||
|
||||
[hotkey]
|
||||
command="editcopy"
|
||||
key="c"
|
||||
ctrl=yes
|
||||
alt=no
|
||||
shift=no
|
||||
[/hotkey]
|
||||
|
||||
[hotkey]
|
||||
command="editpaste"
|
||||
key="v"
|
||||
ctrl=yes
|
||||
alt=no
|
||||
shift=no
|
||||
[/hotkey]
|
||||
|
||||
[resolution]
|
||||
width=800
|
||||
height=600
|
||||
|
@ -143,7 +167,7 @@ height=600
|
|||
|
||||
[menu]
|
||||
is_context_menu=true
|
||||
items=undo,redo,editfloodfill,editfillselection,togglegrid,editsetstartpos
|
||||
items=undo,redo,editfloodfill,editfillselection,togglegrid,editsetstartpos,editcut,editcopy,editpaste
|
||||
[/menu]
|
||||
|
||||
# top panel
|
||||
|
|
|
@ -471,9 +471,9 @@ action_editquit="Quit Editor"
|
|||
action_editsetstartpos="Set Player Start Position"
|
||||
action_editfloodfill="Flood Fill"
|
||||
action_editfillselection="Fill Selection"
|
||||
action_edit_cut="Cut"
|
||||
action_edit_copy="Copy"
|
||||
action_edit_paste="Paste"
|
||||
action_editcut="Cut"
|
||||
action_editcopy="Copy"
|
||||
action_editpaste="Paste"
|
||||
save_hotkeys_button="Save Hotkeys"
|
||||
change_hotkey_button="Change Hotkey"
|
||||
hotkeys_dialog="Hotkey Settings"
|
||||
|
|
|
@ -42,6 +42,7 @@
|
|||
#include <iostream>
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <cmath>
|
||||
|
||||
namespace {
|
||||
const unsigned int undo_limit = 100;
|
||||
|
@ -61,6 +62,13 @@ namespace {
|
|||
map.set_starting_position(start_side, gamemap::location());
|
||||
}
|
||||
}
|
||||
|
||||
double location_distance(const gamemap::location loc1, const gamemap::location loc2) {
|
||||
const double xdiff = loc1.x - loc2.x;
|
||||
const double ydiff = loc1.y - loc2.y;
|
||||
const double dist = std::sqrt(xdiff * xdiff + ydiff * ydiff);
|
||||
return dist;
|
||||
}
|
||||
}
|
||||
|
||||
namespace map_editor {
|
||||
|
@ -210,7 +218,6 @@ void map_editor::edit_flood_fill() {
|
|||
flood_fill(map_, selected_hex_, palette_.selected_terrain(), &log);
|
||||
std::vector<gamemap::location> to_invalidate;
|
||||
map_undo_action action;
|
||||
num_operations_since_save_++;
|
||||
for (terrain_log::iterator it = log.begin(); it != log.end(); it++) {
|
||||
to_invalidate.push_back((*it).first);
|
||||
action.add((*it).second, palette_.selected_terrain(),
|
||||
|
@ -257,17 +264,64 @@ void map_editor::edit_fill_selection() {
|
|||
}
|
||||
|
||||
void map_editor::edit_cut() {
|
||||
|
||||
clipboard_.clear();
|
||||
insert_selection_in_clipboard();
|
||||
edit_fill_selection();
|
||||
}
|
||||
|
||||
void map_editor::edit_copy() {
|
||||
|
||||
clipboard_.clear();
|
||||
insert_selection_in_clipboard();
|
||||
}
|
||||
|
||||
void map_editor::edit_paste() {
|
||||
|
||||
map_undo_action undo_action;
|
||||
std::vector<gamemap::location> filled;
|
||||
gamemap::location start_hex = selected_hex_;
|
||||
// The x coordinate may need to be adjusted because the same
|
||||
// representation of the hexes may not look the same on the map, and
|
||||
// we want to make sure it looks the same when pasted.
|
||||
start_hex.x = start_hex.x % 2 == clipboard_offset_loc_.x % 2 ? start_hex.x : start_hex.x - 1;
|
||||
for (std::vector<clipboard_item>::const_iterator it = clipboard_.begin();
|
||||
it != clipboard_.end(); it++) {
|
||||
const gamemap::location target =
|
||||
gamemap::location(start_hex.x + (*it).x_offset,
|
||||
start_hex.y + (*it).y_offset);
|
||||
if (map_.on_board(target)) {
|
||||
undo_action.add(map_.get_terrain(target), (*it).terrain, target);
|
||||
map_.set_terrain(target, (*it).terrain);
|
||||
filled.push_back(target);
|
||||
}
|
||||
}
|
||||
invalidate_all_and_adjacent(filled);
|
||||
add_undo_action(undo_action);
|
||||
}
|
||||
|
||||
|
||||
void map_editor::insert_selection_in_clipboard() {
|
||||
if (selected_hexes_.empty()) {
|
||||
return;
|
||||
}
|
||||
gamemap::location offset_hex = *(selected_hexes_.begin());
|
||||
std::set<gamemap::location>::const_iterator it;
|
||||
// Find the hex that is closest to the selected one, use this as the
|
||||
// one to calculate the offset from.
|
||||
for (it = selected_hexes_.begin(); it != selected_hexes_.end(); it++) {
|
||||
if (location_distance(selected_hex_, *it) <
|
||||
location_distance(selected_hex_, offset_hex)) {
|
||||
offset_hex = *it;
|
||||
}
|
||||
}
|
||||
clipboard_offset_loc_ = offset_hex;
|
||||
for (it = selected_hexes_.begin(); it != selected_hexes_.end(); it++) {
|
||||
const int x_offset = (*it).x - offset_hex.x;
|
||||
const int y_offset = (*it).y - offset_hex.y;
|
||||
gamemap::TERRAIN terrain = map_.get_terrain(*it);
|
||||
clipboard_.push_back(clipboard_item(x_offset, y_offset, terrain));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool map_editor::can_execute_command(hotkey::HOTKEY_COMMAND command) const {
|
||||
switch (command) {
|
||||
case hotkey::HOTKEY_UNDO:
|
||||
|
@ -285,6 +339,9 @@ bool map_editor::can_execute_command(hotkey::HOTKEY_COMMAND command) const {
|
|||
case hotkey::HOTKEY_EDIT_LOAD_MAP:
|
||||
case hotkey::HOTKEY_EDIT_FLOOD_FILL:
|
||||
case hotkey::HOTKEY_EDIT_FILL_SELECTION:
|
||||
case hotkey::HOTKEY_EDIT_COPY:
|
||||
case hotkey::HOTKEY_EDIT_CUT:
|
||||
case hotkey::HOTKEY_EDIT_PASTE:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
|
@ -302,6 +359,7 @@ void map_editor::add_undo_action(const map_undo_action &action) {
|
|||
if(undo_stack_.size() > undo_limit) {
|
||||
undo_stack_.pop_front();
|
||||
}
|
||||
num_operations_since_save_++;
|
||||
}
|
||||
|
||||
void map_editor::undo() {
|
||||
|
@ -428,7 +486,6 @@ void map_editor::left_button_down(const int mousex, const int mousey) {
|
|||
else {
|
||||
std::vector<gamemap::location> locs =
|
||||
get_tiles(map_, hex, brush_.selected_brush_size());
|
||||
++num_operations_since_save_;
|
||||
redo_stack_.clear();
|
||||
map_undo_action action;
|
||||
std::vector<gamemap::location> to_invalidate;
|
||||
|
|
|
@ -196,13 +196,24 @@ private:
|
|||
void recalculate_starting_pos_labels();
|
||||
|
||||
/// Add an undo action to the undo stack. Resize the stack if it
|
||||
/// gets larger than the maximum size.
|
||||
/// gets larger than the maximum size. Add an operation to the
|
||||
/// number done since save.
|
||||
void add_undo_action(const map_undo_action &action);
|
||||
|
||||
/// Update the selection and highlightning of the hexes the mouse
|
||||
/// currently is over.
|
||||
void update_mouse_over_hexes(const gamemap::location mouse_over_hex);
|
||||
|
||||
/// Insert the currently selected locations in the clipboard.
|
||||
void insert_selection_in_clipboard();
|
||||
|
||||
struct clipboard_item {
|
||||
clipboard_item(int xo, int yo, gamemap::TERRAIN t) :
|
||||
x_offset(xo), y_offset(yo), terrain(t) {}
|
||||
int x_offset, y_offset;
|
||||
gamemap::TERRAIN terrain;
|
||||
};
|
||||
|
||||
display &gui_;
|
||||
gamemap &map_;
|
||||
gui::button tup_, tdown_;
|
||||
|
@ -230,6 +241,8 @@ private:
|
|||
std::set<gamemap::location> mouse_over_hexes_;
|
||||
std::set<gamemap::location> selected_hexes_;
|
||||
bool add_selection_;
|
||||
std::vector<clipboard_item> clipboard_;
|
||||
gamemap::location clipboard_offset_loc_;
|
||||
};
|
||||
|
||||
}
|
||||
|
|
|
@ -77,7 +77,7 @@ HOTKEY_COMMAND string_to_command(const std::string& str)
|
|||
m.insert(val("editfillselection",HOTKEY_EDIT_FILL_SELECTION));
|
||||
m.insert(val("editcut",HOTKEY_EDIT_CUT));
|
||||
m.insert(val("editcopy",HOTKEY_EDIT_COPY));
|
||||
m.insert(val("editpsate",HOTKEY_EDIT_COPY));
|
||||
m.insert(val("editpaste",HOTKEY_EDIT_PASTE));
|
||||
m.insert(val("toggleshroud",HOTKEY_TOGGLE_SHROUD));
|
||||
m.insert(val("updateshroud",HOTKEY_UPDATE_SHROUD));
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue