// SPDX-License-Identifier: GPL-2.0-or-later /** @file * Curve test *//* * Authors: see git history * * Copyright (C) 2020 Authors * Released under GNU GPL v2+, read the file 'COPYING' for more information. */ #include #include "display/curve.h" #include <2geom/curves.h> #include <2geom/path.h> #include <2geom/pathvector.h> class CurveTest : public ::testing::Test { public: Geom::Path path1; Geom::Path path2; Geom::Path path3; Geom::Path path4; static size_t get_refcount(SPCurve const *curve) { return curve->_refcount; } protected: CurveTest() : path4(Geom::Point(3, 5)) // Just a moveto { // Closed path path1.append(Geom::LineSegment(Geom::Point(0, 0), Geom::Point(1, 0))); path1.append(Geom::LineSegment(Geom::Point(1, 0), Geom::Point(1, 1))); path1.close(); // Closed path (ClosingSegment is zero length) path2.append(Geom::LineSegment(Geom::Point(2, 0), Geom::Point(3, 0))); path2.append(Geom::CubicBezier(Geom::Point(3, 0), Geom::Point(2, 1), Geom::Point(1, 1), Geom::Point(2, 0))); path2.close(); // Open path path3.setStitching(true); path3.append(Geom::EllipticalArc(Geom::Point(4, 0), 1, 2, M_PI, false, false, Geom::Point(5, 1))); path3.append(Geom::LineSegment(Geom::Point(5, 1), Geom::Point(5, 2))); path3.append(Geom::LineSegment(Geom::Point(6, 4), Geom::Point(2, 4))); } }; TEST_F(CurveTest, testMoveSemantics) { SPCurve c1; c1.moveto(2, 3); c1.lineto(4, 5); // move construction SPCurve c2(std::move(c1)); ASSERT_EQ(c1.get_segment_count(), 0); ASSERT_EQ(c2.get_segment_count(), 1); // move assignment c1 = std::move(c2); ASSERT_EQ(c1.get_segment_count(), 1); ASSERT_EQ(c2.get_segment_count(), 0); } TEST_F(CurveTest, testRefCount) { auto c1 = std::make_unique(); ASSERT_EQ(get_refcount(c1.get()), 1); { auto c2 = c1->ref(); ASSERT_EQ(c2.get(), c1.get()); ASSERT_EQ(get_refcount(c1.get()), 2); ASSERT_EQ(get_refcount(c2.get()), 2); } ASSERT_EQ(get_refcount(c1.get()), 1); } TEST_F(CurveTest, testGetSegmentCount) { { // Zero segments Geom::PathVector pv; SPCurve curve(pv); ASSERT_EQ(curve.get_segment_count(), 0u); } { // Zero segments Geom::PathVector pv; pv.push_back(Geom::Path()); SPCurve curve(pv); ASSERT_EQ(curve.get_segment_count(), 0u); } { // Individual paths Geom::PathVector pv((Geom::Path())); pv[0] = path1; ASSERT_EQ(SPCurve(pv).get_segment_count(), 3u); pv[0] = path2; ASSERT_EQ(SPCurve(pv).get_segment_count(), 2u); pv[0] = path3; ASSERT_EQ(SPCurve(pv).get_segment_count(), 4u); pv[0] = path4; ASSERT_EQ(SPCurve(pv).get_segment_count(), 0u); pv[0].close(); ASSERT_EQ(SPCurve(pv).get_segment_count(), 0u); } { // Combination Geom::PathVector pv; pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); pv.push_back(path4); SPCurve curve(pv); ASSERT_EQ(curve.get_segment_count(), 9u); } } TEST_F(CurveTest, testNodesInPathForZeroSegments) { { // Zero segments Geom::PathVector pv; SPCurve curve(pv); ASSERT_EQ(curve.nodes_in_path(), 0u); } { // Zero segments Geom::PathVector pv; pv.push_back(Geom::Path()); SPCurve curve(pv); ASSERT_EQ(curve.nodes_in_path(), 1u); } } TEST_F(CurveTest, testNodesInPathForIndividualPaths) { Geom::PathVector pv((Geom::Path())); pv[0] = path1; ASSERT_EQ(SPCurve(pv).nodes_in_path(), 3u); pv[0] = path2; ASSERT_EQ(SPCurve(pv).nodes_in_path(), 2u); // zero length closing segments do not increase the nodecount. pv[0] = path3; ASSERT_EQ(SPCurve(pv).nodes_in_path(), 5u); pv[0] = path4; ASSERT_EQ(SPCurve(pv).nodes_in_path(), 1u); } TEST_F(CurveTest, testNodesInPathForNakedMoveToClosedPath) { Geom::PathVector pv((Geom::Path())); pv[0] = path4; // just a MoveTo pv[0].close(); ASSERT_EQ(SPCurve(pv).nodes_in_path(), 1u); } /* TEST_F(CurveTest, testNodesInPathForPathsCombination) { Geom::PathVector pv; pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); pv.push_back(path4); SPCurve curve(pv); ASSERT_EQ(curve.nodes_in_path(), 12u); } */ TEST_F(CurveTest, testIsEmpty) { ASSERT_TRUE(SPCurve(Geom::PathVector()).is_empty()); ASSERT_FALSE(SPCurve(path1).is_empty()); ASSERT_FALSE(SPCurve(path2).is_empty()); ASSERT_FALSE(SPCurve(path3).is_empty()); ASSERT_FALSE(SPCurve(path4).is_empty()); } TEST_F(CurveTest, testIsClosed) { ASSERT_FALSE(SPCurve(Geom::PathVector()).is_closed()); Geom::PathVector pv((Geom::Path())); ASSERT_FALSE(SPCurve(pv).is_closed()); pv[0].close(); ASSERT_TRUE(SPCurve(pv).is_closed()); ASSERT_TRUE(SPCurve(path1).is_closed()); ASSERT_TRUE(SPCurve(path2).is_closed()); ASSERT_FALSE(SPCurve(path3).is_closed()); ASSERT_FALSE(SPCurve(path4).is_closed()); } /* TEST_F(CurveTest, testLastFirstSegment) { Geom::PathVector pv(path4); ASSERT_EQ(SPCurve(pv).first_segment(), (void *)0); ASSERT_EQ(SPCurve(pv).last_segment(), (void *)0); pv[0].close(); ASSERT_NE(SPCurve(pv).first_segment(), (void *)0); ASSERT_NE(SPCurve(pv).last_segment(), (void *)0); } */ TEST_F(CurveTest, testLastFirstPath) { Geom::PathVector pv; ASSERT_EQ(SPCurve(pv).first_path(), (void *)0); ASSERT_EQ(SPCurve(pv).last_path(), (void *)0); pv.push_back(path1); ASSERT_EQ(*SPCurve(pv).first_path(), pv[0]); ASSERT_EQ(*SPCurve(pv).last_path(), pv[0]); pv.push_back(path2); ASSERT_EQ(*SPCurve(pv).first_path(), pv[0]); ASSERT_EQ(*SPCurve(pv).last_path(), pv[1]); pv.push_back(path3); ASSERT_EQ(*SPCurve(pv).first_path(), pv[0]); ASSERT_EQ(*SPCurve(pv).last_path(), pv[2]); pv.push_back(path4); ASSERT_EQ(*SPCurve(pv).first_path(), pv[0]); ASSERT_EQ(*SPCurve(pv).last_path(), pv[3]); } TEST_F(CurveTest, testFirstPoint) { ASSERT_EQ(*(SPCurve(path1).first_point()), Geom::Point(0, 0)); ASSERT_EQ(*(SPCurve(path2).first_point()), Geom::Point(2, 0)); ASSERT_EQ(*(SPCurve(path3).first_point()), Geom::Point(4, 0)); ASSERT_EQ(*(SPCurve(path4).first_point()), Geom::Point(3, 5)); Geom::PathVector pv; ASSERT_FALSE(SPCurve(pv).first_point()); pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); ASSERT_EQ(*(SPCurve(pv).first_point()), Geom::Point(0, 0)); pv.insert(pv.begin(), path4); ASSERT_EQ(*(SPCurve(pv).first_point()), Geom::Point(3, 5)); } /* TEST_F(CurveTest, testLastPoint) { ASSERT_EQ(*(SPCurve(path1).last_point()), Geom::Point(0, 0)); ASSERT_EQ(*(SPCurve(path2).last_point()), Geom::Point(2, 0)); ASSERT_EQ(*(SPCurve(path3).last_point()), Geom::Point(8, 4)); ASSERT_EQ(*(SPCurve(path4).last_point()), Geom::Point(3, 5)); Geom::PathVector pv; ASSERT_FALSE(SPCurve(pv).last_point()); pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); ASSERT_EQ(*(SPCurve(pv).last_point()), Geom::Point(8, 4)); pv.push_back(path4); ASSERT_EQ(*(SPCurve(pv).last_point()), Geom::Point(3, 5)); } */ TEST_F(CurveTest, testSecondPoint) { ASSERT_EQ(*(SPCurve(path1).second_point()), Geom::Point(1, 0)); ASSERT_EQ(*(SPCurve(path2).second_point()), Geom::Point(3, 0)); ASSERT_EQ(*(SPCurve(path3).second_point()), Geom::Point(5, 1)); ASSERT_EQ(*(SPCurve(path4).second_point()), Geom::Point(3, 5)); Geom::PathVector pv; pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); ASSERT_EQ(*(SPCurve(pv).second_point()), Geom::Point(1, 0)); pv.insert(pv.begin(), path4); ASSERT_EQ(*SPCurve(pv).second_point(), Geom::Point(0, 0)); } /* TEST_F(CurveTest, testPenultimatePoint) { ASSERT_EQ(*(SPCurve(Geom::PathVector(path1)).penultimate_point()), Geom::Point(1, 1)); ASSERT_EQ(*(SPCurve(Geom::PathVector(path2)).penultimate_point()), Geom::Point(3, 0)); ASSERT_EQ(*(SPCurve(Geom::PathVector(path3)).penultimate_point()), Geom::Point(6, 4)); ASSERT_EQ(*(SPCurve(Geom::PathVector(path4)).penultimate_point()), Geom::Point(3, 5)); Geom::PathVector pv; pv.push_back(path1); pv.push_back(path2); pv.push_back(path3); ASSERT_EQ(*(SPCurve(pv).penultimate_point()), Geom::Point(6, 4)); pv.push_back(path4); ASSERT_EQ(*(SPCurve(pv).penultimate_point()), Geom::Point(8, 4)); } */ /* Local Variables: mode:c++ c-file-style:"stroustrup" c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +)) indent-tabs-mode:nil fill-column:99 End: */ // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:fileencoding=utf-8:textwidth=99 :