gltf

package module
v0.28.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 12, 2024 License: BSD-2-Clause Imports: 16 Imported by: 57

README

gltf PkgGoDev Test Coverage Status License Mentioned in Awesome Go

A Go module for efficient and robust serialization/deserialization of glTF 2.0, a royalty-free specification for the efficient transmission and loading of 3D scenes and models by applications, also known as "the JPEG of 3D".

Main FeaturesGetting StartedContributingAbout The Project

Gopher glTF

⭐ Main Features

📜 Getting started

Data Model

qmuntal/gltf implements the whole glTF 2.0 specification. The top level element is the gltf.Document and it contains all the information to hold a gltf document in memory:

// This document does not produce any valid glTF, it is just an example.
gltf.Document{
  Accessors: []*gltf.Accessor{
      {BufferView: gltf.Index(0), ComponentType: gltf.ComponentUshort, Type: gltf.AccessorScalar},
  },
  Asset: gltf.Asset{Version: "2.0", Generator: "qmuntal/gltf"},
  BufferViews: []*gltf.BufferView{
      {ByteLength: 72, ByteOffset: 0, Target: gltf.TargetElementArrayBuffer},
  },
  Buffers: []*gltf.Buffer{{ByteLength: 1033, URI: bufferData}},
  Meshes: []*gltf.Mesh{{
    Name: "Cube",
  }},
  Nodes: []*gltf.Node{{Name: "Cube", Mesh: gltf.Index(0)}},
  Scene:    gltf.Index(0),
  Scenes:   []*gltf.Scene{{Name: "Root Scene", Nodes: []int{0}}},
}
Optional parameters

All optional properties whose default value does not match with the golang type zero value are defines as pointers. Take the following guidelines into account when working with optional values:

  • It is safe to not define them when writing the glTF if the desired value is the default one.
  • It is safe to expect that the optional values are not nil when reading a glTF.
  • When assigning values to optional properties it may be helpful to use these utility functions:
    • gltf.Index(1)
    • gltf.Float(0.5)
Reading a document

A gltf.Document can be decoded from any io.Reader by using gltf.Decoder:

resp, _ := http.Get("https://example.com/static/foo.gltf")
var doc gltf.Document
gltf.NewDecoder(resp.Body).Decode(&doc)
fmt.Print(doc.Asset)

When working with the file system it is more convenient to use gltf.Open as it automatically manages relative external buffers:

doc, _ := gltf.Open("./foo.gltf")
fmt.Print(doc.Asset)

In both cases the decoder will automatically detect if the file is JSON/ASCII (gltf) or Binary (glb) based on its content.

Writing a document

A gltf.Document can be encoded to any io.Writer by using gltf.Encoder:

var buf bytes.Buffer
gltf.NewEncoder(&buf).Encode(&doc)
http.Post("http://example.com/upload", "model/gltf+binary", &buf)

By default gltf.NewEncoder outputs a binary file, to generate a JSON/ASCII file set AsBinary to false:

var buf bytes.Buffer
enc := gltf.NewEncoder(&buf)
enc.AsBinary = false
enc.Encode(&doc)
http.Post("http://example.com/upload", "model/gltf+json", &buf)

When working with the file system it is more convenient to use gltf.Save and gltf.SaveBinary as it automatically manages relative external buffers:

gltf.Save(&doc, "./foo.gltf")
gltf.SaveBinary(&doc, "./foo.glb")
Manipulating buffer views and accessors

The package gltf/modeler defines a friendly API to read and write accessors and buffer views, abstracting away all the byte manipulation work and the idiosyncrasy of the glTF spec.

The following example creates a single colored triangle:

screenshot

doc := gltf.NewDocument()
doc.Meshes = []*gltf.Mesh{{
    Name: "Pyramid",
    Primitives: []*gltf.Primitive{{
        Indices: gltf.Index(modeler.WriteIndices(doc, []uint16{0, 1, 2})),
        Attributes: gltf.PrimitiveAttributes{
          gltf.POSITION: modeler.WritePosition(doc, [][3]float32{{0, 0, 0}, {0, 10, 0}, {0, 0, 10}}),
          gltf.COLOR_0:  modeler.WriteColor(doc, [][3]uint8{{255, 0, 0}, {0, 255, 0}, {0, 0, 255}}),
        },
    }},
}}
doc.Nodes = []*gltf.Node{{Name: "Pyramid", Mesh: gltf.Index(0)}}
doc.Scenes[0].Nodes = append(doc.Scenes[0].Nodes, 0)
gltf.Save(doc, "./test.gltf")
Data interleaving

The data of the attributes that are stored in a single bufferView may be stored as an Array-Of-Structures, which may produce a rendering perfomance boost in static attributes. qmuntal/gltf/modeler facilitates the creation of interleaved accessors and buffer views with the methods WritePrimitiveAttributes, WriteAccessorsInterleaved, and WriteBufferViewInterleaved being the first one the most recommended for creating mesh primitives:

doc := gltf.NewDocument()
attrs, _ := modeler.WritePrimitiveAttributes(doc,
    modeler.PrimitiveAttribute{Name: gltf.POSITION, Data: [][3]float32{{0, 0, 0}, {0, 10, 0}, {0, 0, 10}}},
    modeler.PrimitiveAttribute{Name: gltf.COLOR_0, Data: [][3]uint8{{255, 0, 0}, {0, 255, 0}, {0, 0, 255}}},
)
doc.Meshes = []*gltf.Mesh{{
    Name: "Pyramid",
    Primitives: []*gltf.Primitive{{
        Indices: gltf.Index(modeler.WriteIndices(doc, []uint16{0, 1, 2})),
        Attributes: attrs,
    }},
}}
doc.Nodes = []*gltf.Node{{Name: "Pyramid", Mesh: gltf.Index(0)}}
doc.Scenes[0].Nodes = append(doc.Scenes[0].Nodes, 0)
gltf.Save(doc, "./test.gltf")
Manipulating bytes

