Blender V5.0
smaa_precomputed_textures.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2023 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
5#include <memory>
6
7#include "BLI_smaa_textures.h"
8
9#include "GPU_shader.hh"
10#include "GPU_texture.hh"
11
12#include "COM_context.hh"
13#include "COM_result.hh"
15#include "COM_utilities.hh"
16
17namespace blender::compositor {
18
19/* ------------------------------------------------------------------------------------------------
20 * SMAA Precomputed Textures.
21 */
22
24 : search_texture(context.create_result(ResultType::Float)),
25 area_texture(context.create_result(ResultType::Float2))
26{
27 if (context.use_gpu()) {
28 this->compute_gpu();
29 }
30 else {
31 this->compute_cpu();
32 }
33}
34
36{
37 GPU_TEXTURE_FREE_SAFE(search_texture_);
38 GPU_TEXTURE_FREE_SAFE(area_texture_);
39 this->search_texture.release();
40 this->area_texture.release();
41}
42
44 const char *sampler_name) const
45{
46 const int texture_image_unit = GPU_shader_get_sampler_binding(shader, sampler_name);
47 GPU_texture_bind(search_texture_, texture_image_unit);
48}
49
54
56 const char *sampler_name) const
57{
58 const int texture_image_unit = GPU_shader_get_sampler_binding(shader, sampler_name);
59 GPU_texture_bind(area_texture_, texture_image_unit);
60}
61
66
67void SMAAPrecomputedTextures::compute_gpu()
68{
69 search_texture_ = GPU_texture_create_2d("SMAA Search",
72 1,
73 blender::gpu::TextureFormat::UNORM_8,
75 nullptr);
77 GPU_texture_filter_mode(search_texture_, true);
78
79 area_texture_ = GPU_texture_create_2d("SMAA Area",
82 1,
83 blender::gpu::TextureFormat::UNORM_8_8,
85 nullptr);
87 GPU_texture_filter_mode(area_texture_, true);
88}
89
90void SMAAPrecomputedTextures::compute_cpu()
91{
92 const int2 search_texture_size = int2(SEARCHTEX_WIDTH, SEARCHTEX_HEIGHT);
93 search_texture.allocate_texture(Domain(search_texture_size), false);
94 parallel_for(search_texture_size, [&](const int2 texel) {
95 const float value = searchTexBytes[int64_t(texel.y) * search_texture_size.x + texel.x] /
96 255.0f;
97 search_texture.store_pixel(texel, value);
98 });
99
100 const int2 area_texture_size = int2(AREATEX_WIDTH, AREATEX_HEIGHT);
101 area_texture.allocate_texture(Domain(area_texture_size), false);
102 parallel_for(area_texture_size, [&](const int2 texel) {
103 const float2 value = float2(uchar2(areaTexBytes +
104 (int64_t(texel.y) * area_texture_size.x + texel.x) * 2)) /
105 255.0f;
106 area_texture.store_pixel(texel, value);
107 });
108}
109
110/* ------------------------------------------------------------------------------------------------
111 * SMAA Precomputed Textures Container.
112 */
113
115{
116 /* First, delete the textures if they are no longer needed. */
117 if (textures_ && !textures_->needed) {
118 textures_.reset();
119 }
120
121 /* Second, if they were not deleted, reset their needed status to false to ready them to track
122 * their needed status for the next evaluation. */
123 if (textures_) {
124 textures_->needed = false;
125 }
126}
127
129{
130 if (!textures_) {
131 textures_ = std::make_unique<SMAAPrecomputedTextures>(context);
132 }
133
134 textures_->needed = true;
135 return *textures_;
136}
137
138} // namespace blender::compositor
#define SEARCHTEX_HEIGHT
const unsigned char searchTexBytes[]
#define SEARCHTEX_WIDTH
#define AREATEX_HEIGHT
const unsigned char areaTexBytes[]
#define AREATEX_WIDTH
int GPU_shader_get_sampler_binding(blender::gpu::Shader *shader, const char *name)
void GPU_texture_unbind(blender::gpu::Texture *texture)
@ GPU_DATA_UBYTE
@ GPU_TEXTURE_USAGE_SHADER_READ
#define GPU_TEXTURE_FREE_SAFE(texture)
blender::gpu::Texture * GPU_texture_create_2d(const char *name, int width, int height, int mip_len, blender::gpu::TextureFormat format, eGPUTextureUsage usage, const float *data)
void GPU_texture_filter_mode(blender::gpu::Texture *texture, bool use_filter)
void GPU_texture_bind(blender::gpu::Texture *texture, int unit)
void GPU_texture_update(blender::gpu::Texture *texture, eGPUDataFormat data_format, const void *data)
long long int int64_t
void store_pixel(const int2 &texel, const T &pixel_value)
void allocate_texture(const Domain domain, const bool from_pool=true, const std::optional< ResultStorageType > storage_type=std::nullopt)
Definition result.cc:389
void bind_area_texture(gpu::Shader *shader, const char *sampler_name) const
void bind_search_texture(gpu::Shader *shader, const char *sampler_name) const
void parallel_for(const int2 range, const Function &function)
blender::VecBase< uint8_t, 2 > uchar2
VecBase< int32_t, 2 > int2
VecBase< float, 2 > float2