Merge branch 'blender2.7'

This commit is contained in:
Lukas Stockner 2019-01-18 01:47:32 +01:00
commit 031a9d6424
5 changed files with 90 additions and 31 deletions

View File

@ -214,6 +214,23 @@ void node_cmp_rlayers_register_pass(bNodeTree *ntree, bNode *node, Scene *scene,
}
}
static void cmp_node_rlayer_create_outputs_cb(RenderEngine *UNUSED(engine), Scene *scene, ViewLayer *view_layer,
const char *name, int UNUSED(channels), const char *UNUSED(chanid), int type)
{
/* Register the pass in all scenes that have a render layer node for this layer.
* Since multiple scenes can be used in the compositor, the code must loop over all scenes
* and check whether their nodetree has a node that needs to be updated. */
/* NOTE: using G_MAIN seems valid here,
* unless we want to register that for every other temp Main we could generate??? */
ntreeCompositRegisterPass(scene->nodetree, scene, view_layer, name, type);
for (Scene *sce = G_MAIN->scene.first; sce; sce = sce->id.next) {
if (sce->nodetree && sce != scene) {
ntreeCompositRegisterPass(sce->nodetree, scene, view_layer, name, type);
}
}
}
static void cmp_node_rlayer_create_outputs(bNodeTree *ntree, bNode *node, LinkNodePair *available_sockets)
{
Scene *scene = (Scene *)node->id;
@ -229,7 +246,7 @@ static void cmp_node_rlayer_create_outputs(bNodeTree *ntree, bNode *node, LinkNo
node->storage = data;
RenderEngine *engine = RE_engine_create(engine_type);
engine_type->update_render_passes(engine, scene, view_layer);
RE_engine_update_render_passes(engine, scene, view_layer, cmp_node_rlayer_create_outputs_cb);
RE_engine_free(engine);
MEM_freeN(data);

View File

@ -37,6 +37,8 @@
#include "RNA_types.h"
#include "RE_bake.h"
#include "BLI_threads.h"
struct bNode;
struct bNodeTree;
struct BakePixel;
@ -111,6 +113,9 @@ typedef struct RenderEngineType {
ExtensionRNA ext;
} RenderEngineType;
typedef void (*update_render_passes_cb_t)(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
const char *name, int channels, const char *chanid, int type);
typedef struct RenderEngine {
RenderEngineType *type;
void *py_instance;
@ -137,6 +142,10 @@ typedef struct RenderEngine {
int update_flag;
int job_update_flag;
/* callback for render pass query */
ThreadMutex update_render_passes_mutex;
update_render_passes_cb_t update_render_passes_cb;
rctf last_viewplane;
rcti last_disprect;
float last_viewmat[4][4];
@ -175,6 +184,8 @@ bool RE_engine_is_external(struct Render *re);
void RE_engine_frame_set(struct RenderEngine *engine, int frame, float subframe);
void RE_engine_update_render_passes(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
update_render_passes_cb_t callback);
void RE_engine_register_pass(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
const char *name, int channels, const char *chanid, int type);

View File

@ -44,6 +44,7 @@ struct ImBuf;
struct ListBase;
struct Render;
struct RenderData;
struct RenderEngine;
struct RenderLayer;
struct RenderResult;
struct Scene;
@ -83,8 +84,8 @@ void render_result_single_layer_end(struct Render *re);
/* EXR Tile File Render */
void render_result_save_empty_result_tiles(struct Render *re);
void render_result_exr_file_begin(struct Render *re);
void render_result_exr_file_end(struct Render *re);
void render_result_exr_file_begin(struct Render *re, struct RenderEngine *engine);
void render_result_exr_file_end(struct Render *re, struct RenderEngine *engine);
/* render pass wrapper for gpencil */
struct RenderPass *gp_add_pass(struct RenderResult *rr, struct RenderLayer *rl, int channels, const char *name, const char *viewname);
@ -92,7 +93,7 @@ struct RenderPass *gp_add_pass(struct RenderResult *rr, struct RenderLayer *rl,
void render_result_exr_file_merge(struct RenderResult *rr, struct RenderResult *rrpart, const char *viewname);
void render_result_exr_file_path(struct Scene *scene, const char *layname, int sample, char *filepath);
int render_result_exr_file_read_sample(struct Render *re, int sample);
int render_result_exr_file_read_sample(struct Render *re, int sample, struct RenderEngine *engine);
int render_result_exr_file_read_path(struct RenderResult *rr, struct RenderLayer *rl_single, const char *filepath);
/* EXR cache */

View File

@ -150,6 +150,8 @@ RenderEngine *RE_engine_create_ex(RenderEngineType *type, bool use_for_viewport)
BLI_threaded_malloc_begin();
}
BLI_mutex_init(&engine->update_render_passes_mutex);
return engine;
}
@ -165,6 +167,8 @@ void RE_engine_free(RenderEngine *engine)
BLI_threaded_malloc_end();
}
BLI_mutex_end(&engine->update_render_passes_mutex);
MEM_freeN(engine);
}
@ -711,7 +715,7 @@ int RE_engine_render(Render *re, int do_all)
engine->tile_y = re->party;
if (re->result->do_exr_tile)
render_result_exr_file_begin(re);
render_result_exr_file_begin(re, engine);
/* Clear UI drawing locks. */
if (re->draw_lock) {
@ -765,19 +769,19 @@ int RE_engine_render(Render *re, int do_all)
BLI_rw_mutex_lock(&re->partsmutex, THREAD_LOCK_WRITE);
if (re->result->do_exr_tile) {
BLI_rw_mutex_lock(&re->resultmutex, THREAD_LOCK_WRITE);
render_result_save_empty_result_tiles(re);
render_result_exr_file_end(re, engine);
BLI_rw_mutex_unlock(&re->resultmutex);
}
/* re->engine becomes zero if user changed active render engine during render */
if (!persistent_data || !re->engine) {
RE_engine_free(engine);
re->engine = NULL;
}
if (re->result->do_exr_tile) {
BLI_rw_mutex_lock(&re->resultmutex, THREAD_LOCK_WRITE);
render_result_save_empty_result_tiles(re);
render_result_exr_file_end(re);
BLI_rw_mutex_unlock(&re->resultmutex);
}
if (re->r.scemode & R_EXR_CACHE_FILE) {
BLI_rw_mutex_lock(&re->resultmutex, THREAD_LOCK_WRITE);
render_result_exr_file_cache_write(re);
@ -798,27 +802,29 @@ int RE_engine_render(Render *re, int do_all)
return 1;
}
void RE_engine_register_pass(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
const char *name, int UNUSED(channels), const char *UNUSED(chanid), int type)
void RE_engine_update_render_passes(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
update_render_passes_cb_t callback)
{
/* The channel information is currently not used, but is part of the API in case it's needed in the future. */
if (!(scene && view_layer && engine)) {
if (!(scene && view_layer && engine && callback && engine->type->update_render_passes)) {
return;
}
/* Register the pass in all scenes that have a render layer node for this layer.
* Since multiple scenes can be used in the compositor, the code must loop over all scenes
* and check whether their nodetree has a node that needs to be updated. */
/* NOTE: using G_MAIN seems valid here,
* unless we want to register that for every other temp Main we could generate??? */
ntreeCompositRegisterPass(scene->nodetree, scene, view_layer, name, type);
BLI_mutex_lock(&engine->update_render_passes_mutex);
for (Scene *sce = G_MAIN->scene.first; sce; sce = sce->id.next) {
if (sce->nodetree && sce != scene) {
ntreeCompositRegisterPass(sce->nodetree, scene, view_layer, name, type);
}
engine->update_render_passes_cb = callback;
engine->type->update_render_passes(engine, scene, view_layer);
BLI_mutex_unlock(&engine->update_render_passes_mutex);
}
void RE_engine_register_pass(struct RenderEngine *engine, struct Scene *scene, struct ViewLayer *view_layer,
const char *name, int channels, const char *chanid, int type)
{
if (!(scene && view_layer && engine && engine->update_render_passes_cb)) {
return;
}
engine->update_render_passes_cb(engine, scene, view_layer, name, channels, chanid, type);
}
void RE_engine_free_blender_memory(RenderEngine *engine)

View File

@ -57,6 +57,8 @@
#include "intern/openexr/openexr_multi.h"
#include "RE_engine.h"
#include "render_result.h"
#include "render_types.h"
@ -482,6 +484,7 @@ void render_result_add_pass(RenderResult *rr, const char *name, int channels, co
for (rp = rl->passes.first; rp; rp = rp->next) {
if (!STREQ(rp->name, name)) continue;
if (!STREQ(rp->view, view)) continue;
break;
}
if (!rp) {
@ -1063,8 +1066,25 @@ void render_result_save_empty_result_tiles(Render *re)
}
}
static void render_result_register_pass_cb(RenderEngine *engine, Scene *UNUSED(scene), ViewLayer *view_layer,
const char *name, int channels, const char *chanid, int UNUSED(type))
{
RE_engine_add_pass(engine, name, channels, chanid, view_layer->name);
}
static void render_result_create_all_passes(RenderEngine *engine, Render *re, RenderLayer *rl)
{
if (engine && engine->type->update_render_passes) {
ViewLayer *view_layer;
view_layer = BLI_findstring(&re->view_layers, rl->name, offsetof(ViewLayer, name));
if (view_layer) {
RE_engine_update_render_passes(engine, re->scene, view_layer, render_result_register_pass_cb);
}
}
}
/* begin write of exr tile file */
void render_result_exr_file_begin(Render *re)
void render_result_exr_file_begin(Render *re, RenderEngine *engine)
{
RenderResult *rr;
RenderLayer *rl;
@ -1072,6 +1092,8 @@ void render_result_exr_file_begin(Render *re)
for (rr = re->result; rr; rr = rr->next) {
for (rl = rr->layers.first; rl; rl = rl->next) {
render_result_create_all_passes(engine, re, rl);
render_result_exr_file_path(re->scene, rl->name, rr->sample_nr, str);
printf("write exr tmp file, %dx%d, %s\n", rr->rectx, rr->recty, str);
IMB_exrtile_begin_write(rl->exrhandle, str, 0, rr->rectx, rr->recty, re->partx, re->party);
@ -1080,7 +1102,7 @@ void render_result_exr_file_begin(Render *re)
}
/* end write of exr tile file, read back first sample */
void render_result_exr_file_end(Render *re)
void render_result_exr_file_end(Render *re, RenderEngine *engine)
{
RenderResult *rr;
RenderLayer *rl;
@ -1097,7 +1119,7 @@ void render_result_exr_file_end(Render *re)
render_result_free_list(&re->fullresult, re->result);
re->result = NULL;
render_result_exr_file_read_sample(re, 0);
render_result_exr_file_read_sample(re, 0, engine);
}
/* save part into exr file */
@ -1127,7 +1149,7 @@ void render_result_exr_file_path(Scene *scene, const char *layname, int sample,
}
/* only for temp buffer, makes exact copy of render result */
int render_result_exr_file_read_sample(Render *re, int sample)
int render_result_exr_file_read_sample(Render *re, int sample, RenderEngine *engine)
{
RenderLayer *rl;
char str[FILE_MAXFILE + MAX_ID_NAME + MAX_ID_NAME + 100] = "";
@ -1137,6 +1159,8 @@ int render_result_exr_file_read_sample(Render *re, int sample)
re->result = render_result_new(re, &re->disprect, 0, RR_USE_MEM, RR_ALL_LAYERS, RR_ALL_VIEWS);
for (rl = re->result->layers.first; rl; rl = rl->next) {
render_result_create_all_passes(engine, re, rl);
render_result_exr_file_path(re->scene, rl->name, sample, str);
printf("read exr tmp file: %s\n", str);