esrf

Beamline Instrument Software Support
SPEC Macro documentation: [ Macro Index | BCU Home ]

#%TITLE% centrebeam.mac
#%NAME%
#  Finds beam center (MX beamlines)
#
#%CATEGORY% MX
#
#%DESCRIPTION%
#
#%LOG%
#   $Revision: 1.30 $
#
#   $Log: centrebeam.mac,v $
#   Revision 1.30  2011/04/04 14:46:35  guijarro
#   added call to get zoom factor when using microdiff
#
#   Revision 1.29  2011/04/01 08:33:20  guijarro
#   _get_zoom also sets CB_ZOOMFACTOR global variable, to be able to call _set_zoom properly (it is expecting a factor, not a pos.)
#
#   Revision 1.28  2010/11/02 15:22:47  beteva
#   added _get_zoom(), changed dummy_defs() due to changes in SPEC.
#
#   Revision 1.27  2009/10/29 14:13:32  beteva
#   Remove backstop before centring. Count if needed (CB_COUNT != 0)
#
#   Revision 1.26  2009/09/02 15:04:20  guijarro
#   added CB_DONTCLOSESHUTTERS flag to allow macro to be used from another macro without too much time penalty
#
#   Revision 1.25  2009/04/06 15:29:56  guijarro
#   added possibility to use current transmission for centrebeam, if CB_INIT_TRANSMISSION is <0
#
#   Revision 1.24  2009/03/04 15:55:12  guijarro
#   fixed missing \'{}\'
#
#   Revision 1.23  2009/02/24 14:52:16  beteva
#   added more dummy definitions. CB_SCINT - if nonzero, do not move the scintilator. Added sleep 10s to give time to see the beam. Changed the order of opening/closing the ms shutter.
#
#   Revision 1.22  2009/02/12 15:58:22  beteva
#   added dummy_defs() to prevent errors if microdiff not used
#
#   Revision 1.21  2009/02/10 13:12:11  beteva
#   made complient with the microdiff
#
#   Revision 1.20  2008/10/22 15:30:17  blissadm
#   allow to specify a zoom level for doing centrebeam, instead
#   of chosing a default one: to be done in setup, CB_NOAUTOZOOM=1
#   and CB_ZOOM={0..5}
#
#   Revision 1.19  2008/07/01 07:33:30  blissadm
#   do not open/close shutters anymore, do not sleep for nothing
#   put back front light on at the end (if was on before)
#   syntax error fixed
#
#   Revision 1.18  2008/06/27 15:26:44  spruce
#   if not within tolerence do not quit without making the first move, at least move once. Also report to mxCuBE if not within tolerance.
#
#   Revision 1.17  2008/06/23 11:21:03  guijarro
#   added light2off command to make sure front light is switched off
#
#   Revision 1.16  2008/06/13 13:07:20  rey
#   Add option in centrebeam macro to move the camera zoom or not
#   by default is as previously... it uses the zoom.
#
#   Revision 1.15  2008/02/27 13:24:38  rey
#   documentation changes
#
#Revision 1.14  2008/02/22 10:23:30  gabadinh
#minor bug fix: puts back the beam to the original position if CTRL-C is pressed
#
#Revision 1.13  2007/07/18 12:18:47  spruce
#fixes and tests of previous changes
#
#Revision 1.12  2007/07/11 11:14:16  guijarro
#removed unnecessary reading of X1,Y1,X2,Y2 in zoom xml file
#
#Revision 1.11  2007/07/10 09:15:41  spruce
#check that total movement is not outside range of view
#
#Revision 1.10  2007/07/09 06:24:00  guijarro
#added check for beam presence by checking X and Y beam pos. ;
#do not close frontend in cleanup
#
#Revision 1.9  2007/03/30 15:26:09  spruce
#do not close shutters if retruning to start position.
#Do not move too far away from the current position.
#
#Revision 1.8  2006/12/14 16:31:57  guijarro
#added 'CB_DONTMOVESLITS' global flag ; if set to 1, slits won't move
#
#Revision 1.7  2006/09/15 15:15:09  guijarro
#first tries to centre beam with current attenuation,
#then if it fails it tries with init. att. specified in setup
#
#Revision 1.6  2006/01/24 15:55:35  beteva
#bug fixed, move_poll added
#
#Revision 1.5  2005/12/02 17:56:26  guijarro
#added initial transmission, tolerance and number of iteration parameters
#replaced 'input' by 'getval' in setup
#a unique name has been given to global variables
#
#Revision 1.4  2005/11/09 10:18:25  beteva
#changed prodc_*_safety_shutter to sh*
#
#Revision 1.3  2005/09/19 16:10:29  beteva
#Bugs fixed. Split initialization of slit & table motors and zoom & camera.
#Added prints to the cleanup.
#
#Revision 1.2  2005/09/13 06:54:11  guijarro
#changes to make it even more general. Tested on ID23-2.
#
#Revision 1.1  2005/07/13 14:37:33  beteva
#Initial revision
#
#%END%

