OGS
GeoLib Namespace Reference

Detailed Description

This module consists of classes governing geometric objects and related algorithms.

Namespaces

namespace  IO

Classes

class  AABB
 Class AABB is an axis aligned bounding box around a given set of geometric points of (template) type PNT_TYPE. More...
class  DuplicateGeometry
class  EarClippingTriangulation
struct  GeoObject
class  GEOObjects
 Container class for geometric objects. More...
class  Grid
class  LineSegment
class  MinimalBoundingSphere
struct  MinMaxPoints
struct  NamedRaster
class  OctTree
class  Point
class  PointVec
 This class manages pointers to Points in a std::vector along with a name. It also handles the deletion of points. Furthermore, typically, PointVec objects are managed by GEOObjects using the instance name for identification. For this reason PointVec must have a unique name. More...
class  Polygon
class  PolygonWithSegmentMarker
class  Polyline
 Class Polyline consists mainly of a reference to a point vector and a vector that stores the indices in the point vector. A polyline consists of at least one line segment. The polyline is specified by the points of the line segments. The class Polyline stores ids of pointers to the points in the _ply_pnt_ids vector. More...
class  PolylineWithSegmentMarker
class  QuadTree
class  Raster
 Class Raster is used for managing raster data. More...
struct  RasterHeader
 Contains the relevant information when storing a geoscientific raster data. More...
class  SimplePolygonTree
 This class computes and stores the topological relations between polygons. Every node of the SimplePolygonTree represents a polygon. A child node c of a parent node p mean that the polygon represented by c is contained in the polygon represented by p. More...
class  Station
 A Station (observation site) is basically a Point with some additional information. More...
class  StationBorehole
 A borehole as a geometric object. More...
class  Surface
 A Surface is represented by Triangles. It consists of a reference to a vector of (pointers to) points (_sfc_pnts) and a vector that stores the Triangles consisting of points from _sfc_pnts. More...
class  SurfaceGrid
class  TemplateVec
 The class TemplateVec takes a unique name and manages a std::vector of pointers to data elements of type T. More...
class  Triangle
 Class Triangle consists of a reference to a point vector and a vector that stores the indices in the point vector. A surface is composed by triangles. The class Surface stores the position of pointers to the points of triangles in the _pnt_ids vector. More...

Typedefs

using PolylineVec = TemplateVec<GeoLib::Polyline>
 class PolylineVec encapsulate a std::vector of Polylines additional one can give the vector of polylines a name
using SurfaceVec = TemplateVec<GeoLib::Surface>

Enumerations

enum  Orientation { CW = -1 , COLLINEAR = 0 , CCW = 1 }
enum class  GEOTYPE { POINT , POLYLINE , SURFACE }
enum class  Location {
  LEFT , RIGHT , BEYOND , BEHIND ,
  BETWEEN , SOURCE , DESTINATION
}
enum class  EdgeType { TOUCHING , CROSSING , INESSENTIAL }

Functions

template<typename InputIterator>
std::pair< Eigen::Vector3d, double > getNewellPlane (InputIterator pnts_begin, InputIterator pnts_end)
template<class T_POINT>
std::pair< Eigen::Vector3d, double > getNewellPlane (const std::vector< T_POINT * > &pnts)
template<class T_POINT>
std::pair< Eigen::Vector3d, double > getNewellPlane (const std::vector< T_POINT > &pnts)
template<typename InputIterator>
void rotatePoints (Eigen::Matrix3d const &rot_mat, InputIterator pnts_begin, InputIterator pnts_end)
template<typename InputIterator1, typename InputIterator2>
Eigen::Matrix3d rotatePointsToXY (InputIterator1 p_pnts_begin, InputIterator1 p_pnts_end, InputIterator2 r_pnts_begin, InputIterator2 r_pnts_end)
template<typename P>
void rotatePoints (Eigen::Matrix3d const &rot_mat, std::vector< P * > const &pnts)
Orientation getOrientation (MathLib::Point3d const &p0, MathLib::Point3d const &p1, MathLib::Point3d const &p2)
Orientation getOrientationFast (MathLib::Point3d const &p0, MathLib::Point3d const &p1, MathLib::Point3d const &p2)
bool parallel (Eigen::Vector3d v, Eigen::Vector3d w)
bool lineSegmentIntersect (GeoLib::LineSegment const &s0, GeoLib::LineSegment const &s1, GeoLib::Point &s)
bool lineSegmentsIntersect (const GeoLib::Polyline *ply, GeoLib::Polyline::SegmentIterator &seg_it0, GeoLib::Polyline::SegmentIterator &seg_it1, GeoLib::Point &intersection_pnt)
void rotatePoints (Eigen::Matrix3d const &rot_mat, std::vector< GeoLib::Point * > &pnts)
Eigen::Matrix3d computeRotationMatrixToXY (Eigen::Vector3d const &n)
Eigen::Matrix3d rotatePointsToXY (std::vector< GeoLib::Point * > &pnts)
std::unique_ptr< GeoLib::PointtriangleLineIntersection (MathLib::Point3d const &a, MathLib::Point3d const &b, MathLib::Point3d const &c, MathLib::Point3d const &p, MathLib::Point3d const &q)
void computeAndInsertAllIntersectionPoints (GeoLib::PointVec &pnt_vec, std::vector< GeoLib::Polyline * > &plys)
std::tuple< std::vector< GeoLib::Point * >, Eigen::Vector3d > rotatePolygonPointsToXY (GeoLib::Polygon const &polygon_in)
std::vector< MathLib::Point3dlineSegmentIntersect2d (GeoLib::LineSegment const &ab, GeoLib::LineSegment const &cd)
void sortSegments (MathLib::Point3d const &seg_beg_pnt, std::vector< GeoLib::LineSegment > &sub_segments)
Eigen::Matrix3d compute2DRotationMatrixToX (Eigen::Vector3d const &v)
Eigen::Matrix3d compute3DRotationMatrixToX (Eigen::Vector3d const &v)
Eigen::Matrix3d rotatePointsToXY (std::vector< Point * > &pnts)
void computeAndInsertAllIntersectionPoints (PointVec &pnt_vec, std::vector< Polyline * > &plys)
void sortSegments (MathLib::Point3d const &seg_beg_pnt, std::vector< LineSegment > &sub_segments)
template<typename Container>
auto findVectorByName (Container const &container, std::string const &name)
void markUnusedPoints (GEOObjects const &geo_objects, std::string const &geo_name, std::vector< bool > &transfer_pnts)
int geoPointsToStations (GEOObjects &geo_objects, std::string const &geo_name, std::string &stn_name, bool const only_unused_pnts=true)
 Constructs a station-vector based on the points of a given geometry.
std::string convertGeoTypeToString (GEOTYPE geo_type)
std::ostream & operator<< (std::ostream &os, LineSegment const &s)
std::ostream & operator<< (std::ostream &os, std::pair< GeoLib::LineSegment const &, GeoLib::LineSegment const & > const &seg_pair)
bool operator== (LineSegment const &s0, LineSegment const &s1)
Location getLocationOfPoint (MathLib::Point3d const &source, MathLib::Point3d const &destination, MathLib::Point3d const &pnt)
EdgeType getEdgeType (MathLib::Point3d const &a, MathLib::Point3d const &b, MathLib::Point3d const &pnt)
std::vector< GeoLib::PointgetAllIntersectionPoints (Polygon const &polygon, GeoLib::LineSegment const &segment)
bool operator== (Polygon const &lhs, Polygon const &rhs)
void resetPointIDs (Polyline &polyline, std::vector< std::size_t > const &mapping)
 Resets the point IDs of the polyline corresponding to the mapping.
void markUsedPoints (Polyline const &polyline, std::vector< bool > &used_points)
 Resets the point IDs of the polyline corresponding to the mapping.
bool containsEdge (const Polyline &ply, std::size_t id0, std::size_t id1)
bool operator== (Polyline const &lhs, Polyline const &rhs)
bool pointsAreIdentical (const std::vector< Point * > &pnt_vec, std::size_t i, std::size_t j, double prox)
std::unique_ptr< PolylinecreatePolyline (GeoLib::PointVec const &points_vec, std::vector< std::size_t > &&point_ids)
 Create a polyline from given point ids.
template<typename POLYGONTREETYPE>
void createPolygonTrees (std::list< POLYGONTREETYPE * > &list_of_simple_polygon_hierarchies)
bool isStation (GeoLib::Point const *pnt)
bool isBorehole (GeoLib::Point const *pnt)
bool operator== (Surface const &lhs, Surface const &rhs)
void resetPointIDs (Surface &surface, std::vector< std::size_t > const &mapping)
 Resets the point IDs of the surface corresponding to the mapping.
void markUsedPoints (Surface const &surface, std::vector< bool > &used_points)
std::vector< GeoLib::Point * > generateEquidistantPoints (MathLib::Point3d const &begin, MathLib::Point3d const &end, int const number_of_subdivisions)

Typedef Documentation

◆ PolylineVec

class PolylineVec encapsulate a std::vector of Polylines additional one can give the vector of polylines a name

Definition at line 16 of file PolylineVec.h.

◆ SurfaceVec

Class SurfaceVec encapsulate a std::vector of Surfaces and a name.

Definition at line 17 of file SurfaceVec.h.

Enumeration Type Documentation

◆ EdgeType

enum class GeoLib::EdgeType
strong

edge classification

Enumerator
TOUCHING 

TOUCHING.

CROSSING 

CROSSING.

INESSENTIAL 

INESSENTIAL.

Definition at line 27 of file Polygon.cpp.

28{
29 TOUCHING,
30 CROSSING,
32};
@ INESSENTIAL
INESSENTIAL.
Definition Polygon.cpp:31
@ CROSSING
CROSSING.
Definition Polygon.cpp:30
@ TOUCHING
TOUCHING.
Definition Polygon.cpp:29

◆ GEOTYPE

enum class GeoLib::GEOTYPE
strong
Enumerator
POINT 
POLYLINE 
SURFACE 

Definition at line 11 of file GeoType.h.

◆ Location

