/******************************************************************************* * * McStas, neutron ray-tracing package * Copyright 1997-2002, All rights reserved * Risoe National Laboratory, Roskilde, Denmark * Institut Laue Langevin, Grenoble, France * * Component: Selector * * %Identification * Written by: Peter Link, Andreas Ostermann * Date: MARCH 1999 * Origin: Uni. Gottingen (Germany) * Version: $Revision: 1.8 $ * Release: McStas 1.6 * * velocity selector (helical lamella type) such as V_selector component * * %Description * velocity selector (helical lamella type) * * Example: Selector(xmin=-0.015, xmax=0.015, ymin=-0.025, ymax=0.025, len=0.25, * num=72,width=0.004,radius=0.12,alfa=48.298,feq=500) * These are values for the D11@ILL Dornier 'Dolores' Velocity Selector (NVS 023) * * %VALIDATION * Jun 2005: extensive external test, problems are being solved at the moment * * %BUGS * for transmission calculation, each neutron is supposed to be in the guide centre * * %Parameters * INPUT PARAMETERS: * * xmin: Lower x bound of entry aperture (m) * xmax: Upper x bound of entry aperture (m) * ymin: Lower y bound of entry aperture (m) * ymax: Upper y bound of entry aperture (m) * len: rotor length (m) * num: number of spokes/lamella (1) * width: width of spokes at beam-center (m) * radius: radius of beam-center (m) * alfa: angle of torsion (deg) * feq: frequency of rotation (1/s) * * %Links * See also Additional notes March 1999 and Jan 2000. * * %End *******************************************************************************/ DEFINE COMPONENT Selector DEFINITION PARAMETERS () SETTING PARAMETERS (xmin=-0.015, xmax=0.015, ymin=-0.025, ymax=0.025, len=0.25, num=72,width=0.0004,radius=0.12,alfa=48.298,feq=500) STATE PARAMETERS (x,y,z,vx,vy,vz,t,s1,s2,p) TRACE %{ double E; double dt; double open_angle,closed_angle,n_angle_in,n_angle_out; double sel_phase; PROP_Z0; E=VS2E*(vx*vx+vy*vy+vz*vz); if (xxmax || yymax) ABSORB; /* because outside frame */ dt = len/vz; /* get phase angle of selector rotor as MonteCarlo choice only the free space between two neighboring spokes is taken p is adjusted to transmission for parallel beam */ n_angle_in = atan2( x,y+radius)*RAD2DEG; closed_angle = width/radius*RAD2DEG; open_angle = 360/num-closed_angle; sel_phase = open_angle*rand01(); p *= (open_angle/(closed_angle+open_angle)); PROP_DT(dt); if (xxmax || yymax) ABSORB; /* because outside frame */ /* now let's look whether the neutron is still between the same two spokes or absorbed meanwhile */ n_angle_out = atan2(x,y+radius)*RAD2DEG; /* neutron beam might be divergent */ sel_phase = sel_phase + feq*dt*360 - alfa; /* rotor turned, but spokes are torsaded */ if (n_angle_out<(n_angle_in-sel_phase) || n_angle_out>(n_angle_in-sel_phase+open_angle) ) ABSORB; /* because must have passed absorber */ else SCATTER; %} MCDISPLAY %{ double phi, r0, Width, height, l0, l1; double r; double x0; double x1; double y0; double y1; double z0; double z1; double z2; double z3; double a; double xw, yh; phi = alfa; Width = (xmax-xmin)/2; height = (ymax-ymin)/2; x0 = xmin; x1 = xmax; y0 = ymin; y1 = ymax; l0 = len; l1 = l0; r0 = radius; r = r0 + height; x0 = -Width/2.0; x1 = Width/2.0; y0 = -height/2.0; y1 = height/2.0; z0 = -l0/2.0; z1 = -l1/2.0; z2 = l1/2.0; z3 = l0/2.0; magnify("xy"); xw = Width/2.0; yh = height/2.0; /* Draw apertures */ for(a = z0;;) { multiline(3, x0-xw, (double)y1, a, (double)x0, (double)y1, a, (double)x0, y1+yh, a); multiline(3, x1+xw, (double)y1, a, (double)x1, (double)y1, a, (double)x1, y1+yh, a); multiline(3, x0-xw, (double)y0, a, (double)x0, (double)y0, a, (double)x0, y0-yh, a); multiline(3, x1+xw, (double)y0, a, (double)x1, (double)y0, a, (double)x1, y0-yh, a); if(a == z3) break; else a = z3; } /* Draw cylinder. */ circle("xy", 0, -r0, z1, r); circle("xy", 0, -r0, z2, r); line(0, -r0, z1, 0, -r0, z2); for(a = 0; a < 2*PI; a += PI/8) { multiline(4, 0.0, -r0, z1, r*cos(a), r*sin(a) - r0, z1, r*cos(a + DEG2RAD*phi), r*sin(a + DEG2RAD*phi) - r0, z2, 0.0, -r0, z2); } /* magnify("xy"); multiline(5, (double)xmin, (double)ymin, 0.0, (double)xmax, (double)ymin, 0.0, (double)xmax, (double)ymax, 0.0, (double)xmin, (double)ymax, 0.0, (double)xmin, (double)ymin, 0.0); */ %} END