' Pattern Diagram Rotation.
' Rotation Matrix Generator.
'
' FF Table : step 1 deg.
'
' Author : F5FOD Jean-Pierre Waymel, with the DG7YBN Hartmut Klüver's advices and suggestions.
' Date : november 2016 - february 2017
'
' Program name : step1_matrix_generator_basic_V2-0.bas
' Version 2.0
' From V1.6
' sin(theta1=180), sin(theta2=180), cos(theta1=90), cos(theta2=90) and cos((phi1 - phi2)=90or270) forced to 0.
' If coscos >= 1 => _ACOS(coscos) = 0
' If coscos <= -1 => _ACOS(coscos) = 180
'
'
' The points M, M1 and M2 are situated on a sphere the radius of which is equal to 1 :
' (phi , theta ) : point M, before the rotation ;
' (phi1, theta1) : point M1, directly after a rotation of an angle alpha around OY, towards OZ ;
' (phi2, theta2) : point M2, phi2 and theta2 being a pair of integers step 1 deg.,
' the arc M1M2 having the smallest possible value.
'
' The pairs (phi, theta) are sorted by increasing phi by increasing theta ;
' phi runs from 0 deg. to 360 deg. step 1 deg.
' theta runs from 0 deg. to 180 deg. step 1 deg.
' Then the (phi, theta) pairs are :
' (0, 0), (0, 1),..., (0, 180),
' (1, 0), (1, 1),..., (1, 180),
' ...,
' ..., (360, 180).
'
' There are 181 x 361 = 65341 pairs (phi, theta).
'
' For each pair (phi, theta) before the rotation, a pair (phi1, theta1) was calculated
' by another program : step1_phi1_theta1_generator_V2-0.bas, which delivered a text file
' named "FFstep1_phi1_theta1_basic_**_V2-0.txt" with "**" being the value of the rotation angle.
' The format of this file is : ;;, with phi1 and theta1 in deg.
'
' Due to the sorting, due to the range and the step of phi's and theta's, the value of
' a pair (phi, theta) is "hidden" in each index :
' phi is the result of an euclidian division "\" => (index - 1)\181 ;
' theta is the rest of this division ;
' "- 1" is due to the fact that the index begins at "1" (as the line numbering in Excel)
' when phi and theta begin at "0".
'
' Reversely, index = 181 * phi + theta + 1.
'
' Example for index = 7534 :
' phi = (7534 - 1)\181 = 41 deg.
' theta = [(7534 - 1) - (41 x 181)] = 112 deg.
'
' An index is a simplified way to give a pair (phi, theta).
'
' Unfortunately, the pairs (phi1, theta1) are generally not pairs of integers and not
' in step 1 deg. !
' To further calculate the double trapezoidal sums needed to calculate the antenna temperature,
' we have to get the point M1 the closest possible of a point M2, and that for each point M2.
' Then to get the pair (phi1, theta1) the closest possible
' of a pair of integers step 1 deg. (phi2, theta2) and that for each pair (phi2, theta2).
'
' This program delivers an output file named "FFstep1_phi2_theta2_basic_**_V2-0.txt"
' with "**" being the value of the rotation angle alpha.
' The format of this file is : .
'
DIM index AS LONG
DIM phi1(65341%) AS DOUBLE
DIM theta1(65341%) AS DOUBLE
'
DIM arc(65341%) AS DOUBLE
DIM index(361%, 181%) AS LONG
'
DIM phi1_rad AS DOUBLE
DIM theta1_rad AS DOUBLE
DIM phi2_rad AS DOUBLE
DIM theta2_rad AS DOUBLE
DIM min AS DOUBLE
DIM coscos AS DOUBLE
DIM sin_theta1 AS DOUBLE
DIM sin_theta2 AS DOUBLE
DIM cos_theta1 AS DOUBLE
DIM cos_theta2 AS DOUBLE
DIM cos_phi1_phi2 AS DOUBLE
'
'
' PART 1
' Getting phi1 and theta1 values from the text file.
alpha_entry:
CLS
PRINT " Rotation angle value, in degrees"
PRINT " (any integer value between 1 and 90, step 1) "; ' alpha = 0 => no rotation !
INPUT alpha%
IF alpha% < 1% OR alpha% > 90% THEN GOTO alpha_entry
IF alpha% < 10% THEN alpha$ = "0" + LTRIM$(STR$(alpha%)) ELSE alpha$ = LTRIM$(STR$(alpha%))
'
CLOSE 1%
OPEN "FFstep1_phi1_theta1_basic_" + alpha$ + "_V2-0.txt" FOR INPUT AS #1%
'
FOR index = 1% TO 65341%
INPUT #1%, A$
delimiter_1st% = INSTR(A$, ";")
delimiter_2nd% = INSTR(delimiter_1st% + 1%, A$, ";")
phi1$ = MID$(A$, delimiter_1st% + 1%, delimiter_2nd% - delimiter_1st% - 1%)
theta1$ = RIGHT$(A$, LEN(A$) - delimiter_2nd%)
phi1(index) = VAL(phi1$)
theta1(index) = VAL(theta1$)
NEXT index
CLOSE 1%
'
'
' PART 2
' Which pair (phi, theta) before the rotation will be the more convenient
' to represent a pair (phi2, theta2) after the rotation ?
' We'll name "index(phi2%, theta2%)" the index of this pair (phi, theta).
'
PRINT "phi2 values :"
FOR phi2% = 0% TO 360%
PRINT phi2%,
IF phi2% = 90% THEN SOUND 440%, 18%
IF phi2% = 180% THEN SOUND 540%, 18%
IF phi2% = 270% THEN SOUND 640%, 18%
IF phi2% = 360% THEN SOUND 740%, 18%
phi2_rad = _PI / 180 * phi2%
FOR theta2% = 1% TO 179% ' For the values "0 deg." and 180 deg.",
' see the 2 special cases below where
' x1 = y1 = 0
theta2_rad = _PI / 180 * theta2%
min = 4 ' Put "min" higher than the maximum possible which
' is equal to PI, half a great circle circumference.
FOR index = 1% TO 65341%
theta1_rad = _PI / 180 * theta1(index) ' M1
phi1_rad = _PI / 180 * phi1(index) ' M1
'
sin_theta1 = SIN(theta1_rad)
IF theta1(index) = 180% THEN sin_theta1 = 0%
sin_theta2 = SIN(theta2_rad)
IF theta2% = 180% THEN sin_theta2 = 0%
'
cos_theta1 = COS(theta1_rad)
IF theta1(index) = 90% THEN cos_theta1 = 0%
cos_theta2 = COS(theta2_rad)
IF theta2% = 90% THEN cos_theta2 = 0%
'
cos_phi1_phi2 = COS(phi1_rad - phi2_rad)
IF (phi1(index) - phi2%) = 90% THEN cos_phi1_phi2 = 0%
IF (phi1(index) - phi2%) = 270% THEN cos_phi1_phi2 = 0%
'
coscos = cos_theta1 * cos_theta2 + sin_theta1 * sin_theta2 * cos_phi1_phi2
arc(index) = _ACOS(coscos) ' M1M2 arc.
IF coscos >= 1% THEN arc(index) = 0%
IF coscos <= -1% THEN arc(index) = _PI
'
IF arc(index) < min THEN ' Searching the smallest M1M2 arc.
min = arc(index)
index(phi2%, theta2%) = index
END IF
NEXT index
NEXT theta2%
NEXT phi2%
'
' Test
PRINT
PRINT index(126%, 168%), index(360%, 92%)
'
' Special case : theta2% = 0% => "North pole" : phi2 may take any value !
FOR phi2% = 0% TO 360%
index(phi2%, 0%) = alpha% + 1% ' To get theta2 = 0 deg. after the rotation,
' phi must be equal to 0 and theta to alpha.
' "alpha + 1" is the index of the pair (0, alpha).
NEXT phi2%
'
' Special case : theta2% = 180% => "South pole" : phi2 may take any value !
FOR phi2% = 0% TO 360%
index(phi2%, 180%) = 32580% + (180% - alpha%) + 1% ' To get theta2 = 180 deg.
' after the rotation, phi must be equal
' to 180 deg. and theta to 180 deg. - alpha.
' "32580 + (180 - alpha) + 1" is the index
' of the pair (180, 180 - alpha).
NEXT phi2%
'
'
' PART 3
' Save index and index(phi2%, theta2%) on a file
OPEN "FFstep1_phi2_theta2_basic_" + alpha$ + "_V2-0.txt" FOR OUTPUT AS #1%
index = 0%
FOR phi2% = 0% TO 360%
FOR theta2% = 0% TO 180%
index = index + 1%
PRINT #1%, index, index(phi2%, theta2%)
NEXT theta2%
NEXT phi2%
CLOSE 1%
'
'
' PART 4
' New alpha value ?
PRINT " Another alpha value (Y for 'Yes' or for 'No') ";
INPUT A$
IF A$ = "Y" OR A$ = "y" THEN GOTO alpha_entry
'
'
END