ポリゴンメッシュ (1) - データ構造とレンダリングに必要な計算 -

Slides:



Advertisements
Similar presentations
シミュレーション演習 G. 総合演習 ( Mathematica 演 習) システム創成情報工学科 テキスト作成: 藤尾 光彦 講義担当: 尾下 真樹.
Advertisements

初年次セミナー 第13回 2次元グラフィックス(1).
今回の内容 シェーディング マッピング 光の効果の表現 表面の素材の表現 オブジェクトの形状表現 光の効果の表現 表面の素材の表現
豊洲 304教室 15 JULY コンピュータグラフィックス 2008年度版.
情報処理演習 (9)グラフィックス システム科学領域 日浦 慎作.
初年次セミナー 第14回 2次元グラフィックス(2).
プログラミング演習3 李 亜民クラス 第2回 ラスタライズ.
CGアニメーションの原理 基本技術 対象物体の動きや変形の設定方法 レンダリング技術
豊中高校土曜講座「数学セミナー2003」 プラトン多面体の数学 なぜ正多面体は5種類しかないのか 大阪府立豊中高等学校 深川 久.
今日の内容 前回の演習の復習 前回の復習 ポリゴンの描画方法(復習) 基本オブジェクトの描画 ポリゴンモデルの描画 演習課題.
第13回構造体.
ファーストイヤー・セミナーⅡ 第8回 データの入力.
基礎プログラミングおよび演習 第9回
平成23年8月 情報学群 岡田 守 このスライドは, 前川佳徳編著による「コンピュータグラフィックス」(オーム社)を基に作成されている.
地理情報システム論 第3回 コンピュータシステムおける データ表現(1)
形状モデリングにおいて,任意の自由曲面を定義する必要のある場合がある.自由曲面の表現法について説明する.
レンダリングにおいて写実性を高めるための処理である,シェーディングとテクスチャマッピングについて述べる.
第3回:ボールを上下に動かそう! (オブジェクトの移動、一次元)
第11回 オブジェクト(ベクトル,頂点,面)のクラス化とフラットシェーディング
3次元での回転表示について.
精密工学科プログラミング基礎Ⅱ 第3回資料 今回の授業で習得してほしいこと: 2次元配列の使い方 (前回の1次元配列の復習もします.)
ラスタデータの処理 -微分とその応用- 東京大学 精密工学専攻 大竹豊 資料および授業の情報は :
CGと形状モデリング 授業資料 長井 超慧(東京大学)
C 言語について 補足資料 資料および授業の情報は :
基礎プログラミング演習 第10回.
コンピュータグラフィックスS 第13回 第13回 演習(4):シェーディング、マッピング システム創成情報工学科 尾下 真樹
グラフィックス、その1 色の表示 フォントを変えて文字を表示 直線、四角形、楕円形の描画 円弧の描画 多角形の描画
3D散歩ゲーム 08A2043 谷口盛海 種田研究室.
CGと形状モデリング 授業資料 長井 超慧(東京大学)
CGと形状モデリング 授業資料 1,2限: 大竹豊(東京大学) 3,4限: 俵 丈展(理化学研究所)
プログラミング応用 printfと変数.
グラフアルゴリズムの可視化 数理科学コース 福永研究室 高橋 優子 2018/12/29.
電界中の電子の運動 シミュレータ作成 精密工学科プログラミング基礎 資料.
OpenGLを使ったプログラム作成 澤見研究室
CAD曲線 (ベジエ曲線・Bスプライン曲線)
精密工学科プログラミング基礎 第10回資料 (12/18実施)
点・線分・多角形を レンダリングする方法 東京大学 精密工学専攻 大竹豊.
OpenGLライブラリを用いた3次元フラクタルの描画
CGと形状モデリング 授業資料 1,2限: 大竹豊(東京大学) 3,4限: 俵 丈展(理化学研究所)
3次元での回転表示について.
デジタル画像とC言語.
可視面・不可視面の判定方法と隠れ面(不可視面)の消去法について述べる.
CAD曲面 東京大学 精密工学専攻 大竹豊 資料および授業の情報は :
DirectX勉強会 第2回.
ポリゴンメッシュ (2) - 変形と簡略化- 東京大学 精密工学専攻 大竹豊 資料および授業の情報は :
CGと形状モデリング 授業資料 1,2限: 大竹豊(東京大学) 3,4限: 俵 丈展(理化学研究所)
計算機プログラミングI 第5回 配列 文字列(Stringクラス) mainの引数 配列の利用例
SystemKOMACO Jw_cad 基本操作(3) Ver.1
プロジェクト演習Ⅳ インタラクティブゲーム制作 プログラミング4
資料 線型変換のイメージ 固有値、固有ベクトル 平賀譲(209研究室) 資料
オブジェクト指向言語論 第六回 知能情報学部 新田直也.
プログラミング言語論 第六回 理工学部 情報システム工学科 新田直也.
精密工学科プログラミング基礎Ⅱ 第5回資料 今回の授業で習得してほしいこと: 構造体 (教科書 91 ページ)
アルゴリズムとプログラミング (Algorithms and Programming)
コンピュータグラフィックス 実習3: 光線追跡法
地理情報システム論(総)/ 国民経済計算論(商)
地理情報システム論 第4回 コンピュータシステムおける データ表現(2)
アルゴリズムとデータ構造1 2009年6月15日
バネモデルの シミュレータ作成 精密工学科プログラミング基礎 資料.
精密工学科プログラミング基礎 第7回資料 (11/27実施)
点・線分・多角形を レンダリングする方法 東京大学 精密工学専攻 大竹豊.
アルゴリズムとデータ構造 2010年6月17日
ソフトウェア工学 知能情報学部 新田直也.
精密工学科プログラミング基礎Ⅱ 第2回資料 今回の授業で習得してほしいこと: 配列の使い方 (今回は1次元,次回は2次元をやります.)
ベクトル関数の回転(カール、ローティション)
プログラミング基礎a 第5回 C言語によるプログラミング入門 配列と文字列
プログラミング入門2 第5回 配列 変数宣言、初期化について
CGと形状モデリング 授業資料 1,2限: 大竹豊(東京大学) 3,4限: 俵 丈展(理化学研究所)
オブジェクト指向言語論 第六回 知能情報学部 新田直也.
計算機プログラミングI 第5回 2002年11月7日(木) 配列: 沢山のデータをまとめたデータ どんなものか どうやって使うのか
Presentation transcript:

