diff options
author | Campbell Barton <ideasman42@gmail.com> | 2010-05-23 14:47:19 +0400 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2010-05-23 14:47:19 +0400 |
commit | a9072177bafd5c7da629a1b6fdc1f9cee664a70f (patch) | |
tree | 53a79378f68104c22d19c545cab9fdfa253283b7 /source/blender | |
parent | d1d7c5fbd14d895cc3e9994aad6a4a1fe26701b3 (diff) |
opengl render option 'view_context',
When enabled the context's 3D view will be used for rendering.
When disabled a camera view with solid draw mode will be used.
(Needed for batch rendering out animation previews without having to worry about an existing 3D view, its local layer locking and draw type)
Diffstat (limited to 'source/blender')
-rw-r--r-- | source/blender/editors/render/render_opengl.c | 103 |
1 files changed, 74 insertions, 29 deletions
diff --git a/source/blender/editors/render/render_opengl.c b/source/blender/editors/render/render_opengl.c index aded83c0d16..410509f92cc 100644 --- a/source/blender/editors/render/render_opengl.c +++ b/source/blender/editors/render/render_opengl.c @@ -38,6 +38,7 @@ #include "BLI_dlrbTree.h" #include "DNA_scene_types.h" +#include "DNA_object_types.h" #include "BKE_blender.h" #include "BKE_object.h" @@ -62,6 +63,7 @@ #include "RE_pipeline.h" #include "IMB_imbuf_types.h" +#include "IMB_imbuf.h" #include "RNA_access.h" #include "RNA_define.h" @@ -94,6 +96,17 @@ typedef struct OGLRender { wmTimer *timer; /* use to check if running modal or not (invoke'd or exec'd)*/ } OGLRender; +/* added because v3d is not always valid */ +static unsigned int screen_opengl_layers(OGLRender *oglrender) +{ + if(oglrender->v3d) { + return oglrender->scene->lay | oglrender->v3d->lay; + } + else { + return oglrender->scene->lay; + } +} + static void screen_opengl_render_apply(OGLRender *oglrender) { Scene *scene= oglrender->scene; @@ -106,32 +119,46 @@ static void screen_opengl_render_apply(OGLRender *oglrender) float winmat[4][4]; int sizex= oglrender->sizex; int sizey= oglrender->sizey; + int view_context = (v3d != NULL); - /* bind */ - GPU_offscreen_bind(oglrender->ofs); + rr= RE_AcquireResultRead(oglrender->re); + + if(view_context) { + GPU_offscreen_bind(oglrender->ofs); /* bind */ - /* render 3d view */ - if(rv3d->persp==RV3D_CAMOB && v3d->camera) { - RE_GetCameraWindow(oglrender->re, v3d->camera, scene->r.cfra, winmat); - ED_view3d_draw_offscreen(scene, v3d, ar, sizex, sizey, NULL, winmat); + /* render 3d view */ + if(rv3d->persp==RV3D_CAMOB && v3d->camera) { + RE_GetCameraWindow(oglrender->re, v3d->camera, scene->r.cfra, winmat); + ED_view3d_draw_offscreen(scene, v3d, ar, sizex, sizey, NULL, winmat); + } + else { + ED_view3d_draw_offscreen(scene, v3d, ar, sizex, sizey, NULL, NULL); + } + + glReadPixels(0, 0, sizex, sizey, GL_RGBA, GL_FLOAT, rr->rectf); + + GPU_offscreen_unbind(oglrender->ofs); /* unbind */ } - else - ED_view3d_draw_offscreen(scene, v3d, ar, sizex, sizey, NULL, NULL); + else { + ImBuf *ibuf_view= ED_view3d_draw_offscreen_imbuf_simple(scene, oglrender->sizex, oglrender->sizey, OB_SOLID); + IMB_float_from_rect(ibuf_view); + + memcpy(rr->rectf, ibuf_view->rect_float, sizeof(float) * 4 * oglrender->sizex * oglrender->sizey); + + IMB_freeImBuf(ibuf_view); + } + + /* rr->rectf is now filled with image data */ - /* read in pixels & stamp */ - rr= RE_AcquireResultRead(oglrender->re); - glReadPixels(0, 0, sizex, sizey, GL_RGBA, GL_FLOAT, rr->rectf); if((scene->r.stamp & R_STAMP_ALL) && (scene->r.stamp & R_STAMP_DRAW)) BKE_stamp_buf(scene, NULL, rr->rectf, rr->rectx, rr->recty, 4); + RE_ReleaseResult(oglrender->re); /* update byte from float buffer */ ibuf= BKE_image_acquire_ibuf(oglrender->ima, &oglrender->iuser, &lock); if(ibuf) image_buffer_rect_update(NULL, rr, ibuf, NULL); BKE_image_release_ibuf(oglrender->ima, lock); - - /* unbind */ - GPU_offscreen_unbind(oglrender->ofs); } static int screen_opengl_render_init(bContext *C, wmOperator *op) @@ -142,14 +169,23 @@ static int screen_opengl_render_init(bContext *C, wmOperator *op) GPUOffScreen *ofs; OGLRender *oglrender; int sizex, sizey; + int view_context= RNA_boolean_get(op->ptr, "view_context"); /* ensure we have a 3d view */ - if(!ED_view3d_context_activate(C)) - return 0; + + if(!ED_view3d_context_activate(C)) { + RNA_boolean_set(op->ptr, "view_context", 0); + view_context = 0; + } /* only one render job at a time */ if(WM_jobs_test(CTX_wm_manager(C), scene)) return 0; + + if(!view_context && scene->camera==NULL) { + BKE_report(op->reports, RPT_ERROR, "Scene has no camera."); + return 0; + } /* stop all running jobs, currently previews frustrate Render */ WM_jobs_stop_all(CTX_wm_manager(C)); @@ -177,9 +213,11 @@ static int screen_opengl_render_init(bContext *C, wmOperator *op) oglrender->sizey= sizey; oglrender->scene= scene; - oglrender->v3d= CTX_wm_view3d(C); - oglrender->ar= CTX_wm_region(C); - oglrender->rv3d= CTX_wm_region_view3d(C); + if(view_context) { + oglrender->v3d= CTX_wm_view3d(C); + oglrender->ar= CTX_wm_region(C); + oglrender->rv3d= CTX_wm_region_view3d(C); + } /* create image and image user */ oglrender->ima= BKE_image_verify_viewer(IMA_TYPE_R_RESULT, "Render Result"); @@ -203,6 +241,7 @@ static int screen_opengl_render_init(bContext *C, wmOperator *op) static void screen_opengl_render_end(bContext *C, OGLRender *oglrender) { Scene *scene= oglrender->scene; + int view_context = (oglrender->v3d != NULL); if(oglrender->mh) { if(BKE_imtype_is_movie(scene->r.imtype)) @@ -211,7 +250,7 @@ static void screen_opengl_render_end(bContext *C, OGLRender *oglrender) if(oglrender->timer) { /* exec will not have a timer */ scene->r.cfra= oglrender->cfrao; - scene_update_for_newframe(scene, scene->lay|oglrender->v3d->lay); + scene_update_for_newframe(scene, screen_opengl_layers(oglrender)); WM_event_remove_timer(CTX_wm_manager(C), CTX_wm_window(C), oglrender->timer); } @@ -263,12 +302,12 @@ static int screen_opengl_render_anim_step(bContext *C, wmOperator *op) ImBuf *ibuf; void *lock; char name[FILE_MAXDIR+FILE_MAXFILE]; - unsigned int lay; int ok= 0; + int view_context = (oglrender->v3d != NULL); /* go to next frame */ while(CFRA<oglrender->nfra) { - lay = scene->lay | oglrender->v3d->lay; + unsigned int lay= screen_opengl_layers(oglrender); if(lay & 0xFF000000) lay &= 0xFF000000; @@ -276,14 +315,19 @@ static int screen_opengl_render_anim_step(bContext *C, wmOperator *op) scene_update_for_newframe(scene, lay); CFRA++; } - - scene_update_for_newframe(scene, scene->lay | oglrender->v3d->lay); - if(oglrender->rv3d->persp==RV3D_CAMOB && oglrender->v3d->camera && oglrender->v3d->scenelock) { - /* since scene_update_for_newframe() is used rather - * then ED_update_for_newframe() the camera needs to be set */ - if(scene_camera_switch_update(scene)) - oglrender->v3d->camera= scene->camera; + scene_update_for_newframe(scene, screen_opengl_layers(oglrender)); + + if(view_context) { + if(oglrender->rv3d->persp==RV3D_CAMOB && oglrender->v3d->camera && oglrender->v3d->scenelock) { + /* since scene_update_for_newframe() is used rather + * then ED_update_for_newframe() the camera needs to be set */ + if(scene_camera_switch_update(scene)) + oglrender->v3d->camera= scene->camera; + } + } + else { + scene_camera_switch_update(scene); } /* render into offscreen buffer */ @@ -445,6 +489,7 @@ void RENDER_OT_opengl(wmOperatorType *ot) ot->poll= ED_operator_screenactive; RNA_def_boolean(ot->srna, "animation", 0, "Animation", ""); + RNA_def_boolean(ot->srna, "view_context", 1, "View Context", "Use the current 3D view for rendering, else use scene settings."); } /* function for getting an opengl buffer from a View3D, used by sequencer */ |