Commit: dd2dca2f7e77e7521d13b78e875ffa58a90846f2 Author: Martijn Berger Date: Fri Mar 7 23:16:09 2014 +0100 https://developer.blender.org/rBdd2dca2f7e77e7521d13b78e875ffa58a90846f2
Add support for multiple interpolation modes on cycles image textures All textures are sampled bi-linear currently with the exception of OSL there texture sampling is fixed and set to smart bi-cubic. This patch adds user control to this setting. Added: - bits to DNA / RNA in the form of an enum for supporting multiple interpolations types - changes to the image texture node drawing code ( add enum) - to ImageManager (this needs to know to allocate second texture when interpolation type is different) - to node compiler (pass on interpolation type) - to device tex_alloc this also needs to get the concept of multiple interpolation types - implementation for doing non interpolated lookup for cuda and cpu - implementation where we pass this along to osl ( this makes OSL also do linear untill I add smartcubic to the interface / DNA/ RNA) Reviewers: brecht, dingto Reviewed By: brecht CC: dingto, venomgfx Differential Revision: https://developer.blender.org/D317 =================================================================== M intern/cycles/blender/blender_shader.cpp M intern/cycles/device/device.h M intern/cycles/device/device_cpu.cpp M intern/cycles/device/device_cuda.cpp M intern/cycles/device/device_multi.cpp M intern/cycles/device/device_network.cpp M intern/cycles/device/device_opencl.cpp M intern/cycles/kernel/kernel.cpp M intern/cycles/kernel/kernel.h M intern/cycles/kernel/kernel_compat_cpu.h M intern/cycles/kernel/shaders/node_image_texture.osl M intern/cycles/kernel/svm/svm_image.h M intern/cycles/render/image.cpp M intern/cycles/render/image.h M intern/cycles/render/nodes.cpp M intern/cycles/render/nodes.h M intern/cycles/util/util_types.h M source/blender/editors/space_node/drawnode.c M source/blender/makesdna/DNA_node_types.h M source/blender/makesrna/intern/rna_nodetree.c =================================================================== diff --git a/intern/cycles/blender/blender_shader.cpp b/intern/cycles/blender/blender_shader.cpp index 6175c8e..1559a96 100644 --- a/intern/cycles/blender/blender_shader.cpp +++ b/intern/cycles/blender/blender_shader.cpp @@ -549,6 +549,7 @@ static ShaderNode *add_node(Scene *scene, BL::BlendData b_data, BL::Scene b_scen } image->color_space = ImageTextureNode::color_space_enum[(int)b_image_node.color_space()]; image->projection = ImageTextureNode::projection_enum[(int)b_image_node.projection()]; + image->interpolation = (InterpolationType)b_image_node.interpolation(); image->projection_blend = b_image_node.projection_blend(); get_tex_mapping(&image->tex_mapping, b_image_node.texture_mapping()); node = image; diff --git a/intern/cycles/device/device.h b/intern/cycles/device/device.h index bd309e3..f94075f 100644 --- a/intern/cycles/device/device.h +++ b/intern/cycles/device/device.h @@ -100,7 +100,7 @@ public: /* texture memory */ virtual void tex_alloc(const char *name, device_memory& mem, - bool interpolation = false, bool periodic = false) {}; + InterpolationType interpolation = INTERPOLATION_NONE, bool periodic = false) {}; virtual void tex_free(device_memory& mem) {}; /* pixel memory */ diff --git a/intern/cycles/device/device_cpu.cpp b/intern/cycles/device/device_cpu.cpp index 76123fe..de44feb 100644 --- a/intern/cycles/device/device_cpu.cpp +++ b/intern/cycles/device/device_cpu.cpp @@ -103,9 +103,9 @@ public: kernel_const_copy(&kernel_globals, name, host, size); } - void tex_alloc(const char *name, device_memory& mem, bool interpolation, bool periodic) + void tex_alloc(const char *name, device_memory& mem, InterpolationType interpolation, bool periodic) { - kernel_tex_copy(&kernel_globals, name, mem.data_pointer, mem.data_width, mem.data_height); + kernel_tex_copy(&kernel_globals, name, mem.data_pointer, mem.data_width, mem.data_height, interpolation); mem.device_pointer = mem.data_pointer; stats.mem_alloc(mem.memory_size()); diff --git a/intern/cycles/device/device_cuda.cpp b/intern/cycles/device/device_cuda.cpp index 932fdc3..5133a5c 100644 --- a/intern/cycles/device/device_cuda.cpp +++ b/intern/cycles/device/device_cuda.cpp @@ -451,7 +451,7 @@ public: cuda_pop_context(); } - void tex_alloc(const char *name, device_memory& mem, bool interpolation, bool periodic) + void tex_alloc(const char *name, device_memory& mem, InterpolationType interpolation, bool periodic) { /* determine format */ CUarray_format_enum format; @@ -479,7 +479,7 @@ public: return; } - if(interpolation) { + if(interpolation != INTERPOLATION_NONE) { CUarray handle = NULL; CUDA_ARRAY_DESCRIPTOR desc; @@ -513,7 +513,15 @@ public: cuda_assert(cuTexRefSetArray(texref, handle, CU_TRSA_OVERRIDE_FORMAT)) - cuda_assert(cuTexRefSetFilterMode(texref, CU_TR_FILTER_MODE_LINEAR)) + if(interpolation == INTERPOLATION_CLOSEST) { + cuda_assert(cuTexRefSetFilterMode(texref, CU_TR_FILTER_MODE_POINT)) + } + else if (interpolation == INTERPOLATION_LINEAR){ + cuda_assert(cuTexRefSetFilterMode(texref, CU_TR_FILTER_MODE_LINEAR)) + } + else {/* CUBIC and SMART are unsupported for CUDA */ + cuda_assert(cuTexRefSetFilterMode(texref, CU_TR_FILTER_MODE_LINEAR)) + } cuda_assert(cuTexRefSetFlags(texref, CU_TRSF_NORMALIZED_COORDINATES)) mem.device_pointer = (device_ptr)handle; @@ -570,7 +578,7 @@ public: cuda_pop_context(); } - tex_interp_map[mem.device_pointer] = interpolation; + tex_interp_map[mem.device_pointer] = (interpolation != INTERPOLATION_NONE); } void tex_free(device_memory& mem) diff --git a/intern/cycles/device/device_multi.cpp b/intern/cycles/device/device_multi.cpp index 27b9de0..1e9367c 100644 --- a/intern/cycles/device/device_multi.cpp +++ b/intern/cycles/device/device_multi.cpp @@ -168,7 +168,7 @@ public: sub.device->const_copy_to(name, host, size); } - void tex_alloc(const char *name, device_memory& mem, bool interpolation, bool periodic) + void tex_alloc(const char *name, device_memory& mem, InterpolationType interpolation, bool periodic) { foreach(SubDevice& sub, devices) { mem.device_pointer = 0; diff --git a/intern/cycles/device/device_network.cpp b/intern/cycles/device/device_network.cpp index bffd993..8f00324 100644 --- a/intern/cycles/device/device_network.cpp +++ b/intern/cycles/device/device_network.cpp @@ -162,7 +162,7 @@ public: snd.write_buffer(host, size); } - void tex_alloc(const char *name, device_memory& mem, bool interpolation, bool periodic) + void tex_alloc(const char *name, device_memory& mem, InterpolationType interpolation, bool periodic) { thread_scoped_lock lock(rpc_lock); @@ -559,7 +559,7 @@ protected: else if(rcv.name == "tex_alloc") { network_device_memory mem; string name; - bool interpolation; + InterpolationType interpolation; bool periodic; device_ptr client_pointer; diff --git a/intern/cycles/device/device_opencl.cpp b/intern/cycles/device/device_opencl.cpp index 9117b70..33170e1 100644 --- a/intern/cycles/device/device_opencl.cpp +++ b/intern/cycles/device/device_opencl.cpp @@ -881,7 +881,7 @@ public: mem_copy_to(*i->second); } - void tex_alloc(const char *name, device_memory& mem, bool interpolation, bool periodic) + void tex_alloc(const char *name, device_memory& mem, InterpolationType interpolation, bool periodic) { mem_alloc(mem, MEM_READ_ONLY); mem_copy_to(mem); diff --git a/intern/cycles/kernel/kernel.cpp b/intern/cycles/kernel/kernel.cpp index 6cd14d3..5d74fee 100644 --- a/intern/cycles/kernel/kernel.cpp +++ b/intern/cycles/kernel/kernel.cpp @@ -37,7 +37,7 @@ void kernel_const_copy(KernelGlobals *kg, const char *name, void *host, size_t s assert(0); } -void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t width, size_t height) +void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t width, size_t height, InterpolationType interpolation) { if(0) { } @@ -63,6 +63,7 @@ void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t tex->data = (float4*)mem; tex->width = width; tex->height = height; + tex->interpolation = interpolation; } } else if(strstr(name, "__tex_image")) { @@ -78,6 +79,7 @@ void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t tex->data = (uchar4*)mem; tex->width = width; tex->height = height; + tex->interpolation = interpolation; } } else diff --git a/intern/cycles/kernel/kernel.h b/intern/cycles/kernel/kernel.h index 039dc79..a4f13e7 100644 --- a/intern/cycles/kernel/kernel.h +++ b/intern/cycles/kernel/kernel.h @@ -32,7 +32,7 @@ void *kernel_osl_memory(KernelGlobals *kg); bool kernel_osl_use(KernelGlobals *kg); void kernel_const_copy(KernelGlobals *kg, const char *name, void *host, size_t size); -void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t width, size_t height); +void kernel_tex_copy(KernelGlobals *kg, const char *name, device_ptr mem, size_t width, size_t height, InterpolationType interpolation=INTERPOLATION_LINEAR); void kernel_cpu_path_trace(KernelGlobals *kg, float *buffer, unsigned int *rng_state, int sample, int x, int y, int offset, int stride); diff --git a/intern/cycles/kernel/kernel_compat_cpu.h b/intern/cycles/kernel/kernel_compat_cpu.h index a9c66ec..55f4484 100644 --- a/intern/cycles/kernel/kernel_compat_cpu.h +++ b/intern/cycles/kernel/kernel_compat_cpu.h @@ -117,14 +117,19 @@ template<typename T> struct texture_image { niy = wrap_clamp(iy+1, height); } - float4 r = (1.0f - ty)*(1.0f - tx)*read(data[ix + iy*width]); - r += (1.0f - ty)*tx*read(data[nix + iy*width]); - r += ty*(1.0f - tx)*read(data[ix + niy*width]); - r += ty*tx*read(data[nix + niy*width]); - - return r; + if(interpolation == INTERPOLATION_CLOSEST) { + return read(data[ix + iy*width]); + } + else { + float4 r = (1.0f - ty)*(1.0f - tx)*read(data[ix + iy*width]); + r += (1.0f - ty)*tx*read(data[nix + iy*width]); + r += ty*(1.0f - tx)*read(data[ix + niy*width]); + r += ty*tx*read(data[nix + niy*width]); + return r; + } } + int interpolation; T *data; int width, height; }; @@ -146,7 +151,6 @@ typedef texture_image<uchar4> texture_image_uchar4; #define kernel_tex_fetch_m128i(tex, index) (kg->tex.fetch_m128i(index)) #define kernel_tex_lookup(tex, t, offset, size) (kg->tex.lookup(t, offset, size)) #define kernel_tex_image_interp(tex, x, y) ((tex < MAX_FLOAT_IMAGES) ? kg->texture_float_images[tex].interp(x, y) : kg->texture_byte_images[tex - MAX_FLOAT_IMAGES].interp(x, y)) - #define kernel_data (kg->__data) CCL_NAMESPACE_END diff --git a/intern/cycles/kernel/shaders/node_image_texture.osl b/intern/cycles/kernel/shaders/node_image_texture.osl index caa7556..7238a1e 100644 --- a/intern/cycles/kernel/shaders/node_image_texture.osl +++ b/intern/cycles/kernel/shaders/node_image_texture.osl @@ -17,9 +17,9 @@ #include "stdosl.h" #include "node_color.h" -color image_texture_lookup(string filename, string color_space, float u, float v, output float Alpha, int use_alpha, int is_float) +color image_texture_lookup(string filename, string color_space, float u, float v, output float Alpha, int use_alpha, int is_float, string interpolation) { - color rgb = (color)texture(filename, u, 1.0 - v, "wrap", "periodic", "alpha", Alpha); + color rgb = (color)texture(filename, u, 1.0 - v, "wrap", "periodic", "interp", interpolation, "alpha", Alpha); if (use_alpha) { rgb = color_unpremultiply(rgb, Alpha); @@ -42,6 +42,7 @@ shader node_image_texture( string filename = "", string color_space = "sRGB", string projection = "Flat", + string interpolation = "smartcubic", float projection_blend = 0.0, int is_float = 1, int use_alpha = 1, @@ -54,7 +55,7 @@ shader node_image_texture( p = transform(mapping, p); if (projection == "Flat") { - Color = image_texture_lookup(filename, color_space, p[0], p[1], Alpha, use_alpha, is_float); + Color = image_texture_lookup(filename, color_space, p[0], p[1], Alpha, use_alpha, is_float, interpolation); } else if (projection == "Box") { /* o @@ Diff output truncated at 10240 characters. @@ _______________________________________________ Bf-blender-cvs mailing list [email protected] http://lists.blender.org/mailman/listinfo/bf-blender-cvs
