loadMaterial method

dynamic loadMaterial(
  1. dynamic materialIndex
)

Specification: https://github.com/KhronosGroup/glTF/blob/master/specification/2.0/README.md#materials @param {number} materialIndex @return {Promise

Implementation

loadMaterial(materialIndex) async {
  var parser = this;
  var json = this.json;
  var extensions = this.extensions;
  Map<String, dynamic> materialDef = json["materials"][materialIndex];

  var materialType;
  Map<String, dynamic> materialParams = {};
  Map<String, dynamic> materialExtensions = materialDef["extensions"] ?? {};

  List pending = [];

  if (materialExtensions[
          EXTENSIONS["KHR_MATERIALS_PBR_SPECULAR_GLOSSINESS"]] !=
      null) {
    var sgExtension =
        extensions[EXTENSIONS["KHR_MATERIALS_PBR_SPECULAR_GLOSSINESS"]];
    materialType = sgExtension.getMaterialType(materialIndex);
    pending
        .add(sgExtension.extendParams(materialParams, materialDef, parser));
  } else if (materialExtensions[EXTENSIONS["KHR_MATERIALS_UNLIT"]] != null) {
    var kmuExtension = extensions[EXTENSIONS["KHR_MATERIALS_UNLIT"]];
    materialType = kmuExtension.getMaterialType(materialIndex);
    pending
        .add(kmuExtension.extendParams(materialParams, materialDef, parser));
  } else {
    // Specification:
    // https://github.com/KhronosGroup/glTF/tree/master/specification/2.0#metallic-roughness-material

    Map<String, dynamic> metallicRoughness =
        materialDef["pbrMetallicRoughness"] ?? {};

    materialParams["color"] = new Color(1.0, 1.0, 1.0);
    materialParams["opacity"] = 1.0;

    if (metallicRoughness["baseColorFactor"] is List) {
      List<double> array = List<double>.from(metallicRoughness["baseColorFactor"].map((e) => e.toDouble()));

      materialParams["color"].fromArray(array);
      materialParams["opacity"] = array[3];
    }

    if (metallicRoughness["baseColorTexture"] != null) {
      pending.add(await parser.assignTexture(
          materialParams, 'map', metallicRoughness["baseColorTexture"], sRGBEncoding));
    }

    materialParams["metalness"] = metallicRoughness["metallicFactor"] != null
        ? metallicRoughness["metallicFactor"]
        : 1.0;
    materialParams["roughness"] = metallicRoughness["roughnessFactor"] != null
        ? metallicRoughness["roughnessFactor"]
        : 1.0;

    if (metallicRoughness["metallicRoughnessTexture"] != null) {
      pending.add(await parser.assignTexture(materialParams, 'metalnessMap',
          metallicRoughness["metallicRoughnessTexture"]));
      pending.add(await parser.assignTexture(materialParams, 'roughnessMap',
          metallicRoughness["metallicRoughnessTexture"]));
    }

    materialType = await this._invokeOne((ext) async {
      return ext.getMaterialType != null
          ? await ext.getMaterialType(materialIndex)
          : null;
    });

    final _v = await this._invokeAll((ext) {
      return ext.extendMaterialParams != null &&
          ext.extendMaterialParams(materialIndex, materialParams) != null;
    });

    pending.add(_v);
  }

  if (materialDef["doubleSided"] == true) {
    materialParams["side"] = DoubleSide;
  }

  var alphaMode = materialDef["alphaMode"] ?? ALPHA_MODES["OPAQUE"];

  if (alphaMode == ALPHA_MODES["BLEND"]) {
    materialParams["transparent"] = true;

    // See: https://github.com/mrdoob/three.js/issues/17706
    materialParams["depthWrite"] = false;
  } else {
    materialParams["transparent"] = false;

    if (alphaMode == ALPHA_MODES["MASK"]) {
      materialParams["alphaTest"] = materialDef["alphaCutoff"] != null
          ? materialDef["alphaCutoff"]
          : 0.5;
    }
  }

  if (materialDef["normalTexture"] != null &&
      materialType != MeshBasicMaterial) {
    pending.add(await parser.assignTexture(
        materialParams, 'normalMap', materialDef["normalTexture"]));

    if (materialDef["normalTexture"]["scale"] != null) {
      materialParams["normalScale"] = new Vector2(
          materialDef["normalTexture"].scale,
          materialDef["normalTexture"].scale);
    }
  }

  if (materialDef["occlusionTexture"] != null &&
      materialType != MeshBasicMaterial) {
    pending.add(await parser.assignTexture(
        materialParams, 'aoMap', materialDef["occlusionTexture"]));

    if (materialDef["occlusionTexture"]["strength"] != null) {
      materialParams["aoMapIntensity"] =
          materialDef["occlusionTexture"]["strength"];
    }
  }

  if (materialDef["emissiveFactor"] != null &&
      materialType != MeshBasicMaterial) {
    materialParams["emissive"] =
        new Color(1, 1, 1).fromArray(List<double>.from(materialDef["emissiveFactor"].map((e) => e.toDouble())));
  }

  if (materialDef["emissiveTexture"] != null &&
      materialType != MeshBasicMaterial) {
    pending.add(await parser.assignTexture(
        materialParams, 'emissiveMap', materialDef["emissiveTexture"], sRGBEncoding));
  }

  // await Future.wait(pending);

  var material;

  if (materialType == GLTFMeshStandardSGMaterial) {
    material = extensions[EXTENSIONS["KHR_MATERIALS_PBR_SPECULAR_GLOSSINESS"]]
        .createMaterial(materialParams);
  } else {
    material = createMaterialType(materialType, materialParams);
  }

  if (materialDef["name"] != null) material.name = materialDef["name"];

  assignExtrasToUserData(material, materialDef);

  parser.associations[material] = {
    "type": 'materials',
    "index": materialIndex
  };

  if (materialDef["extensions"] != null)
    addUnknownExtensionsToUserData(extensions, material, materialDef);

  return material;
}