ポリゴンメッシュ (1) - データ構造とレンダリングに必要な計算 - 東京大学 精密工学専攻 大竹豊 資料および授業の情報は : http://www.den.t.u-tokyo.ac.jp/ohtake/GeomPro/

今回の授業の目的 ポリゴンメッシュに関して以下を学ぶ 計算機上でのデータ構造 表示などに必要な微分値の計算

話の流れ ポリゴンメッシュとは? レンダリングの方法 フラットシェーディング スムースシェーディング ラプラシアン平滑化

ポリゴンメッシュとは? 多角形(ポリゴン)の集まりにより表面を表す コンピュータグラフィクスではよく用いられる 三角形メッシュ 産業応用でも近年は利用されつつある 三角形メッシュ 四辺形メッシュ

なぜポリゴンを使うのか? 単純かつ柔軟だから 沢山のポリゴンで 複雑な形状を表現できる

三角形メッシュ 計算機で扱うのに簡単 全ての多角形は必ず三角形群へ分割できる 三角形の載る平面は一つだけ

用語の意味 頂点 辺 面 (又は 三角形)

同じ頂点座標が バラバラにあるので扱いにくい 推称されないメッシュの表現の方法 多角形の頂点座標をそのままならべる (レンダリングするだけなら便利) 四面体 (4 個の三角形) 同じ頂点座標が バラバラにあるので扱いにくい (0.0, 0.0, 0.0) (1.0, 0.0, 0.0) (0.0, 0.0, 1.0) (0.0, 0.0, 0.0) (0.0, 0.0, 1.0) (0.0, 1.0, 0.0) (0.0, 0.0, 0.0) (0.0, 1.0, 0.0) (1.0, 0.0, 0.0) (1.0, 0.0, 0.0) (0.0, 1.0, 0.0) (0.0, 0.0, 1.0)

推称されるメッシュの表現方法 頂点座標のリスト + 面を構成する頂点番号列のリスト 頂点 三角形 0: (0.0, 0.0, 0.0) 頂点座標のリスト + 面を構成する頂点番号列のリスト 3 頂点 三角形 2 0: (0.0, 0.0, 0.0) 1: (1.0, 0.0, 0.0) 2: (0.0, 1.0, 0.0) 3: (0.0, 0.0, 1.0) 0 1 3 0 3 2 0 2 1 1 2 3 1

8面体の例 8個の三角形 6個の頂点 0 1 2 1 3 2 3 4 2 4 0 2 0 5 1 1 5 3 3 5 4 4 5 0 0: (1.0, 0.0, 0.0) 1: (0.0, 1.0, 0.0) 2: (0.0, 0.0, 1.0) 3: (-1.0, 0.0, 0.0) 4: (0.0, -1.0, 0.0) 5: (0.0, 0.0, -1.0) 2 3 4 1 5

