Cesium快速上手2-Model图元使用讲解

Cesium快速上手2-Model图元使用讲解

Model示例讲解
http://localhost:8080/Apps/Sandcastle/index.html?src=development%2F3D%20Models.html&label=Development
在这里插入图片描述
关于primitives

  model = scene.primitives.add(Cesium.Model.fromGltf({
        url : url,
        modelMatrix : modelMatrix,
        minimumPixelSize : 128
    }));

createModel具体使用

function createModel(url, height, heading, pitch, roll) {
  height = Cesium.defaultValue(height, 0.0);
  heading = Cesium.defaultValue(heading, 0.0);
  pitch = Cesium.defaultValue(pitch, 0.0);
  roll = Cesium.defaultValue(roll, 0.0);
  //确定模型的翻转
  const hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);
  const origin = Cesium.Cartesian3.fromDegrees(
    -123.0744619,
    44.0503706,
    height
  );
  const modelMatrix = Cesium.Transforms.headingPitchRollToFixedFrame(
    origin,
    hpr
  );
 // 先移除所有的模型	
  scene.primitives.removeAll(); // Remove previous model
  // 加载模型
  model = scene.primitives.add(
    Cesium.Model.fromGltf({
      url: url,
      modelMatrix: modelMatrix,
      minimumPixelSize: 128,
    })
  );
 //模型准备完毕后	
  model.readyPromise
    .then(function (model) {
      model.color = Cesium.Color.fromAlpha(
        getColor(viewModel.color),
        Number(viewModel.alpha)
      );
      model.colorBlendMode = getColorBlendMode(
        viewModel.colorBlendMode
      );
      model.colorBlendAmount = viewModel.colorBlendAmount;
      // Play and loop all animations at half-speed
      model.activeAnimations.addAll({
        multiplier: 0.5,
        loop: Cesium.ModelAnimationLoop.REPEAT,
      });
	 //确定相机	
      const camera = viewer.camera;

      // Zoom to model
      const controller = scene.screenSpaceCameraController;
      const r =
        2.0 *
        Math.max(model.boundingSphere.radius, camera.frustum.near);
      controller.minimumZoomDistance = r * 0.5;

      const center = Cesium.Matrix4.multiplyByPoint(
        model.modelMatrix,
        model.boundingSphere.center,
        new Cesium.Cartesian3()
      );
      const heading = Cesium.Math.toRadians(230.0);
      const pitch = Cesium.Math.toRadians(-20.0);
      //相机指向模型
      camera.lookAt(
        center,
        new Cesium.HeadingPitchRange(heading, pitch, r * 2.0)
      );
    })
    .catch(function (error) {
      window.alert(error);
    });
}

ScreenSpaceEventHandler事件
设置事件,当鼠标移入到模型的时候,触发,事件类型 ScreenSpaceEventType

