Lecture 8

Meshes
• polygonal soup
Meshes
– polygons specified one-by-one with no explicit information on
shared vertices
• polygonal nonmanifold
– connectivity
information is provided (which vertices are shared)
• polygonal
soup
Lecture 8
Mesh Data Structures
Subdivision
no restrictions on connections between polygons
– polygons specified one-by-one with no explicit information on
• polygonal
manifold
shared vertices
–
no
edge
is
shared by more than two polygons; the faces
• polygonal nonmanifold
adjacent to a vertex form a single ring (incomplete ring for
– connectivity
information is provided (which vertices are shared)
boundary vertices)
no restrictions on connections between polygons
• triangle manifold
• polygonal manifold
– in addition, all faces are triangles
– no edge is shared by more than two polygons; the faces
adjacent to a vertex form a single ring (incomplete ring for
boundary vertices)
• triangle manifold
– in addition, all faces are triangles
Meshes
faces, vertices, edges
• polygonal soup
– polygons specified one-by-one with no explicit information on
shared vertices
• polygonal nonmanifold
– connectivity information is provided (which vertices are shared)
no restrictions on connections between polygons
• polygonal manifold
– no edge is shared by more than two polygons; the faces
adjacent to a vertex form a single ring (incomplete ring for
boundary vertices)
• triangle manifold
– in addition, all faces are triangles
Mesh elements
http://www.c3.hu/docs/maya/UserGuide/ModelingPoly/PolyIntro.html
Mesh elements
Each mesh element can have information
associated with it; typical mesh operations
faces, vertices, edges
involve visiting (traversing) all vertices, faces, or edges
Each mesh element can have information
associated with it; typical mesh operations
involve visiting (traversing) all vertices, faces, or edges
f i1 i2 i3 … in
where i1.. in, are vertex indices; the indices are obtained by
numbering all vertices sequentially as they appear in a
file
Mesh descriptions
• OBJ format
each line defines an element (vertex or face); first
character defines the type
Vertex:
v x, y z
Face with n vertices:
f i1 i2 i3 … in
Types of Mesh Operations
Traversals
1. Iterate over all elements of a certain type,
visiting each only once.
2. Iterate over all elements (faces, edges,
vertices) adjacent to an element
where i1.. in, are vertex indices; the indices are obtained by
numbering all vertices sequentially as they appear in a
file
Note:Vertex indices start at 1, not 0.
Mesh operations
• Types of mesh operations
Types of Mesh Operations
– traversals go over all elements of certain type
– collect adjacent elements (e.g. all neighbors of a vertex)
– refinement
Mesh operations
Refinement
– edge
flipsof mesh operations
• Types
– traversals go over all elements of certain type
Flips
–Edge
collect
adjacent elements (e.g. all neighbors of a vertex)
– refinement
– face
Face Addition/
addition/deletion
– Deletion
edge flips
– face Face
merge
Merge
– face
addition/deletion
– face merge
Types of Mesh Operations
Traversals
1. Iterate over all elements of a certain type,
visiting each only once.
2. Iterate over all elements (faces, edges,
vertices) adjacent to an element
2
3
1
6
4
5
Types of Mesh Operations
A simple mesh representation
One-to-one correspondence with OBJ
Traversals
1. Iterate over all elements of a certain type,
visiting each only once.
2. Iterate over all elements (faces, edges,
vertices) adjacent to an element
1
array of vertices
2 arrays for faces
each face is a list of vertex indices
enumerated clockwise
counter clockwise
4
5
4
0
1
Types of Mesh Operations
Traversals
1. Iterate over all elements of a certain type,
visiting each only once.
2. Iterate over all elements (faces, edges,
vertices) adjacent to an element
3
1
2
4
starting indices of face
vertex lists
6
2
3
0
0
2
3
3
2
4
vertex indices of
all faces
Traversal operations
Complexity of traversal operations w/o additional data
structures as function of the number of vertices,
assuming constant vertex/face ratio
iterate over
collect
adjacent
V
E
F
V
quadratic quadratic linear
E
quadratic quadratic linear
F
quadratic quadratic linear
quadratic
Euler’s Formula : |V|+|F|-|E| = 2-2G
Traversal operations
Most operations such as collecting all adjacent faces for a
vertex are slow, because the connectivity information is
not explicit: one needs to search the whole list of faces
to find faces with a given vertex; if neighbors are
encoded explicitly this can be done in const. time
Traversing faces sharing a vertex
Assuming a mesh without boundary:
fstart = v->face;
f = fstart;
do {
... // perform operations with *f
// assume that vertex i is across edge
if (f->vertex[0]== v)
f = f->face[1]; // crossing edge #1
else if (f->v[1] == v)
f = f->face[2]; // crossing edge #2
else
f = f->face[0]; // crossing edge #0
} while( f ! = fstart);
i
vert. 0 - vert. 2
vert. 1 - vert. 0
vert. 2 - vert. 1
Similar for edges and vertices.
All such operations can be done in const. time per vertex/face/edge.
Face-based mesh representation
Useful primarily for triangle or quad. meshes
Triangle meshes:
struct Face {
Face* face[3]; // pointers
//to neighbors
Vertex* vertex[3];
}
struct Vertex {
Face* face; // pointer to a triangle
//adjacent to the vertex
}
(not really necessary, can refer to vertices using a handle (Face ptr,
vertex index)
4
Half-edge data structure
• General manifold polygonal meshes
– Polygons have variable number of vertices
variable size;
– data structures based on faces are inconvenient and
inefficient.
• Solution: use edge-based structures (winged
edge, half-edge).
– Half-edge is currently most common
– Each edge = 2 half edges; can be interpreted either
as
directed edge or face-edge pair
Constructing a Mesh Data Structure
Half-edge data structure
struct HalfEdge {
Vertex* vertex; // the head vertex the
//half edge is pointing to
Face* face;
// if data stored in faces
HalfEdge* next; // next halfedge in the face
// on the left
HalfEdge* sym; // the other half edge for
//the same edge
}
struct Vertex {
HalfEdge* halfedge; // one of the half edges
// starting at the vertex
}
list of vertices and triangles(vertices in ccw order)
• Given:mesh
Face-based
representation
Construct a face based structure.
•
Useful primarily for triangle or quad. meshes
Triangle meshes:
struct Face {
Face* face[3]; // pointers
//to neighbors
Vertex* vertex[3];
}
F.v[1]
F.f[0]
F.f[2]
F
F.v[2]
• Define:
F.v[0]
F.f[1]
struct Vertex •{ next(i) = (i+1)%3
Face* face; •//prev(i)
pointer
to a triangle
= (i+2)%3
//adjacent to the vertex
• other(i,j) = k , where i,j,k in [0,1,2], i!=j and k!=i & k!=j
}
(not really necessary, can refer to vertices using a handle (Face ptr,
vertex index)
Traversal operations
Vertices adjacent to a vertex v, mesh without
boundary
he = v->halfedge;
do {
he = he->sym->next;
... // perform operations with
// he->vertex
} while (he != v->halfedge)
No “if” statements.
6
Constructing a Mesh Data Structure
EdgeMap : A map (associative array) from edges to faces
directed edge : two integers [i,j]
! i,j in {1,...|V|} : vertex indices.
faces : two integers [m,k]
! m in {1,..., |F|}: face index
! k in {0,1,2}
j
i
edge k
Traversing faces sharing a vertex
face m
Assuming a mesh without boundary:
Use C++ STL map !
fstart = v->face;
f = fstart;
do {
... // perform operations with *f
// assume that vertex i is across edge i
if (f->vertex[0]== v)
f = f->face[1]; // crossing edge #1 vert. 0 - vert. 2
else if (f->v[1] == v)
Constructing a Mesh Data Structure
Pseudo code
for each face
create face structure f, init neighbors to 0
for each tri vertex i=0,1,2
edgemap[f.v[i],f.v[next(i)]] =[f, other(i,next(i))]
endfor
endfor
for each entry[i,j] of edgemap
[f1,e1] = edgemap[i,j]
[f2,e2] = edgemap[j,i]
if f2!=0
f1.f[e1] = f2;
f2.f[e2] = f1;
endif
endfor
4
3
1
2
124
132
234
143
423
Constructing a Half Edge Based
Mesh Data Structure
Constructing a Half Edge Based
Mesh Data Structure
Step 2: Fill edge map
for each face f[i] with n vertices [v1 v2 ... vn]
f[i].he = [v1,v2]
for each vertex vj of face
if vj.he != 0 vj.he = [vj vj+1]
endfor
for each halfedge hej =[vkvm]of face f[i]
hej.face = f[i]
hej.next = next halfedge hej+1 of face
hej.vertex = vm
edgemap(vk,vm) = hej
endfor
endfor
Constructing a Half Edge Based
Mesh Data Structure
Given: List of vertices, list of faces (vertices in ccw order)
Step 3:
Step 1: Create arrays of vertices, faces, and half-edges &
initialize all pointers to zero.
Go over all entries of edge map.
If both edgemap(i,j) and edgemap(j,i) exist
! fill sym fields for both s.t. they point to each other
Half-edges : assign one to every consecutive vertex pair in
each face list
f: [v1 v2 v3 ... vn]
he: [v1v2], [v2v3],...,[vn-1vn]
Properties
Subdivision Surfaces
• Arbitrary Topology - no patch, genera/vertex
valances
• Scalability - level of detail, hardware
• Uniformity of Representation - meshes to splines
• Numerical Stability - good for FEM
• Code Simplicity
From www.pixar.com
E.T. ‘06
Subdivision
The Idea
• Subdivision = Repeated Refinement
• A little bit of history ...
E.T. ‘06
!
Basic ideas in late ‘40s.(deRham)
!
‘70s, Catmull-Clark, Doo-Sabin
!
‘95 Reif - Smoothness
!
Increased complexity to multiresolution
!
Renderman ==> Geri’s Game(1997)
finite resolution!
E.T. ‘06
regular vertex insertion
“quadrisection”
http://www.smlib.com/Manual/SubSrf.html
© 1998-2006 Solid Modeling Solutions and IntegrityWare, Inc.
1/8
p(t) =
∞
!
pi Bi (t)
3/4
1/8
i=−∞
1/2
1/2
E.T. ‘06
1/2 1/2
1/8 3/4 1/8
+ local definition
Even Rule
• Efficiency & Simplicity
E.T. ‘06
E.T. ‘06
Subdivision Schemes
Catmull-Clark
Odd Rules
Subdivision Schemes
1/2 1/2
1/8 3/4 1/8
1/16
3/8+
(cos!)/4
1/16
Loop
1/16
3/8(cos!)/4
1/16
Biermann, et al. 2001
E.T. ‘06
Loop Scheme
• Based on 3-directional quartic box splines
E.T. ‘06
Reduction to a
Triangular Mesh
E.T. ‘06
Loop Scheme :
Boundary
Boundary
1/8
1/4+
cos!/4
Biermann, et al. 2001
E.T. ‘06
1/4cos!/4
1/8
Classification of
Subdivision Schemes
• Type of refinement: Face split vs.Vertex Split
• Type of generated mesh:Triangular vs. Quad
E.T. ‘06
Classification of
Subdivision Schemes
split vs.Vertex Split
• Type of refinement: Face
(Primal)
(Dual)
E.T. ‘06
Classification of
Subdivision Schemes
• Type of refinement: Face split vs.Vertex Split
• Type of generated mesh:Triangular vs. Quad
vs.
Interpolating
• Approximating
E.T. ‘06
Classification of
Subdivision Schemes
Classification of
Subdivision Schemes
• Type of refinement: Face split vs.Vertex Split
• Type of generated mesh:Triangular vs. Quad
• Approximating vs. Interpolating
• Smoothness of limit surface (for reg. meshes)
• Type of refinement: Face split vs.Vertex Split
• Type of generated mesh:Triangular vs. Quad
• Approximating vs. Interpolating
• Smoothness of limit surface (for reg. meshes)
C 1, C 2
C2
[+ Stationary vs. Non-stationary]
E.T. ‘06
E.T. ‘06
Classification of
Subdivision Schemes
Examples
• Type of refinement: Face split vs.Vertex Split
• Type of generated mesh:Triangular vs. Quad
• Approximating vs. Interpolating
• Smoothness of limit surface (for reg. meshes)
C2
E.T. ‘06
Catmull-Clark
, E.T. ‘06
Loop
Loop
Butterfly
Catmull-Clark
Doo-Sabin
Figure 4.20: Different subdivision schemes produce similar results for smooth meshes.
SIGGRAPH 2000
course notes
E.T. ‘06
SIGGRAPH 2000
course notes
Initial mesh
Loop
Catmull-Clark
Catmull-Clark,after
triangulation
Figure 4.21: Applying Loop and Catmull-Clark subdivision schemes to a model of a chess rook. The
initial mesh is shown on the left. Before the Loop scheme was applied, the mesh was triangulated.
Catmull-Clark was applied to the original quadrilateral model and to the triangulated model; note the
substantial difference in surface quality.
distinction is already apparent in the case k = 4, but becomes very noticeable for k = 9.
Figure 4.23 provides a similar comparison showing the effect of different dual quadrilateral subdivision schemes when the control polyhedron is a simple cube (compare to 4.18). Notice the increasing
Loop
topological
Butterfly
geometric
Catmull-Clark
Doo-Sabin
SIGGRAPH 2000
course notes
Figure 4.19: Results of applying various subdivision schemes to a tetrahedron.
4.8.1 Comparison of Dual Quadrilateral Schemes
Dual quadrilateral schemes are the only class of schemes with several members: Doo-Sabin, Midedge,
87
Topological Updates
Step 1: Split all edges in any order adding a vertex on each.
Split all adjacent triangles into two.
Step 2: Flip all edges that connect an old vertex
with a new one