CurveCreator_Diff.cxx
CurveCreator_Displayer.cxx
CurveCreator_Operation.cxx
+ CurveCreator_Section.cxx
CurveCreator_Utils.cxx
CurveCreator_UtilsICurve.cxx
)
namespace CurveCreator
{
//! Points coordinates
- typedef float TypeCoord;
+ typedef double TypeCoord;
/** List of coordinates in format depends on section dimension:
* 2D: [x1, y1, x2, y2, x3, y3, ..]
std::string aName(aBuffer);
int j;
for( j = 0 ; j < mySections.size() ; j++ ){
- aSection = getSection( j );
+ aSection = (CurveCreator_Section*)getSection( j );
if ( aSection && aSection->myName == aName )
break;
}
int aMovedSectionId = theISection >= 0 ? theISection : mySections.size()-1;
if (aMovedSectionId != theNewIndex) {
- CurveCreator_Section* aSection = getSection( aMovedSectionId );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( aMovedSectionId );
// Remove section
CurveCreator::Sections::iterator anIter = mySections.begin() + aMovedSectionId;
CurveCreator_Section* aSection;
for (; i < aNbSections; i++) {
- aSection = getSection( i );
+ aSection = (CurveCreator_Section*)getSection( i );
if ( aSection )
delete aSection;
}
return res;
int anISectionMain = theSections.front();
- CurveCreator_Section* aSectionMain = getSection( anISectionMain );
+ CurveCreator_Section* aSectionMain =
+ (CurveCreator_Section*)getSection( anISectionMain );
std::list <int> aSectionsToJoin = theSections;
aSectionsToJoin.erase( aSectionsToJoin.begin() ); // skip the main section
std::list<int>::const_iterator anIt = aSectionsToJoin.begin(), aLast = aSectionsToJoin.end();
CurveCreator_Section* aSection;
for (; anIt != aLast; anIt++) {
- aSection = getSection( *anIt );
+ aSection = (CurveCreator_Section*)getSection( *anIt );
aSectionMain->myPoints.insert(aSectionMain->myPoints.end(), aSection->myPoints.begin(),
aSection->myPoints.end());
res = removeSectionInternal(*anIt);
const int aNbSections = getNbSections();
for (; i < aNbSections; i++) {
- aSection = getSection( i );
+ aSection = (CurveCreator_Section*)getSection( i );
if ( aSection )
aNbCoords += aSection->myPoints.size();
}
} else {
- aSection = getSection( theISection );
+ aSection = (CurveCreator_Section*)getSection( theISection );
if ( aSection )
aNbCoords = aSection->myPoints.size();
}
//! Get "closed" flag of the specified section
bool CurveCreator_Curve::isClosed( const int theISection ) const
{
- CurveCreator_Section* aSection = getSection( theISection );
+ const CurveCreator_Section* aSection =
+ (CurveCreator_Section*)getSection( theISection );
return aSection ? aSection->myIsClosed : false;
}
int i;
for (i = 0; i < aSize; i++) {
- aSection = getSection( i );
+ aSection = (CurveCreator_Section*)getSection( i );
if( aSection ) {
aSection->myIsClosed = theIsClosed;
redisplayCurve();
}
}
} else {
- aSection = getSection( theISection );
+ aSection = (CurveCreator_Section*)getSection( theISection );
if ( aSection ) {
aSection->myIsClosed = theIsClosed;
redisplayCurve();
//! Returns specified section name
std::string CurveCreator_Curve::getSectionName( const int theISection ) const
{
- CurveCreator_Section* aSection = getSection( theISection );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theISection );
return aSection ? aSection->myName : "";
}
const std::string& theName )
{
bool res = false;
- CurveCreator_Section* aSection = getSection( theISection );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theISection );
if( aSection ) {
aSection->myName = theName;
res = true;
CurveCreator::SectionType CurveCreator_Curve::getSectionType
( const int theISection ) const
{
- CurveCreator_Section* aSection = getSection( theISection );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theISection );
return aSection ? aSection->myType : CurveCreator::Polyline;
}
const int aNbSections = getNbSections();
for (; i < aNbSections; i++) {
- aSection = getSection( i );
+ aSection = (CurveCreator_Section*)getSection( i );
if ( aSection )
aSection->myType = theType;
}
redisplayCurve();
} else {
- aSection = getSection( theISection );
+ aSection = (CurveCreator_Section*)getSection( theISection );
if ( aSection && aSection->myType != theType ){
aSection->myType = theType;
redisplayCurve();
CurveCreator_Section *aSection = 0;
for ( ; anIt != theSectionsMap.end(); anIt++ ) {
int anISection = anIt->first;
- aSection = getSection( anISection );
+ aSection = (CurveCreator_Section*)getSection( anISection );
if( aSection ) {
CurveCreator::PosPointsList aSectionPoints = anIt->second;
CurveCreator::PosPointsList::const_iterator aPntIt = aSectionPoints.begin();
CurveCreator_Section *aSection = 0;
for ( ; anIt != theSectionsMap.end(); anIt++ ) {
int anISection = anIt->first;
- aSection = getSection( anISection );
+ aSection = (CurveCreator_Section*)getSection( anISection );
if( aSection ) {
CurveCreator::PosPointsList aSectionPoints = anIt->second;
CurveCreator::PosPointsList::const_iterator aPntIt = aSectionPoints.begin();
CurveCreator::Coordinates CurveCreator_Curve::getPoint( const int theISection,
const int theIPnt) const
{
- CurveCreator_Section* aSection = getSection( theISection );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theISection );
CurveCreator::Coordinates::const_iterator
anIter = aSection->myPoints.begin() + toICoord(theIPnt);
CurveCreator::Coordinates aResult(anIter, anIter + myDimension);
//=======================================================================
CurveCreator::Coordinates CurveCreator_Curve::getPoints( const int theISection ) const
{
- CurveCreator_Section* aSection = getSection( theISection );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theISection );
return aSection ? aSection->myPoints : CurveCreator::Coordinates();
}
myAISShape = new AIS_Shape( aShape );
}
-CurveCreator_Section* CurveCreator_Curve::getSection( const int theSectionId ) const
-{
- CurveCreator_Section *aSection = 0;
- if ( theSectionId >= 0 && theSectionId < mySections.size() )
- aSection = mySections.at( theSectionId );
-
- return aSection;
-}
-
Handle(AIS_InteractiveObject) CurveCreator_Curve::getAISObject( const bool theNeedToBuild ) const
{
if ( !myAISShape && theNeedToBuild ) {
{
bool aRes = false;
- CurveCreator_Section* aSection = getSection( theSectionId );
+ CurveCreator_Section* aSection = (CurveCreator_Section*)getSection( theSectionId );
if ( !aSection )
return aRes;
virtual bool setSectionType( const int theISection,
const CurveCreator::SectionType theType );
+ //! A virtual method.
+ const CurveCreator_ISection* getSection(const int theSectionIndex) const
+ {
+ if (theSectionIndex >= 0 && theSectionIndex < mySections.size())
+ {
+ return (CurveCreator_ISection*)mySections[theSectionIndex];
+ }
+ return NULL;
+ }
+
+ //! A virtual method.
+ CurveCreator_ISection* getSection(const int theSectionIndex)
+ {
+ return (CurveCreator_ISection*)mySections[theSectionIndex];
+ }
/***********************************************/
/*** Point methods ***/
protected:
virtual void constructAISObject();
- /**
- * Returns the section by the section index or NULL if the index is out of the section
- * list range
- * \param theSectionId the section index
- */
- CurveCreator_Section* getSection( const int theSectionId ) const;
protected:
bool mySkipSorting;
#ifndef _CurveCreator_ICurve_HeaderFile
#define _CurveCreator_ICurve_HeaderFile
+#include "CurveCreator.hxx"
#include "CurveCreator_Macro.hxx"
+
+#include <TColgp_HArray1OfPnt.hxx>
+
#include <deque>
#include <vector>
#include <string>
};
+//! The type represents the interface to the curve section.
+struct CURVECREATOR_EXPORT CurveCreator_ISection
+{
+ //! The destructor.
+ virtual ~CurveCreator_ISection() {}
+
+ //! Calculates the different points of the section.
+ virtual void GetDifferentPoints(
+ const int theDimension, Handle(TColgp_HArray1OfPnt)& thePoints) const = 0;
+};
+
/**
* The CurveCreator_ICurve object is represented as one or more sets of
* connected points; thus CurveCreator_ICurve object can contain several
typedef std::pair<int,int> SectionToPoint;
typedef std::deque<SectionToPoint> SectionToPointList;
- typedef std::deque< std::pair< SectionToPoint,std::deque< float > > > SectionToPointCoordsList;
+ typedef std::deque< std::pair< SectionToPoint, CurveCreator::Coordinates > > SectionToPointCoordsList;
public:
/***********************************************/
/*** Undo/Redo methods ***/
/***********************************************/
+ //! The destructor.
+ virtual ~CurveCreator_ICurve() {}
+
//! Get number of available undo operations
virtual int getNbUndo() const = 0;
virtual bool setSectionType( const int theISection,
const CurveCreator::SectionType theType ) = 0;
+ //! Returns the curve section with the index.
+ virtual const CurveCreator_ISection* getSection(
+ const int theSectionIndex) const = 0;
+
+ //! Returns the curve section with the index.
+ virtual CurveCreator_ISection* getSection(const int theSectionIndex) = 0;
+
/***********************************************/
/*** Point methods ***/
* Insert one or several points to the specified section starting from the given theIPnt index
* (or add these at the end of section points if \a theIPnt is -1).
*/
- virtual bool addPoints( const std::deque<float>& theCoords,
+ virtual bool addPoints( const CurveCreator::Coordinates& theCoords,
const int theISection,
const int theIPnt = -1 ) = 0;
//! Set coordinates of specified point
virtual bool setPoint( const int theISection,
const int theIPnt,
- const std::deque<float>& theNewCoords ) = 0;
+ const CurveCreator::Coordinates& theNewCoords ) = 0;
//! Set coordinates of specified points from different sections
virtual bool setSeveralPoints( const SectionToPointCoordsList &theSectionToPntCoords,
virtual bool removeSeveralPoints( const SectionToPointList &theSectionToPntIDs) = 0;
//! Get coordinates of specified point
- virtual std::deque<float> getPoint( const int theISection,
+ virtual CurveCreator::Coordinates getPoint( const int theISection,
const int theIPnt ) const = 0;
/**
* Get points of a section (the total points in Curve if theISection is equal to -1)..
*/
- virtual std::deque<float> getPoints( const int theISection = -1 ) const = 0;
+ virtual CurveCreator::Coordinates getPoints( const int theISection = -1 ) const = 0;
/**
* Get number of points in specified section or (the total number of points
int nbPoints = pInt[0];
int nbCoords = pInt[1];
- int nbParams = 3+nbCoords;
+ int nbParams = 3+nbCoords*sizeof(double)/sizeof(int);
for (int i = 0; i < nbPoints*nbParams; i=i+nbParams) {
aCoords.clear();
aPoints.clear();
--- /dev/null
+// Copyright (C) 2013-2015 CEA/DEN, EDF R&D, OPEN CASCADE
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
+//
+
+// File: CurveCreator_Section.cxx
+// Author: Aleksandr BOBKOV
+
+#include "CurveCreator_Section.hxx"
+
+#include <vector>
+
+const double POINT_CONFUSION = 1e-4;
+
+//=======================================================================
+// function: GetDifferentPoints
+// purpose:
+//=======================================================================
+void CurveCreator_Section::GetDifferentPoints(
+ const int theDimension, Handle(TColgp_HArray1OfPnt)& thePoints) const
+{
+ std::vector<gp_Pnt> aTmpPoints;
+ CurveCreator::Coordinates::const_iterator aPIt = myPoints.begin();
+ CurveCreator::Coordinates::const_iterator aPItLast = myPoints.end();
+ const gp_Pnt aFirstPoint(
+ *aPIt, *(aPIt + 1), (theDimension == 2) ? 0 : *(aPIt + 2));
+ gp_Pnt aPoint = aFirstPoint;
+ aTmpPoints.push_back(aPoint);
+
+ for (; aPIt != aPItLast; aPIt += theDimension)
+ {
+ const gp_Pnt aPoint2(
+ *aPIt, *(aPIt + 1), (theDimension == 2) ? 0 : *(aPIt + 2));
+ if (!aPoint.IsEqual(aPoint2, POINT_CONFUSION))
+ {
+ aPoint = aPoint2;
+ aTmpPoints.push_back(aPoint);
+ }
+ }
+
+ int aPointCount = aTmpPoints.size();
+ if (myIsClosed)
+ {
+ while (aPointCount > 1 &&
+ aFirstPoint.IsEqual(aTmpPoints[aPointCount - 1], POINT_CONFUSION))
+ {
+ --aPointCount;
+ }
+ }
+
+ thePoints = new TColgp_HArray1OfPnt(1, aPointCount);
+ for (int aPI = 0; aPI < aPointCount; ++aPI)
+ {
+ thePoints->SetValue(aPI + 1, aTmpPoints[aPI]);
+ }
+}
#define _CurveCreator_Section_HeaderFile
#include "CurveCreator.hxx"
+#include "CurveCreator_ICurve.hxx"
#include <string>
//! Structure to store sections representing the CurveCreator_Curve object
-struct CurveCreator_Section
+struct CURVECREATOR_EXPORT CurveCreator_Section :
+ public CurveCreator_ISection
{
//! Constructor. Initializes object with default values.
CurveCreator_Section() : myName("Section"),myType(CurveCreator::Polyline), myIsClosed(false)
CurveCreator::SectionType myType; //!< type of the section
bool myIsClosed; //!< closed or not
+ //! A virtual method.
+ void GetDifferentPoints(const int theDimension, Handle(TColgp_HArray1OfPnt)& thePoints) const;
};
#endif
#include <QTableWidget>
#include <QTableWidgetItem>
+#include <QHeaderView>
#include <QtxDoubleSpinBox.h>
//aLabels << tr( "SECTION_LABEL" ) << tr( "IDENTIFIER_LABEL" ) << aCoord1 << aCoord2;
aLabels << tr( "TABLE_SECTION" ) << tr("TABLE_INDEX") << aCoord1 << aCoord2;
setHorizontalHeaderLabels( aLabels );
+
+ connect( horizontalHeader(), SIGNAL( sectionClicked( int ) ), this, SLOT( OnHeaderClick( int ) ) );
}
void CurveCreator_TableView::setCurve( CurveCreator_ICurve* theCurve )
QTableWidgetItem* anItem;
anItem = new QTableWidgetItem( myCurve->getSectionName( anISection ).c_str() );
- anItem->setFlags( anItem->flags() & ~Qt::ItemIsEnabled );
+ anItem->setFlags( anItem->flags() & ~Qt::ItemIsEditable );
anItem->setData( Qt::UserRole, anISection );
setItem( aRowId, 0, anItem );
anItem = new QTableWidgetItem( QString::number( anIPoint + 1 ) );
anItem->setFlags( anItem->flags() & ~Qt::ItemIsEnabled );
anItem->setData( Qt::UserRole, anIPoint );
+ anItem->setData( Qt::DisplayRole, anIPoint );
setItem( aRowId, 1, anItem );
gp_Pnt aPoint;
setItem( aRowId, 2, anItem );
}
anItem->setData( Qt::UserRole, aPoint.X() );
- anItem->setData( Qt::DisplayRole, QString::number( aPoint.X(), 'f', 2 ) );
+ anItem->setData( Qt::DisplayRole, QString::number( aPoint.X(), 'f', 2 ).toDouble() );
anItem = item( aRowId, 3 );
if ( !anItem ) {
setItem( aRowId, 3, anItem );
}
anItem->setData( Qt::UserRole, aPoint.Y() );
- anItem->setData( Qt::DisplayRole, QString::number( aPoint.Y(), 'f', 2 ) );
+ anItem->setData( Qt::DisplayRole, QString::number( aPoint.Y(), 'f', 2 ).toDouble() );
aRowId++;
}
{
return item( theRowId, 1 )->data( Qt::UserRole ).toInt();
}
+
+void CurveCreator_TableView::OnHeaderClick( int theLogicalId )
+{
+ sortByColumn( theLogicalId, Qt::AscendingOrder );
+}
*/
int getPointId( const int theRowId ) const;
+private slots:
+ void OnHeaderClick( int );
+
private:
CurveCreator_ICurve* myCurve;
#include "CurveCreator_Utils.hxx"
#include "CurveCreator.hxx"
#include "CurveCreator_Curve.hxx"
+#include "CurveCreator_Section.hxx"
#include "CurveCreator_UtilsICurve.hxx"
#include <Basics_OCCTVersion.hxx>
return ResultPoint;
}
-void CurveCreator_Utils::constructShape( const CurveCreator_ICurve* theCurve,
- TopoDS_Shape& theShape )
+//=======================================================================
+// function : constructBSpline
+// purpose :
+//=======================================================================
+bool CurveCreator_Utils::constructBSpline(
+ const Handle(TColgp_HArray1OfPnt)& thePoints,
+ const Standard_Boolean theIsClosed,
+ Handle(Geom_BSplineCurve)& theBSpline)
{
- BRep_Builder aBuilder;
- TopoDS_Compound aComp;
- aBuilder.MakeCompound( aComp );
- for( int iSection = 0 ; iSection < theCurve->getNbSections() ; iSection++ )
+ const int aPointCount = thePoints->Length();
+ if (aPointCount <= 1)
{
- int theISection = iSection;
+ return false;
+ }
- CurveCreator::SectionType aSectType = theCurve->getSectionType( theISection );
- int aPointSize = theCurve->getNbPoints( theISection );
- if ( aPointSize == 0 )
- continue;
+ // Calculate the tangents.
+ TColgp_Array1OfVec aTangents(1, aPointCount);
+ Handle(TColStd_HArray1OfBoolean) aTangentFlags =
+ new TColStd_HArray1OfBoolean(1, aPointCount);
+ GeomAPI_Interpolate aInterpolator(thePoints, theIsClosed, 0);
+ if (aPointCount == 2)
+ {
+ aTangentFlags->SetValue(1, Standard_False);
+ aTangentFlags->SetValue(2, Standard_False);
+ }
+ else
+ {
+ for (Standard_Integer aPN = 1; aPN <= aPointCount; ++aPN)
+ {
+ gp_Vec aTangent;
+ if (aPN != 1 || theIsClosed)
+ {
+ const Standard_Integer aPN1 = (aPN != 1) ? (aPN - 1) : aPointCount;
+ aTangent = gp_Vec(thePoints->Value(aPN1),
+ thePoints->Value(aPN)).Normalized();
+ }
+ if (aPN < aPointCount || theIsClosed)
+ {
+ const Standard_Integer aPN2 = (aPN != aPointCount) ? (aPN + 1) : 1;
+ const gp_Vec aTangent2 = aTangent +
+ gp_Vec(thePoints->Value(aPN), thePoints->Value(aPN2)).Normalized();
+ if (aTangent2.SquareMagnitude() >= Precision::SquareConfusion())
+ {
+ aTangent = aTangent2.Normalized();
+ }
+ else
+ {
+ aTangent = -aTangent;
+ }
+ }
+ aTangents.SetValue(aPN, aTangent);
+ aTangentFlags->SetValue(aPN, Standard_True);
+ }
+ }
- bool aSectIsClosed = theCurve->isClosed( theISection );
- bool isPolyline = aSectType == CurveCreator::Polyline;
-
- int iPoint = 0;
- gp_Pnt aPrevPoint, aPoint;
- // filters the curve points to skip equal points
- std::vector<gp_Pnt> aPoints;
- CurveCreator_UtilsICurve::getPoint( theCurve, theISection, iPoint, aPoint );
- aPoints.push_back( aPoint );
- aPrevPoint = aPoint;
- iPoint++;
- for( ; iPoint < aPointSize; iPoint++ ) {
- CurveCreator_UtilsICurve::getPoint( theCurve, theISection, iPoint, aPoint );
- if ( !isEqualPoints( aPrevPoint, aPoint ) )
- aPoints.push_back( aPoint );
- aPrevPoint = aPoint;
+ // Interpolate.
+ aInterpolator.Load(aTangents, aTangentFlags, Standard_False);
+ aInterpolator.Perform();
+ const bool aResult = (aInterpolator.IsDone() == Standard_True);
+ if (aResult)
+ {
+ theBSpline = aInterpolator.Curve();
+ }
+ return aResult;
+}
+
+//=======================================================================
+// function : constructWire
+// purpose :
+//=======================================================================
+TopoDS_Wire CurveCreator_Utils::ConstructWire(
+ Handle(TColgp_HArray1OfPnt) thePoints,
+ const bool theIsPolyline,
+ const bool theIsClosed)
+{
+ TopoDS_Wire aWire;
+ BRep_Builder aBuilder;
+ aBuilder.MakeWire(aWire);
+ const int aPointCount = thePoints->Length();
+ if (theIsPolyline)
+ {
+ const TopoDS_Vertex aFirstVertex =
+ BRepBuilderAPI_MakeVertex(thePoints->Value(1));
+ TopoDS_Vertex aVertex = aFirstVertex;
+ for (Standard_Integer aPN = 1; aPN < aPointCount; ++aPN)
+ {
+ const TopoDS_Vertex aVertex2 =
+ BRepBuilderAPI_MakeVertex(thePoints->Value(aPN + 1));
+ aBuilder.Add(aWire, BRepBuilderAPI_MakeEdge(aVertex, aVertex2));
+ aVertex = aVertex2;
+ }
+ if (theIsClosed && aPointCount > 1)
+ {
+ aBuilder.Add(aWire, BRepBuilderAPI_MakeEdge(aVertex, aFirstVertex));
}
- int aNbPoints = aPoints.size();
+ }
+ else
+ {
+ Handle(Geom_BSplineCurve) aBSpline;
+ if (constructBSpline(thePoints, theIsClosed, aBSpline))
+ {
+ aBuilder.Add(aWire, BRepBuilderAPI_MakeEdge(aBSpline));
+ }
+ }
+ return aWire;
+}
- if ( aNbPoints == 1 ) {
- aPoint = aPoints.front();
- TopoDS_Vertex aVertex = BRepBuilderAPI_MakeVertex( aPoint ).Vertex();
- aBuilder.Add( aComp, aVertex );
+//=======================================================================
+// function : constructShape
+// purpose :
+//=======================================================================
+void CurveCreator_Utils::constructShape(
+ const CurveCreator_ICurve* theCurve, TopoDS_Shape& theShape)
+{
+ BRep_Builder aBuilder;
+ TopoDS_Compound aShape;
+ aBuilder.MakeCompound(aShape);
+ const int aSectionCount = theCurve->getNbSections();
+ for (int aSectionI = 0; aSectionI < aSectionCount; ++aSectionI)
+ {
+ const int aTmpPointCount = theCurve->getNbPoints(aSectionI);
+ if (aTmpPointCount == 0)
+ {
+ continue;
}
- else if ( aNbPoints > 1 ) {
- Handle(TColgp_HArray1OfPnt) aHCurvePoints = new TColgp_HArray1OfPnt(1, aNbPoints);
- TColgp_Array1OfVec aTangents(1, aNbPoints);
- Handle(TColStd_HArray1OfBoolean) aTangentFlags = new TColStd_HArray1OfBoolean(1, aNbPoints);
- gp_Vec aNullVec(0, 0, 0);
-
- TopoDS_Edge aPointEdge;
- TopoDS_Vertex aVertex;
-
- std::vector<gp_Pnt>::const_iterator aPointIt = aPoints.begin(), aPointLast = aPoints.end();
- aPoint = *aPointIt;
-
- int aHIndex = 1;
- aVertex = BRepBuilderAPI_MakeVertex( aPoint ).Vertex();
- aBuilder.Add( aComp, aVertex );
- if ( !isPolyline ) {
- aHCurvePoints->SetValue( aHIndex, aPoint );
- aTangents.SetValue( aHIndex, aNullVec );
- aTangentFlags->SetValue( aHIndex, Standard_False );
- aHIndex++;
- }
- aPrevPoint = aPoint;
- aPointIt++;
- for( ; aPointIt != aPointLast; aPointIt++ ) {
- aPoint = *aPointIt;
- aVertex = BRepBuilderAPI_MakeVertex( aPoint ).Vertex();
- aBuilder.Add( aComp, aVertex );
- if ( isPolyline ) {
- TopoDS_Edge aPointEdge = BRepBuilderAPI_MakeEdge( aPrevPoint, aPoint ).Edge();
- aBuilder.Add( aComp, aPointEdge );
- }
- else {
- aHCurvePoints->SetValue( aHIndex, aPoint );
- aTangents.SetValue( aHIndex, aNullVec );
- aTangentFlags->SetValue( aHIndex, Standard_False );
- aHIndex++;
- }
- aPrevPoint = aPoint;
- }
- if( aSectIsClosed && ( aNbPoints > 2 ) ) {
- aPoint = aPoints.front();
- aVertex = BRepBuilderAPI_MakeVertex( aPoint ).Vertex();
- aBuilder.Add( aComp, aVertex );
- if ( isPolyline ) {
- aPointEdge = BRepBuilderAPI_MakeEdge( aPrevPoint, aPoint ).Edge();
- aBuilder.Add( aComp, aPointEdge );
- }
- }
- if( !isPolyline ) {
- // compute BSpline
- Handle(Geom_BSplineCurve) aBSplineCurve;
- GeomAPI_Interpolate aGBC(aHCurvePoints, aSectIsClosed, gp::Resolution());
- // correct the spline degree to be as 3 for non-periodic spline if number of points
- // less than 3. It is need to have a knot in each spline point. This knots are used
- // to found a neighbour points when a new point is inserted between two existing.
- if (!aSectIsClosed ) {
- if (aHCurvePoints->Length() == 3)
- aGBC.Load(aTangents, aTangentFlags);
- }
+ // Get the different points.
+ const CurveCreator_ISection* aSection = theCurve->getSection(aSectionI);
+ Handle(TColgp_HArray1OfPnt) aPoints;
+ aSection->GetDifferentPoints(theCurve->getDimension(), aPoints);
+ const int aPointCount = aPoints->Length();
+ const bool isClosed = theCurve->isClosed(aSectionI);
- aGBC.Perform();
- if ( aGBC.IsDone() )
- aBSplineCurve = aGBC.Curve();
- TopoDS_Edge anEdge = BRepBuilderAPI_MakeEdge( aBSplineCurve ).Edge();
- TopoDS_Wire aWire = BRepBuilderAPI_MakeWire( anEdge ).Wire();
- aBuilder.Add( aComp, aWire );
- }
+ // Add the vertices to the shape.
+ for (Standard_Integer aPN = 1; aPN <= aPointCount; ++aPN)
+ {
+ aBuilder.Add(aShape, BRepBuilderAPI_MakeVertex(aPoints->Value(aPN)));
+ }
+
+ // Add the wire to the shape.
+ const bool isPolyline =
+ (theCurve->getSectionType(aSectionI) == CurveCreator::Polyline);
+ const TopoDS_Wire aWire = ConstructWire(aPoints, isPolyline, isClosed);
+ if (!aWire.IsNull())
+ {
+ aBuilder.Add(aShape, aWire);
}
}
- theShape = aComp;
+ theShape = aShape;
}
/**
{
thePoints.clear();
- std::list<float> aSelectedPoints;
+ std::list<double> aSelectedPoints;
gp_Pnt aPnt;
std::map<CompareSectionToPoint, int> aPointsMap;
#include <gp_Pnt.hxx>
#include <Geom_Curve.hxx>
#include <TopoDS_Shape.hxx>
+#include <TopoDS_Wire.hxx>
#include <TColgp_HArray1OfPnt.hxx>
+#include <Geom_BSplineCurve.hxx>
#include <list>
#include <vector> // TODO: remove
gp_Pnt& thePoint, gp_Pnt& thePoint1,
gp_Pnt& thePoint2 );
+ /**
+ * The algorithm builds the cubic B-spline passing through the points that the
+ * tangent vector in each given point P is calculated by the following way:
+ * if point P is preceded by a point A and is followed by a point B then
+ * the tangent vector is equal to (P - A) / |P - A| + (B - P) / |B - P|;
+ * if point P is preceded by a point A but is not followed by any point then
+ * the tangent vector is equal to P - A;
+ * if point P is followed by a point B but is not preceded by any point then
+ * the tangent vector is equal to B - P.
+ */
+ CURVECREATOR_EXPORT static bool constructBSpline( const Handle(TColgp_HArray1OfPnt)& thePoints,
+ const Standard_Boolean theIsClosed,
+ Handle(Geom_BSplineCurve)& theBSpline );
+
+ /**
+ * Constructs the wire corresponding to the section.
+ */
+ CURVECREATOR_EXPORT static TopoDS_Wire ConstructWire(
+ Handle(TColgp_HArray1OfPnt) thePoints,
+ const bool theIsPolyline,
+ const bool theIsClosed);
+
protected:
/*
* Returns whether the clicked point belong to the curve or has a very near projection
const double LOCAL_SELECTION_TOLERANCE = 0.0001;
int CurveCreator_UtilsICurve::findLocalPointIndex( const CurveCreator_ICurve* theCurve,
- int theSectionId, float theX, float theY )
+ int theSectionId, double theX, double theY )
{
int aPntIndex = -1;
if ( !theCurve )
* \param theY the Y coordinate of the point
*/
CURVECREATOR_EXPORT static int findLocalPointIndex( const CurveCreator_ICurve* theCurve,
- int theSectionId, float theX, float theY );
+ int theSectionId, double theX, double theY );
CURVECREATOR_EXPORT static void findSectionsToPoints( const CurveCreator_ICurve* theCurve,
const double theX, const double theY,
*/
void CurveCreator_Widget::onMouseRelease( SUIT_ViewWindow* theWindow, QMouseEvent* theEvent )
{
- if ( getActionMode() != ModificationMode )
+ ActionMode aMode = getActionMode();
+ if ( aMode != ModificationMode )
{
// Emit selectionChanged() signal
getOCCViewer()->performSelectionChanged();
+
+ if ( aMode == AdditionMode )
+ {
+ Handle(AIS_InteractiveContext) aCtx = getAISContext();
+ if ( !aCtx.IsNull() )
+ aCtx->ClearSelected();
+ }
return;
}
if (theEvent->button() != Qt::LeftButton) return;
if ( myDragStarted ) {
bool isDragged = myDragged;
CurveCreator_ICurve::SectionToPointList aDraggedPoints;
- QMap<CurveCreator_ICurve::SectionToPoint, std::deque< float > > anInitialDragPointsCoords;
+ QMap<CurveCreator_ICurve::SectionToPoint, CurveCreator::Coordinates > anInitialDragPointsCoords;
if ( myDragged ) {
aDraggedPoints = myDragPoints;
anInitialDragPointsCoords = myInitialDragPointsCoords;
for ( ; anIt != aLast; anIt++ ) {
int aSectionId = anIt->first;
int aPointId = anIt->second;
- std::deque<float> aPos = myCurve->getPoint( aSectionId, aPointId );
+ CurveCreator::Coordinates aPos = myCurve->getPoint( aSectionId, aPointId );
aCoordList.push_back(
std::make_pair( std::make_pair( aSectionId, aPointId ), aPos ) );
double aX = myLocalPointView->item( theRow, 2 )->data( Qt::UserRole ).toDouble();
double anY = myLocalPointView->item( theRow, 3 )->data( Qt::UserRole ).toDouble();
- std::deque<float> aChangedPos;
+ CurveCreator::Coordinates aChangedPos;
aChangedPos.push_back( aX );
aChangedPos.push_back( anY );
myCurve->setPoint( aCurrSect, aPntIndex, aChangedPos );
double anYDelta = aStartPnt.Y() - anEndPnt.Y();
CurveCreator_ICurve::SectionToPointCoordsList aCoordList;
- std::deque<float> aChangedPos;
+ CurveCreator::Coordinates aChangedPos;
CurveCreator_ICurve::SectionToPointList::const_iterator anIt = myDragPoints.begin(),
aLast = myDragPoints.end();
for ( ; anIt != aLast; anIt++ ) {
* \param theX the X coordinate of the point
* \param theY the Y coordinate of the point
*/
-int CurveCreator_Widget::findLocalPointIndex( int theSectionId, float theX, float theY )
+int CurveCreator_Widget::findLocalPointIndex( int theSectionId, double theX, double theY )
{
return CurveCreator_UtilsICurve::findLocalPointIndex( myCurve, theSectionId, theX, theY );
}
CurveCreator_ICurve::SectionToPointList() );
// curve algorithm
- int findLocalPointIndex( int theSectionId, float theX, float theY );
+ int findLocalPointIndex( int theSectionId, double theX, double theY );
void findSectionsToPoints( const double theX, const double theY,
CurveCreator_ICurve::SectionToPointList& thePoints );
void convert( const CurveCreator_ICurve::SectionToPointList& thePoints,
#include <BRepBuilderAPI_MakeWire.hxx>
#include <ElSLib.hxx>
#include <GeomAPI_Interpolate.hxx>
+#include <TColgp_Array1OfVec.hxx>
#include <TColgp_HArray1OfPnt.hxx>
+#include <TColStd_HArray1OfBoolean.hxx>
#include <TopoDS_Wire.hxx>
const double POINT_CONFUSION_TOLERANCE = 0.0001;
}
//=======================================================================
-// function : MakeInterpolation
-// purpose :
+// function : constructBSpline
+// purpose : See function 'constructBSpline' in file 'CurveCreator_Utils.cxx'.
//=======================================================================
-TopoDS_Shape Sketcher_Utils::MakeInterpolation
- (const std::list <double> &theCoords2D,
- const Standard_Boolean IsClosed,
- const gp_Ax3 &thePlane)
+static bool constructBSpline(
+ const Handle(TColgp_HArray1OfPnt)& thePoints,
+ const Standard_Boolean theIsClosed,
+ Handle(Geom_BSplineCurve)& theBSpline)
{
- std::list <gp_Pnt> aPoints;
- TopoDS_Shape aResult;
-
- To3D(theCoords2D, thePlane, aPoints);
-
- Standard_Integer aNbPnts = aPoints.size();
-
- if (aNbPnts > 1) {
- if (IsClosed &&
- aPoints.front().IsEqual(aPoints.back(), POINT_CONFUSION_TOLERANCE)) {
- // The polyline should be closed, first and last points are confused.
- // Remove the last point.
- aPoints.pop_back();
- --aNbPnts;
- }
+ const int aPointCount = thePoints->Length();
+ if (aPointCount <= 1)
+ {
+ return false;
}
- if (aNbPnts == 1) {
- // The result is vertex.
- aResult = BRepBuilderAPI_MakeVertex(aPoints.front()).Vertex();
- } else if (aNbPnts > 1) {
- std::list <gp_Pnt>::const_iterator anIter = aPoints.begin();
- Handle(TColgp_HArray1OfPnt) aHCurvePoints =
- new TColgp_HArray1OfPnt(1, aNbPnts);
- Standard_Integer i;
-
- for (i = 1; anIter != aPoints.end(); ++anIter, ++i) {
- aHCurvePoints->SetValue(i, *anIter);
+ // Calculate the tangents.
+ TColgp_Array1OfVec aTangents(1, aPointCount);
+ Handle(TColStd_HArray1OfBoolean) aTangentFlags =
+ new TColStd_HArray1OfBoolean(1, aPointCount);
+ GeomAPI_Interpolate aInterpolator(thePoints, theIsClosed, 0);
+ if (aPointCount == 2)
+ {
+ aTangentFlags->SetValue(1, Standard_False);
+ aTangentFlags->SetValue(2, Standard_False);
+ }
+ else
+ {
+ for (Standard_Integer aPN = 1; aPN <= aPointCount; ++aPN)
+ {
+ gp_Vec aTangent;
+ if (aPN != 1 || theIsClosed)
+ {
+ const Standard_Integer aPN1 = (aPN != 1) ? (aPN - 1) : aPointCount;
+ aTangent = gp_Vec(thePoints->Value(aPN1),
+ thePoints->Value(aPN)).Normalized();
+ }
+ if (aPN < aPointCount || theIsClosed)
+ {
+ const Standard_Integer aPN2 = (aPN != aPointCount) ? (aPN + 1) : 1;
+ const gp_Vec aTangent2 = aTangent +
+ gp_Vec(thePoints->Value(aPN), thePoints->Value(aPN2)).Normalized();
+ if (aTangent2.SquareMagnitude() >= Precision::SquareConfusion())
+ {
+ aTangent = aTangent2.Normalized();
+ }
+ else
+ {
+ aTangent = -aTangent;
+ }
+ }
+ aTangents.SetValue(aPN, aTangent);
+ aTangentFlags->SetValue(aPN, Standard_True);
}
+ }
- // Compute BSpline
- Standard_Real aTol = Precision::Confusion();
- GeomAPI_Interpolate aGBC(aHCurvePoints, IsClosed, aTol);
+ // Interpolate.
+ aInterpolator.Load(aTangents, aTangentFlags, Standard_False);
+ aInterpolator.Perform();
+ const bool aResult = (aInterpolator.IsDone() == Standard_True);
+ if (aResult)
+ {
+ theBSpline = aInterpolator.Curve();
+ }
+ return aResult;
+}
- aGBC.Perform();
+//=======================================================================
+// function : MakeInterpolation
+// purpose :
+//=======================================================================
+TopoDS_Shape Sketcher_Utils::MakeInterpolation(
+ const std::list<double>& theCoords2D,
+ const Standard_Boolean theIsClosed,
+ const gp_Ax3& thePlane)
+{
+ if (theCoords2D.size() == 0)
+ {
+ return TopoDS_Shape();
+ }
- if (aGBC.IsDone()) {
- TopoDS_Edge anEdge = BRepBuilderAPI_MakeEdge(aGBC.Curve()).Edge();
- aResult = BRepBuilderAPI_MakeWire(anEdge).Wire();
+ // Get the different points.
+ std::list<gp_Pnt> aTmpPoints;
+ To3D(theCoords2D, thePlane, aTmpPoints);
+ gp_Pnt aFirstPoint = aTmpPoints.front();
+ gp_Pnt aPoint = aFirstPoint;
+ std::list<gp_Pnt>::iterator aPIt = aTmpPoints.begin();
+ for (++aPIt; aPIt != aTmpPoints.end();)
+ {
+ const gp_Pnt aPoint2 = *aPIt;
+ if (!aPoint.IsEqual(aPoint2, POINT_CONFUSION_TOLERANCE))
+ {
+ aPoint = aPoint2;
+ ++aPIt;
+ }
+ else
+ {
+ aTmpPoints.erase(aPIt);
+ }
+ }
+ if (theIsClosed)
+ {
+ while (--aPIt != aTmpPoints.begin() &&
+ aFirstPoint.IsEqual(*aPIt, POINT_CONFUSION_TOLERANCE))
+ {
+ aTmpPoints.erase(aPIt);
}
}
- return aResult;
+ // Process the single point case.
+ const int aPointCount = aTmpPoints.size();
+ if (aPointCount == 1)
+ {
+ return BRepBuilderAPI_MakeVertex(aTmpPoints.front());
+ }
+
+ // Process the other cases.
+ Handle(TColgp_HArray1OfPnt) aPoints =
+ new TColgp_HArray1OfPnt(1, aPointCount);
+ aPIt = aTmpPoints.begin();
+ for (Standard_Integer aPN = 1; aPIt != aTmpPoints.end(); ++aPIt, ++aPN)
+ {
+ aPoints->SetValue(aPN, *aPIt);
+ }
+ Handle(Geom_BSplineCurve) aBSpline;
+ if (constructBSpline(aPoints, theIsClosed, aBSpline))
+ {
+ return BRepBuilderAPI_MakeWire(BRepBuilderAPI_MakeEdge(aBSpline));
+ }
+ return TopoDS_Shape();
}
//=======================================================================