#%UU%
#%MDESC%
def centrebeam_setup '{
global CB_ZOOMPOS CB_DEFAULTZOOM CB_PIXELSPERMMY CB_PIXELSPERMMZ CB_FRAMEGRABBER_DEVICE CB_DONTCLOSESHUTTERS
global CB_WIDTH CB_HEIGHT
global CB_ZOOMMOT CB_CENTRE_OK
global CB_TABLE_Y_COEF CB_TABLE_Z_COEF CB_SLITBOX_Y_COEF CB_SLITBOX_Z_COEF
global CB_INITSTATE[]
global CB_INIT_TRANSMISSION
global CB_ITERATIONS
global CB_TOLERANCE
global CB_ZOOM_HO CB_CAMERA_HO CB_SLITBOX_HO CB_EXPTABLE_HO
global CB_DONTMOVESLITS
global CB_NOAUTOZOOM
global CB_ZOOM CB_UDIFF CB_SCINT CB_COUNT
global CB_MACROS
global CB_ZOOMFACTOR
local nbpars pars i

  CB_CENTRE_OK = 0

  nbpars = split("$*", pars)
  if (nbpars > 0) {
    i = 0
    if (isdigit(pars[i]) == 0) {
      CB_UDIFF = 1
      i = 1
    } else {
      dummy_defs()
    }
    CB_ZOOM_HO = pars[i]
    CB_CAMERA_HO = pars[i+1]
    CB_SLITBOX_HO = pars[i+2]
    CB_EXPTABLE_HO = pars[i+3]
    CB_TABLE_Y_COEF = pars[i+4]
    CB_TABLE_Z_COEF = pars[i+5]
    CB_SLITBOX_Y_COEF = pars[i+6]
    CB_SLITBOX_Z_COEF = pars[i+7]
    CB_INIT_TRANSMISSION = pars[i+8]
    CB_TOLERANCE = pars[i+9]
    CB_ITERATIONS = pars[i+10]
  } else {
    CB_UDIFF = yesno("Are you using the microdiff?",0)
    CB_ZOOM_HO = \
	getval("Zoom motor hardware object(e.g. /motors/zoom or none): ",\
				CB_ZOOM_HO)
    CB_CAMERA_HO = getval("Camera hardware object (e.g. /ccd/falcon): ",\
				CB_CAMERA_HO)
    CB_SLITBOX_HO = getval("Slitbox hardware object (e.g. /slitbox): ",\
				CB_SLITBOX_HO)
    CB_EXPTABLE_HO = getval("Exp. table hardware object (e.g. /exptable): ",\
				CB_EXPTABLE_HO)
    CB_TABLE_Y_COEF = getval("Table horizontal movement coef.(1 or -1): ",\
				CB_TABLE_Y_COEF)
    CB_TABLE_Z_COEF = getval("Table vertical movement coef.(1 or -1): ",\
				CB_TABLE_Z_COEF)
    CB_SLITBOX_Y_COEF = getval("Slitbox vertical movement coef.(1 or -1): ",\
				CB_SLITBOX_Y_COEF)
    CB_SLITBOX_Z_COEF = getval("Slitbox horizontal movement coef.(1 or -1): ",\
				CB_SLITBOX_Z_COEF)
    CB_INIT_TRANSMISSION = getval("Initial transmission (default is 100): ",\
				CB_INIT_TRANSMISSION)
    CB_TOLERANCE = getval("Tolerance (default is 0.001): ", CB_TOLERANCE)
    CB_ITERATIONS = \
      getval("Number of iterations (default is -1, meaning \'automatic\'): ",\
				CB_ITERATIONS)
  }

  if (CB_TABLE_Y_COEF == 0)
    CB_TABLE_Y_COEF = 1
  if (CB_TABLE_Z_COEF == 0)
    CB_TABLE_Z_COEF = 1
  if (CB_SLITBOX_Y_COEF == 0)
    CB_SLITBOX_Y_COEF = 1
  if (CB_SLITBOX_Z_COEF == 0)
    CB_SLITBOX_Z_COEF = 1
  if (CB_INIT_TRANSMISSION == 0)
    CB_INIT_TRANSMISSION = 100
  if (CB_TOLERANCE == 0)
     CB_TOLERANCE = 0.001
  if (CB_ITERATIONS == 0)
     CB_ITERATIONS = -1

  if ((CB_CENTRE_OK = _init_zoom(CB_ZOOM_HO, CB_CAMERA_HO)) == -1)
    exit
  if ((CB_CENTRE_OK = _get_tab_slits(CB_SLITBOX_HO, CB_EXPTABLE_HO)) == -1)
    exit
}'

