Bfc red/green view almost completely fixed

Mon, 19 Mar 2018 12:24:59 +0200

author
Teemu Piippo <teemu@hecknology.net>
date
Mon, 19 Mar 2018 12:24:59 +0200
changeset 1305
31627acdd4b5
parent 1304
bb3f43293cf8
child 1306
be85306198a2

Bfc red/green view almost completely fixed

src/algorithms/invert.cpp file | annotate | diff | comparison | revisions
src/algorithms/invert.h file | annotate | diff | comparison | revisions
src/basics.cpp file | annotate | diff | comparison | revisions
src/basics.h file | annotate | diff | comparison | revisions
src/glShared.h file | annotate | diff | comparison | revisions
src/glcompiler.cpp file | annotate | diff | comparison | revisions
src/lddocument.cpp file | annotate | diff | comparison | revisions
src/lddocument.h file | annotate | diff | comparison | revisions
src/linetypes/modelobject.cpp file | annotate | diff | comparison | revisions
src/linetypes/modelobject.h file | annotate | diff | comparison | revisions
src/toolsets/basictoolset.cpp file | annotate | diff | comparison | revisions
src/toolsets/extprogramtoolset.cpp file | annotate | diff | comparison | revisions
--- a/src/algorithms/invert.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/algorithms/invert.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -128,3 +128,18 @@
 		}
 	}
 }
+
+void invertPolygon(LDPolygon& polygon)
+{
+	switch (polygon.numPolygonVertices())
+	{
+	case 2:
+	case 3:
+		std::swap(polygon.vertices[0], polygon.vertices[1]);
+		break;
+
+	case 4:
+		std::swap(polygon.vertices[1], polygon.vertices[3]);
+		break;
+	}
+}
--- a/src/algorithms/invert.h	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/algorithms/invert.h	Mon Mar 19 12:24:59 2018 +0200
@@ -22,3 +22,4 @@
 bool isflat(class Model* model, Axis* axis);
 Matrix flipmatrix(Axis axis);
 void invert(LDObject* obj, class DocumentManager* context);
+void invertPolygon(LDPolygon& polygon);
--- a/src/basics.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/basics.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -360,3 +360,21 @@
 			return 0;
 	}
 }
+
+/*
+ * Special operator definition that implements the XOR operator for windings.
+ * However, if either winding is NoWinding, then this function returns NoWinding.
+ */
+Winding operator^(Winding one, Winding other)
+{
+	if (one == NoWinding or other == NoWinding)
+		return NoWinding;
+	else
+		return static_cast<Winding>(static_cast<int>(one) ^ static_cast<int>(other));
+}
+
+Winding& operator^=(Winding& one, Winding other)
+{
+	one = one ^ other;
+	return one;
+}
--- a/src/basics.h	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/basics.h	Mon Mar 19 12:24:59 2018 +0200
@@ -44,6 +44,16 @@
 	Z
 };
 
+enum Winding
+{
+	NoWinding,
+	CounterClockwise,
+	Clockwise,
+};
+
+Winding operator^(Winding one, Winding other);
+Winding& operator^=(Winding& one, Winding other);
+
 //
 // Derivative of QVector3D: this class is used for the vertices.
 //
--- a/src/glShared.h	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/glShared.h	Mon Mar 19 12:24:59 2018 +0200
@@ -40,6 +40,11 @@
 	Vertex		vertices[4];
 	int			color;
 
