summaryrefslogtreecommitdiff
path: root/geometry/Point3D.hh
blob: dd171c74cbade9cc264ee694aa20a26b63c71931 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
//==================================================================
// Copyright 2002, softSurfer (www.softsurfer.com)
// This code may be freely used and modified for any purpose
// providing that this copyright notice is included with it.
// SoftSurfer makes no warranty for this code, and cannot be held
// liable for any real or imagined damage resulting from it's use.
// Users of this code must verify correctness for their application.
//==================================================================

// Heavily modified by Randal A. Koene, 20050111

#ifndef SS_Point3D_H
#define SS_Point3D_H

#include <iostream>
using namespace std;

#ifndef SS_Vector3D_H
class Vector3D;
#endif

// utility macros
#define	Pabs(x)		((x) >= 0 ? x : -(x))
#define	Pmin(x,y)	((x) < (y) ? (x) : (y))
#define	Pmax(x,y)	((x) > (y) ? (x) : (y))

// Now:
// (2) Update the Makefile to get compiler directives in line with those
//     that I use.
// (3) Make the basic point classes very lean, add derived class in a
//     separate object file that has all the operators a type usually has.
// (4) Possibly turn these into templates, so that I can choose different
//     types other than double as the member variables and thereby alter
//     precision, memory consumption and more.

#define PDIMSIZE 3

class Point3D {
  friend class Vector3D;
 protected:
  double x, y, z;      // z=0 for 2D, y=z=0 for 1D
 public:
  Point3D(): x(0.0), y(0.0), z(0.0) {}
  Point3D(double X, double Y, double Z = 0.0): x(X), y(Y), z(Z) {}
  ~Point3D() {};

  double X() const { return x; }
  double Y() const { return y; }
  double Z() const { return z; }
  void set_X(double X) { x = X; }
  void set_Y(double Y) { y = Y; }
  void set_Z(double Z) { z = Z; }
  void add_X(double X) { x += X; }
  void add_Y(double Y) { y += Y; }
  void add_Z(double Z) { z += Z; }

  double & operator [] (unsigned int n) {
    if (n==0) return x;
    else if (n==1) return y;
    else return z;
  }

  friend istream& operator>>( istream & input, Point3D & P);
  friend ostream& operator<<( ostream & output, Point3D P);

  int operator==( Point3D Q) { return (x==Q.x && y==Q.y && z==Q.z); }
  int operator!=( Point3D Q) { return (x!=Q.x || y!=Q.y || z!=Q.z); }

  Vector3D operator-( Point3D);       // Vector3D difference
  Point3D  operator+( Vector3D);      // +translate
  Point3D  operator-( Vector3D);      // -translate
  Point3D& operator+=( Vector3D);     // inc translate
  Point3D& operator-=( Vector3D);     // dec translate
  
  //----------------------------------------------------------
  // Point3D Scalar Operations (convenient but often illegal)
  // using any type of scalar (int, float, or double)
  //    are not valid for points in general,
  //    unless they are 'affine' as coeffs of 
  //    a sum in which all the coeffs add to 1,
  //    such as: the sum (a*P + b*Q) with (a+b == 1).
  //    The programmer must enforce this (if they want to).
  
  // Scalar Multiplication
  friend Point3D operator*( int, Point3D);
  friend Point3D operator*( double, Point3D);
  friend Point3D operator*( Point3D, int);
  friend Point3D operator*( Point3D, double);
  // Scalar Division
  friend Point3D operator/( Point3D, int);
  friend Point3D operator/( Point3D, double);

  //----------------------------------------------------------
  // Point3D Addition (also convenient but often illegal)
  //    is not valid unless part of an affine sum.
  //    The programmer must enforce this (if they want to).
  friend Point3D operator+( Point3D, Point3D);     // add points

  // Affine Sum
  // Returns weighted sum, even when not affine, but...
  // Tests if coeffs add to 1.  If not, sets: err = Esum.
  friend Point3D asum( int, int[], Point3D[], int * err = 0);
  friend Point3D asum( int, double[], Point3D[], int * err = 0);

  //----------------------------------------------------------
  // Point3D Relations
  friend double distance( Point3D, Point3D);         // Distance
  friend double distance2( Point3D, Point3D);        // Distance^2
  double distance(Point3D & P); // Distance
  double isLeft( Point3D, Point3D, int * err = 0); // 2D only
  double Area( Point3D, Point3D); 		// any dim for triangle PPP
  
  // Collinearity Conditions (any dim n)
  bool isOnLine( Point3D, Point3D, char);  // is On line (char= flag)
  bool isOnLine( Point3D, Point3D);        // is On line (flag= all)
  bool isBefore( Point3D, Point3D);        // is On line (flag= before)
  bool isBetween( Point3D, Point3D);       // is On line (flag= between)
  bool isAfter( Point3D, Point3D);         // is On line (flag= after)
  bool isOnRay( Point3D, Point3D);         // is On line (flag= between|after)
	
  bool isZero() { return ((x==0.0) && (y==0.0) && (z==0.0)); }
	
};

#endif