FBXProperty.typecode 에 따라, stream 에서 FBX 파일을 읽고 FBXProperty.data 를 초기화시킵니다. 결과를 담을 FBXPropertyout 입니다. 항상 생성자 FBXProperty() 에서 호출되며, 직접 호출하는 일은 없습니다.

Syntax

FBXProperty.readPrimitive(stream, dataType, out)
FBXProperty.readArray(stream, dataType, out)
FBXProperty.readString(stream, dataType, out)
FBXProperty.readRawData(stream, dataType, out)

Parameters

stream

FBX 파일을 읽기 위해 생성한 FileStream.

dataType

배열의 원소의 데이터 형식을 명시하는 DataType 열거형. readPrimitive() , readArray() 함수에서 사용되며, typecode 에 따라 넘겨야하는 값은 아래와 같습니다:

out

결과를 담을 FBXProperty .

Return value

(none)

Description

Typecode 문자를 읽고 나면, FBXProperty 의 자료형을 알 수 있게 됩니다. 원시 자료형(Primitive Type), 배열 타입(Array type), 특별한 타입(Special type)이 존재합니다:

  1. Primitive Types

    원시 자료형(primitive scalar type)들은 항상 little-endian 바이트 순서로 저장되어있습니다. 즉 typecode = I 라면, stream.read(DataType.Uint32, true) 처럼 읽으면 된다는 의미입니다. 이 과정을 수행하는 것이 FBXProperty.readPrimitive() 함수입니다.

  2. Array types

    배열 자료형(Array type)들을 읽기 전에, 먼저 배열의 길이(ArrayLength)와 인코딩 여부(Encoding), 압축된 배열의 크기(CompressedLength)에 대한 정보가 주어집니다:

    Size (Bytes)   Data Type   Name
    ------------- ----------- ---------------
    4              Uint32      ArrayLength
    4              Uint32      Encoding
    4              Uint32      CompressedLength
    ?              ?           Contents
    

    Encoding == 0 이라면, Contents 는 압축이 되어 있지 않기에, 단순히 sizeof(dataType) * ArrayLength 크기의 byte 들을 읽어주면 됩니다. 이때 읽고 있던 ArrayBuffer 를 공유할 수는 없으며, 항상 새로운 ArrayBuffer 를 생성하여 복사해야 합니다. 이는 메모리 정렬 때문입니다. 예를 들어 배열을 읽고 나서 Uint32Array 으로 변환하기 위해서는, ArrayBuffer.byteOffset 이 반드시 4 의 배수이어야 하기 때문입니다.

    Encoding == 1 이라면, Contents 는 deflate/zip 알고리즘으로 압축되어 있으며, CompressedLength 크기의 byte 들을 읽어주어야 합니다. 압축을 풀기 위해서 inflate() 함수를 호출해야 합니다. 압축을 해제하고 나서의, 원본 배열의 크기는 sizeof(dataType) * ArrayLength 처럼 구할 수 있으므로, 불필요한 버퍼의 재할당을 방지하기 위해 미리 할당합니다:

    const arrayLength      = stream.read(DataType.Uint32);
    const encoding         = stream.read(DataType.Uint32);
    const compressedLength = stream.read(DataType.Uint32);
    
    const byteLength = arrayLength * sizeof(dataType);
    
    if(encoding == 0) {
       out.data = new Uint8Array(byteLength);
       
       for(let i=0; i<byteLength; ++i) {
          out.data[i] = stream.read(DataType.Uint8);
       }
    }
    else {
       out.data = new Uint8Array(byteLength);
       inflate(new BitStream(stream), out.data);
    }
    

    이후 읽어들인 Uint8Arraytypecode 에 따라 Float32Array | Float64Array | BitInt64Array | Int32Array 로 변환합니다. 이 과정을 수행하는 것이 FBXProperty.readArray() 함수입니다.

  3. Special types