enum class GeoLib::Location
strong
Enumerator
LEFT 
RIGHT 
BEYOND 
BEHIND 
BETWEEN 
SOURCE 
DESTINATION 

Definition at line 13 of file Polygon.cpp.

◆ Orientation

Enumerator
CW 
COLLINEAR 
CCW 

Definition at line 13 of file AnalyticalGeometry.h.

14{
15 CW = -1,
16 COLLINEAR = 0,
17 CCW = 1
18};

Function Documentation

◆ compute2DRotationMatrixToX()

Eigen::Matrix3d GeoLib::compute2DRotationMatrixToX ( Eigen::Vector3d const & v)

Computes a rotation matrix that rotates the given 2D normal vector parallel to X-axis

Parameters
va 2D normal vector to be rotated
Returns
a 3x3 rotation matrix where the upper, left, 2x2 block contains the entries necessary for the 2D rotation

Definition at line 682 of file AnalyticalGeometry.cpp.

683{
684 Eigen::Matrix3d rot_mat = Eigen::Matrix3d::Zero();
685 const double cos_theta = v[0];
686 const double sin_theta = v[1];
687 rot_mat(0, 0) = rot_mat(1, 1) = cos_theta;
688 rot_mat(0, 1) = sin_theta;
689 rot_mat(1, 0) = -sin_theta;
690 rot_mat(2, 2) = 1.0;
691 return rot_mat;
692}

Referenced by detail::getRotationMatrixToGlobal().

◆ compute3DRotationMatrixToX()

Eigen::Matrix3d GeoLib::compute3DRotationMatrixToX ( Eigen::Vector3d const & v)

Computes a rotation matrix that rotates the given 3D normal vector parallel to X-axis.

Parameters
va 3D normal vector to be rotated
Returns
a 3x3 rotation matrix

Definition at line 694 of file AnalyticalGeometry.cpp.

695{
696 // a vector on the plane
697 Eigen::Vector3d yy = Eigen::Vector3d::Zero();
698 auto const eps = std::numeric_limits<double>::epsilon();
699 if (std::abs(v[0]) > 0.0 && std::abs(v[1]) + std::abs(v[2]) < eps)
700 {
701 yy[2] = 1.0;
702 }
703 else if (std::abs(v[1]) > 0.0 && std::abs(v[0]) + std::abs(v[2]) < eps)
704 {
705 yy[0] = 1.0;
706 }
707 else if (std::abs(v[2]) > 0.0 && std::abs(v[0]) + std::abs(v[1]) < eps)
708 {
709 yy[1] = 1.0;
710 }
711 else
712 {
713 for (unsigned i = 0; i < 3; i++)
714 {
715 if (std::abs(v[i]) > 0.0)
716 {
717 yy[i] = -v[i];
718 break;
719 }
720 }
721 }
722 // z"_vec
723 Eigen::Vector3d const zz = v.cross(yy).normalized();
724 // y"_vec
725 yy = zz.cross(v).normalized();
726
727 Eigen::Matrix3d rot_mat;
728 rot_mat.row(0) = v;
729 rot_mat.row(1) = yy;
730 rot_mat.row(2) = zz;
731 return rot_mat;
732}

Referenced by detail::getRotationMatrixToGlobal().

◆ computeAndInsertAllIntersectionPoints() [1/2]

void GeoLib::computeAndInsertAllIntersectionPoints ( GeoLib::PointVec & pnt_vec,
std::vector< GeoLib::Polyline * > & plys )

Definition at line 389 of file AnalyticalGeometry.cpp.

391{
392 auto computeSegmentIntersections =
393 [&pnt_vec](GeoLib::Polyline& poly0, GeoLib::Polyline& poly1)
394 {
395 for (auto seg0_it(poly0.begin()); seg0_it != poly0.end(); ++seg0_it)
396 {
397 for (auto seg1_it(poly1.begin()); seg1_it != poly1.end(); ++seg1_it)
398 {
399 GeoLib::Point s(0.0, 0.0, 0.0, pnt_vec.size());
400 if (lineSegmentIntersect(*seg0_it, *seg1_it, s))
401 {
402 std::size_t const id(
403 pnt_vec.push_back(new GeoLib::Point(s)));
404 poly0.insertPoint(seg0_it.getSegmentNumber() + 1, id);
405 poly1.insertPoint(seg1_it.getSegmentNumber() + 1, id);
406 }
407 }
408 }
409 };
410
411 for (auto it0(plys.begin()); it0 != plys.end(); ++it0)
412 {
413 auto it1(it0);
414 ++it1;
415 for (; it1 != plys.end(); ++it1)
416 {
417 computeSegmentIntersections(*(*it0), *(*it1));
418 }
419 }
420}
std::size_t push_back(Point *pnt)
Definition PointVec.cpp:124
Class Polyline consists mainly of a reference to a point vector and a vector that stores the indices ...
Definition Polyline.h:29
virtual bool insertPoint(std::size_t pos, std::size_t pnt_id)
Definition Polyline.cpp:44
SegmentIterator begin() const
Definition Polyline.h:177
SegmentIterator end() const
Definition Polyline.h:179
std::size_t size() const
Definition TemplateVec.h:88
bool lineSegmentIntersect(GeoLib::LineSegment const &s0, GeoLib::LineSegment const &s1, GeoLib::Point &s)

References GeoLib::Polyline::begin(), GeoLib::Polyline::end(), GeoLib::Polyline::insertPoint(), lineSegmentIntersect(), GeoLib::PointVec::push_back(), and GeoLib::TemplateVec< T >::size().

Referenced by FileIO::GMSH::GMSHInterface::writeGMSHInputFile().

◆ computeAndInsertAllIntersectionPoints() [2/2]

void GeoLib::computeAndInsertAllIntersectionPoints ( PointVec & pnt_vec,
std::vector< Polyline * > & plys )

Method first computes the intersection points of line segments of Polyline objects (

See also
computeIntersectionPoints()) and pushes each intersection point in the PointVec pnt_vec. For each intersection an id is returned. This id is used to split the two intersecting straight line segments in four straight line segments.

◆ computeRotationMatrixToXY()

Eigen::Matrix3d GeoLib::computeRotationMatrixToXY ( Eigen::Vector3d const & n)

Method computes the rotation matrix that rotates the given vector parallel to the \(z\) axis.

Parameters
nthe (3d) vector that is rotated parallel to the \(z\) axis
Returns
rot_mat 3x3 rotation matrix

Definition at line 286 of file AnalyticalGeometry.cpp.

287{
288 Eigen::Matrix3d rot_mat = Eigen::Matrix3d::Zero();
289 // check if normal points already in the right direction
290 if (n[0] == 0 && n[1] == 0)
291 {
292 rot_mat(1, 1) = 1.0;
293
294 if (n[2] > 0)
295 {
296 // identity matrix
297 rot_mat(0, 0) = 1.0;
298 rot_mat(2, 2) = 1.0;
299 }
300 else
301 {
302 // rotate by pi about the y-axis
303 rot_mat(0, 0) = -1.0;
304 rot_mat(2, 2) = -1.0;
305 }
306
307 return rot_mat;
308 }
309
310 // sqrt (n_1^2 + n_3^2)
311 double const h0(std::sqrt(n[0] * n[0] + n[2] * n[2]));
312
313 // In case the x and z components of the normal are both zero the rotation
314 // to the x-z-plane is not required, i.e. only the rotation in the z-axis is
315 // required. The angle is either pi/2 or 3/2*pi. Thus the components of
316 // rot_mat are as follows.
317 if (h0 < std::numeric_limits<double>::epsilon())
318 {
319 rot_mat(0, 0) = 1.0;
320 if (n[1] > 0)
321 {
322 rot_mat(1, 2) = -1.0;
323 rot_mat(2, 1) = 1.0;
324 }
325 else
326 {
327 rot_mat(1, 2) = 1.0;
328 rot_mat(2, 1) = -1.0;
329 }
330 return rot_mat;
331 }
332
333 double const h1(1 / n.norm());
334
335 // general case: calculate entries of rotation matrix
336 rot_mat(0, 0) = n[2] / h0;
337 rot_mat(0, 1) = 0;
338 rot_mat(0, 2) = -n[0] / h0;
339 rot_mat(1, 0) = -n[1] * n[0] / h0 * h1;
340 rot_mat(1, 1) = h0 * h1;
341 rot_mat(1, 2) = -n[1] * n[2] / h0 * h1;
342 rot_mat(2, 0) = n[0] * h1;
343 rot_mat(2, 1) = n[1] * h1;
344 rot_mat(2, 2) = n[2] * h1;
345
346 return rot_mat;
347}

Referenced by detail::getRotationMatrixToGlobal(), MeshGeoToolsLib::markNodesOutSideOfPolygon(), rotateGeometryToXY(), rotatePointsToXY(), and rotatePolygonPointsToXY().

◆ containsEdge()

bool GeoLib::containsEdge ( const Polyline & ply,
std::size_t id0,
std::size_t id1 )

Definition at line 494 of file Polyline.cpp.

495{
496 if (id0 == id1)
497 {
498 ERR("no valid edge id0 == id1 == {:d}.", id0);
499 return false;
500 }
501 if (id0 > id1)
502 {
503 std::swap(id0, id1);
504 }
505 const std::size_t n(ply.getNumberOfPoints() - 1);
506 for (std::size_t k(0); k < n; k++)
507 {
508 std::size_t ply_pnt0(ply.getPointID(k));
509 std::size_t ply_pnt1(ply.getPointID(k + 1));
510 if (ply_pnt0 > ply_pnt1)
511 {
512 std::swap(ply_pnt0, ply_pnt1);
513 }
514 if (ply_pnt0 == id0 && ply_pnt1 == id1)
515 {
516 return true;
517 }
518 }
519 return false;
520}
void ERR(fmt::format_string< Args... > fmt, Args &&... args)
Definition Logging.h:40
std::size_t getPointID(std::size_t const i) const
Definition Polyline.cpp:149
std::size_t getNumberOfPoints() const
Definition Polyline.cpp:98

References ERR(), GeoLib::Polyline::getNumberOfPoints(), and GeoLib::Polyline::getPointID().

