RenderEngine api: support for viewport rendering, details here:

http://wiki.blender.org/index.php/Dev:2.6/Source/Render/RenderEngineAPI

* This adds a Rendered draw type in the 3D view, only available when
  the render engine implements the view_draw callback.
* 3D view now stores a pointer to a RenderEngine.

* view_draw() callback will do OpenGL drawing instead of the viewport.
* view_update() callback is called after depsgraph updates.
This commit is contained in:
Brecht Van Lommel 2011-11-02 18:20:53 +00:00
parent a59f7e02f8
commit 97a0ae3e1b
16 changed files with 363 additions and 32 deletions

@ -140,6 +140,8 @@
#include "BLO_readfile.h" #include "BLO_readfile.h"
#include "BLO_undofile.h" #include "BLO_undofile.h"
#include "RE_engine.h"
#include "readfile.h" #include "readfile.h"
#include "PIL_time.h" #include "PIL_time.h"
@ -5089,6 +5091,7 @@ void lib_link_screen_restore(Main *newmain, bScreen *curscreen, Scene *curscene)
if(sl->spacetype==SPACE_VIEW3D) { if(sl->spacetype==SPACE_VIEW3D) {
View3D *v3d= (View3D*) sl; View3D *v3d= (View3D*) sl;
BGpic *bgpic; BGpic *bgpic;
ARegion *ar;
if(v3d->scenelock) if(v3d->scenelock)
v3d->camera= NULL; /* always get from scene */ v3d->camera= NULL; /* always get from scene */
@ -5124,6 +5127,15 @@ void lib_link_screen_restore(Main *newmain, bScreen *curscreen, Scene *curscene)
/* not very nice, but could help */ /* not very nice, but could help */
if((v3d->layact & v3d->lay)==0) v3d->layact= v3d->lay; if((v3d->layact & v3d->lay)==0) v3d->layact= v3d->lay;
/* free render engines for now */
for(ar= sa->regionbase.first; ar; ar= ar->next) {
RegionView3D *rv3d= ar->regiondata;
if(rv3d && rv3d->render_engine) {
RE_engine_free(rv3d->render_engine);
rv3d->render_engine= NULL;
}
}
} }
else if(sl->spacetype==SPACE_IPO) { else if(sl->spacetype==SPACE_IPO) {
SpaceIpo *sipo= (SpaceIpo *)sl; SpaceIpo *sipo= (SpaceIpo *)sl;
@ -5262,6 +5274,7 @@ static void direct_link_region(FileData *fd, ARegion *ar, int spacetype)
rv3d->depths= NULL; rv3d->depths= NULL;
rv3d->ri= NULL; rv3d->ri= NULL;
rv3d->render_engine= NULL;
rv3d->sms= NULL; rv3d->sms= NULL;
rv3d->smooth_timer= NULL; rv3d->smooth_timer= NULL;
} }
@ -5403,6 +5416,10 @@ static void direct_link_screen(FileData *fd, bScreen *sc)
v3d->afterdraw_xray.first= v3d->afterdraw_xray.last= NULL; v3d->afterdraw_xray.first= v3d->afterdraw_xray.last= NULL;
v3d->afterdraw_xraytransp.first= v3d->afterdraw_xraytransp.last= NULL; v3d->afterdraw_xraytransp.first= v3d->afterdraw_xraytransp.last= NULL;
v3d->properties_storage= NULL; v3d->properties_storage= NULL;
/* render can be quite heavy, set to wire on load */
if(v3d->drawtype == OB_RENDER)
v3d->drawtype = OB_WIRE;
view3d_split_250(v3d, &sl->regionbase); view3d_split_250(v3d, &sl->regionbase);
} }
@ -10696,7 +10713,7 @@ static void do_versions(FileData *fd, Library *lib, Main *main)
Object *ob=main->object.first; Object *ob=main->object.first;
while (ob) { while (ob) {
/* shaded mode disabled for now */ /* shaded mode disabled for now */
if (ob->dt == OB_SHADED) ob->dt = OB_TEXTURE; if (ob->dt == OB_MATERIAL) ob->dt = OB_TEXTURE;
ob=ob->id.next; ob=ob->id.next;
} }
} }
@ -10711,7 +10728,7 @@ static void do_versions(FileData *fd, Library *lib, Main *main)
for(sl= sa->spacedata.first; sl; sl= sl->next) { for(sl= sa->spacedata.first; sl; sl= sl->next) {
if(sl->spacetype==SPACE_VIEW3D) { if(sl->spacetype==SPACE_VIEW3D) {
View3D *v3d = (View3D *)sl; View3D *v3d = (View3D *)sl;
if (v3d->drawtype == OB_SHADED) v3d->drawtype = OB_SOLID; if (v3d->drawtype == OB_MATERIAL) v3d->drawtype = OB_SOLID;
} }
} }
} }

@ -44,6 +44,8 @@ void ED_operatortypes_render(void);
/* render_shading.c */ /* render_shading.c */
void ED_render_id_flush_update(struct Main *bmain, struct ID *id); void ED_render_id_flush_update(struct Main *bmain, struct ID *id);
void ED_render_engine_changed(struct Main *bmain);
void ED_render_engine_update_tagged(struct bContext *C, struct Main *bmain);
/* render_preview.c */ /* render_preview.c */

