diff options
author | Ton Roosendaal <ton@blender.org> | 2010-12-03 17:26:03 +0300 |
---|---|---|
committer | Ton Roosendaal <ton@blender.org> | 2010-12-03 17:26:03 +0300 |
commit | 52edaae9c5852a025d955e5063285795e87bfb38 (patch) | |
tree | 5898b3cdb8980e0293f8bc567a329181a28390f4 /source/blender/editors | |
parent | cd972535027a73ba70069051fe9038b6a8b5696a (diff) |
Bugfix #20565
Material Node shaders: displaying GLSL + rendering previews crashed.
Reason was non-safe threaded access to material nodes. Now, on a preview
render, a full copy of Material is being made.
Diffstat (limited to 'source/blender/editors')
-rw-r--r-- | source/blender/editors/render/render_preview.c | 26 |
1 files changed, 19 insertions, 7 deletions
diff --git a/source/blender/editors/render/render_preview.c b/source/blender/editors/render/render_preview.c index 5697154998b..af210f49553 100644 --- a/source/blender/editors/render/render_preview.c +++ b/source/blender/editors/render/render_preview.c @@ -148,6 +148,9 @@ typedef struct ShaderPreview { ID *parent; MTex *slot; + /* node materials need full copy during preview render, glsl uses it too */ + Material *matcopy; + int sizex, sizey; unsigned int *pr_rect; int pr_method; @@ -329,9 +332,9 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre sce->r.color_mgt_flag = scene->r.color_mgt_flag; /* exception: don't color manage texture previews or icons */ - if((sp && sp->pr_method==PR_ICON_RENDER) || id_type == ID_TE) + if((id && sp->pr_method==PR_ICON_RENDER) || id_type == ID_TE) sce->r.color_mgt_flag &= ~R_COLOR_MANAGEMENT; - if((sp && sp->pr_method==PR_ICON_RENDER) && id_type != ID_WO) + if((id && sp->pr_method==PR_ICON_RENDER) && id_type != ID_WO) sce->r.alphamode= R_ALPHAPREMUL; else sce->r.alphamode= R_ADDSKY; @@ -340,9 +343,14 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre strcpy(sce->r.engine, scene->r.engine); if(id_type==ID_MA) { - Material *mat= (Material *)id; + Material *mat= NULL; if(id) { + /* work on a copy */ + mat= copy_material((Material *)id); + sp->matcopy= mat; + BLI_remlink(&G.main->mat, mat); + init_render_material(mat, 0, NULL); /* call that retrieves mode_l */ end_render_material(mat); @@ -384,7 +392,7 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre } - if(sp && sp->pr_method==PR_ICON_RENDER) { + if(sp->pr_method==PR_ICON_RENDER) { if (mat->material_type == MA_TYPE_HALO) { sce->lay= 1<<MA_FLAT; } @@ -400,6 +408,10 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre } else { sce->r.mode &= ~(R_OSA|R_RAYTRACE|R_SSS); + + free_material(sp->matcopy); + MEM_freeN(sp->matcopy); + sp->matcopy= NULL; } for(base= sce->base.first; base; base= base->next) { @@ -428,7 +440,7 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre if(mat && mat->mtex[0]) { mat->mtex[0]->tex= tex; - if(sp && sp->slot) + if(tex && sp->slot) mat->mtex[0]->which_output = sp->slot->which_output; /* show alpha in this case */ @@ -444,7 +456,7 @@ static Scene *preview_prepare_scene(Scene *scene, ID *id, int id_type, ShaderPre } } - if(tex && tex->nodetree && sp && sp->pr_method==PR_NODE_RENDER) + if(tex && tex->nodetree && sp->pr_method==PR_NODE_RENDER) ntreeInitPreview(tex->nodetree, sp->sizex, sp->sizey); } else if(id_type==ID_LA) { @@ -987,7 +999,7 @@ static void shader_preview_render(ShaderPreview *sp, ID *id, int split, int firs } /* unassign the pointers, reset vars */ - preview_prepare_scene(sp->scene, NULL, GS(id->name), NULL); + preview_prepare_scene(sp->scene, NULL, GS(id->name), sp); } /* runs inside thread for material and icons */ |