forked from bartvdbraak/blender
Todo/feature request
When using masks or other simple 3D elements in composites, doing a layer re-rendering on a node is a bit clumsy all the time. This commit does two things to help: - new hotkey "Z" in node editor automatically finds render layer that changed and re-renders it + composites - option "Auto Render" does same, but then after every transform edit in 3D window The latter is experimental; real & proper system for this requires full threaded render support (like previews). But it works! Demo file: http://download.blender.org/demo/test/auto_composite.blend Important fix: After any render, all the render layers were tagged "changed", which caused any edit to first totally recomposte everthing. Now it only composites changes. Implementation notes - DAG scene flush now sets 'changed' flags in render layer nodes - Added notifier for 'transform finished' to trigger the update, this is temporarily.
This commit is contained in:
parent
831ce612e9
commit
5c421c328e
@ -71,6 +71,7 @@ class NODE_HT_header(bpy.types.Header):
|
||||
if snode.show_backdrop:
|
||||
row = layout.row(align=True)
|
||||
row.prop(snode, "backdrop_channels", text="", expand=True)
|
||||
layout.prop(snode, "use_auto_render")
|
||||
|
||||
layout.separator()
|
||||
|
||||
|
@ -193,6 +193,7 @@ void nodeClearActiveID(struct bNodeTree *ntree, short idtype);
|
||||
|
||||
void NodeTagChanged(struct bNodeTree *ntree, struct bNode *node);
|
||||
int NodeTagIDChanged(struct bNodeTree *ntree, struct ID *id);
|
||||
void ntreeClearTags(struct bNodeTree *ntree);
|
||||
|
||||
/* ************** Groups ****************** */
|
||||
|
||||
|
@ -41,6 +41,7 @@
|
||||
#include "DNA_lattice_types.h"
|
||||
#include "DNA_key_types.h"
|
||||
#include "DNA_mesh_types.h"
|
||||
#include "DNA_node_types.h"
|
||||
#include "DNA_scene_types.h"
|
||||
#include "DNA_screen_types.h"
|
||||
#include "DNA_windowmanager_types.h"
|
||||
@ -54,6 +55,7 @@
|
||||
#include "BKE_key.h"
|
||||
#include "BKE_library.h"
|
||||
#include "BKE_main.h"
|
||||
#include "BKE_node.h"
|
||||
#include "BKE_mball.h"
|
||||
#include "BKE_modifier.h"
|
||||
#include "BKE_object.h"
|
||||
@ -1923,6 +1925,28 @@ static void dag_scene_flush_layers(Scene *sce, int lay)
|
||||
flush_layer_node(sce, itA->node, lasttime);
|
||||
}
|
||||
|
||||
static void dag_tag_renderlayers(Scene *sce, unsigned int lay)
|
||||
{
|
||||
if(sce->nodetree) {
|
||||
bNode *node;
|
||||
Base *base;
|
||||
unsigned int lay_changed;
|
||||
|
||||
for(base= sce->base.first; base; base= base->next)
|
||||
if(base->lay & lay)
|
||||
if(base->object->recalc)
|
||||
lay_changed |= base->lay;
|
||||
|
||||
for(node= sce->nodetree->nodes.first; node; node= node->next) {
|
||||
if(node->id==(ID *)sce) {
|
||||
SceneRenderLayer *srl= BLI_findlink(&sce->r.layers, node->custom1);
|
||||
if(srl && (srl->lay & lay_changed))
|
||||
NodeTagChanged(sce->nodetree, node);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* flushes all recalc flags in objects down the dependency tree */
|
||||
void DAG_scene_flush_update(Main *bmain, Scene *sce, unsigned int lay, const short time)
|
||||
{
|
||||
@ -1967,6 +1991,8 @@ void DAG_scene_flush_update(Main *bmain, Scene *sce, unsigned int lay, const sho
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dag_tag_renderlayers(sce, lay);
|
||||
}
|
||||
|
||||
static int object_modifiers_use_time(Object *ob)
|
||||
|
@ -3182,10 +3182,7 @@ int ntreeCompositTagAnimated(bNodeTree *ntree)
|
||||
NodeTagChanged(ntree, node);
|
||||
tagged= 1;
|
||||
}
|
||||
else if(node->type==CMP_NODE_R_LAYERS) {
|
||||
NodeTagChanged(ntree, node);
|
||||
tagged= 1;
|
||||
}
|
||||
/* here was tag render layer, but this is called after a render, so re-composites fail */
|
||||
else if(node->type==NODE_GROUP) {
|
||||
if( ntreeCompositTagAnimated((bNodeTree *)node->id) ) {
|
||||
NodeTagChanged(ntree, node);
|
||||
@ -3210,6 +3207,21 @@ void ntreeCompositTagGenerators(bNodeTree *ntree)
|
||||
}
|
||||
}
|
||||
|
||||
/* XXX after render animation system gets a refresh, this call allows composite to end clean */
|
||||
void ntreeClearTags(bNodeTree *ntree)
|
||||
{
|
||||
bNode *node;
|
||||
|
||||
if(ntree==NULL) return;
|
||||
|
||||
for(node= ntree->nodes.first; node; node= node->next) {
|
||||
node->need_exec= 0;
|
||||
if(node->type==NODE_GROUP)
|
||||
ntreeClearTags((bNodeTree *)node->id);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int ntreeTexTagAnimated(bNodeTree *ntree)
|
||||
{
|
||||
bNode *node;
|
||||
|
@ -596,6 +596,9 @@ static void render_endjob(void *rjv)
|
||||
/* else the frame will not update for the original value */
|
||||
ED_update_for_newframe(G.main, rj->scene, rj->win->screen, 1);
|
||||
|
||||
/* XXX above function sets all tags in nodes */
|
||||
ntreeClearTags(rj->scene->nodetree);
|
||||
|
||||
if(rj->srl) {
|
||||
NodeTagIDChanged(rj->scene->nodetree, &rj->scene->id);
|
||||
WM_main_add_notifier(NC_NODE|NA_EDITED, rj->scene);
|
||||
@ -648,6 +651,7 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event)
|
||||
wmJob *steve;
|
||||
RenderJob *rj;
|
||||
Image *ima;
|
||||
int jobflag;
|
||||
const short is_animation= RNA_boolean_get(op->ptr, "animation");
|
||||
const short is_write_still= RNA_boolean_get(op->ptr, "write_still");
|
||||
|
||||
@ -701,6 +705,8 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event)
|
||||
/* ensure at least 1 area shows result */
|
||||
screen_set_image_output(C, event->x, event->y);
|
||||
|
||||
jobflag= WM_JOB_EXCL_RENDER|WM_JOB_PRIORITY|WM_JOB_PROGRESS;
|
||||
|
||||
/* single layer re-render */
|
||||
if(RNA_property_is_set(op->ptr, "layer")) {
|
||||
SceneRenderLayer *rl;
|
||||
@ -712,11 +718,12 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event)
|
||||
|
||||
scn = (Scene *)BLI_findstring(&mainp->scene, scene_name, offsetof(ID, name) + 2);
|
||||
rl = (SceneRenderLayer *)BLI_findstring(&scene->r.layers, rl_name, offsetof(SceneRenderLayer, name));
|
||||
|
||||
|
||||
if (scn && rl) {
|
||||
scene = scn;
|
||||
srl = rl;
|
||||
}
|
||||
jobflag |= WM_JOB_SUSPEND;
|
||||
}
|
||||
|
||||
/* job custom data */
|
||||
@ -733,7 +740,7 @@ static int screen_render_invoke(bContext *C, wmOperator *op, wmEvent *event)
|
||||
rj->reports= op->reports;
|
||||
|
||||
/* setup job */
|
||||
steve= WM_jobs_get(CTX_wm_manager(C), CTX_wm_window(C), scene, "Render", WM_JOB_EXCL_RENDER|WM_JOB_PRIORITY|WM_JOB_PROGRESS);
|
||||
steve= WM_jobs_get(CTX_wm_manager(C), CTX_wm_window(C), scene, "Render", jobflag);
|
||||
WM_jobs_customdata(steve, rj, render_freejob);
|
||||
WM_jobs_timer(steve, 0.2, NC_SCENE|ND_RENDER_RESULT, 0);
|
||||
WM_jobs_callbacks(steve, render_startjob, NULL, NULL, render_endjob);
|
||||
|
@ -2158,6 +2158,51 @@ void NODE_OT_read_fullsamplelayers(wmOperatorType *ot)
|
||||
ot->flag= 0;
|
||||
}
|
||||
|
||||
int node_render_changed_exec(bContext *C, wmOperator *UNUSED(op))
|
||||
{
|
||||
Scene *sce= CTX_data_scene(C);
|
||||
bNode *node;
|
||||
|
||||
for(node= sce->nodetree->nodes.first; node; node= node->next) {
|
||||
if(node->id==(ID *)sce && node->need_exec) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(node) {
|
||||
SceneRenderLayer *srl= BLI_findlink(&sce->r.layers, node->custom1);
|
||||
|
||||
if(srl) {
|
||||
PointerRNA op_ptr;
|
||||
|
||||
WM_operator_properties_create(&op_ptr, "RENDER_OT_render");
|
||||
RNA_string_set(&op_ptr, "layer", srl->name);
|
||||
RNA_string_set(&op_ptr, "scene", sce->id.name+2);
|
||||
|
||||
WM_operator_name_call(C, "RENDER_OT_render", WM_OP_INVOKE_DEFAULT, &op_ptr);
|
||||
|
||||
WM_operator_properties_free(&op_ptr);
|
||||
|
||||
return OPERATOR_FINISHED;
|
||||
}
|
||||
|
||||
}
|
||||
return OPERATOR_CANCELLED;
|
||||
}
|
||||
|
||||
void NODE_OT_render_changed(wmOperatorType *ot)
|
||||
{
|
||||
|
||||
ot->name= "Render Changed Layer";
|
||||
ot->idname= "NODE_OT_render_changed";
|
||||
|
||||
ot->exec= node_render_changed_exec;
|
||||
|
||||
ot->poll= composite_node_active;
|
||||
|
||||
/* flags */
|
||||
ot->flag= 0;
|
||||
}
|
||||
|
||||
|
||||
/* ****************** Make Group operator ******************* */
|
||||
|
||||
|
@ -92,7 +92,7 @@ void node_tree_verify_groups(bNodeTree *nodetree);
|
||||
void snode_autoconnect(SpaceNode *snode, int allow_multiple, int replace);
|
||||
int node_has_hidden_sockets(bNode *node);
|
||||
void node_set_hidden_sockets(SpaceNode *snode, bNode *node, int set);
|
||||
|
||||
int node_render_changed_exec(bContext *, wmOperator *);
|
||||
|
||||
void NODE_OT_duplicate(struct wmOperatorType *ot);
|
||||
void NODE_OT_delete(struct wmOperatorType *ot);
|
||||
@ -115,6 +115,7 @@ void NODE_OT_show_cyclic_dependencies(struct wmOperatorType *ot);
|
||||
void NODE_OT_link_viewer(struct wmOperatorType *ot);
|
||||
void NODE_OT_read_fullsamplelayers(struct wmOperatorType *ot);
|
||||
void NODE_OT_read_renderlayers(struct wmOperatorType *ot);
|
||||
void NODE_OT_render_changed(struct wmOperatorType *ot);
|
||||
|
||||
void NODE_OT_backimage_move(struct wmOperatorType *ot);
|
||||
void NODE_OT_backimage_zoom(struct wmOperatorType *ot);
|
||||
|
@ -78,6 +78,7 @@ void node_operatortypes(void)
|
||||
|
||||
WM_operatortype_append(NODE_OT_read_renderlayers);
|
||||
WM_operatortype_append(NODE_OT_read_fullsamplelayers);
|
||||
WM_operatortype_append(NODE_OT_render_changed);
|
||||
|
||||
WM_operatortype_append(NODE_OT_backimage_move);
|
||||
WM_operatortype_append(NODE_OT_backimage_zoom);
|
||||
@ -170,6 +171,8 @@ void node_keymap(struct wmKeyConfig *keyconf)
|
||||
|
||||
WM_keymap_add_item(keymap, "NODE_OT_read_renderlayers", RKEY, KM_PRESS, KM_CTRL, 0);
|
||||
WM_keymap_add_item(keymap, "NODE_OT_read_fullsamplelayers", RKEY, KM_PRESS, KM_SHIFT, 0);
|
||||
WM_keymap_add_item(keymap, "NODE_OT_render_changed", ZKEY, KM_PRESS, 0, 0);
|
||||
|
||||
|
||||
transform_keymap_for_space(keyconf, keymap, SPACE_NODE);
|
||||
}
|
||||
|
@ -172,13 +172,21 @@ static void node_area_listener(ScrArea *sa, wmNotifier *wmn)
|
||||
case ND_FRAME:
|
||||
ED_area_tag_refresh(sa);
|
||||
break;
|
||||
case ND_TRANSFORM_DONE:
|
||||
if(type==NTREE_COMPOSIT) {
|
||||
if(snode->flag & SNODE_AUTO_RENDER) {
|
||||
snode->recalc= 1;
|
||||
ED_area_tag_refresh(sa);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case NC_WM:
|
||||
if(wmn->data==ND_FILEREAD)
|
||||
ED_area_tag_refresh(sa);
|
||||
break;
|
||||
|
||||
|
||||
/* future: add ID checks? */
|
||||
case NC_MATERIAL:
|
||||
if(type==NTREE_SHADER) {
|
||||
@ -212,7 +220,7 @@ static void node_area_listener(ScrArea *sa, wmNotifier *wmn)
|
||||
|
||||
case NC_IMAGE:
|
||||
if (wmn->action == NA_EDITED) {
|
||||
if(snode->treetype==NTREE_COMPOSIT) {
|
||||
if(type==NTREE_COMPOSIT) {
|
||||
Scene *scene= wmn->window->screen->scene;
|
||||
|
||||
/* note that NodeTagIDChanged is alredy called by BKE_image_signal() on all
|
||||
@ -241,8 +249,15 @@ static void node_area_refresh(const struct bContext *C, struct ScrArea *sa)
|
||||
}
|
||||
else if(snode->treetype==NTREE_COMPOSIT) {
|
||||
Scene *scene= (Scene *)snode->id;
|
||||
if(scene->use_nodes)
|
||||
snode_composite_job(C, sa);
|
||||
if(scene->use_nodes) {
|
||||
/* recalc is set on 3d view changes for auto compo */
|
||||
if(snode->recalc) {
|
||||
snode->recalc= 0;
|
||||
node_render_changed_exec((struct bContext*)C, NULL);
|
||||
}
|
||||
else
|
||||
snode_composite_job(C, sa);
|
||||
}
|
||||
}
|
||||
else if(snode->treetype==NTREE_TEXTURE) {
|
||||
Tex *tex= (Tex *)snode->id;
|
||||
|
@ -338,7 +338,7 @@ static void viewRedrawForce(const bContext *C, TransInfo *t)
|
||||
}
|
||||
}
|
||||
|
||||
static void viewRedrawPost(TransInfo *t)
|
||||
static void viewRedrawPost(bContext *C, TransInfo *t)
|
||||
{
|
||||
ED_area_headerprint(t->sa, NULL);
|
||||
|
||||
@ -346,6 +346,10 @@ static void viewRedrawPost(TransInfo *t)
|
||||
/* if autokeying is enabled, send notifiers that keyframes were added */
|
||||
if (IS_AUTOKEY_ON(t->scene))
|
||||
WM_main_add_notifier(NC_ANIMATION|ND_KEYFRAME|NA_EDITED, NULL);
|
||||
|
||||
/* XXX temp, first hack to get auto-render in compositor work (ton) */
|
||||
WM_event_add_notifier(C, NC_SCENE|ND_TRANSFORM_DONE, CTX_data_scene(C));
|
||||
|
||||
}
|
||||
|
||||
#if 0 // TRANSFORM_FIX_ME
|
||||
@ -1817,7 +1821,7 @@ int transformEnd(bContext *C, TransInfo *t)
|
||||
postTrans(C, t);
|
||||
|
||||
/* send events out for redraws */
|
||||
viewRedrawPost(t);
|
||||
viewRedrawPost(C, t);
|
||||
|
||||
/* Undo as last, certainly after special_trans_update! */
|
||||
|
||||
|
@ -396,8 +396,9 @@ typedef struct SpaceNode {
|
||||
float mx, my; /* mousepos for drawing socketless link */
|
||||
|
||||
struct bNodeTree *nodetree, *edittree;
|
||||
int treetype; /* treetype: as same nodetree->type */
|
||||
short texfrom, pad; /* texfrom object, world or brush */
|
||||
int treetype; /* treetype: as same nodetree->type */
|
||||
short texfrom; /* texfrom object, world or brush */
|
||||
short recalc; /* currently on 0/1, for auto compo */
|
||||
|
||||
struct bGPdata *gpd; /* grease-pencil data */
|
||||
} SpaceNode;
|
||||
@ -407,6 +408,7 @@ typedef struct SpaceNode {
|
||||
#define SNODE_DISPGP 4
|
||||
#define SNODE_USE_ALPHA 8
|
||||
#define SNODE_SHOW_ALPHA 16
|
||||
#define SNODE_AUTO_RENDER 32
|
||||
|
||||
/* snode->texfrom */
|
||||
#define SNODE_TEX_OBJECT 0
|
||||
|
@ -2263,6 +2263,11 @@ static void rna_def_space_node(BlenderRNA *brna)
|
||||
RNA_def_property_ui_text(prop, "Backdrop", "Use active Viewer Node output as backdrop for compositing nodes");
|
||||
RNA_def_property_update(prop, NC_SPACE|ND_SPACE_NODE_VIEW, NULL);
|
||||
|
||||
prop= RNA_def_property(srna, "use_auto_render", PROP_BOOLEAN, PROP_NONE);
|
||||
RNA_def_property_boolean_sdna(prop, NULL, "flag", SNODE_AUTO_RENDER);
|
||||
RNA_def_property_ui_text(prop, "Auto Render", "Re-render and composite changed layer on 3D edits");
|
||||
RNA_def_property_update(prop, NC_SPACE|ND_SPACE_NODE_VIEW, NULL);
|
||||
|
||||
prop= RNA_def_property(srna, "backdrop_zoom", PROP_FLOAT, PROP_NONE);
|
||||
RNA_def_property_float_sdna(prop, NULL, "zoom");
|
||||
RNA_def_property_range(prop, 0.01f, FLT_MAX);
|
||||
|
@ -193,6 +193,7 @@ typedef struct wmNotifier {
|
||||
#define ND_TOOLSETTINGS (15<<16)
|
||||
#define ND_LAYER (16<<16)
|
||||
#define ND_FRAME_RANGE (17<<16)
|
||||
#define ND_TRANSFORM_DONE (18<<16)
|
||||
#define ND_WORLD (92<<16)
|
||||
#define ND_LAYER_CONTENT (101<<16)
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user