Fix #21028: operator redo creates hundreds of images when texture paint is on.
authorBrecht Van Lommel <brechtvanlommel@pandora.be>
Fri, 23 Jul 2010 14:46:31 +0000 (14:46 +0000)
committerBrecht Van Lommel <brechtvanlommel@pandora.be>
Fri, 23 Jul 2010 14:46:31 +0000 (14:46 +0000)
Now operator redo will look for an undo push with the same name in both the
paint/sculpt and global undo stack.

source/blender/editors/include/ED_sculpt.h
source/blender/editors/sculpt_paint/paint_image.c
source/blender/editors/sculpt_paint/paint_intern.h
source/blender/editors/sculpt_paint/paint_undo.c
source/blender/editors/space_view3d/view3d_draw.c
source/blender/editors/util/undo.c

index db2013fb411f3cadaf1d17cda06544e7fdca3627..506813ce626878c5f297d2e5de974865ae89b615 100644 (file)
@@ -49,7 +49,7 @@ void ED_keymap_paint(struct wmKeyConfig *keyconf);
 #define UNDO_PAINT_IMAGE       0
 #define UNDO_PAINT_MESH                1
 
-void ED_undo_paint_step(struct bContext *C, int type, int step);
+int ED_undo_paint_step(struct bContext *C, int type, int step, const char *name);
 void ED_undo_paint_free(void);
 
 #endif
index c1d1f709c5ec6ea1e7a25167c95a47fdaacc191a..4174662359f1e3bbcf612166243c9049d7e41aa5 100644 (file)
@@ -4699,7 +4699,7 @@ static int texture_paint_init(bContext *C, wmOperator *op)
        }
        
        settings->imapaint.flag |= IMAGEPAINT_DRAWING;
-       undo_paint_push_begin(UNDO_PAINT_IMAGE, "Image Paint",
+       undo_paint_push_begin(UNDO_PAINT_IMAGE, op->type->name,
                image_undo_restore, image_undo_free);
 
        /* create painter */
@@ -5440,7 +5440,7 @@ static int texture_paint_camera_project_exec(bContext *C, wmOperator *op)
 
        scene->toolsettings->imapaint.flag |= IMAGEPAINT_DRAWING;
 
-       undo_paint_push_begin(UNDO_PAINT_IMAGE, "Image Paint",
+       undo_paint_push_begin(UNDO_PAINT_IMAGE, op->type->name,
                image_undo_restore, image_undo_free);
 
        /* allocate and initialize spacial data structures */
index 0ae7c7fac19b99ed2194d9f3088d1289799cb7a6..3ed314095ef419f7d689a9e5d7e27d92da104a94 100644 (file)
@@ -121,7 +121,7 @@ typedef enum wmBrushStrokeMode {
 typedef void (*UndoRestoreCb)(struct bContext *C, struct ListBase *lb);
 typedef void (*UndoFreeCb)(struct ListBase *lb);
 
-void undo_paint_push_begin(int type, char *name, UndoRestoreCb restore, UndoFreeCb free);
+void undo_paint_push_begin(int type, const char *name, UndoRestoreCb restore, UndoFreeCb free);
 struct ListBase *undo_paint_push_get_list(int type);
 void undo_paint_push_count_alloc(int type, int size);
 void undo_paint_push_end(int type);
index 5da988f1ae1add2b94da20112d84c41844691773..c2f82b8e2e0f34df09f0f2d951088d2a8b396d0c 100644 (file)
@@ -76,7 +76,7 @@ static void undo_elem_free(UndoStack *stack, UndoElem *uel)
        }
 }
 
-static void undo_stack_push_begin(UndoStack *stack, char *name, UndoRestoreCb restore, UndoFreeCb free)
+static void undo_stack_push_begin(UndoStack *stack, const char *name, UndoRestoreCb restore, UndoFreeCb free)
 {
        UndoElem *uel;
        int nr;
@@ -145,27 +145,35 @@ static void undo_stack_push_end(UndoStack *stack)
        }
 }
 
