Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members

conic_mirror.h

Go to the documentation of this file.
00001 /*
00002 Arroyo - software for the simulation of electromagnetic wave propagation
00003 through turbulence and optics.
00004 
00005 Copyright (c) 2000-2004 California Institute of Technology.  Written by
00006 Dr. Matthew Britton.  For comments or questions about this software,
00007 please contact the author at mbritton@astro.caltech.edu.
00008 
00009 This program is free software; you can redistribute it and/or modify it
00010 under the terms of the GNU General Public License as  published by the
00011 Free Software Foundation; either version 2 of the License, or (at your
00012 option) any later version.
00013 
00014 This program is provided "as is" and distributed in the hope that it
00015 will be useful, but WITHOUT ANY WARRANTY; without even the implied
00016 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  In no
00017 event shall California Institute of Technology be liable to any party
00018 for direct, indirect, special, incidental or consequential damages,
00019 including lost profits, arising out of the use of this software and its
00020 documentation, even if the California Institute of Technology has been
00021 advised of the possibility of such damage.   The California Institute of
00022 Technology has no obligation to provide maintenance, support, updates,
00023 enhancements or modifications.  See the GNU General Public License for
00024 more details.
00025 
00026 You should have received a copy of the GNU General Public License along
00027 with this program; if not, write to the Free Software
00028 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
00029 */
00030 
00031 #ifndef CONIC_MIRROR_H
00032 #define CONIC_MIRROR_H
00033 
00034 #include <iomanip>
00035 #include "optic.h"
00036 #include "diffractive_wavefront.h"
00037 #include "conic_section.h"
00038 
00039 namespace Arroyo {
00040 
00041 
00042   class conic_mirror_base :
00043     public one_to_one_optic,
00044     public conic_section  {
00045 
00046     public:
00047 
00050     conic_mirror_base(){};
00051 
00054     virtual ~conic_mirror_base(){};
00055 
00058     virtual void read(const char * filename) = 0;
00059 
00062     virtual void read(const iofits & iof) = 0;
00063  
00066     virtual void write(const char * filename) const = 0;
00067 
00070     virtual void write(iofits & iof) const = 0;
00071 
00074     virtual void print(ostream & os, const char * prefix="") const = 0;
00075 
00083     virtual three_point get_point_of_intersection(const three_point & tp, 
00084                                                   const three_vector & tv) const = 0;
00085 
00086   };
00087 
00088 
00095 
00096   template<class aperture_type>
00097     class conic_mirror :
00098     public conic_mirror_base {
00099 
00100     private:
00101 
00102     static const bool factory_registration;
00103 
00106     string unique_name() const {return(string("conic mirror"));};
00107 
00108     protected:
00109 
00110     // The aperture
00111     aperture_type ap;
00112 
00113     // The transmission spectrum of this mirror
00114     //mirror_reflectivity_spectrum * mirror_reflec_spec;
00115     
00116     // Here we can either choose to enforce
00117     // the law of reflection, or we can 
00118     // require that the raytrace occurs along
00119     // a ray perpendicular to the wavefront 
00120     // surface.
00121     //
00122     // raytrace_policy=true => law of reflection
00123     // raytrace_policy=false => orthogonal final ray
00124     bool raytrace_policy;
00125 
00131     conic_mirror(){};
00132 
00140     template<class T>
00141       void private_transform(diffractive_wavefront<T> & wf) const;
00142 
00143     public:
00144 
00147     conic_mirror(const conic_mirror & cmr);
00148 
00151     conic_mirror(const char * filename);
00152 
00155     conic_mirror(const iofits & iof);
00156 
00176     conic_mirror(const three_point & vertex, 
00177                  const three_point & focus, 
00178                  double eccty, 
00179                  const aperture_type & in_ap);
00180 
00183     ~conic_mirror(){};
00184 
00187     conic_mirror & operator=(const conic_mirror & cmr);
00188 
00191     void read(const char * filename);
00192 
00195     void read(const iofits & iof);
00196  
00199     void write(const char * filename) const;
00200 
00203     void write(iofits & iof) const;
00204 
00207     void print(ostream & os, const char * prefix="") const;
00208 
00218     bool get_raytrace_policy() const {
00219       return(this->raytrace_policy);
00220     };
00221 
00224     void set_raytrace_policy(bool raytrace_policy){
00225       this->raytrace_policy = raytrace_policy;
00226     };
00227 
00240     rectangular_region get_covering_region(const three_frame & tf) const;
00241 
00249     three_point get_point_of_intersection(const three_point & tp, 
00250                                           const three_vector & tv) const;
00251     
00254     void transform(diffractive_wavefront<float> & wf) const;
00255 
00258     void transform(diffractive_wavefront<double> & wf) const;
00259 
00260   };
00261 
00262 
00263   template<class aperture_type>
00264     conic_mirror<aperture_type>::conic_mirror(const conic_mirror & cmr) {
00265     this->operator=(cmr);
00266   }
00267 
00268   template<class aperture_type>
00269     conic_mirror<aperture_type>::conic_mirror(const char * filename){
00270     this->read(filename);
00271   }
00272 
00273   template<class aperture_type>
00274     conic_mirror<aperture_type>::conic_mirror(const iofits & iof){
00275     this->read(iof);
00276   }
00277 
00278   template<class aperture_type>
00279     conic_mirror<aperture_type>::conic_mirror(const three_point & vtx, 
00280                                               const three_point & focus, 
00281                                               double eccty, 
00282                                               const aperture_type & in_ap) : ap(in_ap){
00283 
00284     this->conic_section::operator=(conic_section(vtx,focus,eccty));
00285 
00286     this->raytrace_policy = true;
00287 
00288     if((this->get_point_of_intersection(ap, ap.z()) - ap).length()>three_frame::precision){
00289       cerr << "conic_mirror::conic_mirror error - "
00290            << "aperture center does not lie on the surface of the conic mirror\n";
00291       throw(string("conic_mirror::conic_mirror"));
00292     }
00293   }
00294  
00295   template<class aperture_type>
00296     conic_mirror<aperture_type> & conic_mirror<aperture_type>::operator=(const conic_mirror & cmr) {
00297     if(this==&cmr) return(*this);
00298     this->conic_section::operator=(cmr);
00299     this->ap = cmr.ap;
00300     this->raytrace_policy=cmr.raytrace_policy;
00301     return(*this);
00302   }
00303 
00304   template<class aperture_type>
00305     void conic_mirror<aperture_type>::read(const char * filename) {
00306     iofits iof;
00307     try{iof.open(filename);}
00308     catch(...){
00309       cerr << "conic_mirror::read - "
00310            << "error opening file " << filename << endl;
00311       throw(string("conic_mirror::read"));
00312     }
00313     try{this->read(iof);}
00314     catch(...){
00315       cerr << "conic_mirror::read - "
00316            << "error reading "
00317            << this->unique_name() << " from file " 
00318            << filename << endl;
00319       throw(string("conic_mirror::read"));
00320     }
00321   }
00322 
00323   template<class aperture_type>
00324     void conic_mirror<aperture_type>::read(const iofits & iof) {
00325     if(!iof.key_exists("TYPE")){
00326       cerr << "conic_mirror::read error - "
00327            << "no power law type specified\n";
00328       throw(string("conic_mirror::read"));
00329     } else {
00330       string type, comment;
00331       iof.read_key("TYPE", type, comment);
00332       if(type!=this->unique_name()){
00333         cerr << "conic_mirror::read error - outer scale of type " 
00334              << type << " rather than type "
00335              << this->unique_name() << endl;
00336         throw(string("conic_mirror::read"));
00337       } else {
00338 
00339         iof.read_key("RAYPLCY", this->raytrace_policy, comment);
00340 
00341         // move to the aperture header
00342         try{
00343           iof.movrel_hdu(1);
00344         } catch(...){
00345           cerr << "conic_mirror::read - error moving to aperture hdu\n";
00346           throw(string("conic_mirror::read"));
00347         }         
00348 
00349         try{
00350           this->ap.read(iof);
00351         } catch(...){
00352           cerr << "conic_mirror::read - error reading aperture\n";
00353           throw(string("conic_mirror::read"));
00354         }         
00355 
00356         try{
00357           this->conic_section::read(iof);
00358         } catch(...){
00359           cerr << "conic_mirror::read - error reading conic section\n";
00360           throw(string("conic_mirror::read"));
00361         }       
00362       }
00363     }
00364 
00365   }
00366  
00367   template<class aperture_type>
00368     void conic_mirror<aperture_type>::write(const char * filename) const {
00369     iofits iof;
00370     try{iof.create(filename);}
00371     catch(...){
00372       cerr << "conic_mirror::write - "
00373            << "error opening file " << filename << endl;
00374       throw(string("conic_mirror::write"));
00375     }
00376 
00377     try{this->write(iof);}
00378     catch(...){
00379       cerr << "conic_mirror::write - "
00380            << "error writing "
00381            << this->unique_name() << " to file " 
00382            << filename << endl;
00383       throw(string("conic_mirror::write"));
00384     }
00385   }
00386 
00387   template<class aperture_type>
00388     void conic_mirror<aperture_type>::write(iofits & iof) const {
00389     Arroyo::fits_header_data<char> tmphdr;
00390     tmphdr.write(iof);
00391 
00392     string type = this->unique_name();
00393     string comment = "object type";
00394     iof.write_key("TYPE", type, comment);
00395     iof.write_key("RAYPLCY", this->raytrace_policy, string("raytrace policy"));
00396 
00397     this->ap.write(iof);
00398     this->conic_section::write(iof);
00399   }
00400 
00401   template<class aperture_type>
00402     void conic_mirror<aperture_type>::print(ostream & os, const char * prefix) const {
00403     int vlspc = 30;
00404     os.setf(std::ios::left, std::ios::adjustfield); 
00405     os << prefix << "TYPE       = " << setw(vlspc) << this->unique_name()
00406        << "/" << "object type" << endl;
00407     os << prefix << "RAYPLCY    = " << setw(vlspc) << this->raytrace_policy
00408        << "/" << "raytrace policy" << endl;
00409     this->conic_section::print(os, prefix);
00410     this->ap.print(os, prefix);
00411   }
00412 
00413   template<class aperture_type>
00414     rectangular_region conic_mirror<aperture_type>::get_covering_region(const three_frame & tf) const {
00415     return(this->ap.get_covering_region(tf));
00416   }
00417 
00418   template<class aperture_type>
00419     three_point conic_mirror<aperture_type>::get_point_of_intersection(const three_point & tp,
00420                                                                        const three_vector & tv) const {
00421 
00422     double distance_to_conic, R_squared, V;
00423     three_vector conic_unit_normal;
00424     three_point point_of_intersection;
00425 
00426     this->conic_section::raytrace(tp,
00427                                   tv,
00428                                   distance_to_conic,
00429                                   point_of_intersection,
00430                                   conic_unit_normal,
00431                                   R_squared,
00432                                   V);
00433 
00434     return(point_of_intersection);
00435   }
00436 
00437   template<class aperture_type>
00438     void conic_mirror<aperture_type>::transform(diffractive_wavefront<float> & wf) const {
00439     try{this->private_transform(wf);}
00440     catch(...){
00441       cerr << "conic_mirror::transform error - "
00442            << "error transforming a float instantiation of diffractive_wavefront\n";
00443       throw(string("conic_mirror::transform"));
00444     }
00445   }
00446 
00447   template<class aperture_type>
00448     void conic_mirror<aperture_type>::transform(diffractive_wavefront<double> & wf) const {
00449     try{this->private_transform(wf);}
00450     catch(...){
00451       cerr << "conic_mirror::transform error - "
00452            << "error transforming a double instantiation of diffractive_wavefront\n";
00453       throw(string("conic_mirror::transform"));
00454     }
00455   }
00456   
00457   template<class aperture_type>
00458     template<class T>
00459     void conic_mirror<aperture_type>::private_transform(diffractive_wavefront<T> & wf) const {
00460 
00461     // Here we do this off the bat to avoid sign convention issues in
00462     // the raytrace that I can't figure out right now.
00463     //wf.set_wavefront_curvature(0);
00464 
00465     //  First, test whether the center of the wavefront 
00466     //  lies on the conic surface
00467     double init_wf_to_conic_OPD, conic_to_final_wf_OPD, conic_R_squared, conic_V;
00468     three_vector conic_unit_normal;
00469     three_point conic_point_of_intersection;    
00470 
00471     try{
00472       this->conic_section::raytrace(wf,
00473                                     wf.z(),
00474                                     init_wf_to_conic_OPD,
00475                                     conic_point_of_intersection,
00476                                     conic_unit_normal,
00477                                     conic_R_squared,
00478                                     conic_V);
00479     } catch(...) {
00480       cerr << "conic_mirror::private_transform - error tracing central ray\n";
00481       throw(string("conic_mirror::private_transform"));
00482     }
00483 
00484     if(fabs(init_wf_to_conic_OPD)>three_frame::precision){
00485       cerr << "conic_mirror::private_transform error - wavefront does not lie on conic surface\n";
00486       cerr << "distance to conic " << init_wf_to_conic_OPD << endl;
00487 
00488       throw(string("conic_mirror::private_transform"));
00489     }
00490     
00491     // Define the three_frame of the final wavefront using the law of
00492     // reflection: rotate the incident wavefront three_frame about the
00493     // vector orthogonal to the plane formed from wf.z() and the
00494     // conic_unit_normal, and then flip the sign on wf.z()
00495     three_frame final_wf_tf(wf);
00496     three_vector perpendicular_vector;
00497 
00498     try{
00499       perpendicular_vector = cross_product(wf.z(),
00500                                            conic_unit_normal);
00501       
00502       if(perpendicular_vector.length()>three_frame::precision){
00503         three_rotation trot(wf, 
00504                           perpendicular_vector, 
00505                             -2*perpendicular_vector.length());
00506         trot.transform(final_wf_tf);
00507       }
00508       final_wf_tf = three_frame(final_wf_tf, 
00509                                 final_wf_tf.x(),
00510                                 final_wf_tf.y(),
00511                                 -1*final_wf_tf.z());
00512     } catch(...) {
00513       cerr << "conic_mirror::private_transform - error forming final three frame\n";
00514       throw(string("conic_mirror::private_transform"));
00515     }
00516 
00517     // Define the final wavefront curvature based on the paraxial approximation
00518     // and the local curvature.
00519     //
00520     // Here the wavefront curvature is positive for diverging wavefronts,
00521     // and the conic curvature is positive for concave conics.
00522     //
00523     // Thus, a diverging wavefront meeting a concave conic with half
00524     // the curvature will yield a flat wavefront, and a flat wavefront
00525     // reflecting off a concave conic will yield a converging wavefront
00526     double initial_wavefront_curvature = wf.get_curvature();
00527     double final_wavefront_curvature = 
00528       initial_wavefront_curvature - 
00529       2*this->conic_section::get_local_curvature(wf);
00530 
00531     if(optic::verbose_level)
00532       cout << "conic_mirror::private_transform: "
00533            << "initial curvature " << initial_wavefront_curvature
00534            << " local curvature " << this->conic_section::get_local_curvature(wf)
00535            << " final curvature " << final_wavefront_curvature
00536            << endl;
00537 
00538     // Define a conic section to represent the final spherical wavefront
00539     three_point final_focus;
00540     conic_section final_wavefront_conic;
00541     if(fabs(final_wavefront_curvature)<three_frame::precision){
00542       final_focus = final_wf_tf + 1e15*wf.z();
00543       final_wavefront_conic = conic_section(wf,
00544                                             final_focus,
00545                                             0);
00546     } else {
00547       final_focus = final_wf_tf - (1/final_wavefront_curvature)*final_wf_tf.z();
00548       final_wavefront_conic = conic_section(wf,
00549                                             final_focus,
00550                                             0);
00551     }
00552 
00553     try{
00554 
00555       // Make the transformation to amp, phase storage in the wf, and
00556       // get the pointer to the raw wavefront data
00557       bool interleaved_storage = is_interleaved_storage(wf);
00558       this->wavefront_amp_phase_conversion(wf);
00559       T * wfdata = get_wavefront_data(wf);
00560 
00561       // The halfpixel information
00562       vector<long> wf_axes = wf.get_axes();
00563       long nelem = wf_axes[0]*wf_axes[1];
00564       double x_halfpix=0, y_halfpix=0;
00565       int x_extrapix=1, y_extrapix=1;
00566       if(wf_axes[1]%2==0){
00567         x_halfpix = .5;
00568         x_extrapix = 0;
00569       }
00570       if(wf_axes[0]%2==0){
00571         y_halfpix = .5;
00572         y_extrapix = 0;
00573       }
00574       
00575       int index;
00576       double residual_OPD;
00577       double wavelength_meters = wf.get_wavelength();
00578       double arc_length_meters;
00579       double twopi = 2*M_PI;
00580       double final_wf_R_squared, final_wf_V;
00581       
00582       three_vector rotation_vector;
00583       three_point initial_pixel_tp, final_pixel_tp;
00584       three_vector initial_pixel_tv, final_pixel_tv;
00585       three_vector perpendicular_vector;
00586       three_point final_wf_point_of_intersection;
00587       three_vector final_wf_unit_normal;
00588 
00589       for(int i=-wf_axes[1]/2; i<wf_axes[1]/2+x_extrapix; i++){
00590         for(int j=-wf_axes[0]/2; j<wf_axes[0]/2+y_extrapix; j++){
00591 
00592           try{
00593             if(fabs(initial_wavefront_curvature)<three_frame::precision){
00594               
00595               initial_pixel_tv = wf.z();
00596               initial_pixel_tp = 
00597                 wf + 
00598                 (i+x_halfpix)*wf.get_pixel_scale()*wf.x()+
00599                 (j+y_halfpix)*wf.get_pixel_scale()*wf.y();
00600               
00601             } else {
00602               
00603               initial_pixel_tv = wf.z();
00604 
00605               three_point wavefront_center_of_curvature = 
00606                 wf - fabs(1/initial_wavefront_curvature)*wf.z();
00607               
00608               // the length of the arc
00609               arc_length_meters = 
00610                 sqrt((i+x_halfpix)*(i+x_halfpix)+
00611                      (j+y_halfpix)*(j+y_halfpix))*
00612                 wf.get_pixel_scale();
00613               
00614               // the vector about which to rotate wf.z() to
00615               // get the ray propagation direction
00616 
00617               if(fabs(arc_length_meters)>three_frame::precision){
00618                 rotation_vector = cross_product(wf.z(),
00619                                                 (i+x_halfpix)*wf.x()+
00620                                                 (j+y_halfpix)*wf.y());
00621                 
00622                 three_rotation trot(wavefront_center_of_curvature,
00623                                     rotation_vector,
00624                                     -1*initial_wavefront_curvature*arc_length_meters);
00625                 
00626                 trot.transform(initial_pixel_tv);
00627               }
00628 
00629               initial_pixel_tp = 
00630                 wavefront_center_of_curvature +
00631                 (1/fabs(initial_wavefront_curvature))*initial_pixel_tv;
00632             }
00633           } catch(...) {
00634             cerr << "conic_mirror::private_transform - error finding initial point on wavefront\n";
00635             throw(string("conic_mirror::private_transform"));
00636           }
00637 
00638 
00639           // If the initial point is on the conic, we can skip the
00640           // analysis
00641           if(this->conic_section::on_conic(initial_pixel_tp))
00642             continue;
00643 
00644           residual_OPD = 0;
00645 
00646           try{
00647             this->conic_section::raytrace(initial_pixel_tp,
00648                                           initial_pixel_tv,
00649                                           init_wf_to_conic_OPD,
00650                                           conic_point_of_intersection,
00651                                           conic_unit_normal,
00652                                           conic_R_squared,
00653                                           conic_V);
00654 
00655             residual_OPD += init_wf_to_conic_OPD;
00656             final_pixel_tp = conic_point_of_intersection;
00657 
00658           } catch(...) {
00659             cerr << "conic_mirror::private_transform - error tracing initial rays\n";
00660             throw(string("conic_mirror::private_transform"));
00661           }
00662 
00663 
00664           try{
00665             if(this->raytrace_policy){
00666               
00667               final_pixel_tv = initial_pixel_tv;
00668 
00669               three_reflection tref(conic_point_of_intersection,
00670                                     conic_unit_normal);
00671               
00672               tref.transform(final_pixel_tv);
00673 
00674               // Make sure we've reflected properly
00675               if(fabs(dot_product(initial_pixel_tv,
00676                                   conic_unit_normal) +
00677                       dot_product(final_pixel_tv,
00678                                   conic_unit_normal))>three_frame::precision){
00679                 cerr << "conic_mirror::private_transform - error forming final ray vector\n";
00680                 
00681                 three_vector tmp = -1*initial_pixel_tv;
00682 
00683                 tmp.print(cerr, "\treflected initial tv ");
00684                 conic_unit_normal.print(cerr, "\tconic normal tv ");
00685                 perpendicular_vector.print(cerr, "\tperp tv ");
00686                 final_pixel_tv.print(cerr, "\tfinal tv ");
00687                 
00688                 cout << "\tlengths: init " 
00689                      << initial_pixel_tv.length()
00690                      << "\treflected "
00691                      << tmp.length()
00692                      << "\tconic unit normal " 
00693                      << conic_unit_normal.length()
00694                      << "\tfinal "
00695                      << final_pixel_tv.length()
00696                      << endl;
00697 
00698                 cout << "\tdot products: " 
00699                      << dot_product(tmp,conic_unit_normal) 
00700                      << "\t" 
00701                      << dot_product(conic_unit_normal, final_pixel_tv) 
00702                      << "\t" 
00703                      << dot_product(tmp,conic_unit_normal) - dot_product(conic_unit_normal, final_pixel_tv) 
00704                      << endl;
00705 
00706                 throw(string("conic_mirror::private_transform"));
00707               }
00708 
00709             } else {
00710               // Requirement that the ray is perpendicular to the
00711               // spherical wavefront surface
00712               final_pixel_tv = final_focus - conic_point_of_intersection;
00713               final_pixel_tv = (1/final_pixel_tv.length())*final_pixel_tv;
00714             }
00715           } catch (...){ 
00716             cerr << "conic_mirror::private_transform - error finding final pixel vector\n";
00717             throw(string("conic_mirror::private_transform"));
00718           }
00719 
00720           try{
00721             final_wavefront_conic.raytrace(final_pixel_tp,
00722                                            final_pixel_tv,
00723                                            conic_to_final_wf_OPD,
00724                                            final_wf_point_of_intersection,
00725                                            final_wf_unit_normal,
00726                                            final_wf_R_squared,
00727                                            final_wf_V);
00728 
00729             residual_OPD += conic_to_final_wf_OPD;
00730           } catch(...) {
00731             cerr << "conic_mirror::private_transform - error tracing final rays\n";
00732             final_pixel_tv.print(cerr, "fpv ");
00733             final_focus.print(cerr, "ffocus ");
00734             final_wf_point_of_intersection.print(cerr, "cnc pt int");
00735             throw(string("conic_mirror::private_transform"));
00736           }
00737 
00738 
00739           if(optic::verbose_level){
00740             cout << "conic_mirror::private_transform - "
00741                  << (i+x_halfpix)*wf.get_pixel_scale()
00742                  << "\t" 
00743                  << (j+y_halfpix)*wf.get_pixel_scale()
00744                  << "\tinitial OPD " 
00745                  << init_wf_to_conic_OPD
00746                  << "\tfinal OPD " 
00747                  << conic_to_final_wf_OPD
00748                  << " net OPD "
00749                  << residual_OPD
00750                  << " phase " 
00751                  << twopi*fmod(residual_OPD/wavelength_meters, 1.)
00752                  << endl;
00753           }
00754 
00755           // Some tests:
00756           if(cross_product(.5*(final_pixel_tv - initial_pixel_tv),conic_unit_normal).length()/1e6>
00757              three_frame::precision){
00758             cout << "conic_mirror::private_transform error - cross product "
00759                  << cross_product(.5*(final_pixel_tv - initial_pixel_tv),conic_unit_normal).length()
00760                  << " indicates initial, final, and conic normal vectors are not coplanar\n";
00761             
00762             initial_pixel_tp.print(cout, "\tinitial pixel tp ");
00763             initial_pixel_tv.print(cout, "\tinitial pixel tv ");
00764             final_pixel_tp.print(cout, "\tfinal pixel tp ");
00765             final_pixel_tv.print(cout, "\tfinal pixel tv ");
00766             conic_point_of_intersection.print(cout, "\tconic pt of intersection ");
00767             conic_unit_normal.print(cout, "\tconic unit normal ");
00768             final_wf_point_of_intersection.print(cout, "\tfinal wf pt of intersection ");
00769             final_wf_unit_normal.print(cout, "\tfinal wf unit normal ");
00770             cout << "\tconic params:  R_squared " << conic_R_squared << "\tV " << conic_V << endl;
00771             cout << "\tfinal wf params:  R_squared " << final_wf_R_squared << "\tV " << final_wf_V << endl;
00772             cout << endl << endl;
00773             three_vector tmp = .5*(final_pixel_tv - initial_pixel_tv);
00774 
00775             tmp.print(cout, "\t.5*(final - initial tv) ");
00776             tmp = (1/tmp.length())*tmp;
00777             tmp.print(cout, "\tnormalized .5*(final - initial tv) ");
00778             conic_unit_normal.print(cout, "\tconic unit normal ");
00779             (tmp-conic_unit_normal).print(cout, "\tdiff vector ");
00780 
00781             cross_product(.5*(final_pixel_tv - initial_pixel_tv),conic_unit_normal).print(cout, "\txproduct " );
00782             cout << "\tInit length " << initial_pixel_tv.length() << endl;
00783             cout << "\tFinal length " << final_pixel_tv.length() << endl;
00784             cout << "\tDiff length " << .5*(final_pixel_tv - initial_pixel_tv).length() << endl;
00785             cout << "\tConic normal length " << conic_unit_normal.length() << endl;
00786             
00787             throw(string("conic_mirror::private_transform"));
00788           }
00789 
00790 
00791           // Set the new phase correctly
00792           //
00793           // A positive residual OPD indicates that the ray is advanced
00794           // wrt the wavefront, so that OPD/wavelength should be
00795           // added to the wavefront phase
00796           try{
00797             index = (i+wf_axes[1]/2)*wf_axes[0]+j+wf_axes[0]/2;
00798             if(interleaved_storage){
00799               wfdata[2*index+1] = 
00800                 fmod(wfdata[2*index+1]+twopi*residual_OPD/wavelength_meters, twopi);
00801               if(wfdata[2*index+1]<0) wfdata[2*index+1]+=twopi;
00802             } else {
00803               wfdata[index+nelem] = 
00804                 fmod(wfdata[index+nelem]+twopi*residual_OPD/wavelength_meters, twopi);
00805               if(wfdata[index+nelem]<0) wfdata[index+nelem]+=twopi;
00806             }
00807           } catch(...) {
00808             cerr << "conic_mirror::private_transform - error updating phases\n";
00809             throw(string("conic_mirror::private_transform"));
00810           }
00811 
00812             
00813           // set the curvature
00814           wf.set_curvature(final_wavefront_curvature);
00815 
00816         }
00817       }
00818     } catch(...) {
00819       cerr << "conic_mirror::private_transform - error raytracing wavefront\n";
00820       throw(string("conic_mirror::private_transform"));
00821     }
00822 
00823     // Do the aperture transformation.  Translate the aperture
00824     // along ap->z() to the transverse plane of the wavefront.  Apply
00825     // the aperture, and translate it back
00826     try{
00827       three_point wf_ap_intsctn_pt = 
00828         ap.get_point_of_intersection(wf,
00829                                      ap.z());
00830 
00831       three_point orig_wf_pt(wf);
00832 
00833       wf.three_point::operator=(wf_ap_intsctn_pt);
00834       ap.transform(wf);
00835 
00836       wf.three_point::operator=(orig_wf_pt);
00837 
00838     } catch(...) {
00839       cerr << "conic_mirror::private_transform - error aperturing wavefront\n";
00840       throw(string("conic_mirror::private_transform"));
00841     }
00842 
00843     // Assign the final wavefront three frame
00844     wf.three_frame::operator=(final_wf_tf);
00845 
00846 
00847   }
00848 }
00849 #endif

Generated on Thu Nov 29 17:16:28 2007 for arroyo by  doxygen 1.3.9.1