From f9e65fcea72fb6c2c4d73b86066be9f0d63c2011 Mon Sep 17 00:00:00 2001 From: Lukas Stockner Date: Fri, 20 Dec 2019 21:46:36 +0100 Subject: [PATCH] Textures: Support UDIM images This adds UDIM support to e.g. the Displacement modifier. The implementation is straightforward: If the image is tiled, lookup the tile based on UVs and shift the UVs into the tile's coordinates. --- source/blender/blenkernel/intern/image.c | 3 ++ .../blender/render/intern/include/texture.h | 1 - .../render/intern/source/imagetexture.c | 48 +++++++++++-------- .../render/intern/source/render_texture.c | 2 +- 4 files changed, 32 insertions(+), 22 deletions(-) diff --git a/source/blender/blenkernel/intern/image.c b/source/blender/blenkernel/intern/image.c index fca81acf038..6d6e5166e1c 100644 --- a/source/blender/blenkernel/intern/image.c +++ b/source/blender/blenkernel/intern/image.c @@ -4652,6 +4652,9 @@ static void image_get_entry_and_index(Image *ima, ImageUser *iuser, int *r_entry frame = iuser ? iuser->framenr : ima->lastframe; } } + else if (ima->source == IMA_SRC_TILED) { + frame = (iuser && iuser->tile) ? iuser->tile : 1001; + } *r_entry = frame; *r_index = index; diff --git a/source/blender/render/intern/include/texture.h b/source/blender/render/intern/include/texture.h index d47413717d4..f051d3ed318 100644 --- a/source/blender/render/intern/include/texture.h +++ b/source/blender/render/intern/include/texture.h @@ -83,7 +83,6 @@ int imagewraposa(struct Tex *tex, const bool skip_load_image); int imagewrap(struct Tex *tex, struct Image *ima, - struct ImBuf *ibuf, const float texvec[3], struct TexResult *texres, struct ImagePool *pool, diff --git a/source/blender/render/intern/source/imagetexture.c b/source/blender/render/intern/source/imagetexture.c index dc7288234b3..47d0986fabd 100644 --- a/source/blender/render/intern/source/imagetexture.c +++ b/source/blender/render/intern/source/imagetexture.c @@ -100,7 +100,6 @@ static void ibuf_get_color(float col[4], struct ImBuf *ibuf, int x, int y) int imagewrap(Tex *tex, Image *ima, - ImBuf *ibuf, const float texvec[3], TexResult *texres, struct ImagePool *pool, @@ -116,35 +115,44 @@ int imagewrap(Tex *tex, retval = texres->nor ? 3 : 1; /* quick tests */ - if (ibuf == NULL && ima == NULL) { + if (ima == NULL) { return retval; } - if (ima) { - /* hack for icon render */ - if (skip_load_image && !BKE_image_has_loaded_ibuf(ima)) { - return retval; - } - - ibuf = BKE_image_pool_acquire_ibuf(ima, &tex->iuser, pool); - - ima->flag |= IMA_USED_FOR_RENDER; + /* hack for icon render */ + if (skip_load_image && !BKE_image_has_loaded_ibuf(ima)) { + return retval; } + + ImageUser *iuser = &tex->iuser; + ImageUser local_iuser; + if (ima->source == IMA_SRC_TILED) { + /* tex->iuser might be shared by threads, so create a local copy. */ + local_iuser = tex->iuser; + iuser = &local_iuser; + + float new_uv[2]; + iuser->tile = BKE_image_get_tile_from_pos(ima, texvec, new_uv, NULL); + fx = new_uv[0]; + fy = new_uv[1]; + } + else { + fx = texvec[0]; + fy = texvec[1]; + } + + ImBuf *ibuf = BKE_image_pool_acquire_ibuf(ima, iuser, pool); + + ima->flag |= IMA_USED_FOR_RENDER; + if (ibuf == NULL || (ibuf->rect == NULL && ibuf->rect_float == NULL)) { - if (ima) { - BKE_image_pool_release_ibuf(ima, ibuf, pool); - } + BKE_image_pool_release_ibuf(ima, ibuf, pool); return retval; } /* setup mapping */ if (tex->imaflag & TEX_IMAROT) { - fy = texvec[0]; - fx = texvec[1]; - } - else { - fx = texvec[0]; - fy = texvec[1]; + SWAP(float, fx, fy); } if (tex->extend == TEX_CHECKER) { diff --git a/source/blender/render/intern/source/render_texture.c b/source/blender/render/intern/source/render_texture.c index 3f3dc9842a5..fe162212b9c 100644 --- a/source/blender/render/intern/source/render_texture.c +++ b/source/blender/render/intern/source/render_texture.c @@ -1219,7 +1219,7 @@ static int multitex(Tex *tex, tex, tex->ima, NULL, texvec, dxt, dyt, texres, pool, skip_load_image); } else { - retval = imagewrap(tex, tex->ima, NULL, texvec, texres, pool, skip_load_image); + retval = imagewrap(tex, tex->ima, texvec, texres, pool, skip_load_image); } if (tex->ima) { BKE_image_tag_time(tex->ima);