+	inline int numPolygonVertices() const
+	{
+		return (num == 5) ? 2 : num;
+	}
+
 	inline int numVertices() const
 	{
 		return (num == 5) ? 4 : num;
--- a/src/glcompiler.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/glcompiler.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -375,7 +375,8 @@
 	case LDObjectType::SubfileReference:
 		{
 			LDSubfileReference* subfileReference = static_cast<LDSubfileReference*>(object);
-			auto data = subfileReference->inlinePolygons(m_documents);
+			// TODO: move winding to Model and use it here
+			auto data = subfileReference->inlinePolygons(m_documents, CounterClockwise);
 
 			for (LDPolygon& poly : data)
 				compilePolygon (poly, index, info);
--- a/src/lddocument.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/lddocument.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -529,7 +529,13 @@
 					if (deep and object->type() == LDObjectType::SubfileReference)
 					{
 						LDSubfileReference* reference = static_cast<LDSubfileReference*>(object);
-						reference->inlineContents(documentManager(), model, deep, renderinline);
+						reference->inlineContents(
+							documentManager(),
+							this->header.winding,
+							model,
+							deep,
+							renderinline
+						);
 					}
 					else
 					{
@@ -568,15 +574,3 @@
 {
 	m_verticesOutdated = true;
 }
-
-/*
- * Special operator definition that implements the XOR operator for windings.
- * However, if either winding is NoWinding, then this function returns NoWinding.
- */
-Winding operator^(Winding one, Winding other)
-{
-	if (one == NoWinding or other == NoWinding)
-		return NoWinding;
-	else
-		return static_cast<Winding>(static_cast<int>(one) ^ static_cast<int>(other));
-}
--- a/src/lddocument.h	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/lddocument.h	Mon Mar 19 12:24:59 2018 +0200
@@ -28,13 +28,6 @@
 struct LDGLData;
 class DocumentManager;
 
-enum Winding
-{
-	NoWinding,
-	CounterClockwise,
-	Clockwise,
-};
-
 struct LDHeader
 {
 	struct HistoryEntry
@@ -79,7 +72,6 @@
 };
 
 Q_DECLARE_OPERATORS_FOR_FLAGS(QFlags<LDHeader::Qualifier>)
-Winding operator^(Winding one, Winding other);
 
 //
 // This class stores a document either as a editable file for the user or for
--- a/src/linetypes/modelobject.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/linetypes/modelobject.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -26,6 +26,7 @@
 #include "../canvas.h"
 #include "../colors.h"
 #include "../glcompiler.h"
+#include "../algorithms/invert.h"
 #include "edgeline.h"
 #include "triangle.h"
 #include "quadrilateral.h"
@@ -154,16 +155,35 @@
 		obj->setColor (parentcolor);
 }
 
+bool shouldInvert(LDSubfileReference* reference, Winding winding, DocumentManager* context)
+{
+	bool result = false;
+	result ^= (reference->isInverted());
+	result ^= (reference->transformationMatrix().determinant() < 0);
+	result ^= (reference->fileInfo(context)->header.winding != winding);
+	return result;
+}
+
 // =============================================================================
 // -----------------------------------------------------------------------------
-void LDSubfileReference::inlineContents(DocumentManager* context, Model& model, bool deep, bool render)
-{
+void LDSubfileReference::inlineContents(
+	DocumentManager* context,
+	Winding parentWinding,
+	Model& model,
+	bool deep,
+	bool render
+) {
 	Model inlined {context};
 	fileInfo(context)->inlineContents(inlined, deep, render);
 
 	// Transform the objects
 	for (LDObject* object : inlined)
+	{
+		if (::shouldInvert(this, parentWinding, context))
+			::invert(object, context);
+
 		TransformObject(object, transformationMatrix(), position(), color());
+	}
 
 	model.merge(inlined);
 }
@@ -214,7 +234,7 @@
 
 // =============================================================================
 //
-QList<LDPolygon> LDSubfileReference::inlinePolygons(DocumentManager* context)
+QList<LDPolygon> LDSubfileReference::inlinePolygons(DocumentManager* context, Winding parentWinding)
 {
 	LDDocument* file = fileInfo(context);
 
@@ -226,6 +246,9 @@
 		{
 			for (int i = 0; i < entry.numVertices(); ++i)
 				entry.vertices[i].transform (transformationMatrix(), position());
+
+			if (::shouldInvert(this, parentWinding, context))
+				::invertPolygon(entry);
 		}
 
 		return data;
--- a/src/linetypes/modelobject.h	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/linetypes/modelobject.h	Mon Mar 19 12:24:59 2018 +0200
@@ -222,8 +222,14 @@
 	virtual QString asText() const override;
 	LDDocument* fileInfo(DocumentManager *context) const;
 	virtual void getVertices(DocumentManager *context, QSet<Vertex>& verts) const override;
-	void inlineContents(DocumentManager* context, Model& model, bool deep, bool render);
-	QList<LDPolygon> inlinePolygons(DocumentManager* context);
+	void inlineContents(
+		DocumentManager* context,
+		Winding parentWinding,
+		Model& model,
+		bool deep,
+		bool render
+	);
+	QList<LDPolygon> inlinePolygons(DocumentManager* context, Winding parentWinding);
 	QString objectListText() const override;
 	QString referenceName() const;
 	int triangleCount(DocumentManager *context) const override;
--- a/src/toolsets/basictoolset.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/toolsets/basictoolset.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -114,7 +114,13 @@
 		if (referenceIndex.isValid())
 		{
 			Model inlined {m_documents};
-			reference->inlineContents(m_documents, inlined, deep, false);
+			reference->inlineContents(
+				m_documents,
+				currentDocument()->header.winding,
+				inlined,
+				deep,
+				false
+			);
 
 			// Merge in the inlined objects
 			for (LDObject* inlinedObject : inlined.objects())
--- a/src/toolsets/extprogramtoolset.cpp	Mon Mar 19 11:04:18 2018 +0200
+++ b/src/toolsets/extprogramtoolset.cpp	Mon Mar 19 12:24:59 2018 +0200
@@ -157,7 +157,7 @@
 		{
 			LDSubfileReference* ref = static_cast<LDSubfileReference*> (obj);
 			Model model {m_documents};
-			ref->inlineContents(m_documents, model, true, false);
+			ref->inlineContents(m_documents, CounterClockwise, model, true, false);
 			writeObjects(model.objects(), f);
 		}
 		else if (obj->type() == LDObjectType::BezierCurve)

mercurial