184 lines
5.4 KiB
184 lines
5.4 KiB
1 year ago
|
<template>
|
||
|
<div class="bg" id="content" ref="ThumbnailRef"></div>
|
||
|
</template>
|
||
|
|
||
|
<script>
|
||
|
import { getScaleByActualData } from "./utils"
|
||
|
import { onceObserver } from "@screen/utils/resizeObserver";
|
||
|
|
||
|
function setFont(size, bold = "normal", family = "微软雅黑") {
|
||
|
return `${bold} ${size}px ${family}`;
|
||
|
}
|
||
|
|
||
|
export default {
|
||
|
name: "Thumbnail",
|
||
|
data() {
|
||
|
return {
|
||
|
list: getScaleByActualData(),
|
||
|
};
|
||
|
},
|
||
|
|
||
|
mounted() {
|
||
|
onceObserver.call(this, this.$refs.ThumbnailRef, () => {
|
||
|
this.$refs.ThumbnailRef.innerHTML = null;
|
||
|
this.mapInit();
|
||
|
})
|
||
|
},
|
||
|
methods: {
|
||
|
async mapInit() {
|
||
|
const content = this.$refs.ThumbnailRef;
|
||
|
|
||
|
const width = content.clientWidth;
|
||
|
const height = content.clientHeight;
|
||
|
const zoom = 3;
|
||
|
const canvas = document.createElement("canvas");
|
||
|
canvas.style.width = width + "px";
|
||
|
canvas.style.height = height + "px";
|
||
|
const w = width * zoom;
|
||
|
const h = height * zoom;
|
||
|
canvas.width = w;
|
||
|
canvas.height = h;
|
||
|
content.appendChild(canvas);
|
||
|
|
||
|
const ctx = canvas.getContext("2d");
|
||
|
ctx.textAlign = "center";
|
||
|
ctx.textBaseline = "middle";
|
||
|
var imgbg = await this.loadImage(require("./images/bg.png"));
|
||
|
ctx.drawImage(imgbg, 0, 0, w, h);
|
||
|
ctx.font = setFont(12 * zoom);
|
||
|
ctx.fillStyle = "#ffffff";
|
||
|
ctx.fillText("G2001济南绕城高速", 66 * zoom, h / 2 - 21 * zoom);
|
||
|
ctx.fillText("G3021德上高速", w - 50 * zoom, h / 2 - 21 * zoom);
|
||
|
|
||
|
ctx.font = setFont(12 * zoom, "italic 900", "Arial Black");
|
||
|
|
||
|
ctx.fillStyle = "#ddc85a";
|
||
|
ctx.fillText("项目起点", 210 * zoom, h / 2 - 50 * zoom);
|
||
|
ctx.fillText("K55+378.7", 210 * zoom, h / 2 - 33 * zoom);
|
||
|
ctx.fillText("项目终点", w - 210 * zoom, h / 2 - 50 * zoom);
|
||
|
ctx.fillText("K208+153.4", w - 210 * zoom, h / 2 - 33 * zoom);
|
||
|
|
||
|
ctx.font = setFont(12 * zoom);
|
||
|
|
||
|
// 修改 位置
|
||
|
ctx.translate(-25 * zoom, 208 * zoom);
|
||
|
|
||
|
this.drawCongestionAreas(ctx, 1404, 80, zoom)
|
||
|
// this.drawCongestionAreas(ctx, 1365, 150, zoom)
|
||
|
|
||
|
for (let i of this.list) {
|
||
|
await this.drawTag(i, zoom, ctx);
|
||
|
}
|
||
|
},
|
||
|
async drayLine(zoom, text, ctx, isFoot = false) {
|
||
|
ctx.setLineDash([4 * zoom, 4 * zoom]);
|
||
|
ctx.strokeStyle = "#37B5D4";
|
||
|
ctx.lineWidth = 6;
|
||
|
if (isFoot) {
|
||
|
ctx.translate(0, 12 * zoom);
|
||
|
ctx.strokeRect(0, 0, 1, 161 * zoom);
|
||
|
ctx.translate(0, -12 * zoom);
|
||
|
} else {
|
||
|
ctx.strokeRect(0, 0, 1, 135 * zoom);
|
||
|
}
|
||
|
|
||
|
ctx.fillStyle = "#37B5D4";
|
||
|
ctx.translate(0, -16 * zoom);
|
||
|
|
||
|
if (isFoot) {
|
||
|
ctx.fillText(text, 0, 54);
|
||
|
ctx.translate(0, 226 * zoom);
|
||
|
ctx.fillText(text, 0, -90);
|
||
|
} else {
|
||
|
ctx.fillText(text, 0, 18);
|
||
|
}
|
||
|
},
|
||
|
async drawTag(info, zoom, ctx) {
|
||
|
let type = "3";
|
||
|
if (info.name.indexOf("枢纽") !== -1) {
|
||
|
type = "0";
|
||
|
} else if (info.name.indexOf("服务区") !== -1) {
|
||
|
type = "2";
|
||
|
} else if (info.name.indexOf("停车区") !== -1) {
|
||
|
type = "1";
|
||
|
}
|
||
|
if (type === "0") {
|
||
|
ctx.translate(info.distance * zoom, -188 * zoom);
|
||
|
ctx.font = setFont(12 * zoom, "600");
|
||
|
await this.drayLine(zoom, info.line, ctx, info.isFoot);
|
||
|
if (info.isFoot) {
|
||
|
ctx.translate(-10 * zoom, -180 * zoom);
|
||
|
} else {
|
||
|
ctx.translate(-10 * zoom, 35 * zoom);
|
||
|
}
|
||
|
if (info.name === "东平湖枢纽") {
|
||
|
const r = -110;
|
||
|
ctx.rotate((r * Math.PI) / 180);
|
||
|
ctx.strokeRect(-15 * zoom, 0, 1, 90 * zoom);
|
||
|
ctx.rotate((r * Math.PI) / -180);
|
||
|
ctx.fillText("S33济徐高速", 124 * zoom, -27 * zoom);
|
||
|
}
|
||
|
} else {
|
||
|
ctx.translate(info.distance * zoom, -169 * zoom);
|
||
|
}
|
||
|
let y = 42 - (info.name.length - 5) * 10;
|
||
|
ctx.fillStyle = "#ffffff";
|
||
|
ctx.font = setFont(12 * zoom);
|
||
|
var img = await this.loadImage(require(`./images/${info.icon || `tag${type}`}.png`));
|
||
|
ctx.drawImage(img, 0, 0, 21 * zoom, 117 * zoom);
|
||
|
ctx.translate(11.1 * zoom, y * zoom);
|
||
|
|
||
|
for (var i = 0; i < info.name.length; i++) {
|
||
|
ctx.fillText(info.name[i], 0, i * 15 * zoom);
|
||
|
}
|
||
|
|
||
|
ctx.translate(0, (169 - y) * zoom);
|
||
|
ctx.font = setFont(10.5 * zoom);
|
||
|
|
||
|
// 修改文字位置
|
||
|
ctx.fillText(info.code, 0, -132);
|
||
|
},
|
||
|
loadImage(url) {
|
||
|
return new Promise((resolve, reject) => {
|
||
|
const img = new Image();
|
||
|
img.setAttribute("crossOrigin", "anonymous");
|
||
|
img.src = url;
|
||
|
img.onload = () => {
|
||
|
// 当图像加载完成后进行resolve
|
||
|
resolve(img);
|
||
|
};
|
||
|
img.onerror = () => {
|
||
|
reject(new Error("图像加载失败"));
|
||
|
};
|
||
|
});
|
||
|
},
|
||
|
drawCongestionAreas(ctx, x, y, zoom) {
|
||
|
const { e: translateX, f: translateY } = ctx.getTransform();
|
||
|
x = translateX * -1 + x * zoom;
|
||
|
y = translateY * -1 + y * zoom;
|
||
|
|
||
|
const rectWidth = 180 * zoom;
|
||
|
const rectHeight = 8 * zoom;
|
||
|
|
||
|
const grad = ctx.createLinearGradient(x, 0, x + rectWidth, 0);
|
||
|
grad.addColorStop(0, 'rgba(217,50,8,0)');
|
||
|
grad.addColorStop(0.27, '#D73208');
|
||
|
grad.addColorStop(0.42, '#D93208');
|
||
|
grad.addColorStop(0.81, '#F5FF83');
|
||
|
grad.addColorStop(1, 'rgba(215,50,8,0)');
|
||
|
|
||
|
ctx.fillStyle = grad;
|
||
|
|
||
|
ctx.fillRect(x, y, rectWidth, rectHeight);
|
||
|
}
|
||
|
},
|
||
|
};
|
||
|
</script>
|
||
|
|
||
|
<style scoped lang="less">
|
||
|
.bg {
|
||
|
height: 100%;
|
||
|
width: 100%;
|
||
|
}
|
||
|
</style>
|