| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597 |
- //
- // This unit is part of the GLScene Engine, http://glscene.org
- //
- unit GLGeometryCoordinates;
- (*
- Helper functions to convert between different three dimensional coordinate
- systems. Room for optimisations.
- *)
- interface
- {$I GLScene.inc}
- uses
- System.Math,
- GLVectorGeometry;
- // Convert cylindrical to cartesian [single]. theta in rad
- procedure Cylindrical_Cartesian(const r, theta, z1: single; var x, y, z: single); overload;
- // Convert cylindrical to cartesian [double]. theta in rads
- procedure Cylindrical_Cartesian(const r, theta, z1: double; var x, y, z: double); overload;
- // Convert cylindrical to cartesian [single] (with error check). theta in rad
- procedure Cylindrical_Cartesian(const r, theta, z1: single; var x, y, z: single;
- var ierr: integer); overload;
- // Convert cylindrical to cartesian [double] (with error check). theta in rad
- procedure Cylindrical_Cartesian(const r, theta, z1: double; var x, y, z: double;
- var ierr: integer); overload;
- // Convert cartesian to cylindrical [single]
- procedure Cartesian_Cylindrical(const x, y, z1: single; var r, theta, z: single); overload;
- // Convert cartesion to cylindrical [double]
- procedure Cartesian_Cylindrical(const x, y, z1: double; var r, theta, z: double); overload;
- // Convert spherical to cartesion. [single] theta,phi in rads
- procedure Spherical_Cartesian(const r, theta, phi: single; var x, y, z: single); overload;
- // Convert spherical to cartesion. [double] theta,phi in rads
- procedure Spherical_Cartesian(const r, theta, phi: double; var x, y, z: double); overload;
- // Convert spherical to cartesian [single] (with error check).theta,phi in rad
- procedure Spherical_Cartesian(const r, theta, phi: single; var x, y, z: single;
- var ierr: integer); overload;
- // Convert spherical to cartesian [double] (with error check).theta,phi in rad
- procedure Spherical_Cartesian(const r, theta, phi: double; var x, y, z: double;
- var ierr: integer); overload;
- // Convert cartesian to spherical [single]
- procedure Cartesian_Spherical(const x, y, z: single; var r, theta, phi: single); overload;
- procedure Cartesian_Spherical(const v: TAffineVector; var r, theta, phi: single); overload;
- // Convert cartesion to spherical [double]
- procedure Cartesian_Spherical(const x, y, z: double; var r, theta, phi: double); overload;
- // Convert Prolate-Spheroidal to Cartesian. [single] eta, phi in rad
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single); overload;
- // Convert Prolate-Spheroidal to Cantesian. [double] eta,phi in rad
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double); overload;
- // Convert Prolate-Spheroidal to Cartesian [single](with error check). eta,phi in rad
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single; var ierr: integer); overload;
- // Convert Prolate-Spheroidal to Cartesian [single](with error check). eta,phi in rad
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double; var ierr: integer); overload;
- // Convert Oblate-Spheroidal to Cartesian. [Single] eta, phi in rad
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single); overload;
- // Convert Oblate-Spheroidal to Cartesian. [Double] eta, phi in rad
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double); overload;
- // Convert Oblate-Spheroidal to Cartesian (with error check). eta,phi in rad
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single; var ierr: integer); overload;
- // Convert Oblate-Spheroidal to Cartesian (with error check).[Double] eta,phi in rad
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double; var ierr: integer); overload;
- // Convert Bipolar to Cartesian. u in rad
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: single;
- var x, y, z: single); overload;
- // Convert Bipolar to Cartesian. [Double] u in rad
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: double;
- var x, y, z: double); overload;
- // Convert Bipolar to Cartesian (with error check). u in rad
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: single;
- var x, y, z: single; var ierr: integer); overload;
- // Convert Bipolar to Cartesian (with error check). [Double] u in rad
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: double;
- var x, y, z: double; var ierr: integer); overload;
- // --------------------------------------------------------------------------
- implementation
- // --------------------------------------------------------------------------
- // ----- Cylindrical_Cartesian ---------------------------------------------
- (* Convert Cylindrical to Cartesian with no checks.
- Ref: http://mathworld.wolfram.com/CylindricalCoordinates.html *)
- procedure Cylindrical_Cartesian(const r, theta, z1: single; var x, y, z: single);
- begin
- SinCosine(theta, r, y, x);
- z := z1;
- end;
- // ----- Cylindrical_Cartesian -------------------------------------------------
- (* Convert Cylindrical to Cartesian with no checks. Double version
- Ref: http://mathworld.wolfram.com/CylindricalCoordinates.html *)
- procedure Cylindrical_Cartesian(const r, theta, z1: double; var x, y, z: double);
- begin
- SinCosine(theta, r, y, x);
- z := z1;
- end;
- // ----- Cylindrical_Cartesian -------------------------------------------------
- (* Convert Cylindrical to Cartesian with checks.
- ierr: [0] = ok,
- [1] = r out of bounds. Acceptable r: [0,inf)
- [2] = theta out of bounds. Acceptable theta: [0,2pi)
- [3] = z1 out of bounds. Acceptable z1 : (-inf,inf)
- Ref: http://mathworld.wolfram.com/CylindricalCoordinates.html *)
- procedure Cylindrical_Cartesian(const r, theta, z1: single; var x, y, z: single;
- var ierr: integer);
- begin
- // check input parameters
- if (r < 0.0) then
- ierr := 1
- else if ((theta < 0.0) or (theta >= 2 * pi)) then
- ierr := 2
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(theta, r, y, x);
- z := z1;
- end;
- end;
- // ----- Cylindrical_Cartesian -------------------------------------------------
- (* Convert Cylindrical to Cartesian with checks.
- ierr: [0] = ok,
- [1] = r out of bounds. Acceptable r: [0,inf)
- [2] = theta out of bounds. Acceptable theta: [0,2pi)
- [3] = z1 out of bounds. Acceptable z1 : (-inf,inf)
- Ref: http://mathworld.wolfram.com/CylindricalCoordinates.html *)
- procedure Cylindrical_Cartesian(const r, theta, z1: double; var x, y, z: double;
- var ierr: integer);
- begin
- // check input parameters
- if (r < 0.0) then
- ierr := 1
- else if ((theta < 0.0) or (theta >= 2 * pi)) then
- ierr := 2
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(theta, r, y, x);
- z := z1;
- end;
- end;
- // ----- Cartesian_Cylindrical -------------------------------------------------
- (* Convert Cartesian to Cylindrical no checks. Single *)
- procedure Cartesian_Cylindrical(const x, y, z1: single; var r, theta, z: single);
- begin
- r := sqrt(x * x + y * y);
- theta := ArcTan2(y, x);
- z := z1;
- end;
- // ----- Cartesian_Cylindrical -------------------------------------------------
- (* Convert Cartesian to Cylindrical no checks. Duoble *)
- procedure Cartesian_Cylindrical(const x, y, z1: double; var r, theta, z: double);
- begin
- r := sqrt(x * x + y * y);
- theta := ArcTan2(y, x);
- z := z1;
- end;
- // ----- Spherical_Cartesian ---------------------------------------------------
- (* Convert Spherical to Cartesian with no checks.
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html *)
- procedure Spherical_Cartesian(const r, theta, phi: single; var x, y, z: single);
- var
- a: single;
- begin
- SinCosine(phi, r, a, z); // z = r*cos(phi), a=r*sin(phi)
- SinCosine(theta, a, y, x); // x = a*cos(theta), y = a*sin(theta)}
- end;
- // ----- Spherical_Cartesian ---------------------------------------------------
- (* Convert Spherical to Cartesian with no checks. Double version.
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html *)
- procedure Spherical_Cartesian(const r, theta, phi: double; var x, y, z: double);
- var
- a: double;
- begin
- SinCosine(phi, r, a, z); // z = r*cos(phi), a=r*sin(phi)
- SinCosine(theta, a, y, x); // x = a*cos(theta), y = a*sin(theta)}
- end;
- // ----- Spherical_Cartesian ---------------------------------------------------
- (* Convert Spherical to Cartesian with checks.
- ierr: [0] = ok,
- [1] = r out of bounds
- [2] = theta out of bounds
- [3] = phi out of bounds
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html *)
- procedure Spherical_Cartesian(const r, theta, phi: single; var x, y, z: single;
- var ierr: integer);
- var
- a: single;
- begin
- if (r < 0.0) then
- ierr := 1
- else if ((theta < 0.0) or (theta >= 2 * pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(phi, r, a, z); // z = r*cos(phi), a=r*sin(phi)
- SinCosine(theta, a, y, x); // x = a*cos(theta), y = a*sin(theta)}
- end;
- end;
- // ----- Spherical_Cartesian ---------------------------------------------------
- (* Convert Spherical to Cartesian with checks.
- ierr: [0] = ok,
- [1] = r out of bounds
- [2] = theta out of bounds
- [3] = phi out of bounds
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html *)
- procedure Spherical_Cartesian(const r, theta, phi: double; var x, y, z: double;
- var ierr: integer);
- var
- a: double;
- begin
- if (r < 0.0) then
- ierr := 1
- else if ((theta < 0.0) or (theta >= 2 * pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(phi, r, a, z); // z = r*cos(phi), a=r*sin(phi)
- SinCosine(theta, a, y, x); // x = a*cos(theta), y = a*sin(theta)}
- end;
- end;
- // ----- Cartesian_Spherical ---------------------------------------------------
- (* convert Cartesian to Spherical, no checks, single
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html
- NB: Could be optimised by using jclmath.pas unit? *)
- procedure Cartesian_Spherical(const x, y, z: single; var r, theta, phi: single);
- begin
- r := sqrt((x * x) + (y * y) + (z * z));
- theta := ArcTan2(y, x);
- phi := ArcCosine(z / r);
- end;
- procedure Cartesian_Spherical(const v: TAffineVector; var r, theta, phi: single);
- begin
- r := VectorLength(v);
- theta := ArcTan2(v.y, v.x);
- phi := ArcCosine(v.z / r);
- end;
- // ----- Cartesian_Spherical ---------------------------------------------------
- (* convert Cartesian to Spherical, no checks, double
- Ref: http://mathworld.wolfram.com/SphericalCoordinates.html
- NB: Could be optimised by using jclmath.pas unit? *)
- procedure Cartesian_Spherical(const x, y, z: double; var r, theta, phi: double);
- begin
- r := sqrt((x * x) + (y * y) + (z * z));
- theta := ArcTan2(y, x);
- phi := ArcCosine(z / r);
- end;
- // ----- ProlateSpheroidal_Cartesian -------------------------------------------
- (* Convert Prolate-Spheroidal to Cartesian with no checks.
- A system of curvilinear coordinates in which two sets of coordinate surfaces are
- obtained by revolving the curves of the elliptic cylindrical coordinates about
- the x-axis, which is relabeled the z-axis. The third set of coordinates
- consists of planes passing through this axis.
- The coordinate system is parameterised by parameter a. A default value of a=1 is
- suggesed:
- http://documents.wolfram.com/v4/AddOns/StandardPackages/Calculus/VectorAnalysis.html
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: single; var x, y, z: single);
- var
- sn, cs, snphi, csphi, shx, chx: single;
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := sn * shx * csphi; // x = a*sin(eta)*sinh(xi)*cos(phi)
- y := sn * shx * snphi; // y = a*sin(eta)*sinh(xi)*sin(phi)
- z := cs * chx; // z = a*cos(eta)*cosh(xi)
- end;
- // ----- ProlateSpheroidal_Cartesian -------------------------------------------
- (* Convert Prolate-Spheroidal to Cartesian with no checks. Double version.
- A system of curvilinear coordinates in which two sets of coordinate surfaces are
- obtained by revolving the curves of the elliptic cylindrical coordinates about
- the x-axis, which is relabeled the z-axis. The third set of coordinates
- consists of planes passing through this axis.
- The coordinate system is parameterised by parameter a. A default value of a=1 is
- suggesed:
- http://documents.wolfram.com/v4/AddOns/StandardPackages/Calculus/VectorAnalysis.html
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: double; var x, y, z: double);
- var
- sn, cs, snphi, csphi, shx, chx: double;
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := sn * shx * csphi; // x = a*sin(eta)*sinh(xi)*cos(phi)
- y := sn * shx * snphi; // y = a*sin(eta)*sinh(xi)*sin(phi)
- z := cs * chx; // z = a*cos(eta)*cosh(xi)
- end;
- // ----- ProlateSpheroidal_Cartesian -------------------------------------------
- (* Convert Prolate-Spheroidal to Cartesian with checks.
- ierr: [0] = ok,
- [1] = xi out of bounds. Acceptable xi: [0,inf)
- [2] = eta out of bounds. Acceptable eta: [0,pi]
- [3] = phi out of bounds. Acceptable phi: [0,2pi)
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single; var ierr: integer); overload;
- var
- sn, cs, snphi, csphi, shx, chx: single;
- begin
- if (xi < 0.0) then
- ierr := 1
- else if ((eta < 0.0) or (eta > pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := sn * shx * csphi; // x = a*sin(eta)*sinh(xi)*cos(phi)
- y := sn * shx * snphi; // y = a*sin(eta)*sinh(xi)*sin(phi)
- z := cs * chx; // z = a*cos(eta)*cosh(xi)
- end;
- end;
- // ----- ProlateSpheroidal_Cartesian -------------------------------------------
- (* Convert Prolate-Spheroidal to Cartesian with checks. Double Version.
- ierr: [0] = ok,
- [1] = xi out of bounds. Acceptable xi: [0,inf)
- [2] = eta out of bounds. Acceptable eta: [0,pi]
- [3] = phi out of bounds. Acceptable phi: [0,2pi)
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure ProlateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double; var ierr: integer); overload;
- var
- sn, cs, snphi, csphi, shx, chx: double;
- begin
- if (xi < 0.0) then
- ierr := 1
- else if ((eta < 0.0) or (eta > pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := sn * shx * csphi; // x = a*sin(eta)*sinh(xi)*cos(phi)
- y := sn * shx * snphi; // y = a*sin(eta)*sinh(xi)*sin(phi)
- z := cs * chx; // z = a*cos(eta)*cosh(xi)
- end;
- end;
- // ----- OblateSpheroidal_Cartesian -------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with no checks.
- A system of curvilinear coordinates in which two sets of coordinate surfaces are
- obtained by revolving the curves of the elliptic cylindrical coordinates about
- the y-axis which is relabeled the z-axis. The third set of coordinates consists
- of planes passing through this axis.
- The coordinate system is parameterised by parameter a. A default value of a=1 is
- suggesed:
- http://documents.wolfram.com/v4/AddOns/StandardPackages/Calculus/VectorAnalysis.html
- Ref: http://mathworld.wolfram.com/OblateSpheroidalCoordinates.html *)
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: single; var x, y, z: single);
- var
- sn, cs, snphi, csphi, shx, chx: single;
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := cs * chx * csphi; // x = a*cos(eta)*cosh(xi)*cos(phi)
- y := cs * chx * snphi; // y = a*cos(eta)*cosh(xi)*sin(phi)
- z := sn * shx; // z = a*sin(eta)*sinh(xi)
- end;
- // ----- OblateSpheroidal_Cartesian -------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with no checks. Double Version.
- A system of curvilinear coordinates in which two sets of coordinate surfaces are
- obtained by revolving the curves of the elliptic cylindrical coordinates about
- the y-axis which is relabeled the z-axis. The third set of coordinates consists
- of planes passing through this axis.
- The coordinate system is parameterised by parameter a. A default value of a=1 is
- suggesed:
- http://documents.wolfram.com/v4/AddOns/StandardPackages/Calculus/VectorAnalysis.html
- Ref: http://mathworld.wolfram.com/OblateSpheroidalCoordinates.html *)
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: double; var x, y, z: double);
- var
- sn, cs, snphi, csphi, shx, chx: double;
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := cs * chx * csphi; // x = a*cos(eta)*cosh(xi)*cos(phi)
- y := cs * chx * snphi; // y = a*cos(eta)*cosh(xi)*sin(phi)
- z := sn * shx; // z = a*sin(eta)*sinh(xi)
- end;
- // ----- OblateSpheroidal_Cartesian -------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with checks.
- ierr: [0] = ok,
- [1] = xi out of bounds. Acceptable xi: [0,inf)
- [2] = eta out of bounds. Acceptable eta: [-0.5*pi,0.5*pi]
- [3] = phi out of bounds. Acceptable phi: [0,2*pi)
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: single;
- var x, y, z: single; var ierr: integer); overload;
- var
- sn, cs, snphi, csphi, shx, chx: single;
- begin
- if (xi < 0.0) then
- ierr := 1
- else if ((eta < -0.5 * pi) or (eta > 0.5 * pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := cs * chx * csphi; // x = a*cos(eta)*cosh(xi)*cos(phi)
- y := cs * chx * snphi; // y = a*cos(eta)*cosh(xi)*sin(phi)
- z := sn * shx; // z = a*sin(eta)*sinh(xi)
- end;
- end;
- // ----- OblateSpheroidal_Cartesian -------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with checks. Double Version.
- ierr: [0] = ok,
- [1] = xi out of bounds. Acceptable xi: [0,inf)
- [2] = eta out of bounds. Acceptable eta: [-0.5*pi,0.5*pi]
- [3] = phi out of bounds. Acceptable phi: [0,2*pi)
- Ref: http://mathworld.wolfram.com/ProlateSpheroidalCoordinates.html *)
- procedure OblateSpheroidal_Cartesian(const xi, eta, phi, a: double;
- var x, y, z: double; var ierr: integer); overload;
- var
- sn, cs, snphi, csphi, shx, chx: double;
- begin
- if (xi < 0.0) then
- ierr := 1
- else if ((eta < -0.5 * pi) or (eta > 0.5 * pi)) then
- ierr := 2
- else if ((phi < 0.0) or (phi >= 2 * pi)) then
- ierr := 3
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(eta, a, sn, cs);
- SinCosine(phi, snphi, csphi);
- shx := sinh(xi);
- chx := cosh(xi);
- x := cs * chx * csphi; // x = a*cos(eta)*cosh(xi)*cos(phi)
- y := cs * chx * snphi; // y = a*cos(eta)*cosh(xi)*sin(phi)
- z := sn * shx; // z = a*sin(eta)*sinh(xi)
- end;
- end;
- // ----- BipolarCylindrical_Cartesian ------------------------------------------
- (* Convert BiPolarCylindrical to Cartesian with no checks.
- http://mathworld.wolfram.com/BipolarCylindricalCoordinates.html *)
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: single; var x, y, z: single);
- var
- cs, sn, shx, chx: single;
- begin
- SinCosine(u, sn, cs);
- shx := sinh(v);
- chx := cosh(v);
- x := a * shx / (chx - cs);
- y := a * sn / (chx - cs);
- z := z1;
- end;
- // ----- BipolarCylindrical_Cartesian ------------------------------------------
- (* Convert BiPolarCylindrical to Cartesian with no checks. Double Version
- http://mathworld.wolfram.com/BipolarCylindricalCoordinates.html *)
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: double; var x, y, z: double);
- var
- cs, sn, shx, chx: double;
- begin
- SinCosine(u, sn, cs);
- shx := sinh(v);
- chx := cosh(v);
- x := a * shx / (chx - cs);
- y := a * sn / (chx - cs);
- z := z1;
- end;
- // ----- BipolarCylindrical_Cartesian ------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with checks.
- ierr: [0] = ok,
- [1] = u out of bounds. Acceptable u: [0,2*pi)
- [2] = v out of bounds. Acceptable v: (-inf,inf)
- [3] = z1 out of bounds. Acceptable z1: (-inf,inf)
- Ref: http://mathworld.wolfram.com/BiPolarCylindricalCoordinates.html *)
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: single;
- var x, y, z: single; var ierr: integer); overload;
- var
- cs, sn, shx, chx: single;
- begin
- if ((u < 0.0) or (u >= 2 * pi)) then
- ierr := 1
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(u, sn, cs);
- shx := sinh(v);
- chx := cosh(v);
- x := a * shx / (chx - cs);
- y := a * sn / (chx - cs);
- z := z1;
- end;
- end;
- // ----- BipolarCylindrical_Cartesian ------------------------------------------
- (* Convert Oblate-Spheroidal to Cartesian with checks. Double Version
- ierr: [0] = ok,
- [1] = u out of bounds. Acceptable u: [0,2*pi)
- [2] = v out of bounds. Acceptable v: (-inf,inf)
- [3] = z1 out of bounds. Acceptable z1: (-inf,inf)
- Ref: http://mathworld.wolfram.com/BiPolarCylindricalCoordinates.html *)
- procedure BipolarCylindrical_Cartesian(const u, v, z1, a: double;
- var x, y, z: double; var ierr: integer); overload;
- var
- cs, sn, shx, chx: double;
- begin
- if ((u < 0.0) or (u >= 2 * pi)) then
- ierr := 1
- else
- ierr := 0;
- if (ierr = 0) then
- begin
- SinCosine(u, sn, cs);
- shx := sinh(v);
- chx := cosh(v);
- x := a * shx / (chx - cs);
- y := a * sn / (chx - cs);
- z := z1;
- end;
- end;
- // =============================================================================
- end.
|