#%UU%
#%MDESC% Find the centre of the beam as function of the transmition factor.
#Start with 100 percent and divide by two until only one beam found. Take the
#backlight out and choose average zoom factor.
def centrebeam '{
  if (CB_CENTRE_OK)
    exit
  if (centrebeam_savstat() == -1)
    exit
  cdef("cleanup_once",";centrebeam_cleanup();","_centrebeam_")

  centrebeam_prepare()

  msopen
  #transmission 100
  #tcount(0.1); waitcount; getcounts
  #p S[i0]
  #transmission CB_INITSTATE[7]
  # do the work
  if (CB_INIT_TRANSMISSION==0)
    CB_INIT_TRANSMISSION = CB_INITSTATE[7]
  CB_CENTRE_OK = _centrebeam(CB_INIT_TRANSMISSION)
  if (CB_CENTRE_OK < 0) {
    if (CB_INIT_TRANSMISSION == 100) {
      centrebeam_cleanup()
    } else {
      printf ("Going for the second run with transmission 100\n")
      CB_CENTRE_OK = 0
      CB_CENTRE_OK = _centrebeam(100)
      if (CB_CENTRE_OK < 0) centrebeam_cleanup()
    }
  } else {
    #now wait to see the beam 
    if (CB_DONTCLOSESHUTTERS==0) { sleep(5) }
    centrebeam_accept()
  }
}'

#%IU% (trans)
#%MDESC% Find the centre of the beam as function of the transmition factor.
#Divide the factor by two until only one beam found.
def _centrebeam(trans) '{
local nspots beamZ beamY dy dz fout iteration totalY totalZ

  if (CB_CENTRE_OK)
    return(-1)
  # set attenuation (if required)
  if (CB_INIT_TRANSMISSION>0) {
    printf ("Setting transmission to %g\n", trans)
    transmission trans
  }

  totalY=0; totalZ=0
  iteration = 0

  while (1) {
    # get beam centre
    esrf_io(CB_FRAMEGRABBER_DEVICE, "DevReadValues", fout)
    nspots = fout[0]
    if (nspots > 1) {
      eprintf ("Cannot centre beam: found more than one spot!\n")

      if (trans < 6) {
        eprintf ("Giving up, transmission factor is %g\n", trans)
        CB_CENTRE_OK = -1
        return(-1)
      }

      printf ("Trying to centre with transmission factor set to %g\n", trans/2)
      return (_centrebeam(trans/2))
    } else if (nspots == 0) {
      eprintf ("Cannot centre beam: no spot found!\n")
      CB_CENTRE_OK = -1
      return(-1)
    }
    beamY = fout[2]
    beamZ = fout[3]
    print "Found 1 spot at " beamY " " beamZ
    if ((beamY < 0) || (beamZ < 0)) {
      eprintf ("Cannot centre beam: no spot found!\n")
      CB_CENTRE_OK = -1
      return(-1)
    }

    # compute positions in millimeters
    # 1. get beamY(Z) from centre instead of upper left corner,
    # 2. then multiply by CB_PIXELSPERMMY(Z)
    # Y: horizontal
    # Z: vertical
    dy = (beamY - (CB_WIDTH / 2)) / CB_PIXELSPERMMY
    dz = (beamZ - (CB_HEIGHT / 2)) / CB_PIXELSPERMMZ

    # add up the movement so far
    totalY = totalY + (beamY-(CB_WIDTH/2))
    totalZ = totalZ + (beamZ-(CB_HEIGHT/2))
    # do not move at all if we the value returned is outside the bounds of the window
    if ((totalY -(CB_WIDTH/2))  > (CB_WIDTH/2) || beamY < 0) {
      print "Horizontal movement will put beam outside the window, aborting..."  totalY
      dy = 0
      return (0)
    } else {
      print "Horizontal translation = " dy
    }
    if ((totalZ - (CB_HEIGHT/2)) > (CB_HEIGHT/2) || beamZ < 0) {
      print "Vertical movement will put beam outside the window, aborting..."  totalY
      dz = 0
      return (0)
    } else {
      print "Vertical translation = " dz
    }
    
    print "Please wait while moving the experimental table and the slits..."
    _mv_tab_slits(dy,dz)

    if ((fabs(dy) < CB_TOLERANCE) && (fabs(dz) < CB_TOLERANCE)) {
      printf ("Done.\n\n")
      return(0)
    }

    if (CB_ITERATIONS > 0) {
      iteration++
      if (iteration >= CB_ITERATIONS) {
        msg = "Sorry, I could not get within the tolerance, resetting to original position.\n\n"
	      print msg
        egui_logmsg(msg)
        centrebeam_cleanup()
        return(0)
      }
    }
    dyPrevious = beamY
    dzPrevious = beamZ
  }

  if (CB_INITSTATE[9] == "IN")
    lightin

  if ( CB_INITSTATE[10] == "ON")
    flighton()
  return(0)
}'

