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 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155
|
//
// Test Suite for C-API GEOSisValidDetail
#include <tut/tut.hpp>
// geos
#include <geos_c.h>
// std
#include <cctype>
#include "capi_test_utils.h"
namespace tut {
//
// Test Group
//
// Common data used in test cases.
struct test_capiisvaliddetail_data : public capitest::utility {
GEOSGeometry* loc_;
char* reason_;
test_capiisvaliddetail_data() : loc_(nullptr), reason_(nullptr)
{
}
void
strToUpper(std::string& str)
{
using std::toupper;
using std::string;
for(string::size_type i = 0, len = str.size(); i < len; ++i) {
str[i] = static_cast<string::value_type>(toupper(str[i]));
}
}
~test_capiisvaliddetail_data()
{
GEOSGeom_destroy(loc_);
GEOSFree(reason_);
}
};
typedef test_group<test_capiisvaliddetail_data> group;
typedef group::object object;
group test_capiisvaliddetail_group("capi::GEOSisValidDetail");
//
// Test Cases
//
// Flag values
template<>
template<>
void object::test<1>
()
{
ensure_equals(GEOSVALID_ALLOW_SELFTOUCHING_RING_FORMING_HOLE, 1);
}
// Valid case
template<>
template<>
void object::test<2>
()
{
// Looks invalid (self-intersecting) but isn't
// (is non-simple though)
geom1_ = GEOSGeomFromWKT("LINESTRING(0 0, 10 0, 5 -5, 5 5)");
int r = GEOSisValidDetail(geom1_, 0, &reason_, &loc_);
ensure_equals(r, 1); // valid
ensure_equals(reason_, (void*)nullptr);
ensure_equals(loc_, (void*)nullptr);
}
// Invalid coordinate
template<>
template<>
void object::test<3>
()
{
geom1_ = GEOSGeomFromWKT("LINESTRING(0 0, 10 0, NaN -5)");
ensure(nullptr != geom1_);
int r = GEOSisValidDetail(geom1_, 0, &reason_, &loc_);
std::string wkt = toWKT(loc_);
strToUpper(wkt);
ensure_equals(r, 0); // invalid
ensure_equals(std::string(reason_), std::string("Invalid Coordinate"));
std::string exp1 = "POINT (NAN -5)";
std::string exp2 = "POINT (-1#IND -5)";
// http://trac.osgeo.org/geos/ticket/656
std::string exp3 = "POINT (1.#QNAN -5)";
std::stringstream ss;
ss << "Expected '" << exp1 << "' or '" << exp2 << "' or '" << exp3 << "', Obtained '" << wkt;
ensure(ss.str(),
wkt == exp1 ||
wkt == exp2 ||
wkt == exp3);
}
// Self intersecting ring forming hole
template<>
template<>
void object::test<4>
()
{
geom1_ = GEOSGeomFromWKT("POLYGON((0 1, -10 10, 10 10, 0 1, 4 6, -4 6, 0 1))");
int r = GEOSisValidDetail(geom1_, 0, &reason_, &loc_);
ensure_equals(r, 0); // invalid
ensure_equals(std::string(reason_), std::string("Ring Self-intersection"));
ensure_equals(toWKT(loc_), "POINT (0 1)");
}
// Self intersecting ring forming hole (with ESRI flag)
template<>
template<>
void object::test<5>
()
{
geom1_ = GEOSGeomFromWKT("POLYGON((0 1, -10 10, 10 10, 0 1, 4 6, -4 6, 0 1))");
int flags = GEOSVALID_ALLOW_SELFTOUCHING_RING_FORMING_HOLE;
int r = GEOSisValidDetail(geom1_, flags, &reason_, &loc_);
ensure_equals(r, 1); // valid
ensure_equals(reason_, (void*)nullptr);
ensure_equals(loc_, (void*)nullptr);
}
// Check it is possible to not request details
template<>
template<>
void object::test<6>
()
{
geom1_ = GEOSGeomFromWKT("POLYGON((0 1, -10 10, 10 10, 0 1, 4 6, -4 6, 0 1))");
int r = GEOSisValidDetail(geom1_, 0, nullptr, nullptr);
ensure_equals(r, 0); // invalid
}
template<>
template<>
void object::test<7>()
{
input_ = fromWKT("CURVEPOLYGON (COMPOUNDCURVE( CIRCULARSTRING (0 0, 1 1, 2 0), (2 0, 1 1)))");
ensure(input_ != nullptr);
char ret = GEOSisValidDetail(input_, 0, nullptr, nullptr);
ensure_equals("error raised on curved geometry", ret, 2);
}
} // namespace tut
|