1 /****************************************************************************
2 **
3 ** Copyright (C) 2016 The Qt Company Ltd.
4 ** Contact: https://www.qt.io/licensing/
5 **
6 ** This file is part of the test suite of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:GPL-EXCEPT$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and The Qt Company. For licensing terms
14 ** and conditions see https://www.qt.io/terms-conditions. For further
15 ** information use the contact form at https://www.qt.io/contact-us.
16 **
17 ** GNU General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU
19 ** General Public License version 3 as published by the Free Software
20 ** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
21 ** included in the packaging of this file. Please review the following
22 ** information to ensure the GNU General Public License requirements will
23 ** be met: https://www.gnu.org/licenses/gpl-3.0.html.
24 **
25 ** $QT_END_LICENSE$
26 **
27 ****************************************************************************/
28
29 #include <QtTest/QtTest>
30 #include <QtPositioning/QGeoCoordinate>
31 #include <QtPositioning/QGeoRectangle>
32 #include <QtPositioning/QGeoPath>
33
34 QT_USE_NAMESPACE
35
36 class tst_QGeoPath : public QObject
37 {
38 Q_OBJECT
39
40 private slots:
41 void defaultConstructor();
42 void listConstructor();
43 void assignment();
44
45 void comparison();
46 void type();
47
48 void path();
49 void width();
50 void size();
51
52 void translate_data();
53 void translate();
54
55 void valid_data();
56 void valid();
57
58 void contains_data();
59 void contains();
60
61 void boundingGeoRectangle_data();
62 void boundingGeoRectangle();
63
64 void extendShape();
65 void extendShape_data();
66 };
67
defaultConstructor()68 void tst_QGeoPath::defaultConstructor()
69 {
70 QGeoPath p;
71 QVERIFY(!p.path().size());
72 QCOMPARE(p.width(), qreal(0.0));
73 QCOMPARE(p.length(), double(0.0));
74 }
75
listConstructor()76 void tst_QGeoPath::listConstructor()
77 {
78 QList<QGeoCoordinate> coords;
79 coords.append(QGeoCoordinate(1,1));
80 coords.append(QGeoCoordinate(2,2));
81 coords.append(QGeoCoordinate(3,0));
82
83 QGeoPath p(coords, 1.0);
84 QCOMPARE(p.width(), qreal(1.0));
85 QCOMPARE(p.path().size(), 3);
86
87 for (const QGeoCoordinate &c : coords) {
88 QCOMPARE(p.path().contains(c), true);
89 }
90 }
91
assignment()92 void tst_QGeoPath::assignment()
93 {
94 QGeoPath p1;
95 QList<QGeoCoordinate> coords;
96 coords.append(QGeoCoordinate(1,1));
97 coords.append(QGeoCoordinate(2,2));
98 coords.append(QGeoCoordinate(3,0));
99 QGeoPath p2(coords, 1.0);
100
101 QVERIFY(p1 != p2);
102
103 p1 = p2;
104 QCOMPARE(p1.path(), coords);
105 QCOMPARE(p1.width(), 1.0);
106 QCOMPARE(p1, p2);
107
108 // Assign c1 to an area
109 QGeoShape area = p1;
110 QCOMPARE(area.type(), p1.type());
111 QVERIFY(area == p1);
112
113 // Assign the area back to a bounding circle
114 QGeoPath p3 = area;
115 QCOMPARE(p3.path(), coords);
116 QCOMPARE(p3.width(), 1.0);
117
118 // Check that the copy is not modified when modifying the original.
119 p1.setWidth(2.0);
120 QVERIFY(p3.width() != p1.width());
121 QVERIFY(p3 != p1);
122 }
123
comparison()124 void tst_QGeoPath::comparison()
125 {
126 QList<QGeoCoordinate> coords;
127 coords.append(QGeoCoordinate(1,1));
128 coords.append(QGeoCoordinate(2,2));
129 coords.append(QGeoCoordinate(3,0));
130 QList<QGeoCoordinate> coords2;
131 coords2.append(QGeoCoordinate(3,1));
132 coords2.append(QGeoCoordinate(4,2));
133 coords2.append(QGeoCoordinate(3,0));
134 QGeoPath c1(coords, qreal(50.0));
135 QGeoPath c2(coords, qreal(50.0));
136 QGeoPath c3(coords, qreal(35.0));
137 QGeoPath c4(coords2, qreal(50.0));
138
139 QVERIFY(c1 == c2);
140 QVERIFY(!(c1 != c2));
141
142 QVERIFY(!(c1 == c3));
143 QVERIFY(c1 != c3);
144
145 QVERIFY(!(c1 == c4));
146 QVERIFY(c1 != c4);
147
148 QVERIFY(!(c2 == c3));
149 QVERIFY(c2 != c3);
150
151 QGeoRectangle b1(QGeoCoordinate(20,20),QGeoCoordinate(10,30));
152 QVERIFY(!(c1 == b1));
153 QVERIFY(c1 != b1);
154
155 QGeoShape *c2Ptr = &c2;
156 QVERIFY(c1 == *c2Ptr);
157 QVERIFY(!(c1 != *c2Ptr));
158
159 QGeoShape *c3Ptr = &c3;
160 QVERIFY(!(c1 == *c3Ptr));
161 QVERIFY(c1 != *c3Ptr);
162 }
163
type()164 void tst_QGeoPath::type()
165 {
166 QGeoPath c;
167 QCOMPARE(c.type(), QGeoShape::PathType);
168 }
169
path()170 void tst_QGeoPath::path()
171 {
172 QList<QGeoCoordinate> coords;
173 coords.append(QGeoCoordinate(1,1));
174 coords.append(QGeoCoordinate(2,2));
175 coords.append(QGeoCoordinate(3,0));
176
177 QGeoPath p;
178 p.setPath(coords);
179 QCOMPARE(p.path().size(), 3);
180
181 for (const QGeoCoordinate &c : coords) {
182 QCOMPARE(p.path().contains(c), true);
183 }
184
185 p.clearPath();
186 QCOMPARE(p.path().size(), 0);
187 QVERIFY(p.boundingGeoRectangle().isEmpty());
188 }
189
width()190 void tst_QGeoPath::width()
191 {
192 QGeoPath p;
193 p.setWidth(10.0);
194 QCOMPARE(p.width(), qreal(10.0));
195 }
196
size()197 void tst_QGeoPath::size()
198 {
199 QList<QGeoCoordinate> coords;
200
201 QGeoPath p1(coords, 3);
202 QCOMPARE(p1.size(), coords.size());
203
204 coords.append(QGeoCoordinate(1,1));
205 QGeoPath p2(coords, 3);
206 QCOMPARE(p2.size(), coords.size());
207
208 coords.append(QGeoCoordinate(2,2));
209 QGeoPath p3(coords, 3);
210 QCOMPARE(p3.size(), coords.size());
211
212 coords.append(QGeoCoordinate(3,0));
213 QGeoPath p4(coords, 3);
214 QCOMPARE(p4.size(), coords.size());
215
216 p4.removeCoordinate(2);
217 QCOMPARE(p4.size(), coords.size() - 1);
218
219 p4.removeCoordinate(coords.first());
220 QCOMPARE(p4.size(), coords.size() - 2);
221 }
222
translate_data()223 void tst_QGeoPath::translate_data()
224 {
225 QTest::addColumn<QGeoCoordinate>("c1");
226 QTest::addColumn<QGeoCoordinate>("c2");
227 QTest::addColumn<QGeoCoordinate>("c3");
228 QTest::addColumn<double>("lat");
229 QTest::addColumn<double>("lon");
230
231 QTest::newRow("Simple") << QGeoCoordinate(1,1) << QGeoCoordinate(2,2) <<
232 QGeoCoordinate(3,0) << 5.0 << 4.0;
233 QTest::newRow("Backward") << QGeoCoordinate(1,1) << QGeoCoordinate(2,2) <<
234 QGeoCoordinate(3,0) << -5.0 << -4.0;
235 }
236
translate()237 void tst_QGeoPath::translate()
238 {
239 QFETCH(QGeoCoordinate, c1);
240 QFETCH(QGeoCoordinate, c2);
241 QFETCH(QGeoCoordinate, c3);
242 QFETCH(double, lat);
243 QFETCH(double, lon);
244
245 QList<QGeoCoordinate> coords;
246 coords.append(c1);
247 coords.append(c2);
248 coords.append(c3);
249 QGeoPath p(coords);
250
251 p.translate(lat, lon);
252
253 for (int i = 0; i < p.path().size(); i++) {
254 QCOMPARE(coords[i].latitude(), p.path()[i].latitude() - lat );
255 QCOMPARE(coords[i].longitude(), p.path()[i].longitude() - lon );
256 }
257 }
258
valid_data()259 void tst_QGeoPath::valid_data()
260 {
261 QTest::addColumn<QGeoCoordinate>("c1");
262 QTest::addColumn<QGeoCoordinate>("c2");
263 QTest::addColumn<QGeoCoordinate>("c3");
264 QTest::addColumn<qreal>("width");
265 QTest::addColumn<bool>("valid");
266
267 QTest::newRow("empty coords") << QGeoCoordinate() << QGeoCoordinate() << QGeoCoordinate() << qreal(5.0) << false;
268 QTest::newRow("invalid coord") << QGeoCoordinate(50, 50) << QGeoCoordinate(60, 60) << QGeoCoordinate(700, 700) << qreal(5.0) << false;
269 QTest::newRow("bad width") << QGeoCoordinate(10, 10) << QGeoCoordinate(11, 11) << QGeoCoordinate(10, 12) << qreal(-5.0) << true;
270 QTest::newRow("NaN width") << QGeoCoordinate(10, 10) << QGeoCoordinate(11, 11) << QGeoCoordinate(10, 12) << qreal(qQNaN()) << true;
271 QTest::newRow("zero width") << QGeoCoordinate(10, 10) << QGeoCoordinate(11, 11) << QGeoCoordinate(10, 12) << qreal(0) << true;
272 QTest::newRow("good") << QGeoCoordinate(10, 10) << QGeoCoordinate(11, 11) << QGeoCoordinate(10, 12) << qreal(5) << true;
273 }
274
valid()275 void tst_QGeoPath::valid()
276 {
277 QFETCH(QGeoCoordinate, c1);
278 QFETCH(QGeoCoordinate, c2);
279 QFETCH(QGeoCoordinate, c3);
280 QFETCH(qreal, width);
281 QFETCH(bool, valid);
282
283 QList<QGeoCoordinate> coords;
284 coords.append(c1);
285 coords.append(c2);
286 coords.append(c3);
287 QGeoPath p(coords, width);
288
289 QCOMPARE(p.isValid(), valid);
290
291 QGeoShape area = p;
292 QCOMPARE(area.isValid(), valid);
293 }
294
contains_data()295 void tst_QGeoPath::contains_data()
296 {
297 QTest::addColumn<QGeoCoordinate>("c1");
298 QTest::addColumn<QGeoCoordinate>("c2");
299 QTest::addColumn<QGeoCoordinate>("c3");
300 QTest::addColumn<qreal>("width");
301 QTest::addColumn<QGeoCoordinate>("probe");
302 QTest::addColumn<bool>("result");
303
304 QList<QGeoCoordinate> c;
305 c.append(QGeoCoordinate(1,1));
306 c.append(QGeoCoordinate(2,2));
307 c.append(QGeoCoordinate(3,0));
308
309 QTest::newRow("One of the points") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(2, 2) << true;
310 QTest::newRow("Not so far away") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(0.8, 0.8) << false;
311 QTest::newRow("Not so far away and large line") << c[0] << c[1] << c[2] << 100000.0 << QGeoCoordinate(0.8, 0.8) << true;
312 }
313
contains()314 void tst_QGeoPath::contains()
315 {
316 QFETCH(QGeoCoordinate, c1);
317 QFETCH(QGeoCoordinate, c2);
318 QFETCH(QGeoCoordinate, c3);
319 QFETCH(qreal, width);
320 QFETCH(QGeoCoordinate, probe);
321 QFETCH(bool, result);
322
323 QList<QGeoCoordinate> coords;
324 coords.append(c1);
325 coords.append(c2);
326 coords.append(c3);
327 QGeoPath p(coords, width);
328
329 QCOMPARE(p.contains(probe), result);
330
331 QGeoShape area = p;
332 QCOMPARE(area.contains(probe), result);
333 }
334
boundingGeoRectangle_data()335 void tst_QGeoPath::boundingGeoRectangle_data()
336 {
337 QTest::addColumn<QGeoCoordinate>("c1");
338 QTest::addColumn<QGeoCoordinate>("c2");
339 QTest::addColumn<QGeoCoordinate>("c3");
340 QTest::addColumn<qreal>("width");
341 QTest::addColumn<QGeoCoordinate>("probe");
342 QTest::addColumn<bool>("result");
343
344 QList<QGeoCoordinate> c;
345 c.append(QGeoCoordinate(1,1));
346 c.append(QGeoCoordinate(2,2));
347 c.append(QGeoCoordinate(3,0));
348
349 QTest::newRow("One of the points") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(2, 2) << true;
350 QTest::newRow("Not so far away") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(0, 0) << false;
351 QTest::newRow("Inside the bounds") << c[0] << c[1] << c[2] << 100.0 << QGeoCoordinate(1, 0) << true;
352 QTest::newRow("Inside the bounds") << c[0] << c[1] << c[2] << 100.0 << QGeoCoordinate(1.1, 0.1) << true;
353 }
354
boundingGeoRectangle()355 void tst_QGeoPath::boundingGeoRectangle()
356 {
357 QFETCH(QGeoCoordinate, c1);
358 QFETCH(QGeoCoordinate, c2);
359 QFETCH(QGeoCoordinate, c3);
360 QFETCH(qreal, width);
361 QFETCH(QGeoCoordinate, probe);
362 QFETCH(bool, result);
363
364 QList<QGeoCoordinate> coords;
365 coords.append(c1);
366 coords.append(c2);
367 coords.append(c3);
368 QGeoPath p(coords, width);
369
370 QGeoRectangle box = p.boundingGeoRectangle();
371 QCOMPARE(box.contains(probe), result);
372 }
373
extendShape()374 void tst_QGeoPath::extendShape()
375 {
376 QFETCH(QGeoCoordinate, c1);
377 QFETCH(QGeoCoordinate, c2);
378 QFETCH(QGeoCoordinate, c3);
379 QFETCH(qreal, width);
380 QFETCH(QGeoCoordinate, probe);
381 QFETCH(bool, before);
382 QFETCH(bool, after);
383
384 QList<QGeoCoordinate> coords;
385 coords.append(c1);
386 coords.append(c2);
387 coords.append(c3);
388 QGeoPath p(coords, width);
389
390
391 QCOMPARE(p.contains(probe), before);
392 p.extendShape(probe);
393 QCOMPARE(p.contains(probe), after);
394 }
395
extendShape_data()396 void tst_QGeoPath::extendShape_data()
397 {
398 QTest::addColumn<QGeoCoordinate>("c1");
399 QTest::addColumn<QGeoCoordinate>("c2");
400 QTest::addColumn<QGeoCoordinate>("c3");
401 QTest::addColumn<qreal>("width");
402 QTest::addColumn<QGeoCoordinate>("probe");
403 QTest::addColumn<bool>("before");
404 QTest::addColumn<bool>("after");
405
406 QList<QGeoCoordinate> c;
407 c.append(QGeoCoordinate(1,1));
408 c.append(QGeoCoordinate(2,2));
409 c.append(QGeoCoordinate(3,0));
410
411 QTest::newRow("One of the points") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(2, 2) << true << true;
412 QTest::newRow("Not so far away") << c[0] << c[1] << c[2] << 0.0 << QGeoCoordinate(0, 0) << false << true;
413 QTest::newRow("Not so far away and large line") << c[0] << c[1] << c[2] << 100000.0 << QGeoCoordinate(0.8, 0.8) << true << true;
414 }
415
416 QTEST_MAIN(tst_QGeoPath)
417 #include "tst_qgeopath.moc"
418