docs: update covid demo

This commit is contained in:
thinkinggis 2020-03-16 18:06:21 +08:00
parent f690cbfcdf
commit 6eec1a19bc
21 changed files with 288 additions and 79 deletions

View File

@ -77,9 +77,10 @@ const World = React.memo(function Map() {
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
fetch('https://lab.isaaclin.cn/nCoV/api/area?latest=1').then((d) =>
d.json(),
),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
]);
const worldData = joinData(geoData, ncovData.results);
const pointdata = worldData.features.map((feature: any) => {
@ -221,4 +222,4 @@ const World = React.memo(function Map() {
</>
);
});
ReactDOM.render(<World />, document.getElementById('map'));
ReactDOM.render(<World />, document.getElementById('map'));

View File

@ -86,9 +86,10 @@ const World = React.memo(function Map() {
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
fetch('https://lab.isaaclin.cn/nCoV/api/area?latest=1').then((d) =>
d.json(),
),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
]);
const worldData = joinData(geoData, ncovData.results);
const pointdata = worldData.features.map((feature: any) => {

View File

@ -71,9 +71,10 @@ const World = React.memo(function Map() {
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
fetch('https://lab.isaaclin.cn/nCoV/api/area?latest=1').then((d) =>
d.json(),
),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
]);
const worldData = joinData(geoData, ncovData.results);
const pointdata = worldData.features.map((feature: any) => {

View File

@ -70,9 +70,10 @@ const World = React.memo(function Map() {
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
fetch('https://lab.isaaclin.cn/nCoV/api/area?latest=1').then((d) =>
d.json(),
),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
]);
setData(joinData(geoData, ncovData.results));
};
@ -168,4 +169,4 @@ const World = React.memo(function Map() {
</>
);
});
ReactDOM.render(<World />, document.getElementById('map'));
ReactDOM.render(<World />, document.getElementById('map'));

View File

@ -71,9 +71,10 @@ const World = React.memo(function Map() {
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
fetch('https://lab.isaaclin.cn/nCoV/api/area?latest=1').then((d) =>
d.json(),
),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
]);
setData(joinData(geoData, ncovData.results));
};

View File

@ -0,0 +1,225 @@
import {
HeatmapLayer,
LayerEvent,
LineLayer,
MapboxScene,
Marker,
PointLayer,
PolygonLayer,
Popup,
} from '@antv/l7-react';
import * as React from 'react';
import ReactDOM from 'react-dom';
const colors =
['#f7fcf0','#e0f3db','#ccebc5','#a8ddb5','#7bccc4','#4eb3d3','#2b8cbe','#08589e'].reverse();
function joinData(geodata: any, ncovData: any) {
const ncovDataObj: any = {};
ncovData.forEach((item: any) => {
const {
countryName,
countryEnglishName,
currentConfirmedCount,
confirmedCount,
suspectedCount,
curedCount,
deadCount,
} = item;
if (countryName === '中国') {
if (!ncovDataObj[countryName]) {
ncovDataObj[countryName] = {
countryName,
countryEnglishName,
currentConfirmedCount: 0,
confirmedCount: 0,
suspectedCount: 0,
curedCount: 0,
deadCount: 0,
};
} else {
ncovDataObj[countryName].currentConfirmedCount += currentConfirmedCount;
ncovDataObj[countryName].confirmedCount += confirmedCount;
ncovDataObj[countryName].suspectedCount += suspectedCount;
ncovDataObj[countryName].curedCount += curedCount;
ncovDataObj[countryName].deadCount += deadCount;
}
} else {
ncovDataObj[countryName] = {
countryName,
countryEnglishName,
currentConfirmedCount,
confirmedCount,
suspectedCount,
curedCount,
deadCount,
};
}
});
const geoObj: any = {};
geodata.features.forEach((feature: any) => {
const { name } = feature.properties;
geoObj[name] = feature.properties;
const ncov = ncovDataObj[name] || {};
feature.properties = {
...feature.properties,
...ncov,
};
});
return geodata;
}
const World = React.memo(function Map() {
const [data, setData] = React.useState();
const [filldata, setfillData] = React.useState();
const [popupInfo, setPopupInfo] = React.useState<{
lnglat: number[];
feature: any;
}>();
React.useEffect(() => {
const fetchData = async () => {
const [geoData, ncovData, gridData] = await Promise.all([
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/e62a2f3b-ea99-4c98-9314-01d7c886263d.json',
).then((d) => d.json()),
// https://lab.isaaclin.cn/nCoV/api/area?latest=1
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/0676f102-22f6-4c75-ab12-1ae200834b1c.json',
).then((d) => d.json()),
fetch(
'https://gw.alipayobjects.com/os/bmw-prod/8990e8b4-c58e-419b-afb9-8ea3daff2dd1.json',
).then((d) => d.json()),
]);
const worldData = joinData(geoData, ncovData.results);
const pointdata = worldData.features.map((feature: any) => {
return feature.properties;
});
setfillData(gridData);
setData(pointdata);
};
fetchData();
}, []);
function showPopup(args: any): void {
setPopupInfo({
lnglat: args.lngLat,
feature: args.feature,
});
}
return (
<>
<MapboxScene
map={{
center: [110.19382669582967, 50.258134],
pitch: 0,
style: 'blank',
zoom: 1,
}}
style={{
position: 'absolute',
top: 0,
left: 0,
right: 0,
bottom: 0,
}}
>
{popupInfo && (
<Popup lnglat={popupInfo.lnglat}>
{popupInfo.feature.name}
<ul
style={{
margin: 0,
}}
>
<li>:{popupInfo.feature.currentConfirmedCount}</li>
<li>:{popupInfo.feature.confirmedCount}</li>
<li>:{popupInfo.feature.curedCount}</li>
<li>:{popupInfo.feature.deadCount}</li>
</ul>
</Popup>
)}
{data && [
<HeatmapLayer
key={'1'}
source={{
data: filldata,
transforms: [
{
type: 'hexagon',
size: 500000,
field: 'capacity',
method: 'sum',
},
],
}}
color={{
values: 'rgb(221,230,238)',
}}
shape={{
values: 'hexagon',
}}
style={{
coverage: 0.7,
angle: 0.3,
opacity: 0.8,
}}
/>,
<PointLayer
key={'2'}
options={{
autoFit: true,
}}
source={{
data,
parser: {
type: 'json',
coordinates: 'centroid',
},
}}
scale={{
values: {
confirmedCount: {
type: 'log',
},
},
}}
color={{
field: 'confirmedCount',
values: (count) => {
return count > 10000
? colors[6]
: count > 1000
? colors[5]
: count > 500
? colors[4]
: count > 100
? colors[3]
: count > 10
? colors[2]
: count > 1
? colors[1]
: colors[0];
},
}}
shape={{
values: 'circle',
}}
active={{
option: {
color: '#0c2c84',
},
}}
size={{
field: 'confirmedCount',
values: [0, 20],
}}
style={{
opacity: 0.6,
}}
>
<LayerEvent type="mousemove" handler={showPopup} />
</PointLayer>,
]}
</MapboxScene>
</>
);
});
ReactDOM.render(<World />, document.getElementById('map'));

