summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarc Jeanmougin <marc@jeanmougin.fr>2016-11-02 23:08:41 +0000
committerMarc Jeanmougin <marcjeanmougin@free.fr>2016-11-02 23:08:41 +0000
commit6162cf1a9f6953319e0e3d6b56354c5cb0f26352 (patch)
treeeee7e33b24751c74fe63ae746583b09458c39a46
parentfix prefs icon (diff)
downloadinkscape-6162cf1a9f6953319e0e3d6b56354c5cb0f26352.tar.gz
inkscape-6162cf1a9f6953319e0e3d6b56354c5cb0f26352.zip
Add some unit tests for object-set cppification
(bzr r15203)
-rw-r--r--src/object-set.cpp4
-rw-r--r--src/selection-chemistry.cpp6
-rw-r--r--src/sp-item.cpp11
-rw-r--r--src/sp-item.h1
-rw-r--r--src/ui/dialog/align-and-distribute.cpp2
-rw-r--r--testfiles/src/object-set-test.cpp228
6 files changed, 221 insertions, 31 deletions
diff --git a/src/object-set.cpp b/src/object-set.cpp
index fd0b908d1..65e7d45d6 100644
--- a/src/object-set.cpp
+++ b/src/object-set.cpp
@@ -204,7 +204,7 @@ SPItem *ObjectSet::_sizeistItem(bool sml, CompareSize compare) {
SPItem *ist = NULL;
for (auto i = items.begin(); i != items.end(); ++i) {
- Geom::OptRect obox = SP_ITEM(*i)->desktopPreferredBounds();
+ Geom::OptRect obox = SP_ITEM(*i)->documentPreferredBounds();
if (!obox || obox.empty()) {
continue;
}
@@ -212,7 +212,7 @@ SPItem *ObjectSet::_sizeistItem(bool sml, CompareSize compare) {
Geom::Rect bbox = *obox;
gdouble size = compare == AREA ? bbox.area() :
- (compare == VERTICAL ? bbox.width() : bbox.height());
+ (compare == VERTICAL ? bbox.height() : bbox.width());
size = sml ? size : size * -1;
if (size < max) {
max = size;
diff --git a/src/selection-chemistry.cpp b/src/selection-chemistry.cpp
index 2f9e72e2c..2db059afe 100644
--- a/src/selection-chemistry.cpp
+++ b/src/selection-chemistry.cpp
@@ -946,7 +946,7 @@ enclose_items(std::vector<SPItem*> const &items)
Geom::OptRect r;
for (std::vector<SPItem*>::const_iterator i = items.begin();i!=items.end();++i) {
- r.unionWith((*i)->desktopVisualBounds());
+ r.unionWith((*i)->documentVisualBounds());
}
return r;
}
@@ -1000,7 +1000,7 @@ void ObjectSet::raise(bool skip_undo){
// if the sibling is an item AND overlaps our selection,
SPItem *newItem = dynamic_cast<SPItem *>(newref);
if (newItem) {
- Geom::OptRect newref_bbox = newItem->desktopVisualBounds();
+ Geom::OptRect newref_bbox = newItem->documentVisualBounds();
if ( newref_bbox && selected->intersects(*newref_bbox) ) {
// AND if it's not one of our selected objects,
if ( std::find(items_copy.begin(),items_copy.end(),newref)==items_copy.end()) {
@@ -1077,7 +1077,7 @@ void ObjectSet::lower(bool skip_undo){
// if the sibling is an item AND overlaps our selection,
SPItem *newItem = dynamic_cast<SPItem *>(newref);
if (newItem) {
- Geom::OptRect ref_bbox = newItem->desktopVisualBounds();
+ Geom::OptRect ref_bbox = newItem->documentVisualBounds();
if ( ref_bbox && selected->intersects(*ref_bbox) ) {
// AND if it's not one of our selected objects,
if (items_copy.end()==std::find(items_copy.begin(),items_copy.end(),newref)) {
diff --git a/src/sp-item.cpp b/src/sp-item.cpp
index f52784489..36a9c3c9d 100644
--- a/src/sp-item.cpp
+++ b/src/sp-item.cpp
@@ -868,6 +868,17 @@ Geom::OptRect SPItem::bounds(BBoxType type, Geom::Affine const &transform) const
}
}
+Geom::OptRect SPItem::documentPreferredBounds() const
+{
+ if (Inkscape::Preferences::get()->getInt("/tools/bounding_box") == 0) {
+ return documentBounds(SPItem::VISUAL_BBOX);
+ } else {
+ return documentBounds(SPItem::GEOMETRIC_BBOX);
+ }
+}
+
+
+
Geom::OptRect SPItem::documentGeometricBounds() const
{
return geometricBounds(i2doc_affine());
diff --git a/src/sp-item.h b/src/sp-item.h
index bdc6a0ad9..a03bab9f3 100644
--- a/src/sp-item.h
+++ b/src/sp-item.h
@@ -258,6 +258,7 @@ public:
Geom::OptRect documentVisualBounds() const;
Geom::OptRect documentBounds(BBoxType type) const;
+ Geom::OptRect documentPreferredBounds() const;
/**
* Get item's geometric bbox in desktop coordinate system.
diff --git a/src/ui/dialog/align-and-distribute.cpp b/src/ui/dialog/align-and-distribute.cpp
index 7ba6df978..236832beb 100644
--- a/src/ui/dialog/align-and-distribute.cpp
+++ b/src/ui/dialog/align-and-distribute.cpp
@@ -129,7 +129,7 @@ void ActionAlign::do_action(SPDesktop *desktop, int index)
SPItem *focus = NULL;
Geom::OptRect b = Geom::OptRect();
Selection::CompareSize horiz = (a.mx0 != 0.0) || (a.mx1 != 0.0)
- ? Selection::HORIZONTAL : Selection::VERTICAL;
+ ? Selection::VERTICAL : Selection::HORIZONTAL;
switch (AlignTarget(prefs->getInt("/dialogs/align/align-to", 6)))
{
diff --git a/testfiles/src/object-set-test.cpp b/testfiles/src/object-set-test.cpp
index 83c1e4ff2..3bf408d6b 100644
--- a/testfiles/src/object-set-test.cpp
+++ b/testfiles/src/object-set-test.cpp
@@ -12,11 +12,15 @@
#include <doc-per-case-test.h>
#include <src/sp-factory.h>
#include <src/sp-rect.h>
+#include <src/sp-path.h>
+#include <src/sp-use.h>
+#include <src/sp-root.h>
#include <src/object-set.h>
#include <xml/node.h>
#include <src/xml/text-node.h>
#include <src/xml/simple-document.h>
-
+//#include <unistd.h>
+#include <2geom/transforms.h>
using namespace Inkscape;
using namespace Inkscape::XML;
@@ -32,9 +36,9 @@ public:
G = new SPObject();
H = new SPObject();
X = new SPObject();
- set = new ObjectSet();
- set2 = new ObjectSet();
- auto sd = new SimpleDocument();
+ set = new ObjectSet(_doc);
+ set2 = new ObjectSet(_doc);
+ auto sd = _doc->getReprDoc();
auto xt = new TextNode(Util::share_string("x"), sd);
auto ht = new TextNode(Util::share_string("h"), sd);
auto gt = new TextNode(Util::share_string("g"), sd);
@@ -53,6 +57,24 @@ public:
C->invoke_build(_doc, ct, 0);
B->invoke_build(_doc, bt, 0);
A->invoke_build(_doc, at, 0);
+
+ //create 3 rects at root of document
+ Inkscape::XML::Node *repr = _doc->getReprDoc()->createElement("svg:rect");
+ _doc->getRoot()->appendChild(repr);
+ r1.reset(dynamic_cast<SPRect*>(_doc->getObjectByRepr(repr)));
+ repr = _doc->getReprDoc()->createElement("svg:rect");
+ _doc->getRoot()->appendChild(repr);
+ r2.reset(dynamic_cast<SPRect*>(_doc->getObjectByRepr(repr)));
+ repr = _doc->getReprDoc()->createElement("svg:rect");
+ _doc->getRoot()->appendChild(repr);
+ r3.reset(dynamic_cast<SPRect*>(_doc->getObjectByRepr(repr)));
+ EXPECT_EQ(6, _doc->getRoot()->children.size());//metadata, defs, namedview, and those three rects.
+ r1->x = r1->y = r2->x = r2->y = r3->x = r3->y = 0;
+ r1->width = r1->height = r2->width = r2->height = r3->width = r3->height = 10;
+ r1->set_shape();
+ r2->set_shape();
+ r3->set_shape();
+
}
~ObjectSetTest() {
delete set;
@@ -76,6 +98,9 @@ public:
SPObject* G;
SPObject* H;
SPObject* X;
+ std::unique_ptr<SPRect> r1;
+ std::unique_ptr<SPRect> r2;
+ std::unique_ptr<SPRect> r3;
ObjectSet* set;
ObjectSet* set2;
};
@@ -148,32 +173,40 @@ TEST_F(ObjectSetTest, Advanced) {
TEST_F(ObjectSetTest, Items) {
// cannot test smallestItem and largestItem functions due to too many dependencies
// uncomment if the problem is fixed
- SPRect* rect10x100 = (SPRect *) SPFactory::createObject("svg:rect");
-// rect10x100->invoke_build(_doc, _doc->rroot, 1);
- SPRect* rect20x40 = (SPRect *) SPFactory::createObject("svg:rect");
-// rect20x40->invoke_build(_doc, _doc->rroot, 1);
-// SPRect* rect30x30 = (SPRect *) SPFactory::createObject("svg:rect");
-// rect30x30->invoke_build(_doc, _doc->rroot, 1);
-// rect10x100->width = 10;
-// rect10x100->height = 100;
-// rect20x40->width = 20;
-// rect20x40->height = 40;
-// rect30x30->width = 30;
-// rect30x30->height = 30;
+
+ SPRect* rect10x100 = &*r1;
+ rect10x100->x = rect10x100->x = 0;
+ rect10x100->width = 10;
+ rect10x100->height = 100;
+ rect10x100->set_shape();
+
+ SPRect* rect20x40 = &*r2;
+ rect20x40->x = rect20x40->x = 0;
+ rect20x40->width = 20;
+ rect20x40->height = 40;
+ rect20x40->set_shape();
+
+ SPRect* rect30x30 = &*r3;
+ rect30x30->x = rect30x30->x = 0;
+ rect30x30->width = 30;
+ rect30x30->height = 30;
+ rect30x30->set_shape();
+
+
set->add(rect10x100);
EXPECT_EQ(rect10x100, set->singleItem());
EXPECT_EQ(rect10x100->getRepr(), set->singleRepr());
set->add(rect20x40);
EXPECT_EQ(nullptr, set->singleItem());
EXPECT_EQ(nullptr, set->singleRepr());
-// set->add(rect30x30);
-// EXPECT_EQ(3, set->size());
-// EXPECT_EQ(rect10x100, set->smallestItem(ObjectSet::CompareSize::HORIZONTAL));
-// EXPECT_EQ(rect30x30, set->smallestItem(ObjectSet::CompareSize::VERTICAL));
-// EXPECT_EQ(rect20x40, set->smallestItem(ObjectSet::CompareSize::AREA));
-// EXPECT_EQ(rect30x30, set->largestItem(ObjectSet::CompareSize::HORIZONTAL));
-// EXPECT_EQ(rect10x100, set->largestItem(ObjectSet::CompareSize::VERTICAL));
-// EXPECT_EQ(rect10x100, set->largestItem(ObjectSet::CompareSize::AREA));
+ set->add(rect30x30);
+ EXPECT_EQ(3, set->size());
+ EXPECT_EQ(rect10x100, set->smallestItem(ObjectSet::CompareSize::HORIZONTAL));
+ EXPECT_EQ(rect30x30, set->smallestItem(ObjectSet::CompareSize::VERTICAL));
+ EXPECT_EQ(rect20x40, set->smallestItem(ObjectSet::CompareSize::AREA));
+ EXPECT_EQ(rect30x30, set->largestItem(ObjectSet::CompareSize::HORIZONTAL));
+ EXPECT_EQ(rect10x100, set->largestItem(ObjectSet::CompareSize::VERTICAL));
+ EXPECT_EQ(rect10x100, set->largestItem(ObjectSet::CompareSize::AREA));
}
TEST_F(ObjectSetTest, Ranges) {
@@ -310,7 +343,7 @@ TEST_F(ObjectSetTest, TwoSets) {
}
TEST_F(ObjectSetTest, SetRemoving) {
- ObjectSet *objectSet = new ObjectSet();
+ ObjectSet *objectSet = new ObjectSet(_doc);
A->attach(B, nullptr);
objectSet->add(A);
objectSet->add(C);
@@ -319,3 +352,148 @@ TEST_F(ObjectSetTest, SetRemoving) {
EXPECT_STREQ(nullptr, A->getId());
EXPECT_STREQ(nullptr, C->getId());
}
+
+TEST_F(ObjectSetTest, Delete) {
+ //we cannot use the same item as in other tests since it will be freed at the test destructor
+ Inkscape::XML::Node *repr = _doc->getReprDoc()->createElement("svg:rect");
+ _doc->getRoot()->appendChild(repr);
+ SPRect *r1 = dynamic_cast<SPRect*>(_doc->getObjectByRepr(repr));
+
+ EXPECT_EQ(_doc->getRoot(), r1->parent);
+ set->add(r1);
+ set->deleteItems();
+ EXPECT_EQ(0, set->size());
+ EXPECT_EQ(nullptr, r1->parent);
+}
+
+TEST_F(ObjectSetTest, Ops) {
+ set->add(r1.get());
+ set->add(r2.get());
+ set->add(r3.get());
+ set->duplicate();
+ EXPECT_EQ(9, _doc->getRoot()->children.size());//metadata, defs, namedview, and those 3x2 rects.
+ EXPECT_EQ(3, set->size());
+ EXPECT_FALSE(set->includes(r1.get()));
+ set->deleteItems();
+ EXPECT_TRUE(set->isEmpty());
+ set->add(r1.get());
+ set->add(r2.get());
+ set->add(r3.get());
+ set->group();//r1-3 are now invalid (grouping makes copies)
+ r1.release();
+ r2.release();
+ r3.release();
+ EXPECT_EQ(4, _doc->getRoot()->children.size());
+ EXPECT_EQ(1, set->size());
+ set->ungroup();
+ EXPECT_EQ(6, _doc->getRoot()->children.size());
+ EXPECT_EQ(3, set->size());
+ /* Uncomment this when toNextLayer is made desktop-independent
+ set->group();
+ set2->add(set->singleItem()->childList(false)[0]);
+ EXPECT_EQ(3, set->singleItem()->children.size());
+ EXPECT_EQ(4, _doc->getRoot()->children.size());
+ set2->popFromGroup();
+ EXPECT_EQ(2, set->singleItem()->children.size());
+ EXPECT_EQ(5, _doc->getRoot()->children.size());
+ set->ungroup();
+ set->add(set2->singleItem());
+ */
+ set->clone();
+ EXPECT_EQ(9, _doc->getRoot()->children.size());
+ EXPECT_EQ(3, set->size());
+ EXPECT_NE(nullptr,dynamic_cast<SPUse*>(*(set->items().begin())));
+ EXPECT_EQ(nullptr,dynamic_cast<SPRect*>(*(set->items().begin())));
+ set->unlink();
+ EXPECT_EQ(9, _doc->getRoot()->children.size());
+ EXPECT_EQ(3, set->size());
+ EXPECT_EQ(nullptr,dynamic_cast<SPUse*>(*(set->items().begin())));
+ EXPECT_NE(nullptr,dynamic_cast<SPRect*>(*(set->items().begin())));
+ set->clone(); //creates 3 clones
+ set->clone(); //creates 3 clones of clones
+ EXPECT_EQ(15, _doc->getRoot()->children.size());
+ EXPECT_EQ(3, set->size());
+ EXPECT_NE(nullptr,dynamic_cast<SPUse*>( ((SPUse*)(*(set->items().begin())))->get_original()));//"original is a Use"
+ set->unlink(); //clone of clone of rect -> rect
+ EXPECT_EQ(nullptr,dynamic_cast<SPUse*>(*(set->items().begin())));
+ EXPECT_NE(nullptr,dynamic_cast<SPRect*>(*(set->items().begin())));
+ set->clone();
+ set->set(*(set->items().begin()));
+ set->cloneOriginal();//get clone original
+ EXPECT_EQ(18, _doc->getRoot()->children.size());
+ EXPECT_EQ(1, set->size());
+ EXPECT_NE(nullptr,dynamic_cast<SPRect*>(*(set->items().begin())));
+ //let's stop here.
+ // TODO: write a hundred more tests to check clone (non-)displacement when grouping, ungrouping and unlinking...
+ TearDownTestCase();
+ SetUpTestCase();
+}
+
+TEST_F(ObjectSetTest, ZOrder) {
+ //sp_object_compare_position_bool == true iff "r1<r2" iff r1 is "before" r2 in the file, ie r1 is lower than r2
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r2.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r2.get(),r3.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r3.get()));
+ EXPECT_FALSE(sp_object_compare_position_bool(r2.get(),r1.get()));
+ EXPECT_FALSE(sp_object_compare_position_bool(r3.get(),r1.get()));
+ EXPECT_FALSE(sp_object_compare_position_bool(r3.get(),r2.get()));
+ //1 2 3
+ set->set(r2.get());
+ set->raise();
+ //1 3 2
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r3.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r3.get(),r2.get()));//!
+ set->set(r3.get());
+ set->lower();
+ //3 1 2
+ EXPECT_TRUE(sp_object_compare_position_bool(r3.get(),r1.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r2.get()));
+ set->raiseToTop();
+ //1 2 3
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r2.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r2.get(),r3.get()));
+ set->lowerToBottom();
+ //3 1 2
+ EXPECT_TRUE(sp_object_compare_position_bool(r3.get(),r1.get()));
+ EXPECT_TRUE(sp_object_compare_position_bool(r1.get(),r2.get()));
+}
+
+TEST_F(ObjectSetTest, Combine) {
+ set->add(r1.get());
+ set->add(r2.get());
+ set->combine();
+ r1.release();
+ r2.release();
+ EXPECT_EQ(1, set->size());
+ EXPECT_EQ(5, _doc->getRoot()->children.size());
+ set->breakApart();
+ EXPECT_EQ(2, set->size());
+ EXPECT_EQ(6, _doc->getRoot()->children.size());
+ set->deleteItems();
+ set->set(r3.get());
+ set->toCurves();
+ r3.release();
+ auto x = set->singleItem();
+ EXPECT_NE(nullptr,dynamic_cast<SPPath*>(x));
+ EXPECT_EQ(nullptr,dynamic_cast<SPRect*>(x));
+ set->deleteItems();
+}
+
+TEST_F(ObjectSetTest, Moves) {
+ set->add(r1.get());
+ set->moveRelative(15,15);
+ EXPECT_EQ(15,r1->x.value);
+ Geom::Point p(20,20);
+ Geom::Scale s(2);
+ set->setScaleRelative(p,s);
+ EXPECT_EQ(10,r1->x.value);
+ EXPECT_EQ(20,r1->width.value);
+ set->toCurves();
+ r1.release();
+ auto x = set->singleItem();
+ EXPECT_EQ(20,(*(x->documentVisualBounds()))[0].extent());
+ set->rotate90(true);
+ set->rotate90(true);
+ EXPECT_EQ(20,(*(x->documentVisualBounds()))[0].extent());
+ set->deleteItems();
+}