Blender V5.0
result.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 <cstdint>
6#include <optional>
7#include <string>
8#include <variant>
9
10#include "MEM_guardedalloc.h"
11
12#include "BLI_assert.h"
13#include "BLI_cpp_type.hh"
15#include "BLI_generic_span.hh"
18#include "BLI_utildefines.h"
19
20#include "GPU_shader.hh"
21#include "GPU_state.hh"
22#include "GPU_texture.hh"
23#include "GPU_texture_pool.hh"
24
25#include "COM_context.hh"
27#include "COM_domain.hh"
28#include "COM_result.hh"
29
30namespace blender::compositor {
31
32Result::Result(Context &context) : context_(&context) {}
33
35 : context_(&context), type_(type), precision_(precision)
36{
37}
38
40 : context_(&context), type_(Result::type(format)), precision_(Result::precision(format))
41{
42}
43
45{
46 switch (type) {
52 case ResultType::Int:
56 return false;
58 return true;
59 }
60
62 return true;
63}
64
66{
67 switch (precision) {
69 switch (type) {
71 return blender::gpu::TextureFormat::SFLOAT_16;
74 return blender::gpu::TextureFormat::SFLOAT_16_16_16_16;
76 /* RGB textures are not fully supported by hardware, so we store Float3 results in RGBA
77 * textures. */
78 return blender::gpu::TextureFormat::SFLOAT_16_16_16_16;
80 return blender::gpu::TextureFormat::SFLOAT_16_16;
81 case ResultType::Int:
82 return blender::gpu::TextureFormat::SINT_16;
84 return blender::gpu::TextureFormat::SINT_16_16;
86 /* No bool texture formats, so we store in an 8-bit integer. Precision doesn't matter. */
87 return blender::gpu::TextureFormat::SINT_8;
89 /* Menu values are technically stored in 32-bit integers, but 8 is sufficient in
90 * practice. */
91 return blender::gpu::TextureFormat::SINT_8;
93 /* Single only types do not support GPU code path. */
96 break;
97 }
98 break;
100 switch (type) {
102 return blender::gpu::TextureFormat::SFLOAT_32;
105 return blender::gpu::TextureFormat::SFLOAT_32_32_32_32;
107 /* RGB textures are not fully supported by hardware, so we store Float3 results in RGBA
108 * textures. */
109 return blender::gpu::TextureFormat::SFLOAT_32_32_32_32;
111 return blender::gpu::TextureFormat::SFLOAT_32_32;
112 case ResultType::Int:
113 return blender::gpu::TextureFormat::SINT_32;
114 case ResultType::Int2:
115 return blender::gpu::TextureFormat::SINT_32_32;
116 case ResultType::Bool:
117 /* No bool texture formats, so we store in an 8-bit integer. Precision doesn't matter. */
118 return blender::gpu::TextureFormat::SINT_8;
119 case ResultType::Menu:
120 /* Menu values are technically stored in 32-bit integers, but 8 is sufficient in
121 * practice. */
122 return blender::gpu::TextureFormat::SINT_8;
124 /* Single only types do not support GPU storage. */
127 break;
128 }
129 break;
130 }
131
133 return blender::gpu::TextureFormat::SFLOAT_32_32_32_32;
134}
135
137{
138 switch (type) {
144 return GPU_DATA_FLOAT;
145 case ResultType::Int:
146 case ResultType::Int2:
147 case ResultType::Bool:
148 case ResultType::Menu:
149 return GPU_DATA_INT;
151 /* Single only types do not support GPU storage. */
154 break;
155 }
156
158 return GPU_DATA_FLOAT;
159}
160
163{
164 switch (precision) {
166 switch (format) {
167 /* Already half precision, return the input format. */
168 case blender::gpu::TextureFormat::SFLOAT_16:
169 case blender::gpu::TextureFormat::SFLOAT_16_16:
170 case blender::gpu::TextureFormat::SFLOAT_16_16_16:
171 case blender::gpu::TextureFormat::SFLOAT_16_16_16_16:
172 case blender::gpu::TextureFormat::SINT_16:
173 case blender::gpu::TextureFormat::SINT_16_16:
174 return format;
175
176 /* Used to store booleans where precision doesn't matter. */
177 case blender::gpu::TextureFormat::SINT_8:
178 return format;
179
180 case blender::gpu::TextureFormat::SFLOAT_32:
181 return blender::gpu::TextureFormat::SFLOAT_16;
182 case blender::gpu::TextureFormat::SFLOAT_32_32:
183 return blender::gpu::TextureFormat::SFLOAT_16_16;
184 case blender::gpu::TextureFormat::SFLOAT_32_32_32:
185 return blender::gpu::TextureFormat::SFLOAT_16_16_16;
186 case blender::gpu::TextureFormat::SFLOAT_32_32_32_32:
187 return blender::gpu::TextureFormat::SFLOAT_16_16_16_16;
188 case blender::gpu::TextureFormat::SINT_32:
189 return blender::gpu::TextureFormat::SINT_16;
190 case blender::gpu::TextureFormat::SINT_32_32:
191 return blender::gpu::TextureFormat::SINT_16_16;
192 default:
193 break;
194 }
195 break;
197 switch (format) {
198 /* Already full precision, return the input format. */
199 case blender::gpu::TextureFormat::SFLOAT_32:
200 case blender::gpu::TextureFormat::SFLOAT_32_32:
201 case blender::gpu::TextureFormat::SFLOAT_32_32_32:
202 case blender::gpu::TextureFormat::SFLOAT_32_32_32_32:
203 case blender::gpu::TextureFormat::SINT_32:
204 case blender::gpu::TextureFormat::SINT_32_32:
205 return format;
206
207 /* Used to store booleans where precision doesn't matter. */
208 case blender::gpu::TextureFormat::SINT_8:
209 return format;
210
211 case blender::gpu::TextureFormat::SFLOAT_16:
212 return blender::gpu::TextureFormat::SFLOAT_32;
213 case blender::gpu::TextureFormat::SFLOAT_16_16:
214 return blender::gpu::TextureFormat::SFLOAT_32_32;
215 case blender::gpu::TextureFormat::SFLOAT_16_16_16:
216 return blender::gpu::TextureFormat::SFLOAT_32_32_32;
217 case blender::gpu::TextureFormat::SFLOAT_16_16_16_16:
218 return blender::gpu::TextureFormat::SFLOAT_32_32_32_32;
219 case blender::gpu::TextureFormat::SINT_16:
220 return blender::gpu::TextureFormat::SINT_32;
221 case blender::gpu::TextureFormat::SINT_16_16:
222 return blender::gpu::TextureFormat::SINT_32_32;
223 default:
224 break;
225 }
226 break;
227 }
228
230 return format;
231}
232
234{
235 switch (format) {
236 case blender::gpu::TextureFormat::SFLOAT_16:
237 case blender::gpu::TextureFormat::SFLOAT_16_16:
238 case blender::gpu::TextureFormat::SFLOAT_16_16_16:
239 case blender::gpu::TextureFormat::SFLOAT_16_16_16_16:
240 case blender::gpu::TextureFormat::SINT_16:
241 case blender::gpu::TextureFormat::SINT_16_16:
243 case blender::gpu::TextureFormat::SFLOAT_32:
244 case blender::gpu::TextureFormat::SFLOAT_32_32:
245 case blender::gpu::TextureFormat::SFLOAT_32_32_32:
246 case blender::gpu::TextureFormat::SFLOAT_32_32_32_32:
247 case blender::gpu::TextureFormat::SINT_32:
248 case blender::gpu::TextureFormat::SINT_32_32:
250 /* Used to store booleans where precision doesn't matter. */
251 case blender::gpu::TextureFormat::SINT_8:
253 default:
254 break;
255 }
256
259}
260
262{
263 switch (format) {
264 case blender::gpu::TextureFormat::SFLOAT_16:
265 case blender::gpu::TextureFormat::SFLOAT_32:
266 return ResultType::Float;
267 case blender::gpu::TextureFormat::SFLOAT_16_16:
268 case blender::gpu::TextureFormat::SFLOAT_32_32:
269 return ResultType::Float2;
270 case blender::gpu::TextureFormat::SFLOAT_16_16_16:
271 case blender::gpu::TextureFormat::SFLOAT_32_32_32:
272 return ResultType::Float3;
273 case blender::gpu::TextureFormat::SFLOAT_16_16_16_16:
274 case blender::gpu::TextureFormat::SFLOAT_32_32_32_32:
275 return ResultType::Color;
276 case blender::gpu::TextureFormat::SINT_16:
277 case blender::gpu::TextureFormat::SINT_32:
278 return ResultType::Int;
279 case blender::gpu::TextureFormat::SINT_16_16:
280 case blender::gpu::TextureFormat::SINT_32_32:
281 return ResultType::Int2;
282 case blender::gpu::TextureFormat::SINT_8:
283 return ResultType::Bool;
284 default:
285 break;
286 }
287
289 return ResultType::Color;
290}
291
293{
294 switch (channels_count) {
295 case 1:
296 return ResultType::Float;
297 case 2:
298 return ResultType::Float2;
299 case 3:
300 return ResultType::Float3;
301 case 4:
302 return ResultType::Color;
303 default:
304 break;
305 }
306
308 return ResultType::Color;
309}
310
312{
313 switch (type) {
315 return CPPType::get<float>();
316 case ResultType::Int:
317 return CPPType::get<int32_t>();
319 return CPPType::get<float4>();
321 return CPPType::get<float4>();
323 return CPPType::get<float2>();
325 return CPPType::get<float3>();
326 case ResultType::Int2:
327 return CPPType::get<int2>();
328 case ResultType::Bool:
329 return CPPType::get<bool>();
330 case ResultType::Menu:
334 }
335
337 return CPPType::get<float>();
338}
339
341{
342 switch (type) {
344 return "float";
346 return "float2";
348 return "float3";
350 return "float4";
352 return "color";
353 case ResultType::Int2:
354 return "int2";
355 case ResultType::Int:
356 return "int";
357 case ResultType::Bool:
358 return "bool";
359 case ResultType::Menu:
360 return "menu";
362 return "string";
363 }
364
366 return "";
367}
368
369Result::operator blender::gpu::Texture *() const
370{
371 return this->gpu_texture();
372}
373
375{
376 return Result::cpp_type(this->type());
377}
378
383
388
390 const bool from_pool,
391 const std::optional<ResultStorageType> storage_type)
392{
393 /* Make sure we are not allocating a result that should not be computed. */
394 BLI_assert(this->should_compute());
396
397 is_single_value_ = false;
398 this->allocate_data(domain.size, from_pool, storage_type);
399 domain_ = domain;
400}
401
403{
404 /* Make sure we are not allocating a result that should not be computed. */
405 BLI_assert(this->should_compute());
406
407 is_single_value_ = true;
408
409 /* Single values are stored in 1x1 image as well as the single value members. Further, they are
410 * always allocated from the pool. Finally, single value only types do not support GPU code
411 * paths, so we always allocate on CPU. */
413 this->allocate_data(int2(1), true, ResultStorageType::CPU);
414 }
415 else {
416 this->allocate_data(int2(1), true);
417 }
418
419 domain_ = Domain::identity();
420
421 /* It is important that we initialize single values because the variant member that stores single
422 * values need to have its type initialized. */
423 switch (type_) {
425 this->set_single_value(0.0f);
426 break;
428 this->set_single_value(float4(0.0f));
429 break;
431 this->set_single_value(float4(0.0f));
432 break;
434 this->set_single_value(float2(0.0f));
435 break;
437 this->set_single_value(float3(0.0f));
438 break;
439 case ResultType::Int:
440 this->set_single_value(0);
441 break;
442 case ResultType::Int2:
443 this->set_single_value(int2(0));
444 break;
445 case ResultType::Bool:
446 this->set_single_value(false);
447 break;
448 case ResultType::Menu:
450 break;
452 this->set_single_value(std::string(""));
453 break;
454 }
455}
456
461
462Result Result::upload_to_gpu(const bool from_pool) const
463{
464 BLI_assert(storage_type_ == ResultStorageType::CPU);
465 BLI_assert(this->is_allocated());
466
467 Result result = Result(*context_, this->type(), this->precision());
468 result.allocate_texture(this->domain().size, from_pool, ResultStorageType::GPU);
469
471 return result;
472}
473
475{
476 BLI_assert(storage_type_ == ResultStorageType::GPU);
477 BLI_assert(this->is_allocated());
478
479 Result result = Result(*context_, this->type(), this->precision());
481 void *data = GPU_texture_read(*this, this->get_gpu_data_format(), 0);
482 result.steal_data(data, this->domain().size);
483
484 return result;
485}
486
487void Result::bind_as_texture(gpu::Shader *shader, const char *texture_name) const
488{
489 BLI_assert(storage_type_ == ResultStorageType::GPU);
490
491 /* Make sure any prior writes to the texture are reflected before reading from it. */
493
494 const int texture_image_unit = GPU_shader_get_sampler_binding(shader, texture_name);
495 GPU_texture_bind(this->gpu_texture(), texture_image_unit);
496}
497
498void Result::bind_as_image(gpu::Shader *shader, const char *image_name, bool read) const
499{
500 BLI_assert(storage_type_ == ResultStorageType::GPU);
501
502 /* Make sure any prior writes to the texture are reflected before reading from it. */
503 if (read) {
505 }
506
507 const int image_unit = GPU_shader_get_sampler_binding(shader, image_name);
508 GPU_texture_image_bind(this->gpu_texture(), image_unit);
509}
510
512{
513 BLI_assert(storage_type_ == ResultStorageType::GPU);
515}
516
518{
519 BLI_assert(storage_type_ == ResultStorageType::GPU);
521}
522
523void Result::share_data(const Result &source)
524{
525 BLI_assert(type_ == source.type_);
526 BLI_assert(!this->is_allocated() && source.is_allocated());
527
528 /* Overwrite everything except reference count. */
529 const int reference_count = reference_count_;
530 *this = source;
531 reference_count_ = reference_count;
532
533 /* External data is intrinsically shared, and data_reference_count_ is nullptr in this case since
534 * it is not needed. */
535 if (!is_external_) {
536 (*data_reference_count_)++;
537 }
538}
539
541{
542 BLI_assert(type_ == source.type_);
543 BLI_assert(precision_ == source.precision_);
544 BLI_assert(!this->is_allocated() && source.is_allocated());
545
546 /* Overwrite everything except reference counts. */
547 const int reference_count = reference_count_;
548 *this = source;
549 reference_count_ = reference_count;
550
551 source = Result(*context_, type_, precision_);
552}
553
555{
556 BLI_assert(!this->is_allocated());
557
558 const int64_t array_size = int64_t(size.x) * int64_t(size.y);
559 cpu_data_ = GMutableSpan(this->get_cpp_type(), data, array_size);
560 storage_type_ = ResultStorageType::CPU;
561 domain_ = Domain(size);
562 data_reference_count_ = new int(1);
563}
564
565/* Returns true if the given GPU texture is compatible with the type and precision of the given
566 * result. */
567[[maybe_unused]] static bool is_compatible_texture(const blender::gpu::Texture *texture,
568 const Result &result)
569{
570 /* Float3 types are an exception, see the documentation on the get_gpu_texture_format method for
571 * more information. */
572 if (result.type() == ResultType::Float3) {
574 Result::gpu_texture_format(blender::gpu::TextureFormat::SFLOAT_32_32_32,
575 result.precision()))
576 {
577 return true;
578 }
579 }
580
581 return GPU_texture_format(texture) == result.get_gpu_texture_format();
582}
583
585{
587 BLI_assert(!this->is_allocated());
588
590 storage_type_ = ResultStorageType::GPU;
591 is_external_ = true;
592 is_single_value_ = false;
594}
595
597{
598 BLI_assert(!this->is_allocated());
599
600 const int64_t array_size = int64_t(size.x) * int64_t(size.y);
601 cpu_data_ = GMutableSpan(this->get_cpp_type(), data, array_size);
602 storage_type_ = ResultStorageType::CPU;
603 is_external_ = true;
604 domain_ = Domain(size);
605}
606
608{
609 BLI_assert(type_ == result.type());
610 BLI_assert(precision_ == result.precision());
611 BLI_assert(!this->is_allocated());
612
613 /* Steal the data of the given result and mark it as wrapping external data, but create a
614 * temporary copy of the result first, since steal_data will reset it. */
615 Result result_copy = result;
616 this->steal_data(result_copy);
617 is_external_ = true;
618}
619
620void Result::set_transformation(const float3x3 &transformation)
621{
622 domain_.transformation = transformation;
623}
624
625void Result::transform(const float3x3 &transformation)
626{
627 domain_.transform(transformation);
628}
629
631{
632 return domain_.realization_options;
633}
634
636{
637 return domain_.realization_options;
638}
639
641{
642 reference_count_ = count;
643}
644
646{
647 reference_count_ += count;
648}
649
651{
652 reference_count_ -= count;
653}
654
656{
657 /* Decrement the reference count, and if it is not yet zero, return and do not free. */
658 reference_count_--;
659 BLI_assert(reference_count_ >= 0);
660 if (reference_count_ != 0) {
661 return;
662 }
663
664 this->free();
665}
666
668{
669 if (is_external_) {
670 return;
671 }
672
673 if (!this->is_allocated()) {
674 return;
675 }
676
677 /* Data is still shared with some other result, so decrement data reference count and reset data
678 * members without actually freeing the data itself. */
679 BLI_assert(*data_reference_count_ >= 1);
680 if (*data_reference_count_ != 1) {
681 (*data_reference_count_)--;
682
683 switch (storage_type_) {
685 gpu_texture_ = nullptr;
686 break;
689 break;
690 }
691
692 data_reference_count_ = nullptr;
693 derived_resources_ = nullptr;
694
695 return;
696 }
697
698 switch (storage_type_) {
700 if (is_from_pool_) {
702 }
703 else {
705 }
706 gpu_texture_ = nullptr;
707 break;
709 MEM_freeN(this->cpu_data().data());
711 break;
712 }
713
714 delete data_reference_count_;
715 data_reference_count_ = nullptr;
716
717 delete derived_resources_;
718 derived_resources_ = nullptr;
719}
720
722{
723 return reference_count_ != 0;
724}
725
727{
728 if (!derived_resources_) {
729 derived_resources_ = new DerivedResources();
730 }
731 return *derived_resources_;
732}
733
735{
736 return type_;
737}
738
740{
741 return precision_;
742}
743
745{
746 /* Changing the type can only be done if it wasn't allocated yet. */
747 BLI_assert(!this->is_allocated());
748 type_ = type;
749}
750
752{
753 /* Changing the precision can only be done if it wasn't allocated yet. */
754 BLI_assert(!this->is_allocated());
755 precision_ = precision;
756}
757
759{
760 return is_single_value_;
761}
762
764{
765 switch (storage_type_) {
767 return this->gpu_texture();
769 return this->cpu_data().data();
770 }
771
772 return false;
773}
774
776{
777 return reference_count_;
778}
779
781{
782 const int64_t pixel_size = this->get_cpp_type().size;
783 if (this->is_single_value()) {
784 return pixel_size;
785 }
786 const int2 image_size = this->domain().size;
787 return pixel_size * image_size.x * image_size.y;
788}
789
791{
792 return std::visit([](const auto &value) { return GPointer(&value); }, single_value_);
793}
794
796{
797 return std::visit([](auto &value) { return GMutablePointer(&value); }, single_value_);
798}
799
801{
803 BLI_assert(this->is_allocated());
804
805 switch (storage_type_) {
807 switch (type_) {
812 case ResultType::Int:
813 case ResultType::Int2:
814 case ResultType::Bool:
815 case ResultType::Menu:
817 this->gpu_texture(), this->get_gpu_data_format(), this->single_value().get());
818 break;
819 case ResultType::Float3: {
820 /* Float3 results are stored in 4-component textures due to hardware limitations. So
821 * pad the value with a zero before updating. */
822 const float4 vector_value = float4(this->get_single_value<float3>(), 0.0f);
823 GPU_texture_update(this->gpu_texture(), GPU_DATA_FLOAT, vector_value);
824 break;
825 }
827 /* Single only types do not support GPU storage. */
830 break;
831 }
832 break;
834 this->get_cpp_type().copy_assign(this->single_value().get(), this->cpu_data().data());
835 break;
836 }
837}
838
839void Result::allocate_data(const int2 size,
840 const bool from_pool,
841 const std::optional<ResultStorageType> storage_type)
842{
843 BLI_assert(!this->is_allocated());
844
845 const bool use_gpu = storage_type.has_value() ? storage_type.value() == ResultStorageType::GPU :
846 context_->use_gpu();
847 if (use_gpu) {
848 storage_type_ = ResultStorageType::GPU;
849 is_from_pool_ = from_pool;
850
853 if (from_pool) {
855 }
856 else {
857 gpu_texture_ = GPU_texture_create_2d(__func__, size.x, size.y, 1, format, usage, nullptr);
858 }
859 }
860 else {
861 storage_type_ = ResultStorageType::CPU;
862
863 const CPPType &cpp_type = this->get_cpp_type();
864 const int64_t item_size = cpp_type.size;
865 const int64_t alignment = cpp_type.alignment;
866 const int64_t array_size = int64_t(size.x) * int64_t(size.y);
867 const int64_t memory_size = array_size * item_size;
868
869 void *data = MEM_mallocN_aligned(memory_size, alignment, AT);
870 cpp_type.default_construct_n(data, array_size);
871
872 cpu_data_ = GMutableSpan(cpp_type, data, array_size);
873 }
874
875 data_reference_count_ = new int(1);
876}
877
878} // namespace blender::compositor
#define BLI_assert_unreachable()
Definition BLI_assert.h:93
#define BLI_assert(a)
Definition BLI_assert.h:46
#define AT
int GPU_shader_get_sampler_binding(blender::gpu::Shader *shader, const char *name)
@ GPU_BARRIER_TEXTURE_FETCH
Definition GPU_state.hh:37
@ GPU_BARRIER_SHADER_IMAGE_ACCESS
Definition GPU_state.hh:35
@ GPU_BARRIER_TEXTURE_UPDATE
Definition GPU_state.hh:39
void GPU_memory_barrier(GPUBarrier barrier)
Definition gpu_state.cc:326
int GPU_texture_height(const blender::gpu::Texture *texture)
blender::gpu::TextureFormat GPU_texture_format(const blender::gpu::Texture *texture)
void GPU_texture_unbind(blender::gpu::Texture *texture)
int GPU_texture_width(const blender::gpu::Texture *texture)
eGPUDataFormat
@ GPU_DATA_INT
@ GPU_DATA_FLOAT
eGPUTextureUsage
@ GPU_TEXTURE_USAGE_GENERAL
void * GPU_texture_read(blender::gpu::Texture *texture, eGPUDataFormat data_format, int mip_level)
void GPU_texture_image_bind(blender::gpu::Texture *texture, int unit)
void GPU_texture_image_unbind(blender::gpu::Texture *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_bind(blender::gpu::Texture *texture, int unit)
void GPU_texture_free(blender::gpu::Texture *texture)
void GPU_texture_update(blender::gpu::Texture *texture, eGPUDataFormat data_format, const void *data)
Read Guarded memory(de)allocation.
BMesh const char void * data
long long int int64_t
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
Definition btDbvt.cpp:52
static const CPPType & get()
void copy_assign(const void *src, void *dst) const
const void * data() const
virtual bool use_gpu() const =0
static Domain identity()
Definition domain.cc:36
void decrement_reference_count(int count=1)
Definition result.cc:650
void share_data(const Result &source)
Definition result.cc:523
RealizationOptions & get_realization_options()
Definition result.cc:630
Result upload_to_gpu(const bool from_pool) const
Definition result.cc:462
const CPPType & get_cpp_type() const
Definition result.cc:374
int reference_count() const
Definition result.cc:775
void allocate_texture(const Domain domain, const bool from_pool=true, const std::optional< ResultStorageType > storage_type=std::nullopt)
Definition result.cc:389
static eGPUDataFormat gpu_data_format(const ResultType type)
Definition result.cc:136
int64_t size_in_bytes() const
Definition result.cc:780
void wrap_external(blender::gpu::Texture *texture)
Definition result.cc:584
void unbind_as_texture() const
Definition result.cc:511
Result download_to_cpu() const
Definition result.cc:474
static blender::gpu::TextureFormat gpu_texture_format(ResultType type, ResultPrecision precision)
Definition result.cc:65
static const char * type_name(const ResultType type)
Definition result.cc:340
bool is_allocated() const
Definition result.cc:763
void set_transformation(const float3x3 &transformation)
Definition result.cc:620
static bool is_single_value_only_type(ResultType type)
Definition result.cc:44
GPointer single_value() const
Definition result.cc:790
blender::gpu::Texture * gpu_texture_
blender::gpu::TextureFormat get_gpu_texture_format() const
Definition result.cc:379
eGPUDataFormat get_gpu_data_format() const
Definition result.cc:384
void set_single_value(const T &value)
static ResultType type(blender::gpu::TextureFormat format)
Definition result.cc:261
void bind_as_texture(gpu::Shader *shader, const char *texture_name) const
Definition result.cc:487
ResultPrecision precision() const
Definition result.cc:739
ResultType type() const
Definition result.cc:734
blender::gpu::Texture * gpu_texture() const
static ResultType float_type(const int channels_count)
Definition result.cc:292
void set_precision(ResultPrecision precision)
Definition result.cc:751
void transform(const float3x3 &transformation)
Definition result.cc:625
void increment_reference_count(int count=1)
Definition result.cc:645
const Domain & domain() const
static const CPPType & cpp_type(const ResultType type)
Definition result.cc:311
int64_t channels_count() const
void unbind_as_image() const
Definition result.cc:517
static ResultPrecision precision(blender::gpu::TextureFormat format)
Definition result.cc:233
Result(Context &context)
Definition result.cc:32
DerivedResources & derived_resources()
Definition result.cc:726
void bind_as_image(gpu::Shader *shader, const char *image_name, bool read=false) const
Definition result.cc:498
void set_reference_count(int count)
Definition result.cc:640
bool is_single_value() const
Definition result.cc:758
void steal_data(Result &source)
Definition result.cc:540
const T & get_single_value() const
void set_type(ResultType type)
Definition result.cc:744
blender::gpu::Texture * acquire_texture(int width, int height, blender::gpu::TextureFormat format, eGPUTextureUsage usage)
static TexturePool & get()
void release_texture(blender::gpu::Texture *tmp_tex)
TEX_TEMPLATE DataVec texture(T, FltCoord, float=0.0f) RET
int count
format
void * MEM_mallocN_aligned(size_t len, size_t alignment, const char *str)
Definition mallocn.cc:138
void MEM_freeN(void *vmemh)
Definition mallocn.cc:113
static bool is_compatible_texture(const blender::gpu::Texture *texture, const Result &result)
Definition result.cc:567
VecBase< float, 4 > float4
VecBase< int32_t, 2 > int2
VecBase< float, 2 > float2
MatBase< float, 3, 3 > float3x3
VecBase< float, 3 > float3