00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 
00034 PKG = "pr2_camera_synchronizer"
00035 import roslib; roslib.load_manifest(PKG)
00036 from pr2_camera_synchronizer.synchronizer_classes import *
00037 import unittest
00038 import pr2_camera_synchronizer.cfg.CameraSynchronizerConfig as Config
00039                              
00040 DIGITS = 16
00041 
00042 def issorted(l):
00043     copy = list(l)
00044     copy.sort()
00045     return copy == l
00046 
00047 def interlace(l1, l2):
00048     l = zip(l1, l2)
00049     return list(sum(l, ()))
00050 
00051 class TestProjector(unittest.TestCase):
00052     def runCase(self, rate, length, shift, out_repeat_period, out_proj_end, out_alt_end, out_noproj_end, level = lvl_projector):
00053         config = { 
00054                 param_proj_rate : rate,  
00055                 "projector_pulse_length" : length,
00056                 "projector_pulse_shift" : shift,
00057                 "projector_tweak" : 0,
00058                 "projector_mode" : Config.CameraSynchronizer_ProjectorOn,
00059                 }
00060         proj = Projector()
00061         proj.process_update(config, level)
00062 
00063         if level & lvl_projector != 0:
00064             self.assert_(math.fmod(config["projector_rate"], ETHERCAT_INTERVAL)) 
00065             self.assert_(config["projector_pulse_length"] >= length, "Pulse length %f"%config["projector_pulse_length"]) 
00066             self.assertEqual(config["projector_pulse_length"], proj.pulse_length) 
00067             self.assert_(math.fmod(proj.pulse_length, ETHERCAT_INTERVAL) == 0, "Pulse length %f"%proj.pulse_length) 
00068             self.assertEqual(len(proj.pulse_ends), 4) 
00069             self.assertEqual(len(proj.pulse_starts), 4) 
00070             self.assert_(issorted(interlace(proj.pulse_starts, proj.pulse_ends))) 
00071             self.assertEqual(4. / proj.repeat_period, config["projector_rate"]) 
00072 
00073         self.assertEqual(out_repeat_period, proj.repeat_period) 
00074         self.assertEqual(out_proj_end, proj.proj_end_offset)
00075         self.assertEqual(out_noproj_end, proj.noproj_end_offset)
00076         self.assertAlmostEqual(out_alt_end, proj.alt_end_offset, DIGITS)
00077 
00078         return proj, config
00079 
00080     def testBasicFunctionality(self):
00081         proj,config = self.runCase(30, 0.002, 0,   0.132, 0.003, 0.036, 0.032)
00082 
00083 class TestCamera(unittest.TestCase):
00084   def runCase(self, proj_rate, proj_length, proj_shift, rate, trig_mode, out_period, out_ext_trig, out_imager_period, out_end_offset, level = 1, reset_camera = False):
00085       paramnames = dict((name,name) for name in camera_parameters)
00086       config = {
00087               param_proj_rate : proj_rate,  
00088               "projector_pulse_length" : proj_length,
00089               "projector_pulse_shift" : proj_shift,
00090               "projector_tweak" : 0,
00091               "projector_mode" : Config.CameraSynchronizer_ProjectorOn,
00092               param_rate : rate,
00093               param_trig_mode : trig_mode,
00094               "camera_reset" : reset_camera,
00095               }
00096 
00097       proj = Projector()
00098       proj.process_update(config, lvl_projector)
00099       camera = Camera("test_cam", proj, 1, **paramnames)
00100       camera.process_update(config, level)
00101 
00102       if level & 1 == 0:
00103           self.assert_(math.fmod(camera.period, ETHERCAT_INTERVAL) == 0) 
00104           self.assertEqual(config[param_rate], 1. / camera.period) 
00105       
00106       self.assert_(out_period > 0, "Period %f"%out_period) 
00107       self.assertAlmostEqual(camera.period, out_period, DIGITS) 
00108       self.assertEqual(camera.ext_trig, out_ext_trig) 
00109       self.assert_(out_imager_period > 0, "Imager period %f"%out_imager_period) 
00110       self.assertAlmostEqual(camera.imager_period, out_imager_period, DIGITS) 
00111       self.assertAlmostEqual(camera.end_offset, out_end_offset, DIGITS) 
00112 
00113       return camera, proj, config
00114 
00115   def testBasicAlwaysProj(self): 
00116       self.runCase(60, 0.001, 0,   30, Config.CameraSynchronizer_WithProjector,      0.034,  True,  0.033, 0.002) 
00117   def testBasicAlternateProj(self):
00118       self.runCase(60, 0.001, 0,   30, Config.CameraSynchronizer_AlternateProjector, 0.034,  True,  0.033, 0.019) 
00119   def testBasicNoProj(self):
00120       self.runCase(60, 0.001, 0,   30, Config.CameraSynchronizer_WithoutProjector,   0.034,  True,  0.033, 0.016) 
00121   def testBasicFreeRun(self):
00122       self.runCase(60, 0.001, 0,   30, Config.CameraSynchronizer_InternalTrigger,   1/30.0, False, 1/30.0,    -1) 
00123 
00124 if __name__ == '__main__':
00125     import rostest
00126     import rospy
00127     import time
00128 
00129     
00130     rospy.get_time = time.time
00131     
00132     rostest.rosrun(PKG, 'test_projector', TestProjector)
00133     rostest.rosrun(PKG, 'test_camera', TestCamera)
00134     killAsynchronousUpdaters()