const handler = new Cesium.ScreenSpaceEventHandler(scene.canvas);
handler.setInputAction(function (movement) {
  const pick = scene.pick(movement.endPosition);
  if (
    Cesium.defined(pick) &&
    Cesium.defined(pick.node) &&
    Cesium.defined(pick.mesh)
  ) {
    // Output glTF node and mesh under the mouse.
    console.log(`node: ${pick.node.name}. mesh: ${pick.mesh.name}`);
  }
}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

Model子节点控制
每一个模型,都应该是由很多节点组合而成,对于每一个节点都应该有旋转,平移,缩放功能

// this can be changed to any glTF model
const modelUrl = "../../SampleData/models/CesiumMan/Cesium_Man.glb";

const viewModel = {
  nodeName: undefined,
  showTranslation: false,
  showRotation: false,
  showScale: false,
  transformations: {},
};

Cesium.knockout.track(viewModel);

// transformation is a computed property returning the values storage for the current node name
Cesium.knockout.defineProperty(
  viewModel,
  "transformation",
  function () {
    const transformations = viewModel.transformations;
    const nodeName = viewModel.nodeName;
    if (!Cesium.defined(transformations[nodeName])) {
      transformations[nodeName] = {
        translationX: 0.0,
        translationY: 0.0,
        translationZ: 0.0,
        rotationHeading: 0.0,
        rotationPitch: 0.0,
        rotationRoll: 0.0,
        scaleX: 1.0,
        scaleY: 1.0,
        scaleZ: 1.0,
      };
      Cesium.knockout.track(transformations[nodeName]);
    }
    return transformations[nodeName];
  }
);

// these writable computed properties produce individual values for use in the UI
[
  "translationX",
  "translationY",
  "translationZ",
  "rotationHeading",
  "rotationPitch",
  "rotationRoll",
  "scaleX",
  "scaleY",
  "scaleZ",
].forEach(function (p) {
  Cesium.knockout.defineProperty(viewModel, p, {
    get: function () {
      return viewModel.transformation[p];
    },
    set: function (value) {
      // coerce values to number
      viewModel.transformation[p] = +value;
    },
  });
});

// these computed properties return each element of the transform
Cesium.knockout.defineProperty(viewModel, "translation", function () {
  return new Cesium.Cartesian3(
    viewModel.translationX,
    viewModel.translationY,
    viewModel.translationZ
  );
});
Cesium.knockout.defineProperty(viewModel, "rotation", function () {
  const hpr = new Cesium.HeadingPitchRoll(
    viewModel.rotationHeading,
    viewModel.rotationPitch,
    viewModel.rotationRoll
  );
  return Cesium.Quaternion.fromHeadingPitchRoll(hpr);
});
Cesium.knockout.defineProperty(viewModel, "scale", function () {
  return new Cesium.Cartesian3(
    viewModel.scaleX,
    viewModel.scaleY,
    viewModel.scaleZ
  );
});
// this computed property combines the above properties into a single matrix to be applied to the node
Cesium.knockout.defineProperty(viewModel, "matrix", function () {
  return Cesium.Matrix4.fromTranslationQuaternionRotationScale(
    viewModel.translation,
    viewModel.rotation,
    viewModel.scale
  );
});

const toolbar = document.getElementById("toolbar");
Cesium.knockout.applyBindings(viewModel, toolbar);

const viewer = new Cesium.Viewer("cesiumContainer");
const scene = viewer.scene;

const height = 250000.0;
const origin = Cesium.Cartesian3.fromDegrees(
  -123.0744619,
  44.0503706,
  height
);
const modelMatrix = Cesium.Transforms.headingPitchRollToFixedFrame(
  origin,
  new Cesium.HeadingPitchRoll()
);

const model = scene.primitives.add(
  Cesium.Model.fromGltf({
    url: modelUrl,
    modelMatrix: modelMatrix,
    minimumPixelSize: 128,
  })
);

model.readyPromise
  .then(function (model) {
    const camera = viewer.camera;

    // Zoom to model
    const controller = scene.screenSpaceCameraController;
    const r =
      2.0 * Math.max(model.boundingSphere.radius, camera.frustum.near);
    controller.minimumZoomDistance = r * 0.5;

    const center = Cesium.Matrix4.multiplyByPoint(
      model.modelMatrix,
      model.boundingSphere.center,
      new Cesium.Cartesian3()
    );
    const heading = Cesium.Math.toRadians(230.0);
    const pitch = Cesium.Math.toRadians(-20.0);
    camera.lookAt(
      center,
      new Cesium.HeadingPitchRange(heading, pitch, r * 2.0)
    );

    // enumerate nodes and add options
    const options = Object.keys(model._runtime.nodesByName).map(
      function (nodeName) {
        return {
          text: nodeName,
          onselect: function () {
            viewModel.nodeName = nodeName;
          },
        };
      }
    );
    options[0].onselect();
    Sandcastle.addToolbarMenu(options);

    // respond to viewmodel changes by applying the computed matrix
    Cesium.knockout
      .getObservable(viewModel, "matrix")
      .subscribe(function (newValue) {
        const node = model.getNode(viewModel.nodeName);
        if (!Cesium.defined(node.originalMatrix)) {
          node.originalMatrix = node.matrix.clone();
        }
        node.matrix = Cesium.Matrix4.multiply(
          node.originalMatrix,
          newValue,
          new Cesium.Matrix4()
        );
      });
  })
  .catch(function (error) {
    window.alert(error);
  });


  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值