The package gltf/binary defines a friendly and efficient API to read and write bytes from buffers, abstracting away all the byte manipulation work. This package is very low level and normal users should use gltf/modeler instead as it provides another level of abstraction that understands how bytes are associated to other entities.

This package is very similary to the Go binary package, the main differences are that it is highly specialized in glTF data types and that it only have to deal with little endian encoding.

Dealing with extensions

qmuntal/gltf is designed to support dynamic extensions. By default only the core specification is decoded and the data inside the extensions objects are stored as json.RawMessage so they can be decoded by the caller or automatically encoded when saving the document.

Some of the official extensions are implemented under ext.

To decode one of the supported extensions the only required action is to import the associated package, this way the extension will not be stored as json.RawMessage but as the type defined in the extension package:

import (
  "github.com/qmuntal/gltf"
  "github.com/qmuntal/gltf/ext/lightspunctual"
)

func main() {
  doc, _ := gltf.Open("./foo.gltf")
    if v, ok := doc.Extensions[lightspunctual.ExtensionName]; ok {
        for _, l := range v.(lightspunctual.Lights) {
            fmt.Print(l.Type)
        }
    }
}

It is not necessary to call gltf.RegisterExtension for built-in extensions, as these auto-register themselves when the package is initialized.

External extension

This list is the list of known extensions implemented in other modules:

Custom extensions

To implement a custom extension encoding, provide a struct that can be encoded as a JSON object as dictated by the spec.

To implement a custom extension decoding, call gltf.RegisterExtension at least once before decoding, providing the identifier of the extension and a function that decodes the JSON bytes to the desired struct:

const ExtensionName = "FAKE_Extension"

type Foo struct {
    BufferView int          `json:"bufferView"`
    Attributes gltf.Attributes  `json:"attributes"`
}

func init() {
    gltf.RegisterExtension(ExtensionName, Unmarshal)
}

func Unmarshal(data []byte) (any, error) {
    foo := new(Foo)
    err := json.Unmarshal(data, foo)
    return foo, err
}

🙋 Contributing

PRs, issues, and feedback from ninja gophers are very welcomed.

About The Project

This library is a complete implementation of glTF 2.0, and its explicit aim is to provide a production-ready, idiomatic and curated API to perform any kind of glTF manipulation.

It is out of the scope to implement convertes to/from other file formats and to provide mechanisms to create and manipulate 3D geometry.

The current API is still not frozen and can suffer minor changes until it reached v1.0.

Please use the issue tracker or the if you'd like to report problems or discuss features.

Documentation

Index

Examples

Constants

View Source
const (
	POSITION   = "POSITION"
	NORMAL     = "NORMAL"
	TANGENT    = "TANGENT"
	TEXCOORD_0 = "TEXCOORD_0"
	TEXCOORD_1 = "TEXCOORD_1"
	WEIGHTS_0  = "WEIGHTS_0"
	JOINTS_0   = "JOINTS_0"
	COLOR_0    = "COLOR_0"
)

Attribute names defined in the spec.

Variables

View Source
var (
	// DefaultMatrix defines an identity matrix.
	DefaultMatrix = [16]float64{1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}
	// DefaultRotation defines a quaternion without rotation.
	DefaultRotation = [4]float64{0, 0, 0, 1}
	// DefaultScale defines a scaling that does not modify the size of the object.
	DefaultScale = [3]float64{1, 1, 1}
	// DefaultTranslation defines a translation that does not move the object.
	DefaultTranslation = [3]float64{0, 0, 0}
)

Functions

func DenormalizeByte added in v0.17.0

func DenormalizeByte(v int8) float32

NormalizeByte denormalize a int8 into a float32

func DenormalizeRGB added in v0.17.0

func DenormalizeRGB(v [3]uint8) [3]float32

DenormalizeRGB transform a RGB uint8 color (from 0 to 255) to its float represtation (from 0 to 1).

func DenormalizeRGB64 added in v0.17.0

func DenormalizeRGB64(v [3]uint16) [3]float32

DenormalizeRGB64 transform a RGB uint16 color (from 0 to 65535) to its float represtation (from 0 to 1).

func DenormalizeRGBA added in v0.17.0

func DenormalizeRGBA(v [4]uint8) [4]float32

DenormalizeRGBA transform a RGBA uint8 color (from 0 to 255) to its float represtation (from 0 to 1).

func DenormalizeRGBA64 added in v0.17.0

func DenormalizeRGBA64(v [4]uint16) [4]float32

DenormalizeRGBA64 transform a RGBA uint16 color (from 0 to 65535) to its float represtation (from 0 to 1).

func DenormalizeShort added in v0.17.0

func DenormalizeShort(v int16) float32

DenormalizeShort denormalize a int16 into a float32

func DenormalizeUbyte added in v0.17.0

func DenormalizeUbyte(v uint8) float32

DenormalizeUbyte denormalize a uint8 into a float32

func DenormalizeUshort added in v0.17.0

func DenormalizeUshort(v uint16) float32

DenormalizeuShort denormalize a uint16 into a float32

func Float

func Float(val float64) *float64

Float is an utility function that returns a pointer to a float64.

func Index added in v0.8.0

func Index(i int) *int

Index is an utility function that returns a pointer to a int.

func NormalizeByte added in v0.17.0

func NormalizeByte(v float32) int8

NormalizeByte normalize a float32 into a int8

func NormalizeRGB added in v0.17.0

func NormalizeRGB(v [3]float32) [3]uint8

NormalizeRGB transform a RGB float32 color (from 0 to 1) to its uint8 represtation (from 0 to 255).

func NormalizeRGB64 added in v0.17.0

func NormalizeRGB64(v [3]float32) [3]uint16

NormalizeRGB64 transform a RGB float32 color (from 0 to 1) to its uint16 represtation (from 0 to 65535).

func NormalizeRGBA added in v0.17.0

func NormalizeRGBA(v [4]float32) [4]uint8

NormalizeRGB transform a RGBA float32 color (from 0 to 1) to its uint8 represtation (from 0 to 255).

