Blender V5.0
sample_pixel.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2025 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
5#include "MEM_guardedalloc.h"
6
7#include "GPU_compute.hh"
8#include "GPU_shader.hh"
9#include "GPU_state.hh"
10#include "GPU_texture.hh"
11#include "GPU_texture_pool.hh"
12
13#include "COM_context.hh"
14#include "COM_result.hh"
15
17
18namespace blender::compositor {
19
20static char const *get_pixel_sampler_shader_name(const Interpolation &interpolation)
21{
22 switch (interpolation) {
25 return "compositor_sample_pixel_bicubic";
28 return "compositor_sample_pixel";
29 }
31 return "compositor_sample_pixel";
32}
33
35 const Result &input,
36 const Interpolation &interpolation,
37 const ExtensionMode &extension_mode_x,
38 const ExtensionMode &extension_mode_y,
39 const float2 coordinates)
40{
41 gpu::Shader *shader = context.get_shader(get_pixel_sampler_shader_name(interpolation));
42 GPU_shader_bind(shader);
43
44 GPU_shader_uniform_2fv(shader, "coordinates_u", coordinates);
45
46 Result output = context.create_result(input.type());
47 output.allocate_texture(int2(1));
48
49 if (interpolation == Interpolation::Anisotropic) {
51 GPU_texture_mipmap_mode(input, true, true);
52 }
53 else {
54 const bool use_bilinear = ELEM(interpolation, Interpolation::Bilinear, Interpolation::Bicubic);
55 GPU_texture_filter_mode(input, use_bilinear);
56 }
57
60
61 input.bind_as_texture(shader, "input_tx");
62 output.bind_as_image(shader, "output_img");
63
64 GPU_compute_dispatch(shader, 1, 1, 1);
65
66 input.unbind_as_texture();
67 output.unbind_as_image();
69
71 float *pixel = static_cast<float *>(GPU_texture_read(output, GPU_DATA_FLOAT, 0));
72 output.release();
73
74 float4 sampled_value = float4(0.0f, 0.0f, 0.0f, 1.0f);
75 output.get_cpp_type().copy_assign(pixel, sampled_value);
76
77 MEM_freeN(pixel);
78
79 return sampled_value;
80}
81
83 const Interpolation &interpolation,
84 const ExtensionMode &extension_mode_x,
85 const ExtensionMode &extension_mode_y,
86 const float2 coordinates)
87{
88 return input.sample(coordinates, interpolation, extension_mode_x, extension_mode_y);
89}
90
91/* Samples a pixel from a result. */
93 const Result &input,
94 const Interpolation &interpolation,
95 const ExtensionMode &extension_mode_x,
96 const ExtensionMode &extension_mode_y,
97 const float2 coordinates)
98{
99 if (input.is_single_value()) {
100 switch (input.type()) {
102 return float4(input.get_single_value<float>(), 0.0f, 0.0f, 1.0f);
104 return float4(input.get_single_value<float2>(), 0.0f, 1.0f);
106 return float4(input.get_single_value<float3>(), 1.0f);
109 return input.get_single_value<float4>();
110 default:
111 break;
112 }
113
115 return float4(0.0f);
116 }
117 if (context.use_gpu()) {
118 return sample_pixel_gpu(
119 context, input, interpolation, extension_mode_x, extension_mode_y, coordinates);
120 }
121 else {
122 return sample_pixel_cpu(input, interpolation, extension_mode_x, extension_mode_y, coordinates);
123 }
124}
125
126} // namespace blender::compositor
#define BLI_assert_unreachable()
Definition BLI_assert.h:93
#define ELEM(...)
void GPU_compute_dispatch(blender::gpu::Shader *shader, uint groups_x_len, uint groups_y_len, uint groups_z_len, const blender::gpu::shader::SpecializationConstants *constants_state=nullptr)
void GPU_shader_bind(blender::gpu::Shader *shader, const blender::gpu::shader::SpecializationConstants *constants_state=nullptr)
void GPU_shader_uniform_2fv(blender::gpu::Shader *sh, const char *name, const float data[2])
void GPU_shader_unbind()
@ GPU_BARRIER_TEXTURE_UPDATE
Definition GPU_state.hh:39
void GPU_memory_barrier(GPUBarrier barrier)
Definition gpu_state.cc:326
void GPU_texture_extend_mode_y(blender::gpu::Texture *texture, GPUSamplerExtendMode extend_mode)
void GPU_texture_extend_mode_x(blender::gpu::Texture *texture, GPUSamplerExtendMode extend_mode)
void GPU_texture_anisotropic_filter(blender::gpu::Texture *texture, bool use_aniso)
@ GPU_DATA_FLOAT
void GPU_texture_mipmap_mode(blender::gpu::Texture *texture, bool use_mipmap, bool use_filter)
void * GPU_texture_read(blender::gpu::Texture *texture, eGPUDataFormat data_format, int mip_level)
void GPU_texture_filter_mode(blender::gpu::Texture *texture, bool use_filter)
Read Guarded memory(de)allocation.
#define input
#define output
void MEM_freeN(void *vmemh)
Definition mallocn.cc:113
float4 sample_pixel(Context &context, const Result &input, const Interpolation &interpolation, const ExtensionMode &extension_mode_x, const ExtensionMode &extension_mode_y, const float2 coordinates)
static char const * get_pixel_sampler_shader_name(const Interpolation &interpolation)
GPUSamplerExtendMode map_extension_mode_to_extend_mode(const ExtensionMode &mode)
Definition domain.cc:70
static float4 sample_pixel_cpu(const Result &input, const Interpolation &interpolation, const ExtensionMode &extension_mode_x, const ExtensionMode &extension_mode_y, const float2 coordinates)
static float4 sample_pixel_gpu(Context &context, const Result &input, const Interpolation &interpolation, const ExtensionMode &extension_mode_x, const ExtensionMode &extension_mode_y, const float2 coordinates)
VecBase< float, 4 > float4
VecBase< int32_t, 2 > int2
VecBase< float, 2 > float2
VecBase< float, 3 > float3