//============================================================================= //============================================================================= // Copyright 2004 by the author, Joseph M. Howard. // All rights reserved. // No part of this ccl program script may be reproduced, transmitted, transcribed, // stored in a retrieval system, or translated into any language or computer language, // in any form or by any means, electronic, mechanical, magnetic, optical, chemical, manual or // otherwise, without the prior written permission of the author. // Users of this ccl program script are authorized to modify this code for their // own personal use, be it to improve efficiency or to suit specific needs. // Suggestions to the author regarding changes are always welcome. //============================================================================= //============================================================================= // Revision History // v2004.01.20 First public release of SLIDERS // v2004.02.26 Fixed conflict with Standard and Premium version (commands in Tools/Special/Spherical Mirrors) cmd aboutSLIDERS() { prt; prt "====================="; prt "SLIDERS v2004.02.26"; prt "====================="; prt; prt "Author: Joseph M. Howard, Ph.D."; prt; prt "These routines are based on analytic correction of optical systems."; prt "The fundamental idea is to remove individual degrees of freedom (such as a"; prt "thickness or a curvature) from the design space to ensure a given set of"; prt "low order image properties (such as defocus or spherical aberration). "; prt; prt "A simple example of controling low order image properties "; prt "is the 'solve' feature built into OSLO, where the user "; prt "can give up control of a thickness parameter, or curvature if desired, "; prt "to set the marginal ray height to zero at the following surface."; prt "In such a solve, OSLO iterates the parameter numerically to achieve the"; prt "desired effect, and no knowledge of the system is necessary, just the local"; prt "properties of the raytrace. "; prt; prt "In SLIDERS, however, the process is analytic. Equations have been developed "; prt "for each class of system to ensure the given effect. Consider a Ritchey-Chretien"; prt "telescope, for example, which can be found under the '2 mirror telescopes' menu"; prt "of SLIDERS. The degrees of freedom for an unconstrained two conic mirror system number"; prt "six: two thicknesses, two curvatures, and two conic constants. In SLIDERS, however, the "; prt "curvatures are 'solved' by the equations built into the macro to ensure zero defocus "; prt "and the desired f/# of the telescope. Additionally, the two conic constants are 'solved'"; prt "to ensure zero spherical and coma aberrations. The result is that you, the designer, "; prt "have control over the mirror seperations, and the back focal distance of the telescope."; prt "Note that each class of system (e.g. two mirror, three mirror, etc.) requires its own"; prt "set of equations, hence multiple SLIDERS routines are provided to the user. More details"; prt "on each SLIDERS routine can be found from the referenced paper in the text window"; prt "when the routine is started from the SLIDERS menu."; prt; prt "I welcome any contributions or feedback to these educational design tools, and encourage"; prt "you to send any questions or comments to:"; prt; prt "Joseph.M.Howard(a)nasa.gov"; prt; prt " Go Navy, Beat Army!!"; prt; prt "Bibliography"; prt "============"; prt "[1] Joseph M. Howard, 'Optical design using computer graphics,'"; prt " Applied Optics, Vol. 40, No. 19, 3225-3231 (2001)."; prt "[2] Joseph M. Howard, 'Optical design tools for reflective optical systems,'"; prt " Proc. SPIE, Vol. 4849, 407-412 (2002)."; prt "[3] Joseph M. Howard, 'SLIDERS: the next generation of automated optical design tools has arrived,'"; prt " Proc. SPIE, Vol. 5174, 19-25 (2003)."; } ////////////////////////////////// // // // Main window menu for SLIDERS // // // ////////////////////////////////// /* this is placed here for reference, a seperate a_menu ccl is required to activate these menu items menu SLIDERS { "R,2 mirror telescopes" = "RS2inf_sldrs", "C,Classroom Demonstrations" = "$ClassDemos", "O,'Optical Design by Pictures', Applied Optics paper" = "$Pictures", "U,Unobstructed Spherical Mirror Systems, Ph.D. Thesis" = "$SphereMirrors", "S,Conic Telescope Systems, D. Korsch equations" = "$Telescopes", "A,About SLIDERS" = "aboutSLIDERS", } menu ClassDemos { "S,Seidel Aberration Viewer..." = "sl_3rd", "D,Doublet Design..." = "sl_doublet", "T,Triplet Bending..." = "open public \"len/demo/edu/demotrip.len\";sl_trip 0.0;", } menu Pictures { "1,Example 1: Achromatic microscope objective" = "Micro_4", "2,Example 2: 3 spherical mirror telescope" = "three_mirINF_sldrs", "3,Example 3: 3 concentric sphere relay" = "Concentric_3Sphere_sldrs", } menu Telescopes { "2,2 mirror telescopes" = "RS2inf_sldrs", "3,3 mirror telescopes" = "RS3inf_sldrs", "4,4 mirror telescopes" = "RS4inf_sldrs", } menu SphereMirrors { "1, 1 Mirror -- Finite Conjugate" = SM1_sldrs, "1, 1 Mirror -- Object at INF" = SM1INF_sldrs, "2, 2 Mirror -- Finite Conjugate" = SM2_sldrs, "2, 2 Mirror -- Object at INF" = SM2INF_sldrs, "2, 2 Mirror -- Afocal" = SM2afo_sldrs, "3, 3 Mirror -- Finite Conjugate" = SM3_sldrs, "3, 3 Mirror -- Object at INF" = SM3INF_sldrs, "2, 3 Mirror -- Afocal" = SM3afo_sldrs, "4, 4 Mirror -- Finite Conjugate" = SM4_sldrs, "4, 4 Mirror -- Object at INF" = SM4INF_sldrs, } */ //============================================================================= //============================================================================= double sec(double theta) {return (1/cos(theta));} double csc(double theta) {return (1/sin(theta));} double cot(double theta) {return (1/tan(theta));} double arcsin(double theta) {return (asin(theta));} double arctan(double theta) {return (atan2(theta, 1));} double atan(double theta) {return (atan2(theta, 1));} double sqr(double argument) {return (argument**2);} double sign( double dummy ) { if (dummy<0.0) return -1.0; else if (dummy>0.0) return 1.0; else return 0.0; } //============================================================================= //============================================================================= //The following routine used with permission from the author: Bryan D. Stone //============================================================================= //============================================================================= /* Copyright 1999: Bryan D. Stone */ double thmin, thmax, defmin, defmax, entmin, entmax; /*******************************************************************/ /*******************************************************************/ // Prototypes cmd micro_4(); cmd micro_4_setup(double phitot, double phi1, double mag, double th1, double th2, double th3, double th4, double th5, double cv1, double cv4, double entpuploc, double NAobj, double objsize, double wav0, double wav1, double wav2); cmd micro_4_sldrs(double power, double phi1, double mag, double th1, double curv1, double curv2, double epl, double curvmin, double curvmax, double thimin, double thimax, double magmin, double magmax, double defmin, double defmax, double eplmin, double eplmax, double powmin, double powmax, double phi1min, double phi1max); cmd micro_4_clbck(int slider_id, double slider_value); cmd micro_4_vary(double phitot, double phi1, double mag, double th1, double th2, double th3, double th4, double th5, double curv1, double curv4, double entpuploc); cmd get_curvs(double crvs2and3[], double cv1, double aa0, double cc0, double ua0, double ya1, double n1,double n2,double d1,double d2,double v1,double v2, double phitot); cmd standard_setup(); cmd sct_tre_calbck(int slider_id, double slider_value); cmd get_ABCD(int surf1, int surf2, double ABCD[][]); cmd show_chiefrays(); cmd three_fp(); cmd three_treps(); cmd label_cardpts(); cmd my_spot_diagram(); cmd my_tran_ray_plot(); cmd mult2x2(double m1[][], double m2[][], double m3[][]); double my_arr_max(double anarr[], int arr_len); double my_arr_min(double anarr[], int arr_len); double my_arr_max2(double anarr2[][], int arr_len1, int arr_len2); double my_arr_min2(double anarr2[][], int arr_len1, int arr_len2); cmd simple_error_handler(); #define SCAT_OR_TRE_SLDR_ID 2 /*******************************************************************/ /*******************************************************************/ cmd micro_4() { double curv1, curv4, th1, th2, th3, th4, th5, mag, epl, power, phi1, phi1max, phi1min, magmin, magmax, powmin, powmax, wavmin, wavmax, waveband, curvmin, curvmax; double NAobj, objsize, wav0, wav1, wav2; curv1 = 0.051; curv4=0.075; curvmin = -0.1; curvmax = 0.1; thmin =0.0; thmax = 20; mag = -0.1; magmin = -2, magmax = 2; epl = 0; entmin=-100; entmax = 100; power = 0.05; powmin =-0.1; powmax = 0.1; phi1 = 0.025; phi1min =-0.1; phi1max = 0.1; defmin = -2; defmax = 2; NAobj = 0.025; objsize = 5.0; th1=3; th2=2; th3=9; th4=3; th5=2; wav0 = 0.5876; wav1 = 0.4861; wav2 = 0.6563; stp outp off; micro_4_setup(power, phi1, mag, th1, th2, th3, th4, th5, curv1, curv4, epl, NAobj, objsize, wav0, wav1, wav2); micro_4_sldrs(power, phi1, mag, th1, curv1, curv4, epl, curvmin, curvmax, thmin, thmax, magmin, magmax, defmin, defmax, entmin, entmax, powmin, powmax, phi1min, phi1max); stp outp on; stp gacl on; } /*******************************************************************/ /*******************************************************************/ cmd micro_4_setup(double phitot, double phi1, double mag, double th1, double th2, double th3, double th4, double th5, double cv1, double cv4, double entpuploc, double NAobj, double objsize, double wav0, double wav1, double wav2) { char gaclstat, outpstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); outpstat = char_pref(outp); set_preference(outp, off); file_new("Microscope", cus, 7); lid("Achromatic Microscope Objective"); des("bds sldrs"); uni mm; //sets units to cm nao NAobj; //object space NA obh objsize; //object height //wv 0.55; //wavelength for evaluation ast 1; //make first surface the aperture stop gla name 2 bk7; gla name 3 sf5; gla name 5 bk7; gla name 6 sf5; wv wav0 wav1 wav2; ap(imsnbr, 0.5); standard_setup; micro_4_vary(phitot, phi1, mag, th1, th2, th3, th4, th5, cv1, cv4, entpuploc); if (gaclstat) set_preference(graphics_autoclear, on); if (outpstat) set_preference(outp, on); } /*******************************************************************/ /*******************************************************************/ cmd micro_4_sldrs(double power, double phi1, double mag, double th1, double curv1, double curv2, double epl, double curvmin, double curvmax, double thimin, double thimax, double magmin, double magmax, double defmin, double defmax, double eplmin, double eplmax, double powmin, double powmax, double phi1min, double phi1max) { char gaclstat, outpstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); outpstat = char_pref(outp); set_preference(outp, off); GRAPHWIN_SLIDERASSIGN(11,r,d,"total power", micro_4_clbck,powmin,powmax,power); GRAPHWIN_SLIDERASSIGN(12,r,d,"power of doublet 1", micro_4_clbck,phi1min,phi1max,phi1); GRAPHWIN_SLIDERASSIGN(13,r,d,"Magnification", micro_4_clbck,magmin,magmax,mag); GRAPHWIN_SLIDERASSIGN(14,r,d,"Curv of surf 1 of lens 1", micro_4_clbck,curvmin,curvmax,curv1); GRAPHWIN_SLIDERASSIGN(15,r,d,"Curv of surf 1 of lens 3", micro_4_clbck,curvmin,curvmax,curv2); GRAPHWIN_SLIDERASSIGN(16,r,d,"Wavelength Range", micro_4_clbck,0,1,1); GRAPHWIN_SLIDERASSIGN(18,i,d,"Th to vary (0->6)", micro_4_clbck,0,6,0); GRAPHWIN_SLIDERASSIGN(17,r,d,"Thickness", micro_4_clbck,eplmin,eplmax,epl); GRAPHWIN_SLIDERASSIGN(SCAT_OR_TRE_SLDR_ID,i,d,"spots OR ray plots", sct_tre_calbck,0,1,1); graphwin_slidershow; gwo(5);gwr; show_chiefrays; gwo(1);gwr; gwo(2);gwr; gwo(3);gwr; three_treps; gwo(4);gwr; drl; label_cardpts; ddr; if (gaclstat) set_preference(graphics_autoclear, on); if (outpstat) set_preference(outp, on); } /*******************************************************************/ /*******************************************************************/ cmd micro_4_clbck(int slider_id, double slider_value) { char gaclstat, outpstat; double curv1, curv4, th1, th2, th3, th4, th5, mag, gscale, power, phi1, entpuploc, wavrange; int draw_rays, draw_obj; install_error_handler("simple_error_handler"); gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); outpstat = char_pref(outp); set_preference(outp, off); gscale = real_pref(scal); gwo(1);gclear; gwo(2);gclear; gwo(3);gclear; power = graphwin_slidervalue(11); phi1 = graphwin_slidervalue(12); mag = graphwin_slidervalue(13); curv1 = graphwin_slidervalue(14); curv4 = graphwin_slidervalue(15); entpuploc = th[1]; th1 = th[2]; th2 = th[3]; th3 = th[4]; th4 = th[5]; th5 = th[6]; if (slider_id==11) power = slider_value; else if (slider_id==12) phi1 = slider_value; else if (slider_id==13) mag = slider_value; else if (slider_id==14) curv1 = slider_value; else if (slider_id==15) curv4 = slider_value; else if (slider_id==16) wv(0.5876, 0.5876-(0.5876-0.4861)*slider_value, 0.5876+(0.6563-0.5876)*slider_value); else if (slider_id==17) { if (graphwin_slidervalue(18)<0.5) entpuploc = slider_value; else if (graphwin_slidervalue(18)<1.5) th1 = slider_value; else if (graphwin_slidervalue(18)<2.5) th2 = slider_value; else if (graphwin_slidervalue(18)<3.5) th3 = slider_value; else if (graphwin_slidervalue(18)<4.5) th4 = slider_value; else if (graphwin_slidervalue(18)<5.5) th5 = slider_value; else th(imsnbr, slider_value); } else if (slider_id==18) { if (slider_value<0.5) graphwin_sliderreset(17, r, entmin, entmax, entpuploc); else if (slider_value<1.5) graphwin_sliderreset(17, r, thmin, thmax, th1); else if (slider_value<2.5) graphwin_sliderreset(17, r, thmin, thmax, th2); else if (slider_value<3.5) graphwin_sliderreset(17, r, thmin, thmax, th3); else if (slider_value<4.5) graphwin_sliderreset(17, r, thmin, thmax, th4); else if (slider_value<5.5) graphwin_sliderreset(17, r, thmin, thmax, th5); else graphwin_sliderreset(17, r, defmin, defmax, th[imsnbr]); } if ((power != 0.0) && (mag != 0.0)) { //cmd micro_4_vary(power, phi1, mag, th1, th2, th3, th4, th5, curv1, curv4, entpuploc) micro_4_vary(power, phi1, mag, th1, th2, th3, th4, th5, curv1, curv4, entpuploc); gwo(5);gclear; show_chiefrays; if (graphwin_slidervalue(SCAT_OR_TRE_SLDR_ID)==0) three_fp; else three_treps; gwo(4);gclear; drl; label_cardpts; ddr; } if (gaclstat) set_preference(graphics_autoclear, on); if (outpstat) set_preference(outp, on); delete_error_handler; } /*******************************************************************/ /*******************************************************************/ cmd micro_4_vary(double phitot, double phi1, double mag, double th1, double th2, double th3, double th4, double th5, double curv1, double curv4, double entpuploc) { double th0, th6, ya1, ua0; double abcd[2][2], aa0,bb0,cc0,dd0, den, curvs2and3[2], n1,n2,n3,n4,v1,v2,v3,v4; double wavelengths[10]; int i0, numwavelengths; char gaclstat, outpstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); outpstat = char_pref(outp); set_preference(outp, off); cv 2 curv1; cv 5 curv4; th 0 -1.0/(phitot*mag)-entpuploc; th 1 entpuploc; th 2 th1; th 3 th2; th 4 th3; th 5 th4; th 6 th5; th 7 0; //remember wavelengths numwavelengths = numw; sbr 1 0 0; wav; for (i0=0; i00) //one real root { dum = -bc/2 + sqrt(discr); a0 = sgn(dum)* pow(fabs(dum), 1.0/3.0); dum = -bc/2 - sqrt(discr); b0 = sgn(dum)* pow(fabs(dum), 1.0/3.0); phi2[0] = a0+b0 - pc/3; phi2[1] = 99999; phi2[2] = 99999; } else if (discr==0) //three real roots, at least two equal { phi2[0] = 2.0* sgn(-bc/2)*pow(fabs(-bc/2), 1.0/3.0); phi2[1] = -sgn(-bc/2)*pow(fabs(-bc/2), 1.0/3.0); phi2[2] = 99999; } else //three real roots { dum = acos(-bc/2.0/sqrt(-ac*ac*ac/27.0)); phi2[0] = 2*sqrt(-ac/3.0) * cos(dum/3.0) - pc/3; phi2[1] = 2*sqrt(-ac/3.0) * cos(dum/3.0 + 2.0*pi/3.0) - pc/3; phi2[2] = 2*sqrt(-ac/3.0) * cos(dum/3.0 + 4.0*pi/3.0) - pc/3; } } if (fabs(phi2[0]) < fabs(phi2[1])) dum = phi2[0]; else dum = phi2[1]; if (fabs(phi2[2]) < dum) dum = phi2[2]; crvs2and3[0] = dum/(n2-n1); phi3 = -((k3 + k5*dum)/(k4 + k6*dum)); crvs2and3[1] = phi3/(1-n2); } /*******************************************************************/ /*******************************************************************/ cmd standard_setup() { drw(imsnbr, on); //draw image surface drl_raystosrf(set, img); //draw rays to image drl_aperstop(set, on); //draw aperture stop drl_nbrfpts(set, 3); //use three field points drl_yfieldpt(0, set, -1); drl_yfieldpt(1, set, 0); drl_yfieldpt(2, set, 1); drl_nbrrays(0, set, 3); drl_nbrrays(1, set, 3); drl_nbrrays(2, set, 3); drl_minpup(0, set, -1); drl_minpup(1, set, -1); drl_minpup(2, set, -1); drl_maxpup(0, set, 1); drl_maxpup(1, set, 1); drl_maxpup(2, set, 1); stp scvm on; //turn on spreadsheet curvature mode stp prtz on; //print zeros } /*******************************************************************/ /*******************************************************************/ cmd sct_tre_calbck(int slider_id, double slider_value) { char gaclstat, outpstat; install_error_handler("simple_error_handler"); gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); outpstat = char_pref(outp); set_preference(outp, off); gwo(1);gclear; gwo(2);gclear; gwo(3);gclear; if (slider_value<0.5) three_fp; else three_treps; if (gaclstat) set_preference(graphics_autoclear, on); if (outpstat) set_preference(outp, on); delete_error_handler; } /*******************************************************************/ /*******************************************************************/ cmd get_ABCD(int surf1, int surf2, double ABCD[][]) { int nsurf, i; double T[2][2], R[2][2], mult; nsurf = surf2-surf1; char outpstat; double d[nsurf], index[nsurf], c[nsurf]; outpstat = char_pref(outp); set_preference(outp, off); mult = 1.0; sbr 1 0 0; rin; for (i=surf1; imaxap) maxap=ap[i];} draw_graphics(mov, 0, 0, b6, 1); pen 8; draw_graphics(sym, 2); draw_graphics(dra, 0, 1.1*maxap, b6, 1); draw_graphics(mov, 0, 1.15*maxap, b6-.05*maxap, 1); pen 7; draw_graphics(lab, P); draw_graphics(mov, 0, 0, b6-a13, 1); pen 8; draw_graphics(sym, 7); draw_graphics(dra, 0, 1.1*maxap, b6-a13, 1); draw_graphics(mov, 0, 1.15*maxap, b6-a13-.05*maxap, 1); pen 7; draw_graphics(lab, F); draw_graphics(mov, 0, 0, b7, imsnbr-1); pen 6; draw_graphics(sym, 2); draw_graphics(dra, 0, -1.1*maxap, b7, imsnbr-1); draw_graphics(mov, 0, -1.3*maxap, b7-.05*maxap, imsnbr-1); pen 5; draw_graphics(lab, P'); draw_graphics(mov, 0, 0, b7+a13, imsnbr-1); pen 6; draw_graphics(sym, 7); draw_graphics(dra, 0, -1.1*maxap, b7+a13, imsnbr-1); draw_graphics(mov, 0, -1.3*maxap, b7+a13-.05*maxap, imsnbr-1); pen 5; draw_graphics(lab, F'); if (gaclstat) set_preference(graphics_autoclear, on); if (outpstat) set_preference(outp, on); } /*******************************************************************/ /*******************************************************************/ cmd my_spot_diagram() { double spot_diag_sym, minx, maxx, miny, maxy, scale, expon, mant; int i, j, nrays[numw], ntotrays, count; spd_apdiv(set, 11.05); sbr 1 0 0; spot_diagram_data; ntotrays = 0; spot_diag_sym = a5; for (i=0; ifabs(miny)) scale = fabs(minx); else scale = fabs(miny); if (fabs(maxx)>scale) scale = fabs(maxx); if (fabs(maxy)>scale) scale = fabs(maxy); expon = floor(log10(scale)); mant = scale/(pow(10, expon)); if (mant<2.0) mant=2.0; else if (mant<5.0) mant = 5.0; else mant = 10.0; scale = mant * pow(10, expon); window(iso, -1.0*scale, 1.0*scale, -1.2*scale, 1.4*scale); pen(1); line_style(sol); moveto(scale, scale); linerel(-2*scale, 0); linerel(0, -2*scale); linerel(2*scale, 0); linerel(0, 2*scale); lorigin 02; moveto(scale, scale); linerel(0.07*scale, 0.0); moverel(0.03*scale, 0.0); label "%-6.1g" scale; lorigin 02; moveto(scale, -scale); linerel(0.07*scale, 0.0); moverel(0.03*scale, 0.0); label "%-6.1g" -scale; lorigin 06; moveto(-scale, -scale); linerel(0.0, -0.07*scale); moverel(0.0, -0.03*scale); label "%-6.1g" -scale; lorigin 06; moveto(scale, -scale); linerel(0.0, -0.07*scale); moverel(0.0, -0.03*scale); label "%-6.1g" scale; count = 0; for (i=0; imax1) max1 = fabs(max2); if (fabs(max3)>max1) max1 = fabs(max3); if (fabs(min1)>max1) max1 = fabs(min1); if (fabs(min2)>max1) max1 = fabs(min2); if (fabs(min3)>max1) max1 = fabs(min3); expon = floor(log10(max1)); mant = max1/(pow(10, expon)); if (mant<2.0) mant=2.0; else if (mant<5.0) mant = 5.0; else mant = 10.0; scale = mant * pow(10, expon); line_style(sol); pen(1); viewport(0,0.5,0,1); window(tow, -1.2, 1.2, -1.2*scale, 1.4*scale); moveto(-1,-0.05*scale);lineto(-1,0); lineto(1,0);lineto(1,-0.05*scale); lsz 1.5; moveto(-1, -0.07*scale); lor 06; lab "-1"; lsz 1.5; moveto(1, -0.07*scale); lor 06; lab "1"; moveto(0.05,-scale); lineto(0,-scale); lineto(0,scale); lineto(0.05,scale); lsz 1.25; moveto(0.08, scale); lor 02; label "%-6.1g" scale; lsz 1.25; moveto(0.08, -scale); lor 02; label "%-6.1g" -scale; lsz 2.0; moveto(0, 1.1*scale); lor 04; label "epsy"; lsz 1.5; moveto(1.05,0); lor 02; label "fy"; for (i=0; immax) mmax = anarr[i]; } return mmax; } /*******************************************************************/ /*******************************************************************/ double my_arr_min(double anarr[], int arr_len) { int i; double mmin; mmin = anarr[0]; for (i=1; immax) mmax = anarr2[i][j]; } return mmax; } /*******************************************************************/ /*******************************************************************/ double my_arr_min2(double anarr2[][], int arr_len1, int arr_len2) { int i, j; double mmin; mmin = anarr2[0][0]; for (i=0; i0) { draw_lens y -th[1] 0 0 0 0 0 0.2*scale; draw_default_rays(); DrawMirrorCentersSLIDERS(); ShowSpotsSLIDERS(show_spots); sbr; sps; basal_spot_size = c1*10000.0; message("Basal RMS spot size = %4.2f microns", basal_spot_size); } else message(" Invalid System "); if (gaclstat); set_preference(graphics_autoclear, on); stp outp on; stp noeb off; } //=================================================================================================== double three_mirINF_setup(double t1val,double t2val,double t3val,double d1val,double c1val,double m1val,double m2val) { double d3val,d2val,c2val,c3val; // Dependent parameters double cost1,sint1,cost2,sint2,cost3,sint3,xmax,xmin,ymax,ymin,x[5], y[5]; int ValidSys = 1; t1val *= dr; // Convert degrees to radians t2val *= dr; t3val *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); cost3 = cos(t3val); sint3 = sin(t3val); if ( (m1val==0) || (m2val==0) || (c1val==0) ) ValidSys = 0; else { c2val = -(cost2*(cost1 + 2*c1val*m2val*pow(cost1,2) - cost1*pow(cost3,2) + 2*c1val*m1val*pow(cost3,2))* pow(2*cost1*(1 + 2*c1val*cost1*d1val)*m2val*pow(cost2,2) + 2*(cost1 + 2*c1val*d1val)*m1val*pow(cost3,2),-1)); c3val = -(cost1*cost3*pow(m1val,-1)*pow(m2val,-1)*pow(sint3,2)*pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),2)* pow(2*c1val*pow(cost1,2)*pow(cost2,2)*pow(1 + 2*c1val*cost1*d1val,2)*pow(m2val,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + m1val*pow(cost3,2)*pow(cost1 + 2*c1val*d1val,2)*(2*c1val*m1val*pow(cost3,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + cost1*(1 + 2*c1val*cost1*d1val)*pow(sint2,2)*pow(sint3,2)) + cost1*(cost1 + 2*c1val*d1val)*(1 + 2*c1val*cost1*d1val)*m2val* (2*c1val*m1val*(1 + pow(cost2,2))*pow(cost3,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2)*pow(sint2,2)*pow(sint3,2)),-1))/2.; d2val = pow(cost1,-1)*(2*c1val*d1val*m1val + cost1*(m1val + m2val) + 2*c1val*d1val*m2val*pow(cost1,2))* (cost1*(1 + 2*c1val*cost1*d1val)*m2val*pow(cost2,2) + (cost1 + 2*c1val*d1val)*m1val*pow(cost3,2))*pow(sint3,-2)* pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),-1); d3val = -(m1val*m2val*pow(cost1,-1)*pow(sint3,-2)*(2*c1val*cost1*(1 + 2*c1val*cost1*d1val)*m2val*(-pow(cost1,2) + pow(cost2,2) - 2*c1val*cost1*d1val*pow(sint2,2)) + (cost1 + 2*c1val*d1val)*(2*c1val*m1val*pow(cost3,2)*(-pow(cost1,2) + pow(cost2,2) - 2*c1val*cost1*d1val*pow(sint2,2)) - cost1*(1 + 2*c1val*cost1*d1val)*pow(sint2,2)*pow(sint3,2)))* pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),-1)); } if (d2val<0) ValidSys = 0; if (ValidSys) { th 1 -d1val; th 2 d2val; th 3 -d3val; cv 1 c1val; cv 2 -c2val; cv 3 c3val; tla 1 t1val/dr; tla 2 t2val/dr; tla 3 t3val/dr; x[0]=0.0; y[0] = 0.0; x[1] = 0.0; y[1] = 0.0; x[2] = x[1] - d1val*cos(2*t1val); y[2] = y[1] - d1val*sin(2*t1val); x[3] = x[2] + d2val*cos(2*t1val+2*t2val); y[3] = y[2] + d2val*sin(2*t1val+2*t2val); x[4] = x[3] + d3val*cos(2*t1val+2*t2val+2*t3val); y[4] = y[3] + d3val*sin(2*t1val+2*t2val+2*t3val); xmax = max(x[0], max(x[1], max(x[2], max(x[3], x[4])))); xmin = min(x[0], min(x[1], min(x[2], min(x[3], x[4])))); ymax = max(y[0], max(y[1], max(y[2], max(y[3], y[4])))); ymin = min(y[0], min(y[1], min(y[2], min(y[3], y[4])))); return max(xmax-xmin, ymax-ymin); } else return(0); } //=================================================================================================== static cmd MirrorStartupINFSLIDERS() { stp outp off; stp noeb off; // wvg 1 .4 .7; wv_ 1 .5; uni cm; ast 1; drw imsnbr on; drl_aperstop set off; drl_firstsrf set 1; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrrays 0 set 3; drl_nbrrays 1 set 3; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 3; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; drl_hatchrefl set on; for (i=1;i 0) { graphwin_open(2); gclear(); set_object_point 0 0;// usr 0 0 0 0 0; pls ref sym 0 0; graphwin_open(3); gclear(); set_object_point 1 1;// usr 0 0 0 0 0; pls ref sym 0 0; graphwin_open(4); gclear(); set_object_point -1 1;// usr 0 0 0 0 0; pls ref sym 0 0; } else { graphwin_open(2); gclear(); graphwin_open(3); gclear(); graphwin_open(4); gclear(); } } /* Copyright 2000: Joseph M. Howard */ /****************************************************************************** *******************************************************************************/ //Prototypes cmd Concentric_3Sphere_sldrs(); cmd Concentric_3Sphere_setup(double r1val,double r2ratio,double r3ratio,double d0ratio,double hval,int PetzvalCorrection); static cmd C3Sphere_chng(int slider_id, double slider_value); /**************************************************************************************/ /**************************************************************************************/ cmd Concentric_3Sphere_sldrs() { double r1val, r2ratio, r3ratio, d0ratio, hval; double na, object_height, ent_pupil, fnumber; int show_spots, show_rays, PetzvalCorrection; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(graphics_labels, on); set_preference(graphics_axes, on); stp outp off; file_new Concentric3Spheres cus 4; lid "3 Concentric Spherical Mirrors"; des "Joe Howard"; uni mm; ast 1; drw 0 on; drw imsnbr on; drl_aperstop set off; drl_firstsrf set 0; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrfpts set 3; drl_nbrrays 0 set 3; drl_nbrrays 1 set 3; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 3; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; drl_hatchrefl set on; gla 2 refl_hatch; gla 3 refl_hatch; gla 4 refl_hatch; wv 2.0; opdw set off; //opd measured in lens units for (i=2;i<7;i++) gwc i; //remove all current graphics windows graphwin_open(1); graphwin_reset(); graphwin_sliderassign(1, real, drag, "Mirror 1 radius (r1)", "C3sphere_chng", 500, 5000, Za[20] = r1val = 800.0); graphwin_sliderassign(2, real, drag, "Mirror 2 (r2/r1)", "C3sphere_chng", .2001, .7999, Za[21] = r2ratio = 0.5); graphwin_sliderassign(3, real, drag, "Mirror 3 (r3/r1)", "C3sphere_chng", .3001, 1.699, Za[22] = r3ratio = 1.0); graphwin_sliderassign(4, real, drag, "Obj Distance (d0/r1)", "C3sphere_chng", .701, 1.301, Za[23] = d0ratio = 1.0); graphwin_sliderassign(5, real, drag, "Obj Decenter (h/r1)", "C3sphere_chng", 0.0, 1.0, Za[24] = hval = 100.0/r1val); graphwin_sliderassign(6, real, drag, "Obj Size", "C3sphere_chng", 1, 100, Za[25] = object_height = 50.0); graphwin_sliderassign(7, real, drag, "Pupil Distance (0=inf)", "C3sphere_chng", -10000.0, 10000.0, Za[26] = ent_pupil = 0.0); graphwin_sliderassign(8, real, drag, "Input f/# = 1/(2*NA)", "C3sphere_chng", 0.1, 30.0, Za[27] = fnumber = 24.0); graphwin_sliderassign(9, int, drag, "Show spots?", "C3sphere_chng", 0, 1, Za[28] = show_spots = 1); graphwin_sliderassign(10, int, drag, "Show ray plots?", "C3sphere_chng", 0, 1, Za[29] = show_rays = 1); graphwin_sliderassign(11, int, drag, "Correct Petzval Curv?", "C3sphere_chng", 0, 1, Za[30] = PetzvalCorrection = 1); graphwin_slidershow(); nao 1/(2*fnumber); obh object_height; Concentric_3Sphere_setup(r1val,r2ratio,r3ratio,d0ratio,hval,PetzvalCorrection); th 0 ent_pupil; th 1 th[1]-ent_pupil; ray_aiming_mode set tel; ap 2 hval*r1val+object_height+d0ratio*r1val/(2*fnumber); ap 4 hval*r1val+object_height+d0ratio*r1val/(2*fnumber); draw_lens; draw_default_rays(); graphwin_open(2); gclear(); gwe "rptg_spots"; graphwin_open(3); gclear(); gwe "rpt_ric ray 0 0 0 0 0 0 0 0:rpt_ric"; if (gaclstat) set_preference(graphics_autoclear, on); stp outp on; } /**************************************************************************************/ cmd Concentric_3Sphere_setup(double r1val,double r2ratio,double r3ratio,double d0ratio,double hval,int PetzvalCorrection) { double ObjectDistance,ImageDistance,r2val,r3val; // Dependent parameters r2val = r2ratio*r1val; if (PetzvalCorrection) r3val = 1/fabs(1/r1val-1/r2val);//Corrects Petzval Curvature else r3val = r3ratio*r1val; ObjectDistance = d0ratio*r1val; ImageDistance = (2.0-d0ratio)*r3val; th 1 ObjectDistance; th 2 -(r1val-r2val); th 3 (r3val-r2val); th 4 -ImageDistance; rd 2 -r1val; rd 3 -r2val; rd 4 -r3val; dcy 2 -hval*r1val; dcy imsnbr -hval*r1val; ap 2 fabs(hval)+obh*2; ap 4 fabs(hval)+obh*2; } //=================================================================================================== static cmd C3Sphere_chng(int slider_id, double slider_value) { double r1val, r2ratio, r3ratio, d0ratio, hval; double na, object_height, ent_pupil, fnumber, maxspotrad, PKVALopd, RMSopd, strehl; int show_spots, show_rays, PetzvalCorrection; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(output_text, off); stp noeb on; r1val = Za[20]; r2ratio = Za[21]; r3ratio = Za[22]; d0ratio = Za[23]; hval = Za[24]; object_height = Za[25]; ent_pupil = Za[26]; fnumber = Za[27]; show_spots = Za[28]; show_rays = Za[29]; PetzvalCorrection = Za[30]; if (slider_id == 1) Za[20] = r1val = slider_value; else if (slider_id == 2) Za[21] = r2ratio = slider_value; else if (slider_id == 3) Za[22] = r3ratio = slider_value; else if (slider_id == 4) Za[23] = d0ratio = slider_value; else if (slider_id == 5) Za[24] = hval = slider_value; else if (slider_id == 6) Za[25] = object_height = slider_value; else if (slider_id == 7) Za[26] = ent_pupil = slider_value; else if (slider_id == 8) Za[27] = fnumber = slider_value; else if (slider_id == 9) Za[28] = show_spots = slider_value; else if (slider_id == 10) Za[29] = show_rays = slider_value; else if (slider_id == 11) Za[30] = PetzvalCorrection = slider_value; // if r3 is changed, turn the Petzval correction off if (slider_id == 3) graphwin_sliderreset(11, i, 0, 1, Za[30] = PetzvalCorrection = 0); if (object_height > 1.0) { drl_nbrfpts set 3; drl_nbrrays 0 set 3; drl_nbrrays 1 set 3; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 3; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; } else drl_nbrfpts set 1; graphwin_open(1); gclear(); nao 1/(2*fnumber); obh object_height; Concentric_3Sphere_setup(r1val,r2ratio,r3ratio,d0ratio,hval,PetzvalCorrection); th 0 ent_pupil; th 1 th[1]-ent_pupil; if ( fabs(ent_pupil)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; autofocus; if (slider_id == 2) graphwin_sliderreset(3, r, .3001, 1.699, Za[22] = rd[4]/rd[2]); ap 2 hval*r1val+object_height+d0ratio*r1val/(2*fnumber); ap 4 hval*r1val+object_height+d0ratio*r1val/(2*fnumber); draw_lens; draw_default_rays(); maxspotrad = 0.0; PKVALopd = 0.0; RMSopd = 0.0; strehl = 1.0; for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { sop i j; twr; sps none 0.0; wvf; if(c1>maxspotrad) maxspotrad=c1; if(a2>PKVALopd) PKVALopd = a2; if(b2>RMSopd) RMSopd = b2; if(c21e10) //Object at Infinity { ImgFnum = SMimagefnum(); Ymag = Za[1]; Xmag = Za[2]; message("Maximum RMS Spot Radius over field: %4.2f microns Diffraction Limit = %4.2f microns\nBasal Image Fnum = %2.2f PM f/# = %2.2f" , maxspotrad*uni*1000.0, difflimit*uni*1000.0,ImgFnum, -rd[2]/(4*ap[2])); } else //Finite Conjugate { SMmagfnum(); Ymag = Za[1]; Xmag = Za[2]; message("Maximum RMS Spot Radius over field: %4.2f microns Diffraction Limit = %4.2f microns\nBasal Magnification: Y = %4.2f\tX = %4.2f" , maxspotrad*uni*1000.0, difflimit*uni*1000.0,Ymag,Xmag); } } //======================================================== //======================================================== cmd SMevaluatestuff() { double maxspotrad = 0.0; double difflimit; int i,j; install_error_handler(SMerrfuncevaluatestuff); sop 0 0; sbr; sps; difflimit = d1; for(i=0;i<2;i++) //x field point (only half needed due to symmetry) { for(j=-1;j<2;j++) //y field point { sbr; sop j i; sbr; sps none 0.0; if(c1>maxspotrad) maxspotrad=c1; } } Za[1] = maxspotrad; Za[2] = difflimit; //Diffraction limited spotradius from fby 0 fbx 0 delete_error_handler(); } //======================================================== //======================================================== cmd SMerrfuncevaluatestuff() { char outpstat = char_pref(outp); stp outp on; prt "Ray trace error encountered!"; if (!outpstat) stp outp off; Za[1] = Za[2] = Za[3] = 1e10; // set to bad system Errno = 0; //continue with the procedure } double SMsign( double dummy ) { if (dummy<0.0) return -1.0; else if (dummy>0.0) return 1.0; else return 0.0; } /* Copyright 2002: Joseph M. Howard */ //=================================================================================================================== //=================================================================================================================== // "Unobstructed afocal systems of spherical mirrors" by Joseph M. Howard //=================================================================================================================== //=================================================================================================================== // Prototypes cmd SM2afo_sldrs(); cmd SM2afo_chng(int slider_id, double slider_value); cmd SM2afo_example(int slider_id, double slider_value); // Callback for examples int SM_2afo(double d1val,double c1val,double c2val,double t1val,double t2val,double m1val,double m2val); int SM_2afoALT(double d1val,double c1val,double c2val,double t1val,double t2val,double m1val,double m2val); double SM_2afoFINDt2val(double theta1,double theta2,double m1val); static double SM2afoZero(double m1val, double theta1, double theta2); static double SM2afodZero(double theta1, double theta2); cmd SM3afo_sldrs(); cmd SM3afo_chng(int slider_id, double slider_value); cmd SM3afo_example(int slider_id, double slider_value); // Callback for examples int SM_3afo(double d1val,double d2val,double c1val,double c2val,double c3val,double t1val,double t2val,double t3val,double m1val,double m2val); cmd SMMessageAFO(); cmd SMMessageAFO(); // ======================================================================= // ======================================================================= cmd SM2afo_sldrs() { stp outp off; stp gacl off; stp noeb on; double d1val, c1val, c2val, Theta1, Theta2, m1val, m2val; double HFOV, EntPupLoc, EntranceBeamRadius; file_new SM2afo cus 3; lid "Afocal 2 spherical mirror system"; SMStartup(); drw 0 off; drw imsnbr off; afo afo; dlfd set 1000.0; //set final distance for image space rays dlnf set 1; //look at only one field point graphwin_sliderassign(20, real, drag, "Mirror 1-2 Sep (d1)", "SM2afo_chng", 100.0, 2000.0, Za[20] = d1val = 1000.0); graphwin_sliderassign(21, real, drag, "Theta 1", "SM2afo_chng", 1.0, 40.0, Za[21] = Theta1 = 5.0); graphwin_sliderassign(22, real, drag, "Theta 2", "SM2afo_chng", -40.0, 40.0, Za[22] = Theta2 = -10.0); graphwin_sliderassign(23, real, drag, "M1: Mag in Y-Z plane", "SM2afo_chng", 0.1, 10.0, Za[23] = m1val = 4.0); graphwin_sliderassign(40, real, drag, "HFOV", "SM2afo_chng", 0.01, 10.0, Za[40] = HFOV = 0.01); graphwin_sliderassign(41, real, drag, "Ent Pupil Loc", "SM2afo_chng", -2000.0, 2000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "SM2afo_chng", 1.0, 300.0, Za[42] = EntranceBeamRadius = 50.0); graphwin_slidershow(); SM2afo_chng(22, Za[22]); //SM2afo_example(70,1); prt "Unobstructed afocal systems of spherical mirrors"; prt " Joseph M. Howard "; prt " SPIE Annual Meeting (2002)."; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM2afo_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d1val, c1val, c2val, Theta1, Theta2, m1val, m2val; double HFOV, EntPupLoc, EntranceBeamRadius; double Spotsize, DiffLimit; d1val = Za[20]; Theta1 = Za[21]; Theta2 = Za[22]; m1val = Za[23]; m2val = Za[24]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = Theta1 = slider_value; else if (slider_id == 22) Za[22] = Theta2 = slider_value; else if (slider_id == 23) Za[23] = m1val = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; if (slider_id == 21 || slider_id == 22) // set m1val for a defined Theta1 and Theta2 { m1val = cos(Theta1*dr)*(sin(Theta2*dr)**2)/(cos(Theta2*dr)*(sin(Theta1*dr)**2)); graphwin_sliderreset(23, r, 0.1, 10.0, Za[23] = m1val); } else if (slider_id == 23) // reset Theta2 for a defined m1val { Theta2 = SM_2afoFINDt2val(Theta1, Theta2, m1val); graphwin_sliderreset(22, r, -40.0, 40.0, Za[22] = Theta2); } graphwin_open(1); gclear(); if (m1val < 0) { message("Invalid System, M1 must be > 0.0"); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System, M1 must be > 0."); } else if ( SM_2afo(d1val,&c1val,&c2val,Theta1,Theta2,&m1val,&m2val) ) //if ( SM_2afoalt2(d1val,&c1val,&c2val,Theta1,&Theta2,m1val,&m2val) ) //needs debugging { th 2 -d1val; th 3 d1val; // set image distance to equal mirror spacing cv 2 c1val; cv 3 -c2val; tla 2 Theta1; tla 3 Theta2; th 1 EntPupLoc; ebr EntranceBeamRadius; ang HFOV; if (HFOV>0.01) {dlnf set 3;} else dlnf set 1; draw_lens y -th[2]; draw_default_rays(); SMDrawCenters(); sbr; sps; SpotSize = c1; DiffLimit = d1; //m1val = cos(Theta1*dr)*(sin(Theta2*dr)**2)/(cos(Theta2*dr)*(sin(Theta1*dr)**2)); //m2val = m1val*cos(Theta2*dr)/cos(Theta1*dr); message("Basal: RMSSpotRad = %10.10f um, Diff Limit %10.10f um, Ratio = %4.2f\n m1val = %4.2f m2val = %4.2f Anamorphic Ratio: %5.5f" , SpotSize*uni*1000.0,DiffLimit*uni*1000.0,SpotSize/DiffLimit,m1val,m2val,m1val/m2val); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //======================================= //======================================= int SM_2afo(double d1val,double c1val,double c2val,double t1val,double t2val,double m1val,double m2val) { int ValidSys = 1; double cost1,sint1,cost2,sint2; t1val *= dr; // Convert degrees to radians t2val *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); c1val = -(cost1**2-cost2**2)/(2*cost1*(sint2**2)*d1val); c2val = (cost1**2-cost2**2)/(2*cost2*(sint1**2)*d1val); m1val = cost1*(sint2**2)/(cost2*(sint1**2)); m2val = m1val*cost2/cost1; return ValidSys; } double SM_2afoFINDt2val(double theta1,double theta2,double m1val) { double convergence = 3e-10, stepsize; int ValidSys = 1, i, maxiterations = 10; theta1 = theta1*dr; theta2 = theta2*dr; //starting point for t2 is current value if (ValidSys) { for (i = 0; i < maxiterations; i++) // FindZero Loop (Newton's Method) { stepsize = -SM2afoZero(m1val,theta1,theta2)/SM2afodZero(theta1,theta2); theta2 += stepsize; if ( sqrt(stepsize*stepsize) < convergence ) break; } // end FindZero Loop while (theta2 < -Pi/2) theta2 += Pi; while (theta2 > Pi/2) theta2 -= Pi; } return theta2/dr; //return value in degrees } static double SM2afoZero(double m1val, double theta1, double theta2) { return( Cot(theta1)*Csc(theta1)*Sin(theta2)*Tan(theta2) - m1val ); } static double SM2afodZero(double theta1, double theta2) { return( Cot(theta1)*Csc(theta1)*(Sin(theta2) + Sec(theta2)*Tan(theta2)) ); } // This is an attempt to constrain theta 2 by having m1val as an input. Needs debugging. int SM_2afoALT(double d1val,double c1val,double c2val,double t1val,double t2val,double m1val,double m2val) { int ValidSys = 1; double cost1,sint1,cost2; t1val *= dr; // Convert degrees to radians cost1 = cos(t1val); sint1 = sin(t1val); cost2 = (pow(cost1,-1)*(m1val*(-1 + pow(cost1,2)) - pow(4*pow(cost1,2) + pow(m1val - m1val*pow(cost1,2),2),0.5)))/2.; //cost2 = (pow(cost1,-1)*(m1val*(-1 + pow(cost1,2)) + pow(4*pow(cost1,2) + pow(m1val - m1val*pow(cost1,2),2),0.5)))/2.; //this solution mostly invalid for acos //cost2 = -(m1val*sint1**2+sqrt(4*cost1**2+m1val**2*sint1**4))/(2*cost1); //quadratic solution 1 //cost2 = -(m1val*sint1**2-sqrt(4*cost1**2+m1val**2*sint1**4))/(2*cost1); //quadratic solution 2 c1val = -(cost1**2-cost2**2)/(2*cost1*(-1+cost2**2)*d1val); c2val = (cost1**2-cost2**2)/(2*cost2*(sint1**2)*d1val); m2val = m1val*cost2/cost1; t2val = acos(cost2)/dr; //put t2val into degrees if (t2val>90.0) t2val-=180.0; return ValidSys; } cmd SM2afo_grid() { double theta1, theta2, m1val; int i,numdata=10; double FOM[numdata]; stp outp off; // int fileid = fopen("E:\OSLO62beta\private\PS3mirC_data",w); // if (fileid<0) abort("File open failure!!"); for (i = 1; i < 11; i++) { m1val = i; SM2afo_chng(23, Za[23]=i); //setup lens sbr; sps; FOM[i-1] = c1/d1; //ration of geometric spotsize to diffraction limit prt i FOM[i-1]; } // if (esc) {fclose(fileid); abort;} // fclose(fileid); stp outp on; } //=============================================================================== //=============================================================================== //=============================================================================== //=============================================================================== cmd SM3afo_sldrs() { stp outp off; stp gacl off; stp noeb on; double d1val, d2val, c1val, c2val, c3val, Theta1, Theta2, Theta3, m1val, m2val, mval; double HFOV, EntPupLoc, EntranceBeamRadius; file_new SM3afo cus 4; lid "Afocal 3 spherical mirror system"; SMStartup(); drw 0 off; drw imsnbr off; afo afo; dlfd set 1000.0; //set final distance for image space rays dlnf set 1; //look at only one field point graphwin_sliderassign(20, real, drag, "d1 (Mir 1-2 sep)", "SM3afo_chng", 100.0, 2000.0, Za[20] = d1val = 1000.0); graphwin_sliderassign(21, real, drag, "Theta 1", "SM3afo_chng", 1.0, 40.0, Za[21] = Theta1 = 4.0); graphwin_sliderassign(22, real, drag, "Theta 2", "SM3afo_chng", -40.0, 40.0, Za[22] = Theta2 = -6.0); graphwin_sliderassign(23, real, drag, "Theta 3", "SM3afo_chng", -40.0, 40.0, Za[23] = Theta3 = 12.0); graphwin_sliderassign(26, real, drag, "M1=M2 nonanamorph", "SM3afo_chng", -10.0, 10.0, Za[26] = mval = 4.0); graphwin_sliderassign(24, real, drag, "M1 (mag in plane)", "SM3afo_chng", -10.0, 10.0, Za[24] = m1val = 4.0); graphwin_sliderassign(25, real, drag, "M2 (mag out plane)", "SM3afo_chng", -10.0, 10.0, Za[25] = m2val = 4.0); graphwin_sliderassign(40, real, drag, "HFOV", "SM3afo_chng", 0.01, 10.0, Za[40] = HFOV = 0.01); graphwin_sliderassign(41, real, drag, "Ent Pupil Loc", "SM3afo_chng", -2000.0, 2000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "SM3afo_chng", 1.0, 300.0, Za[42] = EntranceBeamRadius = 50.0); graphwin_sliderassign(70, int, drag, "Examples", "SM3afo_example", 1, 10, 1); graphwin_slidershow(); SM3afo_chng(20, Za[20]); //SM3afo_example(70,1); prt "Unobstructed afocal systems of spherical mirrors"; prt " Joseph M. Howard "; prt " SPIE Annual Meeting (2002)."; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM3afo_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d1val, d2val, c1val, c2val, c3val, Theta1, Theta2, Theta3, m1val, m2val, mval; double HFOV, EntPupLoc, EntranceBeamRadius; double Spotsize, DiffLimit; int ValidSys; d1val = Za[20]; Theta1 = Za[21]; Theta2 = Za[22]; Theta3 = Za[23]; m1val = Za[24]; m2val = Za[25]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = Theta1 = slider_value; else if (slider_id == 22) Za[22] = Theta2 = slider_value; else if (slider_id == 23) Za[23] = Theta3 = slider_value; else if (slider_id == 24) Za[24] = m1val = slider_value; else if (slider_id == 25) Za[25] = m2val = slider_value; else if (slider_id == 26) Za[26] = mval = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; if (slider_id == 26) // set as non-anamorphic { graphwin_sliderreset(24, r, -10.0, 10.0, Za[24] = m1val = mval); graphwin_sliderreset(25, r, -10.0, 10.0, Za[25] = m2val = mval); } graphwin_open(1); gclear(); ValidSys = SM_3afo(d1val,&d2val,&c1val,&c2val,&c3val,Theta1,Theta2,Theta3,m1val,m2val); if ( ValidSys == 1 ) { th 2 -d1val; th 3 d2val; th 4 -d2val; // set image distance to equal final mirror spacing cv 2 c1val; cv 3 -c2val; cv 4 c3val; tla 2 Theta1; tla 3 Theta2; tla 4 Theta3; th 1 EntPupLoc; ebr EntranceBeamRadius; ang HFOV; if (HFOV>0.01) {dlnf set 3;} else dlnf set 1; draw_lens y -th[2]; draw_default_rays(); SMDrawCenters(); sbr; sps; SpotSize = c1; DiffLimit = d1; message("Basal: RMSSpotRad = %10.10f um, Diff Limit %10.10f um, Ratio = %4.2f\n m1val = %4.2f m2val = %4.2f Anamorphic Ratio: %5.5f" , SpotSize*uni*1000.0,DiffLimit*uni*1000.0,SpotSize/DiffLimit,m1val,m2val,m1val/m2val); } else if ( ValidSys == -1 ) { message("Unphysical System: d2 < 0"); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Unphysical System: d2 < 0"); } else { message("Invalid System: div by 0"); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System: div by 0"); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= // d1 t1 t2 t3 mval double SM3afoexamples[10][5]={ 1.0000e+03, 2.682241, 9.572183, -8.358330, 2.000000, 1.0000e+03, 2.720739, -25.270658, 6.841296, 2.000000, 1.0000e+03, 2.988079, 23.090572, -16.615427, 3.000000, 1.0000e+03, 2.321202, -39.973940, 8.853435, 3.000000, 1.0000e+03, 1.973974, 33.679135, 6.721113, 4.000000, 1.0000e+03, 2.083474, -39.840567, 8.997250, 4.000000, 1.0000e+03, 1.948837, 21.642303, -16.102609, 5.000000, 1.0000e+03, 1.848871, -39.865011, 9.212410, 6.000000, 1.0000e+03, 1.859485, -31.786547, 12.467070, 7.000000, 1.0000e+03, 1.741783, -3.276915, 11.734070, 8.000000 }; cmd SM3afo_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 100.0, 2000.0, Za[20] = SM3afoexamples[slider_value-1][0]); graphwin_sliderreset(21, r, 1.0, 40.0, Za[21] = SM3afoexamples[slider_value-1][1]); graphwin_sliderreset(22, r, -40.0, 40.0, Za[22] = SM3afoexamples[slider_value-1][2]); graphwin_sliderreset(23, r, -40.0, 40.0, Za[23] = SM3afoexamples[slider_value-1][3]); graphwin_sliderreset(26, r, 1.0, 10.0, Za[26] = SM3afoexamples[slider_value-1][4]); SM3afo_chng(26, Za[26]); //initiate change } //======================================= //======================================= int SM_3afo(double d1val,double d2val,double c1val,double c2val,double c3val,double t1val,double t2val,double t3val,double m1val,double m2val) { int ValidSys = 1; double c1D, c2D, c3D, d2D, c1N, c2N, c3N, d2N; double cost1,cost2,cost3; double NumZero = 1e-10; t1val *= dr; // Convert degrees to radians t2val *= dr; t3val *= dr; cost1 = cos(t1val); cost2 = cos(t2val); cost3 = cos(t3val); // Robust method, checks for all division by zero failure modes c1D = 2*d1val*(cost3*m1val - cost1*m2val); c2D = 2*d1val*(cost3*m1val*(1 - m2val*(-1 + pow(cost1,2))*(-1 + pow(cost2,2))) - cost1*m2val*pow(cost2,2) + cost1*m2val*pow(cost2,2)*pow(cost3,2) - m1val*pow(cost3,3)); c3D = 2*d1val*(cost3*m1val - cost1*m2val)*(cost3*m1val*(-1 + m2val*(-1 + pow(cost1,2))*(-1 + pow(cost2,2))) + cost1*m2val*pow(cost2,2) - cost1*m2val*pow(cost2,2)*pow(cost3,2) + m1val*pow(cost3,3)); d2D = m1val*m2val*(1 + cost1*cost3*m1val - m2val - pow(cost3,2))* (-(m2val*pow(cost1,3)) - cost3*m1val*pow(cost2,2) + cost3*m1val*pow(cost1,2)*pow(cost2,2) + cost1*(-1 + m2val - pow(cost2,2)*(-1 + pow(cost3,2)) + pow(cost3,2))); if ( fabs(c1D)< NumZero || fabs(c2D)< NumZero || fabs(c3D)< NumZero || fabs(d2D)< NumZero ) return ValidSys = 0; //prevents division by zero problems else { c1N = -1 - cost1*cost3*m1val + m2val + pow(cost3,2); c2N = cost2*(cost3*m1val - cost1*m2val)*(-1 - cost1*cost3*m1val + m2val + pow(cost3,2)); c3N = m1val*m2val*(1 + cost1*cost3*m1val - m2val - pow(cost3,2))* (-(m2val*pow(cost1,3)) - cost3*m1val*pow(cost2,2) + cost3*m1val*pow(cost1,2)*pow(cost2,2) + cost1*(-1 + m2val - pow(cost2,2)*(-1 + pow(cost3,2)) + pow(cost3,2))); d2N = -(d1val*(-(cost1*cost3*m2val) + m1val*(1 + m2val*(-1 + pow(cost1,2))))* (cost3*m1val*(-1 + m2val*(-1 + pow(cost1,2))*(-1 + pow(cost2,2))) + cost1*m2val*pow(cost2,2) - cost1*m2val*pow(cost2,2)*pow(cost3,2) + m1val*pow(cost3,3))); c1val = c1N/c1D; c2val = c2N/c2D; c3val = c3N/c3D; d2val = d2N/d2D; } /* // Less robust, but provides faster calculations if (d1val == 0 || (m1val == m2val && t1val == t3val)) return ValidSys=0; c1val = -((-1 - cost1*cost3*m1val + m2val + pow(cost3,2))*pow(-2*cost3*d1val*m1val + 2*cost1*d1val*m2val,-1)); c2val = -(cost2*(cost3*m1val - cost1*m2val)*(-1 - cost1*cost3*m1val + m2val + pow(cost3,2))*pow(d1val,-1)* pow(cost3*m1val*(-1 + m2val*(-1 + pow(cost1,2))*(-1 + pow(cost2,2))) + cost1*m2val*pow(cost2,2) - cost1*m2val*pow(cost2,2)*pow(cost3,2) + m1val*pow(cost3,3),-1))/2.; c3val = (m1val*m2val*(m2val*pow(cost1,3) + cost3*m1val*pow(cost2,2) - cost3*m1val*pow(cost1,2)*pow(cost2,2) + cost1*(1 - m2val + pow(cost2,2)*(-1 + pow(cost3,2)) - pow(cost3,2)))* (-1 - cost1*cost3*m1val + m2val + pow(cost3,2))*pow(d1val,-1)* pow(cost1*cost3*m1val*m2val*(1 + m2val*(-1 + pow(cost1,2)) + (1 + m2val - m2val*pow(cost1,2))*pow(cost2,2)) - cost1*m1val*m2val*(1 + pow(cost2,2))*pow(cost3,3) + pow(cost3,4)*pow(m1val,2) - pow(cost1,2)*pow(cost2,2)*pow(m2val,2) + pow(cost3,2)*((-1 + m2val*(-1 + pow(cost1,2))*(-1 + pow(cost2,2)))*pow(m1val,2) + pow(cost1,2)*pow(cost2,2)*pow(m2val,2)),-1))/2.; d2val = d1val*pow(m1val,-1)*pow(m2val,-1)*(cost1*m1val*m2val*(-1 + m2val - m2val*pow(cost1,2))*pow(cost2,2) + cost1*m1val*m2val*(-1 + m2val - m2val*pow(cost1,2) + (1 + 2*m2val*(-1 + pow(cost1,2)))*pow(cost2,2))* pow(cost3,2) + cost1*m1val*m2val*pow(cost3,4) - pow(cost3,3)*((1 + m2val*(-1 + pow(cost1,2)))*pow(m1val,2) + pow(cost1,2)*pow(cost2,2)*pow(m2val,2)) + cost3*(pow(cost1,2)*pow(cost2,2)*pow(m2val,2) + pow(m1val,2)*(1 - m2val*(-1 + pow(cost1,2))*(-2 + pow(cost2,2)) - (-1 + pow(cost2,2))*pow(m2val,2)*pow(-1 + pow(cost1,2),2))))* pow(m2val*pow(cost1,3) + cost3*m1val*pow(cost2,2) - cost3*m1val*pow(cost1,2)*pow(cost2,2) + cost1*(1 - m2val + pow(cost2,2)*(-1 + pow(cost3,2)) - pow(cost3,2)),-1)* pow(-1 - cost1*cost3*m1val + m2val + pow(cost3,2),-1); */ if (d2val<0) ValidSys = -1; //unphysical system return ValidSys; } /****************************************************************************** *******************************************************************************/ //Prototypes cmd RS2inf_sldrs(); int RS2inf_setup(double d1val,double d2val,double fval); cmd RS2inf_chng(int slider_id, double slider_value); cmd EvaluateStuff(); static cmd DrawMirrorCentersSLIDERS(); cmd SMmessage(); int RS2mirINF_CV(double fval,double d1val,double d2val,double c1val,double c2val); int RS2mirINF_CC(double fval,double d1val,double d2val,double c1val,double c2val,double k1val,double k2val,int class); /**************************************************************************************/ /**************************************************************************************/ cmd slowjoe() {RS2inf_sldrs;} cmd RS2inf_sldrs() { double d1val, d2val, AxisDecenter, AxisTilt, EntPupLoc, fnum, EntranceBeamRadius, HFOV; int Class; prt "Rotationally Symmetric 2-mirror telescopes."; prt " Class 1: Cassegrain or Gregorian (Spherical aberration corrected)"; prt " Class 2: Ritchey-Chretien (3rd order spherical and coma corrected)"; prt " Class 3: Dall-Kirkham (3rd order spherical corrected)"; prt " Class 4: Inverse Dall-Kirkham (3rd order spherical corrected)"; prt " Class 5: Spherical Mirrors (First-order parameters set)"; stp outp off; stp gacl off; stp noeb on; file_new RS2mirINF cus 3; wv_ 1 .5; uni mm; des "JMH"; drl_firstsrf set 1; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrrays 0 set 4; drl_nbrrays 1 set 4; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 4; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; drl_hatchrefl set on; drw 0 off; ast 1; gla 2 reflect; gla 3 reflect; drw imsnbr on; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mirror Separation (d1)", "RS2inf_chng", 100.0, 10000.0, Za[20] = d1val = 2000.0); graphwin_sliderassign(21, real, drag, "Image Distance (d2)", "RS2inf_chng", 100.0, 10000.0, Za[21] = d2val = 2500.0); graphwin_sliderassign(22, real, drag, "Axis Decenter", "RS2inf_chng", -3000.0, 3000.0, Za[22] = AxisDecenter = 0.0); graphwin_sliderassign(23, real, drag, "Axis Tilt", "RS2inf_chng", -45.0, 45.0, Za[23] = AxisTilt = 0.0); graphwin_sliderassign(24, real, drag, "F-number", "RS2inf_chng", -30.0, 30.0, Za[24] = fnum = 20.0); graphwin_sliderassign(40, real, drag, "HFOV (arc minutes)", "RS2inf_chng", 1.0, 100, Za[40] = HFOV = 5.0); graphwin_sliderassign(41, real, drag, "Ent Pupil Loc", "RS2inf_chng", -5000.0, 5000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "RS2inf_chng", 100.0, 5000.0, Za[42] = EntranceBeamRadius = 500.0); graphwin_sliderassign(50, int, drag, "Telescope Class", "RS2inf_chng", 1, 5, 1); za[50] = 1; graphwin_slidershow(); ray_aiming_mode set crr; RS2inf_chng(20, Za[20]); stp outp on; stp gacl on; stp noeb off; } //=================================================================================================== //=================================================================================================== cmd RS2inf_chng(int slider_id, double slider_value) { double d1val, d2val, AxisDecenter, AxisTilt, EntPupLoc; double c1val, c2val, k1val, k2val, fval; double fnum, EntranceBeamRadius, HFOV; double maxspotrad = 0.0, PKVALopd = 0.0, RMSopd = 0.0, strehl = 1.0; double PetzvalRad, SiedelDistortion; int Class; stp outp off; stp gacl off; stp noeb on; d1val = Za[20]; d2val = Za[21]; AxisDecenter = Za[22]; AxisTilt = Za[23]; fnum = Za[24]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; Class = Za[50]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = d2val = slider_value; else if (slider_id == 22) Za[22] = AxisDecenter = slider_value; else if (slider_id == 23) Za[23] = AxisTilt = slider_value; else if (slider_id == 24) Za[24] = fnum = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; else if (slider_id == 50) Za[50] = Class = slider_value; graphwin_open(1); gclear(); ang HFOV/60; ebr EntranceBeamRadius; th 1 -EntPupLoc; tla 2 AxisTilt; dcy 2 AxisDecenter; fval = fnum*2*EntranceBeamRadius; if ( RS2mirINF_CV(fval,d1val,d2val,&c1val,&c2val) ) { RS2mirINF_CC(fval,d1val,d2val,c1val,c2val,&k1val,&k2val,Class); th 2 -d1val; th 3 d2val; cv 2 c1val; cv 3 c2val; cc 2 k1val; cc 3 k2val; if (EntPupLoc>0.0) { drw ast off; draw_lens y -1.25*th[2]; } else { //drw ast on; draw_lens y -1.25*th[2];} draw_default_rays(); DrawMirrorCentersSLIDERS(); SMmessage(); } else message(" Invalid System "); stp outp on; stp gacl on; stp noeb off; } //=================================================================================================== //=================================================================================================== //Setup routines int RS2mirINF_CV(double fval,double d1val,double d2val,double c1val,double c2val) { int ValidSys = 1; if ( (fval==0) || (d1val==0) || (d2val==0) || (d1val + d2val - fval==0) ) ValidSys = 0; else { c1val = (d2val - fval)/(2.*d1val*fval); c2val = (d1val + d2val - fval)/(2.*d1val*d2val); } return ValidSys; } int RS2mirINF_CC(double fval,double d1val,double d2val,double c1val,double c2val,double k1val,double k2val,int class) { int ValidSys = 1; if (class==1) //Cassagrain { k1val = pow(fval-d2val,3)*(8*c1val**-3)/(64*(d1val**3)*(fval**3)); k2val = (fval-d1val-d2val)*(fval+d1val-d2val)**2*(8*c2val**-3)/(64*(d1val**3)*(d2val**3)); lid "Cassegrain/Gregorian Telescope"; } else if (class==2) //Ritchey-Chretien { k1val = pow(d2val - fval,-3)*(2*d2val*pow(d1val,2) - pow(d2val - fval,3)); k2val = ((d2val + fval)*pow(d1val,2) - pow(d1val,3) + d1val*pow(d2val - fval,2) - pow(d2val - fval,3))* pow(d1val + d2val - fval,-3); lid "Ritchey-Chretien Telescope"; } else if (class==3) //Dall-Kirkham { k1val = (fval*(fval-d2val)**3-d2val*(fval-d1val-d2val)*(fval+d1val-d2val)**2)*(8*c1val**-3)/(64*d1val**3*fval**4); k2val = 0.0; lid "Dall-Kirkham Telescope"; } else if (class==4) //Inverse Dall-Kirkham { k1val = 0.0; k2val = (fval*(d2val-fval)**3+d2val*(fval-d1val-d2val)*(fval+d1val-d2val)**2)*(8*c2val**-3)/(64*d1val**3*d2val**4); lid "Inverse Dall-Kirkham Telescope"; } else if (class==5) //Spherical Mirrors { k1val = 0.0; k2val = 0.0; lid "Spherical Mirror Telescope"; } return(ValidSys); } //======================================== //======================================== // Copyright 2001: Joseph M. Howard //======================================== //======================================== //======================================== // Prototypes cmd RS3inf_sldrs(); cmd RS3inf_chng(int slider_id, double slider_value); double RS3inf_setup(double d1val, double d2val, double d3val, double Pfnum, double OTAfnum, double EntranceBeamRadius); //======================================== cmd RS3inf_sldrs() { double d1val, d2val, d3val, Pfnum, OTAfnum, EntranceBeamRadius, HFOV, AxisTilt; double ImageDistance, FMlocation, FMtilt; int Pos_Neg_f, FMstop, ImageOpt, ConicOpt, OptImgCv; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(graphics_labels, on); set_preference(graphics_axes, on); stp outp off; file_new Tel3conics cus 5; gcs 1; lid "3 Conic Mirror Telescope"; des "JMH"; uni mm; drw imsnbr on; drl_aperstop set off; drl_firstsrf set 1; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrrays 0 set 4; drl_nbrrays 1 set 4; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 4; drl_yfieldpt 2 set -1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_hatchrefl set on; ast 1; gla 2 reflect; gla 3 reflect; gla 4 reflect; gla 5 refl_hatch; //Fold mirror rco 5 5; //setup a coordinate return for Fold mirror wv 1.0; opdw set off; //opd measured in lens units graphwin_sliderassign(20, real, drag, "Pri -> Sec (d1)", "RS3inf_chng", 5500.0, 7500.0, Za[20] = d1val = 6765.5047855731927); graphwin_sliderassign(21, real, drag, "Sec -> Tert (d2)", "RS3inf_chng", 6000.0, 8000.0, Za[21] = d2val = 7556.5217391304341); graphwin_sliderassign(22, real, drag, "Image Dist (d3)", "RS3inf_chng", 3500.0, 5500.0, Za[22] = d3val = 4704.1321656352466); graphwin_sliderassign(23, real, drag, "Primary f/#", "RS3inf_chng", .85, 2.0, Za[23] = Pfnum = 1.13636363435); graphwin_sliderassign(24, real, drag, "Telescope f/#", "RS3inf_chng", -25, -15, Za[24] = OTAfnum = -20.0); graphwin_sliderassign(25, real, drag, "Ent Beam Rad (mm)", "RS3inf_chng", 3000.0, 4000.0, Za[25] = EntranceBeamRadius = 6600.0/2.0); graphwin_sliderassign(26, real, drag, "HFOV (arc minutes)", "RS3inf_chng", 1, 8, Za[26] = HFOV = 3.5); graphwin_sliderassign(27, real, drag, "Axis Tilt (degrees)", "RS3inf_chng", -1.0, 1.0, Za[27] = AxisTilt = -.2); graphwin_sliderassign(31, real, drag, "FM Location/d3", "RS3inf_chng", 0.0, 1.0, Za[31] = FMlocation = 0.362340); graphwin_sliderassign(32, real, drag, "FM tilt", "RS3inf_chng", -5.0, 5.0, Za[32] = FMtilt = 2.0); graphwin_slidershow(); RS3inf_chng(20, Za[20]); prt "==============================="; prt "3 Mirror Telescope Design tool"; prt "Written by Joseph M. Howard"; prt "==============================="; prt; prt "Three mirror telescopes are analytically corrected"; prt " for O(3) Spherical, Coma, and Astigmatism."; } //================================================================================= //================================================================================= cmd RS3inf_chng(int slider_id, double slider_value) { double d1val, d2val, d3val, Pfnum, OTAfnum, EntranceBeamRadius, HFOV, AxisTilt; double ImageDistance, FMlocation, FMtilt; double RMSopd; double stoplocation, focal_length, FBY, FBX, Zsm, Ztm, ZFM, Zimage, ExitPupDist; double dummy; int FMstop, ImageOpt, ConicOpt, OptImgCv; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(output_text, off); stp noeb on; d1val = Za[20]; d2val = Za[21]; d3val = Za[22]; Pfnum = Za[23]; OTAfnum = Za[24]; EntranceBeamRadius = Za[25]; HFOV = Za[26]; AxisTilt = Za[27]; FMlocation = Za[31]; FMtilt = Za[32]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = d2val = slider_value; else if (slider_id == 22) Za[22] = d3val = slider_value; else if (slider_id == 23) Za[23] = Pfnum = slider_value; else if (slider_id == 24) Za[24] = OTAfnum = slider_value; else if (slider_id == 25) Za[25] = EntranceBeamRadius = slider_value; else if (slider_id == 26) Za[26] = HFOV = slider_value; else if (slider_id == 27) Za[27] = AxisTilt = slider_value; else if (slider_id == 31) Za[31] = FMlocation = slider_value; else if (slider_id == 32) Za[32] = FMtilt = slider_value; focal_length = OTAfnum*EntranceBeamRadius*2; ebr EntranceBeamRadius; ang HFOV/60; tla 1 AxisTilt; tla imsnbr-1 FMtilt; if ( ImageDistance = RS3inf_setup(d1val, d2val, d3val, Pfnum, OTAfnum, EntranceBeamRadius) ) // if ValidSys { th 4 -FMlocation*ImageDistance; th 5 ImageDistance*(1.0-FMlocation); //draw system gclear(); draw_lens y -th[2]/2; draw_default_rays(); } else { //setup fails gclear(); message(" Invalid System "); } if (gaclstat); set_preference(graphics_autoclear, on); stp outp on; stp noeb off; } double RS3inf_setup(double d1val, double d2val, double d3val, double Pfnum, double OTAfnum, double EntranceBeamRadius) { double r1val,r2val,r3val,k1val,k2val,k3val; // Dependent parameters double fval, m2val, m3val, p2val, p3val; double clear_aperture; int ValidSys = 1; if ( (d2val<=0) || (OTAfnum==0) )//|| (CassFocus==0) )) ValidSys = 0; else { clear_aperture = 2*EntranceBeamRadius; fval = OTAfnum*clear_aperture; r1val = 2*clear_aperture*Pfnum; r2val = (2*d2val*fval*(2*d1val - r1val))/(2*d1val*fval + 2*d2val*fval + (d3val - fval)*r1val); r3val = (2*d2val*d3val*r1val)/(2*d1val*fval + (d2val + d3val - fval)*r1val); m2val = (2*d2val*d3val - d2val*r3val - d3val*r3val + fval*r3val)*pow(d1val,-1)*pow(2*d3val - r3val,-1); m3val = (2*d3val - r3val)*pow(r3val,-1); p2val = (2*d2val*d3val - d2val*r3val - d3val*r3val)*pow(2*d1val*d3val - d1val*r3val + fval*r3val,-1); p3val = (2*d1val*d3val - d1val*r3val + fval*r3val)*pow(2*d2val*fval + d1val*r3val - fval*r3val,-1); k3val = (m3val - p3val)*pow(1 + m3val,-2)*(-(m3val*(-1 + p2val)*pow(1 + m2val,2)*pow(m2val - p2val,-1)* ((-1 + m2val)*pow(1 + m2val,-1) - (-1 + p2val)*pow(1 + p2val,-1))) - 2*m2val*m3val*(m2val*pow(1 + m2val,-1) - 2*p2val*pow(1 + p2val,-1)) - (-1 + p3val)*pow(1 + m3val,2)*pow(m3val - p3val,-1)* ((-1 + m3val)*pow(1 + m2val,-1)*pow(m3val,-1) - (-1 + p3val)*pow(1 + p2val,-1)*pow(p3val,-1)) )*pow(1 + p3val,-1)*pow((1 + m3val)*pow(1 + m2val,-1)*pow(m3val,-1) - (1 + p3val)*pow(1 + p2val,-1)*pow(p3val,-1),-1); k2val = (m2val - p2val)*pow(1 + m2val,-2)*pow(m3val,-1)*pow(1 + p2val,-1)* (-2*m3val*pow(m2val,2)*pow(1 + m2val,-1) - (-1 + m2val)*(1 + m2val)*m3val*(-1 + p2val)*pow(m2val - p2val,-1) - (1 + p3val)*pow(1 + m2val,-1)*pow(m3val,-1)*pow(1 + m3val,3)*pow(m3val - p3val,-1)* (k3val + (-1 + m3val)*(-1 + p3val)*pow(1 + m3val,-1)*pow(1 + p3val,-1))); k1val = pow(m2val,-3)*pow(m3val,-3)*(-(pow(m2val,3)*pow(m3val,3)) - p2val*(k2val + pow(-1 + m2val,2)*pow(1 + m2val,-2))*pow(1 + m2val,4)*pow(m3val,3)* pow(m2val - p2val,-1) - p2val*p3val*(k3val + pow(-1 + m3val,2)*pow(1 + m3val,-2))* pow(1 + m3val,4)*pow(m3val - p3val,-1)); } if (ValidSys) { th 2 -d1val; th 3 d2val; th 4 -d3val; rd 2 -r1val; rd 3 r2val; rd 4 -r3val; cc 2 k1val; cc 3 k2val; cc 4 k3val; return d3val; //Image Distance } else return(ValidSys); //else return 0 } /****************************************************************************** *******************************************************************************/ //Prototypes cmd RS4inf_sldrs(); cmd RS4INF_chng(int slider_id, double slider_value); int RS4INF_setup(double m3val,double deltad2,double m4val,double obs_ratio,double Pfnum,double OTAfnum); cmd fspots(); /**************************************************************************************/ /**************************************************************************************/ cmd RS4inf_sldrs() { double m3val, deltad2, m4val, obs_ratio, Pfnum, OTAfnum, HFOV, EntranceBeamRadius, FieldTilt; int Pos_Neg_f, show_spots, show_rays, ImageOpt, ConicOpt; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(graphics_labels, on); set_preference(graphics_axes, on); stp outp off; file_new Tel4conics cus 5; lid "4-mirror conic telescope"; des "JMH"; uni mm; ast 1; drw imsnbr on; drl_aperstop set off; drl_firstsrf set 1; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrfpts set 3; drl_nbrrays 0 set 4; drl_nbrrays 1 set 4; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 4; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; drl_hatchrefl set on; gla 2 reflect; gla 3 reflect; gla 4 reflect; gla 5 reflect; wv 2; opdw set off; //opd measured in lens units m3val = -1.7; m4val = 0.465; deltad2 = -1800.0; obs_ratio = 0.045; Pfnum = 1.25; OTAfnum = 24.0; HFOV = 2.0; EntranceBeamRadius = 4000.0; FieldTilt = -0.08; Pos_Neg_f = 1.0; Za[20] = m3val; Za[21] = deltad2; Za[22] = m4val; Za[23] = obs_ratio; Za[24] = Pfnum; Za[25] = OTAfnum; Za[26] = HFOV; Za[27] = EntranceBeamRadius; Za[28] = FieldTilt; Za[29] = Pos_Neg_f; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(1, real, drag, "Mirror 3 mag. (m3)", "RS4INF_chng", -2.001, 2.001, m3val); graphwin_sliderassign(2, real, drag, "Tertiary position", "RS4INF_chng", -3001, 3001, deltad2); graphwin_sliderassign(3, real, drag, "Mirror 4 mag. (m4)", "RS4INF_chng", -4.001, 4.001, m4val); graphwin_sliderassign(4, real, drag, "Linear obs ratio", "RS4INF_chng", -.201, .201, obs_ratio); graphwin_sliderassign(5, real, drag, "Primary f/#", "RS4INF_chng", .5, 5, Pfnum); graphwin_sliderassign(6, real, drag, "OTA f/#", "RS4INF_chng", 10, 30, OTAfnum); graphwin_sliderassign(7, real, drag, "HFOV (arc mins)", "RS4INF_chng", 1, 10, HFOV); graphwin_sliderassign(8, real, drag, "EBR (mm)", "RS4INF_chng", 3000, 5000.0, EntranceBeamRadius ); graphwin_sliderassign(9, real, drag, "Field Tilt (deg)", "RS4INF_chng", -1.0, 1.0, FieldTilt); graphwin_sliderassign(10, int, drag, "Sign of f", "RS4INF_chng", -1, 1, Pos_Neg_f); graphwin_slidershow(); RS4INF_chng(1,m3val); if (gaclstat) set_preference(graphics_autoclear, on); stp outp on; prt "==============================="; prt "4 Mirror Telescope Design tool"; prt "Written by Joseph M. Howard"; prt "==============================="; prt; prt "Four mirror telescopes are analytically corrected"; prt "for all O(3) image aberrations:"; prt "Spherical, Coma, Astigmatism, Petzval Cv, and Distortion."; } //=================================================================================================== cmd RS4INF_chng(int slider_id, double slider_value) { double m3val, deltad2, m4val, obs_ratio, Pfnum, OTAfnum, HFOV, EntranceBeamRadius, FieldTilt; int Pos_Neg_f, show_spots, show_rays, ImageOpt, ConicOpt; double maxspotrad, PKVALopd, RMSopd, strehl, petzval, exitpupildist; char gaclstat; gaclstat = char_pref(graphics_autoclear); set_preference(graphics_autoclear, off); set_preference(output_text, off); stp noeb on; m3val = Za[20]; deltad2 = Za[21]; m4val = Za[22]; obs_ratio = Za[23]; Pfnum = Za[24]; OTAfnum = Za[25]; HFOV = Za[26]; EntranceBeamRadius = Za[27]; FieldTilt = Za[28]; Pos_Neg_f = Za[29]; if (slider_id == 1) m3val = slider_value; else if (slider_id == 2) deltad2 = slider_value; else if (slider_id == 3) m4val = slider_value; else if (slider_id == 4) obs_ratio = slider_value; else if (slider_id == 5) Pfnum = slider_value; else if (slider_id == 6) OTAfnum = slider_value; else if (slider_id == 7) HFOV = slider_value; else if (slider_id == 8) EntranceBeamRadius = slider_value; else if (slider_id == 9) tla 1 FieldTilt=slider_value; else if (slider_id == 10) { if (slider_value != 0) Pos_Neg_f = slider_value; } Za[20] = m3val; Za[21] = deltad2; Za[22] = m4val; Za[23] = obs_ratio; Za[24] = Pfnum; Za[25] = OTAfnum; Za[26] = HFOV; Za[27] = EntranceBeamRadius; Za[28] = FieldTilt; Za[29] = Pos_Neg_f; graphwin_open(1); gclear(); tla 1 FieldTilt; ang HFOV/60; ebr EntranceBeamRadius; if ( RS4INF_setup(m3val,deltad2,m4val,obs_ratio,Pfnum,OTAfnum) ) { th imsnbr 0.0; //reset image parameters cv imsnbr 0.0; tla imsnbr 0.0; maxspotrad = 0.0; PKVALopd = 0.0; RMSopd = 0.0; strehl = 1.0; for(i=-1;i<2;i++) { for(j=-1;j<2;j++) { sop i j; twr; sps none 0.0; wvf; if(c1>maxspotrad) maxspotrad=c1; if(a2>PKVALopd) PKVALopd = a2; if(b2>RMSopd) RMSopd = b2; if(c20 || th[3]<0 || th[4]>0) message("System is Unphysical!!!\t\tMax: RMS SpotRad (um) = %6.3f\tPkVal OPD (nm) = %6.3f\tRMS OPD = %6.3f \nMin Strehl = %2.3f\tPetzRad = %3.4f\t\tPetzRad-ImgDist = %3.4f" , maxspotrad*1000.0,PKVALopd*1000000.0,RMSopd*1000000.0,strehl,petzval,rd[imsnbr]+th[imsnbr-1]); } else message(" Invalid System "); if (gaclstat); set_preference(graphics_autoclear, on); stp outp on; stp noeb off; } /**************************************************************************************/ int RS4INF_setup(double m3val,double deltad2,double m4val,double obs_ratio,double Pfnum,double OTAfnum) { double d1val,d2val,d3val,d4val,r1val,r2val,r3val,r4val,k1val,k2val,k3val,k4val; // Dependent parameters double epsval, Pos_Neg_f, clear_aperture, m2val, fval, p2val, p3val, p4val; // Alternate parameters double coef0, coef1, coef2; int soln,ValidSys = 1; if ( (m3val==0) || (m4val==0) || (obs_ratio==0)) ValidSys = 0; else { Pos_Neg_f = Za[29]; clear_aperture = 2*Za[27]; epsval = -obs_ratio; //OTA F-number determines fval fval = Pos_Neg_f*OTAfnum*clear_aperture; //Primary F-number determines r1val r1val = 2*clear_aperture*Pfnum; //choose r1 instead of m2 m2val = 2*fval*pow(m3val,-1)*pow(m4val,-1)*pow(r1val,-1); //constrain p3val such that tertiary mirror (d2val) is located at primary +/- deltad2 p3val = (1 + epsval + m2val)*m3val*(-((1 + epsval)*fval) + m2val*(epsval*fval + deltad2*m3val*m4val))* pow((1 + epsval)*m2val*((-1 + epsval)*fval + deltad2*m3val*m4val) - fval*pow(1 + epsval,2) + m3val*(-(epsval*fval) + deltad2*m4val)*pow(m2val,2),-1); //epsval replaces p2val (obstruction ratio) p2val = m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1); // zero petzval with p4val p4val = -(m4val*pow(-1 - m4val*p3val + m3val*m4val* (1 - m2val*p3val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*p3val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))),-1)); r2val = 2*epsval*fval*pow(1 + m2val,-1)*pow(m3val,-1)*pow(m4val,-1); r3val = 2*epsval*fval*m2val*p3val*pow(1 + epsval + m2val,-1)*pow(m4val,-1)*pow(m3val - p3val,-1); r4val = 2*epsval*fval*m2val*p3val*p4val*pow(1 + epsval + m2val,-1)*pow(m4val - p4val,-1); d1val = (1 + epsval)*fval*pow(m2val,-1)*pow(m3val,-1)*pow(m4val,-1); d2val = epsval*fval*(-((1 + epsval)*p3val) + m3val*(1 + epsval + m2val*(1 + p3val)))*pow(1 + epsval + m2val,-1)* pow(m3val,-1)*pow(m4val,-1)*pow(m3val - p3val,-1); d3val = epsval*fval*m2val*p3val*(-((1 + p3val)*p4val) + m4val*(1 - p3val*p4val + m3val*(1 + p4val)))* pow(1 + epsval + m2val,-1)*pow(m4val,-1)*pow(m3val - p3val,-1)*pow(m4val - p4val,-1); d4val = epsval*fval*m2val*(1 + m4val)*p3val*p4val*pow(1 + epsval + m2val,-1)*pow(m4val - p4val,-1); k1val = -(pow(m2val,-3)*pow(m3val,-3)*pow(m4val,-3)*pow(1 + p3val,-1)*pow(p4val,-1)*pow(1 + p4val,-1)* ((1 + p3val)*p4val*(1 + p4val)*pow(m2val,3)*pow(m3val,3)*pow(m4val,3)* (1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + 2*m2val*p3val*p4val*(-((1 + p3val)*p4val) - m4val*(-1 + (2 + p3val)*p4val) + 2*pow(m4val,2))* pow(1 + (1 + m2val)*pow(epsval,-1),-1)*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + 2*m2val*pow(m3val,2)*pow(m4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1)* (-1 + 2*p3val*pow(p4val,2) + pow(m2val,2)*pow(p3val,2)*pow(p4val,2)* pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 2*m2val*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m4val*(-1 + 2*p4val + pow(p4val,2)* (2 + 2*p3val + m2val*pow(p3val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1)* (-2 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) + m2val*(-1 + 2*p3val*pow(p4val,2) + pow(p3val,2)*pow(p4val,2)*(2 + 3*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + m4val*(-1 + 2*p4val + pow(p4val,2)* (2 + 2*p3val + pow(p3val,2)* (2 + 3*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))))) + 2*m2val*m3val*m4val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)* (-((-1 + p4val)*p4val*(1 + m2val*(1 + p3val) + p3val*(2 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) + pow(m4val,2)*(-1 + 2*p4val + p3val*pow(p4val,2)* (-2 + p3val*(-2 + pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m2val*(-1 + 2*p4val + p3val*pow(p4val,2)* (-2 + 3*p3val*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 2*m2val*p3val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) + m4val*(-1 + pow(p4val,2)*(-2 - 2*p3val + pow(p3val,2)*(-2 + pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + 2*p4val*(1 + p3val*(2 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m2val*(-1 + 2*(1 + p3val)*p4val + pow(p4val,2)*(-2 - 2*p3val + m2val*pow(p3val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1)* (2 + 3*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))))))* pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1)); k2val = pow(1 + m2val,-1)*pow(m4val,-1)*pow(p4val,-1)*pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1)* (2*m2val*(1 + p3val)*(-1 + p4val)*p4val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) - (1 + p3val)*p4val*(1 + p4val)*pow(m2val,3)*pow(m3val,2)*pow(m4val,2)* (1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + m4val*((m3val - p3val)*p3val*pow(p4val,2) - 3*(1 + m3val)*pow(m2val,3)*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) + p3val*(p3val + m3val*(1 + 2*p3val))*pow(m2val,2)*pow(p4val,2)* pow(1 + (1 + m2val)*pow(epsval,-1),-2) + m2val*(2 - 4*(1 + p3val)*p4val + pow(2 + p3val,2)*pow(p4val,2) - m3val*(-2 + 2*p3val*pow(p4val,2) + pow(p3val,2)*pow(p4val,2)))* pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + pow(m4val,2)*(-((m3val - p3val)*p4val*(-(p3val*p4val) + m3val*(1 + p4val))) - 3*(1 + m3val)*pow(m2val,3)*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) + p3val*p4val*pow(m2val,2)*(p3val*p4val + m3val*(1 + 2*(1 + p3val)*p4val) + (1 + p4val)*pow(m3val,2))*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + m2val*(2 - 4*p4val + (-1 + p3val)*p4val*(1 + p4val)*pow(m3val,2) + p3val*(4 + p3val)*pow(p4val,2) - m3val*(-2 - 2*(-2 + p3val)*p4val + (4 + pow(p3val,2))*pow(p4val,2)))* pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + m3val*m4val*p4val*pow(m2val,2)*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))* (p3val*((1 + p3val)*p4val + m4val*(1 + (2 + p3val)*p4val))* (1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + m3val*m4val*(1 + p4val)*(1 + p3val*(2 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) - m2val*(2*(1 + p3val)*(-1 + p4val)*p4val + m4val*(2 - 4*(1 + p3val)*p4val + pow(p4val,2)* (4 + 4*p3val + pow(p3val,2)*(1 + pow(m2val,3)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) - 3*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m3val*(2 + 2*p3val*pow(p4val,2)* (-1 + pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + pow(p3val,2)*pow(p4val,2)*(-1 + pow(m2val,3)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) - pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 3*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) + pow(m4val,2)*(2 - 4*p4val + 4*p3val*pow(p4val,2) + pow(p3val,2)*pow(p4val,2) + pow(m2val,3)*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) - 3*pow(m2val,2)*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - m2val*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + p4val*(1 + p4val)*pow(m3val,2)*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))* (-1 + p3val*(1 + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m3val*(2 + pow(p4val,2)*(-4 - pow(p3val,2) + pow(m2val,3)*pow(p3val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-3) - (-4 + p3val)*p3val*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + m2val*p3val*(8 + 3*p3val)*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + 2*p4val*(-2 + p3val*pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2))))))* pow((1 + m2val)*m3val*m4val*(1 + p4val) - (1 + m4val)*p3val*p4val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)),-1)* pow(-(p3val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m3val*(1 + m2val*(1 + p3val) - m2val*p3val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)),-1); k3val = -(pow(1 + m3val,-1)*pow(m4val,-1)*pow(1 + p3val,-1)*pow(p4val,-1)* pow(-((1 + p3val)*p4val) + m4val*(1 - p3val*p4val + m3val*(1 + p4val)),-1)* (p3val*p4val*(2*p3val*(-1 + p4val) + (1 + p3val)*(-1 + p3val*p4val)*pow(m4val,2) + m4val*(2*p3val*(-2 + p4val) + p4val + p4val*pow(p3val,2)))* (1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + (1 + p3val)*p4val*(1 + p4val)*pow(m3val,3)*pow(m4val,2)* (1 + m2val*(1 + p3val) - m2val*p3val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) - m3val*(2*p3val*(-1 + p4val)*p4val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + pow(m4val,2)*(-((1 + m2val)*p4val) - p4val*pow(p3val,2)*(2 - p4val + m2val*(1 + 2*p4val) + m2val*(1 - 3*p4val)*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + p3val*(-2 + m2val*(-2 + 2*p4val + pow(p4val,2)) - p4val*(-1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + pow(p4val,2)*(2 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + pow(p3val,3)*pow(p4val,2)*(-1 + 2*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*(1 + 6*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 4*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) + m4val*((1 + m2val)*pow(p4val,2) + pow(p3val,2)*pow(p4val,2)*(3 - m2val + 4*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) - p3val*(2 + m2val*(2 + pow(p4val,2)) + 4*p4val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) - pow(p4val,2)*(1 + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + pow(p3val,3)*pow(p4val,2)*(-1 + 2*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*(1 + 6*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 4*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))))) + m4val*pow(m3val,2)*(-2 - pow(p4val,2) + 2*p3val*pow(p4val,2) - pow(p3val,2)*pow(p4val,2) + 2*pow(m2val,2)*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + m2val*p3val*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) - 2*m2val*pow(p3val,2)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*pow(p3val,3)*pow(p4val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m4val*(-2 + p4val*(2 + p3val*(-3 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + pow(p3val,2)*(-1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + pow(p4val,2)*(1 + m2val*pow(p3val,3)*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + pow(p3val,2)*(-2 + 2*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)) + p3val*(-1 + 2*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))) - m2val*(2 + pow(p4val,2)*(1 - p3val + pow(p3val,3) - pow(p3val,2)*(1 + 6*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) + 4*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m4val*(2 + 2*p4val*(-1 + 2*p3val + pow(p3val,2)) + pow(p4val,2)*(-1 + 3*p3val + pow(p3val,3) + pow(p3val,2)*(1 - 6*pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2) - 4*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))))))* pow(-(p3val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))) + m3val*(1 + m2val*(1 + p3val) - m2val*p3val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)),-1)); k4val = -((m4val - p4val)*pow(1 + m4val,-1)*pow(p3val,2)*pow(1 + p4val,-1)* (m4val*((1 + m2val)*m3val*m4val*((-1 + m3val*(-3 + p3val) + 3*p3val)*pow(m3val - p3val,-1)* pow(p3val,-2)*(-1 + pow(p3val,2)) + (-1 + m4val*(-3 + p4val) + 3*p4val)*pow(p3val,-2)*pow(m4val - p4val,-1)*pow(p4val,-2)* (-1 + pow(p4val,2)) + (-1 + pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2))* (-1 + 3*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*(-3 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))* pow(m2val - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1)) + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))* (-4*m2val*m3val*m4val - m4val*(1 + (1 + m2val)*pow(epsval,-1))*pow(m2val,-1)*pow(1 + m3val,2)* pow(m3val - p3val,-1)*pow(-1 + p3val,2)*pow(p3val,-1) - (1 + (1 + m2val)*pow(epsval,-1))*pow(m2val,-1)*pow(1 + m4val,2)*pow(p3val,-1)* pow(m4val - p4val,-1)*pow(-1 + p4val,2)*pow(p4val,-1) - m3val*m4val*(1 + (1 + m2val)*pow(epsval,-1))*pow(m2val,-1)*pow(1 + m2val,2)* pow(m2val - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1)* pow(-1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2)))* (-(pow(1 + m2val,2)*pow(m3val,2)*pow(p3val,-2)*pow(1 + p3val,2)) + pow(1 + m3val,2)*pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2)) - (1 + p3val)*pow(p3val,-2)*((1 + m2val)*m3val*(1 + p3val) - (1 + m3val)*p3val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))* (-(pow(1 + m2val,2)*pow(m3val,2)*pow(m4val,2)* ((-1 + m3val*(-3 + p3val) + 3*p3val)*pow(m3val - p3val,-1)*pow(p3val,-2)* (-1 + pow(p3val,2)) + (-1 + m4val*(-3 + p4val) + 3*p4val)*pow(p3val,-2)* pow(m4val - p4val,-1)*pow(p4val,-2)*(-1 + pow(p4val,2)) + (-1 + pow(m2val,2)*pow(1 + (1 + m2val)*pow(epsval,-1),-2))* (-1 + 3*m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1) + m2val*(-3 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))* pow(m2val - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1))) + (2*pow(m2val,2)*pow(m3val,2)*pow(m4val,2) + (-1 + m3val)*(-1 + p3val)*pow(1 + m3val,2)*pow(m4val,2)*pow(m3val - p3val,-1) + (-1 + m4val)*(-1 + p4val)*pow(1 + m4val,2)*pow(m4val - p4val,-1) + (-1 + m2val)*pow(1 + m2val,2)*pow(m3val,2)*pow(m4val,2)* (-1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1))* pow(m2val - m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),-1))* pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2)))* pow(m4val*(1 + p4val)*pow(p4val,-2)*((1 + m2val)*m3val*m4val*(1 + p4val) - (1 + m4val)*p3val*p4val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))* (-(pow(1 + m2val,2)*pow(m3val,2)*pow(p3val,-2)*pow(1 + p3val,2)) + pow(1 + m3val,2)*pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2)) - (1 + p3val)*((1 + m2val)*m3val*(1 + p3val) - (1 + m3val)*p3val*(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1)))* (-(pow(1 + m2val,2)*pow(m3val,2)*pow(m4val,2)*pow(p3val,-2)*pow(p4val,-2)*pow(1 + p4val,2)) + pow(1 + m4val,2)*pow(1 + m2val*pow(1 + (1 + m2val)*pow(epsval,-1),-1),2)),-1)); } if (ValidSys) { th 2 -d1val; th 3 d2val; th 4 -d3val; th 5 d4val; rd 2 -r1val; rd 3 r2val; rd 4 -r3val; rd 5 r4val; cc 2 k1val; cc 3 k2val; cc 4 k3val; cc 5 k4val; } return(ValidSys); } /****************************************************************************** *******************************************************************************/ //Prototypes cmd PS3mirC_sldrs(); cmd PS3mirC_chng(int slider_id, double slider_value); int PSCM_3_Confocal( double d0, double d1, double d2, double d3, double GII, double tant1, double tant2, double tant3, double tantobj, double tantim, double m, double S11I, double S22I, double S111I, double S122I, double S11II, double S22II, double S111II, double S122II, double S11III, double S22III, double S111III, double S122III); int setup_conicsurf(int surfNum, int nRefl, double S11, double S22, double S111, double S122, double thetaval, double dval); /**************************************************************************************/ /**************************************************************************************/ cmd PS3mirC_sldrs() { stp outp off; stp gacl off; stp noeb on; double d0val, d1val, d2val, d3val, gIIval, theta1, thetaobj, thetaim, mval; double EntPupLoc, fnum, ObjectHeight; int ImageOpt, ConicOpt, EvalStuff; file_new PS3mirC cus 7; lid "Plane Symmetric 3-mirror relay"; des "JMH"; wv_ 1 0.5; uni mm; ast 1; drw 0 on; // change for INF drw imsnbr on; tla imsnbr 0.0; //needed to set coord surf at img drl_aperstop set off; drl_lastsrf set imsnbr; drl_raystosrf set img; drl_nbrfpts set 3; drl_nbrrays 0 set 4; drl_nbrrays 1 set 4; drl_yfieldpt 1 set 1.0; drl_maxpup 1 set 1.0; drl_minpup 1 set -1.0; drl_nbrrays 2 set 4; drl_yfieldpt 2 set -1.0; drl_maxpup 2 set 1.0; drl_minpup 2 set -1.0; drl_hatchrefl set on; ray_aiming_mode set crr; opdw set off; //opd measured in lens units gla 2 reflect; drw 2 off; dt 2 -1; gla 4 reflect; drw 4 off; dt 4 -1; gla 6 reflect; drw 6 off; dt 6 -1; drw imsnbr off; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "d0", "PS3mirC_chng", 1, 5000.0, Za[20] = d0val = 500.0); graphwin_sliderassign(21, real, drag, "d1", "PS3mirC_chng", 1, 5000.0, Za[21] = d1val = 300.0); graphwin_sliderassign(22, real, drag, "d2", "PS3mirC_chng", 1, 5000.0, Za[22] = d2val = 270.0); graphwin_sliderassign(23, real, drag, "d3", "PS3mirC_chng", 1, 5000.0, Za[23] = d3val = 800.0); graphwin_sliderassign(24, real, drag, "gII", "PS3mirC_chng", -500.0, 500.0, Za[24] = gIIval = 355.0); graphwin_sliderassign(25, real, drag, "Theta 1", "PS3mirC_chng", 0.0, 50.0, Za[25] = theta1 = 15.0); graphwin_sliderassign(26, real, drag, "Theta Obj", "PS3mirC_chng", -40.0, 40.0, Za[26] = thetaobj = 0.0); graphwin_sliderassign(27, real, drag, "Theta Img", "PS3mirC_chng", -40.0, 40.0, Za[27] = thetaim = 0.0); graphwin_sliderassign(28, real, drag, "Magnification (m)", "PS3mirC_chng", -5.0, 5.0, Za[28] = mval = 1.0); graphwin_sliderassign(40, real, drag, "Object height", "PS3mirC_chng", 10.0, 200.0, Za[40] = ObjectHeight = 7.5); graphwin_sliderassign(41, real, drag, "Ent Pupil (0=INF)", "PS3mirC_chng", -5000.0, 5000.0, Za[41] = EntPupLoc = -1573.0); graphwin_sliderassign(42, real, drag, "Fnum in object space", "PS3mirC_chng", -30.0, 30.0, Za[42] = fnum = 18.0); graphwin_sliderassign(70, int, drag, "Examples", "PS3mirC_ex", 1, 5, 1); graphwin_slidershow(); PS3mirC_chng(20, Za[20]); stp outp on; stp gacl on; stp noeb off; } //=================================================================================================== //=================================================================================================== cmd PS3mirC_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d0val, d1val, d2val, d3val, gIIval, theta1, thetaobj, thetaim, mval; double S11I, S22I, S111I, S122I; double S11II, S22II, S111II, S122II; double S11III, S22III, S111III, S122III; double theta2, theta3, tant2, tant3; double EntPupLoc, fnum, ObjectHeight; int ImageOpt, ConicOpt, EvalStuff; double maxspotrad = 0.0, PKVALopd = 0.0, RMSopd = 0.0, strehl = 1.0; double ImageTilt, ImageWidthX, ImageWidthY, Image_loc, Exit_pup_loc; d0val = Za[20]; d1val = Za[21]; d2val = Za[22]; d3val = Za[23]; gIIval = Za[24]; theta1 = Za[25]; thetaobj = Za[26]; thetaim = Za[27]; mval = Za[28]; ObjectHeight = Za[40]; EntPupLoc = Za[41]; fnum = Za[42]; ImageOpt = Za[50]; ConicOpt = Za[51]; if (slider_id == 20) Za[20] = d0val = slider_value; else if (slider_id == 21) Za[21] = d1val = slider_value; else if (slider_id == 22) Za[22] = d2val = slider_value; else if (slider_id == 23) Za[23] = d3val = slider_value; else if (slider_id == 24) Za[24] = gIIval = slider_value; else if (slider_id == 25) Za[25] = theta1 = slider_value; else if (slider_id == 26) Za[26] = thetaobj = slider_value; else if (slider_id == 27) Za[27] = thetaim = slider_value; else if (slider_id == 28) Za[28] = mval = slider_value; else if (slider_id == 40) Za[40] = ObjectHeight = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = fnum = slider_value; obh ObjectHeight; nao 1/(2*fnum); if ( fabs(EntPupLoc)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; graphwin_open(1); gclear(); // if ( Build3MirConicCCL(d0val,d1val,d2val,d3val,gIIval,tan(theta1*dr),tan(thetaobj*dr),tan(thetaim*dr),mval) ) // setup_conic(3, 0, 0); if ( PSCM_3_Confocal( d0val,d1val,d2val, d3val, gIIval, tan(theta1*dr),&tant2,&tant3,tan(thetaobj*dr),tan(thetaim*dr),mval, &S11I, &S22I, &S111I, &S122I, &S11II, &S22II, &S111II, &S122II, &S11III, &S22III, &S111III, &S122III) ) { theta2 = atan(tant2)/dr; theta3 = atan(tant3)/dr; if ( setup_conicsurf(2, 0, S11I, S22I, S111I, S122I, theta1, d1val) && setup_conicsurf(4, 1, S11II, S22II, S111II, S122II, theta2, d2val) && setup_conicsurf(6, 2, S11III, S22III, S111III, S122III, theta3, d3val) ) { tla 0 thetaobj; tla imsnbr thetaim; th 0 EntPupLoc; th 1 d0val-EntPupLoc; th imsnbr 0.0; //reset image defocus before optimization draw_lens y; draw_default_rays(); } else { //Message1(); } } else message(" Invalid System "); stp outp on; stp gacl on; stp noeb off; } double PS3mirCexamples[5][9]={ // d0 d1 d2 d3 gII t1 tobj tim mag 115.02048, 1998.73600, 1272.84402, 1038.56188, -886.73909, 9.54976, 9.98182, 4.17927, -4.0, 126.55412, 179.85185, 228.16715, 1999.63013, 91.12454, 8.85367, 7.31430, -6.84472, -4.0, 126.82457, 100.00807, 100.15048, 999.99828, 59.73121, 9.34886, 9.99771, 0.86229, -4.0, 757.35358, 999.95919, 644.47724, 809.66761, -890.76115, 7.12335, 8.11423, 1.43980, -4.0, 1998.68256, 972.56782, 1998.77073, 555.32002, 292.44032, 4.77913, -9.96135, -0.08822, -4.0, }; cmd PS3mirC_ex(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, real, 1, 5000.0, Za[20] = PS3mirCexamples[slider_value-1][0]); graphwin_sliderreset(21, real, 1, 5000.0, Za[21] = PS3mirCexamples[slider_value-1][1]); graphwin_sliderreset(22, real, 1, 5000.0, Za[22] = PS3mirCexamples[slider_value-1][2]); graphwin_sliderreset(23, real, 1, 5000.0, Za[23] = PS3mirCexamples[slider_value-1][3]); graphwin_sliderreset(24, real, -500.0, 500.0, Za[24] = PS3mirCexamples[slider_value-1][4]); graphwin_sliderreset(25, real, 0.0, 50.0, Za[25] = PS3mirCexamples[slider_value-1][5]); graphwin_sliderreset(26, real, -40.0, 40.0, Za[26] = PS3mirCexamples[slider_value-1][6]); graphwin_sliderreset(27, real, -40.0, 40.0, Za[27] = PS3mirCexamples[slider_value-1][7]); graphwin_sliderreset(28, real, -5.0, 5.0, Za[28] = -PS3mirCexamples[slider_value-1][8]); graphwin_sliderreset(40, r, 0.01, 100.0, Za[40] = 10.0);// obj = 2 cm square graphwin_sliderreset(42, r, 0.1, 30.0, Za[42] = 5.0);//fnum = 5.0 -> nao = 0.1 PS3mirC_chng(20, Za[20]); //initiate change } int PSCM_3_Confocal( double d0, double d1, double d2, double d3, double GII, double tant1, double tant2, double tant3, double tantobj, double tantim, double m, double S11I, double S22I, double S111I, double S122I, double S11II, double S22II, double S111II, double S122II, double S11III, double S22III, double S111III, double S122III) { double cost1, cost2, cost3; int ValidSys = 1; tant2 = ((m*(-(d0*(2*d2*tant1 + GII*(2*tant1 + tantim))) - (d2*GII + d1*(d2 + GII))*(2*tant1 - tantobj)) + d3*GII*(2*tant1 - tantobj))*pow(d0,-1)*pow(d2,-1)*pow(m,-1))/2.; tant3 = (pow(d0,-1)*pow(d2,-1)*(d0*d2*GII*m*(-(d2*tantim) + d0*m*tantim + d3*tantobj) + d3*(d2 + GII)*m*(2*tant1 - tantobj)*pow(d1,2) - d1*(d0*d2*(d2 + GII)*m*tantim - d3*m*(2*d0*d2*tant1 + 2*d0*GII*tant1 + 2*d2*GII*tant1 + d0*GII*tantim - d2*GII*tantobj) + GII*(2*tant1 - tantobj)*pow(d3,2)))*pow(m,-1)* pow(d1*(d2 + d3 + GII) + GII*(d2 + d3 - d0*m),-1))/2.; cost1 = cos(atan(tant1)); cost2 = cos(atan(tant2)); cost3 = cos(atan(tant3)); S22I = -((-(d3*GII) + d0*d2*m + d1*d2*m + d0*GII*m + d1*GII*m + d2*GII*m)*pow(cost1,-1)*pow(d0,-1)* pow(d1*d2 + d1*GII + d2*GII,-1)*pow(m,-1))/2.; S11I = cost1*cost1*S22I; S22II = (pow(cost2,-1)*pow(GII,-1))/2.; S11II = cost2*cost2*S22II; S22III = -((d1*d2 + d1*d3 + d1*GII + d2*GII + d3*GII - d0*GII*m)*pow(cost3,-1)*pow(d3,-1)* pow(d1*d2 + d1*GII + d2*GII,-1))/2.; S11III = cost3*cost3*S22III; S122I = (pow(d0,-2)*pow(d1,-1)*pow(d2*GII + d1*(d2 + GII),-2)*pow(m,-2)* (-2*GII*(d2 + GII)*m*(d2*m*tant1 - d3*tantobj)*pow(d1,2) + d0*d2*m*(-2*(d0*m*tantim + d3*tantobj) + d2*(tantim + m*tantobj))*pow(GII,2) + d1*(-2*d3*GII*m*(d0*(d2*tant1 + GII*(tant1 + tantim)) - d2*GII*tantobj) + (tant1 - 2*tantobj)*pow(d3,2)*pow(GII,2) + m*(d0*d2*GII*(d2 + GII)*(tantim + m*tantobj) - m*tant1*pow(d2,2)*pow(GII,2) + m*tant1*pow(d0,2)*pow(d2 + GII,2))) - tant1*pow(d1,3)*pow(d2 + GII,2)*pow(m,2)))/4.; S111I = 3*cost1*cost1*S122I; S122II = (pow(d0,-1)*pow(d1,-1)*pow(d2,-1)*pow(GII,-2)* (-(d3*(d2 + GII)*m*(2*tant1 - tantobj)*pow(d1,3)) + pow(d1,2)*(-(d3*m*(d0*(2*d2*tant1 + 2*GII*tant1 + GII*tantim) + GII*(3*d2 + 2*GII)*(2*tant1 - tantobj))) + d0*(d2 + GII)*m*(2*GII*(2*m*tant1 + tantim) + d2*(2*m*tant1 + 2*tantim + m*tantobj)) + GII*(2*tant1 - tantobj)*pow(d3,2)) + 2*d0*d2*m*(-2*(d0*m*tantim + d3*tantobj) + d2*(tantim + m*tantobj))*pow(GII,2) + d1*(-(d3*GII*m*(2*d2*GII*(2*tant1 - tantobj) + d0*(3*d2*(2*tant1 + tantobj) + 2*GII*(4*tant1 + tantim + tantobj)))) + 2*(2*tant1 - tantobj)*pow(d3,2)*pow(GII,2) + d0*m*(d2*GII*(2*d2*m*tant1 + 4*GII*m*tant1 + 4*d2*tantim + 4*GII*tantim + 3*d2*m*tantobj + 2*GII*m*tantobj) + d0*m*(6*d2*GII*tant1 - 3*d2*GII*tantim + 2*tant1*pow(d2,2) + 4*tant1*pow(GII,2) - 2*tantim*pow(GII,2)))))*pow(m,-1)*pow(d1*d3 + d0*d2*m,-1))/8.; S111II = 3*cost2*cost2*S122II; S122III = (pow(d0,-1)*pow(d2,-1)*pow(d3,-2)*pow(d2*GII + d1*(d2 + GII),-2)*pow(m,-1)* (d3*(d2 + GII)*(d2 - d3 + GII)*m*(2*tant1 - tantobj)*pow(d1,3) - d0*d2*m*(-d2 + d3 + 3*d0*m)*(-(d2*tantim) + d0*m*tantim + d3*tantobj)*pow(GII,2) + pow(d1,2)*(m*(2*d0*d3*tant1 + 4*d3*GII*tant1 + d0*d3*tantim - 2*d0*GII*tantim - 2*d3*GII*tantobj)* pow(d2,2) - d0*m*tantim*pow(d2,3) + d3*GII*(d3*(-(d0*m*(2*tant1 + tantim)) - GII*(1 + m)*(2*tant1 - tantobj)) + d0*GII*m*(2*(1 + m)*tant1 + 3*tantim + m*tantobj) + (2*tant1 - tantobj)*pow(d3,2)) + d2*(d3*GII*m*(4*GII*tant1 - 2*GII*tantobj + d0*(2*(2 + m)*tant1 + 4*tantim + m*tantobj)) + (-2*d0*m*tant1 + GII*(-2*tant1 - 4*m*tant1 + tantobj + 2*m*tantobj))*pow(d3,2) - d0*m*tantim*pow(GII,2))) + d1*GII* (m*(d3*GII*(2*tant1 - tantobj) + d0*(-2*GII*tantim + d3*(2*tant1 + 2*tantim + tantobj)) + 4*m*tantim*pow(d0,2))*pow(d2,2) - 2*d0*m*tantim*pow(d2,3) + d3*GII*(-(d0*d3*m*(4*tant1 + tantim + 3*tantobj)) + (2*tant1 - tantobj)*pow(d3,2) + (2*tant1 - 3*tantim)*pow(d0,2)*pow(m,2)) + d2*(d0*d3*m*(d0*m*(2*tant1 - tantim) + GII*(2*(1 + m)*tant1 + 4*tantim + tantobj + m*tantobj)) + (-(GII*(1 + m)*(2*tant1 - tantobj)) - d0*m*(2*tant1 + tantobj))*pow(d3,2) + 4*GII*tantim*pow(d0,2)*pow(m,2)))))/8.; S111III = 3*cost3*cost3*S122III; return ValidSys; } int setup_conicsurf(int surfNum, int nRefl, double S11, double S22, double S111, double S122, double thetaval, double dval) { double cval, kval, hval, ww, zz, dummy1, dummy2, dummy3; double sign_ = pow(-1, nRefl); //nRefl is the number of reflections PRIOR to surfnum double NumZero = 1e-10; int ValidSys = 1; char outpstat = char_pref(outp); // This prevents division by zero problems in the c k and h equations if ( fabs(S11)NumZero ) ValidSys = 0; // The value under the square root of the offsets must be positive else if ( pow(S122,2) + pow(S11 - S22,2)*pow(S22,2) < 0.0 ) ValidSys = 0; // Test if the surface is a conic. if ( ValidSys ) if ( fabs(S111-3*S122*S11/S22)>NumZero ) printf("Note that S111 and S122 of Surf %d do not match that of a conic!\n",surfnum); if (ValidSys) { // prt S11 S22 S122; cval = S22*pow(S22*pow(S11,-1),0.5); // Note: a failure occurs when thetaval = 0.0, needs to be fixed // if (fabs(S11 - S22)0.1) { drl_nbrfpts set 3; drl_nbrrays 1 set 3; drl_nbrrays 2 set 3; } else drl_nbrfpts set 1; } if ( fabs(EntPupLoc)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; nao 1/(2*fnum); obh ObjectHeight; graphwin_open(1); gclear(); if ( SM1_setup(d0val,r1val,t1val) ) { th 0 EntPupLoc; th 1 d0val-EntPupLoc; draw_lens y; draw_default_rays(); SMDrawCenters(); message("Basal Line Image Length = %4.2f",BasalLineImageLength); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //======================================================================================================================= //======================================================================================================================= int SM1_setup (double d0val, double r1val, double t1val) { double d1val, c1val, delta0, cosOmega, timg, cost1; int ValidSys = 1; t1val *= dr; // Convert angles to radians cost1 = cos(t1val); if (r1val==0.0 || d0val==0.0) ValidSys = 0; else { c1val = 1/r1val; d1val = -d0val/(2*c1val*d0val*cost1 + 1); delta0 = sqrt( r1val*r1val + d0val*d0val + 2*d0val*r1val*cost1 ); cosOmega = -(cost1 + c1val*d0val*cos(2*t1val))/(c1val*delta0); if ( (d0val>0) && (d1val>0) && (c1val>0) ) // unphysical timg = - asin(cosOmega); else if ( (d0val>0) && (d1val>0) && (c1val<0) ) // checked timg = - asin(cosOmega); else if ( (d0val>0) && (d1val<0) && (c1val>0) ) // checked timg = - asin(cosOmega); else if ( (d0val>0) && (d1val<0) && (c1val<0) ) // checked timg = asin(cosOmega); else if ( (d0val<0) && (d1val>0) && (c1val>0) ) // checked timg = - asin(cosOmega); else if ( (d0val<0) && (d1val>0) && (c1val<0) ) // checked timg = asin(cosOmega); else if ( (d0val<0) && (d1val<0) && (c1val>0) ) // checked timg = asin(cosOmega); else if ( (d0val<0) && (d1val<0) && (c1val<0) ) // unphysical timg = asin(cosOmega); th 0 d0val; th 2 -d1val; cv 2 c1val; tla 2 t1val/dr; tla 3 timg/dr; } return ValidSys; } //====================================================================================== //====================================================================================== // Object at Infinity //====================================================================================== //====================================================================================== cmd SM1INF_sldrs() { stp outp off; stp gacl off; stp noeb on; double r1val, hval, HFOV, EntPupLoc, EntranceBeamRadius; file_new SM1INF cus 2; lid "1 Spherical Mirror (INF)"; SMStartup(); drl_firstsrf set 1; drl_nbrfpts set 1; drw 0 off; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mir 1 Radius (scale)", "SM1INF_chng", -2000.0, 2000.0, Za[20] = r1val = -1000.0); graphwin_sliderassign(21, real, drag, "Off-axis fractional ht", "SM1INF_chng", 0.0, 1.0, Za[21] = hval = 1/sqrt(2.0)); graphwin_sliderassign(40, real, drag, "HFOV", "SM1INF_chng", 0.1, 10.0, Za[40] = HFOV = 0.1); graphwin_sliderassign(41, real, drag, "Ent Pupil Location", "SM1INF_chng", -1000.0, 1000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Radius", "SM1INF_chng", 1.0, 200.0, Za[42] = EntranceBeamRadius = 100.0); graphwin_slidershow(); SM1INF_chng(20,Za[20]); prt "Imaging a point to a line with a spherical mirror"; prt " Joseph M. Howard and Bryan D. Stone"; prt " Applied Optics Vol. 37, No. 10, 1826-1834 (1998)"; stp outp on; stp gacl on; stp noeb off; } //======================================================================================================================= //======================================================================================================================= cmd SM1INF_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double r1val, hval, HFOV, EntPupLoc, EntranceBeamRadius; r1val = Za[20]; hval = Za[21]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; if (slider_id == 20) Za[20] = r1val = slider_value; else if (slider_id == 21) Za[21] = hval = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; if (slider_id == 40) //HFOV { if (HFOV>0.1) { drl_nbrfpts set 3; drl_nbrrays 1 set 3; drl_nbrrays 2 set 3; } else drl_nbrfpts set 1; } ang HFOV; ebr EntranceBeamRadius; graphwin_open(1); gclear(); if ( SM1INF_setup(r1val,hval) ) { th 1 EntPupLoc; draw_lens y SMsign(r1val)*th[2]; draw_default_rays(); SMDrawCenters(); message("Basal Line Image Length = %4.2f",BasalLineImageLength); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //======================================================================================================================= //======================================================================================================================= int SM1INF_setup (double r1val, double hval) { double c1val, d1val, t1val, cost1, cosOmega, timg; int ValidSys = 1; if (r1val==0.0 || fabs(hval)>=1.0) ValidSys = 0; else // Object at Infinity { c1val = 1/r1val; cost1 = sqrt(1 - hval*hval); t1val = acos(cost1); d1val = -1/(2*c1val*cost1); cosOmega = 1 - 2*hval*hval; timg = pi/2 - acos(cosOmega); th 2 -d1val; cv 2 c1val; tla 2 t1val/dr; tla imsnbr timg/dr; } return ValidSys; } //======================================================== //======================================================== double BasalLineImageLength() { double Ywidth, Ymax, Ymin; char outpstat = char_pref(outp); stp outp off; int i,j,k; sop 0 0; sbr; tra std loc 0.0 0.0 imsnbr imsnbr n 1; //trace base ray Ymax = Ymin = a1; sbr; tra std loc 1.0 0.0 imsnbr imsnbr n 1; //top of pupil if (a1Ymax) Ymax = a1; sbr; tra std loc -1.0 0.0 imsnbr imsnbr n 1; //bottom of pupil if (a1Ymax) Ymax = a1; sbr; Za[1] = Ywidth = fabs(Ymax-Ymin); if(outpstat) stp outp on; return Ywidth; } //=================================================================================================================== //=================================================================================================================== // "Imaging a point with two spherical mirrors" by Joseph M. Howard and Bryan D. Stone //=================================================================================================================== //=================================================================================================================== //Prototypes cmd SM2_sldrs(); cmd SM2_chng(int slider_id, double slider_value); // Callback for two_mir_sldrs() int SM2_setup(double d1scale, double t1val, double t2val, int soln); cmd SM2_example(int slider_id, double slider_value); // Callback for examples //============================================================= //============================================================= cmd SM2_sldrs() { stp outp off; stp gacl off; stp noeb on; double d1val, t1val, t2val; int soln; double ObjectHeight, EntPupLoc, fnum, imtilt; int ImageOpt, CvOpt; file_new SM2 cus 3; lid "Two Sphere Relay"; SMStartup(); drl_nbrfpts set 1; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "d1 (scales system)", "SM2_chng", 1.0, 1000.0, Za[20] = d1val = 500.0); graphwin_sliderassign(21, real, drag, "Theta 1", "SM2_chng", 1.0, 80.0, Za[21] = t1val = 45.0); graphwin_sliderassign(22, real, drag, "Theta 2", "SM2_chng", -80.0, 80.0 , Za[22] = t2val = 45.0); graphwin_sliderassign(23, int, drag, "Which solution?", "SM2_chng", 1, 3, Za[23] = soln = 1); graphwin_sliderassign(40, real, drag, "Object Height", "SM2_chng", 0.01, 100.0, Za[40] = ObjectHeight = 0.01); graphwin_sliderassign(41, real, drag, "Ent Pupil (0=INF)", "SM2_chng", -5000.0, 5000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Fnum (object space)", "SM2_chng", 0.1, 30.0, Za[42] = fnum = 10.0); graphwin_sliderassign(50, real, drag, "Image Tilt", "SM2_chng", -10.0, 10.0, Za[50] = imtilt = 0.0); graphwin_sliderassign(70, int, drag, "Published Examples", "SM2_example", 1, 19, 8); graphwin_slidershow(); SM2_example(70,8); prt "Imaging a point with two spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " J. Opt. Soc. Am. A Vol. 15, No. 12, 3045-3056 (1998)"; stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= cmd SM2_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d1val, t1val, t2val; int soln; double ObjectHeight, EntPupLoc, fnum, imtilt; d1val = Za[20]; t1val = Za[21]; t2val = Za[22]; soln = Za[23]; ObjectHeight = Za[40];; EntPupLoc = Za[41]; fnum = Za[42]; imtilt = Za[50]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = t1val = slider_value; else if (slider_id == 22) Za[22] = t2val = slider_value; else if (slider_id == 23) Za[23] = soln = slider_value; else if (slider_id == 40) Za[40] = ObjectHeight = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = fnum = slider_value; else if (slider_id == 50) Za[50] = imtilt = slider_value; nao 1/(2*fnum); obh ObjectHeight; if (ObjectHeight>0.1) { drl_nbrfpts set 3; drl_nbrrays 1 set 3; drl_nbrrays 2 set 3; } else drl_nbrfpts set 1; if ( fabs(EntPupLoc)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; graphwin_open(1); gclear(); if ( SM2_setup(d1val,t1val,t2val,soln) ) { th 1 th[0]-EntPupLoc; th 0 EntPupLoc; tla imsnbr imtilt; draw_lens y; draw_default_rays(); SMDrawCenters(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= int SM2_setup (double d1scale, double t1val, double t2val, int soln) { double m, p, q, r, a, b, dum1, dum2, dum3, dum4, c1d0, c1d0_1, c1d0_2, c1d0_3, d0val, d1val, d2val, c1val, c2val; double mag1, mag2, cost1, cost2, x[4], y[4], xmax, xmin, ymax, ymin; int ValidSys, i; ValidSys = 1; t1val *= dr; // Convert angles to radians t2val *= dr; cost1 = cos(t1val); cost2 = cos(t2val); if ( fabs(t1val) < 1e-10 || fabs(t2val) < 1e-10 || d1scale <= 0.0 ) ValidSys = 0; else if ( fabs(t1val + t2val) < 1e-10 ) { if (soln == 1) { dum1 = cos(t1val) / (sin(t1val) * sin(t1val)); c1val = dum1; c2val = dum1; d0val = -cos(t1val) / (dum1*2.0); d2val = d0val; d1val = 1.0; } else ValidSys = 0; } else //t1val + t2val != 0 { r = 0.5 * cos(t1val) * (sin(t1val - 3 * t2val) + sin(t1val - t2val) - 10 * sin(t1val + t2val) + sin(3 * t1val + t2val) + 6 * sin(t1val + 3 * t2val) - sin(t1val + 5 * t2val)); q = (4 * sin(t1val - 3 * t2val) + 10 * sin(t1val - t2val) + sin(3 * t1val - t2val) - 40 * sin(t1val + t2val) + 12 * sin(3 * (t1val + t2val)) - 10 * sin(3 * t1val + t2val)); q = 0.25 * (q + sin(5 * t1val + t2val) + 22 * sin(t1val + 3 * t2val) - 4 * sin(t1val + 5 * t2val) - 2 * sin(3 * t1val + 5 * t2val)); p = (-sin(2 * t1val - t2val) - 29 * sin(t2val) - 5 * sin(3 * t2val) - 31 * sin(2 * t1val + t2val) - sin(4 * t1val + t2val) + 29 * sin(2 * t1val + 3 * t2val)); p = 0.25 * (p + 6 * sin(4 * t1val + 3 * t2val) - 5 * sin(2 * t1val + 5 * t2val) - sin(4 * t1val + 5 * t2val)); m = -(2 + cos(2 * t1val) + 2 * cos(2 * t2val) - 6 * cos(2 * (t1val + t2val)) + cos(2 * (t1val + 2 * t2val))) * sin(t1val + t2val); if (m == 0) //m=0 { if (p == 0) //p=0 { if (soln == 1) c1d0 = -r / q; { ValidSys = 0; } } //p=0 else { //p not equal 0} dum1 = q * q - 4 * p * r; if ((dum1 < 0) || (soln > 2)) { ValidSys = 0; } else { if (soln == 1) c1d0 = (-q + sqrt(dum1)) / (2 * p); else c1d0 = (-q - sqrt(dum1)) / (2 * p); } } //p not equal zero } //m=0 else { //m not equal zero r = r / m; q = q / m; p = p / m; a = (3 * q - p * p) / 3.0; b = (2 * p * p * p - 9 * p * q + 27 * r) / 27; dum1 = b * b / 4 + a * a * a / 27; if (dum1 > 0) //one real solution { if (soln > 1) { //no solution for this case ValidSys = 0; } //no solution for this case else { dum2 = -b / 2 - sqrt(dum1); dum1 = -b / 2 + sqrt(dum1); if (dum2 > 0) dum2 = exp(log(dum2) / 3); else dum2 = -exp(log(-dum2) / 3); if (dum1 > 0) dum1 = exp(log(dum1) / 3); else dum1 = -exp(log(-dum1) / 3); c1d0 = dum1 + dum2 - p / 3; } } //one real solution else if (dum1 == 0) //three real solutions--two of which are equal { if (soln > 2) { //no solution for this case ValidSys = 0; } //no solution for this case} else { dum2 = -b / 2; if (dum2 > 0) dum2 = exp(log(dum2) / 3); else dum2 = -exp(log(-dum2) / 3); if (soln == 1) c1d0 = 2 * dum2 - p / 3; else c1d0 = -dum2 - p / 3; } } //three real solutions--two of which are equal else { //three real solutions dum2 = acos(-b / (2 * sqrt(-a * a * a / 27))); c1d0_1 = 2 * sqrt(-a / 3) * cos(dum2 / 3) - p / 3; c1d0_2 = 2 * sqrt(-a / 3) * cos(dum2 / 3 + 2 * pi / 3) - p / 3; c1d0_3 = 2 * sqrt(-a / 3) * cos(dum2 / 3 + 4 * pi / 3) - p / 3; if (soln == 1) { if (t2val>0) { if (r<0) c1d0 = c1d0_1; else c1d0 = c1d0_2; } else { if (t1val>-t2val) { if (q<0) c1d0 = c1d0_3; else c1d0 = c1d0_2; } else c1d0 = c1d0_1; } } else if (soln == 2) { if (t2val>0) { if (r<0) c1d0 = c1d0_2; else c1d0 = c1d0_3; } else { if (t1val>-t2val) { if (q<0) c1d0 = c1d0_1; else c1d0 = c1d0_3; } else c1d0 = c1d0_2; } } else { if (t2val>0) { if (r<0) c1d0 = c1d0_3; else c1d0 = c1d0_1; } else { if (t1val>-t2val) { if (q<0) c1d0 = c1d0_2; else c1d0 = c1d0_1; } else c1d0 = c1d0_3; } } } //end three real solutions } //end m not equal zero } //end t1val and t2val not equal to 0 if (ValidSys) { if ((t1val + t2val) != 0) { dum2 = sin(t2val) * sin(t2val); dum3 = (2 * c1d0 + cos(t1val)); dum4 = (sin(t1val + t2val) + c1d0 * sin(2 * t1val + t2val)); if ((dum2 == 0) || (dum3 == 0) || (dum4 == 0)) { ValidSys = 0; dum1 = 0; } else { dum1 = c1d0 * (1 + cos(2 * t2val) + cos(2 * (t1val + t2val)) - 3 * cos(2 * t1val)) - 2 * cos(t1val) + cos(t1val - 2 * t2val) + cos(t1val + 2 * t2val); dum1 = dum1 * sin(t1val + t2val) / (4 * dum2 * dum3 * dum4); } if (dum1 > 0) d0val = fabs(c1d0); else d0val = -fabs(c1d0); c1val = c1d0 / d0val; d1val = dum1 * d0val; c2val = 2 * dum3 * dum2 * dum4 * dum4 / (sin(t1val) * sin(t1val) * sin(t1val) * c1d0 * d0val); c2val = c2val / (-3 * sin(t1val + t2val) - 3 * c1d0 * sin(2 * t1val + t2val) + sin(t1val + 3 * t2val) + c1d0 * sin(2 * t1val + 3 * t2val)); d2val = -(sin(t1val + t2val) + c1d0 * sin(2 * t1val + t2val)) / (c2val * (c1d0 * sin(2 * (t1val + t2val)) + sin(t1val + 2 * t2val))); c1val = c1val*d1val; c2val = c2val*d1val; d0val = d0val/d1val; d2val = d2val/d1val; d1val = 1; d0val *= d1scale; d1val *= d1scale; d2val *= d1scale; c1val /= d1scale; c2val /= d1scale; } } if (ValidSys) { th 0 d0val; th 2 -d1val; th 3 d2val; cv 2 c1val; cv 3 -c2val; tla 2 t1val/dr; tla 3 t2val/dr; } return ValidSys; } //============================================================= //============================================================= double SM2examples[19][4]={ 10.0, -70.0, 1, 5.0, 40.0, -70.0, 1, 10.0, 45.0, -45.0, 1, 2.5, 72.0, -41.0, 1, 2.5, 70.0, -10.0, 1, 2.5, //5 30.0, 30.0, 1, 2.5, 45.0, 45.0, 1, 2.5, 30.0, 60.0, 1, 5.0, 60.0, 30.0, 1, 5.0, 56.0, 54.0, 1, 2.5, //10 60.0, 60.0, 1, 10.0, 32.0, -64.0, 2, 2.5, 56.0, -29.0, 2, 10.0, 60.0, 60.0, 2, 5.0, 32.0, -64.0, 3, 2.5, //15 45.0, -60.0, 3, 5.0, 54.0, -42.0, 3, 10.0, 60.0, 60.0, 3, 2.5, 75.0, 75.0, 3, 10.0 }; cmd SM2_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(21, r, 1.0, 80.0, Za[21] = SM2examples[slider_value-1][0]); graphwin_sliderreset(22, r, -80.0, 80.0, Za[22] = SM2examples[slider_value-1][1]); graphwin_sliderreset(23, i, 1, 3, Za[23] = SM2examples[slider_value-1][2]); graphwin_sliderreset(42, r, 0.1, 30.0, Za[42] = SM2examples[slider_value-1][3]); SM2_chng(21, Za[21]); //initiate change } //Prototypes cmd SM2INF_sldrs(); cmd SM2INF_chng(int slider_id, double slider_value); int SM2INF_setup(double r1val, double t1val); static double SM2INFZero(double t1val, double t2val); static double SM2INFdZero(double t1val, double t2val); cmd SM2INF_example(int slider_id, double slider_value); // Callback for examples //============================================================= //============================================================= cmd SM2INF_sldrs() { stp outp off; stp gacl off; stp noeb on; double r1val, theta1; double HFOV, EntPupLoc, EntranceBeamRadius, imtilt; file_new SM2INF cus 3; lid "Two Sphere Telescope"; SMStartup(); drw 0 off; drl_firstsrf set 1; drl_nbrfpts set 1; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mir 1 Radius", "SM2INF_chng", -1000.0, 1000.0, Za[20] = r1val = 100.0); graphwin_sliderassign(21, real, drag, "Theta 1", "SM2INF_chng", 1.0, 89.0, Za[21] = theta1 = 30.0); graphwin_sliderassign(40, real, drag, "HFOV", "SM2INF_chng", 0.1, 10.0, Za[40] = HFOV = 0.1); graphwin_sliderassign(41, real, drag, "Ent Pupil Loc", "SM2INF_chng", -1000.0, 1000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "SM2INF_chng", 1.0, 200.0, Za[42] = EntranceBeamRadius = 5.0); graphwin_sliderassign(50, real, drag, "Image Tilt", "SM2INF_chng", -10.0, 10.0, Za[50] = imtilt = 0.0); graphwin_sliderassign(70, int, drag, "Examples", "SM2INF_example", 1, 3, 1); graphwin_slidershow(); SM2INF_example(70,1); prt "Imaging a point with two spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " J. Opt. Soc. Am. A Vol. 15, No. 12, 3045-3056 (1998)"; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM2INF_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double r1val, theta1; double HFOV, EntPupLoc, EntranceBeamRadius, imtilt; double MirrorDCY; r1val = Za[20]; theta1 = Za[21]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; imtilt = Za[50]; if (slider_id == 20) Za[20] = r1val = slider_value; else if (slider_id == 21) Za[21] = theta1 = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; else if (slider_id == 50) Za[50] = imtilt = slider_value; ang HFOV; ebr EntranceBeamRadius; if (HFOV>0.1) {drl_nbrfpts set 3; drl_nbrrays 1 set 3; drl_nbrrays 2 set 3;} else drl_nbrfpts set 1; graphwin_open(1); gclear(); if ( SM2INF_setup(r1val, theta1) ) { th 1 EntPupLoc; tla imsnbr imtilt; draw_lens y -th[2]; draw_default_rays(); SMDrawCenters(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ static double SM2INFZero(double t1val, double t2val) { return( 2 + Cos(2*t1val) + 2*Cos(2*t2val) - 6*Cos(2*t1val + 2*t2val) + Cos(2*t1val + 4*t2val) ); } //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ static double SM2INFdZero(double t1val, double t2val) { return( -4*Sin(2*t2val) + 12*Sin(2*t1val + 2*t2val) - 4*Sin(2*t1val + 4*t2val) ); } //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ int SM2INF_setup(double r1val, double t1val) { double d1val, d2val, c1val, c2val, t2val, m11tot, m22tot; double convergence = 3e-8, stepsize, x[4], y[4], xmax, xmin, ymax, ymin; int ValidSys = 1, i, maxiterations = 10; t1val = t1val*dr; if ( ( (r1val > 0) && (t1val == 45.0*dr) ) || fabs(r1val) < 1e-10 ) ValidSys = 0; // Pick starting values for t2val else if (r1val < 0) t2val = (-Pi - 2*Pi*t1val)/6.; else t2val = (Pi - 2*Pi*t1val)/6.; if (ValidSys) { for (i = 0; i < maxiterations; i++) // FindZero Loop (Newton's Method) { stepsize = -SM2INFZero(t1val,t2val)/SM2INFdZero(t1val,t2val); t2val += stepsize; if ( sqrt(stepsize*stepsize) < convergence ) break; } // end FindZero Loop while (t2val < -Pi/2) t2val += Pi; while (t2val > Pi/2) t2val -= Pi; c1val = 1/r1val; d1val = -((-1 + 3*Cos(2*t1val) - Cos(2*t2val) - Cos(2*(t1val + t2val)))*Csc(2*t1val + t2val)*pow(c1val,-1)*pow(Csc(t2val),2)*Sin(t1val + t2val))/8.; d2val = (Csc(2*(t1val + t2val))*Csc(2*t1val + t2val)*pow(c1val,-1)*pow(Csc(t2val),2)*pow(Sin(t1val),3)*(3*Sin(2*t1val + t2val) - Sin(2*t1val + 3*t2val)))/4.; c2val = 4*pow(c1val,2)*pow(Csc(t1val),3)*pow(Sin(t2val),2)*pow(Sin(2*t1val + t2val),2)*pow(-3*c1val*Sin(2*t1val + t2val) + c1val*Sin(2*t1val + 3*t2val),-1); th 2 -d1val; th 3 d2val; cv 2 c1val; cv 3 -c2val; tla 2 t1val/dr; tla 3 t2val/dr; } return ValidSys; } //============================================================= //============================================================= // r1val t1val double SM2INFexamples[3][2]={ 100.0, 30.0, -200.0, 20.0, -200.0, 60.0 }; cmd SM2INF_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 1.0, 80.0, Za[20] = SM2INFexamples[slider_value-1][0]); graphwin_sliderreset(21, r, -80.0, 80.0, Za[21] = SM2INFexamples[slider_value-1][1]); SM2INF_chng(20, Za[20]); //initiate change } /* Copyright 2001: Joseph M. Howard */ //=================================================================================================================== //=================================================================================================================== // "Imaging with three spherical mirrors" by Joseph M. Howard and Bryan D. Stone //=================================================================================================================== //=================================================================================================================== // Prototypes cmd SM3_sldrs(); cmd SM3_chng(int slider_id, double slider_value); cmd SM3_example(int slider_id, double slider_value); // Callback for examples int SM_3(double d0val,double d1val,double d2val,double d3val,double c1val,double c2val,double c3val, double t1val,double t2val,double t3val,double ThetaObj,double ThetaIm,double m1val,double m2val); // ======================================================================= // ======================================================================= cmd SM3_sldrs() { stp outp off; stp gacl off; stp noeb on; double d0val, d1val, d2val, d3val, c1val, r2val, c3val, Theta1, Theta2, Theta3, ThetaObj, ThetaIm, m1val, m2val; double ObjectHeight, EntPupLoc, fnum; int ImageOpt, CvOpt; file_new SM3 cus 4; lid "3 spherical mirror relay"; SMStartup(); graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mirror 1-2 Sep (d1)", "SM3_chng", 1.0, 2000.0, Za[20] = d1val = 500.0); graphwin_sliderassign(21, real, drag, "Mirror 2-3 Sep (d2)", "SM3_chng", 1.0, 2000.0, Za[21] = d2val = 1500.0); graphwin_sliderassign(22, real, drag, "Mir 2 Radius", "SM3_chng", -2000.0, 2000.0, Za[22] = r2val = -1/0.0008); graphwin_sliderassign(23, real, drag, "Theta 1", "SM3_chng", 1.0, 80.0, Za[23] = Theta1 = 30.0); graphwin_sliderassign(24, real, drag, "Theta 2", "SM3_chng", -80.0, 80.0, Za[24] = Theta2 = -8.0); graphwin_sliderassign(25, real, drag, "Theta 3", "SM3_chng", -80.0, 80.0, Za[25] = Theta3 = -16.0); graphwin_sliderassign(26, real, drag, "Theta Obj", "SM3_chng", -40.0, 40.0, Za[26] = ThetaObj = 0.0); graphwin_sliderassign(27, real, drag, "Theta Im", "SM3_chng", -40.0, 40.0, Za[27] = ThetaIm = 0.0); graphwin_sliderassign(28, real, drag, "Mag Y (in plane)", "SM3_chng", -10.0, 10.0, Za[28] = m1val = 4.0); graphwin_sliderassign(29, real, drag, "Mag X (transverse)", "SM3_chng", -10.0, 10.0, Za[29] = m2val = -4.0); graphwin_sliderassign(40, real, drag, "Object Height", "SM3_chng", 0.01, 100.0, Za[40] = ObjectHeight = 10.0); graphwin_sliderassign(41, real, drag, "Ent Pupil (0=INF)", "SM3_chng", -5000.0, 5000.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Fnum (object space)", "SM3_chng", 0.1, 30.0, Za[42] = fnum = 10.0); graphwin_sliderassign(70, int, drag, "Published Examples", "SM3_example", 1, 6, 1); graphwin_slidershow(); SM3_example(70,1); prt "Imaging with three spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " Applied Optics, Vol. 39, No. 19, 3216-3231 (2000)."; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM3_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d0val, d1val, d2val, d3val, c1val, r2val, c3val, Theta1, Theta2, Theta3, ThetaObj, ThetaIm, m1val, m2val; double ObjectHeight, EntPupLoc, fnum; d1val = Za[20]; d2val = Za[21]; r2val = Za[22]; Theta1 = Za[23]; Theta2 = Za[24]; Theta3 = Za[25]; ThetaObj = Za[26]; ThetaIm = Za[27]; m1val = Za[28]; m2val = Za[29]; ObjectHeight = Za[40]; EntPupLoc = Za[41]; fnum = Za[42]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = d2val = slider_value; else if (slider_id == 22) Za[22] = r2val = slider_value; else if (slider_id == 23) Za[23] = Theta1 = slider_value; else if (slider_id == 24) Za[24] = Theta2 = slider_value; else if (slider_id == 25) Za[25] = Theta3 = slider_value; else if (slider_id == 26) Za[26] = ThetaObj = slider_value; else if (slider_id == 27) Za[27] = ThetaIm = slider_value; else if (slider_id == 28) Za[28] = m1val = slider_value; else if (slider_id == 29) Za[29] = m2val = slider_value; else if (slider_id == 40) Za[40] = ObjectHeight = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = fnum = slider_value; nao 1/(2*fnum); obh ObjectHeight; graphwin_open(1); gclear(); if ( SM_3(&d0val,d1val,d2val,&d3val,&c1val,1/r2val,&c3val,Theta1,Theta2,Theta3,ThetaObj,ThetaIm,m1val,m2val) ) { th 1 d0val; th 2 -d1val; th 3 d2val; th 4 -d3val; cv 2 c1val; cv 3 -1/r2val; cv 4 c3val; tla 0 ThetaObj; tla 2 Theta1; tla 3 Theta2; tla 4 Theta3; tla imsnbr ThetaIm; th 0 EntPupLoc; th 1 th[1]-EntPupLoc; if ( fabs(EntPupLoc)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; draw_lens y; draw_default_rays(); SMDrawCenters(); SMDrawMirrorAxis(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= // d1 d2 c2 t1 t2 t3 tobj timg m1 m2 double SM3examples[6][10]={ 868.65, 999.68, 3.301e-3, 4.421, -16.925, -26.068, -19.660, 25.373, 4.0, -4.0, 229.17, 162.29, 2.362e-3, 3.862, -22.268, -37.036, 0.685, 25.361, 4.0, -4.0, 794.48, 998.21, 2.394e-3, 9.259, -27.308, 23.616, -24.560, 21.035, 4.0, -4.0, 999.81, 549.09, 5.213e-4, 4.261, -28.331, 15.177, 3.817, -20.800, 4.0, -4.0, 997.32, 366.96,-1.272e-3, 11.655, -5.929, -21.701, 36.824, -20.778, 4.0, -4.0, 662.60, 317.20, 1.048e-5, 2.890, 79.272, 78.577, 9.155, 16.787, 4.0, -4.0, }; cmd SM3_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 1.0, 2000.0, Za[20] = SM3examples[slider_value-1][0]); graphwin_sliderreset(21, r, 1.0, 2000.0, Za[21] = SM3examples[slider_value-1][1]); graphwin_sliderreset(22, r, -2000.0, 2000.0, Za[22] = 1/SM3examples[slider_value-1][2]); graphwin_sliderreset(23, r, 1.0, 80.0, Za[23] = SM3examples[slider_value-1][3]); graphwin_sliderreset(24, r, -80.0, 80.0, Za[24] = SM3examples[slider_value-1][4]); graphwin_sliderreset(25, r, -80.0, 80.0, Za[25] = SM3examples[slider_value-1][5]); graphwin_sliderreset(26, r, -40.0, 40.0, Za[26] = SM3examples[slider_value-1][6]); graphwin_sliderreset(27, r, -40.0, 40.0, Za[27] = SM3examples[slider_value-1][7]); graphwin_sliderreset(28, r, -10.0, 10.0, Za[28] = SM3examples[slider_value-1][8]); graphwin_sliderreset(29, r, -10.0, 10.0, Za[29] = SM3examples[slider_value-1][9]); graphwin_sliderreset(40, r, 0.01, 100.0, Za[40] = 10.0);// obj = 2 cm square graphwin_sliderreset(42, r, 0.1, 30.0, Za[42] = 5.0);//fnum = 5.0 -> nao = 0.1 SM3_chng(20, Za[20]); //initiate change } //======================================= //======================================= int SM_3(double d0val,double d1val,double d2val,double d3val,double c1val,double c2val,double c3val, double t1val,double t2val,double t3val,double ThetaObj,double ThetaIm,double m1val,double m2val) { int ValidSys = 1; double cost1, sint1, cost2, sint2, cost3, sint3; t1val = t1val*dr; //convert degrees to radians t2val = t2val*dr; t3val = t3val*dr; ThetaObj *= dr; ThetaIm *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); cost3 = cos(t3val); sint3 = sin(t3val); m1val = m1val*sec(ThetaObj)*cos(ThetaIm); //compensate for object and image tilts if ( (m1val==0) || (m2val==0) || (c2val==0) || (d2val<0) ) ValidSys = 0; else { c1val = (cost1*(cost2*(m1val + m2val)*(-1 + m2val + (1 + m1val)*pow(cost3,2)) + 2*c2val*d2val*m1val*(-1 + m2val)*pow(sint3,2) - 2*c2val*d2val*(1 + m1val)*m2val*pow(cost2,2)*pow(sint3,2))*pow((2*c2val*d1val*d2val + cost2*(d1val + d2val))*m1val*pow(sint3,2) + m2val*(cost2*(d1val + d2val + 2*c2val*cost2*d1val*d2val)*pow(cost1,2)*pow(sint3,2) - m1val*pow(sint1,2)*(d1val*(cost2 + 2*c2val*d1val*pow(cost2,2) - cost2*pow(cost3,2) - 2*c2val*d1val*pow(cost3,2)) + (cost2 + 2*c2val*d1val)*(1 + 2*c2val*cost2*d1val)*d2val*pow(sint3,2))),-1))/2.; c3val = -(cost3*pow(m1val,-1)*pow(m2val,-1)*(-2*c2val*d1val*m1val*(-1 + m2val)*m2val*pow(sint1,2) - 2*c2val*d1val*m1val*(1 + m1val)*m2val*pow(cost2,2)*pow(sint1,2) + cost2*(m1val + m2val)*(m1val + m2val*pow(cost1,2) - m1val*m2val*pow(sint1,2)))* pow(-(cost2*(d2val*(-1 + m2val + (1 + m1val)*pow(cost3,2)) + d1val*(-1 + m2val - 4*pow(c2val,2)*pow(d2val,2) + pow(cost3,2)*(1 + m1val + 4*pow(c2val,2)*pow(d2val,2))))* pow(sint1,2)) + 2*c2val*d2val*pow(cost2,2)*(d2val - d2val*pow(cost3,2) - d1val*(-1 + (1 + m1val)*pow(cost3,2))*pow(sint1,2)) + 2*c2val*d2val*(-(d1val*pow(sint1,2)*(m2val - pow(sint3,2))) - d2val*pow(cost1,2)*pow(sint3,2)),-1))/2.; d0val = -(((2*c2val*d1val*d2val + cost2*(d1val + d2val))*m1val*pow(sint3,2) + m2val*(cost2*(d1val + d2val + 2*c2val*cost2*d1val*d2val)*pow(cost1,2)*pow(sint3,2) - m1val*pow(sint1,2)*(d1val*(cost2 + 2*c2val*d1val*pow(cost2,2) - cost2*pow(cost3,2) - 2*c2val*d1val*pow(cost3,2)) + (cost2 + 2*c2val*d1val)*(1 + 2*c2val*cost2*d1val)*d2val*pow(sint3,2))))* pow(cost2*pow(cost3,2)*pow(m1val,2) + cost2*pow(cost1,2)*pow(m2val,2) + m1val*m2val*(-2*c2val*d1val*pow(cost2,2) + cost2*pow(cost3,2) + 2*c2val*d1val*pow(cost3,2) - 2*c2val*cost2*(cost2 + 2*c2val*d1val)*d2val*pow(sint3,2) + pow(cost1,2)*(cost2 + 2*c2val*d1val*pow(cost2,2) - 2*c2val*d1val*pow(cost3,2) + 2*c2val*(1 + 2*c2val*cost2*d1val)*d2val*pow(sint3,2))),-1)); d3val = m1val*m2val*(-(cost2*(d2val*(-1 + m2val + (1 + m1val)*pow(cost3,2)) + d1val*(-1 + m2val - 4*pow(c2val,2)*pow(d2val,2) + pow(cost3,2)*(1 + m1val + 4*pow(c2val,2)*pow(d2val,2))))*pow(sint1,2)) + 2*c2val*d2val*pow(cost2,2)*(d2val - d2val*pow(cost3,2) - d1val*(-1 + (1 + m1val)*pow(cost3,2))*pow(sint1,2)) + 2*c2val*d2val*(-(d1val*pow(sint1,2)*(m2val - pow(sint3,2))) - d2val*pow(cost1,2)*pow(sint3,2)))* pow(cost2*pow(cost3,2)*pow(m1val,2) + cost2*pow(cost1,2)*pow(m2val,2) + m1val*m2val*(-2*c2val*d1val*pow(cost2,2) + cost2*pow(cost3,2) + 2*c2val*d1val*pow(cost3,2) - 2*c2val*cost2*(cost2 + 2*c2val*d1val)*d2val*pow(sint3,2) + pow(cost1,2)*(cost2 + 2*c2val*d1val*pow(cost2,2) - 2*c2val*d1val*pow(cost3,2) + 2*c2val*(1 + 2*c2val*cost2*d1val)*d2val*pow(sint3,2))),-1); } return ValidSys; } // ======================================================================= // ======================================================================= // Prototypes cmd SM3INF_sldrs(); cmd SM3INF_chng(int slider_id, double slider_value); cmd SM3INF_example(int slider_id, double slider_value); // Callback for examples int SM_3INF(double d1val,double d2val,double d3val,double c1val,double c2val,double c3val, double t1val,double t2val,double t3val,double ThetaIm, double m1val,double m2val); // ======================================================================= // ======================================================================= cmd SM3INF_sldrs() { stp outp off; stp gacl off; stp noeb on; double d1val, d2val, d3val, r1val, c2val, c3val, Theta1, Theta2, Theta3, ThetaIm, m1val, m2val; double HFOV, EntPupLoc, EntranceBeamRadius; file_new SM3INF cus 4; lid "3 spherical mirror telescope"; SMStartup(); drw 0 off; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mirror 1-2 Sep (d1)", "SM3INF_chng", 1.0, 2000.0, Za[20] = d1val = 1000.0); graphwin_sliderassign(21, real, drag, "Mir 1 Radius", "SM3INF_chng", -12000.0, 12000.0, Za[21] = r1val = -1/0.00022); graphwin_sliderassign(22, real, drag, "Theta 1", "SM3INF_chng", 1.0, 80.0, Za[22] = Theta1 = 6.0); graphwin_sliderassign(23, real, drag, "Theta 2", "SM3INF_chng", -80.0, 80.0, Za[23] = Theta2 = -18.0); graphwin_sliderassign(24, real, drag, "Theta 3", "SM3INF_chng", -80.0, 80.0, Za[24] = Theta3 = 6.0); graphwin_sliderassign(25, real, drag, "Theta Im", "SM3INF_chng", -40.0, 40.0, Za[25] = ThetaIm = 0.0); graphwin_sliderassign(26, real, drag, "Foc Len Y (in plane)", "SM3INF_chng", -2000.0, 2000.0, Za[26] = m1val = -1000.0); graphwin_sliderassign(27, real, drag, "Foc Len X (perp)", "SM3INF_chng", -2000.0, 2000.0, Za[27] = m2val = 1000.0); graphwin_sliderassign(40, real, drag, "HFOV", "SM3INF_chng", 0.1, 10.0, Za[40] = HFOV = 1.0); graphwin_sliderassign(41, real, drag, "Ent Pupil Loc", "SM3INF_chng", -100.0, 100.0, Za[41] = EntPupLoc = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "SM3INF_chng", 1.0, 300.0, Za[42] = EntranceBeamRadius = 50.0); graphwin_sliderassign(70, int, drag, "Published Examples", "SM3INF_example", 1, 12, 1); graphwin_slidershow(); SM3INF_example(70,1); prt "Imaging with three spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " Applied Optics, Vol. 39, No. 19, 3216-3231 (2000)."; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM3INF_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d1val, d2val, d3val, r1val, c2val, c3val, Theta1, Theta2, Theta3, ThetaIm, m1val, m2val; double HFOV, EntPupLoc, EntranceBeamRadius; d1val = Za[20]; r1val = Za[21]; Theta1 = Za[22]; Theta2 = Za[23]; Theta3 = Za[24]; ThetaIm = Za[25]; m1val = Za[26]; m2val = Za[27]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = r1val = slider_value; else if (slider_id == 22) Za[22] = Theta1 = slider_value; else if (slider_id == 23) Za[23] = Theta2 = slider_value; else if (slider_id == 24) Za[24] = Theta3 = slider_value; else if (slider_id == 25) Za[25] = ThetaIm = slider_value; else if (slider_id == 26) Za[26] = m1val = slider_value; else if (slider_id == 27) Za[27] = m2val = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; graphwin_open(1); gclear(); if ( SM_3INF(d1val,&d2val,&d3val,1/r1val,&c2val,&c3val,Theta1,Theta2,Theta3,ThetaIm,m1val,m2val) ) { th 2 -d1val; th 3 d2val; th 4 -d3val; cv 2 1/r1val; cv 3 -c2val; cv 4 c3val; tla 2 Theta1; tla 3 Theta2; tla 4 Theta3; tla imsnbr ThetaIm; ang HFOV; th 1 EntPupLoc; ebr EntranceBeamRadius; draw_lens y -th[2]; draw_default_rays(); SMDrawCenters(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= // d1 c1 t1 t2 t3 timg f1 f2 double SM3INFexamples[12][8]={ 900.0, 1.000e-4, 10.000, 4.000, -14.000, 0.0, -1000.0, 1000.0, 900.0, -3.000e-4, 70.000, 70.000, 70.000, 0.0, -1000.0, 1000.0, 700.0, -3.000e-4, 10.000, -50.000, -12.000, 0.0, -1000.0, 1000.0, 700.0, -3.000e-4, 10.000, -24.000, 10.000, 0.0, -1000.0, 1000.0, 700.0, -3.000e-4, 10.000, 30.000, -18.000, 0.0, -1000.0, 1000.0, 700.0, -3.000e-4, 10.000, 52.000, 28.000, 0.0, -1000.0, 1000.0, 502.09, 5.473e-4, 8.000, -6.587, 30.882, 0.0, -1000.0, 1000.0, 906.18, -2.741e-4, 68.673, 70.337, -74.087, 0.0, -1000.0, 1000.0, 472.57, -1.510e-5, 48.179, -62.712, -12.493, 0.0, -1000.0, 1000.0, 651.97, -5.548e-4, 4.543, -31.434, 49.364, 0.0, -1000.0, 1000.0, 519.83, -3.607e-4, 6.743, 40.721, -16.058, 0.0, -1000.0, 1000.0, 860.43, -2.210e-4, 6.974, 41.224, 9.162, 0.0, -1000.0, 1000.0, }; cmd SM3INF_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 1.0, 2000.0, Za[20] = SM3INFexamples[slider_value-1][0]); graphwin_sliderreset(21, r, 1/SM3INFexamples[slider_value-1][1]-2000.0, 1/SM3INFexamples[slider_value-1][1]+2000.0, Za[21] = 1/SM3INFexamples[slider_value-1][1]); graphwin_sliderreset(22, r, 1.0, 80.0, Za[22] = SM3INFexamples[slider_value-1][2]); graphwin_sliderreset(23, r, -80.0, 80.0, Za[23] = SM3INFexamples[slider_value-1][3]); graphwin_sliderreset(24, r, -80.0, 80.0, Za[24] = SM3INFexamples[slider_value-1][4]); graphwin_sliderreset(25, r, -40.0, 40.0, Za[25] = SM3INFexamples[slider_value-1][5]); graphwin_sliderreset(26, r, -1000.0, 1000.0, Za[26] = SM3INFexamples[slider_value-1][6]); graphwin_sliderreset(27, r, -1000.0, 1000.0, Za[27] = SM3INFexamples[slider_value-1][7]); if (slider_value==2 || slider_value==8) graphwin_sliderreset(40, r, 0.01, 100.0, Za[40] = 0.01);// HFOV for examples else graphwin_sliderreset(40, r, 0.01, 100.0, Za[40] = 1.0);// HFOV for examples graphwin_sliderreset(42, r, 0.1, 30.0, Za[42] = 50.0);//EBR SM3INF_chng(20, Za[20]); //initiate change } //======================================= //======================================= int SM_3INF(double d1val,double d2val,double d3val,double c1val,double c2val,double c3val, double t1val,double t2val,double t3val,double ThetaIm, double m1val,double m2val) { int ValidSys = 1; double cost1,sint1,cost2,sint2,cost3,sint3; t1val *= dr; // Convert degrees to radians t2val *= dr; t3val *= dr; ThetaIm *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); cost3 = cos(t3val); sint3 = sin(t3val); m1val = m1val*sec(ThetaIm); //accounts for tilted image plane if ( (m1val==0) || (m2val==0) || (c1val==0) ) ValidSys = 0; else { c2val = -(cost2*(cost1 + 2*c1val*m2val*pow(cost1,2) - cost1*pow(cost3,2) + 2*c1val*m1val*pow(cost3,2))* pow(2*cost1*(1 + 2*c1val*cost1*d1val)*m2val*pow(cost2,2) + 2*(cost1 + 2*c1val*d1val)*m1val*pow(cost3,2),-1)); c3val = -(cost1*cost3*pow(m1val,-1)*pow(m2val,-1)*pow(sint3,2)*pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),2)* pow(2*c1val*pow(cost1,2)*pow(cost2,2)*pow(1 + 2*c1val*cost1*d1val,2)*pow(m2val,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + m1val*pow(cost3,2)*pow(cost1 + 2*c1val*d1val,2)*(2*c1val*m1val*pow(cost3,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + cost1*(1 + 2*c1val*cost1*d1val)*pow(sint2,2)*pow(sint3,2)) + cost1*(cost1 + 2*c1val*d1val)*(1 + 2*c1val*cost1*d1val)*m2val* (2*c1val*m1val*(1 + pow(cost2,2))*pow(cost3,2)*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2)) + cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2)*pow(sint2,2)*pow(sint3,2)),-1))/2.; d2val = pow(cost1,-1)*(2*c1val*d1val*m1val + cost1*(m1val + m2val) + 2*c1val*d1val*m2val*pow(cost1,2))* (cost1*(1 + 2*c1val*cost1*d1val)*m2val*pow(cost2,2) + (cost1 + 2*c1val*d1val)*m1val*pow(cost3,2))*pow(sint3,-2)* pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),-1); d3val = -(m1val*m2val*pow(cost1,-1)*pow(sint3,-2)*(2*c1val*cost1*(1 + 2*c1val*cost1*d1val)*m2val*(-pow(cost1,2) + pow(cost2,2) - 2*c1val*cost1*d1val*pow(sint2,2)) + (cost1 + 2*c1val*d1val)*(2*c1val*m1val*pow(cost3,2)*(-pow(cost1,2) + pow(cost2,2) - 2*c1val*cost1*d1val*pow(sint2,2)) - cost1*(1 + 2*c1val*cost1*d1val)*pow(sint2,2)*pow(sint3,2)))* pow((cost1 + 2*c1val*d1val)*m1val + m2val*(cost1*(1 + 2*c1val*cost1*d1val)*pow(cost2,2) + 2*c1val*m1val*(pow(cost1,2) - pow(cost2,2) + 2*c1val*cost1*d1val*pow(sint2,2))),-1)); } // if (d2val<0) // ValidSys = 0; return ValidSys; } //=================================================================================================================== //=================================================================================================================== // "Imaging with four spherical mirrors" by Joseph M. Howard and Bryan D. Stone //=================================================================================================================== //=================================================================================================================== // Prototypes cmd SM4_sldrs(); cmd SM4_chng(int slider_id, double slider_value); cmd SM4_example(int slider_id, double slider_value); // Callback for examples int SM_4(double d0val,double d1val,double d2val,double d3val,double d4val,double c1val,double c2val,double c3val,double c4val, double t1val,double t2val,double t3val,double t4val,double ThetaObj,double ThetaIm,double m1val,double m2val); // ======================================================================= // ======================================================================= cmd SM4_sldrs() { stp outp off; stp gacl off; stp noeb on; file_new four_mirror cus 5; lid "4 spherical mirror relay"; SMStartup(); graphwin_sliderassign(20, real, drag, "d0", "SM4_chng", 10.0, 2000.0, Za[20] = 173.14); graphwin_sliderassign(21, real, drag, "d1", "SM4_chng", 10.0, 2000.0, Za[21] = 173.14); graphwin_sliderassign(22, real, drag, "d2", "SM4_chng", 10.0, 2000.0, Za[22] = 191.92); graphwin_sliderassign(23, real, drag, "r1", "SM4_chng", -2000.0, 2000.0, Za[23] = -1000.0); graphwin_sliderassign(24, real, drag, "r2", "SM4_chng", -2000.0, 2000.0, Za[24] = 1000.0); graphwin_sliderassign(25, real, drag, "Theta 1", "SM4_chng", 1.0, 80.0, Za[25] = 12.711); graphwin_sliderassign(26, real, drag, "Theta 2", "SM4_chng", -80.0, 80.0, Za[26] = -12.711); graphwin_sliderassign(27, real, drag, "Theta 3", "SM4_chng", -80.0, 80.0, Za[27] = 7.284); graphwin_sliderassign(28, real, drag, "Theta 4", "SM4_chng", -80.0, 80.0, Za[28] = -10.291); graphwin_sliderassign(29, real, drag, "Theta Obj", "SM4_chng", -80.0, 80.0, Za[29] = 0.0); graphwin_sliderassign(30, real, drag, "Theta Im", "SM4_chng", -80.0, 80.0, Za[30] = 0.0); graphwin_sliderassign(31, real, drag, "m1", "SM4_chng", -10.0, 10.0, Za[31] = -4.0); graphwin_sliderassign(32, real, drag, "m2", "SM4_chng", -10.0, 10.0, Za[32] = -4.0); graphwin_sliderassign(40, real, drag, "Object Height", "SM4_chng", 0.01, 100.0, Za[40] = 10.0); graphwin_sliderassign(41, real, drag, "Ent Pupil (0=INF)", "SM4_chng", -5000.0, 5000.0, Za[41] = 0.0); graphwin_sliderassign(42, real, drag, "Fnum (object space)", "SM4_chng", 0.1, 30.0, Za[42] = 5.0); graphwin_sliderassign(70, int, drag, "Published Examples", "SM4_example", 1, 8, 1); graphwin_slidershow(); SM4_example(70,1); prt "Imaging with four spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " Applied Optics, Vol. 39, No. 19, 3232-3242 (2000)."; stp outp on; stp gacl on; stp noeb off; } //============================================================================== //============================================================================== cmd SM4_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d0val, d1val, d2val, d3val, d4val, r1val, r2val, c3val, c4val, Theta1, Theta2, Theta3, Theta4, ThetaObj, ThetaIm, m1val, m2val; double ObjectHeight, EntPupLoc, fnum; d0val = Za[20]; d1val = Za[21]; d2val = Za[22]; r1val = Za[23]; r2val = Za[24]; Theta1 = Za[25]; Theta2 = Za[26]; Theta3 = Za[27]; Theta4 = Za[28]; ThetaObj = Za[29]; ThetaIm = Za[30]; m1val = Za[31]; m2val = Za[32]; ObjectHeight = Za[40]; EntPupLoc = Za[41]; fnum = Za[42]; if (slider_id == 20) Za[20] = d0val = slider_value; else if (slider_id == 21) Za[21] = d1val = slider_value; else if (slider_id == 22) Za[22] = d2val = slider_value; else if (slider_id == 23) Za[23] = r1val = slider_value; else if (slider_id == 24) Za[24] = r2val = slider_value; else if (slider_id == 25) Za[25] = Theta1 = slider_value; else if (slider_id == 26) Za[26] = Theta2 = slider_value; else if (slider_id == 27) Za[27] = Theta3 = slider_value; else if (slider_id == 28) Za[28] = Theta4 = slider_value; else if (slider_id == 29) Za[29] = ThetaObj = slider_value; else if (slider_id == 30) Za[30] = ThetaIm = slider_value; else if (slider_id == 31) Za[31] = m1val = slider_value; else if (slider_id == 32) Za[32] = m2val = slider_value; else if (slider_id == 40) Za[40] = ObjectHeight = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = fnum = slider_value; graphwin_open(1); gclear(); nao 1/(2*fnum); obh ObjectHeight; if ( SM_4(d0val,d1val,d2val,&d3val,&d4val,1/r1val,1/r2val,&c3val,&c4val,Theta1,Theta2,Theta3,Theta4,ThetaObj,ThetaIm,m1val,m2val) ) { th 1 d0val; th 2 -d1val; th 3 d2val; th 4 -d3val; th 5 d4val; cv 2 1/r1val; cv 3 -1/r2val; cv 4 c3val; cv 5 -c4val; tla 0 ThetaObj; tla 2 Theta1; tla 3 Theta2; tla 4 Theta3; tla 5 Theta4; tla imsnbr ThetaIm; th 0 EntPupLoc; th 1 th[1]-EntPupLoc; if ( fabs(EntPupLoc)< 0.1 ) ray_aiming_mode set tel; else ray_aiming_mode set crr; draw_lens y; draw_default_rays(); SMDrawCenters(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= // d0 d1 d2 c1 c2 t1 t2 t3 t4 tobj timg m1 m2 double SM4examples[8][13]={ 1016.64, 1332.71, 1526.69, -8.022e-4, -1.624e-3, 6.784, 47.675, 12.407, -44.877, 26.121, -5.607, 4.0, 4.0, 955.07, 690.91, 419.01, -1.183e-3, 2.825e-3, 1.746, -19.560, 6.611, -10.640, -23.460, -4.847, 4.0, 4.0, 210.023, 380.41, 204.57, -3.418e-3, -3.359e-3, 21.767, 47.950, 41.385, 33.058, -7.469, -20.066, -4.0, 4.0, 188.29, 173.14, 191.92, -3.071e-3, 2.805e-3, 4.655, -12.711, 7.284, -10.291, -1.810, 0.393, -4.0, -4.0, 482.23, 370.04, 1367.41, -9.399e-4, 6.432e-4, 13.148, -19.638, 5.043, -5.265, 7.417, -0.061, -4.0, -4.0, 100.10, 125.61, 1999.99, -1.336e-3, 5.959e-6, 24.066, -70.117, -1.768, 11.640, 22.918, -0.107, -4.0, -4.0, 156.65, 363.27, 1020.01, -2.279e-3, 1.199e-3, 10.504, -10.697, 2.308, 8.129, 15.894, 0.731, -4.0, -4.0, 901.15, 831.18, 840.10, -6.659e-4, 6.549e-4, 3.023, 3.754, -6.340, 15.518, 15.762, -1.226, -4.0, -4.0, }; cmd SM4_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 1.0, 2000.0, Za[20] = SM4examples[slider_value-1][0]); graphwin_sliderreset(21, r, 1.0, 2000.0, Za[21] = SM4examples[slider_value-1][1]); graphwin_sliderreset(22, r, 1.0, 2000.0, Za[22] = SM4examples[slider_value-1][2]); graphwin_sliderreset(23, r, -2000.0, 2000.0, Za[23] = 1/SM4examples[slider_value-1][3]); graphwin_sliderreset(24, r, -2000.0, 2000.0, Za[24] = 1/SM4examples[slider_value-1][4]); graphwin_sliderreset(25, r, 1.0, 80.0, Za[25] = SM4examples[slider_value-1][5]); graphwin_sliderreset(26, r, -80.0, 80.0, Za[26] = SM4examples[slider_value-1][6]); graphwin_sliderreset(27, r, -80.0, 80.0, Za[27] = SM4examples[slider_value-1][7]); graphwin_sliderreset(28, r, -80.0, 80.0, Za[28] = SM4examples[slider_value-1][8]); graphwin_sliderreset(29, r, -40.0, 40.0, Za[29] = SM4examples[slider_value-1][9]); graphwin_sliderreset(30, r, -40.0, 40.0, Za[30] = SM4examples[slider_value-1][10]); graphwin_sliderreset(31, r, -10.0, 10.0, Za[31] = SM4examples[slider_value-1][11]); graphwin_sliderreset(32, r, -10.0, 10.0, Za[32] = SM4examples[slider_value-1][12]); graphwin_sliderreset(40, r, 0.01, 100.0, Za[40] = 10.0);// obj = 2 cm square graphwin_sliderreset(42, r, 0.1, 30.0, Za[42] = 5.0);//fnum = 5.0 -> nao = 0.1 SM4_chng(20, Za[20]); //initiate change } //======================================= //======================================= int SM_4(double d0val,double d1val,double d2val,double d3val,double d4val,double c1val,double c2val,double c3val,double c4val, double t1val,double t2val,double t3val,double t4val,double ThetaObj,double ThetaIm,double m1val,double m2val) { int ValidSys = 1; double cost1, sint1, cost2, sint2, cost3, sint3, cost4, sint4; t1val *= dr; //convert degrees to radians t2val *= dr; t3val *= dr; t4val *= dr; ThetaObj *= dr; ThetaIm *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); cost3 = cos(t3val); sint3 = sin(t3val); cost4 = cos(t4val); sint4 = sin(t4val); m1val = m1val*sec(ThetaObj)*cos(ThetaIm); //compensate for object and image tilts if ( (t4val==0) || (m1val==0) || (m2val==0) ) ValidSys = 0; else { c3val = cost3*(-2*c1val*cost2*d0val*(1 + 2*c2val*cost2*d1val)*m2val*pow(cost1,2) + 2*c1val*d0val*(cost2 + 2*c2val*d1val)*m1val*pow(cost4,2) + cost1*(-2*c2val*(d0val + d1val)*m2val*pow(cost2,2) + 2*c2val*(d0val + d1val)*m1val*pow(cost4,2) + cost2*(1 - m2val + (-1 + m1val)*pow(cost4,2))))* pow(2*cost1*cost2*(d1val + d2val + 2*c2val*cost2*d1val*d2val + d0val*(1 + 2*c2val*cost2*d2val + 2*c1val*cost1*(d1val + d2val + 2*c2val*cost2*d1val*d2val)))*m2val* pow(cost3,2) - 2*(cost1*cost2*(d0val + d1val) + cost1*(cost2 + 2*c2val*(d0val + d1val))*d2val + 2*c1val*d0val*(2*c2val*d1val*d2val + cost2*(d1val + d2val)))*m1val* pow(cost4,2),-1); d3val = -(pow(2*c1val*d0val*(2*c2val*d1val*(cost3 + 2*c3val*d2val) + cost2*(cost3 + 2*c3val*(d1val + d2val))) + cost1*(2*c2val*(d0val + d1val)*(cost3 + 2*c3val*d2val) + cost2*(cost3 + 2*c3val*(d0val + d1val + d2val))),-1)* pow(-1 + (1 + 2*c3val*cost3*(d0val + d1val + d2val) + 2*c2val*cost2*(d0val + d1val)*(1 + 2*c3val*cost3*d2val) + 2*c1val*cost1*d0val*(1 + 2*c3val*cost3*(d1val + d2val) + 2*c2val*cost2*d1val*(1 + 2*c3val*cost3*d2val)))*m2val,-1)*pow(sint4,-2)* (-(cost3*(cost1*cost2*(d0val + d1val) + cost1*(cost2 + 2*c2val*(d0val + d1val))*d2val + 2*c1val*d0val*(2*c2val*d1val*d2val + cost2*(d1val + d2val)))*pow(sint4,2)) + m2val*(2*(cost1 + 2*c1val*d0val)*(1 + 2*c1val*cost1*d0val)*(cost2*cost3*(c2val*cost2 + c3val*cost3) - (c3val*cost2 + c2val*cost3)*pow(cost4,2))*pow(d1val,2) + 2*c3val*(cost3 - cost4)*(cost3 + cost4)*(1 + 2*c2val*cost2*(d0val + d1val) + 2*c1val*cost1*d0val*(1 + 2*c2val*cost2*d1val))* (2*c1val*d0val*(cost2 + 2*c2val*d1val) + cost1*(cost2 + 2*c2val*(d0val + d1val)))*pow(d2val,2) + d0val*(2*d0val*(cost1*cost2*cost3*(c1val*cost1 + c2val*cost2 + c3val*cost3) - (c3val*cost1*cost2 + c2val*cost1*cost3 + c1val*cost2*cost3)*pow(cost4,2)) + cost1*cost2*cost3*pow(sint4,2)) + d1val*(cost1*cost2*cost3*pow(sint4,2) + 4*c1val*pow(d0val,2)*((1 + pow(cost1,2))*(cost2*cost3*(c2val*cost2 + c3val*cost3) - (c3val*cost2 + c2val*cost3)*pow(cost4,2)) + c1val*cost1*cost2*cost3*pow(sint4,2)) + 2*d0val*(2*cost1*cost2*cost3*(c2val*cost2 + c3val*cost3) - 2*cost1*(c3val*cost2 + c2val*cost3)*pow(cost4,2) + c1val*cost2*cost3*(1 + pow(cost1,2))*pow(sint4,2))) + d2val*(4*(cost3*(cost1*cost2*pow(c1val,2) + c1val*c3val*cost2*cost3*(1 + pow(cost1,2)) + c1val*c2val*(pow(cost1,2) + pow(cost2,2)) + c2val*cost1*(c2val*cost2 + c3val*cost3*(1 + pow(cost2,2)))) - ((c2val*cost1 + c1val*cost2)*(c1val*cost1 + c2val*cost2)*cost3 + c3val*(c1val*cost2*(1 + pow(cost1,2)) + c2val*cost1*(1 + pow(cost2,2))))*pow(cost4,2))* pow(d0val,2) + cost1*cost2*cost3*pow(sint4,2) + 4*c2val*(cost1 + 2*c1val*d0val)*(1 + 2*c1val*cost1*d0val)*pow(d1val,2)* (c3val*(cost3 - cost4)*(cost3 + cost4)*(1 + pow(cost2,2)) + c2val*cost2*cost3*pow(sint4,2)) - 2*d0val*(2*c3val*cost1*cost2*(-pow(cost3,2) + pow(cost4,2)) - c1val*cost2*cost3*(1 + pow(cost1,2))*pow(sint4,2) - c2val*cost1*cost3*(1 + pow(cost2,2))*pow(sint4,2)) + 2*d1val*(2*c3val*cost2*(cost3 - cost4)*(cost3 + cost4)*(cost1 + 2*c1val*d0val)*(1 + 2*c1val*cost1*d0val) + 4*cost2*cost3*d0val*pow(c2val,2)*(cost1 + c1val*d0val*(1 + pow(cost1,2)))*pow(sint4,2) + c2val*(1 + pow(cost2,2))*(cost1*cost3*pow(sint4,2) + 4*c1val*pow(d0val,2)*(c3val*(cost3 - cost4)*(cost3 + cost4)*(1 + pow(cost1,2)) + c1val*cost1*cost3*pow(sint4,2)) + 2*d0val*(2*c3val*cost1*(cost3 - cost4)*(cost3 + cost4) + c1val*cost3*(1 + pow(cost1,2))*pow(sint4,2)))))))); c4val = ((1 - (1 + 2*c3val*cost3*(d0val + d1val + d2val) + 2*c2val*cost2*(d0val + d1val)*(1 + 2*c3val*cost3*d2val) + 2*c1val*cost1*d0val*(1 + 2*c3val*cost3*(d1val + d2val) + 2*c2val*cost2*d1val*(1 + 2*c3val*cost3*d2val)))*m2val)*pow(cost4,-1)* pow(d1val + d2val + d3val + 2*c3val*cost3*(d1val + d2val)*d3val + 2*c2val*cost2*d1val*(d2val + d3val + 2*c3val*cost3*d2val*d3val) + d0val*(1 + 2*c2val*cost2*d2val + 2*(c2val*cost2 + c3val*cost3 + 2*c2val*c3val*cost2*cost3*d2val)*d3val + 2*c1val*cost1*(d1val + d2val + 2*c2val*cost2*d1val*d2val + d3val + 2*(c3val*cost3*(d1val + d2val) + c2val*cost2*d1val*(1 + 2*c3val*cost3*d2val))*d3val)),-1)* pow(m2val,-1))/2.; d4val = (-2*c1val*cost4*d0val*(cost2*cost3*(d1val + d2val) + cost2*(cost3 + 2*c3val*(d1val + d2val))*d3val + 2*c2val*d1val*(cost3*d2val + cost3*d3val + 2*c3val*d2val*d3val)) + cost1*cost4*(-(cost2*cost3*(d0val + d1val + d2val)) - cost2*(cost3 + 2*c3val*(d0val + d1val + d2val))*d3val - 2*c2val*(d0val + d1val)*(cost3*d2val + cost3*d3val + 2*c3val*d2val*d3val)))* pow(2*c1val*d0val*(2*c2val*d1val*(cost3*cost4 + 2*c4val*cost3*d2val + 2*c3val*cost4*d2val + 2*c4val*(cost3 + 2*c3val*d2val)*d3val) + cost2*(cost3*cost4 + 2*c4val*cost3*d1val + 2*c3val*cost4*d1val + 2*c4val*cost3*d2val + 2*c3val*cost4*d2val + 2*c4val*(cost3 + 2*c3val*(d1val + d2val))*d3val)) + cost1*(2*c2val*(d0val + d1val)*(cost3*cost4 + 2*c4val*cost3*d2val + 2*c3val*cost4*d2val + 2*c4val*(cost3 + 2*c3val*d2val)*d3val) + cost2*(cost3*cost4 + 2*c4val*cost3*d0val + 2*c3val*cost4*d0val + 2*c4val*cost3*d1val + 2*c3val*cost4*d1val + 2*c4val*cost3*d2val + 2*c3val*cost4*d2val + 2*c4val*(cost3 + 2*c3val*(d0val + d1val + d2val))*d3val)),-1); } // if (d3val<0) // ValidSys=0; return ValidSys; } // ======================================================================= // ======================================================================= // Prototypes cmd SM4INF_sldrs(); cmd SM4INF_chng(int slider_id, double slider_value); cmd SM4INF_example(int slider_id, double slider_value); int SM_4INF(double d1val,double d2val,double d3val,double d4val,double c1val,double c2val,double c3val,double c4val, double t1val,double t2val,double t3val,double t4val,double ThetaIm,double m1val,double m2val); // ======================================================================= // ======================================================================= cmd SM4INF_sldrs() { stp outp off; stp gacl off; stp noeb on; file_new SM4INF cus 5; lid "4 spherical mirror telescope"; SMStartup(); drw 0 off; graphwin_open(1); graphwin_reset(); graphwin_sliderassign(20, real, drag, "Mirror 1-2 Sep (d1)", "SM4INF_chng", 1, 200, Za[20] = 53.580); graphwin_sliderassign(21, real, drag, "Mirror 2-3 Sep (d2)", "SM4INF_chng", 1, 200, Za[21] = 83.589); graphwin_sliderassign(22, real, drag, "r1", "SM4INF_chng", -2000.0, 2000.0, Za[22] = 1/.002531); graphwin_sliderassign(23, real, drag, "r2", "SM4INF_chng", -2000.0, 2000.0, Za[23] = -1/.004585); graphwin_sliderassign(24, real, drag, "Theta 1", "SM4INF_chng", 1.0, 80.0, Za[24] = 11.88); graphwin_sliderassign(25, real, drag, "Theta 2", "SM4INF_chng", -80.0, 80.0, Za[25] = -6.402); graphwin_sliderassign(26, real, drag, "Theta 3", "SM4INF_chng", -80.0, 80.0, Za[26] = -10.501); graphwin_sliderassign(27, real, drag, "Theta 4", "SM4INF_chng", -80.0, 80.0, Za[27] = 22.955); graphwin_sliderassign(28, real, drag, "Theta Im", "SM4INF_chng", -80.0, 80.0, Za[28] = 22.955); graphwin_sliderassign(29, real, drag, "Foc Len Y (in plane)", "SM4INF_chng", -2000.0, 2000.0, Za[29] = 100.0); graphwin_sliderassign(30, real, drag, "Foc Len X (perp)", "SM4INF_chng", -2000.0, 2000.0, Za[30] = 100.0); graphwin_sliderassign(40, real, drag, "HFOV", "SM4INF_chng", .01, 5.0, Za[40] = 1.0); graphwin_sliderassign(41, real, drag, "Ent Pupil (0=INF)", "SM4INF_chng", -100.0, 100.0, Za[41] = 0.0); graphwin_sliderassign(42, real, drag, "Ent Beam Rad", "SM4INF_chng", 1.0, 100.0, Za[42] = 5.0); graphwin_sliderassign(70, int, drag, "Published Examples", "SM4INF_example", 1, 8, 8); graphwin_slidershow(); SM4INF_example(70,8); prt "Imaging with four spherical mirrors"; prt " Joseph M. Howard and Bryan D. Stone"; prt " Applied Optics, Vol. 39, No. 19, 3232-3242 (2000)."; stp outp on; stp gacl on; stp noeb off; } /**************************************************************************************/ /**************************************************************************************/ cmd SM4INF_chng(int slider_id, double slider_value) { stp outp off; stp gacl off; stp noeb on; double d1val, d2val, d3val, d4val, r1val, r2val, c3val, c4val, Theta1, Theta2, Theta3, Theta4, ThetaIm, f1val, f2val; double HFOV, EntPupLoc, EntranceBeamRadius; d1val = Za[20]; d2val = Za[21]; r1val = Za[22]; r2val = Za[23]; Theta1 = Za[24]; Theta2 = Za[25]; Theta3 = Za[26]; Theta4 = Za[27]; ThetaIm = Za[28]; f1val = Za[29]; f2val = Za[30]; HFOV = Za[40]; EntPupLoc = Za[41]; EntranceBeamRadius = Za[42]; if (slider_id == 20) Za[20] = d1val = slider_value; else if (slider_id == 21) Za[21] = d2val = slider_value; else if (slider_id == 22) Za[22] = r1val = slider_value; else if (slider_id == 23) Za[23] = r2val = slider_value; else if (slider_id == 24) Za[24] = Theta1 = slider_value; else if (slider_id == 25) Za[25] = Theta2 = slider_value; else if (slider_id == 26) Za[26] = Theta3 = slider_value; else if (slider_id == 27) Za[27] = Theta4 = slider_value; else if (slider_id == 28) Za[28] = ThetaIm = slider_value; else if (slider_id == 29) Za[29] = f1val = slider_value; else if (slider_id == 30) Za[30] = f2val = slider_value; else if (slider_id == 40) Za[40] = HFOV = slider_value; else if (slider_id == 41) Za[41] = EntPupLoc = slider_value; else if (slider_id == 42) Za[42] = EntranceBeamRadius = slider_value; graphwin_open(1); gclear(); if ( SM_4INF(d1val,d2val,&d3val,&d4val,1/r1val,1/r2val,&c3val,&c4val,Theta1,Theta2,Theta3,Theta4,ThetaIm,f1val,f2val) ) { th 2 -d1val; th 3 d2val; th 4 -d3val; th 5 d4val; cv 2 1/r1val; cv 3 -1/r2val; cv 4 c3val; cv 5 -c4val; tla 2 Theta1; tla 3 Theta2; tla 4 Theta3; tla 5 Theta4; tla imsnbr ThetaIm; ang HFOV; th 1 EntPupLoc; ebr EntranceBeamRadius; draw_lens y -th[2]; draw_default_rays(); SMDrawCenters(); SMmessage(); } else { message("Invalid System."); lorigin(4); langle(0); lsize(2.0); moveto(0.5, 0.5); label("Invalid System."); } stp outp on; stp gacl on; stp noeb off; } //============================================================= //============================================================= // d1 d2 c1 c2 t1 t2 t3 t4 timg m1 m2 double SM4INFexamples[8][11]={ 951.12, 378.89, -3.626e-4, 1.540e-3, 2.690, 15.427, -10.808, -4.853, 0.0, -1000.0, -1000.0, 363.18, 1791.67, 9.493e-5, -4.425e-4, 40.512, -12.151, -21.051, -14.423, 0.0, -1000.0, -1000.0, 1992.51, 391.63, -2.712e-4, -1.790e-3, 23.237, 51.389, 55.559, 31.040, 0.0, 1000.0, -1000.0, 606.39, 304.37, -5.062e-5, -6.203e-4, 26.711, 9.176, -35.294, 43.244, 0.0, 1000.0, 1000.0, 601.00, 496.79, -2.976e-4, 2.021e-4, 8.166, -18.360, -10.393, -5.973, 0.0, 1000.0, 1000.0, 693.08, 271.87, -3.534e-4, 3.131e-4, 13.107, -35.143, -34.221, -13.498, 0.0, 1000.0, 1000.0, 233.13, 295.41, -1.026e-4, 2.267e-4, 26.411, -24.102, 9.244, 8.433, 0.0, 1000.0, 1000.0, 535.80, 835.89, 2.531e-4, -4.585e-4, 11.880, -6.402, -10.501, 22.955, 0.0, 1000.0, 1000.0, }; cmd SM4INF_example(int slider_id, double slider_value) // Callback for examples { graphwin_sliderreset(20, r, 1.0, 2000.0, Za[20] = SM4INFexamples[slider_value-1][0]); graphwin_sliderreset(21, r, 1.0, 2000.0, Za[21] = SM4INFexamples[slider_value-1][1]); graphwin_sliderreset(22, r, -2000.0, 2000.0, Za[22] = 1/SM4INFexamples[slider_value-1][2]); graphwin_sliderreset(23, r, -2000.0, 2000.0, Za[23] = 1/SM4INFexamples[slider_value-1][3]); graphwin_sliderreset(24, r, 1.0, 80.0, Za[24] = SM4INFexamples[slider_value-1][4]); graphwin_sliderreset(25, r, -80.0, 80.0, Za[25] = SM4INFexamples[slider_value-1][5]); graphwin_sliderreset(26, r, -80.0, 80.0, Za[26] = SM4INFexamples[slider_value-1][6]); graphwin_sliderreset(27, r, -80.0, 80.0, Za[27] = SM4INFexamples[slider_value-1][7]); graphwin_sliderreset(28, r, -40.0, 40.0, Za[28] = SM4INFexamples[slider_value-1][8]); graphwin_sliderreset(29, r, -1000.0, 1000.0, Za[29] = SM4INFexamples[slider_value-1][9]); graphwin_sliderreset(30, r, -1000.0, 1000.0, Za[30] = SM4INFexamples[slider_value-1][10]); graphwin_sliderreset(40, r, 0.01, 5.0, Za[40] = 1.0);// HFOV = 1.0 degree graphwin_sliderreset(42, r, 1.0, 100.0, Za[42] = 50.0);//EBR = 50.0 SM4INF_chng(20, Za[20]); //initiate change } int SM_4INF(double d1val,double d2val,double d3val,double d4val,double c1val,double c2val,double c3val,double c4val, double t1val,double t2val,double t3val,double t4val,double ThetaIm,double m1val,double m2val) { int ValidSys = 1; double cost1, sint1, cost2, sint2, cost3, sint3, cost4, sint4; t1val *= dr; //convert degrees to radians t2val *= dr; t3val *= dr; t4val *= dr; cost1 = cos(t1val); sint1 = sin(t1val); cost2 = cos(t2val); sint2 = sin(t2val); cost3 = cos(t3val); sint3 = sin(t3val); cost4 = cos(t4val); sint4 = sin(t4val); if ( (t4val==0) || (m2val==0) ) ValidSys = 0; else { c3val = cost3*(-2*c1val*cost2*(1 + 2*c2val*cost2*d1val)*m2val*pow(cost1,2) + 2*c1val*(cost2 + 2*c2val*d1val)*m1val*pow(cost4,2) + cost1*(-2*c2val*m2val*pow(cost2,2) + 2*c2val*m1val*pow(cost4,2) - cost2*pow(sint4,2)))* pow(2*cost1*cost2*(1 + 2*c2val*cost2*d2val + 2*c1val*cost1*(d1val + d2val + 2*c2val*cost2*d1val*d2val))*m2val*pow(cost3,2) - 2*(cost1*(cost2 + 2*c2val*d2val) + 2*c1val*(2*c2val*d1val*d2val + cost2*(d1val + d2val)))*m1val*pow(cost4,2),-1); d3val = -(pow(c3val*cost2*(cost1 + 2*c1val*d1val) + cost3*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val)) + 2*c3val*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val))*d2val, -1)*pow(1 + 2*(c3val*cost3 + c2val*(cost2 + 2*c3val*cost2*cost3*d2val) + c1val*cost1*(1 + 2*c3val*cost3*(d1val + d2val) + 2*c2val*cost2*d1val*(1 + 2*c3val*cost3*d2val)))*m2val,-1)*pow(sint4,-2)* (cost3*(cost1*(cost2 + 2*c2val*d2val) + 2*c1val*(2*c2val*d1val*d2val + cost2*(d1val + d2val)))*pow(sint4,2) + 2*m2val*(cost1*(c2val*cost3*(cost2 - cost4)*(cost2 + cost4) + c3val*cost2*(cost3 - cost4)*(cost3 + cost4) + 2*c2val*c3val*(cost3 - cost4)*(cost3 + cost4)*d2val*(1 + pow(cost2,2)) + 2*cost2*d2val*pow(c2val,2)*(cost3 + 2*c3val*d2val*pow(cost3,2) - cost3*pow(cost4,2) - 2*c3val*d2val*pow(cost4,2))) + c1val*(cost2*cost3*pow(cost1,2) + 2*c2val*cost3*d1val*pow(cost2,2) + 2*c2val*cost3*d1val*pow(cost1,2)*pow(cost2,2) + 2*c3val*cost2*d1val*pow(cost3,2) + 2*c3val*cost2*d1val*pow(cost1,2)*pow(cost3,2) - cost2*cost3*pow(cost4,2) - 2*c3val*cost2*d1val*pow(cost4,2) - 2*c2val*cost3*d1val*pow(cost4,2) - 2*c3val*cost2*d1val*pow(cost1,2)*pow(cost4,2) - 2*c2val*cost3*d1val*pow(cost1,2)*pow(cost4,2) + 4*c2val*c3val*(cost3 - cost4)*(cost3 + cost4)* (pow(cost1,2) + 2*c2val*cost2*d1val*(1 + pow(cost1,2)) + pow(cost2,2))*pow(d2val,2) + 2*d2val*(c3val*cost2*(cost3 - cost4)*(cost3 + cost4)*(1 + pow(cost1,2)) + 2*c2val*c3val*(cost3 - cost4)*(cost3 + cost4)*d1val*(1 + pow(cost1,2))*(1 + pow(cost2,2)) + 2*cost2*cost3*d1val*pow(c2val,2)*(1 + pow(cost1,2))*pow(sint4,2) + c2val*cost3*(pow(cost1,2) + pow(cost2,2))*pow(sint4,2))) + 2*cost1*pow(c1val,2)*(2*c3val*(cost3 - cost4)*(cost3 + cost4)*(cost2 + 2*c2val*d1val)*(1 + 2*c2val*cost2*d1val)*pow(d2val,2) + d1val*(2*d1val*(cost2*cost3*(c2val*cost2 + c3val*cost3) - (c3val*cost2 + c2val*cost3)*pow(cost4,2)) + cost2*cost3*pow(sint4,2)) + d2val*(cost2*cost3*pow(sint4,2) + 4*c2val*pow(d1val,2)* (c3val*(cost3 - cost4)*(cost3 + cost4)*(1 + pow(cost2,2)) + c2val*cost2*cost3*pow(sint4,2)) + 2*d1val*(2*c3val*cost2*(cost3 - cost4)*(cost3 + cost4) + c2val*cost3*(1 + pow(cost2,2))*pow(sint4,2)))))))/2.; c4val = -((1 + 2*(c3val*cost3 + c2val*(cost2 + 2*c3val*cost2*cost3*d2val) + c1val*cost1*(1 + 2*c3val*cost3*(d1val + d2val) + 2*c2val*cost2*d1val*(1 + 2*c3val*cost3*d2val)))*m2val)*pow(cost4,-1)* pow(1 + 2*c3val*cost3*d3val + 2*c2val*cost2*(d2val + d3val + 2*c3val*cost3*d2val*d3val) + 2*c1val*cost1*(d2val + d3val + 2*c3val*cost3*d2val*d3val + d1val*(1 + 2*c3val*cost3*d3val + 2*c2val*cost2*(d2val + d3val + 2*c3val*cost3*d2val*d3val))),-1)*pow(m2val,-1))/2.; d4val = -((cost1*cost4*(cost2*(cost3 + 2*c3val*d3val) + 2*c2val*(cost3*d2val + cost3*d3val + 2*c3val*d2val*d3val)) + 2*c1val*cost4*(cost2*cost3*(d1val + d2val) + cost2*(cost3 + 2*c3val*(d1val + d2val))*d3val + 2*c2val*d1val*(cost3*d2val + cost3*d3val + 2*c3val*d2val*d3val)))* pow(cost4*(c3val*cost2*(cost1 + 2*c1val*d1val) + cost3*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val)) + 2*c3val*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val))*d2val) + c4val*cost3*(cost1*(cost2 + 2*c2val*d2val) + 2*c1val*(2*c2val*d1val*d2val + cost2*(d1val + d2val))) + 2*c4val*(c3val*cost2*(cost1 + 2*c1val*d1val) + cost3*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val)) + 2*c3val*(c1val*cost2 + c2val*(cost1 + 2*c1val*d1val))*d2val)*d3val,-1))/2.; } // if ( (d3val<0) ) // ValidSys = 0; return ValidSys; }