Skip to content

Commit

Permalink
【feature】grid支持多投影
Browse files Browse the repository at this point in the history
  • Loading branch information
songyumeng committed Apr 18, 2024
1 parent 7306526 commit 3be6803
Show file tree
Hide file tree
Showing 7 changed files with 94 additions and 29 deletions.
34 changes: 28 additions & 6 deletions packages/layers/src/heatmap/models/grid.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import {
AttributeType,
CoordinateSystem,
gl,
IEncodeFeature,
IModel,
Expand All @@ -10,6 +11,8 @@ import { IHeatMapLayerStyleOptions } from '../../core/interface';
import { HeatmapGridTriangulation } from '../../core/triangulation';
import heatmapGridVert from '../shaders/grid_vert.glsl';
import heatmapGridFrag from '../shaders/hexagon_frag.glsl';
import { mat2, vec2, vec4 } from 'gl-matrix';
import { transformLnglat, transformOffset } from '../../../../maps/src/mapbox';
export default class GridModel extends BaseModel {
public getUninforms(): IModelUniform {
const { opacity, coverage, angle } =
Expand Down Expand Up @@ -52,12 +55,31 @@ export default class GridModel extends BaseModel {
type: gl.FLOAT,
},
size: 3,
update: (feature: IEncodeFeature) => {
const coordinates = (
feature.version === 'GAODE2.x'
? feature.originCoordinates
: feature.coordinates
) as number[];
update: (feature: IEncodeFeature,featureIdx: number,vertice) => {
let coordinates;
if (feature.version === 'GAODE2.x') {
coordinates = feature.originCoordinates;
} else {
const { coverage = 1, angle } = this.layer.getLayerConfig() as IHeatMapLayerStyleOptions;
const { xOffset, yOffset } = this.layer.getSource().data;
const rotationMatrix = mat2.create();
mat2.rotate(rotationMatrix, rotationMatrix, angle);
const offset = vec2.create();
const vertices = vec2.fromValues(vertice[0], vertice[1]);
vec2.multiply(offset, vertices, vec2.fromValues(xOffset, yOffset));
vec2.multiply(offset, offset, vec2.fromValues(coverage, coverage));
vec2.transformMat2(offset, offset, rotationMatrix);
const lngLat = transformLnglat(
[feature.coordinates[0] + offset[0], feature.coordinates[1] + offset[1]],
this.mapService.map,
256 << 20,
);
if (this.mapService.coordinateSystemService.getCoordinateSystem() === CoordinateSystem.LNGLAT_OFFSET) {
coordinates = lngLat;
} else {
coordinates = transformOffset(lngLat, this.mapService.map, 512);
}
}
return [coordinates[0], coordinates[1], 0];
},
},
Expand Down
3 changes: 2 additions & 1 deletion packages/layers/src/heatmap/shaders/grid_vert.glsl
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,8 @@ void main() {
vec4 project_pos = project_position(vec4(customLnglat, 0, 1.0));
gl_Position = u_Mvp * (project_pos);
} else {
vec2 lnglat = unProjectFlat(a_Pos.xy + offset);
// vec2 lnglat = unProjectFlat(a_Pos.xy + offset)
vec2 lnglat = a_Pos.xy;
vec4 project_pos = project_position(vec4(lnglat, 0, 1.0));
gl_Position = project_common_position_to_clipspace(project_pos);
}
Expand Down
12 changes: 8 additions & 4 deletions packages/layers/src/plugins/DataMappingPlugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,7 @@ export default class DataMappingPlugin implements ILayerPlugin {
const encodeRecord: IEncodeFeature = {
id: record._id,
coordinates: record.coordinates,
originCoordinates: record.originCoordinates,
...preRecord,
};

Expand Down Expand Up @@ -222,10 +223,13 @@ this.adjustData2MapboxCoordinates(mappedData);
) {
mappedData.map((d) => {
d.version = Version['MAPBOX'];
// @ts-ignore
d.originCoordinates = cloneDeep(d.coordinates);
// @ts-ignore
d.coordinates = this.getMapboxCoordiantes(d.coordinates);
if(!d.originCoordinates){
// @ts-ignore
d.originCoordinates = cloneDeep(d.coordinates);
// @ts-ignore
d.coordinates = this.getMapboxCoordiantes(d.coordinates);
}

});
}
}
Expand Down
3 changes: 0 additions & 3 deletions packages/layers/src/plugins/ShaderUniformPlugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,11 +45,9 @@ export default class ShaderUniformPlugin implements ILayerPlugin {
if (zoom <= 12 && this.mapZoom > 12) {
await layer.hooks.init.promise();
this.mapZoom = zoom;
console.log(111);
}
if (zoom > 12 && this.mapZoom <= 12) {
await layer.hooks.init.promise();
console.log(22222);

this.mapZoom = zoom;
}
Expand Down Expand Up @@ -84,7 +82,6 @@ export default class ShaderUniformPlugin implements ILayerPlugin {
// @ts-ignore
sceneCenterMercator = this.mapService.getCustomCoordCenter();
}
console.log(this.cameraService.getZoom(), this.cameraService.getViewProjectionMatrix(),this.coordinateSystemService.getViewportCenterProjection())
const { width, height } = this.rendererService.getViewportSize();
layer.models.forEach((model) => {
model.addUniforms({
Expand Down
35 changes: 35 additions & 0 deletions packages/maps/src/mapbox/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,19 @@ export function fromWGS84(
// @ts-ignore
return map.getCRS().fromWGS84([lng, lat]);
}


export function toWGS84(
coor: [number, number] | undefined,
map: mapboxgl.Map | maplibregl.Map,
) {
if (!coor) return;
const [x, y] = coor || [];
// @ts-ignore
return map.getCRS().toWGS84([x, y]);
}


// mapboxgl多坐标系,获取extent
export function getCRSExtent(map: mapboxgl.Map) {
// @ts-ignore
Expand Down Expand Up @@ -47,6 +60,28 @@ export function transformOffset(
const yScale = ((origin[1] - coor[1]) / height) * worldScales;
return [xScale, yScale];
}
export function transformLnglat(
xy: [number, number],
map: mapboxgl.Map,
worldScale?: number,
targetLnglat?: [number, number],
): [number, number] {
if (!map) {
return xy;
}

const zoom = map.getZoom();
const worldScales = worldScale || getScaleByZoom(zoom);
const extent = getCRSExtent(map);
const width = extent[2] - extent[0];
const height = extent[3] - extent[1];
const origin = targetLnglat
? fromWGS84(targetLnglat, map)
: [extent[0], extent[3]];
const y = origin[1] - (((xy[1]/worldScales)) * height)
const x = (xy[0]/ worldScales * width) + origin[0];
return toWGS84([x,y], map);
}

export function isMultiCoor(map: any): boolean {
if (!map) {
Expand Down
5 changes: 5 additions & 0 deletions packages/source/src/transform/grid.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ const R_EARTH = 6378000;
export function aggregatorToGrid(data: IParserData, option: ITransform) {
const dataArray = data.dataArray;
const { size = 10 } = option;
// 计算出的是当前size在20级时对应的像素值/2
const pixlSize = ((size / (2 * Math.PI * R_EARTH)) * (256 << 20)) / 2;
const { gridHash, gridOffset } = _pointsGridHash(dataArray, size);
const layerData = _getGridLayerDataFromGridHash(gridHash, gridOffset, option);
Expand Down Expand Up @@ -95,6 +96,10 @@ function _getGridLayerDataFromGridHash(
}
Object.assign(item, {
_id: i,
originCoordinates:[
-180 + gridOffset.xOffset * (lonIdx + 0.5),
-90 + gridOffset.yOffset * (latIdx + 0.5),
],
coordinates: aProjectFlat([
-180 + gridOffset.xOffset * (lonIdx + 0.5),
-90 + gridOffset.yOffset * (latIdx + 0.5),
Expand Down
31 changes: 16 additions & 15 deletions packages/utils/src/geo.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
Units,
} from '@turf/helpers';
import { isNumber } from './math';
import { transformOffset } from '../../maps/src/mapbox';

export type IBounds = [[number, number], [number, number]];

Expand Down Expand Up @@ -165,21 +166,21 @@ export function validateLngLat(lnglat: Point, validate: boolean): Point {
return lnglat.length === 3 ? [lng, lat, lnglat[2]] : [lng, lat];
}
export function aProjectFlat(lnglat: number[]) {
const maxs = 85.0511287798;
const lat = Math.max(Math.min(maxs, lnglat[1]), -maxs);
const scale = 256 << 20;
let d = Math.PI / 180;
let x = lnglat[0] * d;
let y = lat * d;
y = Math.log(Math.tan(Math.PI / 4 + y / 2));

const a = 0.5 / Math.PI;
const b = 0.5;
const c = -0.5 / Math.PI;
d = 0.5;
x = scale * (a * x + b);
y = scale * (c * y + d);
return [Math.floor(x), Math.floor(y)];
// const maxs = 85.0511287798;
// const lat = Math.max(Math.min(maxs, lnglat[1]), -maxs);
// const scale = 256 << 20;
// let d = Math.PI / 180;
// let x = lnglat[0] * d;
// let y = lat * d;
// y = Math.log(Math.tan(Math.PI / 4 + y / 2));
// const a = 0.5 / Math.PI;
// const b = 0.5;
// const c = -0.5 / Math.PI;
// d = 0.5;
// x = scale * (a * x + b);
// y = scale * (c * y + d);
// return [Math.floor(x), Math.floor(y)];
return transformOffset(lnglat,window.map,Math.pow(2,20)*256)
}
export function unProjectFlat(px: number[]): [number, number] {
const a = 0.5 / Math.PI;
Expand Down

0 comments on commit 3be6803

Please sign in to comment.