-static void undo_stack_step(bContext *C, UndoStack *stack, int step)
+static int undo_stack_step(bContext *C, UndoStack *stack, int step, const char *name)
 {
        UndoElem *undo;
 
        if(step==1) {
                if(stack->current==NULL);
                else {
-                       if(G.f & G_DEBUG) printf("undo %s\n", stack->current->name);
-                       undo_restore(C, stack, stack->current);
-                       stack->current= stack->current->prev;
+                       if(!name || strcmp(stack->current->name, name) == 0) {
+                               if(G.f & G_DEBUG) printf("undo %s\n", stack->current->name);
+                               undo_restore(C, stack, stack->current);
+                               stack->current= stack->current->prev;
+                               return 1;
+                       }
                }
        }
        else if(step==-1) {
                if((stack->current!=NULL && stack->current->next==NULL) || stack->elems.first==NULL);
                else {
-                       undo= (stack->current && stack->current->next)? stack->current->next: stack->elems.first;
-                       undo_restore(C, stack, undo);
-                       stack->current= undo;
-                       if(G.f & G_DEBUG) printf("redo %s\n", undo->name);
+                       if(!name || strcmp(stack->current->name, name) == 0) {
+                               undo= (stack->current && stack->current->next)? stack->current->next: stack->elems.first;
+                               undo_restore(C, stack, undo);
+                               stack->current= undo;
+                               if(G.f & G_DEBUG) printf("redo %s\n", undo->name);
+                               return 1;
+                       }
                }
        }
+
+       return 0;
 }
 
 static void undo_stack_free(UndoStack *stack)
@@ -181,7 +189,7 @@ static void undo_stack_free(UndoStack *stack)
 
 /* Exported Functions */
 
-void undo_paint_push_begin(int type, char *name, UndoRestoreCb restore, UndoFreeCb free)
+void undo_paint_push_begin(int type, const char *name, UndoRestoreCb restore, UndoFreeCb free)
 {
        if(type == UNDO_PAINT_IMAGE)
                undo_stack_push_begin(&ImageUndoStack, name, restore, free);
@@ -219,12 +227,14 @@ void undo_paint_push_end(int type)
                undo_stack_push_end(&MeshUndoStack);
 }
 
-void ED_undo_paint_step(bContext *C, int type, int step)
+int ED_undo_paint_step(bContext *C, int type, int step, const char *name)
 {
        if(type == UNDO_PAINT_IMAGE)
-               undo_stack_step(C, &ImageUndoStack, step);
+               return undo_stack_step(C, &ImageUndoStack, step, name);
        else if(type == UNDO_PAINT_MESH)
-               undo_stack_step(C, &MeshUndoStack, step);
+               return undo_stack_step(C, &MeshUndoStack, step, name);
+       
+       return 0;
 }
 
 void ED_undo_paint_free(void)
index 86a12cd6221224415aab1bcedc6d73708ff055ba..a59a68f86cf335c11ca798d94c629149c347e703 100644 (file)
@@ -1063,7 +1063,7 @@ static void drawviewborder(Scene *scene, ARegion *ar, View3D *v3d)
 
 /* *********************** backdraw for selection *************** */
 
-void backdrawview3d(Scene *scene, ARegion *ar, View3D *v3d)
+static void backdrawview3d(Scene *scene, ARegion *ar, View3D *v3d)
 {
        RegionView3D *rv3d= ar->regiondata;
        struct Base *base = scene->basact;
index 636ce9dcec5044f0c2b3344a873f622468f6e2cf..1618ef88ba4848c706e243c627fb7a5f039c9ef9 100644 (file)
@@ -116,7 +116,9 @@ static int ed_undo_step(bContext *C, int step, const char *undoname)
                SpaceImage *sima= (SpaceImage *)sa->spacedata.first;
                
                if((obact && obact->mode & OB_MODE_TEXTURE_PAINT) || sima->flag & SI_DRAWTOOL) {
-                       ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step);
+                       if(!ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step, undoname) && undoname)
+                               if(U.uiflag & USER_GLOBALUNDO)
+                                       BKE_undo_name(C, undoname);
 
                        WM_event_add_notifier(C, NC_WINDOW, NULL);
                        return OPERATOR_FINISHED;
@@ -139,10 +141,14 @@ static int ed_undo_step(bContext *C, int step, const char *undoname)
        else {
                int do_glob_undo= 0;
                
-               if(obact && obact->mode & OB_MODE_TEXTURE_PAINT)
-                       ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step);
-               else if(obact && obact->mode & OB_MODE_SCULPT)
-                       ED_undo_paint_step(C, UNDO_PAINT_MESH, step);
+               if(obact && obact->mode & OB_MODE_TEXTURE_PAINT) {
+                       if(!ED_undo_paint_step(C, UNDO_PAINT_IMAGE, step, undoname) && undoname)
+                               do_glob_undo= 1;
+               }
+               else if(obact && obact->mode & OB_MODE_SCULPT) {
+                       if(!ED_undo_paint_step(C, UNDO_PAINT_MESH, step, undoname) && undoname)
+                               do_glob_undo= 1;
+               }
                else if(obact && obact->mode & OB_MODE_PARTICLE_EDIT) {
                        if(step==1)
                                PE_undo(CTX_data_scene(C));