2018-01-29 18:16:11 +01:00
|
|
|
/*
|
|
|
|
* This program is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU General Public License
|
|
|
|
* as published by the Free Software Foundation; either version 2
|
|
|
|
* of the License, or (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program; if not, write to the Free Software Foundation,
|
|
|
|
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
|
|
*
|
2019-01-23 11:29:18 +11:00
|
|
|
* Copyright 2016, Blender Foundation.
|
2018-01-29 18:16:11 +01:00
|
|
|
*/
|
|
|
|
|
2019-02-18 08:08:12 +11:00
|
|
|
/** \file
|
|
|
|
* \ingroup draw_engine
|
2018-01-29 18:16:11 +01:00
|
|
|
*/
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Render functions for final render outputs.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include "DRW_engine.h"
|
|
|
|
#include "DRW_render.h"
|
|
|
|
|
2018-02-01 21:38:16 +01:00
|
|
|
#include "DNA_node_types.h"
|
2018-03-13 04:25:50 +01:00
|
|
|
#include "DNA_object_types.h"
|
2018-02-01 21:38:16 +01:00
|
|
|
|
2020-01-30 15:06:56 +01:00
|
|
|
#include "BKE_global.h"
|
2018-12-18 18:18:00 +01:00
|
|
|
#include "BKE_object.h"
|
2018-10-31 18:31:14 +01:00
|
|
|
|
2018-01-29 18:16:11 +01:00
|
|
|
#include "BLI_rand.h"
|
2018-02-23 13:26:28 -03:00
|
|
|
#include "BLI_rect.h"
|
2018-01-29 18:16:11 +01:00
|
|
|
|
|
|
|
#include "DEG_depsgraph_query.h"
|
|
|
|
|
2020-09-07 19:35:56 +02:00
|
|
|
#include "GPU_capabilities.h"
|
2020-03-19 09:33:03 +01:00
|
|
|
#include "GPU_framebuffer.h"
|
2018-10-31 12:28:59 +01:00
|
|
|
#include "GPU_state.h"
|
2018-01-29 18:16:11 +01:00
|
|
|
|
|
|
|
#include "RE_pipeline.h"
|
|
|
|
|
|
|
|
#include "eevee_private.h"
|
|
|
|
|
2020-02-22 17:08:37 +01:00
|
|
|
/* Return true if init properly. */
|
2020-08-07 00:59:14 +02:00
|
|
|
bool EEVEE_render_init(EEVEE_Data *ved, RenderEngine *engine, struct Depsgraph *depsgraph)
|
2018-01-29 18:16:11 +01:00
|
|
|
{
|
|
|
|
EEVEE_Data *vedata = (EEVEE_Data *)ved;
|
|
|
|
EEVEE_StorageList *stl = vedata->stl;
|
|
|
|
EEVEE_TextureList *txl = vedata->txl;
|
|
|
|
EEVEE_FramebufferList *fbl = vedata->fbl;
|
2020-08-07 00:59:14 +02:00
|
|
|
Scene *scene = DEG_get_evaluated_scene(depsgraph);
|
2018-10-31 18:31:14 +01:00
|
|
|
const float *size_orig = DRW_viewport_size_get();
|
2020-08-07 00:59:14 +02:00
|
|
|
float size_final[2];
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Init default FB and render targets:
|
|
|
|
* In render mode the default framebuffer is not generated
|
|
|
|
* because there is no viewport. So we need to manually create it or
|
|
|
|
* not use it. For code clarity we just allocate it make use of it. */
|
|
|
|
DefaultFramebufferList *dfbl = DRW_viewport_framebuffer_list_get();
|
|
|
|
DefaultTextureList *dtxl = DRW_viewport_texture_list_get();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-10-31 18:31:14 +01:00
|
|
|
/* Alloc transient data. */
|
|
|
|
if (!stl->g_data) {
|
|
|
|
stl->g_data = MEM_callocN(sizeof(*stl->g_data), __func__);
|
|
|
|
}
|
|
|
|
EEVEE_PrivateData *g_data = stl->g_data;
|
|
|
|
g_data->background_alpha = DRW_state_draw_background() ? 1.0f : 0.0f;
|
|
|
|
g_data->valid_double_buffer = 0;
|
|
|
|
copy_v2_v2(g_data->size_orig, size_orig);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-08-07 00:59:14 +02:00
|
|
|
float *camtexcofac = g_data->camtexcofac;
|
|
|
|
if (scene->eevee.flag & SCE_EEVEE_OVERSCAN) {
|
|
|
|
g_data->overscan = scene->eevee.overscan / 100.0f;
|
|
|
|
g_data->overscan_pixels = roundf(max_ff(size_orig[0], size_orig[1]) * g_data->overscan);
|
|
|
|
|
|
|
|
madd_v2_v2v2fl(size_final, size_orig, (float[2]){2.0f, 2.0f}, g_data->overscan_pixels);
|
|
|
|
|
|
|
|
camtexcofac[0] = size_final[0] / size_orig[0];
|
|
|
|
camtexcofac[1] = size_final[1] / size_orig[1];
|
|
|
|
|
|
|
|
camtexcofac[2] = -camtexcofac[0] * g_data->overscan_pixels / size_final[0];
|
|
|
|
camtexcofac[3] = -camtexcofac[1] * g_data->overscan_pixels / size_final[1];
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
copy_v2_v2(size_final, size_orig);
|
|
|
|
g_data->overscan = 0.0f;
|
|
|
|
g_data->overscan_pixels = 0.0f;
|
|
|
|
copy_v4_fl4(camtexcofac, 1.0f, 1.0f, 0.0f, 0.0f);
|
|
|
|
}
|
|
|
|
|
2020-08-07 22:36:11 +10:00
|
|
|
const int final_res[2] = {
|
|
|
|
size_orig[0] + g_data->overscan_pixels * 2.0f,
|
|
|
|
size_orig[1] + g_data->overscan_pixels * 2.0f,
|
|
|
|
};
|
2020-01-30 15:06:56 +01:00
|
|
|
|
|
|
|
int max_dim = max_ii(final_res[0], final_res[1]);
|
|
|
|
if (max_dim > GPU_max_texture_size()) {
|
|
|
|
char error_msg[128];
|
|
|
|
BLI_snprintf(error_msg,
|
|
|
|
sizeof(error_msg),
|
|
|
|
"Error: Reported texture size limit (%dpx) is lower than output size (%dpx).",
|
|
|
|
GPU_max_texture_size(),
|
|
|
|
max_dim);
|
|
|
|
RE_engine_set_error_message(engine, error_msg);
|
|
|
|
G.is_break = true;
|
2020-02-22 17:08:37 +01:00
|
|
|
return false;
|
2020-01-30 15:06:56 +01:00
|
|
|
}
|
|
|
|
|
2019-08-01 13:53:25 +10:00
|
|
|
/* XXX overriding viewport size. Simplify things but is not really 100% safe. */
|
2020-01-30 15:06:56 +01:00
|
|
|
DRW_render_viewport_size_set(final_res);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-03-25 17:46:48 +02:00
|
|
|
/* TODO 32 bit depth */
|
2019-03-20 18:17:16 +11:00
|
|
|
DRW_texture_ensure_fullscreen_2d(&dtxl->depth, GPU_DEPTH24_STENCIL8, 0);
|
|
|
|
DRW_texture_ensure_fullscreen_2d(&txl->color, GPU_RGBA32F, DRW_TEX_FILTER | DRW_TEX_MIPMAP);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_framebuffer_ensure_config(
|
|
|
|
&dfbl->default_fb,
|
|
|
|
{GPU_ATTACHMENT_TEXTURE(dtxl->depth), GPU_ATTACHMENT_TEXTURE(txl->color)});
|
|
|
|
GPU_framebuffer_ensure_config(
|
|
|
|
&fbl->main_fb, {GPU_ATTACHMENT_TEXTURE(dtxl->depth), GPU_ATTACHMENT_TEXTURE(txl->color)});
|
|
|
|
GPU_framebuffer_ensure_config(&fbl->main_color_fb,
|
|
|
|
{GPU_ATTACHMENT_NONE, GPU_ATTACHMENT_TEXTURE(txl->color)});
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-08-12 18:04:08 +02:00
|
|
|
/* Camera could change because of Motion blur. */
|
|
|
|
g_data->cam_original_ob = RE_GetCamera(engine->re);
|
|
|
|
|
2020-08-06 19:58:35 +02:00
|
|
|
return true;
|
|
|
|
}
|
2020-06-23 13:59:55 +02:00
|
|
|
|
2020-08-06 19:58:35 +02:00
|
|
|
void EEVEE_render_modules_init(EEVEE_Data *vedata,
|
|
|
|
RenderEngine *engine,
|
|
|
|
struct Depsgraph *depsgraph)
|
|
|
|
{
|
|
|
|
EEVEE_ViewLayerData *sldata = EEVEE_view_layer_data_ensure();
|
|
|
|
EEVEE_StorageList *stl = vedata->stl;
|
2020-08-12 18:04:08 +02:00
|
|
|
EEVEE_PrivateData *g_data = vedata->stl->g_data;
|
2020-08-06 19:58:35 +02:00
|
|
|
EEVEE_FramebufferList *fbl = vedata->fbl;
|
2020-06-23 13:59:55 +02:00
|
|
|
/* TODO(sergey): Shall render hold pointer to an evaluated camera instead? */
|
2020-08-12 18:04:08 +02:00
|
|
|
struct Object *ob_camera_eval = DEG_get_evaluated_object(depsgraph, g_data->cam_original_ob);
|
2020-08-06 19:58:35 +02:00
|
|
|
EEVEE_render_view_sync(vedata, engine, depsgraph);
|
2020-06-23 13:59:55 +02:00
|
|
|
|
|
|
|
/* `EEVEE_renderpasses_init` will set the active render passes used by `EEVEE_effects_init`.
|
|
|
|
* `EEVEE_effects_init` needs to go second for TAA. */
|
|
|
|
EEVEE_renderpasses_init(vedata);
|
|
|
|
EEVEE_effects_init(sldata, vedata, ob_camera_eval, false);
|
|
|
|
EEVEE_materials_init(sldata, vedata, stl, fbl);
|
|
|
|
EEVEE_shadows_init(sldata);
|
|
|
|
EEVEE_lightprobes_init(sldata, vedata);
|
|
|
|
}
|
|
|
|
|
|
|
|
void EEVEE_render_view_sync(EEVEE_Data *vedata, RenderEngine *engine, struct Depsgraph *depsgraph)
|
|
|
|
{
|
|
|
|
EEVEE_PrivateData *g_data = vedata->stl->g_data;
|
|
|
|
|
2021-02-14 20:58:04 +11:00
|
|
|
/* Set the perspective & view matrix. */
|
2019-05-21 12:34:48 +02:00
|
|
|
float winmat[4][4], viewmat[4][4], viewinv[4][4];
|
2018-03-21 16:38:01 +01:00
|
|
|
/* TODO(sergey): Shall render hold pointer to an evaluated camera instead? */
|
2020-08-12 18:04:08 +02:00
|
|
|
struct Object *ob_camera_eval = DEG_get_evaluated_object(depsgraph, g_data->cam_original_ob);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-03-27 10:05:08 +01:00
|
|
|
RE_GetCameraWindow(engine->re, ob_camera_eval, winmat);
|
2020-08-02 17:17:31 +10:00
|
|
|
RE_GetCameraWindowWithOverscan(engine->re, g_data->overscan, winmat);
|
2019-05-21 12:34:48 +02:00
|
|
|
RE_GetCameraModelMatrix(engine->re, ob_camera_eval, viewinv);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-05-21 12:34:48 +02:00
|
|
|
invert_m4_m4(viewmat, viewinv);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-05-21 12:34:48 +02:00
|
|
|
DRWView *view = DRW_view_create(viewmat, winmat, NULL, NULL, NULL);
|
2020-06-19 17:02:55 +02:00
|
|
|
DRW_view_reset();
|
2019-05-21 12:34:48 +02:00
|
|
|
DRW_view_default_set(view);
|
|
|
|
DRW_view_set_active(view);
|
2020-08-06 19:58:35 +02:00
|
|
|
|
2020-08-07 00:59:14 +02:00
|
|
|
DRW_view_camtexco_set(view, g_data->camtexcofac);
|
2020-06-23 13:59:55 +02:00
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-06-23 13:59:55 +02:00
|
|
|
void EEVEE_render_cache_init(EEVEE_ViewLayerData *sldata, EEVEE_Data *vedata)
|
|
|
|
{
|
2020-08-06 19:58:35 +02:00
|
|
|
EEVEE_view_layer_data_ensure();
|
2018-01-29 18:16:11 +01:00
|
|
|
EEVEE_bloom_cache_init(sldata, vedata);
|
|
|
|
EEVEE_depth_of_field_cache_init(sldata, vedata);
|
|
|
|
EEVEE_effects_cache_init(sldata, vedata);
|
|
|
|
EEVEE_lightprobes_cache_init(sldata, vedata);
|
2018-03-01 19:27:38 +01:00
|
|
|
EEVEE_lights_cache_init(sldata, vedata);
|
2018-03-06 02:19:28 +01:00
|
|
|
EEVEE_materials_cache_init(sldata, vedata);
|
2018-01-29 18:16:11 +01:00
|
|
|
EEVEE_motion_blur_cache_init(sldata, vedata);
|
|
|
|
EEVEE_occlusion_cache_init(sldata, vedata);
|
|
|
|
EEVEE_screen_raytrace_cache_init(sldata, vedata);
|
|
|
|
EEVEE_subsurface_cache_init(sldata, vedata);
|
|
|
|
EEVEE_temporal_sampling_cache_init(sldata, vedata);
|
|
|
|
EEVEE_volumes_cache_init(sldata, vedata);
|
2020-12-04 08:28:43 +01:00
|
|
|
EEVEE_cryptomatte_cache_init(sldata, vedata);
|
2018-01-29 18:16:11 +01:00
|
|
|
}
|
|
|
|
|
2018-07-10 15:02:25 +02:00
|
|
|
/* Used by light cache. in this case engine is NULL. */
|
2018-01-29 18:16:11 +01:00
|
|
|
void EEVEE_render_cache(void *vedata,
|
|
|
|
struct Object *ob,
|
2018-03-13 04:25:50 +01:00
|
|
|
struct RenderEngine *engine,
|
2020-03-17 16:27:08 +01:00
|
|
|
struct Depsgraph *depsgraph)
|
2018-01-29 18:16:11 +01:00
|
|
|
{
|
|
|
|
EEVEE_ViewLayerData *sldata = EEVEE_view_layer_data_ensure();
|
2020-12-04 08:28:43 +01:00
|
|
|
EEVEE_Data *data = vedata;
|
|
|
|
EEVEE_StorageList *stl = data->stl;
|
|
|
|
EEVEE_PrivateData *g_data = stl->g_data;
|
2018-07-10 15:02:25 +02:00
|
|
|
EEVEE_LightProbesInfo *pinfo = sldata->probes;
|
2018-06-07 18:58:06 +02:00
|
|
|
bool cast_shadow = false;
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-12-04 08:28:43 +01:00
|
|
|
const bool do_cryptomatte = (engine != NULL) &&
|
|
|
|
((g_data->render_passes & EEVEE_RENDER_PASS_CRYPTOMATTE) != 0);
|
|
|
|
|
2020-06-23 13:59:55 +02:00
|
|
|
eevee_id_update(vedata, &ob->id);
|
|
|
|
|
2018-07-10 15:02:25 +02:00
|
|
|
if (pinfo->vis_data.collection) {
|
|
|
|
/* Used for rendering probe with visibility groups. */
|
|
|
|
bool ob_vis = BKE_collection_has_object_recursive(pinfo->vis_data.collection, ob);
|
|
|
|
ob_vis = (pinfo->vis_data.invert) ? !ob_vis : ob_vis;
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-07-10 15:02:25 +02:00
|
|
|
if (!ob_vis) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-03-28 23:24:25 +01:00
|
|
|
/* Don't print dupli objects as this can be very verbose and
|
|
|
|
* increase the render time on Windows because of slow windows term.
|
|
|
|
* (see T59649) */
|
|
|
|
if (engine && (ob->base_flag & BASE_FROM_DUPLI) == 0) {
|
2018-07-10 15:02:25 +02:00
|
|
|
char info[42];
|
|
|
|
BLI_snprintf(info, sizeof(info), "Syncing %s", ob->id.name + 2);
|
|
|
|
RE_engine_update_stats(engine, NULL, info);
|
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-12-18 18:18:00 +01:00
|
|
|
const int ob_visibility = DRW_object_visibility_in_active_context(ob);
|
|
|
|
if (ob_visibility & OB_VISIBLE_PARTICLES) {
|
2020-02-27 15:01:33 +01:00
|
|
|
EEVEE_particle_hair_cache_populate(vedata, sldata, ob, &cast_shadow);
|
2020-12-04 08:28:43 +01:00
|
|
|
if (do_cryptomatte) {
|
|
|
|
EEVEE_cryptomatte_particle_hair_cache_populate(data, sldata, ob);
|
|
|
|
}
|
2018-01-29 18:16:11 +01:00
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-12-18 18:18:00 +01:00
|
|
|
if (ob_visibility & OB_VISIBLE_SELF) {
|
2018-06-11 08:37:56 +02:00
|
|
|
if (ELEM(ob->type, OB_MESH, OB_CURVE, OB_SURF, OB_FONT, OB_MBALL)) {
|
2018-06-07 18:58:06 +02:00
|
|
|
EEVEE_materials_cache_populate(vedata, sldata, ob, &cast_shadow);
|
2020-12-04 08:28:43 +01:00
|
|
|
if (do_cryptomatte) {
|
|
|
|
EEVEE_cryptomatte_cache_populate(data, sldata, ob);
|
|
|
|
}
|
2018-06-07 18:58:06 +02:00
|
|
|
}
|
2020-03-17 16:27:08 +01:00
|
|
|
else if (ob->type == OB_HAIR) {
|
|
|
|
EEVEE_object_hair_cache_populate(vedata, sldata, ob, &cast_shadow);
|
2020-12-04 08:28:43 +01:00
|
|
|
if (do_cryptomatte) {
|
|
|
|
EEVEE_cryptomatte_object_hair_cache_populate(data, sldata, ob);
|
|
|
|
}
|
2020-03-17 16:27:08 +01:00
|
|
|
}
|
|
|
|
else if (ob->type == OB_VOLUME) {
|
|
|
|
Scene *scene = DEG_get_evaluated_scene(depsgraph);
|
|
|
|
EEVEE_volumes_cache_object_add(sldata, vedata, scene, ob);
|
|
|
|
}
|
2018-06-07 18:58:06 +02:00
|
|
|
else if (ob->type == OB_LIGHTPROBE) {
|
2018-07-10 15:02:25 +02:00
|
|
|
EEVEE_lightprobes_cache_add(sldata, vedata, ob);
|
2018-06-07 18:58:06 +02:00
|
|
|
}
|
|
|
|
else if (ob->type == OB_LAMP) {
|
|
|
|
EEVEE_lights_cache_add(sldata, ob);
|
2018-01-29 18:16:11 +01:00
|
|
|
}
|
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-06-07 18:58:06 +02:00
|
|
|
if (cast_shadow) {
|
2019-08-22 16:04:25 +02:00
|
|
|
EEVEE_shadows_caster_register(sldata, ob);
|
2018-01-29 18:16:11 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-11-07 13:14:15 +01:00
|
|
|
static void eevee_render_color_result(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
const char *render_pass_name,
|
|
|
|
int num_channels,
|
|
|
|
GPUFrameBuffer *framebuffer,
|
|
|
|
EEVEE_Data *vedata)
|
2018-01-29 18:16:11 +01:00
|
|
|
{
|
2019-11-07 13:14:15 +01:00
|
|
|
RenderPass *rp = RE_pass_find_by_name(rl, render_pass_name, viewname);
|
2020-02-20 14:53:53 +01:00
|
|
|
if (rp == NULL) {
|
|
|
|
return;
|
|
|
|
}
|
2019-11-07 13:14:15 +01:00
|
|
|
GPU_framebuffer_bind(framebuffer);
|
|
|
|
GPU_framebuffer_read_color(framebuffer,
|
2019-01-04 19:08:09 +11:00
|
|
|
vedata->stl->g_data->overscan_pixels + rect->xmin,
|
|
|
|
vedata->stl->g_data->overscan_pixels + rect->ymin,
|
|
|
|
BLI_rcti_size_x(rect),
|
|
|
|
BLI_rcti_size_y(rect),
|
2019-11-07 13:14:15 +01:00
|
|
|
num_channels,
|
2019-01-04 19:08:09 +11:00
|
|
|
0,
|
2020-07-16 02:50:55 +02:00
|
|
|
GPU_DATA_FLOAT,
|
2019-01-04 19:08:09 +11:00
|
|
|
rp->rect);
|
2018-01-31 01:09:38 +01:00
|
|
|
}
|
|
|
|
|
2019-11-07 13:14:15 +01:00
|
|
|
static void eevee_render_result_combined(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *UNUSED(sldata))
|
|
|
|
{
|
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_COMBINED, 4, vedata->stl->effects->final_fb, vedata);
|
|
|
|
}
|
|
|
|
|
2018-01-31 01:09:38 +01:00
|
|
|
static void eevee_render_result_normal(RenderLayer *rl,
|
2018-02-23 13:26:28 -03:00
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
2018-01-31 01:09:38 +01:00
|
|
|
EEVEE_Data *vedata,
|
2019-11-07 13:14:15 +01:00
|
|
|
EEVEE_ViewLayerData *sldata)
|
2018-01-31 01:09:38 +01:00
|
|
|
{
|
2019-11-07 13:14:15 +01:00
|
|
|
const int current_sample = vedata->stl->effects->taa_current_sample;
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-01-31 01:09:38 +01:00
|
|
|
/* Only read the center texel. */
|
2019-11-07 13:14:15 +01:00
|
|
|
if (current_sample > 1) {
|
2018-01-31 01:09:38 +01:00
|
|
|
return;
|
2019-01-25 07:10:13 +11:00
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_NORMAL) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_NORMAL, 0);
|
2019-11-07 13:14:15 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_NORMAL, 3, vedata->fbl->renderpass_fb, vedata);
|
2018-01-31 01:09:38 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_z(RenderLayer *rl,
|
2018-02-23 13:26:28 -03:00
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
2018-01-31 01:09:38 +01:00
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
2019-11-07 13:14:15 +01:00
|
|
|
const int current_sample = vedata->stl->effects->taa_current_sample;
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-01-31 01:09:38 +01:00
|
|
|
/* Only read the center texel. */
|
2019-11-07 13:14:15 +01:00
|
|
|
if (current_sample > 1) {
|
2018-01-31 01:09:38 +01:00
|
|
|
return;
|
2019-01-25 07:10:13 +11:00
|
|
|
}
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_Z) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_Z, 0);
|
2019-11-07 13:14:15 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_Z, 1, vedata->fbl->renderpass_fb, vedata);
|
2018-01-31 01:09:38 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-02-01 18:09:06 +01:00
|
|
|
static void eevee_render_result_mist(RenderLayer *rl,
|
2018-02-23 13:26:28 -03:00
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
2018-03-08 15:22:57 +01:00
|
|
|
EEVEE_Data *vedata,
|
2019-11-07 13:14:15 +01:00
|
|
|
EEVEE_ViewLayerData *sldata)
|
2018-02-01 18:09:06 +01:00
|
|
|
{
|
2020-02-20 14:53:53 +01:00
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_MIST) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_MIST, 0);
|
2019-11-07 13:14:15 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_MIST, 1, vedata->fbl->renderpass_fb, vedata);
|
2018-02-01 18:09:06 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
static void eevee_render_result_shadow(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_SHADOW) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_SHADOW, 0);
|
2020-02-20 14:53:53 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_SHADOW, 3, vedata->fbl->renderpass_fb, vedata);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-02-03 00:00:19 +01:00
|
|
|
static void eevee_render_result_occlusion(RenderLayer *rl,
|
2018-02-23 13:26:28 -03:00
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
2018-03-08 15:22:57 +01:00
|
|
|
EEVEE_Data *vedata,
|
2019-11-07 13:14:15 +01:00
|
|
|
EEVEE_ViewLayerData *sldata)
|
2018-02-03 00:00:19 +01:00
|
|
|
{
|
2020-02-20 14:53:53 +01:00
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_AO) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_AO, 0);
|
2019-11-07 13:14:15 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_AO, 3, vedata->fbl->renderpass_fb, vedata);
|
2018-02-03 00:00:19 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
static void eevee_render_result_bloom(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
if ((vedata->stl->effects->enabled_effects & EFFECT_BLOOM) == 0) {
|
|
|
|
/* Bloom is not enabled. */
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_BLOOM) != 0) {
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_BLOOM, 0);
|
2020-02-20 14:53:53 +01:00
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, RE_PASSNAME_BLOOM, 3, vedata->fbl->renderpass_fb, vedata);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
#define EEVEE_RENDER_RESULT_MATERIAL_PASS(pass_name, eevee_pass_type) \
|
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_##eevee_pass_type) != 0) { \
|
2020-12-04 08:13:54 +01:00
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_##eevee_pass_type, 0); \
|
2020-02-20 14:53:53 +01:00
|
|
|
eevee_render_color_result( \
|
|
|
|
rl, viewname, rect, RE_PASSNAME_##pass_name, 3, vedata->fbl->renderpass_fb, vedata); \
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_diffuse_color(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(DIFFUSE_COLOR, DIFFUSE_COLOR)
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_diffuse_direct(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(DIFFUSE_DIRECT, DIFFUSE_LIGHT)
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_specular_color(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(GLOSSY_COLOR, SPECULAR_COLOR)
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_specular_direct(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(GLOSSY_DIRECT, SPECULAR_LIGHT)
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_emission(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(EMIT, EMIT)
|
|
|
|
}
|
|
|
|
|
|
|
|
static void eevee_render_result_environment(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(ENVIRONMENT, ENVIRONMENT)
|
|
|
|
}
|
|
|
|
|
2020-12-14 09:05:16 +01:00
|
|
|
static void eevee_render_result_volume_light(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
2020-02-20 14:53:53 +01:00
|
|
|
{
|
2020-12-14 09:05:16 +01:00
|
|
|
EEVEE_RENDER_RESULT_MATERIAL_PASS(VOLUME_LIGHT, VOLUME_LIGHT)
|
2020-02-20 14:53:53 +01:00
|
|
|
}
|
|
|
|
|
2020-12-04 08:13:54 +01:00
|
|
|
static void eevee_render_result_aovs(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_AOV) != 0) {
|
|
|
|
const DRWContextState *draw_ctx = DRW_context_state_get();
|
|
|
|
ViewLayer *view_layer = draw_ctx->view_layer;
|
|
|
|
int aov_index = 0;
|
|
|
|
LISTBASE_FOREACH (ViewLayerAOV *, aov, &view_layer->aovs) {
|
|
|
|
if ((aov->flag & AOV_CONFLICT) != 0) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
EEVEE_renderpasses_postprocess(sldata, vedata, EEVEE_RENDER_PASS_AOV, aov_index);
|
|
|
|
switch (aov->type) {
|
|
|
|
case AOV_TYPE_COLOR:
|
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, aov->name, 4, vedata->fbl->renderpass_fb, vedata);
|
|
|
|
break;
|
|
|
|
case AOV_TYPE_VALUE:
|
|
|
|
eevee_render_color_result(
|
|
|
|
rl, viewname, rect, aov->name, 1, vedata->fbl->renderpass_fb, vedata);
|
|
|
|
}
|
|
|
|
aov_index++;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
#undef EEVEE_RENDER_RESULT_MATERIAL_PASS
|
|
|
|
|
2020-12-04 08:28:43 +01:00
|
|
|
static void eevee_render_result_cryptomatte(RenderLayer *rl,
|
|
|
|
const char *viewname,
|
|
|
|
const rcti *rect,
|
|
|
|
EEVEE_Data *vedata,
|
|
|
|
EEVEE_ViewLayerData *sldata)
|
|
|
|
{
|
|
|
|
if ((vedata->stl->g_data->render_passes & EEVEE_RENDER_PASS_CRYPTOMATTE) != 0) {
|
|
|
|
EEVEE_cryptomatte_render_result(rl, viewname, rect, vedata, sldata);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-02-02 00:50:18 +01:00
|
|
|
static void eevee_render_draw_background(EEVEE_Data *vedata)
|
|
|
|
{
|
|
|
|
EEVEE_FramebufferList *fbl = vedata->fbl;
|
2018-03-25 17:46:48 +02:00
|
|
|
EEVEE_StorageList *stl = vedata->stl;
|
2018-02-02 00:50:18 +01:00
|
|
|
EEVEE_PassList *psl = vedata->psl;
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-02-02 00:50:18 +01:00
|
|
|
/* Prevent background to write to data buffers.
|
|
|
|
* NOTE : This also make sure the textures are bound
|
|
|
|
* to the right double buffer. */
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_framebuffer_ensure_config(&fbl->main_fb,
|
|
|
|
{GPU_ATTACHMENT_LEAVE,
|
|
|
|
GPU_ATTACHMENT_LEAVE,
|
|
|
|
GPU_ATTACHMENT_NONE,
|
|
|
|
GPU_ATTACHMENT_NONE,
|
|
|
|
GPU_ATTACHMENT_NONE,
|
|
|
|
GPU_ATTACHMENT_NONE});
|
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-06-02 16:58:07 +02:00
|
|
|
DRW_draw_pass(psl->background_ps);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_framebuffer_ensure_config(&fbl->main_fb,
|
|
|
|
{GPU_ATTACHMENT_LEAVE,
|
|
|
|
GPU_ATTACHMENT_LEAVE,
|
|
|
|
GPU_ATTACHMENT_TEXTURE(stl->effects->ssr_normal_input),
|
|
|
|
GPU_ATTACHMENT_TEXTURE(stl->effects->ssr_specrough_input),
|
2019-08-22 16:04:25 +02:00
|
|
|
GPU_ATTACHMENT_TEXTURE(stl->effects->sss_irradiance),
|
|
|
|
GPU_ATTACHMENT_TEXTURE(stl->effects->sss_radius),
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_ATTACHMENT_TEXTURE(stl->effects->sss_albedo)});
|
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
2018-02-02 00:50:18 +01:00
|
|
|
}
|
|
|
|
|
2018-02-23 13:26:28 -03:00
|
|
|
void EEVEE_render_draw(EEVEE_Data *vedata, RenderEngine *engine, RenderLayer *rl, const rcti *rect)
|
2018-01-31 01:09:38 +01:00
|
|
|
{
|
2018-02-20 10:14:23 -03:00
|
|
|
const char *viewname = RE_GetActiveRenderView(engine->re);
|
2018-01-29 18:16:11 +01:00
|
|
|
EEVEE_PassList *psl = vedata->psl;
|
|
|
|
EEVEE_StorageList *stl = vedata->stl;
|
|
|
|
EEVEE_FramebufferList *fbl = vedata->fbl;
|
|
|
|
DefaultTextureList *dtxl = DRW_viewport_texture_list_get();
|
|
|
|
EEVEE_ViewLayerData *sldata = EEVEE_view_layer_data_ensure();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-01-29 07:46:25 +11:00
|
|
|
/* Push instances attributes to the GPU. */
|
2018-02-14 18:59:15 +01:00
|
|
|
DRW_render_instance_buffer_finish();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-06-07 18:58:06 +02:00
|
|
|
/* Need to be called after DRW_render_instance_buffer_finish() */
|
2021-02-05 16:23:34 +11:00
|
|
|
/* Also we weed to have a correct FBO bound for DRW_hair_update */
|
2018-06-13 22:20:48 +02:00
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
2018-06-07 18:58:06 +02:00
|
|
|
DRW_hair_update();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-06-23 13:59:55 +02:00
|
|
|
/* Sort transparents before the loop. */
|
|
|
|
DRW_pass_sort_shgroup_z(psl->transparent_pass);
|
|
|
|
|
2021-02-12 22:35:18 +01:00
|
|
|
uint tot_sample = stl->g_data->render_sample_count_per_timestep;
|
2019-11-13 14:00:03 +01:00
|
|
|
uint render_samples = 0;
|
|
|
|
|
|
|
|
/* SSR needs one iteration to start properly. */
|
2020-06-23 13:59:55 +02:00
|
|
|
if ((stl->effects->enabled_effects & EFFECT_SSR) && !stl->effects->ssr_was_valid_double_buffer) {
|
2019-11-13 14:00:03 +01:00
|
|
|
tot_sample += 1;
|
|
|
|
}
|
|
|
|
|
2018-03-08 15:22:57 +01:00
|
|
|
while (render_samples < tot_sample && !RE_engine_test_break(engine)) {
|
2020-08-07 22:36:11 +10:00
|
|
|
const float clear_col[4] = {0.0f, 0.0f, 0.0f, 0.0f};
|
2018-03-25 17:46:48 +02:00
|
|
|
float clear_depth = 1.0f;
|
2018-08-15 17:41:36 +02:00
|
|
|
uint clear_stencil = 0x00;
|
2020-08-07 22:36:11 +10:00
|
|
|
const uint primes[3] = {2, 3, 7};
|
2018-01-29 18:16:11 +01:00
|
|
|
double offset[3] = {0.0, 0.0, 0.0};
|
|
|
|
double r[3];
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-07-09 14:34:38 +02:00
|
|
|
if ((stl->effects->enabled_effects & EFFECT_SSR) && (render_samples == 1) &&
|
|
|
|
!stl->effects->ssr_was_valid_double_buffer) {
|
|
|
|
/* SSR needs one iteration to start properly.
|
|
|
|
* This iteration was done, reset to the original target sample count. */
|
|
|
|
render_samples--;
|
|
|
|
tot_sample--;
|
|
|
|
/* Reset sampling (and accumulation) after the first sample to avoid
|
|
|
|
* washed out first bounce for SSR. */
|
|
|
|
EEVEE_temporal_sampling_reset(vedata);
|
|
|
|
stl->effects->ssr_was_valid_double_buffer = stl->g_data->valid_double_buffer;
|
|
|
|
}
|
|
|
|
/* Don't print every samples as it can lead to bad performance. (see T59649) */
|
|
|
|
else if ((render_samples % 25) == 0 || (render_samples + 1) == tot_sample) {
|
|
|
|
char info[42];
|
|
|
|
BLI_snprintf(
|
|
|
|
info, sizeof(info), "Rendering %u / %u samples", render_samples + 1, tot_sample);
|
|
|
|
RE_engine_update_stats(engine, NULL, info);
|
|
|
|
}
|
|
|
|
|
2018-02-26 20:08:48 +01:00
|
|
|
/* Copy previous persmat to UBO data */
|
|
|
|
copy_m4_m4(sldata->common_data.prev_persmat, stl->effects->prev_persmat);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-03-20 18:17:16 +11:00
|
|
|
BLI_halton_3d(primes, offset, stl->effects->taa_current_sample, r);
|
2018-01-29 18:16:11 +01:00
|
|
|
EEVEE_update_noise(psl, fbl, r);
|
2019-05-21 12:34:48 +02:00
|
|
|
EEVEE_temporal_sampling_matrices_calc(stl->effects, r);
|
2018-02-02 01:18:25 +01:00
|
|
|
EEVEE_volumes_set_jitter(sldata, stl->effects->taa_current_sample - 1);
|
2020-06-02 16:58:07 +02:00
|
|
|
EEVEE_materials_init(sldata, vedata, stl, fbl);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-01-07 09:19:07 +01:00
|
|
|
/* Refresh Probes
|
|
|
|
* Shadows needs to be updated for correct probes */
|
|
|
|
EEVEE_shadows_update(sldata, vedata);
|
2018-07-10 15:02:25 +02:00
|
|
|
EEVEE_lightprobes_refresh(sldata, vedata);
|
2018-03-07 23:25:49 +01:00
|
|
|
EEVEE_lightprobes_refresh_planar(sldata, vedata);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-01-31 02:13:45 +01:00
|
|
|
/* Refresh Shadows */
|
2019-08-22 16:04:25 +02:00
|
|
|
EEVEE_shadows_draw(sldata, vedata, stl->effects->taa_view);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2019-05-21 17:53:49 +02:00
|
|
|
/* Set matrices. */
|
|
|
|
DRW_view_set_active(stl->effects->taa_view);
|
|
|
|
|
2018-11-08 19:17:41 +01:00
|
|
|
/* Set ray type. */
|
|
|
|
sldata->common_data.ray_type = EEVEE_RAY_CAMERA;
|
|
|
|
sldata->common_data.ray_depth = 0.0f;
|
2020-08-20 23:09:37 +02:00
|
|
|
GPU_uniformbuf_update(sldata->common_ubo, &sldata->common_data);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
|
|
|
GPU_framebuffer_clear_color_depth_stencil(fbl->main_fb, clear_col, clear_depth, clear_stencil);
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Depth prepass */
|
2020-06-02 16:58:07 +02:00
|
|
|
DRW_draw_pass(psl->depth_ps);
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Create minmax texture */
|
|
|
|
EEVEE_create_minmax_buffer(vedata, dtxl->depth, -1);
|
|
|
|
EEVEE_occlusion_compute(sldata, vedata, dtxl->depth, -1);
|
|
|
|
EEVEE_volumes_compute(sldata, vedata);
|
|
|
|
/* Shading pass */
|
2018-02-02 00:50:18 +01:00
|
|
|
eevee_render_draw_background(vedata);
|
2018-03-25 17:46:48 +02:00
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
2020-06-02 16:58:07 +02:00
|
|
|
DRW_draw_pass(psl->material_ps);
|
2018-01-29 18:16:11 +01:00
|
|
|
EEVEE_subsurface_data_render(sldata, vedata);
|
|
|
|
/* Effects pre-transparency */
|
|
|
|
EEVEE_subsurface_compute(sldata, vedata);
|
|
|
|
EEVEE_reflection_compute(sldata, vedata);
|
|
|
|
EEVEE_refraction_compute(sldata, vedata);
|
|
|
|
/* Opaque refraction */
|
2020-06-02 16:58:07 +02:00
|
|
|
DRW_draw_pass(psl->depth_refract_ps);
|
|
|
|
DRW_draw_pass(psl->material_refract_ps);
|
2018-01-31 01:09:38 +01:00
|
|
|
/* Result NORMAL */
|
2018-02-23 13:26:28 -03:00
|
|
|
eevee_render_result_normal(rl, viewname, rect, vedata, sldata);
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Volumetrics Resolve Opaque */
|
|
|
|
EEVEE_volumes_resolve(sldata, vedata);
|
2019-11-08 16:47:33 +01:00
|
|
|
/* Subsurface output, Occlusion output, Mist output */
|
2020-02-20 14:53:53 +01:00
|
|
|
EEVEE_renderpasses_output_accumulate(sldata, vedata, false);
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Transparent */
|
2019-08-12 01:47:30 +02:00
|
|
|
GPU_framebuffer_texture_attach(fbl->main_color_fb, dtxl->depth, 0, 0);
|
|
|
|
GPU_framebuffer_bind(fbl->main_color_fb);
|
2018-01-29 18:16:11 +01:00
|
|
|
DRW_draw_pass(psl->transparent_pass);
|
2019-08-12 01:47:30 +02:00
|
|
|
GPU_framebuffer_bind(fbl->main_fb);
|
|
|
|
GPU_framebuffer_texture_detach(fbl->main_color_fb, dtxl->depth);
|
2018-01-31 01:09:38 +01:00
|
|
|
/* Result Z */
|
2018-02-23 13:26:28 -03:00
|
|
|
eevee_render_result_z(rl, viewname, rect, vedata, sldata);
|
2018-01-29 18:16:11 +01:00
|
|
|
/* Post Process */
|
|
|
|
EEVEE_draw_effects(sldata, vedata);
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-10-11 13:19:49 +02:00
|
|
|
/* XXX Seems to fix TDR issue with NVidia drivers on linux. */
|
2018-10-31 12:28:59 +01:00
|
|
|
GPU_finish();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-03-08 15:22:57 +01:00
|
|
|
RE_engine_update_progress(engine, (float)(render_samples++) / (float)tot_sample);
|
2018-01-29 18:16:11 +01:00
|
|
|
}
|
2020-06-23 13:59:55 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
void EEVEE_render_read_result(EEVEE_Data *vedata,
|
|
|
|
RenderEngine *engine,
|
|
|
|
RenderLayer *rl,
|
|
|
|
const rcti *rect)
|
|
|
|
{
|
|
|
|
const char *viewname = RE_GetActiveRenderView(engine->re);
|
|
|
|
EEVEE_ViewLayerData *sldata = EEVEE_view_layer_data_ensure();
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2018-02-23 13:26:28 -03:00
|
|
|
eevee_render_result_combined(rl, viewname, rect, vedata, sldata);
|
2019-11-07 13:14:15 +01:00
|
|
|
eevee_render_result_mist(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_occlusion(rl, viewname, rect, vedata, sldata);
|
2020-02-20 14:53:53 +01:00
|
|
|
eevee_render_result_shadow(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_diffuse_color(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_diffuse_direct(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_specular_color(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_specular_direct(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_emission(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_environment(rl, viewname, rect, vedata, sldata);
|
|
|
|
eevee_render_result_bloom(rl, viewname, rect, vedata, sldata);
|
2020-12-14 09:05:16 +01:00
|
|
|
eevee_render_result_volume_light(rl, viewname, rect, vedata, sldata);
|
2020-12-04 08:13:54 +01:00
|
|
|
eevee_render_result_aovs(rl, viewname, rect, vedata, sldata);
|
2020-12-04 08:28:43 +01:00
|
|
|
eevee_render_result_cryptomatte(rl, viewname, rect, vedata, sldata);
|
2018-01-31 01:09:38 +01:00
|
|
|
}
|
2018-02-01 21:38:16 +01:00
|
|
|
|
|
|
|
void EEVEE_render_update_passes(RenderEngine *engine, Scene *scene, ViewLayer *view_layer)
|
|
|
|
{
|
|
|
|
RE_engine_register_pass(engine, scene, view_layer, RE_PASSNAME_COMBINED, 4, "RGBA", SOCK_RGBA);
|
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
#define CHECK_PASS_LEGACY(name, type, channels, chanid) \
|
2018-02-01 21:38:16 +01:00
|
|
|
if (view_layer->passflag & (SCE_PASS_##name)) { \
|
2020-02-20 14:53:53 +01:00
|
|
|
RE_engine_register_pass( \
|
|
|
|
engine, scene, view_layer, RE_PASSNAME_##name, channels, chanid, type); \
|
|
|
|
} \
|
|
|
|
((void)0)
|
|
|
|
#define CHECK_PASS_EEVEE(name, type, channels, chanid) \
|
|
|
|
if (view_layer->eevee.render_passes & (EEVEE_RENDER_PASS_##name)) { \
|
2018-02-01 21:38:16 +01:00
|
|
|
RE_engine_register_pass( \
|
|
|
|
engine, scene, view_layer, RE_PASSNAME_##name, channels, chanid, type); \
|
2019-04-02 17:54:04 +11:00
|
|
|
} \
|
|
|
|
((void)0)
|
2019-04-17 06:17:24 +02:00
|
|
|
|
2020-02-20 14:53:53 +01:00
|
|
|
CHECK_PASS_LEGACY(Z, SOCK_FLOAT, 1, "Z");
|
|
|
|
CHECK_PASS_LEGACY(MIST, SOCK_FLOAT, 1, "Z");
|
|
|
|
CHECK_PASS_LEGACY(NORMAL, SOCK_VECTOR, 3, "XYZ");
|
|
|
|
CHECK_PASS_LEGACY(SHADOW, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(AO, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(DIFFUSE_COLOR, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(DIFFUSE_DIRECT, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(GLOSSY_COLOR, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(GLOSSY_DIRECT, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(EMIT, SOCK_RGBA, 3, "RGB");
|
|
|
|
CHECK_PASS_LEGACY(ENVIRONMENT, SOCK_RGBA, 3, "RGB");
|
2020-12-14 09:05:16 +01:00
|
|
|
CHECK_PASS_EEVEE(VOLUME_LIGHT, SOCK_RGBA, 3, "RGB");
|
2020-02-20 14:53:53 +01:00
|
|
|
CHECK_PASS_EEVEE(BLOOM, SOCK_RGBA, 3, "RGB");
|
2018-02-01 21:38:16 +01:00
|
|
|
|
2020-12-04 08:13:54 +01:00
|
|
|
LISTBASE_FOREACH (ViewLayerAOV *, aov, &view_layer->aovs) {
|
|
|
|
if ((aov->flag & AOV_CONFLICT) != 0) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
switch (aov->type) {
|
|
|
|
case AOV_TYPE_COLOR:
|
|
|
|
RE_engine_register_pass(engine, scene, view_layer, aov->name, 4, "RGBA", SOCK_RGBA);
|
|
|
|
break;
|
|
|
|
case AOV_TYPE_VALUE:
|
|
|
|
RE_engine_register_pass(engine, scene, view_layer, aov->name, 1, "X", SOCK_FLOAT);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2020-12-04 08:28:43 +01:00
|
|
|
EEVEE_cryptomatte_update_passes(engine, scene, view_layer);
|
2020-12-04 08:13:54 +01:00
|
|
|
|
2020-02-28 14:31:03 +01:00
|
|
|
#undef CHECK_PASS_LEGACY
|
|
|
|
#undef CHECK_PASS_EEVEE
|
2018-02-15 18:03:55 +11:00
|
|
|
}
|