Referenced by FileIO::GMSH::GMSHPolygonTree::markSharedSegments(), and FileIO::GMSH::GMSHPolygonTree::writeLineConstraints().

◆ convertGeoTypeToString()

std::string GeoLib::convertGeoTypeToString ( GEOTYPE geo_type)

Definition at line 12 of file GeoType.cpp.

13{
14 switch (geo_type)
15 {
16 case GEOTYPE::POINT:
17 return "POINT";
19 return "POLYLINE";
21 return "SURFACE";
22 }
23
24 // Cannot happen, because switch covers all cases.
25 // Used to silence compiler warning.
26 OGS_FATAL("convertGeoTypeToString(): Given geo type is not supported");
27}
#define OGS_FATAL(...)
Definition Error.h:19

References OGS_FATAL, POINT, POLYLINE, and SURFACE.

Referenced by GEOModels::addNameForElement(), GEOModels::addNameForObjectPoints(), GeoLib::GEOObjects::getGeoObject(), and MainWindow::showGeoNameDialog().

◆ createPolygonTrees()

template<typename POLYGONTREETYPE>
void GeoLib::createPolygonTrees ( std::list< POLYGONTREETYPE * > & list_of_simple_polygon_hierarchies)

creates from a list of simple polygons a list of trees (SimplePolygonTrees)

Definition at line 79 of file SimplePolygonTree.h.

81{
82 for (auto it0 = list_of_simple_polygon_hierarchies.begin();
83 it0 != list_of_simple_polygon_hierarchies.end();
84 ++it0)
85 {
86 auto it1 = list_of_simple_polygon_hierarchies.begin();
87 while (it1 != list_of_simple_polygon_hierarchies.end())
88 {
89 if (it0 == it1)
90 { // don't check same polygons
91 ++it1;
92 // skip test if it1 points to the end after increment
93 if (it1 == list_of_simple_polygon_hierarchies.end())
94 {
95 break;
96 }
97 }
98 if ((*it0)->isPolygonInside(*it1))
99 {
100 (*it0)->insertSimplePolygonTree(*it1);
101 it1 = list_of_simple_polygon_hierarchies.erase(it1);
102 }
103 else
104 {
105 ++it1;
106 }
107 }
108 }
109}

Referenced by FileIO::GMSH::GMSHInterface::writeGMSHInputFile().

◆ createPolyline()

std::unique_ptr< Polyline > GeoLib::createPolyline ( GeoLib::PointVec const & points_vec,
std::vector< std::size_t > && point_ids )

Create a polyline from given point ids.

Definition at line 553 of file Polyline.cpp.

555{
556 auto const& point_id_map = points_vec.getIDMap();
557 auto polyline = std::make_unique<Polyline>(points_vec.getVector());
558 for (auto point_id : point_ids)
559 {
560 if (point_id >= point_id_map.size())
561 {
562 WARN("The point id {} doesn't exist in the underlying PointVec.",
563 point_id);
564 continue;
565 }
566 polyline->addPoint(point_id_map[point_id]);
567 }
568 return polyline;
569}
void WARN(fmt::format_string< Args... > fmt, Args &&... args)
Definition Logging.h:34

References GeoLib::PointVec::getIDMap(), GeoLib::TemplateVec< T >::getVector(), and WARN().

Referenced by generatePolylineGeometry(), and generateQuadGeometry().

◆ findVectorByName()

template<typename Container>
auto GeoLib::findVectorByName ( Container const & container,
std::string const & name )

Function to find PointVec, PolylineVec, or SurfaceVec pointers that are stored in the container

Definition at line 17 of file GEOObjects.cpp.

18{
19 return std::find_if(container.begin(), container.end(),
20 [&name](auto const* vector)
21 { return vector->getName() == name; });
22}

Referenced by GeoLib::GEOObjects::appendPolylineVec(), GeoLib::GEOObjects::appendSurfaceVec(), GeoLib::GEOObjects::exists(), GeoLib::GEOObjects::getSurfaceVec(), GeoLib::GEOObjects::getSurfaceVecObj(), GeoLib::GEOObjects::isPntVecUsed(), GeoLib::GEOObjects::removeSurfaceVec(), and GeoLib::GEOObjects::renameGeometry().

◆ generateEquidistantPoints()

std::vector< GeoLib::Point * > GeoLib::generateEquidistantPoints ( MathLib::Point3d const & begin,
MathLib::Point3d const & end,
int const number_of_subdivisions )

Function generates equidistant points in the interval [begin, end] according to the given number of subdivisions. In case of zero subdivisions a vector containing the begin and the end point is returned.

Definition at line 10 of file GeoLib/Utils.cpp.

13{
14 if (number_of_subdivisions < 0)
15 {
17 "generateEquidistantPoints: number of subdivisions is required to "
18 "be non-negative.");
19 }
20
21 auto const& start = begin.asEigenVector3d();
22 auto const& stop = end.asEigenVector3d();
23 auto const delta = (stop - start) / (number_of_subdivisions + 1);
24
25 std::vector<GeoLib::Point*> points;
26
27 for (int i = 0; i <= number_of_subdivisions; ++i)
28 {
29 auto const p = start + i * delta;
30 points.push_back(new GeoLib::Point{p[0], p[1], p[2]});
31 }
32 points.push_back(new GeoLib::Point{stop[0], stop[1], stop[2]});
33
34 return points;
35}

References MathLib::Point3d::asEigenVector3d(), and OGS_FATAL.

Referenced by generatePolylineGeometry(), and generateQuadPoints().

◆ geoPointsToStations()

int GeoLib::geoPointsToStations ( GEOObjects & geo_objects,
std::string const & geo_name,
std::string & stn_name,
bool const only_unused_pnts )

Constructs a station-vector based on the points of a given geometry.

Definition at line 600 of file GEOObjects.cpp.

602{
603 GeoLib::PointVec const* const pnt_obj(geo_objects.getPointVecObj(geo_name));
604 if (pnt_obj == nullptr)
605 {
606 ERR("Point vector {:s} not found.", geo_name);
607 return -1;
608 }
609 auto const& pnts = pnt_obj->getVector();
610 if (pnts.empty())
611 {
612 ERR("Point vector {:s} is empty.", geo_name);
613 return -1;
614 }
615 std::size_t const n_pnts(pnts.size());
616 std::vector<bool> transfer_pnts(n_pnts, true);
617 if (only_unused_pnts)
618 {
619 markUnusedPoints(geo_objects, geo_name, transfer_pnts);
620 }
621
622 std::vector<GeoLib::Point*> stations;
623 for (std::size_t i = 0; i < n_pnts; ++i)
624 {
625 if (!transfer_pnts[i])
626 {
627 continue;
628 }
629 std::string name = pnt_obj->getItemNameByID(i);
630 if (name.empty())
631 {
632 name = "Station " + std::to_string(i);
633 }
634 stations.push_back(new GeoLib::Station(pnts[i], name));
635 }
636 if (!stations.empty())
637 {
638 geo_objects.addStationVec(std::move(stations), stn_name);
639 }
640 else
641 {
642 WARN("No points found to convert.");
643 return 1;
644 }
645 return 0;
646}
const PointVec * getPointVecObj(const std::string &name) const
void addStationVec(std::vector< Point * > &&stations, std::string &name)
Adds a vector of stations with the given name and colour to GEOObjects.
This class manages pointers to Points in a std::vector along with a name. It also handles the deletio...
Definition PointVec.h:25
void markUnusedPoints(GEOObjects const &geo_objects, std::string const &geo_name, std::vector< bool > &transfer_pnts)

References GeoLib::GEOObjects::addStationVec(), ERR(), GeoLib::PointVec::getItemNameByID(), GeoLib::GEOObjects::getPointVecObj(), GeoLib::TemplateVec< T >::getVector(), markUnusedPoints(), and WARN().

Referenced by MainWindow::convertPointsToStations().

◆ getAllIntersectionPoints()

std::vector< GeoLib::Point > GeoLib::getAllIntersectionPoints ( Polygon const & polygon,
GeoLib::LineSegment const & segment )

Computes all intersections of the straight line segment and the polyline boundary

Parameters
polygonthe polygon the segment line segment that will be processed
segmentthe line segment that will be processed
Returns
a possible empty vector containing the intersection points

Definition at line 178 of file Polygon.cpp.

180{
181 std::vector<GeoLib::Point> intersections;
183 for (auto&& seg_it : polygon)
184 {
185 if (GeoLib::lineSegmentIntersect(seg_it, segment, s))
186 {
187 intersections.push_back(s);
188 }
189 }
190
191 return intersections;
192}

References lineSegmentIntersect().

Referenced by GeoLib::Polygon::containsSegment().

◆ getEdgeType()

EdgeType GeoLib::getEdgeType ( MathLib::Point3d const & a,
MathLib::Point3d const & b,
MathLib::Point3d const & pnt )

from book: Computational Geometry and Computer Graphics in C++, page 119 get the type of edge with respect to the given point (2d method!)

Parameters
afirst point of line segment
blast point of line segment
pntpoint that is edge type computed for
Returns
a value of enum EdgeType

Definition at line 91 of file Polygon.cpp.

94{
95 switch (getLocationOfPoint(a, b, pnt))
96 {
97 case Location::LEFT:
98 {
99 if (a[1] < pnt[1] && pnt[1] <= b[1])
100 {
101 return EdgeType::CROSSING;
102 }
103
105 }
106 case Location::RIGHT:
107 {
108 if (b[1] < pnt[1] && pnt[1] <= a[1])
109 {
110 return EdgeType::CROSSING;
111 }
112
114 }
116 case Location::SOURCE:
118 return EdgeType::TOUCHING;
119 default:
121 }
122}
Location getLocationOfPoint(MathLib::Point3d const &source, MathLib::Point3d const &destination, MathLib::Point3d const &pnt)
Definition Polygon.cpp:44

References BETWEEN, CROSSING, DESTINATION, getLocationOfPoint(), INESSENTIAL, LEFT, RIGHT, SOURCE, and TOUCHING.

Referenced by GeoLib::Polygon::isPntInPolygon().

◆ getLocationOfPoint()

