contrib/mul/mfpf/mfpf_region_about_lineseg.cxx
Go to the documentation of this file.
00001 #include "mfpf_region_about_lineseg.h"
00002 //:
00003 // \file
00004 // \brief Region centred on line between two points
00005 // \author Tim Cootes
00006 
00007 #include <vsl/vsl_binary_loader.h>
00008 #include <vcl_cassert.h>
00009 #include <vcl_sstream.h>
00010 
00011 #include <mbl/mbl_parse_block.h>
00012 #include <mbl/mbl_read_props.h>
00013 
00014 #include <vul/vul_string.h>
00015 
00016 //=======================================================================
00017 // Dflt ctor
00018 //=======================================================================
00019 
00020 mfpf_region_about_lineseg::mfpf_region_about_lineseg()
00021   : i0_(0),i1_(1),rel_wi_(1.2),rel_wj_(0.5),form_("box")
00022 {
00023 }
00024 
00025 //=======================================================================
00026 // Destructor
00027 //=======================================================================
00028 
00029 mfpf_region_about_lineseg::~mfpf_region_about_lineseg()
00030 {
00031 }
00032 
00033 //: Returns false as the region is not centred on an input point
00034 bool mfpf_region_about_lineseg::is_centred_on_pt() const
00035 {
00036   return false;
00037 }
00038 
00039 //: Returns zero
00040 unsigned mfpf_region_about_lineseg::ref_point_index() const
00041 {
00042   return 0;
00043 }
00044 
00045 //: Returns zero also
00046 unsigned mfpf_region_about_lineseg::orig_ref_point_index() const
00047 {
00048   return 0;
00049 }
00050 
00051 //: Replace each point index i with new_index[i]
00052 //  Allows for re-numbering of the points used.
00053 //  Returns true if successful.
00054 bool mfpf_region_about_lineseg::replace_index(
00055                         const vcl_vector<unsigned>& new_index)
00056 {
00057   if (i0_>=new_index.size()) return false;
00058   if (new_index[i0_]==mfpf_invalid_index) return false;
00059   i0_=new_index[i0_];
00060   if (i1_>=new_index.size()) return false;
00061   if (new_index[i1_]==mfpf_invalid_index) return false;
00062   i1_=new_index[i1_];
00063   return true;
00064 }
00065 
00066 //: Returns reference point for region, mid_point(pts[i0],pts[i1])
00067 vgl_point_2d<double> mfpf_region_about_lineseg::get_ref_point(
00068              const vcl_vector<vgl_point_2d<double> >& pts) const
00069 {
00070   assert(i0_<pts.size());
00071   assert(i1_<pts.size());
00072   return midpoint(pts[i0_],pts[i1_]);
00073 }
00074 
00075 //: Defines a region centred on a point
00076 mfpf_region_form mfpf_region_about_lineseg::set_up(
00077             const vcl_vector<vgl_point_2d<double> >& pts)
00078 {
00079   assert(i0_<pts.size());
00080   assert(i1_<pts.size());
00081 
00082   vgl_vector_2d<double> u=pts[i1_]-pts[i0_];
00083   double L=u.length();
00084   wi_=rel_wi_*L;
00085   wj_=rel_wj_*L;
00086 
00087   vgl_point_2d<double> c=midpoint(pts[i0_],pts[i1_]);
00088 
00089   mfpf_pose pose(c,u/L);
00090   return mfpf_region_form(pose,form_,wi_,wj_);
00091 }
00092 
00093 //: Defines a region centred on a point
00094 //  The aspect ratio of the region will be the same as that
00095 //  from the last call to set_up.
00096 mfpf_region_form mfpf_region_about_lineseg::get_region(
00097               const vcl_vector<vgl_point_2d<double> >& pts) const
00098 {
00099   assert(i0_<pts.size());
00100   assert(i1_<pts.size());
00101 
00102   vgl_vector_2d<double> u=pts[i1_]-pts[i0_];
00103   double L=u.length();
00104 
00105   // Compute scale of this box relative to the last one called by set_up
00106   double rel_scale = (rel_wi_*L)/wi_;
00107 
00108   vgl_point_2d<double> c=midpoint(pts[i0_],pts[i1_]);
00109 
00110   mfpf_pose pose(c,(rel_scale/L)*u);
00111   return mfpf_region_form(pose,form_,wi_,wj_);
00112 }
00113 
00114 //=======================================================================
00115 // Method: set_from_stream
00116 //=======================================================================
00117 //: Initialise from a string stream
00118 bool mfpf_region_about_lineseg::set_from_stream(vcl_istream &is)
00119 {
00120   // Cycle through stream and produce a map of properties
00121   vcl_string s = mbl_parse_block(is);
00122   vcl_istringstream ss(s);
00123   mbl_read_props_type props = mbl_read_props_ws(ss);
00124 
00125   // Extract the properties
00126   i0_=vul_string_atoi(props.get_required_property("i0"));
00127   i1_=vul_string_atoi(props.get_required_property("i1"));
00128   rel_wi_=vul_string_atof(props.get_required_property("rel_wi"));
00129   rel_wj_=vul_string_atof(props.get_required_property("rel_wj"));
00130   form_=props.get_optional_property("form","box");
00131 
00132   // Check for unused props
00133   mbl_read_props_look_for_unused_props(
00134       "mfpf_region_about_lineseg::set_from_stream", props, mbl_read_props_type());
00135   return true;
00136 }
00137 
00138 //=======================================================================
00139 // Method: version_no
00140 //=======================================================================
00141 
00142 short mfpf_region_about_lineseg::version_no() const
00143 {
00144   return 1;
00145 }
00146 
00147 //=======================================================================
00148 // Method: is_a
00149 //=======================================================================
00150 
00151 vcl_string mfpf_region_about_lineseg::is_a() const
00152 {
00153   return vcl_string("mfpf_region_about_lineseg");
00154 }
00155 
00156 //: Create a copy on the heap and return base class pointer
00157 mfpf_region_definer* mfpf_region_about_lineseg::clone() const
00158 {
00159   return new mfpf_region_about_lineseg(*this);
00160 }
00161 
00162 //=======================================================================
00163 // Method: print
00164 //=======================================================================
00165 
00166 void mfpf_region_about_lineseg::print_summary(vcl_ostream& os) const
00167 {
00168   os<<"{ i0: "<<i0_<<" i1: "<<i1_
00169     <<" rel_wi: "<<rel_wi_<<" rel_wj: "<<rel_wj_
00170     <<" form: "<<form_<<" } ";
00171 }
00172 
00173 //=======================================================================
00174 // Method: save
00175 //=======================================================================
00176 
00177 void mfpf_region_about_lineseg::b_write(vsl_b_ostream& bfs) const
00178 {
00179   vsl_b_write(bfs,version_no());
00180   vsl_b_write(bfs,i0_);
00181   vsl_b_write(bfs,i1_);
00182   vsl_b_write(bfs,rel_wi_);
00183   vsl_b_write(bfs,rel_wj_);
00184   vsl_b_write(bfs,wi_);
00185   vsl_b_write(bfs,wj_);
00186   vsl_b_write(bfs,form_);
00187 }
00188 
00189 //=======================================================================
00190 // Method: load
00191 //=======================================================================
00192 
00193 void mfpf_region_about_lineseg::b_read(vsl_b_istream& bfs)
00194 {
00195   if (!bfs) return;
00196   short version;
00197   vsl_b_read(bfs,version);
00198   switch (version)
00199   {
00200     case (1):
00201       vsl_b_read(bfs,i0_);
00202       vsl_b_read(bfs,i1_);
00203       vsl_b_read(bfs,rel_wi_);
00204       vsl_b_read(bfs,rel_wj_);
00205       vsl_b_read(bfs,wi_);
00206       vsl_b_read(bfs,wj_);
00207       vsl_b_read(bfs,form_);
00208       break;
00209     default:
00210       vcl_cerr << "I/O ERROR: vsl_b_read(vsl_b_istream&)\n"
00211                << "           Unknown version number "<< version << vcl_endl;
00212       bfs.is().clear(vcl_ios::badbit); // Set an unrecoverable IO error on stream
00213       return;
00214   }
00215 }