Fix T73188: RenderResult as Camera BG Image
In blender 2.79 you could use a render result as a camera background image. This is useful during layout/compositing. During Blender 2.80 development there were 2 issues introduced that removed this feature. * to receive a render result the image required a lock. This lock wasn't passed and therefore no image was read from the result. Generating an GPUTexture from an Blender image also didn't do the locking. * the iuser->scene field wasn't set what is required for render results. This change adds an optional `ibuf` parameter to `GPU_texture_from_blender` that can be passed when available. Reviewed By: fclem, brecht Differential Revision: https://developer.blender.org/D6684
This commit is contained in:
parent
b683fcb628
commit
18c88eac17
@ -522,7 +522,7 @@ static DRWShadingGroup *gpencil_shgroup_fill_create(GPENCIL_e_data *e_data,
|
||||
BKE_image_release_ibuf(image, ibuf, NULL);
|
||||
}
|
||||
else {
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->ima, &iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->ima, &iuser, ibuf, GL_TEXTURE_2D);
|
||||
DRW_shgroup_uniform_texture(grp, "myTexture", texture);
|
||||
DRW_shgroup_uniform_bool_copy(
|
||||
grp, "myTexturePremultiplied", (image->alpha_mode == IMA_ALPHA_PREMUL));
|
||||
@ -705,7 +705,7 @@ DRWShadingGroup *gpencil_shgroup_stroke_create(GPENCIL_e_data *e_data,
|
||||
BKE_image_release_ibuf(image, ibuf, NULL);
|
||||
}
|
||||
else {
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->sima, &iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->sima, &iuser, ibuf, GL_TEXTURE_2D);
|
||||
DRW_shgroup_uniform_texture(grp, "myTexture", texture);
|
||||
DRW_shgroup_uniform_bool_copy(
|
||||
grp, "myTexturePremultiplied", (image->alpha_mode == IMA_ALPHA_PREMUL));
|
||||
@ -878,7 +878,7 @@ static DRWShadingGroup *gpencil_shgroup_point_create(GPENCIL_e_data *e_data,
|
||||
BKE_image_release_ibuf(image, ibuf, NULL);
|
||||
}
|
||||
else {
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->sima, &iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *texture = GPU_texture_from_blender(gp_style->sima, &iuser, ibuf, GL_TEXTURE_2D);
|
||||
DRW_shgroup_uniform_texture(grp, "myTexture", texture);
|
||||
DRW_shgroup_uniform_bool_copy(
|
||||
grp, "myTexturePremultiplied", (image->alpha_mode == IMA_ALPHA_PREMUL));
|
||||
|
@ -134,6 +134,7 @@ static struct GPUTexture *image_camera_background_texture_get(CameraBGImage *bgp
|
||||
float *r_aspect,
|
||||
bool *r_use_alpha_premult)
|
||||
{
|
||||
void *lock;
|
||||
Image *image = bgpic->ima;
|
||||
ImageUser *iuser = &bgpic->iuser;
|
||||
MovieClip *clip = NULL;
|
||||
@ -160,12 +161,19 @@ static struct GPUTexture *image_camera_background_texture_get(CameraBGImage *bgp
|
||||
camera_background_images_stereo_setup(scene, draw_ctx->v3d, image, iuser);
|
||||
}
|
||||
|
||||
ImBuf *ibuf = BKE_image_acquire_ibuf(image, iuser, NULL);
|
||||
iuser->scene = draw_ctx->scene;
|
||||
ImBuf *ibuf = BKE_image_acquire_ibuf(image, iuser, &lock);
|
||||
if (ibuf == NULL) {
|
||||
BKE_image_release_ibuf(image, ibuf, lock);
|
||||
iuser->scene = NULL;
|
||||
return NULL;
|
||||
}
|
||||
width = ibuf->x;
|
||||
height = ibuf->y;
|
||||
tex = GPU_texture_from_blender(image, iuser, ibuf, GL_TEXTURE_2D);
|
||||
BKE_image_release_ibuf(image, ibuf, lock);
|
||||
iuser->scene = NULL;
|
||||
|
||||
tex = GPU_texture_from_blender(image, iuser, GL_TEXTURE_2D);
|
||||
if (tex == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
@ -173,10 +181,6 @@ static struct GPUTexture *image_camera_background_texture_get(CameraBGImage *bgp
|
||||
aspect_x = bgpic->ima->aspx;
|
||||
aspect_y = bgpic->ima->aspy;
|
||||
|
||||
width = ibuf->x;
|
||||
height = ibuf->y;
|
||||
|
||||
BKE_image_release_ibuf(image, ibuf, NULL);
|
||||
break;
|
||||
|
||||
case CAM_BGIMG_SOURCE_MOVIE:
|
||||
@ -376,7 +380,7 @@ void OVERLAY_image_empty_cache_populate(OVERLAY_Data *vedata, Object *ob)
|
||||
* see: T59347 */
|
||||
int size[2] = {0};
|
||||
if (ima != NULL) {
|
||||
tex = GPU_texture_from_blender(ima, ob->iuser, GL_TEXTURE_2D);
|
||||
tex = GPU_texture_from_blender(ima, ob->iuser, NULL, GL_TEXTURE_2D);
|
||||
if (tex) {
|
||||
size[0] = GPU_texture_orig_width(tex);
|
||||
size[1] = GPU_texture_orig_height(tex);
|
||||
|
@ -85,7 +85,7 @@ void OVERLAY_paint_cache_init(OVERLAY_Data *vedata)
|
||||
state = DRW_STATE_WRITE_COLOR | DRW_STATE_DEPTH_EQUAL | DRW_STATE_BLEND_ALPHA;
|
||||
DRW_PASS_CREATE(psl->paint_color_ps, state | pd->clipping_state);
|
||||
|
||||
GPUTexture *tex = GPU_texture_from_blender(imapaint->stencil, NULL, GL_TEXTURE_2D);
|
||||
GPUTexture *tex = GPU_texture_from_blender(imapaint->stencil, NULL, NULL, GL_TEXTURE_2D);
|
||||
|
||||
const bool mask_premult = (imapaint->stencil->alpha_mode == IMA_ALPHA_PREMUL);
|
||||
const bool mask_inverted = (imapaint->flag & IMAGEPAINT_PROJECT_LAYER_STENCIL_INV) != 0;
|
||||
|
@ -210,7 +210,8 @@ WORKBENCH_MaterialData *workbench_forward_get_or_create_material_data(WORKBENCH_
|
||||
if (color_type == V3D_SHADING_TEXTURE_COLOR) {
|
||||
material->shgrp_object_outline = DRW_shgroup_create(sh_data->object_outline_texture_sh,
|
||||
psl->object_outline_pass);
|
||||
GPUTexture *tex = GPU_texture_from_blender(material->ima, material->iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *tex = GPU_texture_from_blender(
|
||||
material->ima, material->iuser, NULL, GL_TEXTURE_2D);
|
||||
DRW_shgroup_uniform_texture(material->shgrp_object_outline, "image", tex);
|
||||
}
|
||||
else {
|
||||
|
@ -376,14 +376,15 @@ void workbench_material_shgroup_uniform(WORKBENCH_PrivateData *wpd,
|
||||
if (use_texture) {
|
||||
if (is_tiled) {
|
||||
GPUTexture *array_tex = GPU_texture_from_blender(
|
||||
material->ima, material->iuser, GL_TEXTURE_2D_ARRAY);
|
||||
material->ima, material->iuser, NULL, GL_TEXTURE_2D_ARRAY);
|
||||
GPUTexture *data_tex = GPU_texture_from_blender(
|
||||
material->ima, material->iuser, GL_TEXTURE_1D_ARRAY);
|
||||
material->ima, material->iuser, NULL, GL_TEXTURE_1D_ARRAY);
|
||||
DRW_shgroup_uniform_texture(grp, "image_tile_array", array_tex);
|
||||
DRW_shgroup_uniform_texture(grp, "image_tile_data", data_tex);
|
||||
}
|
||||
else {
|
||||
GPUTexture *tex = GPU_texture_from_blender(material->ima, material->iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *tex = GPU_texture_from_blender(
|
||||
material->ima, material->iuser, NULL, GL_TEXTURE_2D);
|
||||
DRW_shgroup_uniform_texture(grp, "image", tex);
|
||||
}
|
||||
DRW_shgroup_uniform_bool_copy(
|
||||
|
@ -1226,7 +1226,7 @@ static DRWShadingGroup *drw_shgroup_material_inputs(DRWShadingGroup *grp,
|
||||
else {
|
||||
textarget = GL_TEXTURE_2D;
|
||||
}
|
||||
*tex_ref = tex = GPU_texture_from_blender(input->ima, input->iuser, textarget);
|
||||
*tex_ref = tex = GPU_texture_from_blender(input->ima, input->iuser, NULL, textarget);
|
||||
|
||||
GPU_texture_ref(tex);
|
||||
}
|
||||
|
@ -36,6 +36,7 @@ struct ImageUser;
|
||||
struct MovieClip;
|
||||
struct MovieClipUser;
|
||||
struct PreviewImage;
|
||||
struct ImBuf;
|
||||
|
||||
struct GPUFrameBuffer;
|
||||
typedef struct GPUTexture GPUTexture;
|
||||
@ -187,7 +188,10 @@ GPUTexture *GPU_texture_create_from_vertbuf(struct GPUVertBuf *vert);
|
||||
GPUTexture *GPU_texture_create_buffer(eGPUTextureFormat data_type, const uint buffer);
|
||||
|
||||
GPUTexture *GPU_texture_from_bindcode(int textarget, int bindcode);
|
||||
GPUTexture *GPU_texture_from_blender(struct Image *ima, struct ImageUser *iuser, int textarget);
|
||||
GPUTexture *GPU_texture_from_blender(struct Image *ima,
|
||||
struct ImageUser *iuser,
|
||||
struct ImBuf *ibuf,
|
||||
int textarget);
|
||||
GPUTexture *GPU_texture_from_preview(struct PreviewImage *prv, int mipmap);
|
||||
|
||||
/* movie clip drawing */
|
||||
|
@ -851,7 +851,11 @@ static void gpu_texture_update_from_ibuf(
|
||||
GPU_texture_unbind(tex);
|
||||
}
|
||||
|
||||
GPUTexture *GPU_texture_from_blender(Image *ima, ImageUser *iuser, int textarget)
|
||||
/* Get the GPUTexture for a given `Image`.
|
||||
*
|
||||
* `iuser` and `ibuf` are mutual exclusive parameters. The caller can pass the `ibuf` when already
|
||||
* available. It is also required when requesting the GPUTexture for a render result. */
|
||||
GPUTexture *GPU_texture_from_blender(Image *ima, ImageUser *iuser, ImBuf *ibuf, int textarget)
|
||||
{
|
||||
if (ima == NULL) {
|
||||
return NULL;
|
||||
@ -882,27 +886,33 @@ GPUTexture *GPU_texture_from_blender(Image *ima, ImageUser *iuser, int textarget
|
||||
}
|
||||
|
||||
/* check if we have a valid image buffer */
|
||||
ImBuf *ibuf = BKE_image_acquire_ibuf(ima, iuser, NULL);
|
||||
if (ibuf == NULL) {
|
||||
*tex = GPU_texture_from_bindcode(textarget, bindcode);
|
||||
return *tex;
|
||||
ImBuf *ibuf_intern = ibuf;
|
||||
if (ibuf_intern == NULL) {
|
||||
ibuf_intern = BKE_image_acquire_ibuf(ima, iuser, NULL);
|
||||
if (ibuf_intern == NULL) {
|
||||
*tex = GPU_texture_from_bindcode(textarget, bindcode);
|
||||
return *tex;
|
||||
}
|
||||
}
|
||||
|
||||
if (textarget == GL_TEXTURE_2D_ARRAY) {
|
||||
bindcode = gpu_texture_create_tile_array(ima, ibuf);
|
||||
bindcode = gpu_texture_create_tile_array(ima, ibuf_intern);
|
||||
}
|
||||
else if (textarget == GL_TEXTURE_1D_ARRAY) {
|
||||
bindcode = gpu_texture_create_tile_mapping(ima);
|
||||
}
|
||||
else {
|
||||
bindcode = gpu_texture_create_from_ibuf(ima, ibuf, textarget);
|
||||
bindcode = gpu_texture_create_from_ibuf(ima, ibuf_intern, textarget);
|
||||
}
|
||||
|
||||
BKE_image_release_ibuf(ima, ibuf, NULL);
|
||||
/* if `ibuf` was given, we don't own the `ibuf_intern` */
|
||||
if (ibuf == NULL) {
|
||||
BKE_image_release_ibuf(ima, ibuf_intern, NULL);
|
||||
}
|
||||
|
||||
*tex = GPU_texture_from_bindcode(textarget, bindcode);
|
||||
|
||||
GPU_texture_orig_size_set(*tex, ibuf->x, ibuf->y);
|
||||
GPU_texture_orig_size_set(*tex, ibuf_intern->x, ibuf_intern->y);
|
||||
|
||||
return *tex;
|
||||
}
|
||||
|
@ -222,7 +222,7 @@ static int rna_Image_gl_load(Image *image, ReportList *reports, int frame)
|
||||
BKE_imageuser_default(&iuser);
|
||||
iuser.framenr = frame;
|
||||
|
||||
GPUTexture *tex = GPU_texture_from_blender(image, &iuser, GL_TEXTURE_2D);
|
||||
GPUTexture *tex = GPU_texture_from_blender(image, &iuser, NULL, GL_TEXTURE_2D);
|
||||
|
||||
if (tex == NULL) {
|
||||
BKE_reportf(reports, RPT_ERROR, "Failed to load image texture '%s'", image->id.name + 2);
|
||||
|
Loading…
Reference in New Issue
Block a user