Skip to content

Commit

Permalink
partial2
Browse files Browse the repository at this point in the history
  • Loading branch information
psauvan committed Dec 21, 2024
1 parent b74891c commit 5402c0a
Show file tree
Hide file tree
Showing 3 changed files with 275 additions and 7 deletions.
16 changes: 16 additions & 0 deletions src/geouned/GEOUNED/utils/basic_functions_part1.py
Original file line number Diff line number Diff line change
Expand Up @@ -196,3 +196,19 @@ def __str__(self):
MajorRadius: {self.MajorRadius}
MinorRadius: {self.MinorRadius} """
return outstr


class MetaPlanesParams:
def __init__(self, params):
self.PlaneNumber = len(params[0])
self.Planes = []
self.Edges = params[1]
self.Vertexes = params[2]
for pm in params[0]:
self.Planes.append(PlaneParams(pm))

def __str__(self):
outstr = f"""Metaplane :\n"""
for p in self.Planes:
outstr += f"{p.__str__()} \n"
return outstr
23 changes: 18 additions & 5 deletions src/geouned/GEOUNED/utils/functions.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,14 @@
PlaneParams,
SphereParams,
TorusParams,
MetaPlanesParams,
is_parallel,
)
from . import basic_functions_part2 as BF

from .data_classes import NumericFormat, Options, Tolerances


def get_box(comp, enlargeBox):
bb = FreeCAD.BoundBox(comp.BoundBox)
bb.enlarge(enlargeBox)
Expand Down Expand Up @@ -208,6 +210,9 @@ def __init__(self, params, boundBox, Face=None):
elif params[0] == "Torus":
self.Type = params[0]
self.Surf = TorusParams(params[1])
elif params[0] == "MetaP":
self.Type = params[0]
self.Surf = MetaPlanesParams(params[1])

self.shape = Face

Expand Down Expand Up @@ -321,18 +326,27 @@ def build_surface(self):
torus = Part.makeTorus(majorR, minorR, center, axis)
self.shape = torus.Faces[0]
return
elif self.type == "MetaP":
planes = self.Surf.Planes
vertexes = self.Surf.Vertexes
metaplanes = makeMetaPlane(planes, vertexes, self.__boundBox__)
self.shape = metaplanes

else:
logger.error(f"Type {self.Type} is not defined")
return


class SurfacesDict(dict):
def __init__(self, surfaces=None, offset: int = 0,
def __init__(
self,
surfaces=None,
offset: int = 0,
options: Options = Options(),
tolerances: Tolerances = Tolerances(),
numeric_format: NumericFormat = NumericFormat(),
):
):

self.IndexOffset = offset
self.options = options
self.tolerance = tolerances
Expand Down Expand Up @@ -405,8 +419,6 @@ def extend(self, surface):
for s in surface["Tor"]:
self.add_torus(s)



def add_plane(self, plane, fuzzy):
ex = FreeCAD.Vector(1, 0, 0)
ey = FreeCAD.Vector(0, 1, 0)
Expand Down Expand Up @@ -626,6 +638,7 @@ def add_metaplane(self, mp, fuzzy=False):
else:
return index, True


def split_bop(solid, tools, tolerance, options, scale=0.1):

if tolerance >= 0.1:
Expand Down
243 changes: 241 additions & 2 deletions src/geouned/GEOUNED/utils/meta_planes.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
import FreeCAD
import Part
import numpy
from .geometry_gu import PlaneGu
from .functions import GeounedSurface


def get_metaplanes(solid):
def get_metaplanes(solid, universe_box):
planes = []
for f in solid.Faces:
if type(f.Surface) is Part.Plane:
Expand All @@ -19,7 +23,13 @@ def get_metaplanes(solid):
meta_loop([p], metap, planes)
if len(metap) != 1:
if no_convex(metap):
metaplane_list.append(metap)
mp_params = build_metap_params(metap)
mp = GeounedSurface(
("MetaPlane", mp_params),
universe_box,
Face="Build",
)
metaplane_list.append(mp)
return metaplane_list


Expand Down Expand Up @@ -117,3 +127,232 @@ def other_face_edge(current_edge, current_face, Faces, outer_only=False):
for edge in Edges:
if current_edge.isSame(edge):
return face


def build_metap_params(plane_list):

planeparams = []
edges = []
vertexes = []

for p in plane_list:
plane = PlaneGu(p)
planeparams.append((plane.Position, plane.Axis, plane.dim1, plane.dim2))

ajdacent_planes = [[] for i in range(len(plane_list))]
for i, p1 in enumerate(plane_list):
for j, p2 in enumerate(plane[i + 1 :]):
e = commonEdge(p1, p2)
if e is not None:
ajdacent_planes[i].append((j, e))
ajdacent_planes[j].append((i, e))

vertex_list = []
for i, e1 in enumerate(edges):

for e2 in edges[i + 1 :]:
vertex_list.extend(commonVertex(e1, e2))

vertexes = []
while len(vertex_list) > 0:
v = vertex_list.pop()
n = 0
for vi in reversed(vertex_list):
if v == vi:
n += 1
vertex_list.remove(vi)
if n > 0:
vertexes.append((v, n + 1))

return (planeparams, edges, vertexes)


def commonVertex(e1, e2):
if e1.distToShape(e2) > 0:
return []

common = []
if e1.Vertexes[0] == e2.Vertexes[0]:
common.append(e1.Vertexes[0])
elif e1.Vertexes[0] == e2.Vertexes[1]:
common.append(e1.Vertexes[0])

if e1.Vertexes[1] == e2.Vertexes[0]:
common.append(e1.Vertexes[1])
elif e1.Vertexes[1] == e2.Vertexes[1]:
common.append(e1.Vertexes[1])

return common


def commonEdge(face1, face2, outer_only=True):
if face1.distToShape[0] > 0:
return None

Edges1 = face1.OuterWire.Edges if outer_only else face1.Edges
Edges2 = face2.OuterWire.Edges if outer_only else face2.Edges
for e1 in Edges1:
for e2 in Edges2:
if e1.isSame(e2):
return e1
return None


def makeBoxFaces(box):
if isinstance(box[0], (int, float)):
xmin, ymin, zmin, xmax, ymax, zmax = box
v0 = FreeCAD.Vector(xmin, ymin, zmin)
v1 = FreeCAD.Vector(xmin, ymax, zmin)
v2 = FreeCAD.Vector(xmin, ymax, zmax)
v3 = FreeCAD.Vector(xmin, ymin, zmax)
v4 = FreeCAD.Vector(xmax, ymin, zmin)
v5 = FreeCAD.Vector(xmax, ymax, zmin)
v6 = FreeCAD.Vector(xmax, ymax, zmax)
v7 = FreeCAD.Vector(xmax, ymin, zmax)
face1 = (v0, v1, v2, v3)
face2 = (v7, v6, v5, v4)
face3 = (v0, v3, v7, v4)
face4 = (v5, v6, v2, v1)
face5 = (v4, v5, v1, v0)
face6 = (v6, v7, v3, v2)

faces_points = (face1, face2, face3, face4, face5, face6)
else:
faces_points = box

faces = []
for f in faces_points:
faces.append(Part.Face(Part.makePolygon(f, True)))
return faces


def cut_face(face, plane):
line = face.Surface.intersect(plane)
inter = []
if len(line) > 0:
l = line[0]
for e in face.Edges:
pt = l.intersect(e.Curve)
if len(pt) > 0:
point = pt[0].toShape().Point
if e.isInside(point, 1e-12, True):
inter.append(point)

newpoints = inter[:]
for v in face.Vertexes:
if v.Point.dot(plane.Axis) > 0:
newpoints.append(v.Point)
if len(newpoints) == 0:
return None, None
else:
sorted = sort_points(newpoints, face.Surface.Axis)
return sorted, inter


def cut_box(faces, plane):
updatedfaces = []
newface_points = []
for f in faces:
newface, newpoints = cut_face(f, plane)
if newface is None:
continue
updatedfaces.append(newface)
newface_points.extend(newpoints)

sorted = sort_points(newface_points, plane.Axis)
updatedfaces.append(sorted)

return updatedfaces


def sort_points(point_list, normal):

if len(point_list) == 0:
return []

s = FreeCAD.Vector((0, 0, 0))
for v in point_list:
s = s + v
s = s / len(point_list)

vtxvec = []
for v in point_list:
vtxvec.append(v - s)

X0 = vtxvec[0]
Y0 = normal.cross(X0)

orden = []
for i, v in enumerate(vtxvec):
phi = numpy.arctan2(v.dot(Y0), v.dot(X0))
orden.append((phi, i))
orden.sort()

points = tuple(point_list[p[1]] for p in orden)
return points


def remove_box_faces(point_face_list, faces, boxlim):
plane_points = []
for i, face in enumerate(faces):
if abs(face.Surface.Axis.dot(FreeCAD.Vector(1, 0, 0)) - 1) < 1e-12 and abs(boxlim[0] - face.Surface.Position.X) < 1e-12:
continue
elif (
abs(face.Surface.Axis.dot(FreeCAD.Vector(-1, 0, 0)) - 1) < 1e-12
and abs(boxlim[3] - face.Surface.Position.X) < 1e-12
):
continue
elif (
abs(face.Surface.Axis.dot(FreeCAD.Vector(0, 1, 0)) - 1) < 1e-12 and abs(boxlim[1] - face.Surface.Position.Y) < 1e-12
):
continue
elif (
abs(face.Surface.Axis.dot(FreeCAD.Vector(0, -1, 0)) - 1) < 1e-12
and abs(boxlim[4] - face.Surface.Position.Y) < 1e-12
):
continue
elif (
abs(face.Surface.Axis.dot(FreeCAD.Vector(0, 0, 1)) - 1) < 1e-12 and abs(boxlim[2] - face.Surface.Position.Z) < 1e-12
):
continue
elif (
abs(face.Surface.Axis.dot(FreeCAD.Vector(0, 0, -1)) - 1) < 1e-12
and abs(boxlim[5] - face.Surface.Position.Z) < 1e-12
):
continue
plane_points.append(point_face_list[i])

return plane_points


def fix_points(point_plane_list, vertex_list):
tol = 1e-8
for i, current_plane in enumerate(point_plane_list):
for point in current_plane:
for planepts in point_plane_list[i + 1 :]:
for j in range(len(planepts)):
r = point - planepts[j]
if r.Length < tol:
planepts[j] = point

for v in vertex_list:
for planpts in point_plane_list:
for i in range(len(planpts)):
r = v.Point - planepts[i]
if r.Length < tol:
planpts[i] = v.Point


def makeMetaPlanes(plane_list, vertex_list, box):
boxlim = (box.Xmin, box.YMin, box.Zmin, box.XMax, box.YMax, box.ZMax)
cutfaces = makeBoxFaces(boxlim)
for p in plane_list:
plane = Part.Plane(p.Position, p.Axis)
newbox_points = cut_box(cutfaces, plane)
cutfaces = makeBoxFaces(newbox_points)

plane_points = remove_box_faces(newbox_points, cutfaces, boxlim)
fix_points(plane_points, vertex_list)
metaFaces = Part.Shell(makeBoxFaces(plane_points))

return metaFaces

0 comments on commit 5402c0a

Please sign in to comment.