Location GeoLib::getLocationOfPoint ( MathLib::Point3d const & source,
MathLib::Point3d const & destination,
MathLib::Point3d const & pnt )

2D method - ignores z coordinate. It calculates the location of the point relative to the line segment specified by the points source and destination. (literature reference: Computational Geometry and Computer Graphics in C++; Michael J. Laszlo)

Parameters
sourcethe first point of the line segment
destinationthe end point of the line segment
pntthe test point
Returns
a value of enum Location

Definition at line 44 of file Polygon.cpp.

47{
48 long double const a[2] = {destination[0] - source[0],
49 destination[1] - source[1]}; // vector
50 long double const b[2] = {pnt[0] - source[0],
51 pnt[1] - source[1]}; // vector
52
53 long double const det_2x2(a[0] * b[1] - a[1] * b[0]);
54 constexpr double eps = std::numeric_limits<double>::epsilon();
55
56 if (det_2x2 > eps)
57 {
58 return Location::LEFT;
59 }
60 if (eps < std::abs(det_2x2))
61 {
62 return Location::RIGHT;
63 }
64 if (a[0] * b[0] < 0.0 || a[1] * b[1] < 0.0)
65 {
66 return Location::BEHIND;
67 }
68 if (a[0] * a[0] + a[1] * a[1] < b[0] * b[0] + b[1] * b[1])
69 {
70 return Location::BEYOND;
71 }
72 if (MathLib::sqrDist(pnt, source) < pow(eps, 2))
73 {
74 return Location::SOURCE;
75 }
76 if (MathLib::sqrDist(pnt, destination) < std::sqrt(eps))
77 {
79 }
80 return Location::BETWEEN;
81}
double sqrDist(MathLib::Point3d const &p0, MathLib::Point3d const &p1)
Definition Point3d.cpp:19

References BEHIND, BETWEEN, BEYOND, DESTINATION, LEFT, RIGHT, SOURCE, and MathLib::sqrDist().

Referenced by getEdgeType().

◆ getNewellPlane() [1/3]

template<class T_POINT>
std::pair< Eigen::Vector3d, double > GeoLib::getNewellPlane ( const std::vector< T_POINT * > & pnts)

Compute a supporting plane (represented by plane_normal and the value d) for the polygon. Let \(n\) be the plane normal and \(d\) a parameter. Then for all points \(p \in R^3\) of the plane it holds \( n \cdot p + d = 0\). The Newell algorithm is described in [14] .

Parameters
pntspoints of a closed polyline describing a polygon
Returns
pair of plane_normal and the parameter d: the normal of the plane the polygon is located in, parameter d from the plane equation

Definition at line 39 of file AnalyticalGeometry-impl.h.

41{
42 return getNewellPlane(pnts.begin(), pnts.end());
43}
std::pair< Eigen::Vector3d, double > getNewellPlane(InputIterator pnts_begin, InputIterator pnts_end)

References getNewellPlane().

◆ getNewellPlane() [2/3]

template<class T_POINT>
std::pair< Eigen::Vector3d, double > GeoLib::getNewellPlane ( const std::vector< T_POINT > & pnts)

Same as getNewellPlane(pnts).

Definition at line 46 of file AnalyticalGeometry-impl.h.

48{
49 Eigen::Vector3d plane_normal({0, 0, 0});
50 Eigen::Vector3d centroid({0, 0, 0});
51 std::size_t n_pnts(pnts.size());
52 for (std::size_t i = n_pnts - 1, j = 0; j < n_pnts; i = j, j++)
53 {
54 plane_normal[0] += (pnts[i][1] - pnts[j][1]) *
55 (pnts[i][2] + pnts[j][2]); // projection on yz
56 plane_normal[1] += (pnts[i][2] - pnts[j][2]) *
57 (pnts[i][0] + pnts[j][0]); // projection on xz
58 plane_normal[2] += (pnts[i][0] - pnts[j][0]) *
59 (pnts[i][1] + pnts[j][1]); // projection on xy
60
61 centroid += pnts[j].asEigenVector3d();
62 }
63
64 plane_normal.normalize();
65 double const d = centroid.dot(plane_normal) / n_pnts;
66 return std::make_pair(plane_normal, d);
67}

◆ getNewellPlane() [3/3]

template<typename InputIterator>
std::pair< Eigen::Vector3d, double > GeoLib::getNewellPlane ( InputIterator pnts_begin,
InputIterator pnts_end )

Compute a supporting plane (represented by plane_normal and the value d) for the polygon. Let \(n\) be the plane normal and \(d\) a parameter. Then for all points \(p \in R^3\) of the plane it holds \( n \cdot p + d = 0\). The Newell algorithm is described in [14] .

Parameters
pnts_beginIterator pointing to the initial point of a closed polyline describing a polygon
pnts_endIterator pointing to the element following the last point of a closed polyline describing a polygon
Returns
pair of plane_normal and the parameter d: the normal of the plane the polygon is located in, d parameter from the plane equation

Definition at line 7 of file AnalyticalGeometry-impl.h.

9{
10 Eigen::Vector3d plane_normal({0, 0, 0});
11 Eigen::Vector3d centroid({0, 0, 0});
12 for (auto i = std::prev(pnts_end), j = pnts_begin; j != pnts_end;
13 i = j, ++j)
14 {
15 auto const& pt_i = *(*i);
16 auto const& pt_j = *(*j);
17 plane_normal[0] +=
18 (pt_i[1] - pt_j[1]) * (pt_i[2] + pt_j[2]); // projection on yz
19 plane_normal[1] +=
20 (pt_i[2] - pt_j[2]) * (pt_i[0] + pt_j[0]); // projection on xz
21 plane_normal[2] +=
22 (pt_i[0] - pt_j[0]) * (pt_i[1] + pt_j[1]); // projection on xy
23
24 centroid += pt_j.asEigenVector3d();
25 }
26
27 plane_normal.normalize();
28 auto n_pnts(std::distance(pnts_begin, pnts_end));
29 assert(n_pnts > 2);
30 double d = 0.0;
31 if (n_pnts > 0)
32 {
33 d = centroid.dot(plane_normal) / n_pnts;
34 }
35 return std::make_pair(plane_normal, d);
36}

Referenced by getNewellPlane(), detail::getRotationMatrixToGlobal(), rotateGeometryToXY(), rotatePointsToXY(), and rotatePolygonPointsToXY().

◆ getOrientation()

Orientation GeoLib::getOrientation ( MathLib::Point3d const & p0,
MathLib::Point3d const & p1,
MathLib::Point3d const & p2 )

Computes the orientation of the three 2D-Points. This is a robust method.

Returns
CW (clockwise), CCW (counterclockwise) or COLLINEAR (points are on a line)

Definition at line 39 of file AnalyticalGeometry.cpp.

42{
43 double const orientation = ExactPredicates::getOrientation2d(p0, p1, p2);
44 if (orientation > 0)
45 {
46 return CCW;
47 }
48 if (orientation < 0)
49 {
50 return CW;
51 }
52 return COLLINEAR;
53}
double getOrientation2d(MathLib::Point3d const &a, MathLib::Point3d const &b, MathLib::Point3d const &c)

References CCW, COLLINEAR, CW, and ExactPredicates::getOrientation2d().

Referenced by GeoLib::EarClippingTriangulation::addLastTriangle(), GeoLib::EarClippingTriangulation::clipEars(), GeoLib::Polygon::ensureCCWOrientation(), GeoLib::EarClippingTriangulation::ensureCWOrientation(), MeshToolsLib::ProjectPointOnMesh::getProjectedElement(), GeoLib::EarClippingTriangulation::initLists(), and lineSegmentIntersect2d().

◆ getOrientationFast()

Orientation GeoLib::getOrientationFast ( MathLib::Point3d const & p0,
MathLib::Point3d const & p1,
MathLib::Point3d const & p2 )

Computes the orientation of the three 2D-Points. This is a non-robust method.

Returns
CW (clockwise), CCW (counterclockwise) or COLLINEAR (points are on a line)

Definition at line 55 of file AnalyticalGeometry.cpp.

58{
59 double const orientation =
61 if (orientation > 0)
62 {
63 return CCW;
64 }
65 if (orientation < 0)
66 {
67 return CW;
68 }
69 return COLLINEAR;
70}
double getOrientation2dFast(MathLib::Point3d const &a, MathLib::Point3d const &b, MathLib::Point3d const &c)

References CCW, COLLINEAR, CW, and ExactPredicates::getOrientation2dFast().

◆ isBorehole()

bool GeoLib::isBorehole ( GeoLib::Point const * pnt)

Definition at line 95 of file StationBorehole.cpp.

96{
97 auto const* bh(dynamic_cast<GeoLib::StationBorehole const*>(pnt));
98 return bh != nullptr;
99}
A borehole as a geometric object.

Referenced by MeshGeoToolsLib::GeoMapper::mapStationData().

◆ isStation()

bool GeoLib::isStation ( GeoLib::Point const * pnt)

Definition at line 66 of file Station.cpp.

67{
68 auto const* bh(dynamic_cast<GeoLib::Station const*>(pnt));
69 return bh != nullptr;
70}
A Station (observation site) is basically a Point with some additional information.
Definition Station.h:26

Referenced by MeshGeoToolsLib::GeoMapper::mapOnDEM(), and MeshGeoToolsLib::GeoMapper::mapOnMesh().

◆ lineSegmentIntersect()

bool GeoLib::lineSegmentIntersect ( LineSegment const & s0,
LineSegment const & s1,
Point & s )

A line segment is given by its two end-points. The function checks, if the two line segments (ab) and (cd) intersects.

Parameters
s0the first line segment.
s1the second line segment.
sthe intersection point if the segments do intersect
Returns
true, if the line segments intersect, else false

Definition at line 128 of file AnalyticalGeometry.cpp.

