LoginSignup
17
10
この記事誰得? 私しか得しないニッチな技術で記事投稿!

glTF 2.0 のすべての標準プロパティを雑に眺める(ついでに .glb の構造も)

Last updated at Posted at 2023-07-16

glTF 2.0 ファイルの全体像をさらっと把握できるような資料が見つからないので、個人的に調べたメモをここに貼っておきます。

いくらかの前提知識がある方は、プロパティ名を見るだけでも現状の glTF (の基本機能だけ)で何ができるのかの見当をつけられるのかなと思います。

glTF 2.0 の仕様書

追記:コメントにて、公式の概要図を日本語訳されている方の記事を紹介して頂きました:

エンコード方式

glTFでは、シーンや各種オブジェクトの定義は全般的にJSONで記述し、頂点データなどのみをバイナリで格納します。これらを最終的にどのようにエンコードするかについて、いくつかの選択肢が用意されています。

  • .gltf (JSON) + .bin (Binary buffer) (+ 画像ファイル)
    • JSON部分とバイナリ部分を分ける方法。バイナリ部分は複数個に分けてもいい。
    • テクスチャは別途の画像ファイルにもできるし、Binary bufferに含めることもできる。
    • バイナリ部分を .gltf (JSON) にまとめることも可能
      • Binary buffer を Data URI scheme を使って uri につっこめばいい。例)uri="data:application/octet-stream;base64,xxxxxxxxxxxxxxx
  • .glb (すべて1つのバイナリに固める)
    • 1つの .glb (バイナリファイル) のみで表現する。
    • ごく単純なヘッダと、JSONチャンクと、Binary bufferチャンクをほぼそのままくっつけたようなシンプルな形式。構造は後述。

JSON部分の内容

注意

以下のJSONの構造の説明では省略していますが、JSONのすべてのオブジェクト階層に以下のデータを持たせることができます。

  • extensions
    • glTFの拡張機能を使った記述を行う。あらゆるオブジェクトに持たせられる。
  • extras
    • ユーザ定義の任意データ。あらゆるオブジェクトに持たせられる。

glTFの構造

TODO:

  • 型情報などはもう少し正確にしたい
  • どれが必須 (required) な属性かは示して(示せて)いない

拡張まわり

  • extensionsRequired — このアセットを扱う際の必須の拡張機能を列挙する
  • extensionsUsed — このアセットで使う拡張機能を列挙する

メタデータ

  • asset
    • version: “2.0”
    • generator: string
    • copyright: string
    • minVersion: string

シーングラフ周り

  • scene: Id — デフォルトシーンID
  • scenes: []Scene
    • name: string
    • nodes: []Id — Nodesのうち root nodes を列挙する
  • nodes: []node
    • name: string
    • children: []Id
    • mesh: Id
    • camera: Id
    • skin: Id
    • matrix: [16]number
    • rotation: [4]number — 回転用のquaternion
    • translation: [3]number
    • scale: [3]number
    • weights: []Id — instantiated morph targets 用の weights。targets数ぶん必要
    • extensions (KHR_* などのみ示す)

オブジェクト

  • meshes: []Mesh — メッシュ
    • name: string
    • primitives ([]Primitive)
      • attributes — 頂点データのaccessor
        • POSITION: Id
        • TEXCOORD_n: Id
        • COLOR_n: Id
        • NORMAL: Id
        • TANGENT: Id
        • JOINTS_n: Id
        • WEIGHTS_n: Id
        • (↑これらはOpenGLでの慣習が元になっているが、glTFでは仕様で定められた名前である)
        • その他のカスタム属性も許される。
      • indices: Id — 頂点インデクスのaccessor。指定しない場合はnon-indexed verticesとして解釈する。
      • material: Id
      • mode — 0 (POINTS), 1 (LINES), 2 (LINE_LOOP), 3 (LINE_STRIP), 4 (TRIANGLES), 5 (TRIANGLE_STRIP), 6 (TRIANGLE_FAN)
      • targets — morph targets
        • POSITION: Id
        • TEXCOORD_n: Id
        • NORMAL: Id
        • etc.
      • extensions (KHR_* などのみ示す)
    • weights — morph targets 用の weights。targets数ぶん必要
  • skins ([]Skin) — スキニングを実現するための joints とinverse-bind matrices (IBM)
    • name
    • skeleton — skeleton root として使うnode
    • joints — joint として使われる nodes のリスト
    • inverseBindMatrices — inverse-bind 行列 (IBM) として使う 4x4行列へのaccessor。IBMは joints 分必要。
  • cameras ([]Camera)
    • type — perspective or orthographic
    • orthographic
      • xmag: 1
      • ymag: 1
      • zfar: 100
      • znear: 0.01
    • perspective
      • aspectRatio: 1,
      • yfov: 0.7853981633974483,
      • zfar: 100,
      • znear: 0.01,