#%IU% (ho, path)
#%MDESC% Read the parameters from the hardware object XML file%B%ho%B%, found
#in directory %B%path%B%. Return 0 if OK, -1 if error.
def _cb_xml_read(ho,path) '{
  xml_read(ho, path)
  if ("__error__" in XML_tmp) {
    eprintf ("Error reading from the XML file\n") 
    return(-1)
  }
  return (0)
}'

#%IU% ()
#%MDESC% Read the zoomfactor and calculate the X and Y pixel/mm values.
#Return 0 if OK , -1 if error.
def _get_zoom() '{
global CB_ZOOMFACTOR CB_ZOOMPOS
local calpars[] delta zoompos
  get_angles
  zoompos = A[CB_ZOOMMOT]
  if (CB_UDIFF == 0) {
    _cb_xml_read(CB_ZOOM_HO, "/device/delta")
    delta = XML_tmp[0]["__value__"]
    if (_cb_xml_read(CB_ZOOM_HO, "/device/positions/position/offset") == -1)
      return (-1)

    CB_ZOOMFACTOR=-1
    CB_ZOOMPOS=-1
    local tmp[]
    tmp = asso_keys(XML_tmp)
    for (i in tmp) {
      if (fabs(XML_tmp[i]["__value__"] - zoompos)<=delta) {
        CB_ZOOMPOS = XML_tmp[i]["__value__"]
        CB_ZOOMFACTOR=i
        break
      }
    }

    #get the calibration data for this position
    if (_cb_xml_read(CB_ZOOM_HO, \
	"/device/positions/position/calibrationData/pixelsPerMmY")== -1)
      return (-1)
    CB_PIXELSPERMMY = XML_tmp[zoomfactor]["__value__"]

    if (_cb_xml_read(CB_ZOOM_HO, \
	"/device/positions/position/calibrationData/pixelsPerMmZ")== -1)
      return(-1)
    CB_PIXELSPERMMZ = XML_tmp[zoomfactor]["__value__"]
  } else {
   if (get_cameracalib(calpars) < 0)
      return(-1)

    CB_PIXELSPERMMY = calpars["x"]
    CB_PIXELSPERMMZ = calpars["y"]

    CB_ZOOMFACTOR = tango_get(MICRODIFF_DEVICE, "ZoomPredefinedPosition")
  }
  return(0)
}'


