130
127
/* undo during jobs are running can easily lead to freeing data using by jobs,
131
128
* or they can just lead to freezing job in some other cases */
132
if (WM_jobs_test(CTX_wm_manager(C), CTX_data_scene(C))) {
129
if (WM_jobs_test(CTX_wm_manager(C), CTX_data_scene(C), WM_JOB_TYPE_ANY)) {
133
130
return OPERATOR_CANCELLED;
138
135
return ED_undo_gpencil_step(C, step, undoname);
141
if (sa && sa->spacetype == SPACE_IMAGE) {
138
if (sa && (sa->spacetype == SPACE_IMAGE)) {
142
139
SpaceImage *sima = (SpaceImage *)sa->spacedata.first;
144
if ((obact && obact->mode & OB_MODE_TEXTURE_PAINT) || sima->flag & SI_DRAWTOOL) {
141
if ((obact && (obact->mode & OB_MODE_TEXTURE_PAINT)) || (sima->mode == SI_MODE_PAINT)) {
145
142
if (!ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step, undoname) && undoname)
146
143
if (U.uiflag & USER_GLOBALUNDO)
147
144
BKE_undo_name(C, undoname);
149
146
WM_event_add_notifier(C, NC_WINDOW, NULL);
150
147
return OPERATOR_FINISHED;
154
if (sa && sa->spacetype == SPACE_TEXT) {
151
if (sa && (sa->spacetype == SPACE_TEXT)) {
155
152
ED_text_undo_step(C, step);
157
154
else if (obedit) {
158
if (ELEM7(obedit->type, OB_MESH, OB_FONT, OB_CURVE, OB_SURF, OB_MBALL, OB_LATTICE, OB_ARMATURE)) {
155
if (OB_TYPE_SUPPORT_EDITMODE(obedit->type)) {
160
157
undo_editmode_name(C, undoname);
162
159
undo_editmode_step(C, step);
164
161
WM_event_add_notifier(C, NC_GEOM | ND_DATA, NULL);
168
int do_glob_undo = 0;
165
/* Note: we used to do a fall-through here where if the
166
* mode-specific undo system had no more steps to undo (or
167
* redo), the global undo would run.
169
* That was inconsistent with editmode, and also makes for
170
* unecessarily tricky interaction with the other undo
170
172
if (obact && obact->mode & OB_MODE_TEXTURE_PAINT) {
171
if (!ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step, undoname))
173
ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step, undoname);
174
175
else if (obact && obact->mode & OB_MODE_SCULPT) {
175
if (!ED_undo_paint_step(C, UNDO_PAINT_MESH, step, undoname))
176
ED_undo_paint_step(C, UNDO_PAINT_MESH, step, undoname);
178
178
else if (obact && obact->mode & OB_MODE_PARTICLE_EDIT) {
182
182
PE_redo(CTX_data_scene(C));
189
if (U.uiflag & USER_GLOBALUNDO) {
190
// note python defines not valid here anymore.
192
// XXX BPY_scripts_clear_pyobjects();
195
BKE_undo_name(C, undoname);
197
BKE_undo_step(C, step);
199
WM_event_add_notifier(C, NC_SCENE | ND_LAYER_CONTENT, CTX_data_scene(C));
184
else if (U.uiflag & USER_GLOBALUNDO) {
185
// note python defines not valid here anymore.
187
// XXX BPY_scripts_clear_pyobjects();
190
BKE_undo_name(C, undoname);
192
BKE_undo_step(C, step);
194
WM_event_add_notifier(C, NC_SCENE | ND_LAYER_CONTENT, CTX_data_scene(C));
238
231
if (sa && sa->spacetype == SPACE_IMAGE) {
239
232
SpaceImage *sima = (SpaceImage *)sa->spacedata.first;
241
if ((obact && obact->mode & OB_MODE_TEXTURE_PAINT) || sima->flag & SI_DRAWTOOL) {
234
if ((obact && (obact->mode & OB_MODE_TEXTURE_PAINT)) || (sima->mode == SI_MODE_PAINT)) {
246
if (sa && sa->spacetype == SPACE_TEXT) {
239
if (sa && (sa->spacetype == SPACE_TEXT)) {
249
242
else if (obedit) {
250
if (ELEM7(obedit->type, OB_MESH, OB_FONT, OB_CURVE, OB_SURF, OB_MBALL, OB_LATTICE, OB_ARMATURE)) {
243
if (OB_TYPE_SUPPORT_EDITMODE(obedit->type)) {
251
244
return undo_editmode_valid(undoname);
256
249
/* if below tests fail, global undo gets executed */
258
251
if (obact && obact->mode & OB_MODE_TEXTURE_PAINT) {
259
if (ED_undo_paint_valid(UNDO_PAINT_IMAGE, undoname) )
252
if (ED_undo_paint_valid(UNDO_PAINT_IMAGE, undoname))
262
255
else if (obact && obact->mode & OB_MODE_SCULPT) {
263
if (ED_undo_paint_valid(UNDO_PAINT_MESH, undoname) )
256
if (ED_undo_paint_valid(UNDO_PAINT_MESH, undoname))
266
259
else if (obact && obact->mode & OB_MODE_PARTICLE_EDIT) {
277
270
static int ed_undo_exec(bContext *C, wmOperator *UNUSED(op))
279
/* "last operator" should disappear, later we can tie ths with undo stack nicer */
272
/* "last operator" should disappear, later we can tie this with undo stack nicer */
280
273
WM_operator_stack_clear(CTX_wm_manager(C));
281
274
return ed_undo_step(C, 1, NULL);
284
277
static int ed_undo_push_exec(bContext *C, wmOperator *op)
286
char str[MAXUNDONAME];
279
char str[BKE_UNDO_STR_MAX];
287
280
RNA_string_get(op->ptr, "message", str);
288
281
ED_undo_push(C, str);
289
282
return OPERATOR_FINISHED;
322
315
ot->flag = OPTYPE_INTERNAL;
324
RNA_def_string(ot->srna, "message", "Add an undo step *function may be moved*", MAXUNDONAME, "Undo Message", "");
317
RNA_def_string(ot->srna, "message", "Add an undo step *function may be moved*", BKE_UNDO_STR_MAX, "Undo Message", "");
327
320
void ED_OT_redo(wmOperatorType *ot)
346
339
wmWindowManager *wm = CTX_wm_manager(C);
347
340
struct Scene *scene = CTX_data_scene(C);
342
/* keep in sync with logic in view3d_panel_operator_redo() */
349
343
ARegion *ar = CTX_wm_region(C);
350
ARegion *ar1 = BKE_area_find_region_type(CTX_wm_area(C), RGN_TYPE_WINDOW);
344
ARegion *ar1 = BKE_area_find_region_active_win(CTX_wm_area(C));
353
347
CTX_wm_region_set(C, ar1);
359
353
* (which copy their data), wont stop redo, see [#29579]],
361
355
* note, - WM_operator_check_ui_enabled() jobs test _must_ stay in sync with this */
362
(WM_jobs_test(wm, scene) == 0))
356
(WM_jobs_test(wm, scene, WM_JOB_TYPE_ANY) == 0))
424
420
/* find out which undo system */
426
if (ELEM7(obedit->type, OB_MESH, OB_FONT, OB_CURVE, OB_SURF, OB_MBALL, OB_LATTICE, OB_ARMATURE))
422
if (OB_TYPE_SUPPORT_EDITMODE(obedit->type)) {
427
423
return UNDOSYSTEM_EDITMODE;
430
427
Object *obact = CTX_data_active_object(C);
490
487
if (totitem > 0) {
491
488
uiPopupMenu *pup = uiPupMenuBegin(C, RNA_struct_ui_name(op->type->srna), ICON_NONE);
492
489
uiLayout *layout = uiPupMenuLayout(pup);
493
uiLayout *split = uiLayoutSplit(layout, 0, 0), *column = NULL;
490
uiLayout *split = uiLayoutSplit(layout, 0.0f, FALSE);
491
uiLayout *column = NULL;
496
494
for (c = 0, i = totitem - 1; i >= 0; i--, c++) {
497
495
if ( (c % 20) == 0)
498
column = uiLayoutColumn(split, 0);
496
column = uiLayoutColumn(split, FALSE);
499
497
if (item[i].identifier)
500
498
uiItemIntO(column, item[i].name, item[i].icon, op->type->idname, "item", item[i].value);