Grok  7.6.0
TileComponentBuffer.h
Go to the documentation of this file.
1 
17 #pragma once
18 
19 #include "util.h"
20 #include "grok_intmath.h"
21 #include "TagTree.h"
22 #include "TileProcessor.h"
23 #include <stdexcept>
24 
25 namespace grk {
26 
27 template<typename T> struct res_buf {
28 
29  res_buf(grk_resolution *res, grk_rect_u32 res_bounds) : res(new grk_buffer_2d<T>(res_bounds))
30  {
31  for (uint32_t i = 0; i < 3; ++i)
32  bands[i] = res ? new grk_buffer_2d<T>(res->bands[i]) : nullptr;
33  }
35  delete res;
36  for (uint32_t i = 0; i < 3; ++i)
37  delete bands[i];
38  }
39  bool alloc(bool clear){
40  if (!res->alloc(clear))
41  return false;
42  for (uint32_t i = 0; i < 3; ++i){
43  if (bands[i] && !bands[i]->alloc(clear))
44  return false;
45  }
46  return true;
47  }
48 
51 };
52 
53 
54 /*
55  Note: various coordinate systems are used to describe regions in the tile buffer.
56 
57  1) Canvas coordinate system: JPEG 2000 global image coordinates, independent of sub-sampling
58 
59  2) Tile coordinate system: coordinates relative to a tile's top left hand corner, with
60  sub-sampling accounted for
61 
62  3) Resolution coordinate system: coordinates relative to a resolution's top left hand corner
63 
64  4) Sub-band coordinate system: coordinates relative to a particular sub-band's top left hand corner
65 
66  */
67 
68 template<typename T> struct TileComponentBuffer {
70  uint32_t dx,uint32_t dy,
71  grk_rect unreduced_dim,
72  grk_rect reduced_dim,
73  uint32_t reduced_num_resolutions,
74  uint32_t numresolutions,
75  grk_resolution *tile_comp_resolutions,
76  bool whole_tile) :
77  m_unreduced_bounds(unreduced_dim),
78  m_bounds(reduced_dim),
79  num_resolutions(numresolutions),
80  m_encode(output_image==nullptr),
81  whole_tile_decoding(whole_tile)
82  {
83  //note: only decoder has output image
84  if (output_image) {
85  // tile component coordinates
86  m_unreduced_bounds = grk_rect(ceildiv<uint32_t>(output_image->x0, dx),
87  ceildiv<uint32_t>(output_image->y0, dy),
88  ceildiv<uint32_t>(output_image->x1, dx),
89  ceildiv<uint32_t>(output_image->y1, dy));
90 
92  m_bounds.rectceildivpow2(num_resolutions - reduced_num_resolutions);
93 
94  /* clip region dimensions against tile */
95  reduced_dim.clip(m_bounds, &m_bounds);
97  }
98 
99  /* fill resolutions vector */
100  assert(reduced_num_resolutions>0);
101 
102  for (uint32_t resno = 0; resno < reduced_num_resolutions; ++resno)
103  resolutions.push_back(tile_comp_resolutions+resno);
104 
105  if ( use_band_buffers()) {
106  // lowest resolution equals 0th band
107  res_buffers.push_back(new res_buf<T>(nullptr, tile_comp_resolutions->bands[0].to_u32()) );
108 
109  for (uint32_t resno = 1; resno < reduced_num_resolutions; ++resno)
110  res_buffers.push_back(new res_buf<T>( tile_comp_resolutions+resno, m_bounds.to_u32()) );
111  } else {
112  res_buffers.push_back(new res_buf<T>( nullptr, m_bounds.to_u32()) );
113  }
114  }
116  for (auto& b : res_buffers)
117  delete b;
118  }
129  T* cblk_ptr(uint32_t resno,uint32_t bandno, uint32_t &offsetx, uint32_t &offsety) const {
130  assert(bandno < 3 && resno < resolutions.size());
131  if (resno==0)
132  assert(bandno==0);
133  else
134  assert(bandno < 3);
135 
136  auto res = resolutions[resno];
137  auto band = res->bands + bandno;
138  uint32_t x = offsetx;
139  uint32_t y = offsety;
140 
141  // get code block offset relative to band
142  x -= band->x0;
143  y -= band->y0;
144 
145  if (!use_band_buffers()){
146  auto pres = resno == 0 ? nullptr : resolutions[ resno - 1];
147  // add band offset relative to previous resolution
148  if (band->bandno & 1)
149  x += pres->width();
150  if (band->bandno & 2)
151  y += pres->height();
152  }
153  offsetx = x;
154  offsety = y;
155 
156  if (use_band_buffers()) {
157  auto dest = band_buf(resno,bandno);
158  return dest->data + (uint64_t) x + y * (uint64_t) dest->stride;
159  }
160  auto dest = tile_buf();;
161  return dest->data + (uint64_t) x + y * (uint64_t) dest->stride;
162  }
170  T* ptr(uint32_t resno,uint32_t bandno) const{
171  assert(bandno < 3 && resno < resolutions.size());
172  if (use_band_buffers()){
173  return band_buf(resno,bandno)->data;
174  }
175  auto lower_res = resolutions[resno-1];
176  switch(bandno){
177  case 0:
178  return tile_buf()->data + lower_res->width();
179  break;
180  case 1:
181  return tile_buf()->data + lower_res->height() * stride(resno,bandno);
182  break;
183  case 2:
184  return tile_buf()->data + lower_res->width() +
185  lower_res->height() * stride(resno,bandno);
186  break;
187  default:
188  assert(0);
189  break;
190  }
191  return nullptr;
192  }
193 
200  T* ptr(uint32_t resno) const{
201  if (use_band_buffers()){
202  return res_buffers[resno]->res->data;
203  }
204  return tile_buf()->data;
205  }
206 
212  T* ptr(void) const{
213  return tile_buf()->data;
214  }
221  uint32_t stride(uint32_t resno,uint32_t bandno) const{
222  assert(bandno < 3 && resno < resolutions.size());
223  if (use_band_buffers()){
224  return band_buf(resno,bandno)->stride;
225  }
226  return tile_buf()->stride;
227  }
228 
229  uint32_t stride(uint32_t resno) const{
230  if (use_band_buffers()){
231  return res_buffers[resno]->res->stride;
232  }
233  return tile_buf()->stride;
234  }
235 
236  uint32_t stride(void) const{
237  return tile_buf()->stride;
238  }
239 
240 
241  bool alloc(){
242  for (auto& b : res_buffers) {
243  if (!b->alloc(!m_encode))
244  return false;
245  }
246  // sanity check
247  for (uint32_t i = 1; i < res_buffers.size(); ++i){
248  auto b = res_buffers[i];
249  auto b_prev = res_buffers[i-1];
250  if (!b_prev->res->data)
251  b_prev->res->data = b->bands[0]->data;
252  if (!b->bands[1]->data)
253  b->bands[1]->data = b->bands[2]->data;
254  }
255  return true;
256  }
257 
270  void get_region_band_coordinates(uint32_t resno,
271  uint32_t bandno,
272  uint32_t* tbx0,
273  uint32_t* tby0,
274  uint32_t* tbx1,
275  uint32_t* tby1) const{
276  /* Compute number of decomposition for this band. See table F-1 */
277  uint32_t nb = (resno == 0) ?
278  num_resolutions - 1 :
279  num_resolutions - resno;
280 
281  uint32_t tcx0 = (uint32_t)m_unreduced_bounds.x0;
282  uint32_t tcy0 = (uint32_t)m_unreduced_bounds.y0;
283  uint32_t tcx1 = (uint32_t)m_unreduced_bounds.x1;
284  uint32_t tcy1 = (uint32_t)m_unreduced_bounds.y1;
285  /* Map above tile-based coordinates to sub-band-based coordinates per */
286  /* equation B-15 of the standard */
287  uint32_t x0b = bandno & 1;
288  uint32_t y0b = bandno >> 1;
289  if (tbx0) {
290  *tbx0 = (nb == 0) ? tcx0 :
291  (tcx0 <= (1U << (nb - 1)) * x0b) ? 0 :
292  ceildivpow2<uint32_t>(tcx0 - (1U << (nb - 1)) * x0b, nb);
293  }
294  if (tby0) {
295  *tby0 = (nb == 0) ? tcy0 :
296  (tcy0 <= (1U << (nb - 1)) * y0b) ? 0 :
297  ceildivpow2<uint32_t>(tcy0 - (1U << (nb - 1)) * y0b, nb);
298  }
299  if (tbx1) {
300  *tbx1 = (nb == 0) ? tcx1 :
301  (tcx1 <= (1U << (nb - 1)) * x0b) ? 0 :
302  ceildivpow2<uint32_t>(tcx1 - (1U << (nb - 1)) * x0b, nb);
303  }
304  if (tby1) {
305  *tby1 = (nb == 0) ? tcy1 :
306  (tcy1 <= (1U << (nb - 1)) * y0b) ? 0 :
307  ceildivpow2<uint32_t>(tcy1 - (1U << (nb - 1)) * y0b, nb);
308  }
309  }
310 
316  grk_rect bounds() const{
317  return m_bounds;
318  }
319 
321  return m_unreduced_bounds;
322  }
323 
324  uint64_t strided_area(void){
325  return stride() * m_bounds.height();
326  }
327 
328  // set data to buf without owning it
329  void attach(T* buffer,uint32_t stride){
330  tile_buf()->attach(buffer,stride);
331  }
332  // set data to buf and own it
333  void acquire(T* buffer, uint32_t stride){
334  tile_buf()->acquire(buffer,stride);
335  }
336  // transfer data to buf, and cease owning it
337  void transfer(T** buffer, bool* owns, uint32_t *stride){
338  tile_buf()->transfer(buffer,owns,stride);
339  }
340 
341 private:
342 
343  bool use_band_buffers() const{
344  //return !m_encode && whole_tile_decoding && resolutions.size() > 1;
345  return false;
346  }
347 
348  grk_buffer_2d<T>* band_buf(uint32_t resno,uint32_t bandno) const{
349  assert(bandno < 3 && resno < resolutions.size());
350  return resno > 0 ? res_buffers[resno]->bands[bandno] : res_buffers[resno]->res;
351  }
352 
354  return res_buffers.back()->res;
355  }
356 
358 
359  /* decode: reduced tile component coordinates of region */
360  /* encode: unreduced tile component coordinates of entire tile */
362 
363  std::vector<grk_resolution*> resolutions;
364  std::vector<res_buf<T>* > res_buffers;
365  uint32_t num_resolutions;
366 
367  bool m_encode;
369 };
370 
371 
372 }
grk::TileComponentBuffer::acquire
void acquire(T *buffer, uint32_t stride)
Definition: TileComponentBuffer.h:333
grk::TileComponentBuffer::resolutions
std::vector< grk_resolution * > resolutions
Definition: TileComponentBuffer.h:363
grk::grk_rectangle::to_u32
grk_rect_u32 to_u32()
Definition: util.h:62
grk::grk_rectangle::rectceildivpow2
grk_rectangle< T > & rectceildivpow2(uint32_t power)
Definition: util.h:136
grk::TileComponentBuffer::num_resolutions
uint32_t num_resolutions
Definition: TileComponentBuffer.h:365
grk::TileComponentBuffer::stride
uint32_t stride(void) const
Definition: TileComponentBuffer.h:236
grk::grk_resolution
Definition: TileProcessor.h:164
grk::grk_rectangle< uint32_t >
grk::TileComponentBuffer::band_buf
grk_buffer_2d< T > * band_buf(uint32_t resno, uint32_t bandno) const
Definition: TileComponentBuffer.h:348
grk::TileComponentBuffer::cblk_ptr
T * cblk_ptr(uint32_t resno, uint32_t bandno, uint32_t &offsetx, uint32_t &offsety) const
Get pointer to code block region in tile buffer.
Definition: TileComponentBuffer.h:129
grk::TileComponentBuffer::attach
void attach(T *buffer, uint32_t stride)
Definition: TileComponentBuffer.h:329
TagTree.h
grk::TileComponentBuffer::TileComponentBuffer
TileComponentBuffer(grk_image *output_image, uint32_t dx, uint32_t dy, grk_rect unreduced_dim, grk_rect reduced_dim, uint32_t reduced_num_resolutions, uint32_t numresolutions, grk_resolution *tile_comp_resolutions, bool whole_tile)
Definition: TileComponentBuffer.h:69
grk::grk_rect
grk_rectangle< int64_t > grk_rect
Definition: util.h:45
grk::TileComponentBuffer::m_bounds
grk_rect m_bounds
Definition: TileComponentBuffer.h:361
grk::TileComponentBuffer::unreduced_bounds
grk_rect unreduced_bounds() const
Definition: TileComponentBuffer.h:320
grk::res_buf::alloc
bool alloc(bool clear)
Definition: TileComponentBuffer.h:39
grk::TileComponentBuffer::get_region_band_coordinates
void get_region_band_coordinates(uint32_t resno, uint32_t bandno, uint32_t *tbx0, uint32_t *tby0, uint32_t *tbx1, uint32_t *tby1) const
Get reduced coordinates of sub-band region.
Definition: TileComponentBuffer.h:270
grk::grk_rectangle::clip
bool clip(grk_rectangle< T > &r2, grk_rectangle< T > *result)
Definition: util.h:84
grk::grk_rectangle::x1
T x1
Definition: util.h:51
grk::TileComponentBuffer::ptr
T * ptr(uint32_t resno) const
Get pointer to resolution buffer.
Definition: TileComponentBuffer.h:200
grk::TileComponentBuffer::ptr
T * ptr(uint32_t resno, uint32_t bandno) const
Get pointer to band buffer.
Definition: TileComponentBuffer.h:170
grk::TileComponentBuffer::stride
uint32_t stride(uint32_t resno, uint32_t bandno) const
Get stride of band buffer.
Definition: TileComponentBuffer.h:221
grk::res_buf::bands
grk_buffer_2d< T > * bands[3]
Definition: TileComponentBuffer.h:50
grk::grk_resolution::bands
grk_band bands[3]
Definition: TileProcessor.h:170
grk::TileComponentBuffer::ptr
T * ptr(void) const
Get pointer to tile buffer.
Definition: TileComponentBuffer.h:212
grk::res_buf::res_buf
res_buf(grk_resolution *res, grk_rect_u32 res_bounds)
Definition: TileComponentBuffer.h:29
grk::TileComponentBuffer::stride
uint32_t stride(uint32_t resno) const
Definition: TileComponentBuffer.h:229
grk::grk_rectangle::height
T height()
Definition: util.h:170
grk::TileComponentBuffer::whole_tile_decoding
bool whole_tile_decoding
Definition: TileComponentBuffer.h:368
_grk_image::y0
uint32_t y0
YOsiz: vertical offset from the origin of the reference grid to the top side of the image area.
Definition: grok.h:886
grk::TileComponentBuffer::m_unreduced_bounds
grk_rect m_unreduced_bounds
Definition: TileComponentBuffer.h:357
grk::grk_buffer_2d
Definition: util.h:270
grk
Copyright (C) 2016-2020 Grok Image Compression Inc.
Definition: BitIO.h:27
grk::TileComponentBuffer::use_band_buffers
bool use_band_buffers() const
Definition: TileComponentBuffer.h:343
grk::TileComponentBuffer::res_buffers
std::vector< res_buf< T > * > res_buffers
Definition: TileComponentBuffer.h:364
grok_intmath.h
grk::TileComponentBuffer::strided_area
uint64_t strided_area(void)
Definition: TileComponentBuffer.h:324
grk::res_buf
Definition: TileComponentBuffer.h:27
grk::TileComponentBuffer::bounds
grk_rect bounds() const
Get bounds of tile component decode: reduced tile component coordinates of region encode: unreduced t...
Definition: TileComponentBuffer.h:316
grk::TileComponentBuffer::transfer
void transfer(T **buffer, bool *owns, uint32_t *stride)
Definition: TileComponentBuffer.h:337
grk::TileComponentBuffer::~TileComponentBuffer
~TileComponentBuffer()
Definition: TileComponentBuffer.h:115
grk::res_buf::~res_buf
~res_buf()
Definition: TileComponentBuffer.h:34
grk::res_buf::res
grk_buffer_2d< T > * res
Definition: TileComponentBuffer.h:49
grk::grk_rectangle::x0
T x0
Definition: util.h:49
grk::grk_rectangle::y1
T y1
Definition: util.h:52
_grk_image::x1
uint32_t x1
Xsiz: width of the reference grid.
Definition: grok.h:888
TileProcessor.h
grk::TileComponentBuffer::alloc
bool alloc()
Definition: TileComponentBuffer.h:241
grk::TileComponentBuffer::m_encode
bool m_encode
Definition: TileComponentBuffer.h:367
_grk_image
Image.
Definition: grok.h:880
util.h
grk::grk_rectangle::y0
T y0
Definition: util.h:50
_grk_image::y1
uint32_t y1
Ysiz: height of the reference grid.
Definition: grok.h:890
grk::TileComponentBuffer
Definition: TileComponentBuffer.h:68
grk::TileComponentBuffer::tile_buf
grk_buffer_2d< T > * tile_buf() const
Definition: TileComponentBuffer.h:353
_grk_image::x0
uint32_t x0
XOsiz: horizontal offset from the origin of the reference grid to the left side of the image area.
Definition: grok.h:883