1 /****************************************************************************
2 **
3 ** Copyright (c) 2008-2015 C.B. Barber. All rights reserved.
4 ** $Id: //main/2015/qhull/src/libqhullcpp/QhullRidge.h#4 $$Change: 2079 $
5 ** $DateTime: 2016/02/07 17:43:34 $$Author: bbarber $
6 **
7 ****************************************************************************/
8 
9 #ifndef QHULLRIDGE_H
10 #define QHULLRIDGE_H
11 
12 #include "libqhull_r/qhull_ra.h"
13 #include "libqhullcpp/QhullSet.h"
14 #include "libqhullcpp/QhullVertex.h"
15 #include "libqhullcpp/QhullVertexSet.h"
16 #include "libqhullcpp/QhullFacet.h"
17 
18 #include <ostream>
19 
20 namespace orgQhull {
21 
22 #//!\name Used here
23     class Qhull;
24     class QhullVertex;
25     class QhullVertexSet;
26     class QhullFacet;
27 
28 #//!\name Defined here
29     //! QhullRidge -- Qhull's ridge structure, ridgeT [libqhull.h], as a C++ class
30     class QhullRidge;
31     typedef QhullSet<QhullRidge>  QhullRidgeSet;
32     typedef QhullSetIterator<QhullRidge>  QhullRidgeSetIterator;
33     // see QhullSets.h for QhullRidgeSet and QhullRidgeSetIterator -- avoids circular references
34 
35 /************************
36 a ridge is hull_dim-1 simplex between two neighboring facets.  If the
37 facets are non-simplicial, there may be more than one ridge between
38 two facets.  E.G. a 4-d hypercube has two triangles between each pair
39 of neighboring facets.
40 
41 topological information:
42     vertices            a set of vertices
43     top,bottom          neighboring facets with orientation
44 
45 geometric information:
46     tested              True if ridge is clearly convex
47     nonconvex           True if ridge is non-convex
48 */
49 
50 class QhullRidge {
51 
52 #//!\name Defined here
53 public:
54     typedef ridgeT *   base_type;  // for QhullRidgeSet
55 
56 #//!\name Fields
57 private:
58     ridgeT *            qh_ridge;  //!< Corresponding ridgeT, never 0
59     QhullQh *           qh_qh;     //!< QhullQh/qhT for ridgeT, may be 0
60 
61 #//!\name Class objects
62     static ridgeT       s_empty_ridge;
63 
64 public:
65 #//!\name Constants
66 
67 #//!\name Constructors
QhullRidge()68                         QhullRidge() : qh_ridge(&s_empty_ridge), qh_qh(0) {}
69     explicit            QhullRidge(const Qhull &q);
70                         QhullRidge(const Qhull &q, ridgeT *r);
QhullRidge(QhullQh * qqh)71     explicit            QhullRidge(QhullQh *qqh) : qh_ridge(&s_empty_ridge), qh_qh(qqh) {}
QhullRidge(QhullQh * qqh,ridgeT * r)72                         QhullRidge(QhullQh *qqh, ridgeT *r) : qh_ridge(r ? r : &s_empty_ridge), qh_qh(qqh) {}
73                         // Creates an alias.  Does not copy QhullRidge.  Needed for return by value and parameter passing
QhullRidge(const QhullRidge & other)74                         QhullRidge(const QhullRidge &other) : qh_ridge(other.qh_ridge), qh_qh(other.qh_qh) {}
75                         // Creates an alias.  Does not copy QhullRidge.  Needed for vector<QhullRidge>
76     QhullRidge &        operator=(const QhullRidge &other) { qh_ridge= other.qh_ridge; qh_qh= other.qh_qh; return *this; }
~QhullRidge()77                         ~QhullRidge() {}
78 
79 #//!\name GetSet
bottomFacet()80     QhullFacet          bottomFacet() const { return QhullFacet(qh_qh, qh_ridge->bottom); }
dimension()81     int                 dimension() const { return ((qh_qh && qh_qh->hull_dim) ? qh_qh->hull_dim-1 : 0); }
getBaseT()82     ridgeT *            getBaseT() const { return getRidgeT(); } //!< For QhullSet<QhullRidge>
getRidgeT()83     ridgeT *            getRidgeT() const { return qh_ridge; }
id()84     countT              id() const { return qh_ridge->id; }
isValid()85     bool                isValid() const { return (qh_qh && qh_ridge != &s_empty_ridge); }
86     bool                operator==(const QhullRidge &other) const { return qh_ridge==other.qh_ridge; }
87     bool                operator!=(const QhullRidge &other) const { return !operator==(other); }
otherFacet(const QhullFacet & f)88     QhullFacet          otherFacet(const QhullFacet &f) const { return QhullFacet(qh_qh, (qh_ridge->top==f.getFacetT() ? qh_ridge->bottom : qh_ridge->top)); }
topFacet()89     QhullFacet          topFacet() const { return QhullFacet(qh_qh, qh_ridge->top); }
90 
91 #//!\name foreach
92     bool                hasNextRidge3d(const QhullFacet &f) const;
nextRidge3d(const QhullFacet & f)93     QhullRidge          nextRidge3d(const QhullFacet &f) const { return nextRidge3d(f, 0); }
94     QhullRidge          nextRidge3d(const QhullFacet &f, QhullVertex *nextVertex) const;
vertices()95     QhullVertexSet      vertices() const { return QhullVertexSet(qh_qh, qh_ridge->vertices); }
96 
97 #//!\name IO
98 
99     struct PrintRidge{
100         const QhullRidge *ridge;
101         const char *    print_message;    //!< non-null message
PrintRidgePrintRidge102                         PrintRidge(const char *message, const QhullRidge &r) : ridge(&r), print_message(message) {}
103     };//PrintRidge
print(const char * message)104     PrintRidge          print(const char* message) const { return PrintRidge(message, *this); }
105 };//class QhullRidge
106 
107 }//namespace orgQhull
108 
109 std::ostream &operator<<(std::ostream &os, const orgQhull::QhullRidge &r);
110 std::ostream &operator<<(std::ostream &os, const orgQhull::QhullRidge::PrintRidge &pr);
111 
112 #endif // QHULLRIDGE_H
113