In [21]:
%pylab inline
import pyhull
import string
from pyhull.simplex import Simplex
In [22]:
class MyConvexHull(object):
def __init__(self, res=None, eqs=None, points=None, facets=None):
self.res = res
self.eqs = eqs
self.points = points
self.facets = facets
@classmethod
def from_points(cls, points):
res = pyhull.qconvex('n i', points)
n_dim = int(res[0])-1
n_eqs = int(res[1])
eqs = array([line.split() for line in res[2:2+n_eqs]]).astype(float)
n_facets = int(res[2+n_eqs])
facets = array([line.split() for line in res[3+n_eqs:3+n_eqs+n_facets]]).astype(int)
return cls(res, eqs, points, facets)
@classmethod
def from_halfspaces(cls, interior_point, halfspaces):
opt = 'H{:s} Fp'.format(string.join(array([0,0,0]).astype(str),','))
res = pyhull.qhull_cmd('qhalf', opt, halfspaces)
n_dim = int(res[0])
n_vert = int(res[1])
points = array([line.split() for line in res[2:2+n_vert]]).astype(float)
return cls.from_points(points)
def add_buffer(self, b):
self.eqs[:,-1] -= b
interior_point = (self.points[0] + self.points[1])/2 # since convex
return MyConvexHull.from_halfspaces(interior_point, self.eqs)
def __repr__(self):
return string.join(self.res, '\n')
def contains(self, p):
return False
In [31]:
p = rand(10,2) - 0.5
p = array(bmat([[p],[0.5*p + [0,1]] ,[0.2*p + [1,2]], [0.1*p + [2,2]]])).astype(float)
ch1 = MyConvexHull.from_points(p)
ch1 = ch1.add_buffer(0.1)
plot(p[:,0], p[:,1], 'k.')
for facet in ch1.facets:
plot(ch1.points[facet][:,0], ch1.points[facet][:,1], 'k')
In [ ]: