Port changes from develop branch.
--HG-- branch : feature
This commit is contained in:
parent
5a95ce9c8a
commit
12162e49e8
|
@ -34,6 +34,7 @@
|
|||
#include <QLineF>
|
||||
#include <QSet>
|
||||
#include <QVector>
|
||||
#include <QPainterPath>
|
||||
|
||||
const qreal maxL = 2.4;
|
||||
|
||||
|
@ -207,7 +208,6 @@ QVector<QPointF> VAbstractPiece::CheckLoops(const QVector<QPointF> &points)
|
|||
/*If we got less than 4 points no need seek loops.*/
|
||||
if (count < 4)
|
||||
{
|
||||
qDebug()<<"Less then 4 points. Doesn't need check for loops.";
|
||||
return points;
|
||||
}
|
||||
|
||||
|
@ -235,7 +235,6 @@ QVector<QPointF> VAbstractPiece::CheckLoops(const QVector<QPointF> &points)
|
|||
// That's why we parse from the end
|
||||
for (j = count-1; j >= i+2; --j)
|
||||
{
|
||||
|
||||
j == count-1 ? jNext = 0 : jNext = j+1;
|
||||
QLineF line2(points.at(j), points.at(jNext));
|
||||
|
||||
|
@ -257,11 +256,7 @@ QVector<QPointF> VAbstractPiece::CheckLoops(const QVector<QPointF> &points)
|
|||
// Method IsPointOnLineviaPDP will check it.
|
||||
if (VGObject::IsPointOnLineviaPDP(points.at(j), points.at(i), points.at(i+1))
|
||||
// Lines are not neighbors
|
||||
&& uniqueVertices.size() == 4
|
||||
&& line1.p2() != line2.p2()
|
||||
&& line1.p1() != line2.p1()
|
||||
&& line1.p2() != line2.p1()
|
||||
&& line1.p1() != line2.p2())
|
||||
&& uniqueVertices.size() == 4)
|
||||
{
|
||||
// Left to catch case where segments are on the same line, but do not have real intersections.
|
||||
QLineF tmpLine1 = line1;
|
||||
|
@ -279,21 +274,28 @@ QVector<QPointF> VAbstractPiece::CheckLoops(const QVector<QPointF> &points)
|
|||
|
||||
if (tmpIntrs1 == QLineF::BoundedIntersection || tmpIntrs2 == QLineF::BoundedIntersection)
|
||||
{ // Now we really sure that lines are on the same lines and have real intersections.
|
||||
status = ParallelIntersection;
|
||||
break;
|
||||
QPointF cPoint;
|
||||
const bool caseFlag = ParallelCrossPoint(line1, line2, cPoint);
|
||||
if (not caseFlag || CheckIntersection(points, i, i+1, j, jNext, cPoint))
|
||||
{
|
||||
status = ParallelIntersection;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (intersect == QLineF::BoundedIntersection)
|
||||
{
|
||||
if (uniqueVertices.size() == 4
|
||||
&& line1.p1() != crosPoint
|
||||
&& line1.p2() != crosPoint
|
||||
&& line2.p1() != crosPoint
|
||||
&& line2.p2() != crosPoint)
|
||||
if (uniqueVertices.size() == 4)
|
||||
{ // Break, but not if lines are neighbors
|
||||
status = BoundedIntersection;
|
||||
break;
|
||||
if ((line1.p1() != crosPoint
|
||||
&& line1.p2() != crosPoint
|
||||
&& line2.p1() != crosPoint
|
||||
&& line2.p2() != crosPoint) || CheckIntersection(points, i, i+1, j, jNext, crosPoint))
|
||||
{
|
||||
status = BoundedIntersection;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
status = NoIntersection;
|
||||
|
@ -302,34 +304,12 @@ QVector<QPointF> VAbstractPiece::CheckLoops(const QVector<QPointF> &points)
|
|||
switch (status)
|
||||
{
|
||||
case ParallelIntersection:
|
||||
{
|
||||
/*We have found a loop.*/
|
||||
// Very tricky case
|
||||
// See the file "collection/bugs/Issue_#603.val"
|
||||
const QLineF line1(points.at(i+1), points.at(j));
|
||||
const QLineF line2(points.at(i), points.at(jNext));
|
||||
|
||||
if (line1.length() <= line2.length())
|
||||
{
|
||||
// In this case we did not check a loop edges and can just skip them
|
||||
ekvPoints.append(points.at(i));
|
||||
ekvPoints.append(points.at(jNext));
|
||||
|
||||
i = j; // Skip a loo
|
||||
}
|
||||
else
|
||||
{
|
||||
// In this case a loop edges probably was also chacked and added to the list
|
||||
ekvPoints.clear();// Previous data is wrong and belong to loop.
|
||||
ekvPoints.append(points.at(j));
|
||||
ekvPoints.append(points.at(i+1));
|
||||
|
||||
count = j+1;// All beyond this belong to loop.
|
||||
}
|
||||
ekvPoints.append(points.at(i));
|
||||
ekvPoints.append(points.at(jNext));
|
||||
jNext > j ? i = jNext : i = j; // Skip a loop
|
||||
break;
|
||||
}
|
||||
case BoundedIntersection:
|
||||
/*We have found a loop.*/
|
||||
ekvPoints.append(points.at(i));
|
||||
ekvPoints.append(crosPoint);
|
||||
i = j;
|
||||
|
@ -831,3 +811,128 @@ qreal VAbstractPiece::AngleBetweenBisectors(const QLineF &b1, const QLineF &b2)
|
|||
return angle2;
|
||||
}
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------------------------------------------------
|
||||
bool VAbstractPiece::CheckIntersection(const QVector<QPointF> &points, int i, int iNext, int j, int jNext,
|
||||
const QPointF &crossPoint)
|
||||
{
|
||||
QVector<QPointF> sub1 = SubPath(points, iNext, j);
|
||||
sub1.append(crossPoint);
|
||||
sub1 = CheckLoops(CorrectEquidistantPoints(sub1, false));
|
||||
const qreal sub1Sum = SumTrapezoids(sub1);
|
||||
|
||||
QVector<QPointF> sub2 = SubPath(points, jNext, i);
|
||||
sub2.append(crossPoint);
|
||||
sub2 = CheckLoops(CorrectEquidistantPoints(sub2, false));
|
||||
const qreal sub2Sum = SumTrapezoids(sub2);
|
||||
|
||||
if (sub1Sum < 0 && sub2Sum < 0)
|
||||
{
|
||||
if (Crossing(sub1, sub2))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (not Crossing(sub1, sub2))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------------------------------------------------
|
||||
bool VAbstractPiece::ParallelCrossPoint(const QLineF &line1, const QLineF &line2, QPointF &point)
|
||||
{
|
||||
const bool l1p1el2p1 = (line1.p1() == line2.p1());
|
||||
const bool l1p2el2p2 = (line1.p2() == line2.p2());
|
||||
const bool l1p1el2p2 = (line1.p1() == line2.p2());
|
||||
const bool l1p2el2p1 = (line1.p2() == line2.p1());
|
||||
|
||||
if (l1p2el2p2 || l1p2el2p1)
|
||||
{
|
||||
point = line1.p2();
|
||||
return true;
|
||||
}
|
||||
else if (l1p1el2p1 || l1p1el2p2)
|
||||
{
|
||||
point = line1.p1();
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
point = QPointF();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------------------------------------------------
|
||||
bool VAbstractPiece::Crossing(const QVector<QPointF> &sub1, const QVector<QPointF> &sub2)
|
||||
{
|
||||
if (sub1.isEmpty() || sub2.isEmpty())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
const QRectF sub1Rect = QPolygonF(sub1).boundingRect();
|
||||
const QRectF sub2Rect = QPolygonF(sub2).boundingRect();
|
||||
if (not sub1Rect.intersects(sub2Rect))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
QPainterPath sub1Path;
|
||||
sub1Path.setFillRule(Qt::WindingFill);
|
||||
sub1Path.moveTo(sub1.at(0));
|
||||
for (qint32 i = 1; i < sub1.count(); ++i)
|
||||
{
|
||||
sub1Path.lineTo(sub1.at(i));
|
||||
}
|
||||
sub1Path.lineTo(sub1.at(0));
|
||||
|
||||
QPainterPath sub2Path;
|
||||
sub2Path.setFillRule(Qt::WindingFill);
|
||||
sub2Path.moveTo(sub2.at(0));
|
||||
for (qint32 i = 1; i < sub2.count(); ++i)
|
||||
{
|
||||
sub2Path.lineTo(sub2.at(i));
|
||||
}
|
||||
sub2Path.lineTo(sub2.at(0));
|
||||
|
||||
if (not sub1Path.intersects(sub2Path))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------------------------------------------------
|
||||
QVector<QPointF> VAbstractPiece::SubPath(const QVector<QPointF> &path, int startIndex, int endIndex)
|
||||
{
|
||||
if (path.isEmpty()
|
||||
|| startIndex < 0 || startIndex >= path.size()
|
||||
|| endIndex < 0 || endIndex >= path.size()
|
||||
|| startIndex == endIndex)
|
||||
{
|
||||
return path;
|
||||
}
|
||||
|
||||
QVector<QPointF> subPath;
|
||||
int i = startIndex - 1;
|
||||
do
|
||||
{
|
||||
++i;
|
||||
if (i >= path.size())
|
||||
{
|
||||
i = 0;
|
||||
}
|
||||
subPath.append(path.at(i));
|
||||
} while (i != endIndex);
|
||||
|
||||
return subPath;
|
||||
}
|
||||
|
|
|
@ -170,6 +170,11 @@ protected:
|
|||
private:
|
||||
QSharedDataPointer<VAbstractPieceData> d;
|
||||
|
||||
static bool CheckIntersection(const QVector<QPointF> &points, int i, int iNext, int j, int jNext,
|
||||
const QPointF &crossPoint);
|
||||
static bool ParallelCrossPoint(const QLineF &line1, const QLineF &line2, QPointF &point);
|
||||
static bool Crossing(const QVector<QPointF> &sub1, const QVector<QPointF> &sub2);
|
||||
static QVector<QPointF> SubPath(const QVector<QPointF> &path, int startIndex, int endIndex);
|
||||
static Q_DECL_CONSTEXPR qreal PointPosition(const QPointF &p, const QLineF &line);
|
||||
static qreal MaxLocalSA(const VSAPoint &p, qreal width);
|
||||
static QVector<QPointF> EkvPoint(const VSAPoint &p1Line1, const VSAPoint &p2Line1,
|
||||
|
|
Loading…
Reference in New Issue
Block a user