fixes for auto script execution, changing the user preference also updates the global...
[blender.git] / source / blender / blenkernel / intern / blender.c
index d3d21018c1ca7e9fc61474f7b8605bb7bb6618ad..171b48af974ae99c57aa2b81f4513cb00f8d72fb 100644 (file)
@@ -18,7 +18,7 @@
  *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software Foundation,
- * Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
  *
  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
  * All rights reserved.
@@ -74,6 +74,7 @@
 #include "BKE_displist.h"
 #include "BKE_font.h"
 #include "BKE_global.h"
+#include "BKE_idprop.h"
 #include "BKE_library.h"
 #include "BKE_ipo.h"
 #include "BKE_main.h"
@@ -82,7 +83,7 @@
 #include "BKE_report.h"
 #include "BKE_scene.h"
 #include "BKE_screen.h"
-#include "BKE_sequence.h"
+#include "BKE_sequencer.h"
 #include "BKE_sound.h"
 
 #include "BLI_editVert.h"
@@ -93,6 +94,8 @@
 
 #include "BKE_utildefines.h" // O_BINARY FALSE
 
+#include "WM_api.h" // XXXXX BAD, very BAD dependency (bad level call) - remove asap, elubie
+
 Global G;
 UserDef U;
 ListBase WMlist= {NULL, NULL};
@@ -100,84 +103,12 @@ short ENDIAN_ORDER;
 
 char versionstr[48]= "";
 
-/* ************************************************ */
-/* pushpop facility: to store data temporally, FIFO! */
-
-ListBase ppmain={0, 0};
-
-typedef struct PushPop {
-       struct PushPop *next, *prev;
-       void *data;
-       int len;
-} PushPop;
-
-void pushdata(void *data, int len)
-{
-       PushPop *pp;
-       
-       pp= MEM_mallocN(sizeof(PushPop), "pushpop");
-       BLI_addtail(&ppmain, pp);
-       pp->data= MEM_mallocN(len, "pushpop");
-       pp->len= len;
-       memcpy(pp->data, data, len);
-}
-
-void popfirst(void *data)
-{
-       PushPop *pp;
-       
-       pp= ppmain.first;
-       if(pp) {
-               memcpy(data, pp->data, pp->len);
-               BLI_remlink(&ppmain, pp);
-               MEM_freeN(pp->data);
-               MEM_freeN(pp);
-       }
-       else printf("error in popfirst\n");
-}
-
-void poplast(void *data)
-{
-       PushPop *pp;
-       
-       pp= ppmain.last;
-       if(pp) {
-               memcpy(data, pp->data, pp->len);
-               BLI_remlink(&ppmain, pp);
-               MEM_freeN(pp->data);
-               MEM_freeN(pp);
-       }
-       else printf("error in poplast\n");
-}
-
-void free_pushpop()
-{
-       PushPop *pp;
-
-       pp= ppmain.first;
-       while(pp) {
-               BLI_remlink(&ppmain, pp);
-               MEM_freeN(pp->data);
-               MEM_freeN(pp);
-       }       
-}
-
-void pushpop_test()
-{
-       if(ppmain.first) printf("pushpop not empty\n");
-       free_pushpop();
-}
-
-
-
 /* ********** free ********** */
 
 /* only to be called on exit blender */
 void free_blender(void)
 {
        /* samples are in a global list..., also sets G.main->sound->sample NULL */
-       sound_free_all_samples();
-       
        free_main(G.main);
        G.main= NULL;
 
@@ -227,8 +158,6 @@ static void clear_global(void)
 //     free_vertexpaint();
 
        G.main= NULL;
-       
-       G.f &= ~(G_WEIGHTPAINT + G_VERTEXPAINT + G_FACESELECT + G_PARTICLEEDIT);
 }
 
 /* make sure path names are correct for OS */
@@ -279,15 +208,17 @@ static void clean_paths(Main *main)
 
 static void setup_app_data(bContext *C, BlendFileData *bfd, char *filename) 
 {
-       Object *ob;
        bScreen *curscreen= NULL;
        Scene *curscene= NULL;
+       int recover;
        char mode;
-       
+
        /* 'u' = undo save, 'n' = no UI load */
        if(bfd->main->screen.first==NULL) mode= 'u';
        else if(G.fileflags & G_FILE_NO_UI) mode= 'n';
        else mode= 0;
+
+       recover= (G.fileflags & G_FILE_RECOVER);
        
        clean_paths(bfd->main);
        
@@ -330,9 +261,6 @@ static void setup_app_data(bContext *C, BlendFileData *bfd, char *filename)
                MEM_freeN(bfd->user);
        }
        
