Salome HOME
decoupage insereFissureGenerale, renommée construitFissureGenerale, premiere phase...
[modules/smesh.git] / src / Tools / blocFissure / gmu / identifieElementsDebouchants.py
1 # -*- coding: utf-8 -*-
2
3 import logging
4 import math
5
6 from geomsmesh import geompy
7
8 from produitMixte import produitMixte
9 from whichSide import whichSide
10   
11 def identifieElementsDebouchants(ifil, facesDefaut, partitionPeauFissFond,
12                                 edgesFondIn, edgesFondFiss, wireFondFiss,
13                                 aretesVivesC, fillingFaceExterne,
14                                 edgesPipeIn, verticesPipePeau, rayonPipe,
15                                 facesInside, facesOnside):
16   """
17   elements débouchants (intersection pipe et peau), indexés selon les edges du fond de fissure (edgesFondIn)
18   """
19   
20   logging.info('start')
21  
22   verticesEdgesFondIn = [] # les points du fond de fissure au débouché du pipe sur la peau (indice de edgesFondIn)
23   pipexts = []             # les segments de pipe associés au points de fond de fissure débouchants (même indice)
24   cercles = []             # les cercles de generation des pipes débouchant (même indice)
25   facesFissExt = []        # les faces de la fissure externe associés au points de fond de fissure débouchants (même indice)
26   edgesFissExtPeau = []    # edges des faces de fissure externe sur la peau (même indice)
27   edgesFissExtPipe = []    # edges des faces de fissure externe sur le pipe (même indice)
28
29   #logging.debug("edgesFondIn %s", edgesFondIn)
30   for iedf, edge in enumerate(edgesFondIn):
31     name = "edgeFondIn%d"%iedf
32     geompy.addToStudyInFather(partitionPeauFissFond, edge, name)
33     dist = [ geompy.MinDistance(pt, edge) for pt in verticesPipePeau]
34     ptPeau = verticesPipePeau[dist.index(min(dist))] # le point de verticesPipePeau a distance minimale de l'edge
35     [u, PointOnEdge, EdgeInWireIndex]  = geompy.MakeProjectionOnWire(ptPeau, wireFondFiss)
36     logging.debug("u:%s, EdgeInWireIndex: %s, len(edgesFondFiss): %s", u, EdgeInWireIndex, len(edgesFondFiss))
37     localEdgeInFondFiss = edgesFondFiss[EdgeInWireIndex]
38     centre = PointOnEdge
39     centre2 = geompy.MakeVertexOnCurve(localEdgeInFondFiss, u)
40     geompy.addToStudyInFather(partitionPeauFissFond, centre2, "centre2_%d"%iedf)
41     verticesEdgesFondIn.append(centre)
42     name = "verticeEdgesFondIn%d"%iedf
43     geompy.addToStudyInFather(partitionPeauFissFond, centre, name)
44     norm = geompy.MakeTangentOnCurve(localEdgeInFondFiss, u)
45     geompy.addToStudyInFather(partitionPeauFissFond, centre, "norm%d"%iedf)
46     cercle = geompy.MakeCircle(centre, norm, rayonPipe)
47     geompy.addToStudyInFather(partitionPeauFissFond, cercle, "cerclorig%d"%iedf)
48     [vertex] = geompy.ExtractShapes(cercle, geompy.ShapeType["VERTEX"], False)
49     vec1 = geompy.MakeVector(centre, vertex)
50     vec2 = geompy.MakeVector(centre, ptPeau)
51     angle = geompy.GetAngleRadians(vec1, vec2)
52     # cas général : on reconstitue une portion de pipe, avec l'arête de couture qui coincide
53     #   avec la face de fissure, au niveau du débouché sur la face externe
54     # cas dégénéré : le pipe débouche perpendiculairement à une surface plane à l'origine.
55     #   La partition filling / pipe reconstruit échoue.
56     #   - Si on partitionne le filling avec un simple pipe obtenu par extrusion droite du cercle,
57     #     cela donne un point en trop sur le cercle.
58     #   - Si on prend une vraie surface plane (pas un filling), on peut faire la partition avec 
59     #     les pipes reconstruits              
60     logging.debug("angle=%s", angle)
61     #if abs(angle) > 1.e-7:
62     sommetAxe = geompy.MakeTranslationVector(centre, norm)
63     pm = produitMixte(centre, vertex, ptPeau, sommetAxe)
64     if pm > 0:  # ajout de pi a (-)angle pour éviter des points confondus (partition échoue) dans les cas dégénérés
65       cercle = geompy.MakeRotation(cercle, norm, angle + math.pi)
66     else:
67       cercle = geompy.MakeRotation(cercle, norm, -angle + math.pi)
68     name = "cercle%d"%iedf
69     geompy.addToStudyInFather(partitionPeauFissFond, cercle, name)
70     cercles.append(cercle)
71
72     # --- estimation de la longueur du pipe necessaire de part et d'autre du point de sortie
73     if aretesVivesC is None:
74       faceTestPeau = fillingFaceExterne
75     else:
76       faceTestPeau = facesDefaut[ifil]
77     sideCentre = whichSide(faceTestPeau, centre)
78     locPt0 = geompy.MakeVertexOnCurve(localEdgeInFondFiss, 0.0)
79     locPt1 = geompy.MakeVertexOnCurve(localEdgeInFondFiss, 1.0)
80     sidePt0 = whichSide(faceTestPeau, locPt0)
81     sidePt1 = whichSide(faceTestPeau, locPt1)
82     logging.debug("position centre cercle: %s, extremité edge u0: %s, u1: %s", sideCentre, sidePt0, sidePt1) 
83     normFace = geompy.GetNormal(faceTestPeau, ptPeau)
84     inclPipe = abs(geompy.GetAngleRadians(norm, normFace))
85     lgp = max(rayonPipe/2., abs(3*rayonPipe*math.tan(inclPipe)))
86     logging.debug("angle inclinaison Pipe en sortie: %s degres, lgp: %s", inclPipe*180/math.pi, lgp)
87     
88     # --- position des points extremite du pipe sur l'edge debouchante
89     #     il faut la distance curviligne ofp du point central par rapport à une extrémité de l'edge débouchante
90     locEdgePart = geompy.MakePartition([localEdgeInFondFiss],[centre], [], [], geompy.ShapeType["EDGE"], 0, [], 0)
91     edgesLoc = geompy.ExtractShapes(locEdgePart, geompy.ShapeType["EDGE"], False)
92     edgesLocSorted =[(geompy.MinDistance(edge, locPt0), kk, edge) for kk, edge in enumerate(edgesLoc)]
93     edgesLocSorted.sort()
94     ofp = geompy.BasicProperties(edgesLocSorted[0][2])[0] # distance curviligne centre locPt0
95     logging.debug("distance curviligne centre extremite0: %s", ofp)
96     p1 = geompy.MakeVertexOnCurveByLength(localEdgeInFondFiss, ofp +lgp, locPt0)
97     p2 = geompy.MakeVertexOnCurveByLength(localEdgeInFondFiss, ofp -lgp, locPt0)
98     geompy.addToStudyInFather(wireFondFiss, p1, "p1_%d"%iedf)
99     geompy.addToStudyInFather(wireFondFiss, p2, "p2_%d"%iedf)
100
101     edgePart = geompy.MakePartition([localEdgeInFondFiss], [p1,p2], [], [], geompy.ShapeType["EDGE"], 0, [], 0)
102     edps = geompy.ExtractShapes(edgePart, geompy.ShapeType["EDGE"], True)
103     for edp in edps:
104       if geompy.MinDistance(centre, edp) < 1.e-3:
105         pipext = geompy.MakePipe(cercle, edp)
106         name = "pipeExt%d"%iedf
107         geompy.addToStudyInFather(partitionPeauFissFond, pipext, name)
108         pipexts.append(pipext)
109
110     for ifa, face in enumerate(facesInside):
111       logging.debug("recherche edges communes entre une face inside et (faces onside, edges pipe et fond débouchante)")
112       edgesPeauFis = []
113       edgesPipeFis = []
114       edgesPipeFnd = []
115       try:
116         edgesPeauFis = geompy.GetSharedShapesMulti([geompy.MakeCompound(facesOnside), face], geompy.ShapeType["EDGE"])
117         logging.debug("    faces onside %s",edgesPeauFis)
118         edgesPipeFis = geompy.GetSharedShapesMulti([geompy.MakeCompound(edgesPipeIn), face], geompy.ShapeType["EDGE"])
119         logging.debug("    edgesPipeIn %s", edgesPipeFis)
120         edgesPipeFnd = geompy.GetSharedShapesMulti([geompy.MakeCompound(edgesFondIn), face], geompy.ShapeType["EDGE"])
121         logging.debug("    edgesFondIn %s ", edgesPipeFnd)
122       except:
123         logging.debug("  pb edges communes %s %s %s",edgesPeauFis, edgesPipeFis, edgesPipeFnd)
124         pass
125       if (len(edgesPeauFis) > 0) and (len(edgesPipeFis) > 0) and (len(edgesPipeFnd) == 0):
126         dist = geompy.MinDistance(geompy.MakeCompound(edgesPeauFis), ptPeau)
127         logging.debug("    test distance extrémité reference %s", dist)
128         if dist < 1.e-3: # c'est la face de fissure externe associée
129           logging.debug("    face %s inside ajoutée", ifa)
130           facesFissExt.append(face)
131           name="faceFissExt%d"%iedf
132           geompy.addToStudyInFather(partitionPeauFissFond, face, name)
133           dist = 1.
134           for ipe, edpe in enumerate(edgesPeauFis):
135             for ipi, edpi in enumerate(edgesPipeFis):
136               dist = geompy.MinDistance(edpe, edpi)
137               if dist < 1.e-3:
138                 edgesFissExtPeau.append(edpe)
139                 name="edgesFissExtPeau%d"%iedf
140                 geompy.addToStudyInFather(partitionPeauFissFond, edpe, name)
141                 edgesFissExtPipe.append(edpi)
142                 name="edgesFissExtPipe%d"%iedf
143                 geompy.addToStudyInFather(partitionPeauFissFond, edpi, name)
144                 break
145             if dist < 1.e-3:
146               break
147
148   return (verticesEdgesFondIn, pipexts, cercles, facesFissExt, edgesFissExtPeau, edgesFissExtPipe)