jdg@hpqtdla.sqf.hp.com (James Gentles) (11/23/90)
Of interest to RADIO HAMS and CARTOGRAPHERS with HP28/48 calculators. The following details the contents of my HP28 ham radio directory. Read on if you are interested. Anyone out there got any other stuff for ham applications of the HP28/48 please post or email. 73 James --------------------------------------------------------------------- I have no professional connection with Hewlett-Packard's calculator operations other than as a user of their products. --------------------------------------------------------------------- Opinions expressed are my own, and are not intended to be an official statement by Hewlett-Packard Company --------------------------------------------------------------------- Name: James Gentles GM4WZP Organization: Hewlett-Packard Queensferry Telecomunications Division Email: jdg@hpqtdla.hpsqf.hp.com hp-sdd Address: Station Road, South Queensferry, West Lothian, Scotland --------------------------------------------------------------------- This file contains a collection of HP28 programs used for translation between different co-ordinate systems, calculating Great Circle Distances and bearings, and calculating Radio Horizons. The programs may also be of use to anyone interested in Transverse Mercator Projection Calculations. The co-ordinate systems that can be translated between are: * Latitude and Longitude (the fundamental measure of global position). * The QRA Locator square system where the world is divided into a number of sections, each 2.5 mins latitude and 5 mins longitude. * The Great Britain National Grid reference System, which defines any point in Great Britain to within 100 metres. * The Irish National Grid reference System, which defines any point in Ireland (North and South) to within 100 metres. Note: These National Grid systems are used by Amateurs in the UK and Eire to define a stations position to within a 10Km square. These are collected for a Worked all Britain (WAB) award. Although these National Grid Systems are peculiar to the British Isles, they use a mapping scheme called "Transverse Mercator Projection". These programs could be used for translation between Latitude and longitude and ANY mapping system that uses this projection by altering the constants used to define the projection. These are contained in a list. The programs are written specially for the British and Irish Grids, and their Grid Numbering scheme. This means that 100Km squares are given grid letters, rather than numbers. This extra level of complexity could easily be removed. The raw numbers from the projection are more accurate than the 100 metres. It may even be possible to use the formulae for "Mercator Projection" by simply swapping the Latitude and Longitude entries. "Mercator Projection" is one of the projections commonly used to show the whole world in atlases. It's main disadvantage for 'whole world' maps is the distortion near the poles, making Antartica appear much larger than it should be. For small parts of the globe (e.g. the UK) this projection provides a very accurate model however. Finally in this introduction a brief description of the UK national grid. The grid system allows a map to contain a regular grid for reference and distance calculations over short distances. However, because the map is a projection of the surface of a shape approximating to an oblate spheroid onto a plane (or cylindrical shaped) piece of paper then these grid lines have a very complex relationship to latitude and longitude. The origin of the grid is off the SW corner of England, and there are 4 main squares, each 500Km on all sides. The square nearest the origin is called S (South?), and covers most of England. The square north of that is N (North?) and covers mostly Scotland. The square north of that again is H (?) and covers the most northerly islands of Scotland. Finally the eastern extremity of England just pokes into square T to the east of square S. These letters appear to be named arbitrarily. Each of these 500Km squares is divided into 25 100Km squares as follows: A B C D E F G H J K L M N O P Q R S T U V W X Y Z So for example I live at "NT119779" to the nearest 100metres. The full reference from datum for this is Eastings 311900, Northings 677900. Note program XX6-> is used to do this translation. The Irish grid only covers one of the above described 500Km squares, so it is identical to the British system except the leading N, S, H or T is not required. There now follows a description of each of the objects listed at the end. QRA Locator Square Translator: The following procedures translate between the worldwide QRA (or ANB or Maidenhead, whatever its called) locator system used by Radio Amateurs. ->QRA Takes Latitude from stack level 2, and Longitude from level 1 and returns a string with the Locator. South and West are negative. The input should be in DD.MMSS format. The input is tested to ensure that it is +-90 and +-180 respectively. For example, take QTH ->QRA gives "IO85HX" for my locator. QRA-> Takes a string from the stack level 1 and returns the Latitude in level 2 and Longitude in level 1 of the square center. This is the inverse of ->QRA. The output is in DD.MMSS. Some error trapping is done on the input, but it is not foolproof. Transverse Mercator Projection Routines, to change to Latitude and Longitude, all Latitude and longitude numbers are entered, and returned in DD.MMSSsss format unless otherwise stated. ->NGR Lat and Long to National Grid Reference (Great Britain). Put Latitude on stack (north is +ve), then Longitude on stack (east is +ve), returns a string of format "NT119779". The bottom left corner of the 100m square defined. NGR-> National Grid to Lat and Long. The inverse of ->NGR. Returns the Lat and Long of the centre of the 100m square defined. ->IGR Lat and Long to Irish Grid Reference. Put Latitude on stack (north is +ve), then Longitude on stack (east is +ve), returns a string of format "T119779". The bottom left corner of the 100m square defined. IGR-> Irish Grid to Lat and Long. The inverse of ->IGR. Returns the Lat and Long of the centre of the 100m square defined. ->XX6 Used by ->NGR and ->IGR to translate eastings and northings in metres to a national grid reference, e.g. 311900 677900 become "NT119799" If the coordinates do not fall into one of the 4 500Km squares a "#" is returned in the first character of the string. XX6-> Performs the inverse process of ->XX6. ->TMP Performs the Transverse Mercator Projection. On entry the stack should contain Lat, Long (both in radians), then all the constants in list AIRY or IRISH depending on what projection is being used. The routine returns eastings and northings on the stack in metres. TMP-> Performs the inverse Transverse Mercator Projection. On entry the stack should contain eastings, northings, then all the constants in list AIRY or IRISH depending on what projection is being used. The routine returns Latitude and longitude on the stack in radians. VRH2 Used by ->TMP and TMP-> routines AOM Used by ->TMP and TMP-> routines PHI Used by ->TMP and TMP-> routines ABNE Used by ->TMP and TMP-> routines PAD0 Used by ->XX6 routine AIRY List of constants used by TMP routines for Great Britain. See following listing of object for comments on what individual elements are. IRISH List of constants used by TMP routines for Ireland. See following listing of object for comments on what individual elements are. Great Circle Distance & Bearings: Calculates the distance between your station and the remote station, also gives beam heading required. GCIR Takes the output of QRA-> (Lat and Long) and uses the Lat and Long in QTH to compute the great circle distance and bearing from QTH to the stack Lat and Long. The distance is returned in Level 2, in Km. The bearing, in DD.MMSS from north (+E,-W) is returned in Level 1. This program assumes the earth is a perfect sphere ( we all know this is an approximation as the earth is actually flat :-). This program uses the PRESERVE routine given in the manual to ensure degrees mode is used. QTH Must contain the two numbers << Lat,Long >> representing your stations position, in degrees, minnutes and seconds. ERAD Must contain the equatorial radius of the earth. I use: 6378.888 which is in Kilometers, thus the answer to GCIR is in Km, you can use UNITS to change this constant if you wish. Radio Horizon: Calculates the flat-band line of sight communication distance at VHF. HORIZ Returns the distance between a point on the earth and the VHF radio 'horizon' given the height above sea level. The height is taken from level 1, and the distance returned in level 1, both will be in the same units as ERAD. e.g. For 914m ASL enter 0.914 to give an answer of 124.68 Km. Note this is NOT the same as the line of sight horizon, as it includes a correction of SQRT(4/3) to allow for tropospheric bending. LOFS Line of Sight. Same as HORIZ but does not take into account any bending, can be used for frequencies above VHF or light. The Procedures: ->QRA Checksum BC9E << HMS-> 180 + SWAP HMS-> 90 + -> lo la << IF lo 0 < lo 360 > la 0 < la 180 > OR OR OR THEN la 90 - lo 180 - "Lat/Long out of range" 1 DISP 2 WAIT ABORT END lo 20 / IP 65 + CHR la 10 / IP 65 + CHR lo 20 / FP 10 * IP 48 + CHR la 10 / FP 10 * IP 48 + CHR lo 2 / FP 24 * IP 65 + CHR la FP 24 * IP 65 + CHR >> + + + + + >> QRA-> Checksum 9DE4 << << "Not valid QRA" 1 DISP 1 WAIT >> -> 'er' << DUP IF TYPE 2 <> THEN er EVAL ABORT END DUP IF SIZE 6 <> THEN er EVAL ABORT END -> q << 1 6 FOR i q i DUP SUB NUM 65 - NEXT -> a b c d e f << 'b*10+(d+17)+f/24+1/48-90' EVAL ->HMS 'a*20+(c+17)*2+e/12+1/24-180' EVAL ->HMS >> >> >> >> ->NGR Checksum 7F70 << HMS-> D->R SWAP HMS-> D->R Change to degrees decimal then radians AIRY LIST-> DROP Put constants for Airy projection on stack ->TMP Transverse Mercator Proj returns E&N in meters ->XX6 Translate to grid letters and 100metre accy >> NGR-> Checksum 9E92 << XX6-> Translate grid letters to full coords AIRY LIST-> DROP Put constants for Airy projection on stack TMP-> Transverse Mercator to Lat Long convertion SWAP R->D ->HMS SWAP Translate to deg/min/seconds R->D ->HMS >> ->IGR Checksum 6E58 << HMS-> D->R SWAP HMS-> Same as ->NGR but since Irish grid is only 500Km D->R IRISH LIST-> DROP square then initial grid letter ("S") can be ->TMP ->XX6 2 8 SUB ignored so is stripped off. >> IGR-> Checksum F77C << "S" SWAP + XX6-> IRISH Same as NGR-> but to use same XX6-> routine the LIST-> DROP TMP-> SWAP "S" suffix is added to the grid ref before R->D ->HMS SWAP R->D ->HMS parsing by XX6->, so its output is correct >> ->XX6 Checksum 4FB1 << 100 / IP SWAP 100 / IP -> n e Throw away accuracy better than 100m << e 5000 / IP n 5000 / IP -> es ns Find what 500Km square to be used << IF es 0 == For eastings 0 to 500000 THEN IF ns 2 == Northings 1000000 to 1500000 square H THEN "H" ELSE IF ns 1 == Northings 500000 to 1000000 square N THEN "N" ELSE IF ns 0 == Northings 0 to 500000 square S THEN "S" ELSE "#" ELSE illigal square denoted by # END END END ELSE IF ns 0 == es 1 == AND for eastings 500000 to 1000000 and THEN "T" Northings 0 to 500000 square T ELSE "#" ELSE illigal square denoted by # END END e 1000 / IP 5 MOD Now find letter within square by first numbering 1 + 4 n 1000 squares top left to bottom right. / IP 5 MOD - -> el nl << nl 5 * el + DUP So numbers are 0 to 24 IF 8 <= Skip the number 8 THEN 1 - So numbers are 0 to 7 then 9 thru 25 END 65 + CHR + puch grid character A to H then J thru Z >> e 1000 MOD << STD >> NFMT PAD0 n 1000 MOD << STD >> NFMT PAD0 + + Build into reference e.g. NJ123456 using PAD0 >> to fill in leading 0's in the strings. >> >> XX6-> Checksum E0D1 << -> str << str 3 5 SUB str 6 8 SUB Split incloming string up e.g. N J 123 456 str NUM str 2 f s e n 2 SUB NUM 66 - DUP letters are translated to numbers and s is IF 7 < connditioned to be contiguous top right to THEN 1 + bottom left 0 to 24 END -> e n f s << IF f 72 == IF H square msdigit should be THEN 0 2 ELSE IF f 78 == IF N square msdigit should be THEN 0 1 ELSE IF f 83 == IF S square msdigit should be THEN 0 0 ELSE IF f 84 == IF T square msdigit should be THEN 1 0 ELSE "XX Error" 1 DISP HALT END END END END -> e1 n1 pass the msdigits of easting and northing << s 5 MOD 4 s 5 / IP 5 MOD - -> e2 n2 << e STR-> e1 5000 * e2 1000 * + + 100 * 50 + n STR-> n1 5000 * n2 1000 * + + 100 * 50 + >> Recombine elements into full N&E adding 50meters >> to both to place them at square centre >> >> >> ->TMP Checksum 8523 << Reference Transverse Mercator Projection << RAD -> l k a b k0 l0 n0 e0 f0 Constants, Formulae and Methods << l l0 - k k0 - k k0 + -> p k3 k4 Ordnance Survey Information March 1983 << a b f0 ABNE -> a1 b1 n1 e2 << n1 k3 k4 b1 AOM a1 e2 k VRH2 -> m v r h2 << l l0 - -> p << m n0 + Formula I k SIN k COS v 2 / * * II 'v/24*SIN(k)*COS(k )^3* (5-TAN(k)^2+9*h2)' ->NUM III 'v/720*SIN(k)*COS(k)^5*(61- 58*TAN(k)^2+TAN(k)^4)' ->NUM IIIA p 6 ^ * SWAP p 4 ^ COMPUTE NORTHINGS * + SWAP p SQ * + + k COS v * Formula IV 'v/6* COS(k)^3*(v/r-TAN(k)^2)' ->NUM V 'v/120*COS (k)^5*(5-18*TAN(k)^2+ TAN(k)^4+14*h2-58*TAN(k)^2*h2)' ->NUM VI p 5 ^ * SWAP p 3 ^ * + SWAP p * COMPUTE EASTINGS + e0 + SWAP >> >> >> >> >> >> PRESERVE RETURN TO ORIGINAL STATUS >> TMP-> Checksum 1541 << Reference Transverse Mercator Projection << RAD -> e n a b k0 l0 n0 e0 f0 Constants, Formulae and Methods << e e0 - -> y1 Ordnance Survey Information March 1983 << a b f0 ABNE -> a1 b1 n1 e2 << n n0 n1 k0 a1 b1 PHI -> k k3 k4 << a1 e2 k VRH2 -> v r h2 << k TAN 2 r v * * / Formula VII 'TAN(k) / (24*r*v^3)*(5+3* TAN(k)^2+h2-9*TAN(k)^2*h2)' ->NUM VIII 'TAN(k)/( 720*r*v^5)*(61+90* TAN(k)^2+45*TAN(k)^4 )' ->NUM IX y1 6 ^ * SWAP y1 4 ^ * CALCULATE LATITUDE SWAP - SWAP y1 SQ * + k SWAP - k COS v * INV Formula X '1/(COS(k)*6*v^3)*(v /r+2*TAN(k)^2)' ->NUM XI '1/(COS(k)*120*v^5)*(5+28* TAN(k)^2+24* TAN(k)^4)' ->NUM XII '1/( COS(k)*5040*v^7) *(61 +662*TAN(k)^2+1320* TAN(k) ^4+720*TAN(k)^ 6)' ->NUM XIIA y1 7 ^ * SWAP y1 5 ^ * CALCULATE LONGITUDE SWAP - SWAP y1 3 ^ * + SWAP y1 * SWAP - l0 + >> >> >> >> >> >> PRESERVE >> VRH2 Checksum F951 << -> a1 e2 k << 'a1/SQRT(1-e2*SIN(k )^2)' ->NUM DUP '(1- e2)/(1-e2*SIN(k)^2)' ->NUM * DUP2 / 1 - >> >> AOM Checksum 447F Compute Developed Meridion Arc m << -> n1 k3 k4 b1 stack variables to local variables << '(1+n1+5/4*n1^2+ 5/4* n1^3)*k3' ->NUM '(3*n1+3*n1^2+21/8*n1^3)* SIN(k3)*COS(k4)' ->NUM '(15/8*n1^2+15/ 8*n1^3)* SIN(2*k3)*COS(2*k4)' ->NUM '35/ 24*n1^3*SIN(3*k3)* COS(3*k4)' ->NUM - + - b1 * >> on exit m is on stack >> PHI Checksum DF6C Iteratively Calculate Latitude k << -> n n0 n1 k0 a1 b1 stack variables to local variables << '(n-n0)/a1+k0' ->NUM 0 0 First approximation to Latitude DO DROP2 DUP DUP k0 - SWAP k0 + -> k k3 k4 << n1 k3 k4 b1 AOM -> m re-compute arc of meridian << n n0 - m - DUP IF .001 < THEN k k3 k4 ELSE 'k+(n -n0-m)/a1' re-calculate phi ->NUM k3 k4 END >> >> 4 ROLL UNTIL .001 < UNTIL error is less than .001 END returns k k3 k4 on stack >> >> ABNE Checksum 6926 << -> a b f0 Stack variables to local variables << a f0 * b f0 * -> a1 b1 Scale Major & Minor axes by f0 << a1 b1 DUP2 - a1 b1 + / calculate n from scaled axes a1 SQ b1 SQ - a1 SQ / calculate e^2 (e2) from scaled axes >> >> returns a1 b1 n e2 on stack >> PAD0 Checksum 91D6 << Takes string from stack and WHILE while it is shorter than 3 characters DUP SIZE 3 < REPEAT "0" SWAP + add a leading "0" END >> AIRY Checksum 51C5 Constants defining Transverse Mercator Projection for Airy Spheroid { 6377563.396 Major semi-axis m 6356256.91 Minor semi-axis m .855211333477 True Origin 49 deg N for -3.490658E-2 2 deg W GREAT BRITAIN -100000 False Origin in m E of true origin 400000 m N of true origin .9996012717 } Scale factor on Central meridian Fo IRISH Checksum 2E20 Constants defining Transverse Mercator Projection for Airy Spheroid { 6377563.396 Major semi-axis m 6356256.91 Minor semi-axis m .933751149817 True Origin 53.5 deg N for -.139626340159 8 deg W IRELAND 250000 False Origin in m E of true origin 200000 m N of true origin 1.000035 } Scale factor on Central meridian Fo GCIR Checksum AA31 << << DEG HMS-> SWAP HMS-> QTH HMS-> SWAP HMS-> 4 ROLLD ROT - DUP IF 180 > THEN 360 - END DUP IF -180 < THEN 360 + END IF DUP 0 == THEN .000001 + END ! ensures we dont divide by 0 -> lah laa dif << 'ACOS(SIN(lah)*SIN(laa)+COS(lah)*COS(laa)*COS(dif))' ->NUM DUP 180 / pi * ERAD * ->NUM SWAP -> dis << 'ACOS((SIN(laa)-SIN(lah)*COS(dis))/(COS(lah)*SIN(dis)))' ->NUM >> IF dif 0 > THEN NEG END ->HMS ! correction for E or W of N >> >> PRESERVE >> HORIZ Checksum 6E8B << ERAD * 8 * 3 / SQRT >> LOFS Chechsum D7E9 << ERAD * 2 * SQRT >> ERAD 6378.388 QTH << 55.5910 -3.244 >> Must be in DD.MMSSsss format, Lat,Long SYMBOL KEY: SQRT 131:-Square_root_symbol pi 135:-Symbolic_constant <= 137:-Less_than_&_equal_to <> 139:-Not_equal_to -> 141:-Right_hand_arrow << 146:-Start_program_construct >> 147:-End_program_construct *