func NormalizeRGBA64 added in v0.17.0

func NormalizeRGBA64(v [4]float32) [4]uint16

NormalizeRGBA64 transform a RGBA float32 color (from 0 to 1) to its uint16 represtation (from 0 to 65535).

func NormalizeShort added in v0.17.0

func NormalizeShort(v float32) int16

NormalizeShort normalize a float32 into a int16

func NormalizeUbyte added in v0.17.0

func NormalizeUbyte(v float32) uint8

NormalizeUbyte normalize a float32 into a uint8

func NormalizeUshort added in v0.17.0

func NormalizeUshort(v float32) uint16

NormalizeUshort normalize a float32 into a uint16

func RegisterExtension added in v0.8.0

func RegisterExtension(key string, f func([]byte) (any, error))

RegisterExtension registers a function that returns a new extension of the given byte array. This is intended to be called from the init function in packages that implement extensions.

func Save

func Save(doc *Document, name string) error

Save will save a document as a glTF with the specified by name.

Example
package main

import (
	"github.com/qmuntal/gltf"
)

func main() {
	doc := &gltf.Document{
		Accessors: []*gltf.Accessor{
			{BufferView: gltf.Index(0), ComponentType: gltf.ComponentUshort, Count: 36, Type: gltf.AccessorScalar},
			{BufferView: gltf.Index(1), ComponentType: gltf.ComponentFloat, Count: 24, Max: []float64{0.5, 0.5, 0.5}, Min: []float64{-0.5, -0.5, -0.5}, Type: gltf.AccessorVec3},
			{BufferView: gltf.Index(2), ComponentType: gltf.ComponentFloat, Count: 24, Type: gltf.AccessorVec3},
			{BufferView: gltf.Index(3), ComponentType: gltf.ComponentFloat, Count: 24, Type: gltf.AccessorVec4},
			{BufferView: gltf.Index(4), ComponentType: gltf.ComponentFloat, Count: 24, Type: gltf.AccessorVec2},
		},
		Asset: gltf.Asset{Version: "2.0", Generator: "FBX2glTF"},
		BufferViews: []*gltf.BufferView{
			{Buffer: 0, ByteLength: 72, ByteOffset: 0, Target: gltf.TargetElementArrayBuffer},
			{Buffer: 0, ByteLength: 288, ByteOffset: 72, Target: gltf.TargetArrayBuffer},
			{Buffer: 0, ByteLength: 288, ByteOffset: 360, Target: gltf.TargetArrayBuffer},
			{Buffer: 0, ByteLength: 384, ByteOffset: 648, Target: gltf.TargetArrayBuffer},
			{Buffer: 0, ByteLength: 192, ByteOffset: 1032, Target: gltf.TargetArrayBuffer},
		},
		Buffers: []*gltf.Buffer{{ByteLength: 1224, Data: []byte{97, 110, 121, 32, 99, 97, 114, 110, 97, 108, 32, 112, 108, 101, 97, 115}}},
		Materials: []*gltf.Material{{
			Name: "Default", AlphaMode: gltf.AlphaOpaque, AlphaCutoff: gltf.Float(0.5),
			PBRMetallicRoughness: &gltf.PBRMetallicRoughness{BaseColorFactor: &[4]float64{0.8, 0.8, 0.8, 1}, MetallicFactor: gltf.Float(0.1), RoughnessFactor: gltf.Float(0.99)},
		}},
		Meshes: []*gltf.Mesh{{Name: "Cube", Primitives: []*gltf.Primitive{{Indices: gltf.Index(0), Material: gltf.Index(0), Mode: gltf.PrimitiveTriangles, Attributes: gltf.PrimitiveAttributes{gltf.POSITION: 1, gltf.COLOR_0: 3, gltf.NORMAL: 2, gltf.TEXCOORD_0: 4}}}}},
		Nodes: []*gltf.Node{
			{Name: "RootNode", Children: []int{1, 2, 3}},
			{Name: "Mesh"},
			{Name: "Cube", Mesh: gltf.Index(0)},
			{Name: "Texture Group"},
		},
		Samplers: []*gltf.Sampler{{WrapS: gltf.WrapRepeat, WrapT: gltf.WrapRepeat}},
		Scene:    gltf.Index(0),
		Scenes:   []*gltf.Scene{{Name: "Root Scene", Nodes: []int{0}}},
	}
	if err := gltf.SaveBinary(doc, "./example.glb"); err != nil {
		panic(err)
	}
}
Output:

func SaveBinary added in v0.9.0

func SaveBinary(doc *Document, name string) error

SaveBinary will save a document as a GLB file with the specified by name.

func SizeOfElement added in v0.18.6

func SizeOfElement(c ComponentType, t AccessorType) int

SizeOfElement returns the size, in bytes, of an element. The element size may not be (component size) * (number of components), as some of the elements are tightly packed in order to ensure that they are aligned to 4-byte boundaries.

Types

type Accessor

type Accessor struct {
	Extensions    Extensions    `json:"extensions,omitempty"`
	Extras        any           `json:"extras,omitempty"`
	Name          string        `json:"name,omitempty"`
	BufferView    *int          `json:"bufferView,omitempty"`
	ByteOffset    int           `json:"byteOffset,omitempty"`
	ComponentType ComponentType `json:"componentType"`
	Normalized    bool          `json:"normalized,omitempty"` // Specifies whether integer data values should be normalized.
	Count         int           `json:"count"`                // The number of attributes referenced by this accessor.
	Type          AccessorType  `json:"type"`
	Max           []float64     `json:"max,omitempty"`    // Maximum value of each component in this attribute.
	Min           []float64     `json:"min,omitempty"`    // Minimum value of each component in this attribute.
	Sparse        *Sparse       `json:"sparse,omitempty"` // Sparse storage of attributes that deviate from their initialization value.
}

An Accessor is a typed view into a bufferView. An accessor provides a typed view into a bufferView or a subset of a bufferView similar to how WebGL's vertexAttribPointer() defines an attribute in a buffer.

