00001
00002 #ifndef vimt_sample_grid_bicub_txx_
00003 #define vimt_sample_grid_bicub_txx_
00004
00005
00006
00007
00008
00009 #include "vimt_sample_grid_bicub.h"
00010 #include <vil/vil_sample_grid_bicub.h>
00011 #include <vil/vil_bicub_interp.h>
00012 #include <vnl/vnl_vector.h>
00013 #include <vgl/vgl_vector_2d.h>
00014
00015 inline bool vimt_grid_corner_in_image(const vgl_point_2d<double>& p,
00016 const vil_image_view_base& image)
00017 {
00018 if (p.x()<1) return false;
00019 if (p.x()<1) return false;
00020 if (p.x()+2>image.ni()) return false;
00021 if (p.y()+2>image.nj()) return false;
00022 return true;
00023 }
00024
00025
00026
00027
00028
00029
00030
00031
00032 template <class imType, class vecType>
00033 void vimt_sample_grid_bicub(vnl_vector<vecType>& vec,
00034 const vimt_image_2d_of<imType>& image,
00035 const vgl_point_2d<double>& p0,
00036 const vgl_vector_2d<double>& u,
00037 const vgl_vector_2d<double>& v,
00038 int n1, int n2)
00039 {
00040 vgl_point_2d<double> im_p0 = image.world2im()(p0);
00041 vgl_point_2d<double> im_p1 = image.world2im()(p0+(n1-1)*u);
00042 vgl_point_2d<double> im_p2 = image.world2im()(p0+(n2-1)*v);
00043 int np = image.image().nplanes();
00044 vec.set_size(n1*n2*np);
00045 vecType *vec_data = vec.data_block();
00046
00047 if (image.world2im().form()!=vimt_transform_2d::Projective)
00048 {
00049
00050 vgl_vector_2d<double> im_u(0,0);
00051 if (n1>1) im_u = (im_p1-im_p0)/(n1-1);
00052 vgl_vector_2d<double> im_v(0,0);
00053 if (n2>1) im_v = (im_p2-im_p0)/(n2-1);
00054
00055 vil_sample_grid_bicub(vec_data,image.image(),im_p0.x(),im_p0.y(),
00056 im_u.x(),im_u.y(),im_v.x(),im_v.y(),n1,n2);
00057 return;
00058 }
00059
00060
00061
00062
00063 const vimt_transform_2d& w2i = image.world2im();
00064 bool all_in_image =
00065 vimt_grid_corner_in_image(im_p0,image.image()) &&
00066 vimt_grid_corner_in_image(im_p1,image.image()) &&
00067 vimt_grid_corner_in_image(im_p2,image.image()) &&
00068 vimt_grid_corner_in_image(w2i(p0+(n1-1)*u+(n2-1)*v),image.image());
00069
00070 vgl_point_2d<double> p1=p0;
00071
00072 const imType* plane0 = image.image().top_left_ptr();
00073 unsigned ni = image.image().ni();
00074 unsigned nj = image.image().nj();
00075 vcl_ptrdiff_t istep = image.image().istep();
00076 vcl_ptrdiff_t jstep = image.image().jstep();
00077 vcl_ptrdiff_t pstep = image.image().planestep();
00078
00079 if (all_in_image)
00080 {
00081 if (np==1)
00082 {
00083 for (int i=0;i<n1;++i,p1+=u)
00084 {
00085 vgl_point_2d<double> p=p1;
00086 for (int j=0;j<n2;++j,p+=v,++vec_data)
00087 {
00088 vgl_point_2d<double> im_p = w2i(p);
00089 *vec_data = vil_bicub_interp_raw(im_p.x(),im_p.y(),plane0,istep,jstep);
00090 }
00091 }
00092 }
00093 else
00094 {
00095 for (int i=0;i<n1;++i,p1+=u)
00096 {
00097 vgl_point_2d<double> p=p1;
00098 for (int j=0;j<n2;++j,p+=v)
00099 {
00100 vgl_point_2d<double> im_p = w2i(p);
00101 for (int k=0;k<np;++k,++vec_data)
00102 *vec_data = vil_bicub_interp_raw(im_p.x(),im_p.y(),plane0+k*pstep,istep,jstep);
00103 }
00104 }
00105 }
00106 }
00107 else
00108 {
00109
00110 if (np==1)
00111 {
00112 for (int i=0;i<n1;++i,p1+=u)
00113 {
00114 vgl_point_2d<double> p=p1;
00115 for (int j=0;j<n2;++j,p+=v,++vec_data)
00116 {
00117 vgl_point_2d<double> im_p = w2i(p);
00118 *vec_data = vil_bicub_interp_safe(im_p.x(),im_p.y(),plane0,ni,nj,istep,jstep);
00119 }
00120 }
00121 }
00122 else
00123 {
00124 for (int i=0;i<n1;++i,p1+=u)
00125 {
00126 vgl_point_2d<double> p=p1;
00127 for (int j=0;j<n2;++j,p+=v)
00128 {
00129 vgl_point_2d<double> im_p = w2i(p);
00130 for (int k=0;k<np;++k,++vec_data)
00131 *vec_data = vil_bicub_interp_safe(im_p.x(),im_p.y(),plane0+k*pstep,ni,nj,istep,jstep);
00132 }
00133 }
00134 }
00135 }
00136 }
00137
00138 #define VIMT_SAMPLE_GRID_BICUB_INSTANTIATE( imType, vecType ) \
00139 template void vimt_sample_grid_bicub(vnl_vector<vecType >&, \
00140 const vimt_image_2d_of<imType >&, \
00141 const vgl_point_2d<double >&, \
00142 const vgl_vector_2d<double >&, \
00143 const vgl_vector_2d<double >&, \
00144 int, int)
00145
00146 #endif // vimt_sample_grid_bicub_txx_