[#23095] If no camera is present, a render starts but does nothing, and we have no...
authorSergey Sharybin <sergey.vfx@gmail.com>
Wed, 3 Nov 2010 13:10:09 +0000 (13:10 +0000)
committerSergey Sharybin <sergey.vfx@gmail.com>
Wed, 3 Nov 2010 13:10:09 +0000 (13:10 +0000)
Improve camera checking and move it before starting render jobs

source/blender/editors/render/render_internal.c
source/blender/render/extern/include/RE_pipeline.h
source/blender/render/intern/source/pipeline.c

index 40aba913efe0736d4cba3c0aa0053e95163015f5..bf017856389f0c4f57256db7e1b4ed96bc59cba8 100644 (file)
@@ -637,6 +637,10 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event)
        if(WM_jobs_test(CTX_wm_manager(C), scene))
                return OPERATOR_CANCELLED;
 
+       if(!RE_is_rendering_allowed(scene, op->reports, render_error_reports)) {
+               return OPERATOR_CANCELLED;
+       }
+
        /* stop all running jobs, currently previews frustrate Render */
        WM_jobs_stop_all(CTX_wm_manager(C));
 
index 3b26b673c5da57099c39ce020f1f5c7c60abe2d1..696e52700cb952e20ab30feb6905ab54f4298d98 100644 (file)
@@ -300,5 +300,7 @@ void RE_engine_update_stats(RenderEngine *engine, char *stats, char *info);
 void RE_engines_init(void);
 void RE_engines_exit(void);
 
+int RE_is_rendering_allowed(struct Scene *scene, void *erh, void (*error)(void *handle, char *str));
+
 #endif /* RE_PIPELINE_H */
 
index 9f4f146e15fdb95aa82343ed96ae1967f4b338a1..0eecd9b9585d90fcf32c4087b57960d2d4915907 100644 (file)
@@ -448,7 +448,7 @@ static int passtype_from_name(char *str)
        return 0;
 }
 
-static void render_unique_exr_name(Render *re, char *str, int sample)
+static void scene_unique_exr_name(Scene *scene, char *str, int sample)
 {
        char di[FILE_MAX], name[FILE_MAXFILE+MAX_ID_NAME+100], fi[FILE_MAXFILE];
        
@@ -456,13 +456,18 @@ static void render_unique_exr_name(Render *re, char *str, int sample)
        BLI_splitdirstring(di, fi);
        
        if(sample==0)
-               sprintf(name, "%s_%s.exr", fi, re->scene->id.name+2);
+               sprintf(name, "%s_%s.exr", fi, scene->id.name+2);
        else
-               sprintf(name, "%s_%s%d.exr", fi, re->scene->id.name+2, sample);
+               sprintf(name, "%s_%s%d.exr", fi, scene->id.name+2, sample);
 
        BLI_make_file_string("/", str, btempdir, name);
 }
 
+static void render_unique_exr_name(Render *re, char *str, int sample)
+{
+       scene_unique_exr_name(re->scene, str, sample);
+}
+
 static void render_layer_add_pass(RenderResult *rr, RenderLayer *rl, int channels, int passtype)
 {
        char *typestr= get_pass_name(passtype, 0);
@@ -2588,61 +2593,112 @@ static void do_render_all_options(Render *re)
        }
 }
 