type AccessorType

type AccessorType uint8

AccessorType specifies if the attribute is a scalar, vector, or matrix.

const (
	AccessorScalar AccessorType = iota // SCALAR
	AccessorVec2                       // VEC2
	AccessorVec3                       // VEC3
	AccessorVec4                       // VEC4
	AccessorMat2                       // MAT2
	AccessorMat3                       // MAT3
	AccessorMat4                       // MAT4
)

func (AccessorType) Components added in v0.16.0

func (a AccessorType) Components() int

Components returns the number of components of an accessor type.

func (*AccessorType) MarshalJSON added in v0.8.0

func (a *AccessorType) MarshalJSON() ([]byte, error)

MarshalJSON marshal the accessor type with the correct default values.

func (AccessorType) String added in v0.21.0

func (i AccessorType) String() string

func (*AccessorType) UnmarshalJSON added in v0.8.0

func (a *AccessorType) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the accessor type with the correct default values.

type AlphaMode

type AlphaMode uint8

The AlphaMode enumeration specifying the interpretation of the alpha value of the main factor and texture.

const (
	AlphaOpaque AlphaMode = iota // OPAQUE
	AlphaMask                    // MASK
	AlphaBlend                   // BLEND
)

func (*AlphaMode) MarshalJSON added in v0.8.0

func (a *AlphaMode) MarshalJSON() ([]byte, error)

MarshalJSON marshal the alpha mode with the correct default values.

func (AlphaMode) String added in v0.21.0

func (i AlphaMode) String() string

func (*AlphaMode) UnmarshalJSON added in v0.8.0

func (a *AlphaMode) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the alpha mode with the correct default values.

type Animation

type Animation struct {
	Extensions Extensions          `json:"extensions,omitempty"`
	Extras     any                 `json:"extras,omitempty"`
	Name       string              `json:"name,omitempty"`
	Channels   []*AnimationChannel `json:"channels"`
	Samplers   []*AnimationSampler `json:"samplers"`
}

An Animation keyframe.

type AnimationChannel added in v0.26.0

type AnimationChannel struct {
	Extensions Extensions             `json:"extensions,omitempty"`
	Extras     any                    `json:"extras,omitempty"`
	Sampler    int                    `json:"sampler"`
	Target     AnimationChannelTarget `json:"target"`
}

The AnimationChannel targets an animation's sampler at a node's property.

type AnimationChannelTarget added in v0.26.0

type AnimationChannelTarget struct {
	Extensions Extensions  `json:"extensions,omitempty"`
	Extras     any         `json:"extras,omitempty"`
	Node       *int        `json:"node,omitempty"`
	Path       TRSProperty `json:"path"`
}

AnimationChannelTarget describes the index of the node and TRS property that an animation channel targets. The Path represents the name of the node's TRS property to modify, or the "weights" of the Morph Targets it instantiates. For the "translation" property, the values that are provided by the sampler are the translation along the x, y, and z axes. For the "rotation" property, the values are a quaternion in the order (x, y, z, w), where w is the scalar. For the "scale" property, the values are the scaling factors along the x, y, and z axes.

type AnimationSampler

type AnimationSampler struct {
	Extensions    Extensions    `json:"extensions,omitempty"`
	Extras        any           `json:"extras,omitempty"`
	Input         int           `json:"input"` // The index of an accessor containing keyframe input values.
	Interpolation Interpolation `json:"interpolation,omitempty"`
	Output        int           `json:"output"` // The index of an accessor containing keyframe output values.
}

AnimationSampler combines input and output accessors with an interpolation algorithm to define a keyframe graph (but not its target).

type Asset

type Asset struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Copyright  string     `json:"copyright,omitempty"`  // A copyright message suitable for display to credit the content creator.
	Generator  string     `json:"generator,omitempty"`  // Tool that generated this glTF model. Useful for debugging.
	Version    string     `json:"version"`              // The glTF version that this asset targets.
	MinVersion string     `json:"minVersion,omitempty"` // The minimum glTF version that this asset targets.
}

An Asset is metadata about the glTF asset.

func (*Asset) MarshalJSON added in v0.22.0

func (as *Asset) MarshalJSON() ([]byte, error)

MarshalJSON marshal the asset with the correct default values.

func (*Asset) UnmarshalJSON added in v0.22.0

func (as *Asset) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the asset with the correct default values.

type Buffer

type Buffer struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Name       string     `json:"name,omitempty"`
	URI        string     `json:"uri,omitempty"`
	ByteLength int        `json:"byteLength"`
	Data       []byte     `json:"-"`
}

A Buffer points to binary geometry, animation, or skins. If Data length is 0 and the Buffer is an external resource the Data won't be flushed, which can be useful when there is no need to load data in memory.

func (*Buffer) EmbeddedResource

func (b *Buffer) EmbeddedResource()

EmbeddedResource defines the buffer as an embedded resource and encodes the URI so it points to the the resource.

func (*Buffer) IsEmbeddedResource

func (b *Buffer) IsEmbeddedResource() bool

IsEmbeddedResource returns true if the buffer points to an embedded resource.

type BufferView

type BufferView struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Buffer     int        `json:"buffer"`
	ByteOffset int        `json:"byteOffset,omitempty"`
	ByteLength int        `json:"byteLength"`
	ByteStride int        `json:"byteStride,omitempty"`
	Target     Target     `json:"target,omitempty"`
	Name       string     `json:"name,omitempty"`
}

BufferView is a view into a buffer generally representing a subset of the buffer.

type Camera

type Camera struct {
	Extensions   Extensions    `json:"extensions,omitempty"`
	Extras       any           `json:"extras,omitempty"`
	Name         string        `json:"name,omitempty"`
	Orthographic *Orthographic `json:"orthographic,omitempty"`
	Perspective  *Perspective  `json:"perspective,omitempty"`
}

A Camera projection. A node can reference a camera to apply a transform to place the camera in the scene.

func (*Camera) MarshalJSON added in v0.8.0