#%IU% (zoomfactor)
#%MDESC% Move the zoom to the %B%zoomfactor%B% position. Read the Y and Z
#pixel/mm values.
def _set_zoom(zoomfactor) '{
local calpars[]

  if (CB_UDIFF == 0) {
    if (_cb_xml_read(CB_ZOOM_HO, "/device/positions/position/offset") == -1)
      return (-1)
    CB_ZOOMPOS = XML_tmp[zoomfactor]["__value__"]

    #get the calibration data for this position
    if (_cb_xml_read(CB_ZOOM_HO, \
	"/device/positions/position/calibrationData/pixelsPerMmY")== -1)
      return (-1)
    CB_PIXELSPERMMY = XML_tmp[zoomfactor]["__value__"]

    if (_cb_xml_read(CB_ZOOM_HO, \
	"/device/positions/position/calibrationData/pixelsPerMmZ")== -1)
      return(-1)
    CB_PIXELSPERMMZ = XML_tmp[zoomfactor]["__value__"]

    if (fabs(A[CB_ZOOMMOT]-CB_ZOOMPOS)>1) {
      A[CB_ZOOMMOT] = CB_ZOOMPOS
      move_em; move_poll; get_angles
    }
  } else {
    A[CB_ZOOMMOT] = zoomfactor
    move_em; move_poll; get_angles

    if (wait_ready() < 0)
      return(-1)

    if (get_cameracalib(calpars) < 0)
      return(-1)

    CB_PIXELSPERMMY = calpars["x"]
    CB_PIXELSPERMMZ = calpars["y"]
  }
  return(0)
  
}'

#%UU% (zoomHo, cameraHo)
#%MDESC% Get the %B%zoomMne%B% average zoom factor, the X and Y pixel/mm
#values, the frame grabber device and the image width and height.
def _init_zoom(zoomHo, cameraHo) '{
local zoomFactor zoomMax zoomPos
local lpath[] type

  if (CB_CENTRE_OK)
    return(-1)

  if (CB_UDIFF == 0) {
    lpath[0] = "/device/specname"
    lpath[1] = "/device/positions/position/offset"
  } else {
    lpath[0] = "/device/username"
    lpath[1] = "/device/position"
  }
  #get the zoom motor
  if (_cb_xml_read(zoomHo, lpath[0]) == -1 ) {
    return (-1)
  } else {
    zoomMne = XML_tmp[0]["__value__"]
    CB_ZOOMMOT = motor_num(zoomMne)
    if (CB_ZOOMMOT == -1) {
      eprintf ("%s - wrong motor mnemonic, check your zoom XML file or SPEC configuration\n", zoomMne)
      return(-1)
    }
  }

  type = motor_par(CB_ZOOMMOT, "controller")
  
  #get predefined zoom position
  if (_cb_xml_read(zoomHo, lpath[1]) == -1) {
    if (type == "PSE_MAC_MOT") {
      #find a medium zoom level
      zoomMax = int(get_lim(CB_ZOOMMOT,1))
      CB_DEFAULTZOOM = int(zoomMax/2)
    } else
      return(-1)
  } else {
    if (type == "PSE_MAC_MOT")
      CB_DEFAULTZOOM = XML_tmp[0]["__value__"]
    else {
      #find a medium zoom level
      zoomMax = asso_len(XML_tmp)
      CB_DEFAULTZOOM = int((zoomMax-1)/2)
    }
  }
  #get the framegrabber device server name
  if (_cb_xml_read(cameraHo, "/device/taconame")== -1 ) {
    return(-1)
  }
  CB_FRAMEGRABBER_DEVICE = XML_tmp[0]["__value__"]

  #get the framegrabber image size
  if ((CB_WIDTH = esrf_io(CB_FRAMEGRABBER_DEVICE, "DevCcdXSize")) < 0)
    return(-1)
  if ((CB_HEIGHT = esrf_io(CB_FRAMEGRABBER_DEVICE, "DevCcdYSize")) < 0)
    return(-1)
  return(0)
	
}'

