-
Notifications
You must be signed in to change notification settings - Fork 7
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Added straight skeleton 2 #29
Changes from 8 commits
f83a8b7
c0b949f
1c8d264
5dc909a
d39792b
032fae0
6c623b6
30ccf2d
ec8996a
9b2f245
e93d240
391a8a9
bb3d711
c229d1a
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
******************************************************************************** | ||
compas_cgal.straight_skeleton_2 | ||
******************************************************************************** | ||
|
||
.. currentmodule:: compas_cgal.straight_skeleton_2 | ||
|
||
.. autosummary:: | ||
:toctree: generated/ | ||
:nosignatures: | ||
|
||
create_interior_straight_skeleton |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
from compas.datastructures import Graph | ||
from compas.geometry import Polygon | ||
from compas_viewer import Viewer | ||
|
||
from compas_cgal.straight_skeleton_2 import create_interior_straight_skeleton | ||
|
||
points = [ | ||
(-1.91, 3.59, 0.0), | ||
(-5.53, -5.22, 0.0), | ||
(-0.39, -1.98, 0.0), | ||
(2.98, -5.51, 0.0), | ||
(4.83, -2.02, 0.0), | ||
(9.70, -3.63, 0.0), | ||
(12.23, 1.25, 0.0), | ||
(3.42, 0.66, 0.0), | ||
(2.92, 4.03, 0.0), | ||
(-1.91, 3.59, 0.0), | ||
] | ||
polygon = Polygon(points) | ||
lines = create_interior_straight_skeleton(points) | ||
graph = Graph.from_lines(lines) | ||
|
||
# ============================================================================== | ||
# Viz | ||
# ============================================================================== | ||
|
||
viewer = Viewer(width=1600, height=900) | ||
viewer.renderer_config.show_grid = False | ||
viewer.scene.add(graph, edgecolor=(1.0, 0.0, 0.0)) | ||
viewer.scene.add(polygon) | ||
viewer.show() |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
******************************************************************************** | ||
2D Straight Skeleton | ||
******************************************************************************** | ||
|
||
.. figure:: /_images/cgal_straight_skeleton_2.png | ||
:figclass: figure | ||
:class: figure-img img-fluid | ||
|
||
|
||
.. literalinclude:: straight_skeleton_2.py | ||
:language: python |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
import numpy as np | ||
from compas.geometry import normal_polygon | ||
from compas.tolerance import Tolerance | ||
|
||
from compas_cgal._cgal import straight_skeleton_2 | ||
|
||
from .types import PolylinesNumpy | ||
|
||
|
||
def create_interior_straight_skeleton(points) -> PolylinesNumpy: | ||
"""Compute the skeleton of a polygon. | ||
|
||
Parameters | ||
---------- | ||
points : list of point coordinates or :class:`compas.geometry.Polygon` | ||
The points of the polygon. | ||
|
||
Returns | ||
------- | ||
:attr:`compas_cgal.types.PolylinesNumpy` | ||
The skeleton of the polygon. | ||
|
||
Raises | ||
------ | ||
ValueError | ||
If the normal of the polygon is not [0, 0, 1]. | ||
""" | ||
points = list(points) | ||
tol = Tolerance() | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. remove |
||
if not tol.is_allclose(normal_polygon(points, True), [0, 0, 1]): | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
raise ValueError("Please pass a polygon with a normal vector of [0, 0, 1].") | ||
V = np.asarray(points, dtype=np.float64) | ||
return straight_skeleton_2.create_interior_straight_skeleton(V) |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
|
||
#include "straight_skeleton_2.h" | ||
#include <CGAL/Polygon_2.h> | ||
#include <CGAL/create_straight_skeleton_2.h> | ||
|
||
typedef CGAL::Exact_predicates_inexact_constructions_kernel K; | ||
typedef K::Point_2 Point; | ||
typedef CGAL::Polygon_2<K> Polygon_2; | ||
typedef CGAL::Straight_skeleton_2<K> Ss; | ||
typedef boost::shared_ptr<Ss> SsPtr; | ||
typedef CGAL::Straight_skeleton_2<K>::Halfedge_const_handle Halfedge_const_handle; | ||
typedef CGAL::Straight_skeleton_2<K>::Vertex_const_handle Vertex_const_handle; | ||
|
||
Edges pmp_create_interior_straight_skeleton( | ||
Eigen::Ref<const compas::RowMatrixXd> &V) | ||
{ | ||
Polygon_2 poly; | ||
for (int i = 0; i < V.rows(); i++) | ||
{ | ||
poly.push_back(Point(V(i, 0), V(i, 1))); | ||
} | ||
assert(poly.is_counterclockwise_oriented()); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. perhaps it is worth checking what happens with these assertions on the Python side There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i removed the assert, as the orientation check is anyway on python side |
||
SsPtr iss = CGAL::create_interior_straight_skeleton_2(poly.vertices_begin(), poly.vertices_end()); | ||
Edges edgelist; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. perhaps this typedef conflicts with the one from |
||
for(auto hit = iss->halfedges_begin(); hit != iss->halfedges_end(); ++hit){ | ||
const Halfedge_const_handle h = hit; | ||
if(!h->is_bisector()){ | ||
continue; | ||
} | ||
const Vertex_const_handle& v1 = h->vertex(); | ||
const Vertex_const_handle& v2 = h->opposite()->vertex(); | ||
if(&*v1 < &*v2){ | ||
std::vector<double> s_vec = {v1->point().x(), v1->point().y(), 0}; | ||
std::vector<double> t_vec = {v2->point().x(), v2->point().y(), 0}; | ||
Edge edge = std::make_tuple(s_vec, t_vec); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. same here... |
||
edgelist.push_back(edge); | ||
} | ||
|
||
} | ||
return edgelist; | ||
}; | ||
|
||
|
||
// =========================================================================== | ||
// PyBind11 | ||
// =========================================================================== | ||
|
||
void init_straight_skeleton_2(pybind11::module &m) | ||
{ | ||
pybind11::module submodule = m.def_submodule("straight_skeleton_2"); | ||
|
||
submodule.def( | ||
"create_interior_straight_skeleton", | ||
&pmp_create_interior_straight_skeleton, | ||
pybind11::arg("V").noconvert()); | ||
}; |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
#ifndef COMPAS_STRAIGHT_SKELETON_2_H | ||
#define COMPAS_STRAIGHT_SKELETON_2_H | ||
|
||
#include <compas.h> | ||
|
||
typedef std::tuple<std::vector<double>, std::vector<double>> Edge; | ||
typedef std::list<Edge> Edges; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. perhaps we can move these guys to the compas namespace? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. same for the definitions in There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i put the typedefs of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. It finally builds! just forgot to add the "straight_skeleton_2.cpp" to the setup.py 😅 |
||
|
||
Edges pmp_create_interior_straight_skeleton( | ||
Eigen::Ref<const compas::RowMatrixXd> &V); | ||
|
||
#endif /* COMPAS_STRAIGHT_SKELETON_2_H */ |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
from compas_cgal.straight_skeleton_2 import create_interior_straight_skeleton | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. perhaps it would be worth adding a few tests of "known"/"predictable" skeletons? |
||
|
||
|
||
def test_straight_polygon(): | ||
points = [ | ||
(-1, -1, 0), | ||
(0, -12, 0), | ||
(1, -1, 0), | ||
(12, 0, 0), | ||
(1, 1, 0), | ||
(0, 12, 0), | ||
(-1, 1, 0), | ||
(-12, 0, 0), | ||
] | ||
lines = create_interior_straight_skeleton(points) | ||
assert len(lines) == 8 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
currently you should do
from compas.tolerance import TOL
, which is the global instance of theTolerance
class.i will replace this with a singleton in the future, but currently this would be better...