func (c *Camera) MarshalJSON() ([]byte, error)

MarshalJSON marshal the camera with the correct default values.

type ComponentType

type ComponentType uint16

The ComponentType is the datatype of components in the attribute. All valid values correspond to WebGL enums. 5125 (UNSIGNED_INT) is only allowed when the accessor contains indices.

const (
	ComponentFloat  ComponentType = iota // FLOAT
	ComponentByte                        // BYTE
	ComponentUbyte                       // UNSIGNED_BYTE
	ComponentShort                       // SHORT
	ComponentUshort                      // UNSIGNED_SHORT
	ComponentUint                        // UNSIGNED_INT
)

func (ComponentType) ByteSize added in v0.16.0

func (c ComponentType) ByteSize() int

ByteSize returns the size of a component in bytes.

func (*ComponentType) MarshalJSON added in v0.8.0

func (c *ComponentType) MarshalJSON() ([]byte, error)

MarshalJSON marshal the component type with the correct default values.

func (ComponentType) String added in v0.21.0

func (i ComponentType) String() string

func (*ComponentType) UnmarshalJSON added in v0.8.0

func (c *ComponentType) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the component type with the correct default values.

type CreateFS added in v0.21.0

type CreateFS interface {
	fs.FS
	Create(name string) (io.WriteCloser, error)
}

A CreateFS provides access to a hierarchical file system. Must follow the same naming convention as io/fs.FS.

type Decoder

type Decoder struct {
	Fsys fs.FS
	// contains filtered or unexported fields
}

A Decoder reads and decodes glTF and GLB values from an input stream.

Only buffers with relative URIs will be read from Fsys. Fsys is called to read external resources.

func NewDecoder

func NewDecoder(r io.Reader) *Decoder

NewDecoder returns a new decoder that reads from r.

func NewDecoderFS added in v0.21.0

func NewDecoderFS(r io.Reader, fsys fs.FS) *Decoder

NewDecoder returns a new decoder that reads from r.

func (*Decoder) Decode

func (d *Decoder) Decode(doc *Document) error

Decode reads the next JSON-encoded value from its input and stores it in the value pointed to by doc.

type Document

type Document struct {
	Extensions         Extensions    `json:"extensions,omitempty"`
	Extras             any           `json:"extras,omitempty"`
	ExtensionsUsed     []string      `json:"extensionsUsed,omitempty"`
	ExtensionsRequired []string      `json:"extensionsRequired,omitempty"`
	Accessors          []*Accessor   `json:"accessors,omitempty"`
	Animations         []*Animation  `json:"animations,omitempty"`
	Asset              Asset         `json:"asset"`
	Buffers            []*Buffer     `json:"buffers,omitempty"`
	BufferViews        []*BufferView `json:"bufferViews,omitempty"`
	Cameras            []*Camera     `json:"cameras,omitempty"`
	Images             []*Image      `json:"images,omitempty"`
	Materials          []*Material   `json:"materials,omitempty"`
	Meshes             []*Mesh       `json:"meshes,omitempty"`
	Nodes              []*Node       `json:"nodes,omitempty"`
	Samplers           []*Sampler    `json:"samplers,omitempty"`
	Scene              *int          `json:"scene,omitempty"`
	Scenes             []*Scene      `json:"scenes,omitempty"`
	Skins              []*Skin       `json:"skins,omitempty"`
	Textures           []*Texture    `json:"textures,omitempty"`
}

Document defines the root object for a glTF asset.

func NewDocument added in v0.16.0

func NewDocument() *Document

NewDocument returns a new Document with sane defaults.

func Open

func Open(name string) (*Document, error)

Open will open a glTF or GLB file specified by name and return the Document.

Example
package main

import (
	"fmt"

	"github.com/qmuntal/gltf"
)

func main() {
	doc, err := gltf.Open("fake")
	if err != nil {
		panic(err)
	}
	fmt.Print(doc.Asset)
}
Output:

type Encoder

type Encoder struct {
	AsBinary bool
	Fsys     CreateFS
	// contains filtered or unexported fields
}

An Encoder writes a glTF to an output stream.

Only buffers with relative URIs will be written to Fsys.

func NewEncoder

func NewEncoder(w io.Writer) *Encoder

NewEncoder returns a new encoder that writes to w as a normal glTF file.

func NewEncoderFS added in v0.21.0

func NewEncoderFS(w io.Writer, fsys CreateFS) *Encoder

NewEncoder returns a new encoder that writes to w as a normal glTF file.

func (*Encoder) Encode

func (e *Encoder) Encode(doc *Document) error

Encode writes the encoding of doc to the stream.

func (*Encoder) SetJSONIndent added in v0.22.1

func (e *Encoder) SetJSONIndent(prefix string, indent string)

SetJSONIndent sets json encoded data to have provided prefix and indent settings

type Extensions

type Extensions map[string]any

Extensions is map where the keys are the extension identifiers and the values are the extensions payloads. If a key matches with one of the supported extensions the value will be marshalled as a pointer to the extension struct. If a key does not match with any of the supported extensions the value will be a json.RawMessage so its decoding can be delayed.

func (*Extensions) UnmarshalJSON

func (ext *Extensions) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the extensions with the supported extensions initialized.

type Image

type Image struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Name       string     `json:"name,omitempty"`
	URI        string     `json:"uri,omitempty"`
	MimeType   string     `json:"mimeType,omitempty"`   // Manadatory if BufferView is defined.
	BufferView *int       `json:"bufferView,omitempty"` // Use this instead of the image's uri property.
}

Image data used to create a texture. Image can be referenced by URI or bufferView index. mimeType is required in the latter case.

func (*Image) IsEmbeddedResource

func (im *Image) IsEmbeddedResource() bool

IsEmbeddedResource returns true if the buffer points to an embedded resource.

func (*Image) MarshalData

func (im *Image) MarshalData() ([]byte, error)

MarshalData decode the image from the URI. If the image is not en embedded resource the returned array will be empty.

type Interpolation