#%IU% (slitboxHo,exptableHo)
#%MDESC% Get the slitbox vertical and horizontal motor names, as well as the
#experimental table translation and height motors.
def _get_tab_slits(sslitboxHo, exptableHo) '{
global CB_SB_MNE[] CB_SB_MOT[]
global CB_ET_MNE[] CB_ET_MOT[]
local mmne _motors[]

  #get the slitbox motors
  _motors = xml_readMotorsByRoles(sslitboxHo)

  if (! (("t1v" in _motors)&&("t2v" in _motors) \
        &&("t1h" in _motors)&&("t2h" in _motors))) {
    eprintf("Missing motors in slitbox hardware object or Spec config.\n")
    return (-1)
  } else {
    CB_SB_MNE["t1h"] = _motors["t1h"]
    CB_SB_MNE["t1v"] = _motors["t1v"]
    CB_SB_MNE["t2h"] = _motors["t2h"]
    CB_SB_MNE["t2v"] = _motors["t2v"]

    for (mmne in CB_SB_MNE) {
      CB_SB_MOT[mmne]=motor_num(CB_SB_MNE[mmne])
      if (CB_SB_MOT[mmne] == -1) {
        eprintf ("%s - wrong motor mnemonic, check your slitbox XML file or SPEC configuration\n", \
		CB_SB_MNE[mmne])
        return(-1)
      }
    }
  }

  #get the exptable motors
  _motors = xml_readMotorsByRoles(exptableHo)

  if (! (("translation" in _motors)&&("height" in _motors))) {
    eprintf ("Cannot get the height and/or translation exptable motor(s)\n")
    return(-1)
  } else {
    CB_ET_MNE["translation"] = _motors["translation"]
    CB_ET_MNE["height"] = _motors["height"]
    for (mmne in CB_ET_MNE) {
      CB_ET_MOT[mmne]=motor_num(CB_ET_MNE[mmne])
      if (CB_ET_MOT[mmne] == -1) {
        eprintf ("%s - wrong motor mnemonic, check your exptable XML file or SPEC configuration\n", \
		CB_ET_MNE[mmne])
        return(-1)
      }
    }
  }
  return(0)
}'

#%IU% (dy,dz)
#%MDESC% Move the slitbox vertical motors and the exptable height by %B%dz%B%
#mm. Move the  slitbox horizontal motors and the exptable translation motor
#by %B%dy%B% mm.
def _mv_tab_slits(dy,dz) '{
  if (CB_CENTRE_OK)
    return(-1)

  if (CB_DONTMOVESLITS==0) {
    A[CB_SB_MOT["t1h"]] -= CB_SLITBOX_Y_COEF * dy
    A[CB_SB_MOT["t2h"]] -= CB_SLITBOX_Y_COEF * dy
    A[CB_SB_MOT["t1v"]] += CB_SLITBOX_Z_COEF * dz
    A[CB_SB_MOT["t2v"]] += CB_SLITBOX_Z_COEF * dz
  }

  A[CB_ET_MOT["height"]] += CB_TABLE_Z_COEF * dz
  A[CB_ET_MOT["translation"]] += CB_TABLE_Y_COEF * dy

  move_em; waitmove; get_angles; move_poll
}'

#%IU% ()
#%MDES% Save the initial state.
def centrebeam_savstat() '{
  get_angles

  CB_INITSTATE[0] = A[CB_SB_MOT["t1h"]]
  CB_INITSTATE[1] = A[CB_SB_MOT["t1v"]]
  CB_INITSTATE[2] = A[CB_SB_MOT["t2h"]]
  CB_INITSTATE[3] = A[CB_SB_MOT["t2v"]]

  CB_INITSTATE[4] = A[CB_ET_MOT["height"]]
  CB_INITSTATE[5] = A[CB_ET_MOT["translation"]]

  _get_zoom()
  CB_INITSTATE[6] = CB_ZOOMFACTOR
  CB_INITSTATE[7] = ATT_FACTOR
  CB_INITSTATE[8] = _bshstate(SHUTTER["_CURRENT"])

  CB_INITSTATE[9] = _backlightstate()
  CB_INITSTATE[10] = _flightstate()

  return(0)
}'

#%IU% ()
#%MDESC% Actions taken at the begining of the centrebeam procedure.
def centrebeam_prepare() '{
local stat

  #open the front end
  stat = _check_fe(1)
  if (stat == -1) {
    CB_CENTRE_OK = -1
    msg =  sprintf ("cannot open the Front End, centrebeam aborted")
    eprintf("%s\n", msg)
    return(-1)
  }

  #move the zoom to the predefined position
  if (CB_NOAUTOZOOM) {
    if (_set_zoom(CB_ZOOM) < 0)
      return(-1)
  } else {
    if (_set_zoom(CB_DEFAULTZOOM) < 0)
      return(-1)
  }

  if (CB_UDIFF == 1) {
    CB_INITSTATE[11] = microdiff_phase()
    microdiff_phase(2)
    backout
    apertureout
  } else {
    #remove the backlight to prevent doing centrebeam when no yag is set
    lightout

    if (!CB_SCINT) {
      #put the scintilator in
      scinton
    }
  }
  #switch off the front light
  if (flightoff() < 0)
    return(-1)
  #open the safety shutter
  shopen

}'