131{
132 GeoLib::Point const& pa{s0.getBeginPoint()};
133 GeoLib::Point const& pb{s0.getEndPoint()};
134 GeoLib::Point const& pc{s1.getBeginPoint()};
135 GeoLib::Point const& pd{s1.getEndPoint()};
136
137 if (!isCoplanar(pa, pb, pc, pd))
138 {
139 return false;
140 }
141
142 auto const& a = s0.getBeginPoint().asEigenVector3d();
143 auto const& b = s0.getEndPoint().asEigenVector3d();
144 auto const& c = s1.getBeginPoint().asEigenVector3d();
145 auto const& d = s1.getEndPoint().asEigenVector3d();
146
147 Eigen::Vector3d const v = b - a;
148 Eigen::Vector3d const w = d - c;
149 Eigen::Vector3d const qp = c - a;
150 Eigen::Vector3d const pq = a - c;
151
152 double const eps = std::numeric_limits<double>::epsilon();
153 double const squared_eps = eps * eps;
154 // handle special cases here to avoid computing intersection numerical
155 if (qp.squaredNorm() < squared_eps || (d - a).squaredNorm() < squared_eps)
156 {
157 s = pa;
158 return true;
159 }
160 if ((c - b).squaredNorm() < squared_eps ||
161 (d - b).squaredNorm() < squared_eps)
162 {
163 s = pb;
164 return true;
165 }
166
167 auto isLineSegmentIntersectingAB =
168 [&v](Eigen::Vector3d const& ap, std::size_t i)
169 {
170 // check if p is located at v=(a,b): (ap = t*v, t in [0,1])
171 return 0.0 <= ap[i] / v[i] && ap[i] / v[i] <= 1.0;
172 };
173
174 if (parallel(v, w))
175 { // original line segments (a,b) and (c,d) are parallel
176 if (parallel(pq, v))
177 { // line segment (a,b) and (a,c) are also parallel
178 // Here it is already checked that the line segments (a,b) and (c,d)
179 // are parallel. At this point it is also known that the line
180 // segment (a,c) is also parallel to (a,b). In that case it is
181 // possible to express c as c(t) = a + t * (b-a) (analog for the
182 // point d). Since the evaluation of all three coordinate equations
183 // (x,y,z) have to lead to the same solution for the parameter t it
184 // is sufficient to evaluate t only once.
185
186 // Search id of coordinate with largest absolute value which is will
187 // be used in the subsequent computations. This prevents division by
188 // zero in case the line segments are parallel to one of the
189 // coordinate axis.
190 std::size_t i_max(std::abs(v[0]) <= std::abs(v[1]) ? 1 : 0);
191 i_max = std::abs(v[i_max]) <= std::abs(v[2]) ? 2 : i_max;
192 if (isLineSegmentIntersectingAB(qp, i_max))
193 {
194 s = pc;
195 return true;
196 }
197 Eigen::Vector3d const ad = d - a;
198 if (isLineSegmentIntersectingAB(ad, i_max))
199 {
200 s = pd;
201 return true;
202 }
203 return false;
204 }
205 return false;
206 }
207
208 // general case
209 const double sqr_len_v(v.squaredNorm());
210 const double sqr_len_w(w.squaredNorm());
211
212 Eigen::Matrix2d mat;
213 mat(0, 0) = sqr_len_v;
214 mat(0, 1) = -v.dot(w);
215 mat(1, 1) = sqr_len_w;
216 mat(1, 0) = mat(0, 1);
217
218 Eigen::Vector2d rhs{v.dot(qp), w.dot(pq)};
219
220 rhs = mat.partialPivLu().solve(rhs);
221
222 // no theory for the following tolerances, determined by testing
223 // lower tolerance: little bit smaller than zero
224 const double l(-1.0 * std::numeric_limits<float>::epsilon());
225 // upper tolerance a little bit greater than one
226 const double u(1.0 + std::numeric_limits<float>::epsilon());
227 if (rhs[0] < l || u < rhs[0] || rhs[1] < l || u < rhs[1])
228 {
229 return false;
230 }
231
232 // compute points along line segments with minimal distance
233 GeoLib::Point const p0(a[0] + rhs[0] * v[0], a[1] + rhs[0] * v[1],
234 a[2] + rhs[0] * v[2]);
235 GeoLib::Point const p1(c[0] + rhs[1] * w[0], c[1] + rhs[1] * w[1],
236 c[2] + rhs[1] * w[2]);
237
238 double const min_dist(std::sqrt(MathLib::sqrDist(p0, p1)));
239 double const min_seg_len(
240 std::min(std::sqrt(sqr_len_v), std::sqrt(sqr_len_w)));
241 if (min_dist < min_seg_len * 1e-6)
242 {
243 s[0] = 0.5 * (p0[0] + p1[0]);
244 s[1] = 0.5 * (p0[1] + p1[1]);
245 s[2] = 0.5 * (p0[2] + p1[2]);
246 return true;
247 }
248
249 return false;
250}
Eigen::Vector3d const & asEigenVector3d() const
Definition Point3d.h:55
bool parallel(Eigen::Vector3d v, Eigen::Vector3d w)
bool isCoplanar(const MathLib::Point3d &a, const MathLib::Point3d &b, const MathLib::Point3d &c, const MathLib::Point3d &d)
Checks if the four given points are located on a plane.

References MathLib::Point3d::asEigenVector3d(), GeoLib::LineSegment::getBeginPoint(), GeoLib::LineSegment::getEndPoint(), parallel(), and MathLib::sqrDist().

Referenced by FileIO::GMSH::GMSHPolygonTree::checkIntersectionsSegmentExistingPolylines(), computeAndInsertAllIntersectionPoints(), getAllIntersectionPoints(), GeoLib::Polygon::getNextIntersectionPointPolygonLine(), and lineSegmentsIntersect().

◆ lineSegmentIntersect2d()

std::vector< MathLib::Point3d > GeoLib::lineSegmentIntersect2d ( LineSegment const & ab,
LineSegment const & cd )

A line segment is given by its two end-points. The function checks, if the two line segments (ab) and (cd) intersects. This method checks the intersection only in 2d.

Parameters
abfirst line segment
cdsecond line segment
Returns
empty vector in case there isn't an intersection point, a vector containing one point if the line segments intersect in a single point, a vector containing two points describing the line segment the original line segments are interfering.

Definition at line 446 of file AnalyticalGeometry.cpp.

448{
449 GeoLib::Point const& a{ab.getBeginPoint()};
450 GeoLib::Point const& b{ab.getEndPoint()};
451 GeoLib::Point const& c{cd.getBeginPoint()};
452 GeoLib::Point const& d{cd.getEndPoint()};
453
454 double const orient_abc(getOrientation(a, b, c));
455 double const orient_abd(getOrientation(a, b, d));
456
457 // check if the segment (cd) lies on the left or on the right of (ab)
458 if ((orient_abc > 0 && orient_abd > 0) ||
459 (orient_abc < 0 && orient_abd < 0))
460 {
461 return std::vector<MathLib::Point3d>();
462 }
463
464 // check: (cd) and (ab) are on the same line
465 if (orient_abc == 0.0 && orient_abd == 0.0)
466 {
467 double const eps(std::numeric_limits<double>::epsilon());
468 if (MathLib::sqrDist2d(a, c) < eps && MathLib::sqrDist2d(b, d) < eps)
469 {
470 return {{a, b}};
471 }
472 if (MathLib::sqrDist2d(a, d) < eps && MathLib::sqrDist2d(b, c) < eps)
473 {
474 return {{a, b}};
475 }
476
477 // Since orient_ab and orient_abd vanish, a, b, c, d are on the same
478 // line and for this reason it is enough to check the x-component.
479 auto isPointOnSegment = [](double q, double p0, double p1)
480 {
481 double const t((q - p0) / (p1 - p0));
482 return 0 <= t && t <= 1;
483 };
484
485 // check if c in (ab)
486 if (isPointOnSegment(c[0], a[0], b[0]))
487 {
488 // check if a in (cd)
489 if (isPointOnSegment(a[0], c[0], d[0]))
490 {
491 return {{a, c}};
492 }
493 // check b == c
494 if (MathLib::sqrDist2d(b, c) < eps)
495 {
496 return {{b}};
497 }
498 // check if b in (cd)
499 if (isPointOnSegment(b[0], c[0], d[0]))
500 {
501 return {{b, c}};
502 }
503 // check d in (ab)
504 if (isPointOnSegment(d[0], a[0], b[0]))
505 {
506 return {{c, d}};
507 }
508 std::stringstream err;
509 err.precision(std::numeric_limits<double>::max_digits10);
510 err << ab << " x " << cd;
511 OGS_FATAL(
512 "The case of parallel line segments ({:s}) is not handled yet. "
513 "Aborting.",
514 err.str());
515 }
516
517 // check if d in (ab)
518 if (isPointOnSegment(d[0], a[0], b[0]))
519 {
520 // check if a in (cd)
521 if (isPointOnSegment(a[0], c[0], d[0]))
522 {
523 return {{a, d}};
524 }
525 // check if b==d
526 if (MathLib::sqrDist2d(b, d) < eps)
527 {
528 return {{b}};
529 }
530 // check if b in (cd)
531 if (isPointOnSegment(b[0], c[0], d[0]))
532 {
533 return {{b, d}};
534 }
535 // d in (ab), b not in (cd): check c in (ab)
536 if (isPointOnSegment(c[0], a[0], b[0]))
537 {
538 return {{c, d}};
539 }
540
541 std::stringstream err;
542 err.precision(std::numeric_limits<double>::max_digits10);
543 err << ab << " x " << cd;
544 OGS_FATAL(
545 "The case of parallel line segments ({:s}) is not handled yet. "
546 "Aborting.",
547 err.str());
548 }
549 return std::vector<MathLib::Point3d>();
550 }
551
552 // precondition: points a, b, c are collinear
553 // the function checks if the point c is onto the line segment (a,b)
554 auto isCollinearPointOntoLineSegment = [](MathLib::Point3d const& a,
555 MathLib::Point3d const& b,
556 MathLib::Point3d const& c)
557 {
558 if (b[0] - a[0] != 0)
559 {
560 double const t = (c[0] - a[0]) / (b[0] - a[0]);
561 return 0.0 <= t && t <= 1.0;
562 }
563 if (b[1] - a[1] != 0)
564 {
565 double const t = (c[1] - a[1]) / (b[1] - a[1]);
566 return 0.0 <= t && t <= 1.0;
567 }
568 if (b[2] - a[2] != 0)
569 {
570 double const t = (c[2] - a[2]) / (b[2] - a[2]);
571 return 0.0 <= t && t <= 1.0;
572 }
573 return false;
574 };
575
576 if (orient_abc == 0.0)
577 {
578 if (isCollinearPointOntoLineSegment(a, b, c))
579 {
580 return {{c}};
581 }
582 return std::vector<MathLib::Point3d>();
583 }
584
585 if (orient_abd == 0.0)
586 {
587 if (isCollinearPointOntoLineSegment(a, b, d))
588 {
589 return {{d}};
590 }
591 return std::vector<MathLib::Point3d>();
592 }
593
594 // check if the segment (ab) lies on the left or on the right of (cd)
595 double const orient_cda(getOrientation(c, d, a));
596 double const orient_cdb(getOrientation(c, d, b));
597 if ((orient_cda > 0 && orient_cdb > 0) ||
598 (orient_cda < 0 && orient_cdb < 0))
599 {
600 return std::vector<MathLib::Point3d>();
601 }
602
603 // at this point it is sure that there is an intersection and the system of
604 // linear equations will be invertible
605 // solve the two linear equations (b-a, c-d) (t, s)^T = (c-a) simultaneously
606 Eigen::Matrix2d mat;
607 mat(0, 0) = b[0] - a[0];
608 mat(0, 1) = c[0] - d[0];
609 mat(1, 0) = b[1] - a[1];
610 mat(1, 1) = c[1] - d[1];
611 Eigen::Vector2d rhs{c[0] - a[0], c[1] - a[1]};
612
613 rhs = mat.partialPivLu().solve(rhs);
614 if (0 <= rhs[1] && rhs[1] <= 1.0)
615 {
616 return {MathLib::Point3d{std::array<double, 3>{
617 {c[0] + rhs[1] * (d[0] - c[0]), c[1] + rhs[1] * (d[1] - c[1]),
618 c[2] + rhs[1] * (d[2] - c[2])}}}};
619 }
620 return std::vector<MathLib::Point3d>(); // parameter s not in the valid
621 // range
622}
Orientation getOrientation(MathLib::Point3d const &p0, MathLib::Point3d const &p1, MathLib::Point3d const &p2)
double sqrDist2d(MathLib::Point3d const &p0, MathLib::Point3d const &p1)
Definition Point3d.h:114

