问题原因:
使用Cesium_vue脚手架搭建的项目把Cesium的对象viewer放入到 store、data、computed中,会引起Cesium帧率严重下降的问题,由于vue响应式框架对页面数据渲染是很友好,data选项会把数据里面所有的属性都转换成get,set进行监听。但是对于Cesium庞大的对象直接挂载到vue的data对象上会影响整个页面的渲染效率,降低帧率。特别是加载大体量模型场景时。
解决方案:
// 创建Viewer
var viewer = new Cesium.Viewer(container, {
imageryProvider: Cesium.createTileMapServiceImageryProvider({
url: Cesium.buildModuleUrl('Assets/Textures/NaturalEarthII'),
fileExtension: 'jpg',
}),
baseLayerPicker: false,//是否显示图层选择器
geocoder: false,//是否显示geocoder小器件,右上角查询按钮
animation: false,//是否创建动画小器件,左下角仪表
fullscreenButton: false,//是否显示全屏控件,右下角
vrButton: false,
geocoder: false,//是否显示geocoder小器件,右上角查询按钮
homeButton: false,//是否显示Home按钮
infoBox: false,//是否显示信息框
sceneModePicker: false,//是否显示3D/2D选择器
selectionIndicator: false,
timeline: false,
navigationHelpButton: false,
navigationInstructionsInitiallyVisible: false,
// shouldAnimate: false,
contextOptions: {
webgl: {
antialias: !mobilecheck(),
preserveDrawingBuffer: true
}
},
terrainProvider: new Cesium.EllipsoidTerrainProvider(),
scene3DOnly: true,
shadows: true
});
//将viewer放到window对象当中提供全局调用
window.earthviewer = viewer
如果使用vue-cesium-supermap超图开发库可对下载的node_modules下index.js进行修改

修改内容如下:
init: function init(Cesium) {
var $el = this.$refs.viewer;
var viewer = new Cesium.Viewer($el, {
animation: this.animation,
baseLayerPicker: this.baseLayerPicker,
fullscreenButton: this.fullscreenButton,
vrButton: this.vrButton,
geocoder: this.geocoder,
homeButton: this.homeButton,
infoBox: this.infoBox,
sceneModePicker: this.sceneModePicker,
selectionIndicator: this.selectionIndicator,
timeline: this.timeline,
navigationHelpButton: this.navigationHelpButton,
navigationInstructionsInitiallyVisible: this.navigationInstructionsInitiallyVisible,
scene3DOnly: this.scene3DOnly,
shouldAnimate: this.shouldAnimate,
clockViewModel: this.clockViewModel,
selectedImageryProviderViewModel: this.selectedImageryProviderViewModel,
imageryProviderViewModels: this.imageryProviderViewModels,
selectedTerrainProviderViewModel: this.selectedTerrainProviderViewModel,
terrainProviderViewModels: this.terrainProviderViewModels,
imageryProvider: this.imageryProvider,
terrainProvider: this.terrainProvider,
skyBox: this.skyBox,
skyAtmosphere: this.skyAtmosphere,
fullscreenElement: this.fullscreenElement,
useDefaultRenderLoop: this.useDefaultRenderLoop,
targetFrameRate: this.targetFrameRate,
showRenderLoopErrors: this.showRenderLoopErrors,
automaticallyTrackDataSourceClocks: this.automaticallyTrackDataSourceClocks,
contextOptions: this.contextOptions,
sceneMode: this.sceneMode,
mapProjection: this.mapProjection,
globe: this.globe,
orderIndependentTranslucency: this.orderIndependentTranslucency,
creditContainer: this.creditContainer,
creditViewport: this.creditViewport,
dataSources: this.dataSources,
terrainExaggeration: this.terrainExaggeration,
shadows: this.shadows,
terrainShadows: this.terrainShadows,
mapMode2D: this.mapMode2D,
projectionPicker: this.projectionPicker,
requestRenderMode: this.requestRenderMode,
maximumRenderTimeChange: this.maximumRenderTimeChange,
navigation: this.navigation
});
//修改内容
window.earthviewer = viewer;
if (Cesium.defined(this.camera)) {
viewer.camera.setView({
destination: Cesium.Cartesian3.fromDegrees(this.camera.position.longitude, this.camera.position.latitude, this.camera.position.height),
orientation: {
heading: Cesium.Math.toRadians(this.camera.heading),
pitch: Cesium.Math.toRadians(this.camera.pitch),
roll: Cesium.Math.toRadians(this.camera.roll)
}
});
}
if (Cesium.defined(viewer.animation)) {
var d = new Date();
var hour = 0 - d.getTimezoneOffset();
viewer.animation.viewModel.timeFormatter = function (date, viewModel) {
var dateZone8 = Cesium.JulianDate.addMinutes(date, hour, new Cesium.JulianDate());
var gregorianDate = Cesium.JulianDate.toGregorianDate(dateZone8);
var millisecond = Math.round(gregorianDate.millisecond);
if (Math.abs(viewModel._clockViewModel.multiplier) < 1) {
return Cesium.sprintf('%02d:%02d:%02d.%03d', gregorianDate.hour, gregorianDate.minute, gregorianDate.second, millisecond);
}
return Cesium.sprintf('%02d:%02d:%02d GMT+8', gregorianDate.hour, gregorianDate.minute, gregorianDate.second);
};
}
this.$emit('ready', { Cesium: Cesium, viewer: viewer });
window.earthviewerContainer = (0, _util.getDocumentByClassName)(this.$refs.viewer.children, 'cesium-viewer');
this.resizeControl();
window.someObject = this.someObject;
}
项目其他任何地方都可通过window.earthviewer获取viewer来进行开发
cesium引入的方式不推荐通过node_moudules的方式,通过将cesium放入static,方便修改和调试更换新版本
网友评论