View File

@ -4,6 +4,11 @@
"en": "COVID-19 Map"
},
"demos": [
{
"filename": "covid_grid.tsx",
"title": "世界地图网格背景",
"screenshot": "https://gw.alipayobjects.com/mdn/rms_855bab/afts/img/A*YYNtRZpxH_4AAAAAAAAAAABkARQnAQ"
},
{
"filename": "covid_animate.tsx",
"title": "气泡动图",

View File

@ -88,7 +88,11 @@ export default class InteractionService extends EventEmitter
}
}
private onTouch = (target: TouchEvent) => {
const touch = target.touches[0];
target.stopPropagation();
if (target.targetTouches.length > 1) {
return;
}
const touch = target.targetTouches[0];
// @ts-ignore
this.onHover({
x: touch.pageX,
@ -117,7 +121,9 @@ export default class InteractionService extends EventEmitter
this.isDoubleTap(x, y, lngLat);
return;
}
this.emit(InteractionEvent.Hover, { x, y, lngLat, type });
if (type !== 'click' || type !== 'click') {
this.emit(InteractionEvent.Hover, { x, y, lngLat, type });
}
};
private isDoubleTap(x: number, y: number, lngLat: ILngLat) {

View File

@ -6,7 +6,6 @@ import {
IShaderModuleService,
} from '../../index';
import { TYPES } from '../../types';
import { ICameraService } from '../camera/ICameraService';
import {
IInteractionService,
IInteractionTarget,
@ -102,43 +101,11 @@ export default class PickingService implements IPickingService {
});
});
}
private async pickingLayer(layer: ILayer, target: IInteractionTarget) {
const { getViewportSize, useFramebuffer, clear } = this.rendererService;
const { width, height } = getViewportSize();
if (this.width !== width || this.height !== height) {
this.pickingFBO.resize({
width: Math.round(width / PICKSCALE),
height: Math.round(height / PICKSCALE),
});
this.width = width;
this.height = height;
}
useFramebuffer(this.pickingFBO, () => {
clear({
framebuffer: this.pickingFBO,
color: [0, 0, 0, 0],
stencil: 0,
depth: 1,
});
layer.hooks.beforePickingEncode.call();
layer.renderModels();
layer.hooks.afterPickingEncode.call();
this.pickFromPickingFBO(layer, target);
});
}
private pickFromPickingFBO = (
layer: ILayer,
{ x, y, lngLat, type }: IInteractionTarget,
) => {
const {
getViewportSize,
readPixels,
useFramebuffer,
} = this.rendererService;
const { getViewportSize, readPixels } = this.rendererService;
const { width, height } = getViewportSize();
const { enableHighlight, enableSelect } = layer.getLayerConfig();
@ -247,28 +214,10 @@ export default class PickingService implements IPickingService {
) {
const [r, g, b] = pickedColors;
layer.hooks.beforeHighlight.call([r, g, b]);
// this.layerService.renderLayers();
}
private selectFeature(layer: ILayer, pickedColors: Uint8Array | undefined) {
const [r, g, b] = pickedColors;
layer.hooks.beforeSelect.call([r, g, b]);
// this.layerService.renderLayers();
}
private selectFeatureHandle(
layer: ILayer,
{ featureId }: Partial<IInteractionTarget>,
) {
const pickedColors = encodePickingColor(featureId as number);
this.selectFeature(layer, new Uint8Array(pickedColors));
}
private highlightFeatureHandle(
layer: ILayer,
{ featureId }: Partial<IInteractionTarget>,
) {
const pickedColors = encodePickingColor(featureId as number);
this.highlightPickedFeature(layer, new Uint8Array(pickedColors));
}
}