References GeoLib::LineSegment::getBeginPoint(), GeoLib::LineSegment::getEndPoint(), getOrientation(), OGS_FATAL, and MathLib::sqrDist2d().

Referenced by MeshGeoToolsLib::computeElementSegmentIntersections().

◆ lineSegmentsIntersect()

bool GeoLib::lineSegmentsIntersect ( const Polyline * ply,
Polyline::SegmentIterator & seg_it0,
Polyline::SegmentIterator & seg_it1,
Point & intersection_pnt )

test for intersections of the line segments of the Polyline

Parameters
plythe polyline
seg_it0iterator pointing to the first segment that has an intersection
seg_it1iterator pointing to the second segment that has an intersection
intersection_pntthe intersection point if the segments intersect
Returns
true, if the polyline contains intersections

Definition at line 252 of file AnalyticalGeometry.cpp.

256{
257 std::size_t const n_segs(ply->getNumberOfSegments());
258 // Neighbouring segments always intersects at a common vertex. The algorithm
259 // checks for intersections of non-neighbouring segments.
260 for (seg_it0 = ply->begin(); seg_it0 != ply->end() - 2; ++seg_it0)
261 {
262 seg_it1 = seg_it0 + 2;
263 std::size_t const seg_num_0 = seg_it0.getSegmentNumber();
264 for (; seg_it1 != ply->end(); ++seg_it1)
265 {
266 // Do not check first and last segment, because they are
267 // neighboured.
268 if (!(seg_num_0 == 0 && seg_it1.getSegmentNumber() == n_segs - 1))
269 {
270 if (lineSegmentIntersect(*seg_it0, *seg_it1, intersection_pnt))
271 {
272 return true;
273 }
274 }
275 }
276 }
277 return false;
278}
std::size_t getSegmentNumber() const
Definition Polyline.cpp:376
std::size_t getNumberOfSegments() const
Definition Polyline.cpp:103

References GeoLib::Polyline::begin(), GeoLib::Polyline::end(), GeoLib::Polyline::getNumberOfSegments(), GeoLib::Polyline::SegmentIterator::getSegmentNumber(), and lineSegmentIntersect().

Referenced by GeoLib::Polygon::splitPolygonAtIntersection().

◆ markUnusedPoints()

void GeoLib::markUnusedPoints ( GEOObjects const & geo_objects,
std::string const & geo_name,
std::vector< bool > & transfer_pnts )

Definition at line 562 of file GEOObjects.cpp.

565{
566 GeoLib::PolylineVec const* const ply_obj(
567 geo_objects.getPolylineVecObj(geo_name));
568 if (ply_obj)
569 {
570 std::vector<GeoLib::Polyline*> const& lines(ply_obj->getVector());
571 for (auto* line : lines)
572 {
573 std::size_t const n_pnts(line->getNumberOfPoints());
574 for (std::size_t i = 0; i < n_pnts; ++i)
575 {
576 transfer_pnts[line->getPointID(i)] = false;
577 }
578 }
579 }
580
581 GeoLib::SurfaceVec const* const sfc_obj(
582 geo_objects.getSurfaceVecObj(geo_name));
583 if (sfc_obj)
584 {
585 std::vector<GeoLib::Surface*> const& surfaces = sfc_obj->getVector();
586 for (auto* sfc : surfaces)
587 {
588 std::size_t const n_tri(sfc->getNumberOfTriangles());
589 for (std::size_t i = 0; i < n_tri; ++i)
590 {
591 GeoLib::Triangle const& t = *(*sfc)[i];
592 transfer_pnts[t[0]] = false;
593 transfer_pnts[t[1]] = false;
594 transfer_pnts[t[2]] = false;
595 }
596 }
597 }
598}
TemplateVec< GeoLib::Surface > SurfaceVec
Definition SurfaceVec.h:17
TemplateVec< GeoLib::Polyline > PolylineVec
class PolylineVec encapsulate a std::vector of Polylines additional one can give the vector of polyli...
Definition PolylineVec.h:16

References GeoLib::GEOObjects::getPolylineVecObj(), GeoLib::GEOObjects::getSurfaceVecObj(), and GeoLib::TemplateVec< T >::getVector().

Referenced by geoPointsToStations().

◆ markUsedPoints() [1/2]

void GeoLib::markUsedPoints ( Polyline const & polyline,
std::vector< bool > & used_points )

Resets the point IDs of the polyline corresponding to the mapping.

Definition at line 479 of file Polyline.cpp.

480{
481 if (polyline.getPointsVec().size() != used_points.size())
482 {
483 OGS_FATAL(
484 "internal error in markUsedPoints(): polyline based on point "
485 "vector of size {}, given used_points has size {}",
486 polyline.getPointsVec().size(), used_points.size());
487 }
488 for (std::size_t i = 0; i < polyline.getNumberOfPoints(); ++i)
489 {
490 used_points[polyline.getPointID(i)] = true;
491 }
492}

References GeoLib::Polyline::getNumberOfPoints(), GeoLib::Polyline::getPointID(), GeoLib::Polyline::getPointsVec(), and OGS_FATAL.

Referenced by main().

◆ markUsedPoints() [2/2]

void GeoLib::markUsedPoints ( Surface const & surface,
std::vector< bool > & used_points )

Definition at line 126 of file Surface.cpp.

127{
128 if (surface.getPointVec()->size() != used_points.size())
129 {
130 OGS_FATAL(
131 "internal error in markUsedPoints(): surface based on point vector "
132 "of size {}, given used_points has size {}",
133 surface.getPointVec()->size(), used_points.size());
134 }
135 for (std::size_t i = 0; i < surface.getNumberOfTriangles(); ++i)
136 {
137 auto const& triangle = *surface[i];
138 for (std::size_t k = 0; k < 3; ++k)
139 {
140 used_points[triangle[k]] = true;
141 }
142 }
143}

References GeoLib::Surface::getNumberOfTriangles(), GeoLib::Surface::getPointVec(), and OGS_FATAL.

◆ operator<<() [1/2]

std::ostream & GeoLib::operator<< ( std::ostream & os,
LineSegment const & s )

Definition at line 80 of file LineSegment.cpp.

81{
82 os << "{(" << s.getBeginPoint() << "), (" << s.getEndPoint() << ")}";
83 return os;
84}

References GeoLib::LineSegment::getBeginPoint(), and GeoLib::LineSegment::getEndPoint().

◆ operator<<() [2/2]

std::ostream & GeoLib::operator<< ( std::ostream & os,
std::pair< GeoLib::LineSegment const &, GeoLib::LineSegment const & > const & seg_pair )

Definition at line 86 of file LineSegment.cpp.

89{
90 os << seg_pair.first << " x " << seg_pair.second;
91 return os;
92}

◆ operator==() [1/4]

bool GeoLib::operator== ( LineSegment const & s0,
LineSegment const & s1 )

Compares two objects of type LineSegment.

Note
The comparison is not strict. Two line segments \(s_0 = (b_0, e_0)\) and \(s_1 = (b_1, e_1)\) are equal, if \(\|b_0-b_1\|^2 < \epsilon\) and \(\|e_0-e_1\|^2 < \epsilon\) or \(\|b_0-e_1\|^2 < \epsilon\) and \(\|e_0-b_1\|^2 < \epsilon\) where \(\epsilon\) is the machine precision of double.

Definition at line 94 of file LineSegment.cpp.

95{
96 double const tol(std::numeric_limits<double>::epsilon());
97 return (MathLib::sqrDist(s0.getBeginPoint(), s1.getBeginPoint()) < tol &&
98 MathLib::sqrDist(s0.getEndPoint(), s1.getEndPoint()) < tol) ||
99 (MathLib::sqrDist(s0.getBeginPoint(), s1.getEndPoint()) < tol &&
100 MathLib::sqrDist(s0.getEndPoint(), s1.getBeginPoint()) < tol);
101}

