revision 930 by gross, Thu Jan 18 08:12:58 2007 UTC revision 931 by gross, Fri Jan 19 03:06:33 2007 UTC
# Line 436  class Manifold1D(PrimitiveBase): Line 436  class Manifold1D(PrimitiveBase):
436           returns end point           returns end point
437           """           """
438           raise NotImplementedError()           raise NotImplementedError()
439        def getBoundary(self):
440            """
441            returns a list of the zero-dimensional manifolds forming the boundary of the curve
442            """
443            return [ self.getStartPoint(), self.getEndPoint()]
444
445  class CurveBase(Manifold1D):  class CurveBase(Manifold1D):
446      """      """
# Line 480  class Curve(CurveBase, Primitive): Line 485  class Curve(CurveBase, Primitive):
485         defines a curve form control points         defines a curve form control points
486         """         """
487         if len(points)<2:         if len(points)<2:
488             raise TypeError("Curve needs at least two points")             raise ValueError("Curve needs at least two points")
489         i=0         i=0
490         for p in points:         for p in points:
491                i+=1                i+=1
# Line 763  class CurveLoop(Primitive, PrimitiveBase Line 768  class CurveLoop(Primitive, PrimitiveBase
768         creates a polygon from a list of line curves. The curves must form a closed loop.         creates a polygon from a list of line curves. The curves must form a closed loop.
769         """         """
770         if len(curves)<2:         if len(curves)<2:
771              raise TypeError("at least two curves have to be given.")              raise ValueError("at least two curves have to be given.")
772         for i in range(len(curves)):         for i in range(len(curves)):
773             if not isinstance(curves[i],Manifold1D):             if not isinstance(curves[i],Manifold1D):
774                raise TypeError("%s-th argument is not a Manifold1D object."%i)                raise TypeError("%s-th argument is not a Manifold1D object."%i)
# Line 866  class ReverseCurveLoop(ReversePrimitive, Line 871  class ReverseCurveLoop(ReversePrimitive,
871         creates a polygon from a list of line curves. The curves must form a closed loop.         creates a polygon from a list of line curves. The curves must form a closed loop.
872         """         """
873         if not isinstance(curve_loop, CurveLoop):         if not isinstance(curve_loop, CurveLoop):
874             raise ValueError("arguments need to be an instance of CurveLoop.")             raise TypeError("arguments need to be an instance of CurveLoop.")
875         ReversePrimitive.__init__(self, curve_loop)         ReversePrimitive.__init__(self, curve_loop)
876         PrimitiveBase.__init__(self)         PrimitiveBase.__init__(self)
877
# Line 909  class RuledSurface(Primitive, Manifold2D Line 914  class RuledSurface(Primitive, Manifold2D
914         if not isinstance(loop.getUnderlyingPrimitive(),CurveLoop):         if not isinstance(loop.getUnderlyingPrimitive(),CurveLoop):
915             raise TypeError("argument loop needs to be a CurveLoop object.")             raise TypeError("argument loop needs to be a CurveLoop object.")
916         if len(loop)<2:         if len(loop)<2:
917             raise TypeError("the loop must contain at least two Curves.")             raise ValueError("the loop must contain at least two Curves.")
918         if len(loop)>4:         if len(loop)>4:
919             raise TypeError("the loop must contain at least three Curves.")             raise ValueError("the loop must contain at least three Curves.")
920         Primitive.__init__(self)         Primitive.__init__(self)
921         Manifold2D.__init__(self)         Manifold2D.__init__(self)
922         self.__loop=loop         self.__loop=loop
# Line 981  class ReverseRuledSurface(ReversePrimiti Line 986  class ReverseRuledSurface(ReversePrimiti
986         creates a polygon from a list of line curves. The curves must form a closed loop.         creates a polygon from a list of line curves. The curves must form a closed loop.
987         """         """
988         if not isinstance(surface, RuledSurface):         if not isinstance(surface, RuledSurface):
989             raise ValueError("arguments need to be an instance of CurveLoop.")             raise TypeError("arguments need to be an instance of CurveLoop.")
990         ReversePrimitive.__init__(self, surface)         ReversePrimitive.__init__(self, surface)
991         Manifold2D.__init__(self)         Manifold2D.__init__(self)
992
# Line 1110  class ReversePlaneSurface(ReversePrimiti Line 1115  class ReversePlaneSurface(ReversePrimiti
1115         creates a polygon from a list of line curves. The curves must form a closed loop.         creates a polygon from a list of line curves. The curves must form a closed loop.
1116         """         """
1117         if not isinstance(surface, PlaneSurface):         if not isinstance(surface, PlaneSurface):
1118             raise ValueError("arguments need to be an instance of PlaneSurface.")             raise TypeError("arguments need to be an instance of PlaneSurface.")
1119         ReversePrimitive.__init__(self, surface)         ReversePrimitive.__init__(self, surface)
1120         Manifold2D.__init__(self)         Manifold2D.__init__(self)
1121
# Line 1147  class SurfaceLoop(Primitive, PrimitiveBa Line 1152  class SurfaceLoop(Primitive, PrimitiveBa
1152         creates a surface loop         creates a surface loop
1153         """         """
1154         if len(surfaces)<2:         if len(surfaces)<2:
1155              raise TypeError("at least two surfaces have to be given.")              raise ValueError("at least two surfaces have to be given.")
1156         for i in range(len(surfaces)):         for i in range(len(surfaces)):
1157             if not isinstance(surfaces[i].getUnderlyingPrimitive(),Manifold2D):             if not isinstance(surfaces[i].getUnderlyingPrimitive(),Manifold2D):
1158                raise TypeError("%s-th argument is not a Manifold2D object."%i)                raise TypeError("%s-th argument is not a Manifold2D object."%i)
# Line 1164  class SurfaceLoop(Primitive, PrimitiveBa Line 1169  class SurfaceLoop(Primitive, PrimitiveBa
1169            for i in xrange(len(surfaces)):            for i in xrange(len(surfaces)):
1170               if not used[i]:               if not used[i]:
1171                  i_boundary=surfaces[i].getBoundary()                  i_boundary=surfaces[i].getBoundary()
print i, i_boundary
1172                  for ib in xrange(len(i_boundary)):                    for ib in xrange(len(i_boundary)):
print ib, i_boundary[ib], edges
1173                      if i_boundary[ib] in edges:                      if i_boundary[ib] in edges:
if used_edges[edges.index(i_boundary[ib])]:
raise ValueError("boundary segment %s is shared by more than one surface."%str(i_boundary[ib]))
used_edges[edges.index(i_boundary[ib])]=True
self.__surfaces.append(surfaces[i])
for b in i_boundary:
if not b in edges:
edges.append(b)
used_edges.append(False)
1174                           found=True                           found=True
used[i]=True
1175                           break                           break
1176               if found: break                  if found:
1177                        used[i]=True
1178                        self.__surfaces.append(surfaces[i])
1179                        for ib in xrange(len(i_boundary)):
1180                           if i_boundary[ib] in edges:
1181                             if used_edges[edges.index(i_boundary[ib])]:
1182                                raise ValueError("boundary segment %s is shared by more than one surface."%str(i_boundary[ib].getUnderlyingPrimitive()))
1183                             used_edges[edges.index(i_boundary[ib])]=True
1184                           else:
1185                             edges.append(i_boundary[ib])
1186                             used_edges.append(False)
1187                        break
1189               raise ValueError("loop is not closed.")                 raise ValueError("loop is not closed.")
1190         print min(used_edges), used_edges         if not min(used_edges):
if min(used_edges):
1191            raise ValueError("loop is not closed. Surface is missing.")            raise ValueError("loop is not closed. Surface is missing.")
1192      def __len__(self):      def __len__(self):
1193         """         """
# Line 1222  class SurfaceLoop(Primitive, PrimitiveBa Line 1226  class SurfaceLoop(Primitive, PrimitiveBa
1226              else:              else:
1227                  out="%s"%i.getDirectedID()                  out="%s"%i.getDirectedID()
1228          return "Surface Loop(%s) = {%s};"%(self.getID(),out)          return "Surface Loop(%s) = {%s};"%(self.getID(),out)
1229
1230      def substitute(self,sub_dict):      def substitute(self,sub_dict):
1231          """          """
1232          returns a copy of self with substitutes for the primitives used to construct it given by the dictionary C{sub_dict}.          returns a copy of self with substitutes for the primitives used to construct it given by the dictionary C{sub_dict}.
# Line 1230  class SurfaceLoop(Primitive, PrimitiveBa Line 1235  class SurfaceLoop(Primitive, PrimitiveBa
1235          """          """
1236          if not sub_dict.has_key(self):          if not sub_dict.has_key(self):
1237              new_s=[]              new_s=[]
1238              for s in self.getCurves(): new_s.append(s.substitute(sub_dict))              for s in self.getSurfaces(): new_s.append(s.substitute(sub_dict))
1239              sub_dict[self]=SurfaceLoop(*tuple(new_s))              sub_dict[self]=SurfaceLoop(*tuple(new_s))
1240          return sub_dict[self]          return sub_dict[self]
1241
# Line 1242  class SurfaceLoop(Primitive, PrimitiveBa Line 1247  class SurfaceLoop(Primitive, PrimitiveBa
1247           if isinstance(primitive.getUnderlyingPrimitive(),SurfaceLoop):           if isinstance(primitive.getUnderlyingPrimitive(),SurfaceLoop):
1248              if len(primitive) == len(self):              if len(primitive) == len(self):
1249                  sp0=self.getSurfaces()                  sp0=self.getSurfaces()
1250                  sp1=primitive.getCurves()                  sp1=primitive.getSurfaces()
1251                  for s0 in sp0:                  for s0 in sp0:
1252                      collocated = False                      collocated = False
1253                      for s1 in sp1:                      for s1 in sp1:
# Line 1265  class ReverseSurfaceLoop(ReversePrimitiv Line 1270  class ReverseSurfaceLoop(ReversePrimitiv
1270         creates a polygon from a list of line surfaces. The curves must form a closed loop.         creates a polygon from a list of line surfaces. The curves must form a closed loop.
1271         """         """
1272         if not isinstance(surface_loop, SurfaceLoop):         if not isinstance(surface_loop, SurfaceLoop):
1273             raise ValueError("arguments need to be an instance of SurfaceLoop.")             raise TypeError("arguments need to be an instance of SurfaceLoop.")
1274         ReversePrimitive.__init__(self, surface_loop)         ReversePrimitive.__init__(self, surface_loop)
1275         PrimitiveBase.__init__(self)         PrimitiveBase.__init__(self)
1276
# Line 1277  class ReverseSurfaceLoop(ReversePrimitiv Line 1282  class ReverseSurfaceLoop(ReversePrimitiv
1282
1283      def __len__(self):      def __len__(self):
1284          return len(self.getUnderlyingPrimitive())          return len(self.getUnderlyingPrimitive())
1285  #==========================
1286  class Volume(PrimitiveBase):  #==============================
1287    class Manifold3D(PrimitiveBase):
1288        """
1289        general three-dimensional manifold
1290        """
1291        def __init__(self):
1292           """
1293           create a three-dimensional manifold
1294           """
1295           PrimitiveBase.__init__(self)
1296
1297        def getBoundary(self):
1298            """
1299            returns a list of the one-dimensional manifolds forming the boundary of the volume (including holes)
1300            """
1301            raise NotImplementedError()
1302
1303    class Volume(Manifold3D, Primitive):
1304      """      """
1305      a volume with holes.      a volume with holes.
1306      """      """
# Line 1291  class Volume(PrimitiveBase): Line 1313  class Volume(PrimitiveBase):
1313         @note: A SurfaceLoop defining a hole should not have any surfaces in common with the exterior SurfaceLoop.           @note: A SurfaceLoop defining a hole should not have any surfaces in common with the exterior SurfaceLoop.
1314                A SurfaceLoop defining a hole should not have any surfaces in common with another SurfaceLoop defining a hole in the same volume.                A SurfaceLoop defining a hole should not have any surfaces in common with another SurfaceLoop defining a hole in the same volume.
1315         """         """
1316         super(Volume, self).__init__()         if not isinstance(loop.getUnderlyingPrimitive(), SurfaceLoop):
if not loop.isSurfaceLoop():
1317             raise TypeError("argument loop needs to be a SurfaceLoop object.")             raise TypeError("argument loop needs to be a SurfaceLoop object.")
1318         for i in range(len(holes)):         for i in range(len(holes)):
1319              if not holes[i].isSurfaceLoop():              if not isinstance(holes[i].getUnderlyingPrimitive(), SurfaceLoop):
1320                   raise TypeError("%i th hole needs to be a SurfaceLoop object.")                   raise TypeError("%i th hole needs to be a SurfaceLoop object.")
1321           Primitive.__init__(self)
1322           Manifold3D.__init__(self)
1323         self.__loop=loop         self.__loop=loop
1324         self.__holes=holes         self.__holes=holes
1325      def getHoles(self):      def getHoles(self):
1326           """
1327           returns the hole in the volume
1328           """
1329         return self.__holes         return self.__holes
1330      def getSurfaceLoop(self):      def getSurfaceLoop(self):
1331           """
1332           returns the loop forming the surface
1333           """
1334         return self.__loop         return self.__loop
return Volume(self.getSurfaceLoop()+other, holes=[h+other for h in self.getHoles()])
def collectPrimitiveBases(self):
out=[self] + self.getSurfaceLoop().collectPrimitiveBases()
for i in self.getHoles(): out+=i.collectPrimitiveBases()
return out
def getConstructionPoints(self):
out=self.getSurfaceLoop().getConstructionPoints()
for i in self.getHoles(): out|=i.Points()
return out
1336      def getGmshCommand(self,scaling_factor=1.):      def getGmshCommand(self,scaling_factor=1.):
1337          """          """
1338          returns the Gmsh command(s) to create the primitive          returns the Gmsh command(s) to create the primitive
# Line 1328  class Volume(PrimitiveBase): Line 1348  class Volume(PrimitiveBase):
1348          else:          else:
1349            return "Volume(%s) = {%s};"%(self.getID(),self.getSurfaceLoop().getDirectedID())            return "Volume(%s) = {%s};"%(self.getID(),self.getSurfaceLoop().getDirectedID())
1350
1351        def substitute(self,sub_dict):
1352            """
1353            returns a copy of self with substitutes for the primitives used to construct it given by the dictionary C{sub_dict}.
1354            If a substitute for the object is given by C{sub_dict} the value is returned, otherwise a new instance
1355            with substituted arguments is returned.
1356            """
1357            if not sub_dict.has_key(self):
1358                sub_dict[self]=Volume(self.getSurfaceLoop().substitute(sub_dict),[ h.substitute(sub_dict) for h in self.getHoles()])
1359            return sub_dict[self]
1360
1361        def isColocated(self,primitive):
1362           """
1363           returns True if each curve is collocted with a curve in primitive
1364           """
1365           if hasattr(primitive,"getUnderlyingPrimitive"):
1366              if isinstance(primitive.getUnderlyingPrimitive(),Volume):
1367                 if self.getSurfaceLoop().isColocated(primitive.getSurfaceLoop()):
1368                    hs0=self.getHoles()
1369                    hs1=primitive.getHoles()
1370                    if len(hs0) == len(hs1):
1371                        for h0 in hs0:
1372                           collocated = False
1373                           for h1 in hs1:
1374                             collocated = collocated or h0.isColocated(h1)
1375                           if not collocated: return False
1376                        return True
1377           return False
1378        def collectPrimitiveBases(self):
1379            """
1380            returns primitives used to construct the Surface
1381            """
1382            out=[self] + self.getSurfaceLoop().collectPrimitiveBases()
1383            for i in self.getHoles(): out+=i.collectPrimitiveBases()
1384            return out
1385        def getBoundary(self):
1386            """
1387            returns a list of the one-dimensional manifolds forming the boundary of the Surface (including holes)
1388            """
1389            out = []+ self.getSurfaceLoop().getSurfaces()
1390            for h in self.getHoles(): out+=h.getSurfaces()
1391            return out
1392
1393  class PropertySet(PrimitiveBase):  class PropertySet(PrimitiveBase):
1394      """      """
1395      defines a group L{PrimitiveBase} objects.      defines a group L{PrimitiveBase} objects.
# Line 1340  class PropertySet(PrimitiveBase): Line 1402  class PropertySet(PrimitiveBase):
1402          out=[self]+self.getBoundaryLoop().collectPrimitiveBases()          out=[self]+self.getBoundaryLoop().collectPrimitiveBases()
1403          for i in self.getHoles(): out+=i.collectPrimitiveBases()          for i in self.getHoles(): out+=i.collectPrimitiveBases()
1404          return out          return out

class PrimitiveBaseStack(object):
def __init__(self,*items):
self.__prims=set()
for i in items:
self.__prims|=i.getPrimitives()
self.__prims=list(self.__prims)
self.__prims.sort()

def getGmshCommands(self,scaling_factor=1.):
out=""
for i in self.__prims:
out+=i.getGmshCommand(scaling_factor)+"\n"
return out

Legend:
 Removed from v.930 changed lines Added in v.931