cesium把当前的场景截图,下载图片或pdf
安装
npm install canvas2image --savenpm i jspdf -S
如果安装的插件Canvas2Image不好用,可自建js
Canvas2Image.js
/*** covert canvas to image* and save the image file*/
const Canvas2Image = (function () {// check if support sth.const $support = (function () {const canvas = document.createElement("canvas"),ctx = canvas.getContext("2d");return {canvas: !!ctx,imageData: !!ctx.getImageData,dataURL: !!canvas.toDataURL,btoa: !!window.btoa,};})();const downloadMime = "image/octet-stream";function scaleCanvas(canvas, width, height) {const w = canvas.width,h = canvas.height;if (width === undefined) {width = w;}if (height === undefined) {height = h;}let retCanvas = document.createElement("canvas");let retCtx = retCanvas.getContext("2d");retCanvas.width = width;retCanvas.height = height;retCtx.drawImage(canvas, 0, 0, w, h, 0, 0, width, height);return retCanvas;}function getDataURL(canvas, type, width, height) {canvas = scaleCanvas(canvas, width, height);return canvas.toDataURL(type);}// save file to local with file name and file typefunction saveFile(strData, fileType, fileName = "name") {// document.location.href = strData;let saveLink = document.createElement("a");// download file namesaveLink.download = fileName + "." + fileType;// download file datasaveLink.href = strData;// start downloadsaveLink.click();}function genImage(strData) {let img = document.createElement("img");img.src = strData;return img;}function fixType(type) {type = type.toLowerCase().replace(/jpg/i, "jpeg");const r = type.match(/png|jpeg|bmp|gif/)[0];return "image/" + r;}function encodeData(data) {if (!window.btoa) {// eslint-disable-next-line no-throw-literalthrow "btoa undefined";}let str = "";if (typeof data == "string") {str = data;} else {for (let i = 0; i < data.length; i++) {str += String.fromCharCode(data[i]);}}return btoa(str);}function getImageData(canvas) {const w = canvas.width,h = canvas.height;return canvas.getContext("2d").getImageData(0, 0, w, h);}function makeURI(strData, type) {return "data:" + type + ";base64," + strData;}/*** create bitmap image* 按照规则生成图片响应头和响应体*/const genBitmapImage = function (oData) {//// BITMAPFILEHEADER: http://msdn.microsoft.com/en-us/library/windows/desktop/dd183374(v=vs.85).aspx// BITMAPINFOHEADER: http://msdn.microsoft.com/en-us/library/dd183376.aspx//const biWidth = oData.width;const biHeight = oData.height;const biSizeImage = biWidth * biHeight * 3;const bfSize = biSizeImage + 54; // total header size = 54 bytes//// typedef struct tagBITMAPFILEHEADER {// WORD bfType;// DWORD bfSize;// WORD bfReserved1;// WORD bfReserved2;// DWORD bfOffBits;// } BITMAPFILEHEADER;//const BITMAPFILEHEADER = [// WORD bfType -- The file type signature; must be "BM"0x42,0x4d,// DWORD bfSize -- The size, in bytes, of the bitmap filebfSize & 0xff,(bfSize >> 8) & 0xff,(bfSize >> 16) & 0xff,(bfSize >> 24) & 0xff,// WORD bfReserved1 -- Reserved; must be zero0,0,// WORD bfReserved2 -- Reserved; must be zero0,0,// DWORD bfOffBits -- The offset, in bytes, from the beginning of the BITMAPFILEHEADER structure to the bitmap bits.54,0,0,0,];//// typedef struct tagBITMAPINFOHEADER {// DWORD biSize;// LONG biWidth;// LONG biHeight;// WORD biPlanes;// WORD biBitCount;// DWORD biCompression;// DWORD biSizeImage;// LONG biXPelsPerMeter;// LONG biYPelsPerMeter;// DWORD biClrUsed;// DWORD biClrImportant;// } BITMAPINFOHEADER, *PBITMAPINFOHEADER;//const BITMAPINFOHEADER = [// DWORD biSize -- The number of bytes required by the structure40,0,0,0,// LONG biWidth -- The width of the bitmap, in pixelsbiWidth & 0xff,(biWidth >> 8) & 0xff,(biWidth >> 16) & 0xff,(biWidth >> 24) & 0xff,// LONG biHeight -- The height of the bitmap, in pixelsbiHeight & 0xff,(biHeight >> 8) & 0xff,(biHeight >> 16) & 0xff,(biHeight >> 24) & 0xff,// WORD biPlanes -- The number of planes for the target device. This value must be set to 11,0,// WORD biBitCount -- The number of bits-per-pixel, 24 bits-per-pixel -- the bitmap// has a maximum of 2^24 colors (16777216, Truecolor)24,0,// DWORD biCompression -- The type of compression, BI_RGB (code 0) -- uncompressed0,0,0,0,// DWORD biSizeImage -- The size, in bytes, of the image. This may be set to zero for BI_RGB bitmapsbiSizeImage & 0xff,(biSizeImage >> 8) & 0xff,(biSizeImage >> 16) & 0xff,(biSizeImage >> 24) & 0xff,// LONG biXPelsPerMeter, unused0,0,0,0,// LONG biYPelsPerMeter, unused0,0,0,0,// DWORD biClrUsed, the number of color indexes of palette, unused0,0,0,0,// DWORD biClrImportant, unused0,0,0,0,];const iPadding = (4 - ((biWidth * 3) % 4)) % 4;const aImgData = oData.data;let strPixelData = "";const biWidth4 = biWidth << 2;let y = biHeight;const fromCharCode = String.fromCharCode;do {const iOffsetY = biWidth4 * (y - 1);let strPixelRow = "";for (let x = 0; x < biWidth; x++) {const iOffsetX = x << 2;strPixelRow +=fromCharCode(aImgData[iOffsetY + iOffsetX + 2]) +fromCharCode(aImgData[iOffsetY + iOffsetX + 1]) +fromCharCode(aImgData[iOffsetY + iOffsetX]);}for (let c = 0; c < iPadding; c++) {strPixelRow += String.fromCharCode(0);}strPixelData += strPixelRow;} while (--y);return (encodeData(BITMAPFILEHEADER.concat(BITMAPINFOHEADER)) +encodeData(strPixelData));};/*** saveAsImage* @param canvas canvasElement* @param width {String} image type* @param height {Number} [optional] png width* @param type {string} [optional] png height* @param fileName {String} image name*/const saveAsImage = function (canvas, width, height, type, fileName) {// save file typeconst fileType = type;if ($support.canvas && $support.dataURL) {if (typeof canvas == "string") {canvas = document.getElementById(canvas);}if (type === undefined) {type = "png";}type = fixType(type);if (/bmp/.test(type)) {const data = getImageData(scaleCanvas(canvas, width, height));const strData = genBitmapImage(data);// use new parameter: fileTypesaveFile(makeURI(strData, downloadMime), fileType, fileName);} else {const strData = getDataURL(canvas, type, width, height);// use new parameter: fileTypesaveFile(strData.replace(type, downloadMime), fileType, fileName);}}};const convertToImage = function (canvas, width, height, type) {if ($support.canvas && $support.dataURL) {if (typeof canvas == "string") {canvas = document.getElementById(canvas);}if (type === undefined) {type = "png";}type = fixType(type);if (/bmp/.test(type)) {const data = getImageData(scaleCanvas(canvas, width, height));const strData = genBitmapImage(data);return genImage(makeURI(strData, "image/bmp"));} else {const strData = getDataURL(canvas, type, width, height);return genImage(strData);}}};return {saveAsImage: saveAsImage,saveAsPNG: function (canvas, width, height, fileName) {return saveAsImage(canvas, width, height, "png", fileName);},saveAsJPEG: function (canvas, width, height, fileName) {return saveAsImage(canvas, width, height, "jpeg", fileName);},saveAsGIF: function (canvas, width, height, fileName) {return saveAsImage(canvas, width, height, "gif", fileName);},saveAsBMP: function (canvas, width, height, fileName) {return saveAsImage(canvas, width, height, "bmp", fileName);},convertToImage: convertToImage,convertToPNG: function (canvas, width, height) {return convertToImage(canvas, width, height, "png");},convertToJPEG: function (canvas, width, height) {return convertToImage(canvas, width, height, "jpeg");},convertToGIF: function (canvas, width, height) {return convertToImage(canvas, width, height, "gif");},convertToBMP: function (canvas, width, height) {return convertToImage(canvas, width, height, "bmp");},};
})();// Export function, used in npm
export default Canvas2Image;
全部代码如下
<template><div id="cesiumContainer" style="height: 100vh;"></div><div id="toolbar" style="position: fixed;top:20px;left:220px;"><el-breadcrumb><el-breadcrumb-item>场景设置实例</el-breadcrumb-item><el-breadcrumb-item>场景出图</el-breadcrumb-item></el-breadcrumb><el-row class="mb-4" style="margin-top: 15px"><el-button type="primary" @click="downSceneImg">图片</el-button><el-button type="primary" @click="downScenePdf">pdf</el-button></el-row></div>
</template>
<script>
import * as Cesium from "cesium";
import InitCesiumHide from "../js/InitCesiumHide.js";
import canvas2image from '../js/canvas2image.js';
import JsPDF from 'jspdf';export default {name: 'cesium24002',data() {return {viewer: undefined,scene: undefined}},mounted() {let initCesium = new InitCesiumHide('cesiumContainer')this.viewer = initCesium.initViewer({//cesium状态下允许canvas转图片convertToImagecontextOptions: {webgl: {alpha: true,depth: false,stencil: true,antialias: true,premultipliedAlpha: true,preserveDrawingBuffer: true,failIfMajorPerformanceCaveat: true},allowTextureFilterAnisotropic: true}});//去除版权信息this.viewer._cesiumWidget._creditContainer.style.display = "none";this.scene = this.viewer.scene;this.flyToRight2();},methods: {flyToRight2() {let camera = this.viewer.scene.camera;camera.flyTo({destination: Cesium.Cartesian3.fromDegrees(115.2766, 36.5522, 803.34),/*complete: function () {setTimeout(function () {camera.flyTo({destination: Cesium.Cartesian3.fromDegrees(115.2766, 36.5522, 356.50838555841779),orientation: {heading: Cesium.Math.toRadians(150.0),pitch: Cesium.Math.toRadians(-30.0)},easingFunction: Cesium.EasingFunction.LINEAR_NONE});}, 1000);}*/});},downSceneImg() {let canvas = this.viewer.scene.canvas;let imageWidth = 1000;let img = canvas2image.convertToImage(canvas, imageWidth, imageWidth * canvas.height / canvas.width, 'png');let loadImg = document.createElement('a')loadImg.href = img.srcloadImg.download = 'scene'loadImg.click()},downScenePdf() {let canvas = this.viewer.scene.canvas;let imageWidth = 1000;let imageHeight = imageWidth * canvas.height / canvas.width;let img = canvas2image.convertToImage(canvas, imageWidth, imageHeight, 'png');let PDF = new JsPDF('', 'pt', 'a4');PDF.addImage(img, 'png', 0, 0, imageWidth, imageHeight);PDF.save('scene.pdf')}/*,downSceneImg() {this.viewer.render();this.viewer.canvas.toDataURL("image/png");let canvas = this.viewer.scene.canvas;//只需要定义图片的宽度(高度计算得到)let imageWidth = 500;//保存(下载)图片Canvas2image.saveAsImage(canvas, imageWidth, imageWidth * canvas.height / canvas.width, 'png');//转换图片let genimg = Canvas2image.convertToImage(canvas, imageWidth, imageWidth * canvas.height / canvas.width, 'png');let image = document.getElementById('image');image.src = genimg.src;}*/}
}
</script>
<style>
.el-breadcrumb__inner {color: #ffffff !important;
}
</style>