View File

@ -287,7 +287,8 @@ export default class Scene extends EventEmitter implements ISceneService {
w = bounds.right - bounds.left;
h = bounds.bottom - bounds.top;
}
const canvas = this.$container?.getElementsByTagName('canvas')[0];
// this.$container.
this.rendererService.viewport({
x: 0,
y: 0,
@ -297,6 +298,10 @@ export default class Scene extends EventEmitter implements ISceneService {
// 触发 Map canvas
DOM.triggerResize();
this.coordinateSystemService.needRefresh = true;
if (canvas) {
canvas.width = w * pixelRatio;
canvas.height = h * pixelRatio;
}
// repaint layers
this.render();
}

View File

@ -27,7 +27,7 @@
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-polyfill/7.8.3/polyfill.min.js"></script>
<script src="https://api.mapbox.com/mapbox-gl-js/v1.8.0/mapbox-gl.js"></script>
<script src="../dist/l7-dev.js"></script>
<script src="../dist/l7.js"></script>
<script>
console.log(L7);
const scene = new L7.Scene({

View File

@ -27,7 +27,7 @@
<!-- <script src="https://cdn.jsdelivr.net/npm/symbol-es6@0.1.2/symbol-es6.min.js"></script> -->
<script src="https://api.mapbox.com/mapbox-gl-js/v1.8.0/mapbox-gl.js"></script>
<script src="../dist/l7-dev.js"></script>
<script src="../dist/l7.js"></script>
<script>
console.log(L7);
const scene = new L7.Scene({

View File

@ -27,7 +27,7 @@
<!-- <script src="https://cdn.jsdelivr.net/npm/symbol-es6@0.1.2/symbol-es6.min.js"></script> -->
<script src="https://api.mapbox.com/mapbox-gl-js/v1.8.0/mapbox-gl.js"></script>
<script src="../dist/l7-dev.js"></script>
<script src="../dist/l7.js"></script>
<script>
console.log(L7);
const scene = new L7.Scene({

View File

@ -28,7 +28,7 @@
<!-- <script src="https://cdn.jsdelivr.net/npm/symbol-es6@0.1.2/symbol-es6.min.js"></script> -->
<script src="https://api.mapbox.com/mapbox-gl-js/v1.8.0/mapbox-gl.js"></script>
<script src="../dist/l7-dev.js"></script>
<script src="../dist/l7.js"></script>
<script>
const data =
{"type":"FeatureCollection","features":[

View File

@ -27,7 +27,7 @@
<!-- <script src="https://cdn.jsdelivr.net/npm/symbol-es6@0.1.2/symbol-es6.min.js"></script> -->
<script src="https://api.mapbox.com/mapbox-gl-js/v1.8.0/mapbox-gl.js"></script>
<script src="../dist/l7-dev.js"></script>
<script src="../dist/l7.js"></script>
<script>
console.log(L7);
const scene = new L7.Scene({

View File

@ -12,16 +12,19 @@ import heatmapGridFrag from '../shaders/hexagon_frag.glsl';
interface IHeatMapLayerStyleOptions {
opacity: number;
coverage: number;
angle: number;
}
export default class GridModel extends BaseModel {
public getUninforms(): IModelUniform {
const {
opacity,
coverage,
angle,
} = this.layer.getLayerConfig() as IHeatMapLayerStyleOptions;
return {
u_opacity: opacity || 1.0,
u_coverage: coverage || 0.9,
u_angle: angle || 0,
u_radius: [
this.layer.getSource().data.xOffset,
this.layer.getSource().data.yOffset,
@ -38,6 +41,7 @@ export default class GridModel extends BaseModel {
triangulation: HeatmapGridTriangulation,
depth: { enable: false },
primitive: gl.TRIANGLES,
blend: this.getBlend(),
}),
];
}

View File

@ -13,16 +13,19 @@ import heatmapGridFrag from '../shaders/hexagon_frag.glsl';
interface IHeatMapLayerStyleOptions {
opacity: number;
coverage: number;
angle: number;
}
export default class Grid3DModel extends BaseModel {
public getUninforms(): IModelUniform {
const {
opacity,
coverage,
angle,
} = this.layer.getLayerConfig() as IHeatMapLayerStyleOptions;
return {
u_opacity: opacity || 1.0,
u_coverage: coverage || 1.0,
u_angle: angle || 0,
u_radius: [
this.layer.getSource().data.xOffset,
this.layer.getSource().data.yOffset,
@ -38,6 +41,7 @@ export default class Grid3DModel extends BaseModel {
fragmentShader: heatmapGridFrag,
triangulation: PointExtrudeTriangulation,
depth: { enable: true },
blend: this.getBlend(),
}),
];
}

View File

@ -22,6 +22,7 @@ interface IHeatMapLayerStyleOptions {
opacity: number;
intensity: number;
radius: number;
angle: number;
rampColors: IColorRamp;
}

View File

@ -13,6 +13,7 @@ import heatmapGridVert from '../shaders/hexagon_vert.glsl';
interface IHeatMapLayerStyleOptions {
opacity: number;
coverage: number;
angle: number;
}
export default class HexagonModel extends BaseModel {
@ -20,10 +21,12 @@ export default class HexagonModel extends BaseModel {
const {
opacity,
coverage,
angle,
} = this.layer.getLayerConfig() as IHeatMapLayerStyleOptions;
return {
u_opacity: opacity || 1.0,
u_coverage: coverage || 0.9,
u_angle: angle || 0,
u_radius: [
this.layer.getSource().data.xOffset,
this.layer.getSource().data.yOffset,
@ -40,6 +43,7 @@ export default class HexagonModel extends BaseModel {
triangulation: HeatmapGridTriangulation,
depth: { enable: false },
primitive: gl.TRIANGLES,
blend: this.getBlend(),
}),
];
}

View File

@ -62,6 +62,7 @@ export default class FillModel extends BaseModel {
fragmentShader: pointFillFrag,
triangulation: PointFillTriangulation,
depth: { enable: false },
blend: this.getBlend(),
}),
];
}

View File

@ -18,7 +18,7 @@ const PointLayer = React.memo(function Layer(
return BaseLayer('pointLayer', props);
});
const HeatMapLayer = React.memo(function Layer(
const HeatmapLayer = React.memo(function Layer(
props: ILayerProps & { children?: any },
) {
return BaseLayer('heatmapLayer', props);
@ -46,7 +46,7 @@ export {
PolygonLayer,
LineLayer,
PointLayer,
HeatMapLayer,
HeatmapLayer,
RasterLayer,
ImageLayer,
CityBuildingLayer,