ACloudViewer  3.9.4
A Modern Library for 3D Data Processing
Renderer.cpp
Go to the documentation of this file.
1 // ----------------------------------------------------------------------------
2 // - CloudViewer: www.cloudViewer.org -
3 // ----------------------------------------------------------------------------
4 // Copyright (c) 2018-2024 www.cloudViewer.org
5 // SPDX-License-Identifier: MIT
6 // ----------------------------------------------------------------------------
7 
9 
10 #include <Image.h>
11 #include <Logging.h>
12 
17 
18 namespace cloudViewer {
19 namespace visualization {
20 namespace rendering {
21 
23  [](const ResourceLoadRequest& request,
24  const uint8_t code,
25  const std::string& details) {
26  if (!request.path_.empty()) {
28  "Resource request for path {} failed:\n* Code: {}\n* "
29  "Error: {}",
30  request.path_.data(), code, details.data());
31  } else if (request.data_size_ > 0) {
33  "Resource request failed:\n* Code: {}\n * Error: {}",
34  code, details.data());
35  } else {
37  "Resource request failed: Malformed request");
38  }
39  };
40 
41 ResourceLoadRequest::ResourceLoadRequest(const void* data, size_t data_size)
42  : data_(data),
43  data_size_(data_size),
44  path_(""),
45  error_callback_(kDefaultErrorHandler) {}
46 
48  : data_(nullptr),
49  data_size_(0u),
50  path_(path),
51  error_callback_(kDefaultErrorHandler) {}
52 
54  size_t data_size,
55  ErrorCallback error_callback)
56  : data_(data),
57  data_size_(data_size),
58  path_(""),
59  error_callback_(std::move(error_callback)) {}
60 
62  ErrorCallback error_callback)
63  : data_(nullptr),
64  data_size_(0u),
65  path_(path),
66  error_callback_(std::move(error_callback)) {}
67 
69  View* view,
70  Scene* scene,
71  std::function<void(std::shared_ptr<geometry::Image>)> cb) {
72  auto vp = view->GetViewport();
73  auto render = CreateBufferRenderer();
74  render->Configure(
75  view, scene, vp[2], vp[3], 3, false,
76  // the shared_ptr (render) is const unless the lambda
77  // is made mutable
78  [render, cb](const RenderToBuffer::Buffer& buffer) mutable {
79  auto image = std::make_shared<geometry::Image>();
80  image->width_ = int(buffer.width);
81  image->height_ = int(buffer.height);
82  image->num_of_channels_ = 3;
83  image->bytes_per_channel_ = 1;
84  image->data_ = std::vector<uint8_t>(buffer.bytes,
85  buffer.bytes + buffer.size);
86  cb(image);
87  // This does not actually cause the object to be destroyed--
88  // the lambda still has a copy--but it does ensure that the
89  // object lives long enough for the callback to get executed.
90  // The object will be freed when the callback is unassigned.
91  render = nullptr;
92  });
93 }
94 
96  View* view,
97  Scene* scene,
98  std::function<void(std::shared_ptr<geometry::Image>)> cb,
99  bool z_in_view_space /* = false */) {
100  auto vp = view->GetViewport();
101  auto render = CreateBufferRenderer();
102  double z_near = view->GetCamera()->GetNear();
103  render->Configure(
104  view, scene, vp[2], vp[3], 1, true,
105  // the shared_ptr (render) is const unless the lambda
106  // is made mutable
107  [render, cb, z_in_view_space,
108  z_near](const RenderToBuffer::Buffer& buffer) mutable {
109  auto image = std::make_shared<geometry::Image>();
110  image->width_ = int(buffer.width);
111  image->height_ = int(buffer.height);
112  image->num_of_channels_ = 1;
113  image->bytes_per_channel_ = 4;
114  image->data_.resize(image->width_ * image->height_ *
115  image->num_of_channels_ *
116  image->bytes_per_channel_);
117  memcpy(image->data_.data(), buffer.bytes, buffer.size);
118  // Filament's shaders calculate depth ranging from 1
119  // (near) to 0 (far), which is reversed from what is
120  // normally done, so convert here so that users do not
121  // need to rediscover Filament internals. (And so we
122  // can change it back if Filament decides to swap how
123  // they do it again.)
124  float* pixels = (float*)image->data_.data();
125  int n_pixels = image->width_ * image->height_;
126  if (z_in_view_space) {
127  for (int i = 0; i < n_pixels; ++i) {
128  if (pixels[i] == 0.f) {
130  } else {
131  pixels[i] = z_near / pixels[i];
132  }
133  }
134  } else {
135  for (int i = 0; i < n_pixels; ++i) {
136  pixels[i] = 1.0f - pixels[i];
137  }
138  }
139 
140  cb(image);
141  // This does not actually cause the object to be
142  // destroyed-- the lambda still has a copy--but it
143  // does ensure that the object lives long enough for
144  // the callback to get executed. The object will be
145  // freed when the callback is unassigned.
146  render = nullptr;
147  });
148 }
149 
150 } // namespace rendering
151 } // namespace visualization
152 } // namespace cloudViewer
std::shared_ptr< core::Tensor > image
void RenderToImage(View *view, Scene *scene, std::function< void(std::shared_ptr< geometry::Image >)> cb)
Definition: Renderer.cpp:68
virtual std::shared_ptr< RenderToBuffer > CreateBufferRenderer()=0
void RenderToDepthImage(View *view, Scene *scene, std::function< void(std::shared_ptr< geometry::Image >)> cb, bool z_in_view_space=false)
Definition: Renderer.cpp:95
std::function< void(const ResourceLoadRequest &, const uint8_t, const std::string &)> ErrorCallback
Definition: Renderer.h:42
ResourceLoadRequest(const void *data, size_t data_size)
Definition: Renderer.cpp:41
virtual Camera * GetCamera() const =0
virtual std::array< int, 4 > GetViewport() const =0
#define LogWarning(...)
Definition: Logging.h:72
__device__ __forceinline__ float infinity()
Definition: result_set.h:36
static const std::string path
Definition: PointCloud.cpp:59
static const ResourceLoadRequest::ErrorCallback kDefaultErrorHandler
Definition: Renderer.cpp:22
Generic file read and write utility for python interface.
Definition: Eigen.h:85