#%IU% ()
#%MDESC% Actions taken if ^C pressed.
def centrebeam_cleanup() '{

  printf ("Closing shutters, please wait.\n")
  msclose

  printf ("Resetting zoom, please wait.\n")
  _set_zoom(CB_INITSTATE[6])

  if (CB_DONTMOVESLITS==0) {
    A[CB_SB_MOT["t1h"]] = CB_INITSTATE[0]
    A[CB_SB_MOT["t1v"]] = CB_INITSTATE[1]
    A[CB_SB_MOT["t2h"]] = CB_INITSTATE[2]
    A[CB_SB_MOT["t2v"]] = CB_INITSTATE[3]
  }
  A[CB_ET_MOT["height"]] = CB_INITSTATE[4]
  A[CB_ET_MOT["translation"]] = CB_INITSTATE[5]

  move_em; waitmove; get_angles
  CB_CENTRE_OK = 0

  if (CB_INITSTATE[8] == 3)
    shclose

  if (CB_INIT_TRANSMISSION>0)
    transmission CB_INITSTATE[7]

  if (CB_UDIFF == 1) {
    microdiff_phase(CB_INITSTATE[11])
  } else {
    if (!CB_SCINT) {
      #put the scintilator out
      scintoff
    }

    if (CB_INITSTATE[9] =="IN")
      lightin
  }
 
  printf ("Beam is now reset to the original position.\n")
}'

#%IU% ()
#%MDESC% Resets the zoom and transmission, closes the safety shutter.
#Count if needed to get the i0 counts after the centring, before resizing
#the beam (useful if other procedures use centrebeam).
def centrebeam_accept() '{

  if (CB_COUNT) {
    transmission 100
    ct 0.1
  }
  CB_COUNT = 0

  if (CB_UDIFF == 1) {
    aperturein
    sleep(5)
  }

  if (CB_DONTCLOSESHUTTERS==0) {
    printf ("Closing shutters, please wait.\n")
    msclose
    if (CB_INITSTATE[8] == 3)
      shclose  

    if (CB_INITSTATE[10] == "ON")
      flighton()
  } else {
    CB_DONTCLOSESHUTTERS=0
  }

  if (CB_UDIFF == 1) {
    microdiff_phase(CB_INITSTATE[11])
  } else {
    if (!CB_SCINT) {
      #put the scintilator out
      scintoff
    }
  }

  printf ("Resetting zoom, please wait.\n")
  if (_set_zoom(CB_INITSTATE[6]) < 0)
    return(-1)
  CB_CENTRE_OK = 0

  if (CB_INIT_TRANSMISSION>0)
    transmission CB_INITSTATE[7]
  printf ("Beam is now centred on rotation axis.\n")
}'

#%IU% (val)
#%MDESC% Check if val is a digit. Return 0 if yes, -1 if not.
def isdigit(val) '{

  if ((asc(val) > 47) && (asc(val) < 60) || (asc(val) == 45))
    return(0)
  return(-1) 

}'

#%IU% ()
#%MDESC% Define dummy macros to avoid error in spec if microdiff not used.
def dummy_defs() '{

  if (whatis("wait_ready") == 0)
    eval("def wait_ready()\'{ }\'")

  if (whatis("get_cameracalib") == 0)
    eval("def get_cameracalib() \'{ }\'")

  if (whatis("aperturein") == 0)
    eval("def aperturein \'{ }\'")

  if (whatis("apertureout") == 0)
    eval("def apertureout \'{ }\'")

   if (whatis("microdiff_phase") == 0)
    eval("def microdiff_phase() \'{}\'")

  if (whatis("flighton") == 0)
    eval("def flighton() \'{}\'")

  if (whatis("flightoff") == 0)
    eval("def flightoff() \'{}\'")
}'

#%MACROS%
#%IMACROS%
#%TOC%
#%DEPENDENCIES% safshut.mac id.mac mxcollect.mac
#%AUTHOR% M.Guijarro/A.Beteva
#$Revision: 1.30 $$Date: 2011/04/04 14:46:35 $