diff options
Diffstat (limited to 'source/blender/blenloader/intern/writefile.c')
-rw-r--r-- | source/blender/blenloader/intern/writefile.c | 96 |
1 files changed, 66 insertions, 30 deletions
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c index 536376ac577..ac5366c26a3 100644 --- a/source/blender/blenloader/intern/writefile.c +++ b/source/blender/blenloader/intern/writefile.c @@ -197,7 +197,7 @@ static WriteData *writedata_new(int file) if (wd == NULL) return NULL; - wd->sdna= DNA_sdna_from_data(DNAstr, DNAlen, 0); + wd->sdna = DNA_sdna_from_data(DNAstr, DNAlen, 0); wd->file= file; @@ -511,7 +511,7 @@ static void write_fcurves(WriteData *wd, ListBase *fcurves) writestruct(wd, DATA, "FCurve", 1, fcu); /* curve data */ - if (fcu->bezt) + if (fcu->bezt) writestruct(wd, DATA, "BezTriple", fcu->totvert, fcu->bezt); if (fcu->fpt) writestruct(wd, DATA, "FPoint", fcu->totvert, fcu->fpt); @@ -720,18 +720,31 @@ static void write_nodetree(WriteData *wd, bNodeTree *ntree) write_node_socket(wd, sock); for (sock= node->outputs.first; sock; sock= sock->next) write_node_socket(wd, sock); - + + for (link = node->internal_links.first; link; link = link->next) + writestruct(wd, DATA, "bNodeLink", 1, link); if (node->storage) { /* could be handlerized at some point, now only 1 exception still */ if (ntree->type==NTREE_SHADER && (node->type==SH_NODE_CURVE_VEC || node->type==SH_NODE_CURVE_RGB)) write_curvemapping(wd, node->storage); + else if (ntree->type==NTREE_SHADER && node->type==SH_NODE_SCRIPT) { + NodeShaderScript *nss = (NodeShaderScript *)node->storage; + if (nss->bytecode) + writedata(wd, DATA, strlen(nss->bytecode)+1, nss->bytecode); + /* Write ID Properties -- and copy this comment EXACTLY for easy finding + * of library blocks that implement this.*/ + if (nss->prop) + IDP_WriteProperty(nss->prop, wd); + writestruct(wd, DATA, node->typeinfo->storagename, 1, node->storage); + } else if (ntree->type==NTREE_COMPOSIT && ELEM4(node->type, CMP_NODE_TIME, CMP_NODE_CURVE_VEC, CMP_NODE_CURVE_RGB, CMP_NODE_HUECORRECT)) write_curvemapping(wd, node->storage); else if (ntree->type==NTREE_TEXTURE && (node->type==TEX_NODE_CURVE_RGB || node->type==TEX_NODE_CURVE_TIME) ) write_curvemapping(wd, node->storage); - else if (ntree->type==NTREE_COMPOSIT && node->type==CMP_NODE_MOVIEDISTORTION) - /* pass */; + else if (ntree->type==NTREE_COMPOSIT && node->type==CMP_NODE_MOVIEDISTORTION) { + /* pass */ + } else writestruct(wd, DATA, node->typeinfo->storagename, 1, node->storage); } @@ -776,13 +789,16 @@ typedef struct RenderInfo { char scene_name[MAX_ID_NAME - 2]; } RenderInfo; -static void write_renderinfo(WriteData *wd, Main *mainvar) /* for renderdeamon */ +/* was for historic render-deamon feature, + * now write because it can be easily extracted without + * reading the whole blend file */ +static void write_renderinfo(WriteData *wd, Main *mainvar) { bScreen *curscreen; Scene *sce; RenderInfo data; - /* XXX in future, handle multiple windows with multiple screnes? */ + /* XXX in future, handle multiple windows with multiple screens? */ current_screen_compat(mainvar, &curscreen); for (sce= mainvar->scene.first; sce; sce= sce->id.next) { @@ -884,7 +900,7 @@ static const char *ptcache_data_struct[] = { "", // BPHYS_DATA_ROTATION "", // BPHYS_DATA_AVELOCITY / BPHYS_DATA_XCONST */ "", // BPHYS_DATA_SIZE: - "", // BPHYS_DATA_TIMES: + "", // BPHYS_DATA_TIMES: "BoidData" // case BPHYS_DATA_BOIDS: }; static const char *ptcache_extra_struct[] = { @@ -1237,7 +1253,7 @@ static void write_constraints(WriteData *wd, ListBase *conlist) break; case CONSTRAINT_TYPE_SPLINEIK: { - bSplineIKConstraint *data= (bSplineIKConstraint*)con->data; + bSplineIKConstraint *data = (bSplineIKConstraint *)con->data; /* write points array */ writedata(wd, DATA, sizeof(float)*(data->numpoints), data->points); @@ -1325,7 +1341,7 @@ static void write_modifiers(WriteData *wd, ListBase *modbase) writestruct(wd, DATA, "ClothCollSettings", 1, clmd->coll_parms); writestruct(wd, DATA, "EffectorWeights", 1, clmd->sim_parms->effector_weights); write_pointcaches(wd, &clmd->ptcaches); - } + } else if (md->type==eModifierType_Smoke) { SmokeModifierData *smd = (SmokeModifierData*) md; @@ -1355,7 +1371,7 @@ static void write_modifiers(WriteData *wd, ListBase *modbase) writestruct(wd, DATA, "SmokeFlowSettings", 1, smd->flow); else if (smd->type & MOD_SMOKE_TYPE_COLL) writestruct(wd, DATA, "SmokeCollSettings", 1, smd->coll); - } + } else if (md->type==eModifierType_Fluidsim) { FluidsimModifierData *fluidmd = (FluidsimModifierData*) md; @@ -1383,7 +1399,7 @@ static void write_modifiers(WriteData *wd, ListBase *modbase) writestruct(wd, DATA, "ColorBand", 1, pmd->brush->paint_ramp); writestruct(wd, DATA, "ColorBand", 1, pmd->brush->vel_ramp); } - } + } else if (md->type==eModifierType_Collision) { #if 0 @@ -1603,7 +1619,7 @@ static void write_curves(WriteData *wd, ListBase *idbase) if (cu->vfont) { writedata(wd, DATA, amount_of_chars(cu->str)+1, cu->str); writestruct(wd, DATA, "CharInfo", cu->len+1, cu->strinfo); - writestruct(wd, DATA, "TextBox", cu->totbox, cu->tb); + writestruct(wd, DATA, "TextBox", cu->totbox, cu->tb); } else { /* is also the order of reading */ @@ -1725,9 +1741,10 @@ static void write_customdata(WriteData *wd, ID *id, int count, CustomData *data, writestruct(wd, DATA, structname, datasize, layer->data); } - else + else { printf("%s error: layer '%s':%d - can't be written to file\n", __func__, structname, layer->type); + } } } @@ -1759,6 +1776,9 @@ static void write_meshs(WriteData *wd, ListBase *idbase) backup_mesh.totface = mesh->totface; mesh->totface = 0; /* -- */ + backup_mesh.fdata = mesh->fdata; + memset(&mesh->fdata, 0, sizeof(mesh->fdata)); + /* -- */ #endif /* USE_BMESH_SAVE_WITHOUT_MFACE */ writestruct(wd, ID_ME, "Mesh", 1, mesh); @@ -1782,6 +1802,8 @@ static void write_meshs(WriteData *wd, ListBase *idbase) mesh->mface = backup_mesh.mface; /* -- */ mesh->totface = backup_mesh.totface; + /* -- */ + mesh->fdata = backup_mesh.fdata; #endif /* USE_BMESH_SAVE_WITHOUT_MFACE */ } @@ -1808,13 +1830,13 @@ static void write_meshs(WriteData *wd, ListBase *idbase) mesh->totloop = 0; /* -- */ backup_mesh.fdata = mesh->fdata; - memset(&mesh->fdata, 0, sizeof(CustomData)); + CustomData_reset(&mesh->fdata); /* -- */ backup_mesh.pdata = mesh->pdata; - memset(&mesh->pdata, 0, sizeof(CustomData)); + CustomData_reset(&mesh->pdata); /* -- */ backup_mesh.ldata = mesh->ldata; - memset(&mesh->ldata, 0, sizeof(CustomData)); + CustomData_reset(&mesh->ldata); /* -- */ backup_mesh.edit_btmesh = mesh->edit_btmesh; mesh->edit_btmesh = NULL; @@ -2021,7 +2043,7 @@ static void write_materials(WriteData *wd, ListBase *idbase) write_nodetree(wd, ma->nodetree); } - write_previews(wd, ma->preview); + write_previews(wd, ma->preview); } ma= ma->id.next; } @@ -2077,7 +2099,7 @@ static void write_lamps(WriteData *wd, ListBase *idbase) } if (la->curfalloff) - write_curvemapping(wd, la->curfalloff); + write_curvemapping(wd, la->curfalloff); /* nodetree is integral part of lamps, no libdata */ if (la->nodetree) { @@ -2300,7 +2322,7 @@ static void write_gpencils(WriteData *wd, ListBase *lb) /* write strokes */ for (gps= gpf->strokes.first; gps; gps= gps->next) { writestruct(wd, DATA, "bGPDstroke", 1, gps); - writestruct(wd, DATA, "bGPDspoint", gps->totpoints, gps->points); + writestruct(wd, DATA, "bGPDspoint", gps->totpoints, gps->points); } } } @@ -2536,7 +2558,7 @@ static void write_bone(WriteData *wd, Bone *bone) Bone* cbone; // PATCH for upward compatibility after 2.37+ armature recode - bone->size[0]= bone->size[1]= bone->size[2]= 1.0f; + bone->size[0] = bone->size[1] = bone->size[2] = 1.0f; // Write this bone writestruct(wd, DATA, "Bone", 1, bone); @@ -2868,7 +2890,7 @@ static void write_global(WriteData *wd, int fileflags, Main *mainvar) fg.winpos= G.winpos; /* prevent to save this, is not good convention, and feature with concerns... */ - fg.fileflags= (fileflags & ~(G_FILE_NO_UI|G_FILE_RELATIVE_REMAP|G_FILE_MESH_COMPAT)); + fg.fileflags= (fileflags & ~G_FILE_FLAGS_RUNTIME); fg.globalf= G.f; BLI_strncpy(fg.filename, mainvar->name, sizeof(fg.filename)); @@ -2995,7 +3017,7 @@ static int do_history(const char *name, ReportList *reports) if (BLI_rename(tempname1, tempname2)) { BKE_report(reports, RPT_ERROR, "Unable to make version backup"); return 1; - } + } hisnr--; } @@ -3017,15 +3039,24 @@ int BLO_write_file(Main *mainvar, const char *filepath, int write_flags, ReportL char tempname[FILE_MAX+1]; int file, err, write_user_block; + /* path backup/restore */ + void *path_list_backup = NULL; + const int path_list_flag = (BLI_BPATH_TRAVERSE_SKIP_LIBRARY | BLI_BPATH_TRAVERSE_SKIP_MULTIFILE); + /* open temporary file, so we preserve the original in case we crash */ BLI_snprintf(tempname, sizeof(tempname), "%s@", filepath); file = BLI_open(tempname, O_BINARY+O_WRONLY+O_CREAT+O_TRUNC, 0666); if (file == -1) { - BKE_reportf(reports, RPT_ERROR, "Can't open file %s for writing: %s.", tempname, strerror(errno)); + BKE_reportf(reports, RPT_ERROR, "Cannot open file %s for writing: %s", tempname, strerror(errno)); return 0; } + /* check if we need to backup and restore paths */ + if (UNLIKELY((write_flags & G_FILE_RELATIVE_REMAP) && (G_FILE_SAVE_COPY & write_flags))) { + path_list_backup = BLI_bpath_list_backup(mainvar, path_list_flag); + } + /* remapping of relative paths to new file location */ if (write_flags & G_FILE_RELATIVE_REMAP) { char dir1[FILE_MAX]; @@ -3061,6 +3092,11 @@ int BLO_write_file(Main *mainvar, const char *filepath, int write_flags, ReportL err= write_file_handle(mainvar, file, NULL, NULL, write_user_block, write_flags, thumb); close(file); + if (UNLIKELY(path_list_backup)) { + BLI_bpath_list_restore(mainvar, path_list_flag, path_list_backup); + BLI_bpath_list_free(path_list_backup); + } + if (err) { BKE_report(reports, RPT_ERROR, strerror(errno)); remove(tempname); @@ -3070,10 +3106,10 @@ int BLO_write_file(Main *mainvar, const char *filepath, int write_flags, ReportL /* file save to temporary file was successful */ /* now do reverse file history (move .blend1 -> .blend2, .blend -> .blend1) */ - if (write_flags & G_FILE_HISTORY) { + if (write_flags & G_FILE_HISTORY) { int err_hist = do_history(filepath, reports); if (err_hist) { - BKE_report(reports, RPT_ERROR, "Version backup failed. File saved with @"); + BKE_report(reports, RPT_ERROR, "Version backup failed (file saved with @)"); return 0; } } @@ -3090,23 +3126,23 @@ int BLO_write_file(Main *mainvar, const char *filepath, int write_flags, ReportL if (0==ret) { /* now rename to real file name, and delete temp @ file too */ if (BLI_rename(gzname, filepath) != 0) { - BKE_report(reports, RPT_ERROR, "Can't change old file. File saved with @."); + BKE_report(reports, RPT_ERROR, "Cannot change old file (file saved with @)"); return 0; } BLI_delete(tempname, 0, 0); } else if (-1==ret) { - BKE_report(reports, RPT_ERROR, "Failed opening .gz file."); + BKE_report(reports, RPT_ERROR, "Failed opening .gz file"); return 0; } else if (-2==ret) { - BKE_report(reports, RPT_ERROR, "Failed opening .blend file for compression."); + BKE_report(reports, RPT_ERROR, "Failed opening .blend file for compression"); return 0; } } else if (BLI_rename(tempname, filepath) != 0) { - BKE_report(reports, RPT_ERROR, "Can't change old file. File saved with @"); + BKE_report(reports, RPT_ERROR, "Cannot change old file (file saved with @)"); return 0; } |