type Interpolation uint8

Interpolation algorithm.

const (
	InterpolationLinear      Interpolation = iota // LINEAR
	InterpolationStep                             // STEP
	InterpolationCubicSpline                      // CUBICSPLINE
)

func (*Interpolation) MarshalJSON added in v0.8.0

func (i *Interpolation) MarshalJSON() ([]byte, error)

MarshalJSON marshal the interpolation with the correct default values.

func (Interpolation) String added in v0.21.0

func (i Interpolation) String() string

func (*Interpolation) UnmarshalJSON added in v0.8.0

func (i *Interpolation) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the interpolation with the correct default values.

type MagFilter

type MagFilter uint16

MagFilter is the magnification filter.

const (
	MagUndefined MagFilter = iota // UNDEFINED
	MagLinear                     // LINEAR
	MagNearest                    // NEAREST
)

func (*MagFilter) MarshalJSON added in v0.8.0

func (m *MagFilter) MarshalJSON() ([]byte, error)

MarshalJSON marshal the alpha mode with the correct default values.

func (MagFilter) String added in v0.21.0

func (i MagFilter) String() string

func (*MagFilter) UnmarshalJSON added in v0.8.0

func (m *MagFilter) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the mag filter with the correct default values.

type Material

type Material struct {
	Extensions           Extensions            `json:"extensions,omitempty"`
	Extras               any                   `json:"extras,omitempty"`
	Name                 string                `json:"name,omitempty"`
	PBRMetallicRoughness *PBRMetallicRoughness `json:"pbrMetallicRoughness,omitempty"`
	NormalTexture        *NormalTexture        `json:"normalTexture,omitempty"`
	OcclusionTexture     *OcclusionTexture     `json:"occlusionTexture,omitempty"`
	EmissiveTexture      *TextureInfo          `json:"emissiveTexture,omitempty"`
	EmissiveFactor       [3]float64            `json:"emissiveFactor,omitempty"`
	AlphaMode            AlphaMode             `json:"alphaMode,omitempty"`
	AlphaCutoff          *float64              `json:"alphaCutoff,omitempty"`
	DoubleSided          bool                  `json:"doubleSided,omitempty"`
}

The Material appearance of a primitive.

func (*Material) AlphaCutoffOrDefault added in v0.8.0

func (m *Material) AlphaCutoffOrDefault() float64

AlphaCutoffOrDefault returns the scale if it is not nil, else return the default one.

func (*Material) MarshalJSON

func (m *Material) MarshalJSON() ([]byte, error)

MarshalJSON marshal the material with the correct default values.

func (*Material) UnmarshalJSON

func (m *Material) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the material with the correct default values.

type Mesh

type Mesh struct {
	Extensions Extensions   `json:"extensions,omitempty"`
	Extras     any          `json:"extras,omitempty"`
	Name       string       `json:"name,omitempty"`
	Primitives []*Primitive `json:"primitives"`
	Weights    []float64    `json:"weights,omitempty"`
}

A Mesh is a set of primitives to be rendered. A node can contain one mesh. A node's transform places the mesh in the scene.

type MinFilter

type MinFilter uint16

MinFilter is the minification filter.

const (
	MinUndefined            MinFilter = iota // UNDEFINED
	MinLinear                                // LINEAR
	MinNearestMipMapLinear                   // NEAREST_MIPMAP_LINEAR
	MinNearest                               // NEAREST
	MinNearestMipMapNearest                  // NEAREST_MIPMAP_NEAREST
	MinLinearMipMapNearest                   // LINEAR_MIPMAP_NEAREST
	MinLinearMipMapLinear                    // LINEAR_MIPMAP_LINEAR
)

func (*MinFilter) MarshalJSON added in v0.8.0

func (m *MinFilter) MarshalJSON() ([]byte, error)

MarshalJSON marshal the min filter with the correct default values.

func (MinFilter) String added in v0.21.0

func (i MinFilter) String() string

func (*MinFilter) UnmarshalJSON added in v0.8.0

func (m *MinFilter) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the min filter with the correct default values.

type Node

type Node struct {
	Extensions  Extensions  `json:"extensions,omitempty"`
	Extras      any         `json:"extras,omitempty"`
	Name        string      `json:"name,omitempty"`
	Camera      *int        `json:"camera,omitempty"`
	Children    []int       `json:"children,omitempty"`
	Skin        *int        `json:"skin,omitempty"`
	Matrix      [16]float64 `json:"matrix"` // A 4x4 transformation matrix stored in column-major order.
	Mesh        *int        `json:"mesh,omitempty"`
	Rotation    [4]float64  `json:"rotation"` // The node's unit quaternion rotation in the order (x, y, z, w), where w is the scalar.
	Scale       [3]float64  `json:"scale"`
	Translation [3]float64  `json:"translation"`
	Weights     []float64   `json:"weights,omitempty"` // The weights of the instantiated Morph Target.
}

A Node in the node hierarchy. It can have either a matrix or any combination of translation/rotation/scale (TRS) properties.

func (*Node) MarshalJSON

func (n *Node) MarshalJSON() ([]byte, error)

MarshalJSON marshal the node with the correct default values.

func (*Node) MatrixOrDefault added in v0.8.0

func (n *Node) MatrixOrDefault() [16]float64

MatrixOrDefault returns the node matrix if it represents a valid affine matrix, else return the default one.

func (*Node) RotationOrDefault added in v0.8.0

func (n *Node) RotationOrDefault() [4]float64

RotationOrDefault returns the node rotation if it represents a valid quaternion, else return the default one.

func (*Node) ScaleOrDefault added in v0.8.0

func (n *Node) ScaleOrDefault() [3]float64

ScaleOrDefault returns the node scale if it represents a valid scale factor, else return the default one.

func (*Node) TranslationOrDefault added in v0.8.0

func (n *Node) TranslationOrDefault() [3]float64

TranslationOrDefault returns the node translation.

func (*Node) UnmarshalJSON

func (n *Node) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the node with the correct default values.

