Vead, issu des travaux de thèse d'Hugo Loi, EPI Maverick, permet de concevoir
des arrangements 2D de petits éléments géométriques afin d'obtenir des
textures vectorielles. L'approche cible les artistes techniques qui concevront
des textures à l'aide de scripts, basés sur des opérateurs de partition
(organisation globale de l'arrangement), de mapping (contrôle de
l'organisation locale des éléments) et de fusion (mélange de différents
arrangements).
Pour montrer le potentiel applicatif de cette méthode, des textures générées ont
été utilisées pour texturer des objets 3D et fabriquer via la découpeuse laser
de A4H divers objets usuels.
def CellsRandom(): density = (50 / 400000) props = IrregularProperties(density) part = RandomPartition(props,CROP_ADD_BOUNDARY) def draw_cell(face): tile = Nothing() for e in IncidentEdges(face): line = ToCurve(e) tile = Append(tile, line) return Scale(tile,0.7) txt = MapToFaces(draw_cell,part,DO_NOT_COMPUTE_INCIDENCE) square = StartDomain(2000) planarMapWithoutIncidence = txt(square) Add(planarMapWithoutIncidence) |
|
def Circles(density): # Uniform partition with given density props = IrregularProperties(density) part = UniformPartition(props,KEEP_OUTSIDE) circle = ImportSVG("data/circle.svg") # Mapper: place a circle in each face def face_to_circle(face): src_p = BBoxCenter(circle) dst_p = Centroid(face) return Scale(MatchPoint(circle,src_p,dst_p),Random(face,0.05,0.10,0)) return MapToFaces(face_to_circle,part) |
|
def ANGrid(): theta = pi / 4 width = 200 gridH = StripesProperties(theta,width) gridV = StripesProperties(theta+pi/2.0,width) part = GridPartition(gridH,gridV,KEEP_INSIDE) pattern = ImportElt("data/AN_g.svg",10) def face_to_pattern(face): return MatchFace(pattern,face) txt = MapToFaces(face_to_pattern, part) area = StartDomain(1000) planarMapWithoutIncidence = txt(area) Add(planarMapWithoutIncidence) |
|
def ANCoreMedaillon(): theta = pi / 4 width = 200 gridH = StripesProperties(theta,width) gridV = StripesProperties(theta+pi/2.0,width) SetFaceLabels(gridH,"h1","h2") SetFaceLabels(gridV,"v1","v2") part = GridPartition(gridH,gridV,KEEP_INSIDE) pattern = ImportElt("data/AN.svg",20) pattern_core = ImportElt("data/ANCore.svg",20) def vertex_to_pattern_core(face): rot = Random(face,-1,1,0) if(HasLabel(face,"h1") and HasLabel(face,"v1")): #h1v1 v = Centroid(face) return Rotate(MatchPoint(pattern_core, BBoxCenter(pattern_core),v),rot*pi/6) else: return Nothing() def face_to_pattern(face): src_c = PointLabeled(pattern,"bottom_start") dst_c = PointLabeled(pattern,"top_end") if(HasLabel(face,"h1")): if(HasLabel(face,"v1")): #h1v1 src_v = Location(IncidentVertices(face)[3]) #dst_v = Location(IncidentVertices(face)[0]) v = LocationAt(IncidentEdges(IncidentVertices(face)[0])[1],0.3) + LocationAt(IncidentEdges(IncidentVertices(face)[2])[0],0.3) else: #h1v2 src_v = Location(IncidentVertices(face)[1]) #dst_v = Location(IncidentVertices(face)[2]) v = LocationAt(IncidentEdges(IncidentVertices(face)[2])[0],0.55) + LocationAt(IncidentEdges(IncidentVertices(face)[2])[1],0.45) elif(HasLabel(face,"v1")): #h2v1 src_v = Location(IncidentVertices(face)[2]) #dst_v = Location(IncidentVertices(face)[1]) v = LocationAt(IncidentEdges(IncidentVertices(face)[3])[0],0.45) + LocationAt(IncidentEdges(IncidentVertices(face)[0])[1],0.55) else: #h2v2 src_v = Location(IncidentVertices(face)[0]) #dst_v = Location(IncidentVertices(face)[3]) v = LocationAt(IncidentEdges(IncidentVertices(face)[3])[0],0.4) + LocationAt(IncidentEdges(IncidentVertices(face)[2])[1],0.4) dst_v = v*0.5 return MatchPoints(pattern,src_c,dst_c,src_v,dst_v) txt = MapToFaces(face_to_pattern, part, DO_NOT_COMPUTE_INCIDENCE) txt_core = MapToFaces(vertex_to_pattern_core, part,DO_NOT_COMPUTE_INCIDENCE) area = StartDomain(2000) planarMapWithoutIncidence = txt(area) planarMapWithoutIncidence_core = txt_core(area) Add(planarMapWithoutIncidence) Add(planarMapWithoutIncidence_core) #txt = MapToFaces(face_to_pattern, part) #txt_core = MapToFaces(vertex_to_pattern_core, part) #final_txt = Union(txt, txt_core) #ExportSVG(final_txt,2000) |
|
def ANStarRot(): props = HexagonalProperties(1 / 22000) part = HexagonalPartition(props, KEEP_INSIDE) #pattern = ImportSVG("data/ANStar.svg") pattern = ImportElt("data/ANStar.svg",5) def face_to_pattern(face): return Scale(Rotate(MatchFace(pattern,face),pi/12.0),1.1) first_txt = MapToFaces(face_to_pattern, part, DO_NOT_COMPUTE_INCIDENCE) #ExportSVG(first_txt,1000) square = StartDomain(2000) planarMap = first_txt(square) Add(planarMap) |
|
def BubbleRandom(): density = (50 / 4000000) props = IrregularProperties(density) part = RandomPartition(props,KEEP_INSIDE) #pattern = ImportSVG("data/Bubble.svg") #to get unique pathes and be able to fill elements in inkscape #second argument is sampling, must be set according to pattern size pattern = ImportElt("data/Bubble.svg",10) def face_to_pattern(face): fsize = min(BBoxWidth(face), BBoxHeight(face)) size = fsize / BBoxWidth(pattern) return Scale(MatchFace(pattern,face),size*0.9) #with intersections computation #txt = MapToFaces(face_to_pattern, part) #ExportSVG(txt,2000) #to avoid intersections computation and then get whole elements to fill txt = MapToFaces(face_to_pattern, part, DO_NOT_COMPUTE_INCIDENCE) #instead of ExportSVG that crops stuff and then return empty because of missing incidences #won't draw external square square = StartDomain(2000) planarMapWithoutIncidence = txt(square) Add(planarMapWithoutIncidence) |
|
def SeventiesBig(): theta = pi/6 width = 350 # Grid partition with given width and orientation lines1 = StripesProperties(theta,width) lines2 = StripesProperties(theta+pi/2.0,width) grid_tex = GridPartition(lines1,lines2,KEEP_INSIDE) #square = ImportSVG("data/square.svg") square= ImportElt("data/square.svg",10) # Mapper: place a rounded square in each face def face_to_square(face): i = randint(0,3) v = (Centroid(face) - Location(IncidentVertices(face)[i]))*0.5 return Scale(Translate(MatchFace(square,face),v),0.9) # Return the texture genrated via the mapping operator txt = MapToFaces(face_to_square,grid_tex, DO_NOT_COMPUTE_INCIDENCE) area = StartDomain(2000) planarMapWithoutIncidence = txt(area) Add(planarMapWithoutIncidence) |
|
def Plush(): density = 9e-5 props = IrregularProperties(density) part = UniformPartition(props,KEEP_INSIDE) pattern = ImportSVG("data/plush.svg") def face_to_pattern(face): rot = Random(face,1,6,0) return Scale(Rotate(MatchFace(pattern,face),rot*pi/6),2) first_txt = MapToFaces(face_to_pattern, part) ExportSVG(first_txt,1600) |
|
def Stars(): props = HexagonalProperties(1 / 22000) part = HexagonalPartition(props, KEEP_OUTSIDE) pattern = ImportElt("data/Star.svg",10) def face_to_pattern(face): w = Random(face,1,6,0) return Rotate(MatchFace(pattern,face),w*pi/6) txt = MapToFaces(face_to_pattern, part,DO_NOT_COMPUTE_INCIDENCE) area = StartDomain(1000) planarMap = txt(area) Add(planarMap) |
|
def curves(theta,width): # Stripes partition with given width and orientation props = StripesProperties(theta,width) stripes = StripesPartition(props) line = ImportSVG("data/line6.svg") # Mapper: replace each edge by a curve def line_to_curve(edge): if IsBoundary(edge): return Nothing() src_c = PointLabeled(line,"start") dst_c = PointLabeled(line,"end") src_v = Location(SourceVertex(edge)) dst_v = Location(TargetVertex(edge)) return MatchPoints(line,src_c,dst_c,src_v,dst_v) # Return the texture genrated via the mapping operator return MapToEdges(line_to_curve,stripes) def Floor(): # Grid partition, including face labels size = 2000 lines1 = StripesProperties(0,200) lines2 = StripesProperties(pi/2,200) SetFaceLabels(lines1,"h1","h2") SetFaceLabels(lines2,"v1","v2") grid_tex = GridPartition(lines1,lines2,KEEP_OUTSIDE) # Mapper: creates stripes in each face def face_to_stripes(face): width = BBoxWidth(face)/Random(face,4,6,0) theta = 0 if((HasLabel(face,"h1") and HasLabel(face,"v1")) or (HasLabel(face,"h2") and HasLabel(face,"v2"))): theta = pi/2 #return StripesPartition(lines)(face) return curves(theta, width)(face) # Mapping operator tiled_tex = MapToFaces(face_to_stripes,grid_tex) # Final texture ExportSVG(tiled_tex,size) |
|
def wood_curves(theta,width): # Stripes partition with given width and orientation props = StripesProperties(theta,width) stripes = StripesPartition(props) line = ImportSVG("data/wood_line.svg") # Mapper: replace each edge by a curve def line_to_curve(edge): if IsBoundary(edge): return Nothing() src_c = PointLabeled(line,"start") dst_c = PointLabeled(line,"end") src_v = Location(SourceVertex(edge)) dst_v = Location(TargetVertex(edge)) return MatchPoints(line,src_c,dst_c,src_v,dst_v) # Return the texture genrated via the mapping operator return MapToEdges(line_to_curve,stripes) def Wood(): size = 4000 linesV = StripesProperties(pi/2,200) linesH = StripesProperties(0,2000) part = GridPartition(linesV, linesH, CROP) # Mapper: creates stripes in each face def stripes_to_face(face): width = 10*randint(3,10) return wood_curves(pi/2,width)(face) # Mapping operator tex = MapToFaces(stripes_to_face ,part) # Final texture ExportSVG(tex,size) |
|
def blobs(theta,width): # Grid partition with given width and orientation lines1 = StripesProperties(theta,width) lines2 = StripesProperties(theta+pi/2.0,width) grid_tex = GridPartition(lines1,lines2,KEEP_INSIDE) square = ImportSVG("data/blob.svg") # Mapper: place a rounded square in each face def face_to_blob(face): return Scale(Rotate(MatchFace(square,face),Random(face,0.0,2.0*pi,1)),0.6) # Return the texture genrated via the mapping operator return MapToFaces(face_to_blob,grid_tex) def curves_elt(theta,width): # Stripes partition with given width and orientation props = StripesProperties(theta,width) stripes = StripesPartition(props) line = ImportElt("data/line6.svg",10) # Mapper: replace each edge by a curve def line_to_curve(edge): if IsBoundary(edge): return Nothing() src_c = PointLabeled(line,"start") dst_c = PointLabeled(line,"end") src_v = Location(SourceVertex(edge)) dst_v = Location(TargetVertex(edge)) return MatchPoints(line,src_c,dst_c,src_v,dst_v) # Return the texture genrated via the mapping operator return MapToEdges(line_to_curve,stripes,DO_NOT_COMPUTE_INCIDENCE) def circles_elt(density): # Uniform partition with given density props = IrregularProperties(density) part = UniformPartition(props,KEEP_OUTSIDE) circle = ImportElt("data/circle.svg",10) # Mapper: place a circle in each face def face_to_circle(face): src_p = BBoxCenter(circle) dst_p = Centroid(face) return Scale(MatchPoint(circle,src_p,dst_p),Random(face,0.05,0.10,0)) return MapToFaces(face_to_circle,part,DO_NOT_COMPUTE_INCIDENCE) def Wallpaper(): txt_frame = blobs(pi/3,400) txt_stripes = curves_elt(pi/6,20) txt_circles = circles_elt(9e-5) txt_in = Inside(txt_circles, txt_frame, CROP_ADD_BOUNDARY) txt_out = Outside(txt_stripes, txt_frame, CROP_ADD_BOUNDARY) txt = Union(txt_in, txt_out) area = StartDomain(4000) planarMapWithoutIncidence = txt(area) Add(planarMapWithoutIncidence) |
|
![]() ![]() |
![]() ![]() |
![]() ![]() |
![]() ![]() |
From random bubbles texture to furniture
From random irregular cells texture to trimmed lampshade