Blender  V3.3
COM_ViewerOperation.cc
Go to the documentation of this file.
1 /* SPDX-License-Identifier: GPL-2.0-or-later
2  * Copyright 2011 Blender Foundation. */
3 
4 #include "COM_ViewerOperation.h"
5 #include "BKE_image.h"
6 #include "BKE_scene.h"
7 #include "COM_ExecutionSystem.h"
8 
9 #include "IMB_colormanagement.h"
10 #include "IMB_imbuf.h"
11 #include "IMB_imbuf_types.h"
12 
13 namespace blender::compositor {
14 
15 static int MAX_VIEWER_TRANSLATION_PADDING = 12000;
16 
18 {
19  this->set_image(nullptr);
20  this->set_image_user(nullptr);
21  output_buffer_ = nullptr;
22  depth_buffer_ = nullptr;
23  active_ = false;
24  do_depth_buffer_ = false;
25  view_settings_ = nullptr;
26  display_settings_ = nullptr;
27  use_alpha_input_ = false;
28 
32 
33  image_input_ = nullptr;
34  alpha_input_ = nullptr;
35  depth_input_ = nullptr;
36  rd_ = nullptr;
37  view_name_ = nullptr;
40 }
41 
43 {
44  /* When initializing the tree during initial load the width and height can be zero. */
45  image_input_ = get_input_socket_reader(0);
46  alpha_input_ = get_input_socket_reader(1);
47  depth_input_ = get_input_socket_reader(2);
48  do_depth_buffer_ = (depth_input_ != nullptr);
49 
51  init_image();
52  }
53 }
54 
56 {
57  image_input_ = nullptr;
58  alpha_input_ = nullptr;
59  depth_input_ = nullptr;
60  output_buffer_ = nullptr;
61 }
62 
63 void ViewerOperation::execute_region(rcti *rect, unsigned int /*tile_number*/)
64 {
65  float *buffer = output_buffer_;
66  float *depthbuffer = depth_buffer_;
67  if (!buffer) {
68  return;
69  }
70  const int x1 = rect->xmin;
71  const int y1 = rect->ymin;
72  const int x2 = rect->xmax;
73  const int y2 = rect->ymax;
74  const int offsetadd = (this->get_width() - (x2 - x1));
75  const int offsetadd4 = offsetadd * 4;
76  int offset = (y1 * this->get_width() + x1);
77  int offset4 = offset * 4;
78  float alpha[4], depth[4];
79  int x;
80  int y;
81  bool breaked = false;
82 
83  for (y = y1; y < y2 && (!breaked); y++) {
84  for (x = x1; x < x2; x++) {
85  image_input_->read_sampled(&(buffer[offset4]), x, y, PixelSampler::Nearest);
86  if (use_alpha_input_) {
87  alpha_input_->read_sampled(alpha, x, y, PixelSampler::Nearest);
88  buffer[offset4 + 3] = alpha[0];
89  }
90  depth_input_->read_sampled(depth, x, y, PixelSampler::Nearest);
91  depthbuffer[offset] = depth[0];
92 
93  offset++;
94  offset4 += 4;
95  }
96  if (is_braked()) {
97  breaked = true;
98  }
99  offset += offsetadd;
100  offset4 += offsetadd4;
101  }
102  update_image(rect);
103 }
104 
105 void ViewerOperation::determine_canvas(const rcti &preferred_area, rcti &r_area)
106 {
107  int scene_render_width, scene_render_height;
108  BKE_render_resolution(rd_, false, &scene_render_width, &scene_render_height);
109 
110  rcti local_preferred = preferred_area;
111  local_preferred.xmax = local_preferred.xmin + scene_render_width;
112  local_preferred.ymax = local_preferred.ymin + scene_render_height;
113 
114  NodeOperation::determine_canvas(local_preferred, r_area);
115 }
116 
117 void ViewerOperation::init_image()
118 {
119  Image *ima = image_;
120  ImageUser iuser = *image_user_;
121  void *lock;
122  ImBuf *ibuf;
123 
124  /* make sure the image has the correct number of views */
125  if (ima && BKE_scene_multiview_is_render_view_first(rd_, view_name_)) {
126  BKE_image_ensure_viewer_views(rd_, ima, image_user_);
127  }
128 
130 
131  /* local changes to the original ImageUser */
132  iuser.multi_index = BKE_scene_multiview_view_id_get(rd_, view_name_);
133  ibuf = BKE_image_acquire_ibuf(ima, &iuser, &lock);
134 
135  if (!ibuf) {
137  return;
138  }
139 
140  int padding_x = abs(canvas_.xmin) * 2;
141  int padding_y = abs(canvas_.ymin) * 2;
142  if (padding_x > MAX_VIEWER_TRANSLATION_PADDING) {
143  padding_x = MAX_VIEWER_TRANSLATION_PADDING;
144  }
145  if (padding_y > MAX_VIEWER_TRANSLATION_PADDING) {
146  padding_y = MAX_VIEWER_TRANSLATION_PADDING;
147  }
148 
149  display_width_ = get_width() + padding_x;
150  display_height_ = get_height() + padding_y;
151  if (ibuf->x != display_width_ || ibuf->y != display_height_) {
152  imb_freerectImBuf(ibuf);
155  ibuf->x = display_width_;
156  ibuf->y = display_height_;
157  /* zero size can happen if no image buffers exist to define a sensible resolution */
158  if (ibuf->x > 0 && ibuf->y > 0) {
159  imb_addrectfloatImBuf(ibuf, 4);
160  }
161 
163  }
164 
165  if (do_depth_buffer_) {
166  addzbuffloatImBuf(ibuf);
167  }
168 
169  /* now we combine the input with ibuf */
170  output_buffer_ = ibuf->rect_float;
171 
172  /* needed for display buffer update */
173  ibuf_ = ibuf;
174 
175  if (do_depth_buffer_) {
176  depth_buffer_ = ibuf->zbuf_float;
177  }
178 
179  BKE_image_release_ibuf(image_, ibuf_, lock);
180 
182 }
183 
184 void ViewerOperation::update_image(const rcti *rect)
185 {
186  if (exec_system_->is_breaked()) {
187  return;
188  }
189 
190  float *buffer = output_buffer_;
192  buffer,
193  nullptr,
194  display_width_,
195  0,
196  0,
197  view_settings_,
198  display_settings_,
199  rect->xmin,
200  rect->ymin,
201  rect->xmax,
202  rect->ymax);
203 
204  /* This could be improved to use partial updates. For now disabled as the full frame compositor
205  * would not use partial frames anymore and the image engine requires more testing. */
207  this->update_draw();
208 }
209 
211 {
212  if (this->is_active_viewer_output()) {
214  }
215 
217 }
218 
220  const rcti &area,
222 {
223  if (!output_buffer_) {
224  return;
225  }
226 
227  const int offset_x = area.xmin + (canvas_.xmin > 0 ? canvas_.xmin * 2 : 0);
228  const int offset_y = area.ymin + (canvas_.ymin > 0 ? canvas_.ymin * 2 : 0);
229  MemoryBuffer output_buffer(
230  output_buffer_, COM_DATA_TYPE_COLOR_CHANNELS, display_width_, display_height_);
231  const MemoryBuffer *input_image = inputs[0];
232  output_buffer.copy_from(input_image, area, offset_x, offset_y);
233  if (use_alpha_input_) {
234  const MemoryBuffer *input_alpha = inputs[1];
235  output_buffer.copy_from(
236  input_alpha, area, 0, COM_DATA_TYPE_VALUE_CHANNELS, offset_x, offset_y, 3);
237  }
238 
239  if (depth_buffer_) {
240  MemoryBuffer depth_buffer(
241  depth_buffer_, COM_DATA_TYPE_VALUE_CHANNELS, display_width_, display_height_);
242  const MemoryBuffer *input_depth = inputs[2];
243  depth_buffer.copy_from(input_depth, area, offset_x, offset_y);
244  }
245 
246  rcti display_area;
247  BLI_rcti_init(&display_area,
248  offset_x,
249  offset_x + BLI_rcti_size_x(&area),
250  offset_y,
251  offset_y + BLI_rcti_size_y(&area));
252  update_image(&display_area);
253 }
254 
256 {
258  if (exec_system_->is_breaked()) {
259  return;
260  }
261 
262  init_image();
263  if (output_buffer_ == nullptr) {
264  return;
265  }
266 
267  size_t buf_bytes = (size_t)ibuf_->y * ibuf_->x * COM_DATA_TYPE_COLOR_CHANNELS * sizeof(float);
268  if (buf_bytes > 0) {
269  memset(output_buffer_, 0, buf_bytes);
270  rcti display_area;
271  BLI_rcti_init(&display_area, 0, ibuf_->x, 0, ibuf_->y);
272  update_image(&display_area);
273  }
274 }
275 
276 } // namespace blender::compositor
void BKE_image_release_ibuf(struct Image *ima, struct ImBuf *ibuf, void *lock)
struct ImBuf * BKE_image_acquire_ibuf(struct Image *ima, struct ImageUser *iuser, void **r_lock)
void BKE_image_partial_update_mark_full_update(struct Image *image)
Mark the whole image to be updated.
void BKE_image_ensure_viewer_views(const struct RenderData *rd, struct Image *ima, struct ImageUser *iuser)
void BKE_render_resolution(const struct RenderData *r, const bool use_crop, int *r_width, int *r_height)
Definition: scene.cc:2960
bool BKE_scene_multiview_is_render_view_first(const struct RenderData *rd, const char *viewname)
int BKE_scene_multiview_view_id_get(const struct RenderData *rd, const char *viewname)
#define BLI_assert(a)
Definition: BLI_assert.h:46
BLI_INLINE int BLI_rcti_size_y(const struct rcti *rct)
Definition: BLI_rect.h:190
void BLI_rcti_init(struct rcti *rect, int xmin, int xmax, int ymin, int ymax)
Definition: rct.c:417
BLI_INLINE int BLI_rcti_size_x(const struct rcti *rct)
Definition: BLI_rect.h:186
void BLI_thread_unlock(int type)
Definition: threads.cc:361
@ LOCK_DRAW_IMAGE
Definition: BLI_threads.h:67
void BLI_thread_lock(int type)
Definition: threads.cc:356
#define UNUSED(x)
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble y1
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint y
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble GLdouble x2
void IMB_partial_display_buffer_update(struct ImBuf *ibuf, const float *linear_buffer, const unsigned char *byte_buffer, int stride, int offset_x, int offset_y, const struct ColorManagedViewSettings *view_settings, const struct ColorManagedDisplaySettings *display_settings, int xmin, int ymin, int xmax, int ymax)
void imb_freerectfloatImBuf(struct ImBuf *ibuf)
Definition: allocimbuf.c:80
void IMB_freezbuffloatImBuf(struct ImBuf *ibuf)
Definition: allocimbuf.c:168
bool imb_addrectfloatImBuf(struct ImBuf *ibuf, const unsigned int channels)
Definition: allocimbuf.c:367
void imb_freerectImBuf(struct ImBuf *ibuf)
Definition: allocimbuf.c:97
bool addzbuffloatImBuf(struct ImBuf *ibuf)
Definition: allocimbuf.c:270
Contains defines and structs used throughout the imbuf module.
@ IB_DISPLAY_BUFFER_INVALID
volatile int lock
a MemoryBuffer contains access to the data of a chunk
void copy_from(const MemoryBuffer *src, const rcti &area)
SocketReader * get_input_socket_reader(unsigned int index)
void read_sampled(float result[4], float x, float y, PixelSampler sampler)
void add_input_socket(DataType datatype, ResizeMode resize_mode=ResizeMode::Center)
virtual void determine_canvas(const rcti &preferred_area, rcti &r_area)
void set_image_user(ImageUser *image_user)
void update_memory_buffer_partial(MemoryBuffer *output, const rcti &area, Span< MemoryBuffer * > inputs) override
void execute_region(rcti *rect, unsigned int tile_number) override
when a chunk is executed by a CPUDevice, this method is called
eCompositorPriority get_render_priority() const override
get the render priority of this node.
bool is_active_viewer_output() const override
is this operation the active viewer output user can select an ViewerNode to be active (the result of ...
void determine_canvas(const rcti &preferred_area, rcti &r_area) override
eCompositorPriority
Possible priority settings.
Definition: COM_Enums.h:32
ccl_global float * buffer
ccl_global KernelShaderEvalInput ccl_global float * output
ccl_gpu_kernel_postfix ccl_global float int int int int float bool int offset
static void area(int d1, int d2, int e1, int e2, float weights[2])
constexpr int COM_DATA_TYPE_VALUE_CHANNELS
Definition: COM_defines.h:60
constexpr int COM_DATA_TYPE_COLOR_CHANNELS
Definition: COM_defines.h:62
static int MAX_VIEWER_TRANSLATION_PADDING
T abs(const T &a)
static bNodeSocketTemplate inputs[]
float * zbuf_float
int userflags
float * rect_float
short multi_index
int ymin
Definition: DNA_vec_types.h:64
int ymax
Definition: DNA_vec_types.h:64
int xmin
Definition: DNA_vec_types.h:63
int xmax
Definition: DNA_vec_types.h:63