type NormalTexture

type NormalTexture struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Index      *int       `json:"index,omitempty"`
	TexCoord   int        `json:"texCoord,omitempty"` // The index of texture's TEXCOORD attribute used for texture coordinate mapping.
	Scale      *float64   `json:"scale,omitempty"`
}

A NormalTexture references to a normal texture.

func (*NormalTexture) MarshalJSON

func (n *NormalTexture) MarshalJSON() ([]byte, error)

MarshalJSON marshal the texture info with the correct default values.

func (*NormalTexture) ScaleOrDefault added in v0.8.0

func (n *NormalTexture) ScaleOrDefault() float64

ScaleOrDefault returns the scale if it is not nil, else return the default one.

func (*NormalTexture) UnmarshalJSON

func (n *NormalTexture) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the texture info with the correct default values.

type OcclusionTexture

type OcclusionTexture struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Index      *int       `json:"index,omitempty"`
	TexCoord   int        `json:"texCoord,omitempty"` // The index of texture's TEXCOORD attribute used for texture coordinate mapping.
	Strength   *float64   `json:"strength,omitempty"`
}

An OcclusionTexture references to an occlusion texture

func (*OcclusionTexture) MarshalJSON

func (o *OcclusionTexture) MarshalJSON() ([]byte, error)

MarshalJSON marshal the texture info with the correct default values.

func (*OcclusionTexture) StrengthOrDefault added in v0.8.0

func (o *OcclusionTexture) StrengthOrDefault() float64

StrengthOrDefault returns the strength if it is not nil, else return the default one.

func (*OcclusionTexture) UnmarshalJSON

func (o *OcclusionTexture) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the texture info with the correct default values.

type Orthographic

type Orthographic struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Xmag       float64    `json:"xmag"`  // The horizontal magnification of the view.
	Ymag       float64    `json:"ymag"`  // The vertical magnification of the view.
	Zfar       float64    `json:"zfar"`  // The distance to the far clipping plane.
	Znear      float64    `json:"znear"` // The distance to the near clipping plane.
}

Orthographic camera containing properties to create an orthographic projection matrix.

type PBRMetallicRoughness

type PBRMetallicRoughness struct {
	Extensions               Extensions   `json:"extensions,omitempty"`
	Extras                   any          `json:"extras,omitempty"`
	BaseColorFactor          *[4]float64  `json:"baseColorFactor,omitempty"`
	BaseColorTexture         *TextureInfo `json:"baseColorTexture,omitempty"`
	MetallicFactor           *float64     `json:"metallicFactor,omitempty"`
	RoughnessFactor          *float64     `json:"roughnessFactor,omitempty"`
	MetallicRoughnessTexture *TextureInfo `json:"metallicRoughnessTexture,omitempty"`
}

PBRMetallicRoughness defines a set of parameter values that are used to define the metallic-roughness material model from Physically-Based Rendering (PBR) methodology.

func (*PBRMetallicRoughness) BaseColorFactorOrDefault added in v0.8.0

func (p *PBRMetallicRoughness) BaseColorFactorOrDefault() [4]float64

BaseColorFactorOrDefault returns the base color factor if it is not nil, else return the default one.

func (*PBRMetallicRoughness) MarshalJSON

func (p *PBRMetallicRoughness) MarshalJSON() ([]byte, error)

MarshalJSON marshal the pbr with the correct default values.

func (*PBRMetallicRoughness) MetallicFactorOrDefault added in v0.8.0

func (p *PBRMetallicRoughness) MetallicFactorOrDefault() float64

MetallicFactorOrDefault returns the metallic factor if it is not nil, else return the default one.

func (*PBRMetallicRoughness) RoughnessFactorOrDefault added in v0.8.0

func (p *PBRMetallicRoughness) RoughnessFactorOrDefault() float64

RoughnessFactorOrDefault returns the roughness factor if it is not nil, else return the default one.

func (*PBRMetallicRoughness) UnmarshalJSON

func (p *PBRMetallicRoughness) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the pbr with the correct default values.

type Perspective

type Perspective struct {
	Extensions  Extensions `json:"extensions,omitempty"`
	Extras      any        `json:"extras,omitempty"`
	AspectRatio *float64   `json:"aspectRatio,omitempty"`
	Yfov        float64    `json:"yfov"`           // The vertical field of view in radians.
	Zfar        *float64   `json:"zfar,omitempty"` // The distance to the far clipping plane.
	Znear       float64    `json:"znear"`          // The distance to the near clipping plane.
}

Perspective camera containing properties to create a perspective projection matrix.

type Primitive

type Primitive struct {
	Extensions Extensions            `json:"extensions,omitempty"`
	Extras     any                   `json:"extras,omitempty"`
	Attributes PrimitiveAttributes   `json:"attributes"`
	Indices    *int                  `json:"indices,omitempty"` // The index of the accessor that contains the indices.
	Material   *int                  `json:"material,omitempty"`
	Mode       PrimitiveMode         `json:"mode,omitempty"`
	Targets    []PrimitiveAttributes `json:"targets,omitempty"` // Only POSITION, NORMAL, and TANGENT supported.
}

Primitive defines the geometry to be rendered with the given material.

type PrimitiveAttributes added in v0.27.0

type PrimitiveAttributes = map[string]int

PrimitiveAttributes is a map that each key corresponds to mesh attribute semantic and each value is the index of the accessor containing attribute's data.

type PrimitiveMode

type PrimitiveMode uint8

PrimitiveMode defines the type of primitives to render. All valid values correspond to WebGL enums.

const (
	PrimitiveTriangles     PrimitiveMode = iota // TRIANGLES
	PrimitivePoints                             // POINTS
	PrimitiveLines                              // LINES
	PrimitiveLineLoop                           // LINE_LOOP
	PrimitiveLineStrip                          // LINE_STRIP
	PrimitiveTriangleStrip                      // TRIANGLE_STRIP
	PrimitiveTriangleFan                        // TRIANGLE_FAN
)

