チュートリアル > ジオメトリ データの読み取りと書き込み > ジオメトリ データのテキスト ファイルへの出力 - 第 1 部 |
これは、メッシュ ジオメトリ データを外部のテキスト ファイルに書き込む非常に基本的な例です。書き込まれたファイルは、後で MAXScript、またはスクリプトと ASCII ファイルの読み取りをサポートする他の 3D アプリケーションによって解析することができます。第 1 部では、頂点と面のリストのみを固定パス名に書き込みます。第 2 部では、第 1 部で作成したコードを拡張して、ユーザが書き込み先のファイルを選択できるようにし、エッジの可視性、スムージング グループ、テクスチャ座標などのメッシュ機能をいくつかサポートします。
別のチュートリアルで、ジオメトリ データを読み戻してシーン内にメッシュを再作成するスクリプトを開発します。
Editable_Mesh : GeometryClass および TriMesh : 値
シーン選択内で最初に検出されたオブジェクトの TriMesh スナップショットを作成します。このメソッドで、[スペース ワープ](Space Warp)バインドも含めて、モディファイヤ スタックの頂点の状態を評価します。その結果、シーンではなく、メモリ内に TriMesh 値が格納されます。シーン オブジェクトであるかのようにしてすべての頂点と面にアクセスすることができます。
この時点では、ユーザがシーン内のオブジェクトを選択したかどうか、および最初に選択したオブジェクトがジオメトリ クラスかどうかをまだチェックしていないことに注意してください。これは最終コードの単なるラフ スケッチです。ユーザが、有効なオブジェクトが選択されたことを確認する必要があります。チュートリアルの第 2 部で、このようなテストを追加します。
次に、ファイルの書き込み先を含む変数を定義します。キーワードの #export を使用した GetDir 関数を使用して、書き込み操作用の 3ds Max システム パスの設定を取得します。ここでは、ファイル名 testmesh.dat を追加しています。この名前は、実際に使用する任意の有効な名前にすることができます。第 2 部では、ファイルを開くためのダイアログ ボックスを使用して、ユーザがパスとファイル名を選択できるようにします。
定義された出力パスを使用して新規ファイルを作成し、ユーザ変数の out_file に結果の fileStream 値を格納します。この変数を書き込み先として使用し、ファイルに出力することができます。
作成した TriMesh 値には、シーン内の各メッシュ オブジェクトと同様に、プロパティの .numverts と .numfaces があります。両方の値がこれから何度も必要になるので、これらの値を取得してユーザ変数に格納します。
Editable_Mesh : GeometryClass および TriMesh : 値
ここで、初めてファイルに出力できます。コンマで区切った 2 つのユーザ要素を書き込むことを指定するフォーマット パターンを定義します。この行は、円記号と n で指定する改行の制御文字で終了します。 フォーマット文字列の後に、フォーマット文字列内の % 記号の数と同じ出力の式を用意する必要があります。
頂点と面の数がそれぞれ 8 と 12 の場合 (典型的なボックス)、出力結果は次のようになります。
フォーマット関数の最後の to: で出力先を指定します。指定しないと、既定により MAXScript リスナーに出力されます。
次のステップで、メッシュのすべての頂点を出力します。1 で始まり TriMesh 内の頂点の数で終わる for ループを使用して、すべての頂点を巡回します。ループが繰り返されるごとに、変数 v の値が 1 から num_verts まで変化します。v の値が num_verts の値を超えたときに、ループが終了します。
ループの変数内に現在格納されている値を使用して、tmesh 値に getVert メソッドを呼び出すことによって、対応するインデックス付きの頂点を取得します。その結果はユーザ変数に格納され、頂点のワールド位置を表わす Point3 の値 (3D 位置の値) になります。
Editable_Mesh : GeometryClass および TriMesh : 値
頂点の位置をファイルに書き出す必要があります。vert 変数の値にコンマを続けて出力するために、フォーマット文字列をフォーマット関数に指定します。改行は必要ありません。すべての頂点位置はコンマで区切られて単一の行に表示されます。
ここで v ループは終了し、v 変数が num_verts の値に達しないかぎり、for v ステートメントに戻ります。つまり、ブラケットで囲まれたブロックは、num_verts 内の数だけ繰り返されます。
頂点のリストと面のリストを区切るために、単一の改行文字をファイルに出力します。% のプレースホルダを何も含めなかったので、フォーマット文字列にはユーザ式がないとみなされます。
面リストの出力は頂点リストのコードにとても似ています。ここでは、他の変数を使用します。
さらに、頂点の位置の代わりに面の定義を取得します。平面定義も Point3 値ですが、位置の代わりに面を定義する 3 つの頂点へのインデックスを含みます。したがって、Point3 に格納された数値は、1 から num_verts までの間の整数です。この結果をユーザ変数の face に格納します。
そしてそれを、頂点で行ったのと同じようにファイルに出力します。
ここで f ループは終了し、f 変数が num_faces の値に達しないかぎり、for f ステートメントに戻ります。つまり、ブラケットで囲まれたブロックは、num_faces 内の数だけ繰り返されます。
最後に、ファイルを閉じ、読み取り用に開くことができるようにします。これを実行しないと、Windows OS によってファイルが開いているとマークされ、MAXScript で読み取ることができません。ファイルが明示的に閉じる前にスクリプトでエラーが発生した場合は、 gc() を呼び出して、ガベージ コレクションを実行することができます。この場合、ロックされているすべてのファイルが解除されるという影響があります。
TriMesh の値を削除して、使用したメモリをガーベジ コレクションに解放します。これを行なわないと、スクリプトを複数回実行することによってメモリ リークが発生する可能性があります。
出力が予期したとおりになるように、MAXScript エディタ内でスクリプトの先頭に定義された名前のファイルを開きます。
ワールド原点にある単純な立方体の場合、出力は次のようになります。
スクリプトをテストするには、ジオメトリ オブジェクトを作成し、シーンでそのオブジェクトを選択して、MAXScript エディタのメニューから[ツール](Tools) > [評価](Evaluate)を選択するか、Ctrl+Eを押します。結果の出力ファイルが、新しい MAXScript エディタで開きます。
前に説明したように、これはジオメトリを出力する基本コードです。このコードは、さらにコンパクトにすることができます。以下のコードは、エディタ内でプレビュー用にファイルを開かない、同じコードの短縮バージョンです。2 つのスクリプトを比較して、多少異なる表現があっても同じことを実行している理由を考えてください。
ここで出力を入手したので、対応する入力スクリプトに進んでそのスクリプトを記述し、データを読み戻して新しいシーン オブジェクトを作成します。
チュートリアル - ジオメトリ データのテキスト ファイルからの読み取り - 第 1 部
また、「ジオメトリの出力」チュートリアルの第 2 部で、より堅牢でいくつかの機能を追加したコードを作成します。
チュートリアル - ジオメトリ データのテキスト ファイルからの読み取り - 第 1 部