diff options
author | clifford <clifford@b57f626f-c46c-0410-a088-ec61d464b74c> | 2010-01-05 19:09:01 (GMT) |
---|---|---|
committer | clifford <clifford@b57f626f-c46c-0410-a088-ec61d464b74c> | 2010-01-05 19:09:01 (GMT) |
commit | a02e00083f385a1770103569e07b2b5eb8d7ee4f (patch) | |
tree | eb21fc21ba838912e99e732155ac7de3945624f2 | |
parent | 8457c079e3d9d8aa77b184c1ba1dec09f7116fc6 (diff) |
Clifford Wolf:
New hack for 2d transformations:
create DxfData, transform, tess to polyset, recreate nef
git-svn-id: http://svn.clifford.at/openscad/trunk@203 b57f626f-c46c-0410-a088-ec61d464b74c
-rw-r--r-- | dxfdata.cc | 8 | ||||
-rw-r--r-- | nef2dxf.cc | 62 | ||||
-rw-r--r-- | openscad.h | 16 | ||||
-rw-r--r-- | openscad.pro | 2 | ||||
-rw-r--r-- | polyset.cc | 26 | ||||
-rw-r--r-- | transform.cc | 46 |
6 files changed, 108 insertions, 52 deletions
@@ -23,6 +23,14 @@ #include <QFile> +struct Line { + typedef DxfData::Point Point; + Point *p[2]; + bool disabled; + Line(Point *p1, Point *p2) { p[0] = p1; p[1] = p2; disabled = false; } + Line() { p[0] = NULL; p[1] = NULL; disabled = false; } +}; + DxfData::DxfData(double fn, double fs, double fa, QString filename, QString layername, double xorigin, double yorigin, double scale) { handle_dep(filename); diff --git a/nef2dxf.cc b/nef2dxf.cc new file mode 100644 index 0000000..b7a6c49 --- /dev/null +++ b/nef2dxf.cc @@ -0,0 +1,62 @@ +/* + * OpenSCAD (www.openscad.at) + * Copyright (C) 2009 Clifford Wolf <clifford@clifford.at> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program 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 General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#define INCLUDE_ABSTRACT_NODE_DETAILS + +#include "openscad.h" + +DxfData::DxfData(const struct CGAL_Nef_polyhedron &N) +{ + Grid2d<int> grid; + + typedef CGAL_Nef_polyhedron2::Explorer Explorer; + typedef Explorer::Face_const_iterator fci_t; + typedef Explorer::Halfedge_around_face_const_circulator heafcc_t; + Explorer E = N.p2.explorer(); + + for (fci_t fit = E.faces_begin(), fend = E.faces_end(); fit != fend; ++fit) + { + heafcc_t fcirc(E.halfedge(fit)), fend(fcirc); + int first_point = -1; + CGAL_For_all(fcirc, fend) { + if (E.is_standard(E.target(fcirc))) { + Explorer::Point ep = E.point(E.target(fcirc)); + double x = to_double(ep.x()), y = to_double(ep.y()); + int this_point = -1; + if (grid.has(x, y)) { + this_point = grid.align(x, y); + } else { + this_point = grid.align(x, y) = points.size(); + points.append(Point(x, y)); + } + if (first_point < 0) { + paths.append(Path()); + first_point = this_point; + } + paths.last().points.append(&points[this_point]); + } + } + if (first_point >= 0) { + paths.last().is_closed = 1; + paths.last().points.append(&points[first_point]); + } + } +} + @@ -69,6 +69,7 @@ class CSGChain; class AbstractNode; class AbstractIntersectionNode; class AbstractPolyNode; +struct CGAL_Nef_polyhedron; template <typename T> class Grid2d @@ -419,12 +420,6 @@ public: Point() : x(0), y(0) { } Point(double x, double y) : x(x), y(y) { } }; - struct Line { - Point *p[2]; - bool disabled; - Line(Point *p1, Point *p2) { p[0] = p1; p[1] = p2; disabled = false; } - Line() { p[0] = NULL; p[1] = NULL; disabled = false; } - }; struct Path { QList<Point*> points; bool is_closed, is_inner; @@ -448,6 +443,7 @@ public: QList<Dim> dims; DxfData(double fn, double fs, double fa, QString filename, QString layername = QString(), double xorigin = 0.0, double yorigin = 0.0, double scale = 1.0); + DxfData(const struct CGAL_Nef_polyhedron &N); Point *p(double x, double y); }; @@ -693,13 +689,7 @@ void progress_report_fin(); void dxf_tesselate(PolySet *ps, DxfData *dxf, double rot, bool up, double h); -#else - -// Needed for Mainwin::root_N -// this is a bit hackish - but a pointer is a pointer.. -struct CGAL_Nef_polyhedron; - -#endif /* HIDE_ABSTRACT_NODE_DETAILS */ +#endif /* INCLUDE_ABSTRACT_NODE_DETAILS */ class Highlighter : public QSyntaxHighlighter { diff --git a/openscad.pro b/openscad.pro index 7c7d5ee..55ed83f 100644 --- a/openscad.pro +++ b/openscad.pro @@ -78,7 +78,7 @@ SOURCES += openscad.cc mainwin.cc glview.cc export.cc \ primitives.cc surface.cc control.cc render.cc \ import.cc dxfdata.cc dxftess.cc dxfdim.cc \ dxflinextrude.cc dxfrotextrude.cc highlighter.cc \ - printutils.cc + printutils.cc nef2dxf.cc target.path = /usr/local/bin/ INSTALLS += target @@ -369,15 +369,25 @@ CGAL_Nef_polyhedron PolySet::render_cgal_nef_polyhedron() const { if (this->is2d) { - int len = this->polygons[0].size(); - if (len > 0) { - CGAL_Nef_polyhedron2::Point points[len]; - for (int i = 0; i < len; i++) - points[i] = CGAL_Nef_polyhedron2::Point(this->polygons[0][i].x, - this->polygons[0][i].y); - CGAL_Nef_polyhedron2 N(points, points+len); - return CGAL_Nef_polyhedron(N); + typedef std::list<CGAL_Nef_polyhedron2::Point> point_list_t; + typedef point_list_t::iterator point_list_it; + std::list< point_list_t > pdata_point_lists; + std::list < std::pair < point_list_it, point_list_it > > pdata; + + for (int i = 0; i < this->polygons.size(); i++) { + pdata_point_lists.push_back(point_list_t()); + for (int j = 0; j < this->polygons[i].size(); j++) { + double x = this->polygons[i][j].x; + double y = this->polygons[i][j].y; + CGAL_Nef_polyhedron2::Point p = CGAL_Nef_polyhedron2::Point(x, y); + pdata_point_lists.back().push_back(p); + } + pdata.push_back(std::make_pair(pdata_point_lists.back().begin(), + pdata_point_lists.back().end())); } + + CGAL_Nef_polyhedron2 N(pdata.begin(), pdata.end(), CGAL_Nef_polyhedron2::POLYGONS); + return CGAL_Nef_polyhedron(N); } else { diff --git a/transform.cc b/transform.cc index b7408d7..bd8ad8d 100644 --- a/transform.cc +++ b/transform.cc @@ -210,42 +210,28 @@ CGAL_Nef_polyhedron TransformNode::render_cgal_nef_polyhedron() const if (N.dim == 2) { - // WARNING: There must be an easier way to perform a CGAL_Aff_transformation2 - // on a CGAL_Nef_polyhedron2 than this. But I haven't found the right way to do - // it yet and this solution seams to work well. - + // Unfortunately CGAL provides no transform method for CGAL_Nef_polyhedron2 + // objects. So we convert in to our internal 2d data format, transform it, + // tesselate it and create a new CGAL_Nef_polyhedron2 from it.. What a hack! + CGAL_Aff_transformation2 t( m[0], m[4], m[12], m[1], m[5], m[13], m[15]); - typedef std::list<CGAL_Nef_polyhedron2::Point> point_list_t; - typedef point_list_t::iterator point_list_it; - std::list< point_list_t > pdata_point_lists; - std::list < std::pair < point_list_it, point_list_it > >pdata; - - typedef CGAL_Nef_polyhedron2::Explorer Explorer; - typedef Explorer::Face_const_iterator fci_t; - typedef Explorer::Halfedge_around_face_const_circulator heafcc_t; - Explorer E = N.p2.explorer(); - - for (fci_t fit = E.faces_begin(), fend = E.faces_end(); fit != fend; ++fit) - { - pdata_point_lists.push_back(point_list_t()); - heafcc_t fcirc(E.halfedge(fit)), fend(fcirc); - CGAL_For_all(fcirc, fend) { - if (E.is_standard(E.target(fcirc))) { - Explorer::Point ep = E.point(E.target(fcirc)); - CGAL_Kernel2::Point_2 tp = t.transform(CGAL_Kernel2::Point_2(ep.x(), ep.y())); - // FIXME: This to_double() calls should not be neccessary! It would be much better to reuse - // the gmpq value directly. But I haven't managed to kick CGAL hard enough to do the trick.. - CGAL_Nef_polyhedron2::Point p = CGAL_Nef_polyhedron2::Point(to_double(tp.x()), to_double(tp.y())); - pdata_point_lists.back().push_back(p); - } - } - pdata.push_back(std::make_pair(pdata_point_lists.back().begin(), pdata_point_lists.back().end())); + DxfData dd(N); + for (int i=0; i < dd.points.size(); i++) { + CGAL_Kernel2::Point_2 p = CGAL_Kernel2::Point_2(dd.points[i].x, dd.points[i].y); + p = t.transform(p); + dd.points[i].x = to_double(p.x()); + dd.points[i].y = to_double(p.y()); } - N.p2 = CGAL_Nef_polyhedron2(pdata.begin(), pdata.end(), CGAL_Nef_polyhedron2::POLYGONS); + PolySet ps; + ps.is2d = true; + dxf_tesselate(&ps, &dd, 0, true, 0); + + N = ps.render_cgal_nef_polyhedron(); + ps.refcount = 0; } if (N.dim == 3) { CGAL_Aff_transformation t( |