-static int is_rendering_allowed(Render *re)
+static int check_valid_camera(Scene *scene)
+{
+       int check_comp= 1;
+
+       if (scene->camera == NULL)
+               scene->camera= scene_find_camera(scene);
+
+       if(scene->r.scemode&R_DOSEQ) {
+               if(scene->ed) {
+                       Sequence *seq= scene->ed->seqbase.first;
+
+                       check_comp= 0;
+
+                       while(seq) {
+                               if(seq->type == SEQ_SCENE) {
+                                       if(!seq->scene_camera) {
+                                               if(!seq->scene->camera && !scene_find_camera(seq->scene)) {
+                                                       if(seq->scene == scene) {
+                                                               /* for current scene camera could be unneeded due to compisite nodes */
+                                                               check_comp= 1;
+                                                       } else {
+                                                               /* for other scenes camera is necessary */
+                                                               return 0;
+                                                       }
+                                               }
+                                       }
+                               }
+
+                               seq= seq->next;
+                       }
+               }
+       }
+
+       if(check_comp) { /* no sequencer or sequencer depends on compositor */
+               if(scene->r.scemode&R_DOCOMP && scene->use_nodes) {
+                       bNode *node= scene->nodetree->nodes.first;
+
+                       while(node) {
+                               if(node->type == CMP_NODE_R_LAYERS) {
+                                       Scene *sce= node->id ? (Scene*)node->id : scene;
+
+                                       if(!sce->camera && !scene_find_camera(sce)) {
+                                               /* all render layers nodes need camera */
+                                               return 0;
+                                       }
+                               }
+
+                               node= node->next;
+                       }
+               } else return scene->camera != NULL;
+       }
+
+       return 1;
+}
+
+int RE_is_rendering_allowed(Scene *scene, void *erh, void (*error)(void *handle, char *str))
 {
        SceneRenderLayer *srl;
        
        /* forbidden combinations */
-       if(re->r.mode & R_PANORAMA) {
-               if(re->r.mode & R_BORDER) {
-                       re->error(re->erh, "No border supported for Panorama");
+       if(scene->r.mode & R_PANORAMA) {
+               if(scene->r.mode & R_BORDER) {
+                       error(erh, "No border supported for Panorama");
                        return 0;
                }
-               if(re->r.mode & R_ORTHO) {
-                       re->error(re->erh, "No Ortho render possible for Panorama");
+               if(scene->r.mode & R_ORTHO) {
+                       error(erh, "No Ortho render possible for Panorama");
                        return 0;
                }
        }
        
-       if(re->r.mode & R_BORDER) {
-               if(re->r.border.xmax <= re->r.border.xmin || 
-                  re->r.border.ymax <= re->r.border.ymin) {
-                       re->error(re->erh, "No border area selected.");
+       if(scene->r.mode & R_BORDER) {
+               if(scene->r.border.xmax <= scene->r.border.xmin ||
+                  scene->r.border.ymax <= scene->r.border.ymin) {
+                       error(erh, "No border area selected.");
                        return 0;
                }
        }
        
-       if(re->r.scemode & (R_EXR_TILE_FILE|R_FULL_SAMPLE)) {
+       if(scene->r.scemode & (R_EXR_TILE_FILE|R_FULL_SAMPLE)) {
                char str[FILE_MAX];
                
-               render_unique_exr_name(re, str, 0);
+               scene_unique_exr_name(scene, str, 0);
                
                if (BLI_is_writable(str)==0) {
-                       re->error(re->erh, "Can not save render buffers, check the temp default path");
+                       error(erh, "Can not save render buffers, check the temp default path");
                        return 0;
                }
                
-               /* no osa + fullsample won't work... */
-               if(re->osa==0)
-                       re->r.scemode &= ~R_FULL_SAMPLE;
-               
                /* no fullsample and edge */
-               if((re->r.scemode & R_FULL_SAMPLE) && (re->r.mode & R_EDGE)) {
-                       re->error(re->erh, "Full Sample doesn't support Edge Enhance");
+               if((scene->r.scemode & R_FULL_SAMPLE) && (scene->r.mode & R_EDGE)) {
+                       error(erh, "Full Sample doesn't support Edge Enhance");
                        return 0;
                }
                
        }
        else
-               re->r.scemode &= ~R_FULL_SAMPLE;        /* clear to be sure */
+               scene->r.scemode &= ~R_FULL_SAMPLE;     /* clear to be sure */
        
-       if(re->r.scemode & R_DOCOMP) {
-               if(re->scene->use_nodes) {
-                       bNodeTree *ntree= re->scene->nodetree;
+       if(scene->r.scemode & R_DOCOMP) {
+               if(scene->use_nodes) {
+                       bNodeTree *ntree= scene->nodetree;
                        bNode *node;
                
                        if(ntree==NULL) {
-                               re->error(re->erh, "No Nodetree in Scene");
+                               error(erh, "No Nodetree in Scene");
                                return 0;
                        }
                        
@@ -2652,46 +2708,51 @@ static int is_rendering_allowed(Render *re)
                        
                        
                        if(node==NULL) {
-                               re->error(re->erh, "No Render Output Node in Scene");
+                               error(erh, "No Render Output Node in Scene");
                                return 0;
                        }
                }
        }
        
         /* check valid camera, without camera render is OK (compo, seq) */
-       if(re->scene->camera==NULL)
-               re->scene->camera= scene_find_camera(re->scene);
-       
-       if(!(re->r.scemode & (R_DOSEQ|R_DOCOMP))) {
-               if(re->scene->camera==NULL) {
-                       re->error(re->erh, "No camera");
-                       return 0;
-               }
+       if(!check_valid_camera(scene)) {
+               error(erh, "No camera");
+               return 0;
        }
        
        /* layer flag tests */
-       if(re->r.scemode & R_SINGLE_LAYER) {
-               srl= BLI_findlink(&re->scene->r.layers, re->r.actlay);
+       if(scene->r.scemode & R_SINGLE_LAYER) {
+               srl= BLI_findlink(&scene->r.layers, scene->r.actlay);
                /* force layer to be enabled */
                srl->layflag &= ~SCE_LAY_DISABLE;
        }
        
-       for(srl= re->scene->r.layers.first; srl; srl= srl->next)
+       for(srl= scene->r.layers.first; srl; srl= srl->next)
                if(!(srl->layflag & SCE_LAY_DISABLE))
                        break;
        if(srl==NULL) {
-               re->error(re->erh, "All RenderLayers are disabled");
+               error(erh, "All RenderLayers are disabled");
                return 0;
        }
        
        /* renderer */
-       if(!ELEM(re->r.renderer, R_INTERN, R_YAFRAY)) {
-               re->error(re->erh, "Unknown render engine set");
+       if(!ELEM(scene->r.renderer, R_INTERN, R_YAFRAY)) {
+               error(erh, "Unknown render engine set");
                return 0;
        }
+
        return 1;
 }
 
+static void validate_render_settings(Render *re)
+{
+       if(re->r.scemode & (R_EXR_TILE_FILE|R_FULL_SAMPLE)) {
+               /* no osa + fullsample won't work... */
+               if(re->r.osa==0)
+                       re->r.scemode &= ~R_FULL_SAMPLE;
+       } else re->r.scemode &= ~R_FULL_SAMPLE; /* clear to be sure */
+}
+
 static void update_physics_cache(Render *re, Scene *scene, int UNUSED(anim_init))
 {
        PTCacheBaker baker;
@@ -2768,10 +2829,9 @@ static int render_initialize_from_main(Render *re, Main *bmain, Scene *scene, Sc
        
        /* initstate makes new result, have to send changed tags around */
        ntreeCompositTagRender(re->scene);
-       
-       if(!is_rendering_allowed(re))
-               return 0;
-       
+
+       validate_render_settings(re);
+
        re->display_init(re->dih, re->result);
        re->display_clear(re->dch, re->result);