func (*PrimitiveMode) MarshalJSON added in v0.8.0

func (p *PrimitiveMode) MarshalJSON() ([]byte, error)

MarshalJSON marshal the primitive mode with the correct default values.

func (PrimitiveMode) String added in v0.21.0

func (i PrimitiveMode) String() string

func (*PrimitiveMode) UnmarshalJSON added in v0.8.0

func (p *PrimitiveMode) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the primitive mode with the correct default values.

type Sampler

type Sampler struct {
	Extensions Extensions   `json:"extensions,omitempty"`
	Extras     any          `json:"extras,omitempty"`
	Name       string       `json:"name,omitempty"`
	MagFilter  MagFilter    `json:"magFilter,omitempty"`
	MinFilter  MinFilter    `json:"minFilter,omitempty"`
	WrapS      WrappingMode `json:"wrapS,omitempty"`
	WrapT      WrappingMode `json:"wrapT,omitempty"`
}

Sampler of a texture for filtering and wrapping modes.

type Scene

type Scene struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Name       string     `json:"name,omitempty"`
	Nodes      []int      `json:"nodes,omitempty"`
}

The Scene contains a list of root nodes.

type Skin

type Skin struct {
	Extensions          Extensions `json:"extensions,omitempty"`
	Extras              any        `json:"extras,omitempty"`
	Name                string     `json:"name,omitempty"`
	InverseBindMatrices *int       `json:"inverseBindMatrices,omitempty"` // The index of the accessor containing the floating-point 4x4 inverse-bind matrices.
	Skeleton            *int       `json:"skeleton,omitempty"`            // The index of the node used as a skeleton root. When undefined, joints transforms resolve to scene root.
	Joints              []int      `json:"joints"`                        // Indices of skeleton nodes, used as joints in this skin.
}

Skin defines joints and matrices.

type Sparse

type Sparse struct {
	Extensions Extensions    `json:"extensions,omitempty"`
	Extras     any           `json:"extras,omitempty"`
	Count      int           `json:"count"`   // Number of entries stored in the sparse array.
	Indices    SparseIndices `json:"indices"` // Index array of size count that points to those accessor attributes that deviate from their initialization value.
	Values     SparseValues  `json:"values"`  // Array of size count times number of components, storing the displaced accessor attributes pointed by indices.
}

Sparse storage of attributes that deviate from their initialization value.

type SparseIndices

type SparseIndices struct {
	Extensions    Extensions    `json:"extensions,omitempty"`
	Extras        any           `json:"extras,omitempty"`
	BufferView    int           `json:"bufferView"`
	ByteOffset    int           `json:"byteOffset,omitempty"`
	ComponentType ComponentType `json:"componentType"`
}

SparseIndices defines the indices of those attributes that deviate from their initialization value.

type SparseValues

type SparseValues struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	BufferView int        `json:"bufferView"`
	ByteOffset int        `json:"byteOffset,omitempty"`
}

SparseValues stores the displaced accessor attributes pointed by accessor.sparse.indices.

type TRSProperty

type TRSProperty uint8

TRSProperty defines a local space transformation. TRSproperties are converted to matrices and postmultiplied in the T * R * S order to compose the transformation matrix.

const (
	TRSTranslation TRSProperty = iota // translation
	TRSRotation                       // rotation
	TRSScale                          // scale
	TRSWeights                        // weights
)

func (*TRSProperty) MarshalJSON added in v0.8.0

func (t *TRSProperty) MarshalJSON() ([]byte, error)

MarshalJSON marshal the TRSProperty with the correct default values.

func (TRSProperty) String added in v0.21.0

func (i TRSProperty) String() string

func (*TRSProperty) UnmarshalJSON added in v0.8.0

func (t *TRSProperty) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the TRSProperty with the correct default values.

type Target

type Target uint16

The Target that the GPU buffer should be bound to.

const (
	TargetNone               Target = 0     // NONE
	TargetArrayBuffer        Target = 34962 // ARRAY_BUFFER
	TargetElementArrayBuffer Target = 34963 // ELEMENT_ARRAY_BUFFER
)

func (Target) String added in v0.21.0

func (i Target) String() string

type Texture

type Texture struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Name       string     `json:"name,omitempty"`
	Sampler    *int       `json:"sampler,omitempty"`
	Source     *int       `json:"source,omitempty"`
}

A Texture and its sampler.

type TextureInfo

type TextureInfo struct {
	Extensions Extensions `json:"extensions,omitempty"`
	Extras     any        `json:"extras,omitempty"`
	Index      int        `json:"index"`
	TexCoord   int        `json:"texCoord,omitempty"` // The index of texture's TEXCOORD attribute used for texture coordinate mapping.
}

TextureInfo references to a texture.

type WrappingMode

type WrappingMode uint16

WrappingMode is the wrapping mode of a texture.

const (
	WrapRepeat         WrappingMode = iota // REPEAT
	WrapClampToEdge                        // CLAMP_TO_EDGE
	WrapMirroredRepeat                     // MIRRORED_REPEAT
)

func (*WrappingMode) MarshalJSON added in v0.8.0

func (w *WrappingMode) MarshalJSON() ([]byte, error)

MarshalJSON marshal the wrapping mode with the correct default values.

func (WrappingMode) String added in v0.21.0

func (i WrappingMode) String() string

func (*WrappingMode) UnmarshalJSON added in v0.8.0

func (w *WrappingMode) UnmarshalJSON(data []byte) error

UnmarshalJSON unmarshal the wrapping mode with the correct default values.

Directories

Path Synopsis
Package binary implements simple translation between numbers and byte sequences.
Package binary implements simple translation between numbers and byte sequences.
ext
lightspunctual
Package lightspunctual defines three "punctual" light types: directional, point and spot.
Package lightspunctual defines three "punctual" light types: directional, point and spot.
Package modeler implements helper methods to write common glTF entities (indices, positions, colors, ...) into buffers.
Package modeler implements helper methods to write common glTF entities (indices, positions, colors, ...) into buffers.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL