diff --git a/src/Mod/Path/PathSimulator/App/AppPathSimulator.cpp b/src/Mod/Path/PathSimulator/App/AppPathSimulator.cpp
index 60cc760025..9acf340097 100644
--- a/src/Mod/Path/PathSimulator/App/AppPathSimulator.cpp
+++ b/src/Mod/Path/PathSimulator/App/AppPathSimulator.cpp
@@ -67,6 +67,7 @@ PyMOD_INIT_FUNC(PathSimulator)
try {
Base::Interpreter().runString("import Part");
Base::Interpreter().runString("import Path");
+ Base::Interpreter().runString("import Mesh");
}
catch (const Base::Exception& e) {
PyErr_SetString(PyExc_ImportError, e.what());
diff --git a/src/Mod/Path/PathSimulator/App/CMakeLists.txt b/src/Mod/Path/PathSimulator/App/CMakeLists.txt
index 45d37fa534..d9fd8eb86b 100644
--- a/src/Mod/Path/PathSimulator/App/CMakeLists.txt
+++ b/src/Mod/Path/PathSimulator/App/CMakeLists.txt
@@ -14,6 +14,7 @@ include_directories(
set(PathSimulator_LIBS
Path
Part
+ Mesh
FreeCADApp
)
diff --git a/src/Mod/Path/PathSimulator/App/PathSimPy.xml b/src/Mod/Path/PathSimulator/App/PathSimPy.xml
index 4de8b7f8c6..d6228ed39b 100644
--- a/src/Mod/Path/PathSimulator/App/PathSimPy.xml
+++ b/src/Mod/Path/PathSimulator/App/PathSimPy.xml
@@ -25,8 +25,18 @@ Start a simulation process on a box shape stock with given resolution\n
- SetCurrentTool(tool):\n
-Set the current Path Tool for the subsequent simulator operations.\n
+
+ SetCurrentTool(tool):\n
+ Set the current Path Tool for the subsequent simulator operations.\n
+
+
+
+
+
+
+ GetResultMesh():\n
+ Return the current mesh result of the simulation.\n
+
diff --git a/src/Mod/Path/PathSimulator/App/PathSimPyImp.cpp b/src/Mod/Path/PathSimulator/App/PathSimPyImp.cpp
index c5767ba70a..2b530cd2aa 100644
--- a/src/Mod/Path/PathSimulator/App/PathSimPyImp.cpp
+++ b/src/Mod/Path/PathSimulator/App/PathSimPyImp.cpp
@@ -23,6 +23,8 @@
#include "PreCompiled.h"
#include "Mod/Path/PathSimulator/App/PathSim.h"
+#include
+#include
// inclusion of the generated files (generated out of PathSimPy.xml)
#include "PathSimPy.h"
@@ -49,19 +51,47 @@ int PathSimPy::PyInit(PyObject* /*args*/, PyObject* /*kwd*/)
}
-PyObject* PathSimPy::BeginSimulation(PyObject * /*args*/, PyObject * /*kwds*/)
+PyObject* PathSimPy::BeginSimulation(PyObject * args, PyObject * kwds)
{
- PyErr_SetString(PyExc_NotImplementedError, "Not yet implemented");
- return 0;
+ static char *kwlist[] = { "stock", "resolution", NULL };
+ PyObject *pObjStock;
+ float resolution;
+ if (!PyArg_ParseTupleAndKeywords(args, kwds, "O!f", kwlist, &(Part::TopoShapePy::Type), &pObjStock, &resolution))
+ return 0;
+ PathSim *sim = getPathSimPtr();
+ Part::TopoShape *stock = static_cast(pObjStock)->getTopoShapePtr();
+ sim->BeginSimulation(stock, resolution);
+ Py_IncRef(Py_None);
+ return Py_None;
}
PyObject* PathSimPy::SetCurrentTool(PyObject * /*args*/)
{
- PyErr_SetString(PyExc_NotImplementedError, "Not yet implemented");
- return 0;
+ PyErr_SetString(PyExc_NotImplementedError, "Not yet implemented");
+ return 0;
}
+PyObject* PathSimPy::GetResultMesh(PyObject * args)
+{
+ if (!PyArg_ParseTuple(args, ""))
+ return 0;
+ cStock *stock = getPathSimPtr()->m_stock;
+ Mesh::MeshObject *mesh = new Mesh::MeshObject();
+ Mesh::MeshPy *meshpy = new Mesh::MeshPy(mesh);
+ stock->Tesselate(*mesh);
+ return meshpy;
+}
+
+/* test script
+import PathSimulator
+sim = PathSimulator.PathSim()
+stock = Part.makeBox(20,20,5)
+sim.BeginSimulation(stock,0.1)
+msh = sim.GetResultMesh()
+Mesh.show(msh)
+
+*/
diff --git a/src/Mod/Path/PathSimulator/App/PreCompiled.h b/src/Mod/Path/PathSimulator/App/PreCompiled.h
index c1a83a5430..4e604df386 100644
--- a/src/Mod/Path/PathSimulator/App/PreCompiled.h
+++ b/src/Mod/Path/PathSimulator/App/PreCompiled.h
@@ -31,6 +31,7 @@
# define PathSimulatorExport __declspec(dllexport)
# define PathExport __declspec(dllexport)
# define PartExport __declspec(dllimport)
+# define MeshExport __declspec(dllimport)
#else // for Linux
# define PathSimulatorAppExport
#endif
diff --git a/src/Mod/Path/PathSimulator/App/VolSim.cpp b/src/Mod/Path/PathSimulator/App/VolSim.cpp
index 07af032652..1317928366 100644
--- a/src/Mod/Path/PathSimulator/App/VolSim.cpp
+++ b/src/Mod/Path/PathSimulator/App/VolSim.cpp
@@ -20,6 +20,7 @@
* *
***************************************************************************/
+#include "PreCompiled.h"
#include
#include "VolSim.h"
@@ -151,7 +152,7 @@ float cStock::FindRectTop(int & xp, int & yp, int & x_size, int & y_size, bool s
return z;
}
-int cStock::TesselTop(Model3D *model, int xp, int yp)
+int cStock::TesselTop(Mesh::MeshObject & mesh, int xp, int yp)
{
int x_size, y_size;
float z = FindRectTop(xp, yp, x_size, y_size, true);
@@ -182,7 +183,7 @@ int cStock::TesselTop(Model3D *model, int xp, int yp)
Point3D pbr(xp + x_size, yp, z);
Point3D ptl(xp, yp + y_size, z);
Point3D ptr(xp + x_size, yp + y_size, z);
- model->AddQuad(pbl, pbr, ptr, ptl);
+ AddQuad(mesh, pbl, pbr, ptr, ptl);
}
if (farRect)
@@ -294,7 +295,7 @@ void cStock::FindRectBot(int & xp, int & yp, int & x_size, int & y_size, bool sc
}
-int cStock::TesselBot(Model3D *model, int xp, int yp)
+int cStock::TesselBot(Mesh::MeshObject & mesh, int xp, int yp)
{
int x_size, y_size;
FindRectBot(xp, yp, x_size, y_size, true);
@@ -323,7 +324,7 @@ int cStock::TesselBot(Model3D *model, int xp, int yp)
Point3D pbr(xp + x_size, yp, m_pz);
Point3D ptl(xp, yp + y_size, m_pz);
Point3D ptr(xp + x_size, yp + y_size, m_pz);
- model->AddQuad(pbl, ptl, ptr, pbr);
+ AddQuad(mesh, pbl, ptl, ptr, pbr);
if (farRect)
return -1;
@@ -332,7 +333,7 @@ int cStock::TesselBot(Model3D *model, int xp, int yp)
}
-int cStock::TesselSidesX(Model3D *model, int yp)
+int cStock::TesselSidesX(Mesh::MeshObject & mesh, int yp)
{
float lastz1 = m_pz;
if (yp < m_y)
@@ -356,14 +357,11 @@ int cStock::TesselSidesX(Model3D *model, int yp)
{
if (abs(newz1 - lastz1) < m_res && abs(newz2 - lastz2) < m_res)
continue;
- Point3D pbl(lastpoint, yp, lastz1);
- Point3D pbr(x, yp, lastz1);
- Point3D ptl(lastpoint, yp, lastz2);
- Point3D ptr(x, yp, lastz2);
- if (lastz2 > lastz1)
- model->AddQuad(pbl, pbr, ptr, ptl);
- else
- model->AddQuad(pbl, ptl, ptr, pbr);
+ Point3D pbl(lastpoint, yp, lastz1);
+ Point3D pbr(x, yp, lastz1);
+ Point3D ptl(lastpoint, yp, lastz2);
+ Point3D ptr(x, yp, lastz2);
+ AddQuad(mesh, pbl, ptl, ptr, pbr);
}
lastz1 = newz1;
lastz2 = newz2;
@@ -372,7 +370,7 @@ int cStock::TesselSidesX(Model3D *model, int yp)
return 0;
}
-int cStock::TesselSidesY(Model3D *model, int xp)
+int cStock::TesselSidesY(Mesh::MeshObject & mesh, int xp)
{
float lastz1 = m_pz;
if (xp < m_x)
@@ -400,10 +398,7 @@ int cStock::TesselSidesY(Model3D *model, int xp)
Point3D pbl(xp, y, lastz1);
Point3D ptr(xp, lastpoint, lastz2);
Point3D ptl(xp, y, lastz2);
- if (lastz2 > lastz1)
- model->AddQuad(pbl, pbr, ptr, ptl);
- else
- model->AddQuad(pbl, ptl, ptr, pbr);
+ AddQuad(mesh, pbl, ptl, ptr, pbr);
}
lastz1 = newz1;
lastz2 = newz2;
@@ -412,30 +407,38 @@ int cStock::TesselSidesY(Model3D *model, int xp)
return 0;
}
-void cStock::AdjustCoordinates(Model3D *model)
+void cStock::SetFacetPoints(MeshCore::MeshGeomFacet & facet, Point3D & p1, Point3D & p2, Point3D & p3)
{
- for (int i = 0; i < model->triangles.size(); i++)
- {
- for (int j = 0; j < 3; j++)
- {
- Point3D & t = model->triangles[i].points[j];
- t.x = (float)t.x * m_res + m_px;
- t.y = (float)t.y * m_res + m_py;
- }
- }
+ facet._aclPoints[0][0] = p1.x * m_res + m_px;
+ facet._aclPoints[0][1] = p1.y * m_res + m_py;
+ facet._aclPoints[0][2] = p1.z;
+ facet._aclPoints[1][0] = p2.x * m_res + m_px;
+ facet._aclPoints[1][1] = p2.y * m_res + m_py;
+ facet._aclPoints[1][2] = p2.z;
+ facet._aclPoints[2][0] = p3.x * m_res + m_px;
+ facet._aclPoints[2][1] = p3.y * m_res + m_py;
+ facet._aclPoints[2][2] = p3.z;
+ facet.CalcNormal();
}
-
-Model3D *cStock::Tesselate()
+void cStock::AddQuad(Mesh::MeshObject & mesh, Point3D & p1, Point3D & p2, Point3D & p3, Point3D & p4)
+{
+ MeshCore::MeshGeomFacet facet;
+ SetFacetPoints(facet, p1, p2, p3);
+ mesh.addFacet(facet);
+ SetFacetPoints(facet, p1, p3, p4);
+ mesh.addFacet(facet);
+}
+
+void cStock::Tesselate(Mesh::MeshObject & mesh)
{
- Model3D *model = new Model3D();
for (int y = 0; y < m_y; y++)
{
for (int x = 0; x < m_x; x++)
{
int attr = m_attr[x][y];
if ((attr & SIM_TESSEL_TOP) == 0)
- x += TesselTop(model, x, y);
+ x += TesselTop(mesh, x, y);
}
}
for (int y = 0; y < m_y; y++)
@@ -445,15 +448,13 @@ Model3D *cStock::Tesselate()
if ((m_stock[x][y] - m_pz) < m_res)
m_attr[x][y] |= SIM_TESSEL_BOT;
if ((m_attr[x][y] & SIM_TESSEL_BOT) == 0)
- x += TesselBot(model, x, y);
+ x += TesselBot(mesh, x, y);
}
}
for (int y = 0; y <= m_y; y++)
- TesselSidesX(model, y);
+ TesselSidesX(mesh, y);
for (int x = 0; x <= m_x; x++)
- TesselSidesY(model, x);
- AdjustCoordinates(model);
- return model;
+ TesselSidesY(mesh, x);
}
diff --git a/src/Mod/Path/PathSimulator/App/VolSim.h b/src/Mod/Path/PathSimulator/App/VolSim.h
index 1af34a137a..accc247164 100644
--- a/src/Mod/Path/PathSimulator/App/VolSim.h
+++ b/src/Mod/Path/PathSimulator/App/VolSim.h
@@ -27,6 +27,7 @@
#define PATHSIMULATOR_VolSim_H
#include
+#include
#define SIM_EPSILON 0.00001
#define SIM_TESSEL_TOP 1
@@ -82,15 +83,32 @@ struct cLineSegment
struct Model3D
{
- Model3D() {}
- std::vector triangles;
+ Model3D(float px, float py, float res) : pos_x(px), pos_y(py), resolution(res) {}
+ void SetFacetPoints(MeshCore::MeshGeomFacet & facet, Point3D & p1, Point3D & p2, Point3D & p3)
+ {
+ facet._aclPoints[0][0] = p1.x * resolution + pos_x;
+ facet._aclPoints[0][1] = p1.y * resolution + pos_y;
+ facet._aclPoints[0][2] = p1.z;
+ facet._aclPoints[1][0] = p2.x * resolution + pos_x;
+ facet._aclPoints[1][1] = p2.y * resolution + pos_y;
+ facet._aclPoints[1][2] = p2.z;
+ facet._aclPoints[2][0] = p3.x * resolution + pos_x;
+ facet._aclPoints[2][1] = p3.y * resolution + pos_y;
+ facet._aclPoints[2][2] = p3.z;
+ facet.CalcNormal();
+ }
+
inline void AddQuad(Point3D & p1, Point3D & p2, Point3D & p3, Point3D & p4)
{
- Triangle3D t1(p1, p2, p3);
- Triangle3D t2(p1, p3, p4);
- triangles.push_back(t1);
- triangles.push_back(t2);
+ MeshCore::MeshGeomFacet facet;
+ SetFacetPoints(facet, p1, p2, p3);
+ mesh.addFacet(facet);
+ SetFacetPoints(facet, p1, p3, p4);
+ mesh.addFacet(facet);
}
+
+ float pos_x, pos_y, resolution;
+ Mesh::MeshObject mesh;
};
class cSimTool
@@ -145,22 +163,23 @@ class cStock
public:
cStock(float px, float py, float pz, float lx, float ly, float lz, float res);
~cStock();
- Model3D *Tesselate();
- void CreatePocket(float x, float y, float rad, float height);
- void ApplyLinearTool(Point3D & p1, Point3D & p2, cSimTool &tool);
- void ApplyCircularTool(Point3D & p1, Point3D & p2, Point3D & cent, cSimTool &tool, bool isCCW);
- inline Point3D & ToInner(Point3D & p) {
+ void Tesselate(Mesh::MeshObject & mesh);
+ void CreatePocket(float x, float y, float rad, float height);
+ void ApplyLinearTool(Point3D & p1, Point3D & p2, cSimTool &tool);
+ void ApplyCircularTool(Point3D & p1, Point3D & p2, Point3D & cent, cSimTool &tool, bool isCCW);
+ inline Point3D & ToInner(Point3D & p) {
return Point3D((p.x - m_px) / m_res, (p.y - m_py) / m_res, p.z);
}
private:
float FindRectTop(int & xp, int & yp, int & x_size, int & y_size, bool scanHoriz);
void FindRectBot(int & xp, int & yp, int & x_size, int & y_size, bool scanHoriz);
- int TesselTop(Model3D *model, int x, int y);
- int TesselBot(Model3D *model, int x, int y);
- int TesselSidesX(Model3D *model, int yp);
- int TesselSidesY(Model3D *model, int xp);
- void AdjustCoordinates(Model3D *model);
+ void SetFacetPoints(MeshCore::MeshGeomFacet & facet, Point3D & p1, Point3D & p2, Point3D & p3);
+ void AddQuad(Mesh::MeshObject & mesh, Point3D & p1, Point3D & p2, Point3D & p3, Point3D & p4);
+ int TesselTop(Mesh::MeshObject & mesh, int x, int y);
+ int TesselBot(Mesh::MeshObject & mesh, int x, int y);
+ int TesselSidesX(Mesh::MeshObject & mesh, int yp);
+ int TesselSidesY(Mesh::MeshObject & mesh, int xp);
Array2D m_stock;
Array2D m_attr;
float m_px, m_py, m_pz; // stock zero position