ライト(拡張):

アニメーション

  • animations ([]Animation)
    • name
    • channels
      • sampler: Id
      • target — アニメーションで変化させる対象。現状はnodeのTRSとweightsのみ制御できる。
        • node: Id
        • path: “translation” | “rotation” | “scale” | “weights”
    • samplers ([]sampler)
      • input: Id — キーフレームタイムスタンプの列 (float Scalar) を表す accessor の Id
      • output: Id — 各タイムスタンプでの出力値を表す accessor の Id
      • interpolation: “LINEAR” | “STEP” | “CUBICSPLINE”

マテリアル

テクスチャ

  • textures ([]Texture)
    • name
    • source: Id — image
    • sampler: Id — sampler
    • extensions (KHR_* などのみ示す)
  • images — 画像
    • name
    • uri — 相対パスまたはData URI
    • bufferView: Id — バッファを参照することも可能
    • mimeType — “image/jpeg” など
  • samplers ([]sampler) — テクスチャのフィルタやwrappingなどを設定
    • magFilter
    • minFilter
    • wrapS
    • wrapT

バイナリバッファ

  • accessors — bufferView をどう見るか。
    • name
    • bufferView: Id
    • componentType: 5120 (BYTE) | 5121 (UNSIGNED_BYTE) | 5122 (SHORT) | 5123 (UNSIGNED_SHORT) | 5125 (UNSIGNED_INT) | 5126 (FLOAT) — 要素の型
    • count — 要素数
    • max: []number
    • min: []number
    • type: “SCALAR” | “VEC2” | “VEC3” | “VEC4” | “MAT2” | “MAT3” | “MAT4”
    • sparse — bufferをインデクスでアクセスするaccessorも作れる
      • count: integer
      • indices
        • bufferView
        • byteOffset
        • componentType
      • values
        • bufferView
        • byteOffset
    • normalized — 整数型の値を [0, 1] ないしは [-1, 1] に正規化して扱うべきかを示す。
    • byteOffset: integer — bufferViewの先頭からのオフセット
  • bufferViews — バッファの一部分への参照
    • buffer: Id
    • byteLength: integer
    • byteOffset: integer
    • target: 34962 (ARRAY_BUFFER) | 34963 (ELEMENT_ARRAY_BUFFER)
    • extensions
  • buffers — 実バイナリバッファの参照 (uri)
    • byteLength: integer
    • uri: string — .bin データへのパス、または Data URI scheme でのバイナリ埋め込み

その他の extensions (KHR_* のみ示す):

glTF を glb (バイナリ) でエンコードする場合の形式

とてもシンプル。先頭のヘッダ部に、JSONチャンクとBINチャンクが続く。

ヘッダ

フィールド 説明
magic uint32 0x46546C67 ('glTF')
version uint32 2
length uint32 このglbファイルのサイズ

各チャンク

フィールド 説明
chunkLength uint32 このチャンクの chunkData のサイズ
chunkType uint32 'JSON' or 'BIN\x00'
chunkData [chunkLength]byte データ本体(パディングについての注意あり)

パディングについての注意。chunkData は、長さが 4 bytes の倍数にアライメントされるように末尾にパディングを入れなければならない。JSONチャンクでは空白文字 (0x20) をパディングとして使い、BINチャンクでは 0x00 をパディングとして使う。

チャンクは次の2種類のみ:

  • Structured JSON Content(1個)
    • データはJSONをそのまま (utf-8) 格納
  • Binary buffer(1個または0個)
17
10
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
17
10