1 /**********************************************************************
3 * GEOS - Geometry Engine Open Source
4 * http://geos.osgeo.org
6 * Copyright (C) 2006 Refractions Research Inc.
8 * This is free software; you can redistribute and/or modify it under
9 * the terms of the GNU Lesser General Licence as published
10 * by the Free Software Foundation.
11 * See the COPYING file for more information.
13 **********************************************************************
15 * Last port: noding/snapround/HotPixel.java r320 (JTS-1.12)
17 **********************************************************************/
19 #include <geos/noding/snapround/HotPixel.h>
20 #include <geos/noding/NodedSegmentString.h>
21 #include <geos/algorithm/LineIntersector.h>
22 #include <geos/geom/Coordinate.h>
25 # include "geos/noding/snapround/HotPixel.inl"
28 #include <algorithm> // for std::min and std::max
33 using namespace geos::algorithm
;
34 using namespace geos::geom
;
37 namespace noding
{ // geos.noding
38 namespace snapround
{ // geos.noding.snapround
40 HotPixel::HotPixel(const Coordinate
& newPt
, double newScaleFactor
,
41 LineIntersector
& newLi
)
46 scaleFactor(newScaleFactor
)
48 if (scaleFactor
!= 1.0) {
56 HotPixel::getSafeEnvelope() const
58 static const double SAFE_ENV_EXPANSION_FACTOR
= 0.75;
60 if (safeEnv
.get() == NULL
) {
61 double safeTolerance
= SAFE_ENV_EXPANSION_FACTOR
/ scaleFactor
;
62 safeEnv
= auto_ptr
<Envelope
>(new Envelope(originalPt
.x
- safeTolerance
,
63 originalPt
.x
+ safeTolerance
,
64 originalPt
.y
- safeTolerance
,
65 originalPt
.y
+ safeTolerance
73 HotPixel::initCorners(const Coordinate
& pt
)
75 double tolerance
= 0.5;
76 minx
= pt
.x
- tolerance
;
77 maxx
= pt
.x
+ tolerance
;
78 miny
= pt
.y
- tolerance
;
79 maxy
= pt
.y
+ tolerance
;
82 corner
[0] = Coordinate(maxx
, maxy
);
83 corner
[1] = Coordinate(minx
, maxy
);
84 corner
[2] = Coordinate(minx
, miny
);
85 corner
[3] = Coordinate(maxx
, maxy
);
89 HotPixel::intersects(const Coordinate
& p0
,
90 const Coordinate
& p1
) const
92 if (scaleFactor
== 1.0) return intersectsScaled(p0
, p1
);
94 copyScaled(p0
, p0Scaled
);
95 copyScaled(p1
, p1Scaled
);
97 return intersectsScaled(p0Scaled
, p1Scaled
);
102 HotPixel::intersectsScaled(const Coordinate
& p0
,
103 const Coordinate
& p1
) const
106 double const segMinx
= (std::min
)(p0
.x
, p1
.x
);
107 double const segMaxx
= (std::max
)(p0
.x
, p1
.x
);
108 double const segMiny
= (std::min
)(p0
.y
, p1
.y
);
109 double const segMaxy
= (std::max
)(p0
.y
, p1
.y
);
111 bool isOutsidePixelEnv
= maxx
< segMinx
116 if (isOutsidePixelEnv
) return false;
118 bool intersects
= intersectsToleranceSquare(p0
, p1
);
120 // Found bad envelope test
121 assert(!(isOutsidePixelEnv
&& intersects
));
128 HotPixel::intersectsToleranceSquare(const Coordinate
& p0
,
129 const Coordinate
& p1
) const
131 bool intersectsLeft
= false;
132 bool intersectsBottom
= false;
134 li
.computeIntersection(p0
, p1
, corner
[0], corner
[1]);
135 if (li
.isProper()) return true;
137 li
.computeIntersection(p0
, p1
, corner
[1], corner
[2]);
138 if (li
.isProper()) return true;
139 if (li
.hasIntersection()) intersectsLeft
= true;
141 li
.computeIntersection(p0
, p1
, corner
[2], corner
[3]);
142 if (li
.isProper()) return true;
143 if (li
.hasIntersection()) intersectsBottom
= true;
145 li
.computeIntersection(p0
, p1
, corner
[3], corner
[0]);
146 if (li
.isProper()) return true;
148 if (intersectsLeft
&& intersectsBottom
) return true;
150 if (p0
.equals2D(pt
)) return true;
151 if (p1
.equals2D(pt
)) return true;
158 HotPixel::intersectsPixelClosure(const Coordinate
& p0
,
159 const Coordinate
& p1
)
161 li
.computeIntersection(p0
, p1
, corner
[0], corner
[1]);
162 if (li
.hasIntersection()) return true;
163 li
.computeIntersection(p0
, p1
, corner
[1], corner
[2]);
164 if (li
.hasIntersection()) return true;
165 li
.computeIntersection(p0
, p1
, corner
[2], corner
[3]);
166 if (li
.hasIntersection()) return true;
167 li
.computeIntersection(p0
, p1
, corner
[3], corner
[0]);
168 if (li
.hasIntersection()) return true;
174 HotPixel::addSnappedNode(NodedSegmentString
& segStr
, size_t segIndex
)
176 const Coordinate
& p0
= segStr
.getCoordinate(segIndex
);
177 const Coordinate
& p1
= segStr
.getCoordinate(segIndex
+ 1);
179 if (intersects(p0
, p1
))
181 //cout << "snapped: " << snapPt << endl;
182 segStr
.addIntersection(getCoordinate(), segIndex
);
189 } // namespace geos.noding.snapround
190 } // namespace geos.noding
193 /**********************************************************************
195 * Revision 1.8 2006/05/03 17:51:24 strk
196 * system headers included after package headers
198 * Revision 1.7 2006/03/24 09:52:41 strk
199 * USE_INLINE => GEOS_INLINE
201 * Revision 1.6 2006/03/14 12:55:56 strk
202 * Headers split: geomgraphindex.h, nodingSnapround.h
204 * Revision 1.5 2006/03/03 10:46:21 strk
205 * Removed 'using namespace' from headers, added missing headers in .cpp files, removed useless includes in headers (bug#46)
207 * Revision 1.4 2006/02/21 16:53:49 strk
208 * MCIndexPointSnapper, MCIndexSnapRounder
210 * Revision 1.3 2006/02/19 19:46:49 strk
211 * Packages <-> namespaces mapping for most GEOS internal code (uncomplete, but working). Dir-level libs for index/ subdirs.
213 * Revision 1.2 2006/02/18 21:08:09 strk
214 * - new CoordinateSequence::applyCoordinateFilter method (slow but useful)
215 * - SegmentString::getCoordinates() doesn't return a clone anymore.
216 * - SegmentString::getCoordinatesRO() obsoleted.
217 * - SegmentString constructor does not promises constness of passed
218 * CoordinateSequence anymore.
219 * - NEW ScaledNoder class
220 * - Stubs for MCIndexPointSnapper and MCIndexSnapRounder
221 * - Simplified internal interaces of OffsetCurveBuilder and OffsetCurveSetBuilder
223 * Revision 1.1 2006/02/14 13:28:26 strk
224 * New SnapRounding code ported from JTS-1.7 (not complete yet).
225 * Buffer op optimized by using new snaprounding code.
226 * Leaks fixed in XMLTester.
228 **********************************************************************/