メッシュデータを記述したファイル 頂点座標と三角形の頂点番号のリスト この授業での独自フォーマットです (業界標準は : STL, OBJ, PLY など) 6 8 1.0 0.0 0.0 0.0 1.0 0.0 0.0 0.0 1.0 -1.0 0.0 0.0 0.0 -1.0 0.0 0.0 0.0 -1.0 0 1 2 1 3 2 3 4 2 4 0 2 0 5 1 1 5 3 3 5 4 4 5 0 頂点と三角形の数 頂点座標 このようにファイルに 記述されており プログラムから 読み込まれる 三角形の 頂点番号のリスト 八面体のメッシュが記述されたファイル

C++ での配列 (*マーク版) 配列のサイズが変数の時に使う 1次元配列で 長さが変数の場合 2次元配列で 縦の長さのみ変数の場合 宣言 ( A[?] という意味) 宣言 ( V[?][3] という意味) float *A; float (*V)[3]; サイズを決定 (N はint型の変数) サイズを決定 (N はint型の変数) A = new float[N]; V = new float[N][3]; 使い方は普通の配列と同じ 使い方は普通の2次元配列と同じ A[0] = 20; A[1] = 30; … V[0][0] = 20; V[0][1] = 30; … 使い終わったら消す 使い終わったら消す delete[] A; delete[] V;

C++ でのデータ構造 頂点座標 (x,y,z)の 2次元配列 サイズ : [頂点数][3] int verN; float (*ver)[3]; int triN; int (*tri)[3]; void allocateArrays() { ver = new float[verN][3]; tri = new int[triN][3]; } 三角形の頂点番号 の2次元配列 サイズ : [三角形数][3] 配列のメモリを 確保する

三角形を レンダリング ( 3fv の “v” は ベクトルの v) OpenGL による描画 void drawMesh() { glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); for(int i=0; i<triN; i++) { int* t = tri[i]; glBegin(GL_POLYGON); glVertex3fv( ver[ t[0] ] ); glVertex3fv( ver[ t[1] ] ); glVertex3fv( ver[ t[2] ] ); glEnd(); } 辺を線分で 描くモード 三角形を レンダリング ( 3fv の “v” は ベクトルの v)

課題 1 prog3-1 を使う 以下の操作を確認せよ 左ドラッグ:回転 右ドラッグ:拡大・縮小 真中ドラッグ:平行移動 “main” 関数中 (一番下) で呼び出される 関数“readMesh” の引数を変えることにより フォルダ “data” の下にあるメッシュファイル を読み込んで表示してみよ ピラミッドの形を表す メッシュファイルを作成せよ

話の流れ ポリゴンメッシュとは? レンダリングの方法 フラットシェーディング スムースシェーディング ラプラシアン平滑化

オブジェクトの光の反射特性 Phong の近似モデル 拡散反射 鏡面反射 環境反射 光の方向に 面が垂直だと大 光の方向に   面が垂直だと大 鏡面反射 光の反射方向 と視線方向が近いと大 環境反射 定数 全方位への反射 光源は手前 てかてか度 照明と関係ない色

Phong モデル 反射を決めるのは、形状側では位置と法線のみ 光源の数だけ以下の値を足す 光源 視点 法線 曲面 接平面 最も鏡面反射が 強い方向 曲面 接平面

フラットシェーディング 法線は三角形が載る平面の法線 各三角形が同じ色で表示される 光源 視点 法線 メッシュ

三角形の法線の計算法 2つの辺の外積を正規化したベクトル 3つの頂点番号は、時計と反対回りに並んでいる 1. 外積 2. 正規化

法線計算の計算機実装 宣言とメモリの確保 法線の計算ルーチン float (*norT)[3]; norT = new float[triN][3]; 法線の計算ルーチン for(int i=0; i<triN; i++) { int* t = tri[i]; float* A = ver[ t[0] ]; float* B = ver[ t[1] ]; float* C = ver[ t[2] ]; float cx = ??; float cy = ??; float cz = ??; float l = sqrt(cx*cx + cy*cy + cz*cz); norT[i][0] = cx/l; norT[i][1] = cy/l; norT[i][2] = cz/l; } 添え字を書くのが 面倒なので いったん代入 外積 の計算 正規化

