blob: e82283f684625eec941b3fa10c1b607d721833fd (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
|
// undo.h -*-c++-*-
//
// Copyright 2000 Daniel Burrows
//
//
#ifndef UNDO_H
#define UNDO_H
#include <list>
#include <sigc++/signal.h>
/** \brief A generic structure for undo information.
*
* \file undo.h
*/
class undoable
// represents an action which can be undone.
{
public:
virtual void undo()=0;
// Undoes the action (doh! :) )
virtual ~undoable() {}
};
class undo_group:public undoable
// Groups several undo actions into a single shot -- does them from first to
// last..
{
std::list<undoable *> items;
public:
virtual void undo()
{
for(std::list<undoable *>::iterator i=items.begin(); i!=items.end(); i++)
(*i)->undo();
}
void add_item(undoable *item)
{
items.push_front(item);
}
bool empty() {return items.empty();}
virtual ~undo_group()
{
for(std::list<undoable *>::iterator i=items.begin(); i!=items.end(); i++)
delete *i;
}
};
class undo_list
// A very very simple way to allow things to be undone. It takes
// responsibility for deleting pointers that it's given.
{
std::list<undoable *> items;
std::list<unsigned int> floors;
public:
undo_list() {floors.push_back(0);}
void undo();
void add_item(undoable *item)
// Inserts an item into the stack of undoable actions
{
items.push_front(item);
changed();
}
void clear_items();
unsigned int size() {return items.size();}
void collapse_to(unsigned int prev_size);
void revert_to(unsigned int prev_size);
// These can be used to place a 'mark' in the undo stack at a given point,
// then either collapse actions after that point to a single action
// (collapse_to) or revert them altogether (revert_to)
void push_floor(unsigned int floor);
void pop_floor();
/** \brief Emitted after a new entry is added to the list and after
* an entry is removed from the list.
*/
sigc::signal0<void> changed;
virtual ~undo_list()
{
for(std::list<undoable *>::iterator i=items.begin(); i!=items.end(); i++)
delete (*i);
}
};
#endif
|