概述
就之前的路径动画和开关动画结合,实现效果:点击开关->播放开门动画->0.5s后,按钮回到初始位置->5s后,播放关门动画。连续点击开关,推拉门会一直保持开着的状态,停止点击开关5s后,推拉门会关上。
最终效果录屏
代码实现
deepblueJson.js
/* deepblueJson.js */
const deepblueLeafJson = [
{
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "a341be0f-d5df-48c3-9c36-8af547e64000",
"name": "室内",
"url": "...", // 此处为 室内模型 3dtiles数据地址
"xbsjPosition": [
2.044452086968357,
0.6398399028959787,
271.22052428840794
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
}
];
export default deepblueLeafJson;
switchJson.js
/* switchJson.js */
const switchJson = [
{
"ref": "switch0",
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "b7a4c6d4-23f3-474e-a828-f34264e40416",
"name": "前台-开关",
"url": `...`, // 此处为 开关模型 3dtiles数据地址
"xbsjPosition": [
2.04445046799674,
0.6398405354461021,
276.1871900601074
],
"xbsjRotation": [
0,
-0.08726646259971647,
0
],
"xbsjScale": [
0.05,
0.05,
0.05
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
},
{
"ref": "switch1",
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "f1e7c69f-dc49-4ae1-a7f4-e06de262b81a",
"name": "东走廊-北开关",
"url": `...`, // 此处为 开关模型 3dtiles数据地址
"xbsjPosition": [
2.0444537081870697,
0.6398405398321795,
276.0500531178269
],
"xbsjRotation": [
0,
0.08726646259971647,
0
],
"xbsjScale": [
0.05,
0.05,
0.05
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
},
{
"ref": "switch2",
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "a9ff6500-db41-4ac4-b625-ee1d230ca368",
"name": "东走廊-南开关",
"url": `...`, // 此处为 开关模型 3dtiles数据地址
"xbsjPosition": [
2.044453705485192,
0.6398378621520856,
276.0524963624675
],
"xbsjRotation": [
0,
0.08726646259971647,
0
],
"xbsjScale": [
0.05,
0.05,
0.05
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
},
{
"ref": "switch3",
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "788772f1-7700-44fe-b88a-727125fb9574",
"name": "展厅-开关",
"url": `...`, // 此处为 开关模型 3dtiles数据地址
"xbsjPosition": [
2.0444540754666938,
0.6398411828712737,
276.1240135896563
],
"xbsjRotation": [
0,
0.08726646259971647,
0
],
"xbsjScale": [
0.03,
0.03,
0.03
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
}
];
export default switchJson;
glassDoorJson.js
/* glassDoorJson.js */
const glassDoorJson = [
{
"ref": "model1",
"czmObject": {
"xbsjType": "Tileset",
"xbsjGuid": "73ed68f3-1dc4-40e7-bddb-50a3e7be4bed",
"name": "玻璃门",
"url": "...", // 此处为 玻璃门模型 3dtiles数据地址
"xbsjPosition": [
2.0444504835730815,
0.6398409689910697,
273.0587282572857
],
"xbsjUseOriginTransform": false,
"xbsjClippingPlanes": {},
"xbsjCustomShader": {}
}
},{
"ref": "path1",
"czmObject": {
"xbsjType": "Path",
"xbsjGuid": "791ba4ac-a022-4f04-8e36-66dff64aa24d",
"name": "路径动画",
"positions": [
[
2.0444504835730815,
0.6398409689910697,
273.0587282572857
],
[
2.0444504835730815,
0.639841101,
273.0587282572857
]
],
"rotations": [
[
0,
0,
0
],
[
0,
0,
0
]
],
"currentSpeed": 1,
"playing": false
}
},{
"ref": "path2",
"czmObject": {
"xbsjType": "Path",
"xbsjGuid": "0a1e9f7e-18fb-4996-bd1a-1303a2fcc6cc",
"name": "路径动画",
"positions": [
[
2.0444504835730815,
0.639841101,
273.0587282572857
],
[
2.0444504835730815,
0.6398409689910697,
273.0587282572857
]
],
"rotations": [
[
0,
0,
0
],
[
0,
0,
0
]
],
"currentSpeed": 1,
"playing": false
}
}
];
export default glassDoorJson;
deepblue_ani.js
注意连续点击按钮时,不应该出现开/关门动画重复从最初位置播放的情况:
- 使用变量控制开/关门动画的执行
- 关门动画和开关动画的定时器在每次动画执行前要清空 ```javascript / deepblue_ani.js /
let openDoor = false; let closeTimer = null; // 关门动画定时器 let switchTimer = null; // 开关动画定时器
// 室内模型-玻璃门 开门 动画 function openDoorAnimation (earth) { const model1 = earth.sceneTree.$refs.model1.czmObject; const path1 = earth.sceneTree.$refs.path1.czmObject; if (model1.xbsjPosition[1] !== path1.positions[1][1] && openDoor) { // 开关按下并且推拉门没有移动到路径终点时,执行开门动画 path1.playing = true; XE.MVVM.watch(path1, ‘currentPosition’, position => { model1.xbsjPosition = […position]; }); } }
// 室内模型-玻璃门 关门 动画 function closeDoorAnimation (earth) { const model1 = earth.sceneTree.$refs.model1.czmObject; const path2 = earth.sceneTree.$refs.path2.czmObject; if(closeTimer) { // 关门动画开始前,清空定时器,避免出现重复播放关门动画的情况 clearTimeout(closeTimer) } if (model1.xbsjPosition[1] !== path2.positions[1][1] && !openDoor) { // 开关没被按下并且推拉门没有移动到路径终点时,执行关门动画 closeTimer = setTimeout(()=>{ path2.playing = true; XE.MVVM.watch(path2, ‘currentPosition’, position2 => { model1.xbsjPosition = […position2]; }) }, 5000) } }
// 室内模型-开关 按下动画 function switchAnimation (earth) { const switch1 = earth.sceneTree.$refs.switch1.czmObject; console.log(switch1.xbsjPosition[0] / Math.PI * 180); switch1.onclick = () => { if (switchTimer) { clearTimeout(switchTimer) } switch1.xbsjRotation = [ 0, 0.08726646259971647, 0]; switch1.xbsjPosition = [2.044450471145981, 0.6398405354461021, 276.1871900601074]; // 开关按下,执行开门动画 openDoor = true; openDoorAnimation(earth); switchTimer = setTimeout(()=>{ switch1.xbsjRotation = [ 0, -0.08726646259971647, 0]; switch1.xbsjPosition = [2.04445046799674, 0.6398405354461021, 276.1871900601074] // 开关恢复原位,执行关门动画 openDoor = false; closeDoorAnimation(earth); }, 500);
} }
export default switchAnimation;
<a name="tL1W9"></a>
### index.js
```javascript
/* index.js */
import deepblueLeafJson from '@/constant/deepblueJson'; // 引入路径可根据实际情况调整
import switchJson from '@/constant/switchJson'; // 引入路径可根据实际情况调整
import glassDoorJson from '@/constant/glassDoorJson'; // 引入路径可根据实际情况调整
import switchAnimation from '@/pages/DigitalTwin/deepblue_ani'; // 引入路径可根据实际情况调整
class animationDemo extends Component{
constructor(props) {
super(props);
this.earth = null;
},
componentDidMount() {
XE.ready().then(()=>{
// 加载标绘插件 js
...
}).then(()=>{
this.startUp();
})
},
startUp = ()=>{
// 创建 Earth实例
this.earth = new XE.Earth("earthContainer");
// 开启拾取(鼠标点击事件)
this.earth.interaction.picking.enabled = true;
// 通过JSON配置创建节点
this.earth.sceneTree.root.children.push(...deepblueLeafJson, ...switchJson, ...glassDoorJson);
switchAnimation(this.earth);
}
return (
<div id="earthContainer"></div>
)
}
export default animationDemo;