塗りつぶし多角形を フラットシェーディング OpenGLでのフラットシェーディング void flatShading() { glPolygonMode(GL_FRONT, GL_FILL); glShadeModel(GL_FLAT); for(int i=0; i<triN; i++) { int* t = tri[i]; glBegin(GL_POLYGON); glNormal3fv(norT[i]); glVertex3fv(ver[ t[0] ]); glVertex3fv(ver[ t[1] ]); glVertex3fv(ver[ t[2] ]); glEnd(); } 塗りつぶし多角形を フラットシェーディング で描くモード 三角形の 法線を設定

スムースシェーディング (色補間) 頂点で法線を定義して色を計算する 三角形は色を線形補間して塗りつぶされる メッシュ 光源 視点 法線 メッシュ 法線 色を補間 ※ 法線補間をする方法もある (計算量が若干多いが高品質)

頂点法線の計算法 頂点が属している三角形群の法線の平均 三角形の面積を重みとする平均が良い 頂点法線 足し合わせて 正規化する 長さが面積で 向きが法線方向の ベクトル

頂点法線の計算アルゴリズム すべての頂点法線をゼロベクトルにする 各三角形において すべての頂点法線を正規化する 三角形の2辺の外積を計算する 得られた外積ベクトルを、 その三角形をなす3頂点の法線へ足しこむ すべての頂点法線を正規化する

頂点法線計算の計算機実装 宣言とメモリの確保 頂点法線の計算ルーチン float (*norV)[3]; norV = new float[verN][3]; 頂点法線の計算ルーチン //すべての頂点法線をゼロベクトルにする for(int i=0; i<verN; i++) ??? //各三角形において for(int i=0; i<triN; i++){ //三角形の辺の外積を計算して //得られた外積ベクトルを //その三角形をなす頂点の法線へ足しこむ } //すべての頂点法線を正規化する

OpenGL による スムースシェーディング void smoothShading() { glPolygonMode(GL_FRONT, GL_FILL); glShadeModel(GL_SMOOTH); for(int i=0; i<numTriangles; i++) { int* t = triangles[i]; glBegin(GL_POLYGON); for(int j=0; j<3; j++){ glNormal3fv(vertexNormals[ t[j] ]); glVertex3fv(vertices[ t[j] ]); } glEnd(); スムース シェーディングで 塗りつぶしポリゴンを 描くモード 頂点法線を 三角形の各頂点で 指定する (3回指定する)

課題 2 prog3-1 を使う 以下の操作を確認せよ ‘f’ キー : フラットシェーディングを ON/OFF ‘s’ キー : スムースシェーディングを ON/OFF ‘w’ キー : ワイヤの描画の ON/OFF 関数 “computeTriangleNormals” の中の   三角形の2辺の外積の計算を完成させよ フラットシェーディングが正しく行われるようになる 課題1で作ったピラミッドを表示せよ 黒い面がないようにする 関数 “computeVertexNormal” を完成させよ スムースシェーディングが正しく行われるようになる

話の流れ ポリゴンメッシュとは? レンダリングの方法 フラットシェーディング スムースシェーディング ラプラシアン平滑化

メッシュの平滑化 スキャンなどにより得られたメッシュ上の ノイズを除去する方法 ラプラシアン平滑化がよくつかわれる ノイズのあるメッシュ スキャンなどにより得られたメッシュ上の ノイズを除去する方法 ラプラシアン平滑化がよくつかわれる スキャン 平滑化 ノイズのあるメッシュ 滑らかなメッシュ

ラプラシアン 隣接する頂点へのベクトルの平均 ※ 隣接する頂点が6個の場合

ラプラシアンによる凹凸度評価 ラプラシアンの法線方向に関する成分で、 凹凸度を評価できる :外向きの単位法線 凹凸度 (白が正・黒が負)

ラプラシアン平滑化 各頂点座標へラプラシアンを足すことを繰り返す 繰り返し

ラプラシアンの計算のアルゴリズム 全ての頂点において 各三角形 (A, B, C) において ラプラシアンをゼロベクトルにする 隣接頂点数のカウンタをゼロにする 各三角形 (A, B, C) において ベクトル AB を A のラプラシアンに足し、 A の隣接頂点数を1増やす ベクトル BC を B のラプラシアンに足し、 B の隣接頂点数を1増やす ベクトル CA を C のラプラシアンに足し、 C の隣接頂点数を1増やす 全ての頂点において、 ラプラシアンを隣接頂点数で割る 足す

ラプラシアン計算の計算機実装 宣言とメモリの確保 ラプラシアンの計算ルーチン float (*lap)[3]; int *neiN lap = new float[verN][3]; neiN = new int[verN]; ラプラシアンの計算ルーチン //全ての頂点において // ラプラシアンと隣接頂点数をゼロにする ??? //各三角形において for(int i=0; i<triN; i++){ //各辺のベクトルを始点のラプラシアンに足し //各頂点の隣接頂点数を1増やす } //全ての頂点においてラプラシアンを隣接頂点数で割る

課題 3 prog3-1 を使う 関数 “computeLaplacians” を完成させよ “l”キーを押すと呼び出されるラプラシアン平滑化を行う関数 “laplacianSmoothing” を完成させよ ラプラシアンスムーシングにおいて dt の値を負にした場合どうなるか確かめよ