References GeoLib::LineSegment::getBeginPoint(), GeoLib::LineSegment::getEndPoint(), and MathLib::sqrDist().

◆ operator==() [2/4]

bool GeoLib::operator== ( Polygon const & lhs,
Polygon const & rhs )

comparison operator for polygons

Parameters
lhsthe first polygon
rhsthe second polygon
Returns
true, if the polygons describe the same geometrical object

Definition at line 585 of file Polygon.cpp.

586{
587 if (lhs.getNumberOfPoints() != rhs.getNumberOfPoints())
588 {
589 return false;
590 }
591
592 const std::size_t n(lhs.getNumberOfPoints());
593 const std::size_t start_pnt(lhs.getPointID(0));
594
595 // search start point of first polygon in second polygon
596 bool nfound(true);
597 std::size_t k(0);
598 for (; k < n - 1 && nfound; k++)
599 {
600 if (start_pnt == rhs.getPointID(k))
601 {
602 nfound = false;
603 break;
604 }
605 }
606
607 // case: start point not found in second polygon
608 if (nfound)
609 {
610 return false;
611 }
612
613 // *** determine direction
614 // opposite direction
615 if (k == n - 2)
616 {
617 for (k = 1; k < n - 1; k++)
618 {
619 if (lhs.getPointID(k) != rhs.getPointID(n - 1 - k))
620 {
621 return false;
622 }
623 }
624 return true;
625 }
626
627 // same direction - start point of first polygon at arbitrary position in
628 // second polygon
629 if (lhs.getPointID(1) == rhs.getPointID(k + 1))
630 {
631 std::size_t j(k + 2);
632 for (; j < n - 1; j++)
633 {
634 if (lhs.getPointID(j - k) != rhs.getPointID(j))
635 {
636 return false;
637 }
638 }
639 j = 0; // new start point at second polygon
640 for (; j < k + 1; j++)
641 {
642 if (lhs.getPointID(n - (k + 2) + j + 1) != rhs.getPointID(j))
643 {
644 return false;
645 }
646 }
647 return true;
648 }
649 // opposite direction with start point of first polygon at arbitrary
650 // position
651 // *** ATTENTION
652 WARN(
653 "operator==(Polygon const& lhs, Polygon const& rhs) - not tested case "
654 "(implementation is probably buggy) - please contact "
655 "thomas.fischer@ufz.de mentioning the problem.");
656 // in second polygon
657 if (lhs.getPointID(1) == rhs.getPointID(k - 1))
658 {
659 std::size_t j(k - 2);
660 for (; j > 0; j--)
661 {
662 if (lhs.getPointID(k - 2 - j) != rhs.getPointID(j))
663 {
664 return false;
665 }
666 }
667 // new start point at second polygon - the point n-1 of a polygon is
668 // equal to the first point of the polygon (for this reason: n-2)
669 j = n - 2;
670 for (; j > k - 1; j--)
671 {
672 if (lhs.getPointID(n - 2 + j + k - 2) != rhs.getPointID(j))
673 {
674 return false;
675 }
676 }
677 return true;
678 }
679 return false;
680}

◆ operator==() [3/4]

bool GeoLib::operator== ( Polyline const & lhs,
Polyline const & rhs )

comparison operator

Parameters
lhsfirst polyline
rhssecond polyline
Returns
true, if the polylines consists of the same sequence of line segments

Definition at line 522 of file Polyline.cpp.

523{
524 if (lhs.getNumberOfPoints() != rhs.getNumberOfPoints())
525 {
526 return false;
527 }
528
529 const std::size_t n(lhs.getNumberOfPoints());
530 for (std::size_t k(0); k < n; k++)
531 {
532 if (lhs.getPointID(k) != rhs.getPointID(k))
533 {
534 return false;
535 }
536 }
537
538 return true;
539}

References GeoLib::Polyline::getNumberOfPoints(), and GeoLib::Polyline::getPointID().

◆ operator==() [4/4]

bool GeoLib::operator== ( Surface const & lhs,
Surface const & rhs )

Definition at line 103 of file Surface.cpp.

104{
105 return &lhs == &rhs;
106}

◆ parallel()

bool GeoLib::parallel ( Eigen::Vector3d v,
Eigen::Vector3d w )

Check if the two vectors \(v, w \in R^3\) are in parallel

Parameters
vfirst vector
wsecond vector
Returns
true if the vectors are in parallel, else false

Definition at line 72 of file AnalyticalGeometry.cpp.

73{
74 const double eps(std::numeric_limits<double>::epsilon());
75 double const eps_squared = eps * eps;
76
77 // check degenerated cases
78 if (v.squaredNorm() < eps_squared)
79 {
80 return false;
81 }
82
83 if (w.squaredNorm() < eps_squared)
84 {
85 return false;
86 }
87
88 v.normalize();
89 w.normalize();
90
91 bool parallel(true);
92 if (std::abs(v[0] - w[0]) > eps)
93 {
94 parallel = false;
95 }
96 if (std::abs(v[1] - w[1]) > eps)
97 {
98 parallel = false;
99 }
100 if (std::abs(v[2] - w[2]) > eps)
101 {
102 parallel = false;
103 }
104
105 if (!parallel)
106 {
107 parallel = true;
108 // change sense of direction of v_normalised
109 v *= -1.0;
110 // check again
111 if (std::abs(v[0] - w[0]) > eps)
112 {
113 parallel = false;
114 }
115 if (std::abs(v[1] - w[1]) > eps)
116 {
117 parallel = false;
118 }
119 if (std::abs(v[2] - w[2]) > eps)
120 {
121 parallel = false;
122 }
123 }
124
125 return parallel;
126}

References parallel().

Referenced by lineSegmentIntersect(), and parallel().

◆ pointsAreIdentical()

bool GeoLib::pointsAreIdentical ( const std::vector< Point * > & pnt_vec,
std::size_t i,
std::size_t j,
double prox )

Definition at line 541 of file Polyline.cpp.

545{
546 if (i == j)
547 {
548 return true;
549 }
550 return MathLib::sqrDist(*pnt_vec[i], *pnt_vec[j]) < prox;
551}

References MathLib::sqrDist().

Referenced by GeoLib::Polyline::constructPolylineFromSegments().

◆ resetPointIDs() [1/2]

void GeoLib::resetPointIDs ( Polyline & polyline,
std::vector< std::size_t > const & mapping )

Resets the point IDs of the polyline corresponding to the mapping.

Definition at line 464 of file Polyline.cpp.

465{
466 if (polyline.getPointsVec().size() != mapping.size())
467 {
468 OGS_FATAL(
469 "internal error in resetPointIDs(): polyline based on point vector "
470 "of size {}, given mapping has size {}",
471 polyline.getPointsVec().size(), mapping.size());
472 }
473 for (std::size_t i = 0; i < polyline.getNumberOfPoints(); ++i)
474 {
475 polyline.setPointID(i, mapping[polyline.getPointID(i)]);
476 }
477}
void setPointID(std::size_t idx, std::size_t id)
Definition Polyline.cpp:162
std::vector< Point * > const & getPointsVec() const
Definition Polyline.cpp:174

References GeoLib::Polyline::getNumberOfPoints(), GeoLib::Polyline::getPointID(), GeoLib::Polyline::getPointsVec(), OGS_FATAL, and GeoLib::Polyline::setPointID().

Referenced by main(), and FileIO::GMSH::GMSHPolygonTree::writeAdditionalPointData().

◆ resetPointIDs() [2/2]

void GeoLib::resetPointIDs ( Surface & surface,
std::vector< std::size_t > const & mapping )

Resets the point IDs of the surface corresponding to the mapping.

Definition at line 108 of file Surface.cpp.

109{
110 if (surface.getPointVec()->size() != mapping.size())
111 {
112 OGS_FATAL(
113 "internal error in resetPointIDs(): surface based on point vector "
114 "of size {}, given mapping vector has size {}",
115 surface.getPointVec()->size(), mapping.size());
116 }
117 for (std::size_t i = 0; i < surface.getNumberOfTriangles(); ++i)
118 {
119 auto& triangle = *surface[i];
120 const_cast<std::size_t&>(triangle[0]) = mapping[triangle[0]];
121 const_cast<std::size_t&>(triangle[1]) = mapping[triangle[1]];
122 const_cast<std::size_t&>(triangle[2]) = mapping[triangle[2]];
123 }
124}
std::size_t getNumberOfTriangles() const
Definition Surface.cpp:76
const std::vector< Point * > * getPointVec() const

References GeoLib::Surface::getNumberOfTriangles(), GeoLib::Surface::getPointVec(), and OGS_FATAL.

◆ rotatePoints() [1/3]

template<typename InputIterator>
void GeoLib::rotatePoints ( Eigen::Matrix3d const & rot_mat,
InputIterator pnts_begin,
InputIterator pnts_end )

rotate points according to the rotation matrix

Parameters
rot_mat3x3 dimensional rotation matrix
pnts_beginIterator pointing to the initial element in a vector of points to be rotated
pnts_endIterator pointing to the element following the last element in a vector of points to be rotated

Definition at line 70 of file AnalyticalGeometry-impl.h.

72{
73 for (auto it = pnts_begin; it != pnts_end; ++it)
74 {
75 (*it)->asEigenVector3d() = rot_mat * (*it)->asEigenVector3d();
76 }
77}

Referenced by MeshGeoToolsLib::markNodesOutSideOfPolygon(), rotateGeometryToXY(), rotateMesh(), rotatePoints(), rotatePoints(), rotatePointsToXY(), rotatePolygonPointsToXY(), and FileIO::GMSH::GMSHInterface::writeGMSHInputFile().

◆ rotatePoints() [2/3]

void GeoLib::rotatePoints ( Eigen::Matrix3d const & rot_mat,
std::vector< GeoLib::Point * > & pnts )

Definition at line 280 of file AnalyticalGeometry.cpp.

