HKL rotation (BW5)

The following VM has been coded for BW5. It can be used at other diffractometer beamlines as well.

Before the virtual motor can be used, the following command has to be entered: ONLINE> def vm1.

#!/bin/env perl -w
# file name: /online_dir/vm1.pl
#
# this script drives a diffractometer in a circle around a
# reflection in the h-k plane, 0 - 360, clockwise. The 
# zero-degree position is in the direction of the h axis.
# 0   ( h + r, k, 0)
# 90  ( k, k - r, 0). 
# 90  ( k - r, k, 0). 
# 270 ( h, k + r, 0) 
# 
use Spectra; 
use POSIX; 

my ($method, $value_new) = @ARGV; 
my $deg2rad = 0.0174533; 
my $rad2deg = 57.2958;
my $status = 1; 
#
#
#
my $r = 0.2; 
my ( $h0, $k0, $l0) = ( 2, 0, 0); 
my $flag_0_to_360 = 1; 
#
#
if( $method eq "set_position")
{
    if( $flag_0_to_360)
    {
	if( $value_new < 0 || $value_new > 360)
	{
	    $status = Spectra::error( "vm1: requested position not in [0., 360.]"); 
	    goto finish;
	}
    }
    else
    {
	if( $value_new < -180 || $value_new > 180.)
	{
	    $status = Spectra::error( "vm1: requested position not in [-180, 180]"); 
	    goto finish;
	}
    }
    my $h_new = $h0 + $r*POSIX::cos( $value_new*$deg2rad); 
    my $k_new = $k0 - $r*POSIX::sin( $value_new*$deg2rad); 
    $status = Spectra::hkl( h => $h_new, 
			    k => $k_new, 
			    l => $l0);
    goto finish;
}

if( $method eq "get_position")
{
    my $x = Spectra::h() - $h0; 
    my $y = Spectra::k() - $k0; 
    $y = -$y;                   # clockwise 
    my $res = POSIX::atan2( $y, $x)*$rad2deg; 
    if( $flag_0_to_360)
    {
	$res = 360. + $res if( $res < 0); 
    }
    $SYM{RETURN_VALUE} = $res;     
    goto finish;
}
if( $method eq "get_limit_min")
{
    if( $flag_0_to_360)
    {
	$SYM{RETURN_VALUE} = 0;
    }
    else
    {
	$SYM{RETURN_VALUE} = -180.;
    }
    goto finish;
}
if( $method eq "get_limit_max")
{
    if( $flag_0_to_360)
    {
	$SYM{RETURN_VALUE} = 360.;
    }
    else
    {
	$SYM{RETURN_VALUE} = 180.;
    }
    goto finish;
}

if( $method eq "exec_stop")
{
    Util::log( "method exec-stop"); 
}
finish:
 $status;