doxygen: add newline after \file
[blender.git] / source / blender / blenkernel / BKE_undo_system.h
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  */
16 #ifndef __BKE_UNDO_SYSTEM_H__
17 #define __BKE_UNDO_SYSTEM_H__
18
19 /** \file
20  * \ingroup bke
21  */
22
23 struct Main;
24 struct UndoStep;
25 struct bContext;
26
27 /* ID's */
28 struct Main;
29 struct Mesh;
30 struct Object;
31 struct Scene;
32 struct Text;
33
34 #include "DNA_ID.h"
35 #include "DNA_listBase.h"
36
37 typedef struct UndoRefID { struct ID *ptr; char name[MAX_ID_NAME]; } UndoRefID;
38 /* UndoRefID_Mesh & friends. */
39 #define UNDO_REF_ID_TYPE(ptr_ty) \
40         typedef struct UndoRefID_##ptr_ty { struct ptr_ty *ptr; char name[MAX_ID_NAME]; } UndoRefID_##ptr_ty
41 UNDO_REF_ID_TYPE(Mesh);
42 UNDO_REF_ID_TYPE(Object);
43 UNDO_REF_ID_TYPE(Scene);
44 UNDO_REF_ID_TYPE(Text);
45
46 typedef struct UndoStack {
47         ListBase         steps;
48         struct UndoStep *step_active;
49         /**
50          * The last memfile state read, used so we can be sure the names from the
51          * library state matches the state an undo step was written in.
52          */
53         struct UndoStep *step_active_memfile;
54
55         /**
56          * Some undo systems require begin/end, see: #UndoType.step_encode_init
57          *
58          * \note This is not included in the 'steps' list.
59          * That is done once end is called.
60          */
61         struct UndoStep *step_init;
62 } UndoStack;
63
64
65 typedef struct UndoStep {
66         struct UndoStep *next, *prev;
67         char name[64];
68         const struct UndoType *type;
69         /** Size in bytes of all data in step (not including the step). */
70         size_t data_size;
71         /** Users should never see this step (only use for internal consistency). */
72         bool skip;
73         /** Some situations require the global state to be stored, edge cases when exiting modes. */
74         bool use_memfile_step;
75         /** For use by undo systems that accumulate changes (text editor, painting). */
76         bool is_applied;
77         /* Over alloc 'type->struct_size'. */
78 } UndoStep;
79
80 typedef void (*UndoTypeForEachIDRefFn)(void *user_data, struct UndoRefID *id_ref);
81
82 typedef struct UndoType {
83         struct UndoType *next, *prev;
84         /** Only for debugging. */
85         const char *name;
86
87         /**
88          * When NULL, we don't consider this undo type for context checks.
89          * Operators must explicitly set the undo type and handle adding the undo step.
90          * This is needed when tools operate on data which isn't the primary mode (eg, paint-curve in sculpt mode).
91          */
92         bool (*poll)(struct bContext *C);
93
94         /**
95          * None of these callbacks manage list add/removal.
96          *
97          * Note that 'step_encode_init' is optional,
98          * some undo types need to perform operatons before undo push finishes.
99          */
100         void (*step_encode_init)(struct bContext *C, UndoStep *us);
101
102         bool (*step_encode)(struct bContext *C, struct Main *bmain, UndoStep *us);
103         void (*step_decode)(struct bContext *C, struct Main *bmain, UndoStep *us, int dir);
104
105         /**
106          * \note When freeing all steps,
107          * free from the last since #MemFileUndoType will merge with the next undo type in the list. */
108         void (*step_free)(UndoStep *us);
109
110         void (*step_foreach_ID_ref)(UndoStep *us, UndoTypeForEachIDRefFn foreach_ID_ref_fn, void *user_data);
111
112         bool use_context;
113
114         int step_size;
115 } UndoType;
116
117 /* expose since we need to perform operations on spesific undo types (rarely). */
118 extern const UndoType *BKE_UNDOSYS_TYPE_IMAGE;
119 extern const UndoType *BKE_UNDOSYS_TYPE_MEMFILE;
120 extern const UndoType *BKE_UNDOSYS_TYPE_PAINTCURVE;
121 extern const UndoType *BKE_UNDOSYS_TYPE_PARTICLE;
122 extern const UndoType *BKE_UNDOSYS_TYPE_SCULPT;
123 extern const UndoType *BKE_UNDOSYS_TYPE_TEXT;
124
125 #define BKE_UNDOSYS_TYPE_IS_MEMFILE_SKIP(ty) \
126         ELEM(ty, BKE_UNDOSYS_TYPE_IMAGE)
127
128 UndoStack      *BKE_undosys_stack_create(void);
129 void            BKE_undosys_stack_destroy(UndoStack *ustack);
130 void            BKE_undosys_stack_clear(UndoStack *ustack);
131 void            BKE_undosys_stack_clear_active(UndoStack *ustack);
132 bool            BKE_undosys_stack_has_undo(UndoStack *ustack, const char *name);
133 void            BKE_undosys_stack_init_from_main(UndoStack *ustack, struct Main *bmain);
134 void            BKE_undosys_stack_init_from_context(UndoStack *ustack, struct bContext *C);
135 UndoStep       *BKE_undosys_stack_active_with_type(UndoStack *ustack, const UndoType *ut);
136 UndoStep       *BKE_undosys_stack_init_or_active_with_type(UndoStack *ustack, const UndoType *ut);
137 void            BKE_undosys_stack_limit_steps_and_memory(UndoStack *ustack, int steps, size_t memory_limit);
138
139 /* Only some UndoType's require init. */
140 UndoStep *BKE_undosys_step_push_init_with_type(UndoStack *ustack, struct bContext *C, const char *name, const UndoType *ut);
141 UndoStep *BKE_undosys_step_push_init(UndoStack *ustack, struct bContext *C, const char *name);
142
143 bool BKE_undosys_step_push_with_type(UndoStack *ustack, struct bContext *C, const char *name, const UndoType *ut);
144 bool BKE_undosys_step_push(UndoStack *ustack, struct bContext *C, const char *name);
145
146 UndoStep *BKE_undosys_step_find_by_name_with_type(UndoStack *ustack, const char *name, const UndoType *ut);
147 UndoStep *BKE_undosys_step_find_by_type(UndoStack *ustack, const UndoType *ut);
148 UndoStep *BKE_undosys_step_find_by_name(UndoStack *ustack, const char *name);
149
150 bool BKE_undosys_step_undo_with_data_ex(UndoStack *ustack, struct bContext *C, UndoStep *us, bool use_skip);
151 bool BKE_undosys_step_undo_with_data(UndoStack *ustack, struct bContext *C, UndoStep *us);
152 bool BKE_undosys_step_undo(UndoStack *ustack, struct bContext *C);
153
154 bool BKE_undosys_step_redo_with_data_ex(UndoStack *ustack, struct bContext *C, UndoStep *us, bool use_skip);
155 bool BKE_undosys_step_redo_with_data(UndoStack *ustack, struct bContext *C, UndoStep *us);
156 bool BKE_undosys_step_redo(UndoStack *ustack, struct bContext *C);
157
158 bool BKE_undosys_step_load_data(UndoStack *ustack, struct bContext *C, UndoStep *us);
159
160 void BKE_undosys_step_undo_from_index(UndoStack *ustack, struct bContext *C, int index);
161 UndoStep *BKE_undosys_step_same_type_next(UndoStep *us);
162 UndoStep *BKE_undosys_step_same_type_prev(UndoStep *us);
163
164 /* Type System */
165 UndoType *BKE_undosys_type_append(void (*undosys_fn)(UndoType *));
166 void      BKE_undosys_type_free_all(void);
167
168 /* ID Accessor */
169 #if 0  /* functionality is only used internally for now. */
170 void BKE_undosys_foreach_ID_ref(UndoStack *ustack, UndoTypeForEachIDRefFn foreach_ID_ref_fn, void *user_data);
171 #endif
172
173 /* Use when the undo step stores many arbitrary pointers. */
174 struct UndoIDPtrMap;
175 struct UndoIDPtrMap *BKE_undosys_ID_map_create(void);
176 void                 BKE_undosys_ID_map_destroy(struct UndoIDPtrMap *map);
177 void                 BKE_undosys_ID_map_add(struct UndoIDPtrMap *map, ID *id);
178 struct ID           *BKE_undosys_ID_map_lookup(const struct UndoIDPtrMap *map, const struct ID *id_src);
179
180 void BKE_undosys_ID_map_add_with_prev(
181         struct UndoIDPtrMap *map, struct ID *id,
182         struct ID **id_prev);
183 struct ID *BKE_undosys_ID_map_lookup_with_prev(
184         const struct UndoIDPtrMap *map, struct ID *id_src,
185         struct ID *id_prev_match[2]);
186
187 void BKE_undosys_ID_map_foreach_ID_ref(
188         struct UndoIDPtrMap *map,
189         UndoTypeForEachIDRefFn foreach_ID_ref_fn, void *user_data);
190
191 void BKE_undosys_print(UndoStack *ustack);
192
193 #endif  /* __BKE_UNDO_SYSTEM_H__ */