cesium 图层构建的那些事 (十六)

今天我们来讲下聚合图层

首先我们定义参数

  • export enum ECluserLayerType {
  • circle = 0,
  • shine = 1,
  • image = 2,//未实现
  • }
  •  
  • interface ClusterColor {
  • value: number,
  • color: string
  • }
  •  
  • export interface PBaseCluserLayer {
  • enabled?: boolean,// 开启聚集统计
  • pixelRange?: number,// 获取或设置像素范围以扩展屏幕空间边界框。
  • minimumClusterSize?: number,//获取或设置可以集群的最小屏幕空间对象数
  • cluster?: {
  • type: ECluserLayerType,//聚集时候展示的类型
  • label?: {
  • size?: number,
  • color?: string,
  • font?: string
  • }
  • colors?: Array<ClusterColor>,//必须从大到小
  • image?: String//如果type是image,则必须填写图片地址image
  • }
  •  
  • }

聚合辅助类
```javascript

import {ECluserLayerType, PBaseCluserLayer} from "./PBaseCluserLayer";

export class ClusterType {
private static cache: any = {};

  • static getCluserImage(option: any, entities: any) {
  • if (option.type === ECluserLayerType.circle) {
  • return this.drawCircle(option, entities);
  • } else if (option.type === ECluserLayerType.shine) {
  • return this.drawShine(option, entities);
  • } else if (option.type === ECluserLayerType.image) {
  • } else {
  • throw new Error("类型无法识别:" + option.type);
  • }
  • }
  •  
  • private static drawCircle(option: any, entities: any) {
  • let labelSize = option.label.size;
  • const labelColor = option.label.color;
  • const labelFont = option.label.font;
  • const num = entities.length;
  • let diameter = labelSize * (String(num).length + 1);
  • let color: string = "";
  • let scale: number = 1;
  • const len = option.colors.length;
  • for (let index = len - 1; index >= 0; index--) {
  • var item = option.colors[index];
  • if (num >= item.value) {
  • color = item.color;
  • scale = (len - index) / len;
  • break;
  • }
  • }
  • diameter -= diameter * scale / 3;
  • labelSize -= labelSize * scale / 3;
  • const key = color + "-" + num + diameter + labelSize + labelColor + labelFont;
  • let canvas: any = this.cache[key];
  • if (!canvas) {
  • canvas = document.createElement('canvas')
  • canvas.width = canvas.height = diameter;
  • const ctx: any = canvas.getContext('2d');
  • const center = diameter / 2;
  • ctx.translate(center, center);
  • ctx.save();
  • ctx.beginPath()
  • ctx.globalAlpha = .5;
  • ctx.fillStyle = color;
  • ctx.arc(0, 0, center, 0, 2 * Math.PI)
  • ctx.closePath()
  • ctx.fill()
  • ctx.beginPath()
  • ctx.globalAlpha = 0.9;
  • ctx.fillStyle = color;
  • ctx.arc(0, 0, center * 0.7, 0, 2 * Math.PI);
  • ctx.fill()
  • ctx.closePath();
  • ctx.globalAlpha = 1;
  • ctx.fillStyle = labelColor;
  • ctx.font = `${labelSize}px ${labelFont}`;
  • ctx.fillText(String(num), -(diameter - labelSize * 0.85) / 4, labelSize / 2 - labelSize / 10);
  • ctx.restore()
  • canvas = this.cache[key] = canvas.toDataURL()
  • }
  • return canvas
  • }
  •  
  • private static drawShine(option: any, entities: any) {
  • let labelSize = option.label.size;
  • const labelColor = option.label.color;
  • const labelFont = option.label.font;
  • const num = entities.length;
  • let diameter = labelSize * (String(num).length + 1);
  • let color: string = "";
  • let scale: number = 1;
  • const len = option.colors.length;
  • for (let index = len - 1; index >= 0; index--) {
  • var item = option.colors[index];
  • if (num >= item.value) {
  • color = item.color;
  • scale = (len - index) / len;
  • break;
  • }
  • }
  • diameter -= diameter * scale / 3;
  • labelSize -= labelSize * scale / 3;
  • const key = color + "-" + num + diameter + labelSize + labelColor + labelFont;
  • let canvas: any = this.cache[key];
  • if (!canvas) {
  • canvas = document.createElement('canvas')
  • canvas.width = canvas.height = diameter;
  • const ctx: any = canvas.getContext('2d');
  • const center = diameter / 2;
  • ctx.translate(center, center);
  • ctx.save();
  • ctx.beginPath()
  • ctx.globalAlpha = 1;
  • ctx.fillStyle = color;
  • ctx.arc(0, 0, center * 0.6, 0, 2 * Math.PI);
  • ctx.closePath()
  • ctx.fill()
  • ctx.closePath();
  • ctx.lineWidth = center * 0.1;
  • let startAngle = -Math.PI / 12
  • let angle = Math.PI / 2
  • let intervalAngle = Math.PI / 6
  • for (let i = 0; i < 3; i++) {
  • ctx.beginPath()
  • ctx.globalAlpha = 0.6;
  • ctx.strokeStyle = color;
  • ctx.arc(0, 0, center * 0.75, startAngle, startAngle + angle, false);
  • ctx.stroke();
  • ctx.closePath();
  • ctx.beginPath()
  • ctx.globalAlpha = 0.2;
  • ctx.arc(0, 0, center * 0.9, startAngle, startAngle + angle, false);
  • ctx.stroke();
posted @ 2022-01-20 17:45  haibalai  阅读(102)  评论(0编辑  收藏  举报