1 #include <cmath>
2 #include "vil_openjpeg_pyramid_image_resource.h"
3 //:
4 // \file
5 // Do not remove the following notice
6 // Approved for public Release, distribution unlimited
7 // DISTAR Case 14074
8 
9 #ifdef _MSC_VER
10 #  include "vcl_msvc_warnings.h"
11 #endif
12 
13 // By definition, each level is a factor of 2 reduced in scale
14 static float
scale_at_level(unsigned level)15 scale_at_level(unsigned level)
16 {
17   if (level == 0)
18     return 1.0f;
19   float s = std::pow(2.0f, -static_cast<float>(level));
20   return s;
21 }
22 
vil_openjpeg_pyramid_image_resource(vil_image_resource_sptr const & openjpeg)23 vil_openjpeg_pyramid_image_resource::vil_openjpeg_pyramid_image_resource(vil_image_resource_sptr const & openjpeg)
24   : openjpeg_sptr_(openjpeg)
25 {
26   ptr_ = nullptr;
27   if (!openjpeg_sptr_)
28     return;
29   ptr_ = dynamic_cast<vil_openjpeg_image *>(openjpeg_sptr_.ptr());
30 }
31 
32 unsigned
nplanes() const33 vil_openjpeg_pyramid_image_resource::nplanes() const
34 {
35   unsigned ret = 0;
36   if (ptr_)
37     ret = ptr_->nplanes();
38   return ret;
39 }
40 
41 //: The number of pixels in each row.
42 // Dimensions:  Planes x ni x nj.
43 // This method refers to the base (max resolution) image
44 unsigned
ni() const45 vil_openjpeg_pyramid_image_resource::ni() const
46 {
47   unsigned ret = 0;
48   if (ptr_)
49     ret = ptr_->ni();
50   return ret;
51 }
52 
53 //: The number of pixels in each column.
54 // Dimensions:  Planes x ni x nj.
55 // This method refers to the base (max resolution) image
56 unsigned
nj() const57 vil_openjpeg_pyramid_image_resource::nj() const
58 {
59   unsigned ret = 0;
60   if (ptr_)
61     ret = ptr_->nj();
62   return ret;
63 }
64 
65 //: Pixel Format.
66 vil_pixel_format
pixel_format() const67 vil_openjpeg_pyramid_image_resource::pixel_format() const
68 {
69   if (ptr_)
70     return ptr_->pixel_format();
71   return VIL_PIXEL_FORMAT_UNKNOWN;
72 }
73 
74 //: Return a string describing the file format.
75 // Only file images have a format, others return 0
76 char const *
file_format() const77 vil_openjpeg_pyramid_image_resource::file_format() const
78 {
79   return "openjpeg_pyramid";
80 }
81 
82 
83 // === Methods particular to pyramid resource ===
84 
85 //: Number of pyramid levels.
86 unsigned
nlevels() const87 vil_openjpeg_pyramid_image_resource::nlevels() const
88 {
89   if (!ptr_)
90     return 0;
91   return ptr_->nreductions() + 1;
92 }
93 
94 //: Get a partial view from the image from a specified pyramid level
95 vil_image_view_base_sptr
get_copy_view(unsigned i0,unsigned ni,unsigned j0,unsigned nj,unsigned level) const96 vil_openjpeg_pyramid_image_resource::get_copy_view(unsigned i0, unsigned ni, unsigned j0, unsigned nj, unsigned level)
97   const
98 {
99   if (!ptr_ || !(ptr_->is_valid()))
100     return nullptr;
101   if (level >= this->nlevels())
102     level = this->nlevels() - 1;
103   return ptr_->get_copy_view_reduced(i0, ni, j0, nj, level);
104 }
105 
106 //: Get a partial view from the image in the pyramid closest to scale.
107 // The origin and size parameters are in the coordinate system of the base image.
108 // The scale factor is with respect to the base image (base scale = 1.0).
109 vil_image_view_base_sptr
get_copy_view(unsigned i0,unsigned ni,unsigned j0,unsigned nj,const float scale,float & actual_scale) const110 vil_openjpeg_pyramid_image_resource::get_copy_view(unsigned i0,
111                                                    unsigned ni,
112                                                    unsigned j0,
113                                                    unsigned nj,
114                                                    const float scale,
115                                                    float & actual_scale) const
116 {
117   if (scale >= 1.0f)
118   {
119     actual_scale = 1.0f;
120     return this->get_copy_view(i0, ni, j0, nj, 0);
121   }
122   float f_lev = -std::log(scale) / std::log(2.0f);
123   auto level = static_cast<unsigned>(f_lev);
124   if (level >= this->nlevels())
125     level = this->nlevels() - 1;
126   actual_scale = scale_at_level(level);
127   return this->get_copy_view(i0, ni, j0, nj, level);
128 }
129 
130 //: Get an image resource from the pyramid at the specified level
131 vil_image_resource_sptr
get_resource(const unsigned level) const132 vil_openjpeg_pyramid_image_resource::get_resource(const unsigned level) const
133 {
134   if (level == 0)
135     return openjpeg_sptr_;
136   return nullptr;
137 }
138 
139 //: for debug purposes
140 void
print(const unsigned)141 vil_openjpeg_pyramid_image_resource::print(const unsigned /*level*/)
142 {}
143