282{
283 rotatePoints(rot_mat, pnts.begin(), pnts.end());
284}
void rotatePoints(Eigen::Matrix3d const &rot_mat, InputIterator pnts_begin, InputIterator pnts_end)

References rotatePoints().

◆ rotatePoints() [3/3]

template<typename P>
void GeoLib::rotatePoints ( Eigen::Matrix3d const & rot_mat,
std::vector< P * > const & pnts )

rotate points according to the rotation matrix

Parameters
rot_mat3x3 dimensional rotation matrix
pntsvector of points

Definition at line 104 of file AnalyticalGeometry-impl.h.

105{
106 rotatePoints(rot_mat, pnts.begin(), pnts.end());
107}

References rotatePoints().

◆ rotatePointsToXY() [1/3]

template<typename InputIterator1, typename InputIterator2>
Eigen::Matrix3d GeoLib::rotatePointsToXY ( InputIterator1 p_pnts_begin,
InputIterator1 p_pnts_end,
InputIterator2 r_pnts_begin,
InputIterator2 r_pnts_end )

rotate points to X-Y plane

Parameters
p_pnts_beginIterator pointing to the initial element in a vector of points used for computing a rotation matrix
p_pnts_endIterator pointing to the element following the last point in a vector of points used for computing a rotation matrix
r_pnts_beginIterator pointing to the initial element in a vector of points to be rotated
r_pnts_endIterator pointing to the element following the last point in a vector of points to be rotated Points are rotated using a rotation matrix computed from the first three points in the vector. Point coordinates are modified as a result of the rotation.

Definition at line 80 of file AnalyticalGeometry-impl.h.

84{
85 assert(std::distance(p_pnts_begin, p_pnts_end) > 2);
86
87 // compute the plane normal
88 auto const [plane_normal, d] =
89 GeoLib::getNewellPlane(p_pnts_begin, p_pnts_end);
90
91 // rotate points into x-y-plane
92 Eigen::Matrix3d const rot_mat = computeRotationMatrixToXY(plane_normal);
93 rotatePoints(rot_mat, r_pnts_begin, r_pnts_end);
94
95 for (auto it = r_pnts_begin; it != r_pnts_end; ++it)
96 {
97 (*(*it))[2] = 0.0; // should be -= d but there are numerical errors
98 }
99
100 return rot_mat;
101}
Eigen::Matrix3d computeRotationMatrixToXY(Eigen::Vector3d const &n)

References computeRotationMatrixToXY(), getNewellPlane(), and rotatePoints().

Referenced by GeoLib::EarClippingTriangulation::EarClippingTriangulation(), GeoLib::Polygon::ensureCCWOrientation(), rotatePointsToXY(), and FileIO::GMSH::GMSHInterface::writeGMSHInputFile().

◆ rotatePointsToXY() [2/3]

Eigen::Matrix3d GeoLib::rotatePointsToXY ( std::vector< GeoLib::Point * > & pnts)

Definition at line 349 of file AnalyticalGeometry.cpp.

350{
351 return rotatePointsToXY(pnts.begin(), pnts.end(), pnts.begin(), pnts.end());
352}
Eigen::Matrix3d rotatePointsToXY(InputIterator1 p_pnts_begin, InputIterator1 p_pnts_end, InputIterator2 r_pnts_begin, InputIterator2 r_pnts_end)

References rotatePointsToXY().

◆ rotatePointsToXY() [3/3]

Eigen::Matrix3d GeoLib::rotatePointsToXY ( std::vector< Point * > & pnts)

rotate points to X-Y plane

Parameters
pntsa vector of points with a minimum length of three. Points are rotated using a rotation matrix computed from the first three points in the vector. Point coordinates are modified as a result of the rotation.

◆ rotatePolygonPointsToXY()

std::tuple< std::vector< GeoLib::Point * >, Eigen::Vector3d > GeoLib::rotatePolygonPointsToXY ( GeoLib::Polygon const & polygon_in)

Function rotates a polygon to the xy plane. For this reason, (1) the points of the given polygon are copied, (2) a so called Newell plane is computed (getNewellPlane()) and the points are rotated, (3) for accuracy reasons the \(z\) coordinates of the rotated points are set to zero

See also
getNewellPlane()
Parameters
polygon_ina copy of the polygon_in polygon will be rotated
Returns
vector of rotated points and normal based on the original Newell plane

Definition at line 423 of file AnalyticalGeometry.cpp.

424{
425 // 1 copy all points
426 std::vector<GeoLib::Point*> polygon_points;
427 polygon_points.reserve(polygon_in.getNumberOfPoints());
428 for (std::size_t k(0); k < polygon_in.getNumberOfPoints(); k++)
429 {
430 polygon_points.push_back(new GeoLib::Point(*(polygon_in.getPoint(k))));
431 }
432
433 // 2 rotate points
434 auto [plane_normal, d_polygon] = GeoLib::getNewellPlane(polygon_points);
435 Eigen::Matrix3d const rot_mat =
437 GeoLib::rotatePoints(rot_mat, polygon_points);
438
439 // 3 set z coord to zero
440 std::for_each(polygon_points.begin(), polygon_points.end(),
441 [](GeoLib::Point* p) { (*p)[2] = 0.0; });
442
443 return {polygon_points, plane_normal};
444}

References computeRotationMatrixToXY(), getNewellPlane(), GeoLib::Polyline::getNumberOfPoints(), GeoLib::Polyline::getPoint(), and rotatePoints().

Referenced by MeshGeoToolsLib::markNodesOutSideOfPolygon().

◆ sortSegments() [1/2]

void GeoLib::sortSegments ( MathLib::Point3d const & seg_beg_pnt,
std::vector< GeoLib::LineSegment > & sub_segments )

Definition at line 624 of file AnalyticalGeometry.cpp.

626{
627 double const eps(std::numeric_limits<double>::epsilon());
628
629 auto findNextSegment =
630 [&eps](MathLib::Point3d const& seg_beg_pnt,
631 std::vector<GeoLib::LineSegment>& sub_segments,
632 std::vector<GeoLib::LineSegment>::iterator& sub_seg_it)
633 {
634 if (sub_seg_it == sub_segments.end())
635 {
636 return;
637 }
638 // find appropriate segment for the given segment begin point
639 auto act_beg_seg_it = std::find_if(
640 sub_seg_it, sub_segments.end(),
641 [&seg_beg_pnt, &eps](GeoLib::LineSegment const& seg)
642 {
643 return MathLib::sqrDist(seg_beg_pnt, seg.getBeginPoint()) <
644 eps ||
645 MathLib::sqrDist(seg_beg_pnt, seg.getEndPoint()) < eps;
646 });
647 if (act_beg_seg_it == sub_segments.end())
648 {
649 return;
650 }
651 // if necessary correct orientation of segment, i.e. swap beg and
652 // end
653 if (MathLib::sqrDist(seg_beg_pnt, act_beg_seg_it->getEndPoint()) <
654 MathLib::sqrDist(seg_beg_pnt, act_beg_seg_it->getBeginPoint()))
655 {
656 std::swap(act_beg_seg_it->getBeginPoint(),
657 act_beg_seg_it->getEndPoint());
658 }
659 assert(sub_seg_it != sub_segments.end());
660 // exchange segments within the container
661 if (sub_seg_it != act_beg_seg_it)
662 {
663 std::swap(*sub_seg_it, *act_beg_seg_it);
664 }
665 };
666
667 // find start segment
668 auto seg_it = sub_segments.begin();
669 findNextSegment(seg_beg_pnt, sub_segments, seg_it);
670
671 while (seg_it != sub_segments.end())
672 {
673 MathLib::Point3d& new_seg_beg_pnt(seg_it->getEndPoint());
674 seg_it++;
675 if (seg_it != sub_segments.end())
676 {
677 findNextSegment(new_seg_beg_pnt, sub_segments, seg_it);
678 }
679 }
680}

References MathLib::sqrDist().

Referenced by MeshGeoToolsLib::mapLineSegment().

◆ sortSegments() [2/2]

void GeoLib::sortSegments ( MathLib::Point3d const & seg_beg_pnt,
std::vector< LineSegment > & sub_segments )

Sorts the vector of segments such that the \(i\)-th segment is connected with the \(i+1\)st segment, i.e. the end point of the \(i\)-th segment is the start point of the \(i+1\)st segment. The current implementation requires that all segments have to be connectable. In order to obtain a unique result the segments are sorted such that the begin point of the first segment is seg_beg_pnt.

◆ triangleLineIntersection()

std::unique_ptr< Point > GeoLib::triangleLineIntersection ( MathLib::Point3d const & a,
MathLib::Point3d const & b,
MathLib::Point3d const & c,
MathLib::Point3d const & p,
MathLib::Point3d const & q )

Calculates the intersection points of a line PQ and a triangle ABC. This method requires ABC to be counterclockwise and PQ to point downward.

Returns
Intersection point or nullptr if there is no intersection.

Definition at line 354 of file AnalyticalGeometry.cpp.

358{
359 Eigen::Vector3d const pq = q.asEigenVector3d() - p.asEigenVector3d();
360 Eigen::Vector3d const pa = a.asEigenVector3d() - p.asEigenVector3d();
361 Eigen::Vector3d const pb = b.asEigenVector3d() - p.asEigenVector3d();
362 Eigen::Vector3d const pc = c.asEigenVector3d() - p.asEigenVector3d();
363
364 double u = pq.cross(pc).dot(pb);
365 if (u < 0)
366 {
367 return nullptr;
368 }
369 double v = pq.cross(pa).dot(pc);
370 if (v < 0)
371 {
372 return nullptr;
373 }
374 double w = pq.cross(pb).dot(pa);
375 if (w < 0)
376 {
377 return nullptr;
378 }
379
380 const double denom(1.0 / (u + v + w));
381 u *= denom;
382 v *= denom;
383 w *= denom;
384 return std::make_unique<GeoLib::Point>(u * a[0] + v * b[0] + w * c[0],
385 u * a[1] + v * b[1] + w * c[1],
386 u * a[2] + v * b[2] + w * c[2]);
387}

References MathLib::Point3d::asEigenVector3d().

Referenced by MeshGeoToolsLib::GeoMapper::getMeshElevation().