Catmull–Clark subdivision surface: Difference between revisions

m
Automated syntax highlighting fixup (second round - minor fixes)
m (syntax highlighting fixup automation)
m (Automated syntax highlighting fixup (second round - minor fixes))
Line 1:
{{task|3D}}[[Category:Graphics algorithms]]{{requires|Graphics}}
[[Category:Geometry]]
{{task|3D}}{{requires|Graphics}}
Implement the Catmull-Clark surface subdivision ([[wp:Catmull–Clark_subdivision_surface|description on Wikipedia]]), which is an algorithm that maps from a surface (described as a set of points and a set of polygons with vertices at those points) to another more refined surface. The resulting surface will always consist of a mesh of quadrilaterals.
 
Line 42 ⟶ 44:
 
For edges and vertices not next to a hole, the standard algorithm from above is used.
 
=={{header|C}}==
[[file:catmull-C.png|center]]
Only the subdivision part. The [[Catmull–Clark_subdivision_surface/C|full source]] is way too long to be shown here. Lots of macros, you'll have to see the full code to know what's what.
<syntaxhighlight lang="c">vertex face_point(face f)
{
int i;
Line 139 ⟶ 140:
return nm;
}</syntaxhighlight>
 
=={{header|Go}}==
{{trans|Python}}
Line 146:
 
See the original version for full comments.
<syntaxhighlight lang="go">package main
 
import (
Line 487:
[ 4 23 13 20]
</pre>
 
=={{header|Haskell}}==
<syntaxhighlight lang="haskell">{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE ScopedTypeVariables #-}
 
Line 853 ⟶ 852:
(22,[24,15,5,8])
(23,[22,8,5,7])</pre>
 
=={{header|J}}==
 
<syntaxhighlight lang="j">avg=: +/ % #
 
havePoints=: e."1/~ i.@#
Line 882 ⟶ 880:
Example use:
 
<syntaxhighlight lang="j">NB.cube
points=: _1+2*#:i.8
mesh=: 1 A."1 I.(,1-|.)8&$@#&0 1">4 2 1
Line 915 ⟶ 913:
│ │ 0.555556 0.555556 0.555556│
└──────────┴─────────────────────────────┘</syntaxhighlight>
 
=={{header|Julia}}==
<syntaxhighlight lang="julia">using Makie, Statistics
 
# Point3f0 is a 3-tuple of 32-bit floats for 3-dimensional space, and all Points are 3D.
Line 1,063 ⟶ 1,060:
println("Press Enter to continue", readline())
</syntaxhighlight>
 
=={{header|Mathematica}}/{{header|Wolfram Language}}==
This implementation supports tris, quads, and higher polys, as well as surfaces with holes.
The function relies on three externally defined general functionality functions:
 
<syntaxhighlight lang=Mathematica"mathematica">subSetQ[large_,small_] := MemberQ[large,small]
subSetQ[large_,small_List] := And@@(MemberQ[large,#]&/@small)
 
Line 1,083 ⟶ 1,079:
 
 
<syntaxhighlight lang=Mathematica"mathematica">CatMullClark[{Points_,faces_}]:=Block[{avgFacePoints,avgEdgePoints,updatedPoints,newEdgePoints,newPoints,edges,newFaces,weights,pointUpdate,edgeUpdate,newIndex},
edges = DeleteDuplicates[Flatten[Partition[#,2,1,-1]&/@faces,1],Sort[#1]==Sort[#2]&];
avgFacePoints=Mean[Points[[#]]] &/@ faces;
Line 1,113 ⟶ 1,109:
 
The implimentation can be tested with polygons with and without holes by using the polydata
<syntaxhighlight lang=Mathematica"mathematica">{points,faces}=PolyhedronData["Cube",{"VertexCoordinates","FaceIndices"}];
 
Function[iteration,
Line 1,121 ⟶ 1,117:
 
For a surface with holes the resulting iterative subdivision will be:
<syntaxhighlight lang=Mathematica"mathematica">faces = Delete[faces, 6];
Function[iteration, Graphics3D[
(Polygon[iteration[[1]][[#]]] & /@ iteration[[2]])
Line 1,128 ⟶ 1,124:
 
This code was written in Mathematica 8.
 
=={{header|Nim}}==
{{trans|Go}}
{{trans|Python}}
<syntaxhighlight lang=Nim"nim">import algorithm
import tables
 
Line 1,542 ⟶ 1,537:
[ 2, 20, 13, 17]
[ 4, 23, 13, 20]</pre>
 
=={{header|OCaml}}==
{{incorrect|OCaml|wrong output data}}
Line 1,552 ⟶ 1,546:
In the [[Catmull–Clark subdivision surface/OCaml|sub-page]] there is also a program in OCaml+OpenGL which displays a cube subdivided 2 times with this algorithm.
 
<syntaxhighlight lang="ocaml">open Dynar
 
let add3 (x1, y1, z1) (x2, y2, z2) (x3, y3, z3) =
Line 1,691 ⟶ 1,685:
Another implementation which should work with holes, but has only been tested on a cube
{{works with|OCaml|4.02+}}
<syntaxhighlight lang=OCaml"ocaml">type point = { x: float; y : float; z : float }
let zero = { x = 0.0; y = 0.0; z = 0.0 }
let add a b = { x = a.x+.b.x; y = a.y+.b.y; z = a.z+.b.z }
Line 1,800 ⟶ 1,794:
Face: (0.7500, 0.0000, 0.7500) (0.5556, -0.5556, 0.5556) (0.0000, -0.7500, 0.7500) (0.0000, 0.0000, 1.0000)
}</pre>
 
=={{header|Phix}}==
{{trans|Go}}
<!--<syntaxhighlight lang=Phix"phix">(phixonline)-->
<span style="color: #000080;font-style:italic;">-- demo\rosetta\Catmull_Clark_subdivision_surface.exw</span>
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span>
Line 2,074 ⟶ 2,067:
{ 4,23,13,20}}
</pre>
 
=={{header|Python}}==
<syntaxhighlight lang="python">
"""
 
Line 2,634 ⟶ 2,626:
graph_output(output_points, output_faces)
</syntaxhighlight>
 
=={{header|Rust}}==
{{trans|Python}}
<syntaxhighlight lang=Rust"rust">
pub struct Vector3 {pub x: f64, pub y: f64, pub z: f64, pub w: f64}
 
Line 2,922 ⟶ 2,913:
}
</syntaxhighlight>
 
=={{header|Tcl}}==
This code handles both holes and arbitrary polygons in the input data.
<syntaxhighlight lang="tcl">package require Tcl 8.5
 
# Use math functions and operators as commands (Lisp-like).
Line 3,051 ⟶ 3,041:
 
<center>[[File:Tcl-Catmull.png]]</center>
 
=={{header|Wren}}==
{{trans|Go}}
Line 3,058 ⟶ 3,047:
{{libheader|Wren-math}}
{{libheader|Wren-fmt}}
<syntaxhighlight lang="ecmascript">import "/dynamic" for Tuple, Struct
import "/sort" for Sort
import "/math" for Int
Line 3,383 ⟶ 3,372:
[ 4 23 13 20]
</pre>
 
[[Category:Geometry]]
10,327

edits