Download src/Mod/Part/App/Geom2d/Curve2dPyImp.cpp from AbdulElahGwaith/FreeCAD: direct link, hf CLI and curl.
- Browser
- Download file 31.4 kB
-
https://huggingface.co/AbdulElahGwaith/FreeCAD/resolve/main/src/Mod/Part/App/Geom2d/Curve2dPyImp.cpp
- Command line
-
hf download hf://AbdulElahGwaith/FreeCAD/src/Mod/Part/App/Geom2d/Curve2dPyImp.cpp
-
curl -L -o Curve2dPyImp.cpp https://huggingface.co/AbdulElahGwaith/FreeCAD/resolve/main/src/Mod/Part/App/Geom2d/Curve2dPyImp.cpp
31.4 kB
| // SPDX-License-Identifier: LGPL-2.1-or-later | |
| /*************************************************************************** | |
| * Copyright (c) 2016 Werner Mayer <wmayer[at]users.sourceforge.net> * | |
| * * | |
| * This file is part of the FreeCAD CAx development system. * | |
| * * | |
| * This library is free software; you can redistribute it and/or * | |
| * modify it under the terms of the GNU Library General Public * | |
| * License as published by the Free Software Foundation; either * | |
| * version 2 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 Library General Public License for more details. * | |
| * * | |
| * You should have received a copy of the GNU Library General Public * | |
| * License along with this library; see the file COPYING.LIB. If not, * | |
| * write to the Free Software Foundation, Inc., 59 Temple Place, * | |
| * Suite 330, Boston, MA 02111-1307, USA * | |
| * * | |
| ***************************************************************************/ | |
| namespace Part | |
| { | |
| extern const Py::Object makeGeometryCurvePy(const Handle(Geom_Curve) & c); | |
| } | |
| using namespace Part; | |
| // returns a string which represents the object e.g. when printed in python | |
| std::string Curve2dPy::representation() const | |
| { | |
| return "<Curve2d object>"; | |
| } | |
| PyObject* Curve2dPy::PyMake(struct _typeobject*, PyObject*, PyObject*) // Python wrapper | |
| { | |
| // never create such objects with the constructor | |
| PyErr_SetString(PyExc_RuntimeError, "You cannot create an instance of the abstract class 'Curve2d'."); | |
| return nullptr; | |
| } | |
| // constructor method | |
| int Curve2dPy::PyInit(PyObject* /*args*/, PyObject* /*kwd*/) | |
| { | |
| return 0; | |
| } | |
| PyObject* Curve2dPy::reverse(PyObject* args) | |
| { | |
| if (PyArg_ParseTuple(args, "")) { | |
| try { | |
| Handle(Geom2d_Curve) curve = Handle(Geom2d_Curve)::DownCast(getGeom2dCurvePtr()->handle()); | |
| curve->Reverse(); | |
| Py_Return; | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| return nullptr; | |
| } | |
| namespace Part | |
| { | |
| extern Py::Object shape2pyshape(const TopoDS_Shape& shape); | |
| void create3dCurve(const TopoDS_Edge& edge) | |
| { | |
| TopoDS_Edge edge3d; | |
| BRepAdaptor_Curve adapt_curve(edge); | |
| switch (adapt_curve.GetType()) { | |
| case GeomAbs_Line: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Line(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| case GeomAbs_Circle: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Circle(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| case GeomAbs_Ellipse: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Ellipse(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| case GeomAbs_Hyperbola: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Hyperbola(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| case GeomAbs_Parabola: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Parabola(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| case GeomAbs_BezierCurve: { | |
| BRepBuilderAPI_MakeEdge mkBuilder3d( | |
| adapt_curve.Bezier(), | |
| adapt_curve.FirstParameter(), | |
| adapt_curve.LastParameter() | |
| ); | |
| edge3d = mkBuilder3d.Edge(); | |
| } break; | |
| default: | |
| edge3d = edge; | |
| BRepLib::BuildCurves3d(edge3d, Precision::Confusion(), GeomAbs_Shape::GeomAbs_C1, 14, 10000); | |
| break; | |
| } | |
| Standard_Real aFirst, aLast; | |
| Handle(Geom_Curve) curve = BRep_Tool::Curve(edge3d, aFirst, aLast); | |
| BRep_Builder builder; | |
| builder.UpdateEdge(edge, curve, Precision::Confusion()); | |
| builder.Range(edge, aFirst, aLast, true); | |
| return; | |
| } | |
| } // namespace Part | |
| PyObject* Curve2dPy::toShape(PyObject* args) const | |
| { | |
| if (PyArg_ParseTuple(args, "")) { | |
| try { | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepBuilderAPI_MakeEdge2d mkBuilder(curv); | |
| TopoDS_Shape edge = mkBuilder.Shape(); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_Clear(); | |
| double u1, u2; | |
| if (PyArg_ParseTuple(args, "dd", &u1, &u2)) { | |
| try { | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepBuilderAPI_MakeEdge2d mkBuilder(curv, u1, u2); | |
| TopoDS_Shape edge = mkBuilder.Shape(); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_Clear(); | |
| PyObject* p; | |
| if (PyArg_ParseTuple(args, "O!", &(Part::GeometrySurfacePy::Type), &p)) { | |
| try { | |
| Handle(Geom_Surface) surf = Handle(Geom_Surface)::DownCast( | |
| static_cast<GeometrySurfacePy*>(p)->getGeomSurfacePtr()->handle() | |
| ); | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepBuilderAPI_MakeEdge mkBuilder(curv, surf); | |
| TopoDS_Edge edge = mkBuilder.Edge(); | |
| create3dCurve(edge); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_Clear(); | |
| if (PyArg_ParseTuple(args, "O!dd", &(Part::GeometrySurfacePy::Type), &p, &u1, &u2)) { | |
| try { | |
| Handle(Geom_Surface) surf = Handle(Geom_Surface)::DownCast( | |
| static_cast<GeometrySurfacePy*>(p)->getGeomSurfacePtr()->handle() | |
| ); | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepBuilderAPI_MakeEdge mkBuilder(curv, surf, u1, u2); | |
| TopoDS_Edge edge = mkBuilder.Edge(); | |
| create3dCurve(edge); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_Clear(); | |
| if (PyArg_ParseTuple(args, "O!", &(Part::TopoShapeFacePy::Type), &p)) { | |
| try { | |
| const TopoDS_Face& face = TopoDS::Face( | |
| static_cast<TopoShapeFacePy*>(p)->getTopoShapePtr()->getShape() | |
| ); | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepAdaptor_Surface adapt(face); | |
| BRepBuilderAPI_MakeEdge mkBuilder(curv, adapt.Surface().Surface()); | |
| TopoDS_Edge edge = mkBuilder.Edge(); | |
| create3dCurve(edge); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_Clear(); | |
| if (PyArg_ParseTuple(args, "O!dd", &(Part::TopoShapeFacePy::Type), &p, &u1, &u2)) { | |
| try { | |
| const TopoDS_Face& face = TopoDS::Face( | |
| static_cast<TopoShapeFacePy*>(p)->getTopoShapePtr()->getShape() | |
| ); | |
| Handle(Geom2d_Curve) curv = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| BRepAdaptor_Surface adapt(face); | |
| BRepBuilderAPI_MakeEdge mkBuilder(curv, adapt.Surface().Surface(), u1, u2); | |
| TopoDS_Edge edge = mkBuilder.Edge(); | |
| create3dCurve(edge); | |
| return Py::new_reference_to(shape2pyshape(edge)); | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| PyErr_SetString(PyExc_TypeError, "empty parameter list, parameter range or surface expected"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::discretize(PyObject* args, PyObject* kwds) const | |
| { | |
| try { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| if (c.IsNull()) { | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| Geom2dAdaptor_Curve adapt(c); | |
| double first = adapt.FirstParameter(); | |
| double last = adapt.LastParameter(); | |
| // use Number kwds | |
| static const std::array<const char*, 4> kwds_numPoints {"Number", "First", "Last", nullptr}; | |
| PyErr_Clear(); | |
| int numPoints = -1; | |
| if (Base::Wrapped_ParseTupleAndKeywords( | |
| args, | |
| kwds, | |
| "i|dd", | |
| kwds_numPoints, | |
| &numPoints, | |
| &first, | |
| &last | |
| )) { | |
| GCPnts_UniformAbscissa discretizer; | |
| discretizer.Initialize(adapt, numPoints, first, last); | |
| if (discretizer.IsDone() && discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt2d p = adapt.Value(discretizer.Parameter(i)); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| // use Distance kwds | |
| static const std::array<const char*, 4> kwds_Distance {"Distance", "First", "Last", nullptr}; | |
| PyErr_Clear(); | |
| double distance = -1; | |
| if (Base::Wrapped_ParseTupleAndKeywords(args, kwds, "d|dd", kwds_Distance, &distance, &first, &last)) { | |
| GCPnts_UniformAbscissa discretizer; | |
| discretizer.Initialize(adapt, distance, first, last); | |
| if (discretizer.IsDone() && discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt2d p = adapt.Value(discretizer.Parameter(i)); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| // use Deflection kwds | |
| static const std::array<const char*, 4> kwds_Deflection {"Deflection", "First", "Last", nullptr}; | |
| PyErr_Clear(); | |
| double deflection; | |
| if (Base::Wrapped_ParseTupleAndKeywords( | |
| args, | |
| kwds, | |
| "d|dd", | |
| kwds_Deflection, | |
| &deflection, | |
| &first, | |
| &last | |
| )) { | |
| GCPnts_UniformDeflection discretizer(adapt, deflection, first, last); | |
| if (discretizer.IsDone() && discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt p = discretizer.Value(i); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| // use TangentialDeflection kwds | |
| static const std::array<const char*, 6> | |
| kwds_TangentialDeflection {"Angular", "Curvature", "First", "Last", "Minimum", nullptr}; | |
| PyErr_Clear(); | |
| double angular; | |
| double curvature; | |
| int minimumPoints = 2; | |
| if (Base::Wrapped_ParseTupleAndKeywords( | |
| args, | |
| kwds, | |
| "dd|ddi", | |
| kwds_TangentialDeflection, | |
| &angular, | |
| &curvature, | |
| &first, | |
| &last, | |
| &minimumPoints | |
| )) { | |
| GCPnts_TangentialDeflection discretizer(adapt, first, last, angular, curvature, minimumPoints); | |
| if (discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt p = discretizer.Value(i); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| // use QuasiNumber kwds | |
| static const std::array<const char*, 4> kwds_QuasiNumPoints { | |
| "QuasiNumber", | |
| "First", | |
| "Last", | |
| nullptr | |
| }; | |
| PyErr_Clear(); | |
| int quasiNumPoints; | |
| if (Base::Wrapped_ParseTupleAndKeywords( | |
| args, | |
| kwds, | |
| "i|dd", | |
| kwds_QuasiNumPoints, | |
| &quasiNumPoints, | |
| &first, | |
| &last | |
| )) { | |
| GCPnts_QuasiUniformAbscissa discretizer(adapt, quasiNumPoints, first, last); | |
| if (discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt2d p = adapt.Value(discretizer.Parameter(i)); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| // use QuasiDeflection kwds | |
| static const std::array<const char*, 4> kwds_QuasiDeflection { | |
| "QuasiDeflection", | |
| "First", | |
| "Last", | |
| nullptr | |
| }; | |
| PyErr_Clear(); | |
| double quasiDeflection; | |
| if (Base::Wrapped_ParseTupleAndKeywords( | |
| args, | |
| kwds, | |
| "d|dd", | |
| kwds_QuasiDeflection, | |
| &quasiDeflection, | |
| &first, | |
| &last | |
| )) { | |
| GCPnts_QuasiUniformDeflection discretizer(adapt, quasiDeflection, first, last); | |
| if (discretizer.NbPoints() > 0) { | |
| Py::List points; | |
| int nbPoints = discretizer.NbPoints(); | |
| for (int i = 1; i <= nbPoints; i++) { | |
| gp_Pnt p = discretizer.Value(i); | |
| points.append(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| else { | |
| PyErr_SetString(PartExceptionOCCError, "Discretization of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| } | |
| catch (const Base::Exception& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.what()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Wrong arguments"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::length(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u = c->FirstParameter(); | |
| double v = c->LastParameter(); | |
| double t = Precision::Confusion(); | |
| if (!PyArg_ParseTuple(args, "|ddd", &u, &v, &t)) { | |
| return nullptr; | |
| } | |
| Geom2dAdaptor_Curve adapt(c); | |
| double len = GCPnts_AbscissaPoint::Length(adapt, u, v, t); | |
| return PyFloat_FromDouble(len); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::parameterAtDistance(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double abscissa; | |
| double u = 0; | |
| if (!PyArg_ParseTuple(args, "d|d", &abscissa, &u)) { | |
| return nullptr; | |
| } | |
| Geom2dAdaptor_Curve adapt(c); | |
| GCPnts_AbscissaPoint abscissaPoint(adapt, abscissa, u); | |
| double parm = abscissaPoint.Parameter(); | |
| return PyFloat_FromDouble(parm); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::value(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u; | |
| if (!PyArg_ParseTuple(args, "d", &u)) { | |
| return nullptr; | |
| } | |
| gp_Pnt2d p = c->Value(u); | |
| return Py::new_reference_to(Base::Vector2dPy::create(p.X(), p.Y())); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::tangent(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u; | |
| if (!PyArg_ParseTuple(args, "d", &u)) { | |
| return nullptr; | |
| } | |
| gp_Dir2d dir; | |
| Geom2dLProp_CLProps2d prop(c, u, 2, Precision::Confusion()); | |
| if (prop.IsTangentDefined()) { | |
| prop.Tangent(dir); | |
| } | |
| return Py::new_reference_to(Base::Vector2dPy::create(dir.X(), dir.Y())); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::normal(PyObject* args) const | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u; | |
| if (!PyArg_ParseTuple(args, "d", &u)) { | |
| return nullptr; | |
| } | |
| gp_Dir2d dir; | |
| Geom2dLProp_CLProps2d prop(c, u, 2, Precision::Confusion()); | |
| prop.Normal(dir); | |
| return Py::new_reference_to(Base::Vector2dPy::create(dir.X(), dir.Y())); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::curvature(PyObject* args) const | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u; | |
| if (!PyArg_ParseTuple(args, "d", &u)) { | |
| return nullptr; | |
| } | |
| Geom2dLProp_CLProps2d prop(c, u, 2, Precision::Confusion()); | |
| double C = prop.Curvature(); | |
| return Py::new_reference_to(Py::Float(C)); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::centerOfCurvature(PyObject* args) const | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u; | |
| if (!PyArg_ParseTuple(args, "d", &u)) { | |
| return nullptr; | |
| } | |
| Geom2dLProp_CLProps2d prop(c, u, 2, Precision::Confusion()); | |
| gp_Pnt2d pnt; | |
| prop.CentreOfCurvature(pnt); | |
| return Py::new_reference_to(Base::Vector2dPy::create(pnt.X(), pnt.Y())); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::parameter(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| PyObject* p; | |
| if (!PyArg_ParseTuple(args, "O!", Base::Vector2dPy::type_object(), &p)) { | |
| return nullptr; | |
| } | |
| Base::Vector2d v = Py::toVector2d(p); | |
| gp_Pnt2d pnt(v.x, v.y); | |
| Geom2dAPI_ProjectPointOnCurve ppc(pnt, c); | |
| double val = ppc.LowerDistanceParameter(); | |
| return Py::new_reference_to(Py::Float(val)); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::toBSpline(PyObject* args) | |
| { | |
| Handle(Geom2d_Geometry) g = getGeometry2dPtr()->handle(); | |
| Handle(Geom2d_Curve) c = Handle(Geom2d_Curve)::DownCast(g); | |
| try { | |
| if (!c.IsNull()) { | |
| double u, v; | |
| u = c->FirstParameter(); | |
| v = c->LastParameter(); | |
| if (!PyArg_ParseTuple(args, "|dd", &u, &v)) { | |
| return nullptr; | |
| } | |
| ShapeConstruct_Curve scc; | |
| Handle(Geom2d_BSplineCurve) spline = scc.ConvertToBSpline(c, u, v, Precision::Confusion()); | |
| if (spline.IsNull()) { | |
| Standard_NullValue::Raise("Conversion to B-spline failed"); | |
| } | |
| return new BSplineCurve2dPy(new Geom2dBSplineCurve(spline)); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PartExceptionOCCError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |
| PyObject* Curve2dPy::approximateBSpline(PyObject* args) | |
| { | |
| double tolerance; | |
| int maxSegment, maxDegree; | |
| const char* order = "C2"; | |
| if (!PyArg_ParseTuple(args, "dii|s", &tolerance, &maxSegment, &maxDegree, &order)) { | |
| return nullptr; | |
| } | |
| GeomAbs_Shape absShape; | |
| std::string str = order; | |
| if (str == "C0") { | |
| absShape = GeomAbs_C0; | |
| } | |
| else if (str == "G1") { | |
| absShape = GeomAbs_G1; | |
| } | |
| else if (str == "C1") { | |
| absShape = GeomAbs_C1; | |
| } | |
| else if (str == "G2") { | |
| absShape = GeomAbs_G2; | |
| } | |
| else if (str == "C2") { | |
| absShape = GeomAbs_C2; | |
| } | |
| else if (str == "C3") { | |
| absShape = GeomAbs_C3; | |
| } | |
| else if (str == "CN") { | |
| absShape = GeomAbs_CN; | |
| } | |
| else { | |
| absShape = GeomAbs_C2; | |
| } | |
| try { | |
| Handle(Geom2d_Curve) self = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| Geom2dConvert_ApproxCurve approx(self, tolerance, absShape, maxSegment, maxDegree); | |
| if (approx.IsDone()) { | |
| return new BSplineCurve2dPy(new Geom2dBSplineCurve(approx.Curve())); | |
| } | |
| else if (approx.HasResult()) { | |
| std::stringstream str; | |
| str << "Maximum error (" << approx.MaxError() << ") is outside tolerance"; | |
| PyErr_SetString(PyExc_RuntimeError, str.str().c_str()); | |
| return nullptr; | |
| } | |
| else { | |
| PyErr_SetString(PyExc_RuntimeError, "Approximation of curve failed"); | |
| return nullptr; | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PartExceptionOCCError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| } | |
| Py::String Curve2dPy::getContinuity() const | |
| { | |
| GeomAbs_Shape c = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle())->Continuity(); | |
| std::string str; | |
| switch (c) { | |
| case GeomAbs_C0: | |
| str = "C0"; | |
| break; | |
| case GeomAbs_G1: | |
| str = "G1"; | |
| break; | |
| case GeomAbs_C1: | |
| str = "C1"; | |
| break; | |
| case GeomAbs_G2: | |
| str = "G2"; | |
| break; | |
| case GeomAbs_C2: | |
| str = "C2"; | |
| break; | |
| case GeomAbs_C3: | |
| str = "C3"; | |
| break; | |
| case GeomAbs_CN: | |
| str = "CN"; | |
| break; | |
| default: | |
| str = "Unknown"; | |
| break; | |
| } | |
| return Py::String(str); | |
| } | |
| Py::Boolean Curve2dPy::getClosed() const | |
| { | |
| return Py::Boolean( | |
| Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle())->IsClosed() ? true : false | |
| ); | |
| } | |
| Py::Boolean Curve2dPy::getPeriodic() const | |
| { | |
| return Py::Boolean( | |
| Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle())->IsPeriodic() ? true : false | |
| ); | |
| } | |
| Py::Float Curve2dPy::getFirstParameter() const | |
| { | |
| return Py::Float(Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle())->FirstParameter()); | |
| } | |
| Py::Float Curve2dPy::getLastParameter() const | |
| { | |
| return Py::Float(Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle())->LastParameter()); | |
| } | |
| PyObject* Curve2dPy::getCustomAttributes(const char* /*attr*/) const | |
| { | |
| return nullptr; | |
| } | |
| int Curve2dPy::setCustomAttributes(const char* /*attr*/, PyObject* /*obj*/) | |
| { | |
| return 0; | |
| } | |
| PyObject* Curve2dPy::intersectCC(PyObject* args) const | |
| { | |
| Handle(Geom2d_Curve) curve1 = Handle(Geom2d_Curve)::DownCast(getGeometry2dPtr()->handle()); | |
| try { | |
| if (!curve1.IsNull()) { | |
| PyObject* p; | |
| double prec = Precision::Confusion(); | |
| if (!PyArg_ParseTuple(args, "O!|d", &(Part::Curve2dPy::Type), &p, &prec)) { | |
| return nullptr; | |
| } | |
| Handle(Geom2d_Curve) curve2 = Handle(Geom2d_Curve)::DownCast( | |
| static_cast<Geometry2dPy*>(p)->getGeometry2dPtr()->handle() | |
| ); | |
| Py::List points; | |
| Geom2dAPI_InterCurveCurve intersector(curve1, curve2, prec); | |
| if ((intersector.NbPoints() == 0) && (intersector.NbSegments() == 0)) { | |
| // No intersection | |
| return Py::new_reference_to(Py::List()); | |
| } | |
| if (intersector.NbPoints() > 0) { | |
| // Cross intersections | |
| for (int i = 1; i <= intersector.NbPoints(); i++) { | |
| gp_Pnt2d p1 = intersector.Point(i); | |
| points.append(Base::Vector2dPy::create(p1.X(), p1.Y())); | |
| } | |
| } | |
| if (intersector.NbSegments() > 0) { | |
| // Tangential intersections | |
| Geom2dAPI_ExtremaCurveCurve intersector2( | |
| curve1, | |
| curve2, | |
| curve1->FirstParameter(), | |
| curve1->LastParameter(), | |
| curve2->FirstParameter(), | |
| curve2->LastParameter() | |
| ); | |
| for (int i = 1; i <= intersector2.NbExtrema(); i++) { | |
| if (intersector2.Distance(i) > prec) { | |
| continue; | |
| } | |
| gp_Pnt2d p1, p2; | |
| intersector2.Points(i, p1, p2); | |
| points.append(Base::Vector2dPy::create(p1.X(), p1.Y())); | |
| } | |
| } | |
| return Py::new_reference_to(points); | |
| } | |
| } | |
| catch (Standard_Failure& e) { | |
| PyErr_SetString(PyExc_RuntimeError, e.GetMessageString()); | |
| return nullptr; | |
| } | |
| PyErr_SetString(PyExc_TypeError, "Geometry is not a curve"); | |
| return nullptr; | |
| } | |