@ -56,11 +56,110 @@
#include "GPU_material.h" #include "GPU_material.h"
#include "RE_engine.h"
#include "ED_node.h" #include "ED_node.h"
#include "ED_render.h" #include "ED_render.h"
#include "render_intern.h" // own include #include "render_intern.h" // own include
/***************************** Render Engines ********************************/
void ED_render_engine_update_tagged(bContext *C, Main *bmain)
{
/* viewport rendering update on data changes, happens after depsgraph
* updates if there was any change. context is set to the 3d view */
bScreen *sc, *prev_sc= CTX_wm_screen(C);
ScrArea *sa, *prev_sa= CTX_wm_area(C);
ARegion *ar, *prev_ar= CTX_wm_region(C);
for(sc=bmain->screen.first; sc; sc=sc->id.next) {
for(sa=sc->areabase.first; sa; sa=sa->next) {
if(sa->spacetype != SPACE_VIEW3D)
continue;
for(ar=sa->regionbase.first; ar; ar=ar->next) {
RegionView3D *rv3d;
RenderEngine *engine;
if(ar->regiontype != RGN_TYPE_WINDOW)
continue;
rv3d= ar->regiondata;
engine= rv3d->render_engine;
if(engine && (engine->flag & RE_ENGINE_DO_UPDATE)) {
CTX_wm_screen_set(C, sc);
CTX_wm_area_set(C, sa);
CTX_wm_region_set(C, ar);
engine->flag &= ~RE_ENGINE_DO_UPDATE;
engine->type->view_update(engine, C);
}
}
}
}
CTX_wm_screen_set(C, prev_sc);
CTX_wm_area_set(C, prev_sa);
CTX_wm_region_set(C, prev_ar);
}
void ED_render_engine_changed(Main *bmain)
{
/* on changing the render engine type, clear all running render engines */
bScreen *sc;
ScrArea *sa;
ARegion *ar;
for(sc=bmain->screen.first; sc; sc=sc->id.next) {
for(sa=sc->areabase.first; sa; sa=sa->next) {
if(sa->spacetype != SPACE_VIEW3D)
continue;
for(ar=sa->regionbase.first; ar; ar=ar->next) {
RegionView3D *rv3d;
if(ar->regiontype != RGN_TYPE_WINDOW)
continue;
rv3d= ar->regiondata;
if(rv3d->render_engine) {
RE_engine_free(rv3d->render_engine);
rv3d->render_engine= NULL;
}
}
}
}
}
static void tag_render_engines(Main *bmain)
{
/* tag running render engines for update later on */
bScreen *sc;
ScrArea *sa;
ARegion *ar;
for(sc=bmain->screen.first; sc; sc=sc->id.next) {
for(sa=sc->areabase.first; sa; sa=sa->next) {
if(sa->spacetype != SPACE_VIEW3D)
continue;
for(ar=sa->regionbase.first; ar; ar=ar->next) {
RegionView3D *rv3d;
if(ar->regiontype != RGN_TYPE_WINDOW)
continue;
rv3d= ar->regiondata;
if(rv3d->render_engine)
rv3d->render_engine->flag |= RE_ENGINE_DO_UPDATE;
}
}
}
}
/***************************** Updates *********************************** /***************************** Updates ***********************************
* ED_render_id_flush_update gets called from DAG_id_tag_update, to do * * ED_render_id_flush_update gets called from DAG_id_tag_update, to do *
* editor level updates when the ID changes. when these ID blocks are in * * editor level updates when the ID changes. when these ID blocks are in *
@ -220,8 +319,10 @@ static void scene_changed(Main *bmain, Scene *UNUSED(scene))
void ED_render_id_flush_update(Main *bmain, ID *id) void ED_render_id_flush_update(Main *bmain, ID *id)
{ {
if(!id) if(!id) {
tag_render_engines(bmain);
return; return;
}
switch(GS(id->name)) { switch(GS(id->name)) {
case ID_MA: case ID_MA:

@ -104,7 +104,7 @@
/* this condition has been made more complex since editmode can draw textures */ /* this condition has been made more complex since editmode can draw textures */
#define CHECK_OB_DRAWTEXTURE(vd, dt) \ #define CHECK_OB_DRAWTEXTURE(vd, dt) \
((vd->drawtype==OB_TEXTURE && dt>OB_SOLID) || \ ((vd->drawtype==OB_TEXTURE && dt>OB_SOLID) || \
(vd->drawtype==OB_SOLID && vd->flag2 & V3D_SOLID_TEX)) (vd->drawtype==OB_SOLID && vd->flag2 & V3D_SOLID_TEX))
static void draw_bounding_volume(Scene *scene, Object *ob); static void draw_bounding_volume(Scene *scene, Object *ob);
@ -2696,8 +2696,7 @@ static void draw_mesh_fancy(Scene *scene, ARegion *ar, View3D *v3d, RegionView3D
totface = dm->getNumFaces(dm); totface = dm->getNumFaces(dm);
/* vertexpaint, faceselect wants this, but it doesnt work for shaded? */ /* vertexpaint, faceselect wants this, but it doesnt work for shaded? */
if(dt!=OB_SHADED) glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
glFrontFace((ob->transflag&OB_NEG_SCALE)?GL_CW:GL_CCW);
// Unwanted combination. // Unwanted combination.
if (is_paint_sel) draw_wire = 0; if (is_paint_sel) draw_wire = 0;
@ -2814,7 +2813,7 @@ static void draw_mesh_fancy(Scene *scene, ARegion *ar, View3D *v3d, RegionView3D
dm->drawLooseEdges(dm); dm->drawLooseEdges(dm);
} }
} }
else if(dt==OB_SHADED) { else if(dt==OB_PAINT) {
if(ob==OBACT) { if(ob==OBACT) {
if(ob && ob->mode & OB_MODE_WEIGHT_PAINT) { if(ob && ob->mode & OB_MODE_WEIGHT_PAINT) {
/* enforce default material settings */ /* enforce default material settings */
@ -5955,7 +5954,9 @@ void draw_object(Scene *scene, ARegion *ar, View3D *v3d, Base *base, int flag)
} }
/* maximum drawtype */ /* maximum drawtype */
dt= MIN2(v3d->drawtype, ob->dt); dt= v3d->drawtype;
if(dt==OB_RENDER) dt= OB_SOLID;
dt= MIN2(dt, ob->dt);
if(v3d->zbuf==0 && dt>OB_WIRE) dt= OB_WIRE; if(v3d->zbuf==0 && dt>OB_WIRE) dt= OB_WIRE;
dtx= 0; dtx= 0;
@ -5970,7 +5971,7 @@ void draw_object(Scene *scene, ARegion *ar, View3D *v3d, Base *base, int flag)
dt= OB_SOLID; dt= OB_SOLID;
} }
else { else {
dt= OB_SHADED; dt= OB_PAINT;
} }
glEnable(GL_DEPTH_TEST); glEnable(GL_DEPTH_TEST);

@ -56,6 +56,7 @@
#include "WM_api.h" #include "WM_api.h"
#include "WM_types.h" #include "WM_types.h"
#include "RE_engine.h"
#include "RNA_access.h" #include "RNA_access.h"
@ -344,6 +345,9 @@ static SpaceLink *view3d_duplicate(SpaceLink *sl)
v3do->lay= v3dn->localvd->lay; v3do->lay= v3dn->localvd->lay;
v3do->lay &= 0xFFFFFF; v3do->lay &= 0xFFFFFF;
} }
if(v3dn->drawtype == OB_RENDER)
v3dn->drawtype = OB_SOLID;
/* copy or clear inside new stuff */ /* copy or clear inside new stuff */
@ -549,6 +553,9 @@ static void view3d_main_area_free(ARegion *ar)
if(rv3d->ri) { if(rv3d->ri) {
// XXX BIF_view3d_previewrender_free(rv3d); // XXX BIF_view3d_previewrender_free(rv3d);
} }
if(rv3d->render_engine)
RE_engine_free(rv3d->render_engine);
if(rv3d->depths) { if(rv3d->depths) {
if(rv3d->depths->depths) MEM_freeN(rv3d->depths->depths); if(rv3d->depths->depths) MEM_freeN(rv3d->depths->depths);
@ -573,6 +580,7 @@ static void *view3d_main_area_duplicate(void *poin)
new->depths= NULL; new->depths= NULL;
new->ri= NULL; new->ri= NULL;
new->render_engine= NULL;
new->gpd= NULL; new->gpd= NULL;
new->sms= NULL; new->sms= NULL;
new->smooth_timer= NULL; new->smooth_timer= NULL;

@ -62,6 +62,7 @@
#include "BKE_screen.h" #include "BKE_screen.h"
#include "BKE_unit.h" #include "BKE_unit.h"
#include "RE_engine.h"
#include "RE_pipeline.h" // make_stars #include "RE_pipeline.h" // make_stars
#include "IMB_imbuf_types.h" #include "IMB_imbuf_types.h"
@ -2518,6 +2519,62 @@ static void draw_viewport_fps(Scene *scene, ARegion *ar)
BLF_draw_default_ascii(22, ar->winy-17, 0.0f, printable, sizeof(printable)-1); BLF_draw_default_ascii(22, ar->winy-17, 0.0f, printable, sizeof(printable)-1);
} }
static int view3d_main_area_draw_engine(const bContext *C, ARegion *ar)
{
Scene *scene= CTX_data_scene(C);
View3D *v3d = CTX_wm_view3d(C);
RegionView3D *rv3d= CTX_wm_region_view3d(C);
RenderEngineType *type;
if(!rv3d->render_engine) {
type= RE_engines_find(scene->r.engine);
if(!(type->view_update && type->view_draw))
return 0;
rv3d->render_engine= RE_engine_create(type);
type->view_update(rv3d->render_engine, C);
}
view3d_main_area_setup_view(scene, v3d, ar, NULL, NULL);
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
ED_region_pixelspace(ar);
type= rv3d->render_engine->type;
type->view_draw(rv3d->render_engine, C);
return 1;
}
static void view3d_main_area_draw_engine_info(RegionView3D *rv3d, ARegion *ar)
{
rcti rect;
const int header_height = 18;
if(!rv3d->render_engine || !rv3d->render_engine->text)
return;
/* background box */
rect= ar->winrct;
rect.xmin= 0;
rect.ymin= ar->winrct.ymax - ar->winrct.ymin - header_height;
rect.xmax= ar->winrct.xmax - ar->winrct.xmin;
rect.ymax= ar->winrct.ymax - ar->winrct.ymin;
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);
glColor4f(0.0f, 0.0f, 0.0f, 0.25f);
glRecti(rect.xmin, rect.ymin, rect.xmax+1, rect.ymax+1);
glDisable(GL_BLEND);
/* text */
UI_ThemeColor(TH_TEXT_HI);
UI_DrawString(12, rect.ymin + 5, rv3d->render_engine->text);
}
/* warning: this function has duplicate drawing in ED_view3d_draw_offscreen() */ /* warning: this function has duplicate drawing in ED_view3d_draw_offscreen() */
static void view3d_main_area_draw_objects(const bContext *C, ARegion *ar, const char **grid_unit) static void view3d_main_area_draw_objects(const bContext *C, ARegion *ar, const char **grid_unit)
{ {
@ -2728,6 +2785,11 @@ static void view3d_main_area_draw_info(const bContext *C, ARegion *ar, const cha
else else
draw_view_icon(rv3d); draw_view_icon(rv3d);
if(rv3d->render_engine) {
view3d_main_area_draw_engine_info(rv3d, ar);
return;
}
if((U.uiflag & USER_SHOW_FPS) && screen->animtimer) { if((U.uiflag & USER_SHOW_FPS) && screen->animtimer) {
draw_viewport_fps(scene, ar); draw_viewport_fps(scene, ar);
} }
@ -2755,9 +2817,12 @@ void view3d_main_area_draw(const bContext *C, ARegion *ar)
View3D *v3d = CTX_wm_view3d(C); View3D *v3d = CTX_wm_view3d(C);
const char *grid_unit= NULL; const char *grid_unit= NULL;
view3d_main_area_draw_objects(C, ar, &grid_unit); /* draw viewport using external renderer? */
if(!(v3d->drawtype == OB_RENDER && view3d_main_area_draw_engine(C, ar))) {
ED_region_pixelspace(ar); /* draw viewport using opengl */
view3d_main_area_draw_objects(C, ar, &grid_unit);
ED_region_pixelspace(ar);
}
view3d_main_area_draw_info(C, ar, grid_unit); view3d_main_area_draw_info(C, ar, grid_unit);

@ -385,8 +385,11 @@ typedef struct DupliObject {
#define OB_BOUNDBOX 1 #define OB_BOUNDBOX 1
#define OB_WIRE 2 #define OB_WIRE 2
#define OB_SOLID 3 #define OB_SOLID 3
#define OB_SHADED 4 #define OB_MATERIAL 4
#define OB_TEXTURE 5 #define OB_TEXTURE 5
#define OB_RENDER 6
#define OB_PAINT 100 /* temporary used in draw code */
/* dtx: flags, char! */ /* dtx: flags, char! */
#define OB_AXIS 2 #define OB_AXIS 2

@ -39,6 +39,7 @@ struct SpaceLink;
struct Base; struct Base;
struct BoundBox; struct BoundBox;
struct RenderInfo; struct RenderInfo;
struct RenderEngine;
struct bGPdata; struct bGPdata;
struct SmoothViewStore; struct SmoothViewStore;
struct wmTimer; struct wmTimer;
@ -115,6 +116,7 @@ typedef struct RegionView3D {
struct RegionView3D *localvd; /* allocated backup of its self while in localview */ struct RegionView3D *localvd; /* allocated backup of its self while in localview */
struct RenderInfo *ri; struct RenderInfo *ri;
struct RenderEngine *render_engine;
struct ViewDepths *depths; struct ViewDepths *depths;
/* animated smooth view */ /* animated smooth view */
@ -164,8 +166,8 @@ typedef struct View3D {
int layact; int layact;
/** /**
* The drawing mode for the 3d display. Set to OB_WIRE, OB_SOLID, * The drawing mode for the 3d display. Set to OB_BOUNDBOX, OB_WIRE, OB_SOLID,
* OB_SHADED or OB_TEXTURE */ * OB_TEXTURE, OB_MATERIAL or OB_RENDER */
short drawtype; short drawtype;
short ob_centre_cursor; /* optional bool for 3d cursor to define center */ short ob_centre_cursor; /* optional bool for 3d cursor to define center */
short scenelock, around; short scenelock, around;

@ -95,6 +95,40 @@ static void engine_render(RenderEngine *engine, struct Scene *scene)
RNA_parameter_list_free(&list); RNA_parameter_list_free(&list);
} }
static void engine_view_update(RenderEngine *engine, const struct bContext *context)
{
extern FunctionRNA rna_RenderEngine_view_update_func;
PointerRNA ptr;
ParameterList list;
FunctionRNA *func;
RNA_pointer_create(NULL, engine->type->ext.srna, engine, &ptr);
func= &rna_RenderEngine_view_update_func;
RNA_parameter_list_create(&list, &ptr, func);
RNA_parameter_set_lookup(&list, "context", &context);
engine->type->ext.call(NULL, &ptr, func, &list);
RNA_parameter_list_free(&list);
}
static void engine_view_draw(RenderEngine *engine, const struct bContext *context)
{
extern FunctionRNA rna_RenderEngine_view_draw_func;
PointerRNA ptr;
ParameterList list;
FunctionRNA *func;
RNA_pointer_create(NULL, engine->type->ext.srna, engine, &ptr);
func= &rna_RenderEngine_view_draw_func;
RNA_parameter_list_create(&list, &ptr, func);
RNA_parameter_set_lookup(&list, "context", &context);
engine->type->ext.call(NULL, &ptr, func, &list);
RNA_parameter_list_free(&list);
}
/* RenderEngine registration */ /* RenderEngine registration */
static void rna_RenderEngine_unregister(Main *UNUSED(bmain), StructRNA *type) static void rna_RenderEngine_unregister(Main *UNUSED(bmain), StructRNA *type)
@ -114,7 +148,7 @@ static StructRNA *rna_RenderEngine_register(Main *bmain, ReportList *reports, vo
RenderEngineType *et, dummyet = {NULL}; RenderEngineType *et, dummyet = {NULL};
RenderEngine dummyengine= {NULL}; RenderEngine dummyengine= {NULL};
PointerRNA dummyptr; PointerRNA dummyptr;
int have_function[2]; int have_function[4];
/* setup dummy engine & engine type to store static properties in */ /* setup dummy engine & engine type to store static properties in */
dummyengine.type= &dummyet; dummyengine.type= &dummyet;
@ -151,6 +185,8 @@ static StructRNA *rna_RenderEngine_register(Main *bmain, ReportList *reports, vo
et->update= (have_function[0])? engine_update: NULL; et->update= (have_function[0])? engine_update: NULL;
et->render= (have_function[1])? engine_render: NULL; et->render= (have_function[1])? engine_render: NULL;
et->view_update= (have_function[2])? engine_view_update: NULL;
et->view_draw= (have_function[3])? engine_view_draw: NULL;
BLI_addtail(&R_engines, et); BLI_addtail(&R_engines, et);
@ -251,6 +287,17 @@ static void rna_def_render_engine(BlenderRNA *brna)
RNA_def_function_flag(func, FUNC_REGISTER_OPTIONAL); RNA_def_function_flag(func, FUNC_REGISTER_OPTIONAL);
RNA_def_pointer(func, "scene", "Scene", "", ""); RNA_def_pointer(func, "scene", "Scene", "", "");
/* viewport render callbacks */
func= RNA_def_function(srna, "view_update", NULL);
RNA_def_function_ui_description(func, "Update on data changes for viewport render");
RNA_def_function_flag(func, FUNC_REGISTER_OPTIONAL);
RNA_def_pointer(func, "context", "Context", "", "");
func= RNA_def_function(srna, "view_draw", NULL);
RNA_def_function_ui_description(func, "Draw viewport render");
RNA_def_function_flag(func, FUNC_REGISTER_OPTIONAL);
RNA_def_pointer(func, "context", "Context", "", "");
/* tag for redraw */ /* tag for redraw */
RNA_def_function(srna, "tag_redraw", "engine_tag_redraw"); RNA_def_function(srna, "tag_redraw", "engine_tag_redraw");
RNA_def_function_ui_description(func, "Request redraw for viewport rendering"); RNA_def_function_ui_description(func, "Request redraw for viewport rendering");

@ -40,6 +40,7 @@
#include "BLI_math.h" #include "BLI_math.h"
/* Include for Bake Options */ /* Include for Bake Options */
#include "RE_engine.h"
#include "RE_pipeline.h" #include "RE_pipeline.h"
#ifdef WITH_QUICKTIME #ifdef WITH_QUICKTIME
@ -55,6 +56,8 @@
#include <libavformat/avformat.h> #include <libavformat/avformat.h>
#endif #endif
#include "ED_render.h"
#include "WM_api.h" #include "WM_api.h"
#include "WM_types.h" #include "WM_types.h"
@ -773,6 +776,11 @@ static int rna_RenderSettings_engine_get(PointerRNA *ptr)
return 0; return 0;
} }
static void rna_RenderSettings_engine_update(Main *bmain, Scene *UNUSED(unused), PointerRNA *UNUSED(ptr))
{
ED_render_engine_changed(bmain);
}
static void rna_Scene_glsl_update(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr) static void rna_Scene_glsl_update(Main *UNUSED(bmain), Scene *UNUSED(scene), PointerRNA *ptr)
{ {
Scene *scene= (Scene*)ptr->id.data; Scene *scene= (Scene*)ptr->id.data;
@ -3212,7 +3220,7 @@ static void rna_def_scene_render_data(BlenderRNA *brna)
RNA_def_property_enum_funcs(prop, "rna_RenderSettings_engine_get", "rna_RenderSettings_engine_set", RNA_def_property_enum_funcs(prop, "rna_RenderSettings_engine_get", "rna_RenderSettings_engine_set",
"rna_RenderSettings_engine_itemf"); "rna_RenderSettings_engine_itemf");
RNA_def_property_ui_text(prop, "Engine", "Engine to use for rendering"); RNA_def_property_ui_text(prop, "Engine", "Engine to use for rendering");
RNA_def_property_update(prop, NC_WINDOW, NULL); RNA_def_property_update(prop, NC_WINDOW, "rna_RenderSettings_engine_update");
prop= RNA_def_property(srna, "has_multiple_engines", PROP_BOOLEAN, PROP_NONE); prop= RNA_def_property(srna, "has_multiple_engines", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_boolean_funcs(prop, "rna_RenderSettings_multiple_engines_get", NULL); RNA_def_property_boolean_funcs(prop, "rna_RenderSettings_multiple_engines_get", NULL);

@ -47,6 +47,9 @@
#include "WM_api.h" #include "WM_api.h"
#include "WM_types.h" #include "WM_types.h"
#include "RE_engine.h"
#include "RE_pipeline.h"
#include "RNA_enum_types.h" #include "RNA_enum_types.h"
EnumPropertyItem space_type_items[] = { EnumPropertyItem space_type_items[] = {
@ -98,8 +101,8 @@ EnumPropertyItem viewport_shade_items[] = {
{OB_BOUNDBOX, "BOUNDBOX", ICON_BBOX, "Bounding Box", "Display the object's local bounding boxes only"}, {OB_BOUNDBOX, "BOUNDBOX", ICON_BBOX, "Bounding Box", "Display the object's local bounding boxes only"},
{OB_WIRE, "WIREFRAME", ICON_WIRE, "Wireframe", "Display the object as wire edges"}, {OB_WIRE, "WIREFRAME", ICON_WIRE, "Wireframe", "Display the object as wire edges"},
{OB_SOLID, "SOLID", ICON_SOLID, "Solid", "Display the object solid, lit with default OpenGL lights"}, {OB_SOLID, "SOLID", ICON_SOLID, "Solid", "Display the object solid, lit with default OpenGL lights"},
//{OB_SHADED, "SHADED", ICON_SMOOTH, "Shaded", "Display the object solid, with preview shading interpolated at vertices"},
{OB_TEXTURE, "TEXTURED", ICON_POTATO, "Textured", "Display the object solid, with face-assigned textures"}, {OB_TEXTURE, "TEXTURED", ICON_POTATO, "Textured", "Display the object solid, with face-assigned textures"},
{OB_RENDER, "RENDERED", ICON_SMOOTH, "Rendered", "Display render preview"},
{0, NULL, 0, NULL, NULL}}; {0, NULL, 0, NULL, NULL}};
#ifdef RNA_RUNTIME #ifdef RNA_RUNTIME
@ -313,6 +316,25 @@ static void rna_SpaceView3D_layer_update(Main *bmain, Scene *UNUSED(scene), Poin
DAG_on_visible_update(bmain, FALSE); DAG_on_visible_update(bmain, FALSE);
} }
static void rna_SpaceView3D_viewport_shade_update(Main *bmain, Scene *scene, PointerRNA *ptr)
{
View3D *v3d= (View3D*)(ptr->data);
ScrArea *sa= rna_area_from_space(ptr);
if(v3d->drawtype != OB_RENDER) {
ARegion *ar;
for(ar=sa->regionbase.first; ar; ar=ar->next) {
RegionView3D *rv3d = ar->regiondata;
if(rv3d && rv3d->render_engine) {
RE_engine_free(rv3d->render_engine);
rv3d->render_engine= NULL;
}
}
}
}
static void rna_SpaceView3D_pivot_update(Main *bmain, Scene *UNUSED(scene), PointerRNA *ptr) static void rna_SpaceView3D_pivot_update(Main *bmain, Scene *UNUSED(scene), PointerRNA *ptr)
{ {
if (U.uiflag & USER_LOCKAROUND) { if (U.uiflag & USER_LOCKAROUND) {
@ -423,6 +445,29 @@ static void rna_RegionView3D_view_matrix_set(PointerRNA *ptr, const float *value
ED_view3d_from_m4((float (*)[4])values, rv3d->ofs, rv3d->viewquat, &rv3d->dist); ED_view3d_from_m4((float (*)[4])values, rv3d->ofs, rv3d->viewquat, &rv3d->dist);
} }
static EnumPropertyItem *rna_SpaceView3D_viewport_shade_itemf(bContext *UNUSED(C), PointerRNA *ptr, PropertyRNA *UNUSED(prop), int *free)
{
Scene *scene = ((bScreen*)ptr->id.data)->scene;
RenderEngineType *type = RE_engines_find(scene->r.engine);
EnumPropertyItem *item= NULL;
int totitem= 0;
RNA_enum_items_add_value(&item, &totitem, viewport_shade_items, OB_BOUNDBOX);
RNA_enum_items_add_value(&item, &totitem, viewport_shade_items, OB_WIRE);
RNA_enum_items_add_value(&item, &totitem, viewport_shade_items, OB_SOLID);
RNA_enum_items_add_value(&item, &totitem, viewport_shade_items, OB_TEXTURE);
if(type->view_draw) {
RNA_enum_items_add_value(&item, &totitem, viewport_shade_items, OB_RENDER);
}
RNA_enum_item_end(&item, &totitem);
*free= 1;
return item;
}
/* Space Image Editor */ /* Space Image Editor */
static PointerRNA rna_SpaceImageEditor_uvedit_get(PointerRNA *ptr) static PointerRNA rna_SpaceImageEditor_uvedit_get(PointerRNA *ptr)
@ -1227,8 +1272,9 @@ static void rna_def_space_view3d(BlenderRNA *brna)
prop= RNA_def_property(srna, "viewport_shade", PROP_ENUM, PROP_NONE); prop= RNA_def_property(srna, "viewport_shade", PROP_ENUM, PROP_NONE);
RNA_def_property_enum_sdna(prop, NULL, "drawtype"); RNA_def_property_enum_sdna(prop, NULL, "drawtype");
RNA_def_property_enum_items(prop, viewport_shade_items); RNA_def_property_enum_items(prop, viewport_shade_items);
RNA_def_property_enum_funcs(prop, NULL, NULL, "rna_SpaceView3D_viewport_shade_itemf");
RNA_def_property_ui_text(prop, "Viewport Shading", "Method to display/shade objects in the 3D View"); RNA_def_property_ui_text(prop, "Viewport Shading", "Method to display/shade objects in the 3D View");
RNA_def_property_update(prop, NC_SPACE|ND_SPACE_VIEW3D, NULL); RNA_def_property_update(prop, NC_SPACE|ND_SPACE_VIEW3D, "rna_SpaceView3D_viewport_shade_update");
prop= RNA_def_property(srna, "local_view", PROP_POINTER, PROP_NONE); prop= RNA_def_property(srna, "local_view", PROP_POINTER, PROP_NONE);
RNA_def_property_pointer_sdna(prop, NULL, "localvd"); RNA_def_property_pointer_sdna(prop, NULL, "localvd");

@ -71,6 +71,9 @@ typedef struct RenderEngineType {
void (*update)(struct RenderEngine *engine, struct Main *bmain, struct Scene *scene); void (*update)(struct RenderEngine *engine, struct Main *bmain, struct Scene *scene);
void (*render)(struct RenderEngine *engine, struct Scene *scene); void (*render)(struct RenderEngine *engine, struct Scene *scene);
void (*view_update)(struct RenderEngine *engine, const struct bContext *context);
void (*view_draw)(struct RenderEngine *engine, const struct bContext *context);
/* RNA integration */ /* RNA integration */
ExtensionRNA ext; ExtensionRNA ext;
} RenderEngineType; } RenderEngineType;

@ -61,7 +61,7 @@
static RenderEngineType internal_render_type = { static RenderEngineType internal_render_type = {
NULL, NULL, NULL, NULL,
"BLENDER_RENDER", "Blender Render", RE_INTERNAL, "BLENDER_RENDER", "Blender Render", RE_INTERNAL,
NULL, NULL, NULL, NULL, NULL, NULL,
{NULL, NULL, NULL}}; {NULL, NULL, NULL}};
#ifdef WITH_GAMEENGINE #ifdef WITH_GAMEENGINE
@ -69,7 +69,7 @@ static RenderEngineType internal_render_type = {
static RenderEngineType internal_game_type = { static RenderEngineType internal_game_type = {
NULL, NULL, NULL, NULL,
"BLENDER_GAME", "Blender Game", RE_INTERNAL|RE_GAME, "BLENDER_GAME", "Blender Game", RE_INTERNAL|RE_GAME,
NULL, NULL, NULL, NULL, NULL, NULL,
{NULL, NULL, NULL}}; {NULL, NULL, NULL}};
#endif #endif

@ -55,6 +55,8 @@
#include "GPU_draw.h" #include "GPU_draw.h"
#include "GPU_extensions.h" #include "GPU_extensions.h"
#include "RE_engine.h"
#include "WM_api.h" #include "WM_api.h"
#include "WM_types.h" #include "WM_types.h"
#include "wm.h" #include "wm.h"
@ -113,6 +115,19 @@ static int wm_area_test_invalid_backbuf(ScrArea *sa)
return 1; return 1;
} }
static void wm_region_test_render_do_draw(ScrArea *sa, ARegion *ar)
{
if(sa->spacetype == SPACE_VIEW3D) {
RegionView3D *rv3d = ar->regiondata;
RenderEngine *engine = (rv3d)? rv3d->render_engine: NULL;
if(engine && (engine->flag & RE_ENGINE_DO_DRAW)) {
ar->do_draw = 1;
engine->flag &= ~RE_ENGINE_DO_DRAW;
}
}
}
/********************** draw all **************************/ /********************** draw all **************************/
/* - reference method, draw all each time */ /* - reference method, draw all each time */
@ -205,7 +220,7 @@ static void wm_method_draw_overlap_all(bContext *C, wmWindow *win, int exchange)
for(sa= screen->areabase.first; sa; sa= sa->next) for(sa= screen->areabase.first; sa; sa= sa->next)
for(ar= sa->regionbase.first; ar; ar= ar->next) for(ar= sa->regionbase.first; ar; ar= ar->next)
if(ar->swinid && !wm_area_test_invalid_backbuf(sa)) if(ar->swinid && !wm_area_test_invalid_backbuf(sa))
ED_region_tag_redraw(ar); ED_region_tag_redraw(ar);
/* flush overlapping regions */ /* flush overlapping regions */
if(screen->regionbase.first) { if(screen->regionbase.first) {
@ -662,13 +677,28 @@ static int wm_draw_update_test_window(wmWindow *win)
{ {
ScrArea *sa; ScrArea *sa;
ARegion *ar; ARegion *ar;
int do_draw= 0;
for(ar= win->screen->regionbase.first; ar; ar= ar->next) { for(ar= win->screen->regionbase.first; ar; ar= ar->next) {
if(ar->do_draw_overlay) { if(ar->do_draw_overlay) {
wm_tag_redraw_overlay(win, ar); wm_tag_redraw_overlay(win, ar);
ar->do_draw_overlay= 0; ar->do_draw_overlay= 0;
} }
if(ar->swinid && ar->do_draw)
do_draw= 1;
} }
for(sa= win->screen->areabase.first; sa; sa= sa->next) {
for(ar=sa->regionbase.first; ar; ar= ar->next) {
wm_region_test_render_do_draw(sa, ar);
if(ar->swinid && ar->do_draw)
do_draw = 1;
}
}
if(do_draw)
return 1;
if(win->screen->do_refresh) if(win->screen->do_refresh)
return 1; return 1;
@ -681,15 +711,6 @@ static int wm_draw_update_test_window(wmWindow *win)
if(win->screen->do_draw_drag) if(win->screen->do_draw_drag)
return 1; return 1;
for(ar= win->screen->regionbase.first; ar; ar= ar->next)
if(ar->swinid && ar->do_draw)
return 1;
for(sa= win->screen->areabase.first; sa; sa= sa->next)
for(ar=sa->regionbase.first; ar; ar= ar->next)
if(ar->swinid && ar->do_draw)
return 1;
return 0; return 0;
} }

@ -59,6 +59,7 @@
#include "ED_fileselect.h" #include "ED_fileselect.h"
#include "ED_info.h" #include "ED_info.h"
#include "ED_render.h"
#include "ED_screen.h" #include "ED_screen.h"
#include "ED_view3d.h" #include "ED_view3d.h"
#include "ED_util.h" #include "ED_util.h"
@ -311,6 +312,7 @@ void wm_event_do_notifiers(bContext *C)
/* XXX make lock in future, or separated derivedmesh users in scene */ /* XXX make lock in future, or separated derivedmesh users in scene */
if(!G.rendering) { if(!G.rendering) {
/* depsgraph & animation: update tagged datablocks */ /* depsgraph & animation: update tagged datablocks */
Main *bmain = CTX_data_main(C);
/* copied to set's in scene_update_tagged_recursive() */ /* copied to set's in scene_update_tagged_recursive() */
win->screen->scene->customdata_mask= win_combine_v3d_datamask; win->screen->scene->customdata_mask= win_combine_v3d_datamask;
@ -318,7 +320,9 @@ void wm_event_do_notifiers(bContext *C)
/* XXX, hack so operators can enforce datamasks [#26482], gl render */ /* XXX, hack so operators can enforce datamasks [#26482], gl render */
win->screen->scene->customdata_mask |= win->screen->scene->customdata_mask_modal; win->screen->scene->customdata_mask |= win->screen->scene->customdata_mask_modal;
scene_update_tagged(CTX_data_main(C), win->screen->scene); scene_update_tagged(bmain, win->screen->scene);
ED_render_engine_update_tagged(C, bmain);
} }
} }

@ -72,6 +72,7 @@ struct Object;
struct PBVHNode; struct PBVHNode;
struct Render; struct Render;
struct RenderEngine; struct RenderEngine;
struct RenderEngineType;
struct RenderLayer; struct RenderLayer;
struct RenderResult; struct RenderResult;
struct ScrArea; struct ScrArea;
@ -194,6 +195,7 @@ struct ImBuf *ED_space_image_buffer(struct SpaceImage *sima){return (struct ImBu
void ED_screen_set_scene(struct bContext *C, struct Scene *scene){} void ED_screen_set_scene(struct bContext *C, struct Scene *scene){}
void ED_area_tag_redraw_regiontype(struct ScrArea *sa, int regiontype){} void ED_area_tag_redraw_regiontype(struct ScrArea *sa, int regiontype){}
void ED_render_engine_changed(struct Main *bmain) {}
struct PTCacheEdit *PE_get_current(struct Scene *scene, struct Object *ob){return (struct PTCacheEdit *) NULL;} struct PTCacheEdit *PE_get_current(struct Scene *scene, struct Object *ob){return (struct PTCacheEdit *) NULL;}
void PE_current_changed(struct Scene *scene, struct Object *ob){} void PE_current_changed(struct Scene *scene, struct Object *ob){}
@ -387,6 +389,7 @@ void RE_engines_exit() {}
void RE_engine_report(struct RenderEngine *engine, int type, const char *msg) {} void RE_engine_report(struct RenderEngine *engine, int type, const char *msg) {}
ListBase R_engines = {NULL, NULL}; ListBase R_engines = {NULL, NULL};
void RE_engine_free(struct RenderEngine *engine) {} void RE_engine_free(struct RenderEngine *engine) {}
struct RenderEngineType *RE_engines_find(const char *idname) {}
/* python */ /* python */
struct wmOperatorType *WM_operatortype_find(const char *idname, int quiet){return (struct wmOperatorType *) NULL;} struct wmOperatorType *WM_operatortype_find(const char *idname, int quiet){return (struct wmOperatorType *) NULL;}