-       /* samples is a global list... */
-       sound_free_all_samples();
-       
        /* case G_FILE_NO_UI or no screens in file */
        if(mode) {
                /* leave entire context further unaltered? */
@@ -363,8 +291,6 @@ static void setup_app_data(bContext *C, BlendFileData *bfd, char *filename)
        if (G.f & G_SWAP_EXCHANGE) bfd->globalf |= G_SWAP_EXCHANGE;
        else bfd->globalf &= ~G_SWAP_EXCHANGE;
 
-       if ((U.flag & USER_DONT_DOSCRIPTLINKS)) bfd->globalf &= ~G_DOSCRIPTLINKS;
-
        G.f= bfd->globalf;
 
        if (!G.background) {
@@ -375,26 +301,21 @@ static void setup_app_data(bContext *C, BlendFileData *bfd, char *filename)
        if(G.main->versionfile < 250)
                do_versions_ipos_to_animato(G.main); // XXX fixme... complicated versionpatching
        
-       /* baseflags, groups, make depsgraph, etc */
-       set_scene_bg(CTX_data_scene(C));
-
-       /* last stage of do_versions actually, that sets recalc flags for recalc poses */
-       for(ob= G.main->object.first; ob; ob= ob->id.next) {
-               if(ob->type==OB_ARMATURE)
-                       if(ob->recalc) object_handle_update(CTX_data_scene(C), ob);
-       }
-       
-       /* now tag update flags, to ensure deformers get calculated on redraw */
-       DAG_scene_update_flags(CTX_data_scene(C), CTX_data_scene(C)->lay);
+       /* in case of autosave or quit.blend, use original filename instead
+        * use relbase_valid to make sure the file is saved, else we get <memory2> in the filename */
+       if(recover && bfd->filename[0] && G.relbase_valid)
+               filename= bfd->filename;
        
-       if (G.f & G_DOSCRIPTLINKS) {
-               /* there's an onload scriptlink to execute in screenmain */
-// XXX         mainqenter(ONLOAD_SCRIPT, 1);
-       }
-       if (G.sce != filename) /* these are the same at times, should never copy to the same location */
-               strcpy(G.sce, filename);
+       /* these are the same at times, should never copy to the same location */
+       if(G.sce != filename)
+               BLI_strncpy(G.sce, filename, FILE_MAX);
        
        BLI_strncpy(G.main->name, filename, FILE_MAX); /* is guaranteed current file */
+
+       /* baseflags, groups, make depsgraph, etc */
+       set_scene_bg(CTX_data_scene(C));
+
+       DAG_on_load_update();
        
        MEM_freeN(bfd);
 }
@@ -415,11 +336,27 @@ static int handle_subversion_warning(Main *main)
 
 void BKE_userdef_free(void)
 {
+       wmKeyMap *km;
+       wmKeyMapItem *kmi;
+
+       for(km=U.keymaps.first; km; km=km->next) {
+               for(kmi=km->items.first; kmi; kmi=kmi->next) {
+                       if(kmi->properties) {
+                               IDP_FreeProperty(kmi->properties);
+                               MEM_freeN(kmi->properties);
+                       }
+                       if(kmi->ptr)
+                               MEM_freeN(kmi->ptr);
+               }
+
+               BLI_freelistN(&km->items);
+       }
        
        BLI_freelistN(&U.uistyles);
        BLI_freelistN(&U.uifonts);
        BLI_freelistN(&U.themes);
-       
+       BLI_freelistN(&U.keymaps);
+       BLI_freelistN(&U.addons);
 }
 
 /* returns:
@@ -433,6 +370,9 @@ int BKE_read_file(bContext *C, char *dir, void *unused, ReportList *reports)
        BlendFileData *bfd;
        int retval= 1;
 
+       if(strstr(dir, ".B25.blend")==0) /* dont print user-pref loading */
+               printf("read blend: %s\n", dir);
+
        bfd= BLO_read_from_file(dir, reports);
        if (bfd) {
                if(bfd->user) retval= 2;
@@ -479,6 +419,7 @@ int BKE_read_file_from_memfile(bContext *C, MemFile *memfile, ReportList *report
        return (bfd?1:0);
 }
 
+
 /* *****************  testing for break ************* */
 
 static void (*blender_test_break_cb)(void)= NULL;
@@ -522,6 +463,9 @@ static int read_undosave(bContext *C, UndoElem *uel)
        char scestr[FILE_MAXDIR+FILE_MAXFILE];
        int success=0, fileflags;
        
+       /* This is needed so undoing/redoing doesnt crash with threaded previews going */
+       WM_jobs_stop_all(CTX_wm_manager(C));
+       
        strcpy(scestr, G.sce);  /* temporal store */
        fileflags= G.fileflags;
        G.fileflags |= G_FILE_NO_UI;
@@ -635,8 +579,7 @@ void BKE_write_undo(bContext *C, char *name)
        }
 }
 
-/* 1= an undo, -1 is a redo. we have to make sure 'curundo' remains at current situation
- * Note, ALWAYS call sound_initialize_sounds after BKE_undo_step() */
+/* 1= an undo, -1 is a redo. we have to make sure 'curundo' remains at current situation */
 void BKE_undo_step(bContext *C, int step)
 {
        
@@ -692,6 +635,22 @@ void BKE_undo_number(bContext *C, int nr)
        BKE_undo_step(C, 0);
 }
 
+/* go back to the last occurance of name in stack */
+void BKE_undo_name(bContext *C, const char *name)
+{
+       UndoElem *uel;
+       
+       for(uel= undobase.last; uel; uel= uel->prev) {
+               if(strcmp(name, uel->name)==0)
+                       break;
+       }
+       if(uel && uel->prev) {
+               curundo= uel->prev;
+               BKE_undo_step(C, 0);
+       }
+}
+
+
 char *BKE_undo_menu_string(void)
 {
        UndoElem *uel;
@@ -750,3 +709,20 @@ void BKE_undo_save_quit(void)
        else printf("Saved session recovery to %s\n", str);
 }
 
+/* sets curscene */
+Main *BKE_undo_get_main(Scene **scene)
+{
+       Main *mainp= NULL;
+       BlendFileData *bfd= BLO_read_from_memfile(G.main, G.sce, &curundo->memfile, NULL);
+       
+       if(bfd) {
+               mainp= bfd->main;
+               if(scene)
+                       *scene= bfd->curscene;
+               
+               MEM_freeN(bfd);
+       }
+       
+       return mainp;
+}
+