diff --git a/docs/api/layer/layer.zh.md b/docs/api/layer/layer.zh.md
index 4b2af44899..78ca4aa56d 100644
--- a/docs/api/layer/layer.zh.md
+++ b/docs/api/layer/layer.zh.md
@@ -532,6 +532,18 @@ layer.select(false);
layer.setSelect(id);
```
+### getLegendItems
+
+获取图例配置
+
+#### 参数
+
+- name 获取的图例类型 `color|size`
+
+```ts
+layer.getLegendItems('color');
+```
+
## 鼠标事件
鼠标事件回调参数 target
diff --git a/gatsby-config.js b/gatsby-config.js
index 218ec551ba..0ec9d6b854 100644
--- a/gatsby-config.js
+++ b/gatsby-config.js
@@ -39,6 +39,66 @@ module.exports = {
}
}
],
+ ecosystems: [
+ {
+ name: {
+ zh: 'L7 React组件',
+ en: 'L7React L7 For React',
+ },
+ url: 'http://antv.vision/L7-react/',
+ },
+ {
+ name: {
+ zh: 'L7 地理围栏绘制组件库',
+ en: 'L7Draw',
+ },
+ url: 'http://antv.vision/L7-draw/',
+ },
+ {
+ name: {
+ zh: 'L7 行政区划可视化库',
+ en: 'L7Boundary',
+ },
+ url: 'http://antv.vision/L7-boundary/',
+ },
+ {
+ name: {
+ zh: '地理可视分开发框架',
+ en: 'Dipper',
+ },
+ url: 'http://antv.vision/Dipper',
+ },
+ ],
+ Dipper: [
+ {
+ name: {
+ zh: 'L7 React组件',
+ en: 'L7React L7 For React',
+ },
+ url: 'http://antv.vision/L7-react/',
+ },
+ {
+ name: {
+ zh: 'L7Draw 地理围栏绘制组件库',
+ en: 'L7Draw',
+ },
+ url: 'http://antv.vision/L7-draw/',
+ },
+ {
+ name: {
+ zh: 'L7Plot',
+ en: 'L7Plot',
+ },
+ url: 'http://antv.vision/L7-draw/',
+ },
+ {
+ name: {
+ zh: 'L7Boundary 行政区划可视化库',
+ en: 'L7Boundary',
+ },
+ url: 'http://antv.vision/L7-boundary/',
+ },
+ ],
docs: [
{
slug: 'api/l7',
diff --git a/package.json b/package.json
index 0990165218..25a997cf09 100644
--- a/package.json
+++ b/package.json
@@ -6,9 +6,10 @@
"url": "https://github.com/antvis/L7"
},
"devDependencies": {
- "@antv/dipper": "^0.0.5",
- "@antv/dipper-widgets": "^0.0.5",
+ "@antv/dipper": "0.0.6",
+ "@antv/dipper-widgets": "0.0.6",
"@antv/g2": "^3.5.9",
+ "@antv/g2plot": "^2.3.40",
"@antv/gatsby-theme-antv": "^1.1.1",
"@antv/l7-district": "^2.3.9",
"@antv/l7-draw": "^2.3.40",
@@ -89,6 +90,7 @@
"jest-styled-components": "^6.2.1",
"lerna": "^3.16.4",
"lint-staged": "^9.2.4",
+ "mockjs": "^1.1.0",
"npm-run-all": "^4.1.5",
"popmotion": "^9.4.2",
"postcss": "^7.0.18",
diff --git a/site/components/Dipper/index.tsx b/site/components/Dipper/index.tsx
new file mode 100644
index 0000000000..9496845a91
--- /dev/null
+++ b/site/components/Dipper/index.tsx
@@ -0,0 +1,36 @@
+// eslint-disable-next-line no-unused-vars
+import React from 'react';
+import '../../css/dipper.css';
+
+interface DipperProps {
+ dipper: {
+ title: string;
+ image: string;
+ link: string
+ }[]
+}
+
+export function Dipper(props: DipperProps) {
+ const { dipper } = props;
+
+ const jumoDemo = (url: string) => {
+ window.open(url, '_blank');
+ };
+
+ return (
+
+
Dipper 地理分析应用开发框架
+
Dipper 是基于 L7 地理分析应用开发框架,用于快速构建和开发地理分析应用。用户通过组件化、模块化低代码的方式配置地图分析、指挥类应用。
+
+ {dipper.map(item => {
+ return (
+
+
+
{item.title}
+
+ );
+ })}
+
+
+ );
+}
diff --git a/site/components/DipperMap/index.tsx b/site/components/DipperMap/index.tsx
new file mode 100644
index 0000000000..6ca385247c
--- /dev/null
+++ b/site/components/DipperMap/index.tsx
@@ -0,0 +1,43 @@
+// eslint-disable-next-line no-unused-vars
+import { Carousel } from 'antd';
+import React from 'react';
+import '../../css/dippermap.css';
+
+interface DipperMapProps {
+ dippermap: {
+ desc: string;
+ img: string;
+ alt: string
+ }[]
+}
+
+export function DipperMap(props: DipperMapProps) {
+ const { dippermap } = props;
+
+ const jumpDipperMap = (url: string) => {
+ window.open(url, '_blank');
+ };
+
+ return (
+
+
Dipper Map 地理可视化分析工具
+
DipperMap 基于L7 地图可视分析工具,用户自由上传地理数据进行可视化化配置。
+
+
+ {dippermap.map(item => {
+ return (
+
+
{item.desc}
+
+
+ );
+ })}
+
+
+
+ );
+}
diff --git a/site/components/analysis/components/Bar/index.tsx b/site/components/analysis/components/Bar/index.tsx
new file mode 100644
index 0000000000..96e57e7860
--- /dev/null
+++ b/site/components/analysis/components/Bar/index.tsx
@@ -0,0 +1,43 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Bar } from '@antv/g2plot';
+
+export interface ChatData {
+ data: object[];
+ legend?: boolean;
+ loading?: boolean;
+}
+
+export function BarCahrt({ data }: ChatData) {
+ const id = useRef();
+ const [barplot, setBarplot] = useState();
+ useEffect(() => {
+ if (!barplot && id.current) {
+ const bar = new Bar(id.current, {
+ // @ts-ignore
+ data: data.sort((a, b) => b.xField - a.xField),
+ autoFit: true,
+ xField: 'yField',
+ yField: 'xField',
+ xAxis: false,
+ label: {
+ position: 'left',
+ style: {
+ fill: '#fff',
+ },
+ },
+ legend: {
+ position: 'top-left',
+ },
+ });
+
+ bar.render();
+ setBarplot(bar);
+ } else {
+ barplot.update({
+ data,
+ });
+ }
+ }, [id.current, data]);
+
+ return ;
+}
diff --git a/site/components/analysis/components/Line/index.tsx b/site/components/analysis/components/Line/index.tsx
new file mode 100644
index 0000000000..f03969bb13
--- /dev/null
+++ b/site/components/analysis/components/Line/index.tsx
@@ -0,0 +1,36 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Line } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+import { Spin } from 'antd';
+
+export function LineCahrt({ data, loading }: ChatData) {
+ const id = useRef();
+ const [lineplot, setLinePlot] = useState();
+
+ useEffect(() => {
+ if (!lineplot && id.current && data) {
+ const lineplot = new Line(id.current, {
+ data,
+ autoFit: true,
+ xField: 'xField',
+ yField: 'yField',
+ seriesField: 'series',
+ legend: {
+ position: 'top-left',
+ },
+ });
+ lineplot.render();
+ setLinePlot(lineplot);
+ } else {
+ lineplot.update({
+ data,
+ });
+ }
+ }, [id.current, data]);
+
+ return (
+
+
+
+ );
+}
diff --git a/site/components/analysis/components/Pie/index.tsx b/site/components/analysis/components/Pie/index.tsx
new file mode 100644
index 0000000000..0738922d0f
--- /dev/null
+++ b/site/components/analysis/components/Pie/index.tsx
@@ -0,0 +1,44 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Pie } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+import { Spin } from 'antd';
+
+export function PieChart({ data, legend, loading }: ChatData) {
+ const id = useRef();
+ const [pieplot, setPiePlot] = useState();
+
+ useEffect(() => {
+ if (!pieplot && id.current && data) {
+ const pie = new Pie(id.current, {
+ data,
+ autoFit: true,
+ angleField: 'xField',
+ colorField: 'yField',
+ radius: 0.7,
+ label: {
+ type: 'spider',
+ labelHeight: 28,
+ content: '{name}\n{percentage}',
+ },
+ legend: legend
+ ? {
+ position: 'top-left',
+ }
+ : false,
+ });
+
+ pie.render();
+ setPiePlot(pie);
+ } else {
+ pieplot.update({
+ data,
+ });
+ }
+ }, [id.current, data]);
+
+ return (
+
+
+
+ );
+}
diff --git a/site/components/analysis/components/SingleLine/index.tsx b/site/components/analysis/components/SingleLine/index.tsx
new file mode 100644
index 0000000000..f0513b1319
--- /dev/null
+++ b/site/components/analysis/components/SingleLine/index.tsx
@@ -0,0 +1,28 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Line } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+
+export function SingleLineCahrt({ data }: ChatData) {
+ const id = useRef();
+ const [lineplot, setLinePlot] = useState();
+
+
+ useEffect(() => {
+ if (!lineplot && id.current && data) {
+ const area = new Line(id.current, {
+ data,
+ autoFit: true,
+ xField: 'xField',
+ yField: 'yField',
+ });
+ area.render();
+ setLinePlot(area);
+ }else{
+ lineplot.update({
+ data
+ })
+ }
+ }, [id.current,data]);
+
+ return ;
+}
diff --git a/site/components/analysis/components/StackArea/index.tsx b/site/components/analysis/components/StackArea/index.tsx
new file mode 100644
index 0000000000..97ffaf2ce1
--- /dev/null
+++ b/site/components/analysis/components/StackArea/index.tsx
@@ -0,0 +1,42 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Area } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+
+export function StackAreaCahrt({ data }: ChatData) {
+ const id = useRef();
+ const [pieplot, setAreaPlot] = useState
();
+ const [list,setData] = useState([])
+
+ useEffect(()=>{
+ fetch('https://gw.alipayobjects.com/os/bmw-prod/b21e7336-0b3e-486c-9070-612ede49284e.json')
+ .then((res) => res.json())
+ .then((data) => {
+ setData(data);
+ });
+ },[])
+
+
+
+ useEffect(() => {
+ if (!pieplot && id.current && list) {
+ const area = new Area(id.current, {
+ data:list,
+ autoFit: true,
+ xField: 'date',
+ yField: 'value',
+ seriesField: 'country',
+ legend:{
+ position:'top-left'
+ }
+ });
+ area.render();
+ setAreaPlot(area);
+ }else{
+ pieplot.update({
+ data:list
+ })
+ }
+ }, [id.current,data]);
+
+ return
;
+}
diff --git a/site/components/rumbling/configs/config.ts b/site/components/analysis/configs/config.ts
similarity index 70%
rename from site/components/rumbling/configs/config.ts
rename to site/components/analysis/configs/config.ts
index 7624c934aa..78a6c16e0c 100644
--- a/site/components/rumbling/configs/config.ts
+++ b/site/components/analysis/configs/config.ts
@@ -4,30 +4,20 @@ export const config: Partial
= {
viewData: {
global: {
filterData: [],
- sceneCode: 'iot_terminal_dominant',
areaCode: '330100',
view: 'task',
},
widgets: {
citySelect: {
options: CityList,
- value: [330000, 330100],
+ value: ['330000', '330100'],
},
},
},
headerbar: {
display: true,
- logo: {
- display: true,
- value:
- 'https://gw.alipayobjects.com/mdn/rms_855bab/afts/img/A*ObVJT4IxmlkAAAAAAAAAAAAAARQnAQ',
- style: {
- height: '24px',
- width: '24px',
- },
- },
title: {
- value: '区代指挥中心',
+ value: '数据分析',
display: true,
},
children: [
@@ -41,21 +31,6 @@ export const config: Partial = {
action: 'queryArea',
},
},
- {
- display: true,
- options: [
- {
- label: '热区分析',
- value: 'hotspot',
- },
- {
- label: '任务管理',
- value: 'task',
- },
- ],
- position: 'center',
- type: 'navibar',
- },
{
display: false,
position: 'right',
@@ -69,24 +44,37 @@ export const config: Partial = {
},
panel: {
display: true,
- enableToggle: true,
- defaultTitle: '所有网格',
- opened: true,
- width: 360,
+ options: {
+ enableToggle: true,
+ defaultTitle: '所有网格',
+ opened: true,
+ width: 426,
+ },
position: 'right',
children: [
{
- type: 'siderbartabcontent',
+ display: true,
+ type: 'meshName',
+ title: '网格名称',
+ },
+ {
+ display: true,
+ type: 'meshchart',
+ title: '所有网格数据',
+ },
+ {
+ display: false,
+ type: 'panelTabContent',
title: '所有网格',
children: [
{
display: true,
type: 'mesh_indicator',
- title: '数据查看',
+ title: '业务数据',
},
{
type: 'total_data_panel',
- title: '地图面板',
+ title: '人员数据',
},
],
},
@@ -106,9 +94,27 @@ export const config: Partial = {
{
display: true,
position: 'topleft',
+ type: 'filter',
+ title: '筛选',
+ },
+ {
+ display: true,
+ position: 'bottomright',
+ type: 'location',
+ title: '定位',
+ },
+ {
+ display: true,
+ position: 'bottomright',
type: 'mapStyle',
title: '地图样式',
},
+ {
+ display: true,
+ position: 'topleft',
+ type: 'searchPlaces',
+ title: '地区搜索',
+ },
],
defaultcontrols: [
{
@@ -136,7 +142,7 @@ export const config: Partial = {
},
fill: {
field: 'unit_price',
- color: SingleSequentialColorScale.Blue,
+ color: ['#A9D3FF', '#82B1FF', '#6294FF', '#457BFF', '#2962FF'],
bandNum: 5,
scale: 'quantile',
unknownName: '无类型',
diff --git a/site/components/analysis/configs/mock.ts b/site/components/analysis/configs/mock.ts
new file mode 100644
index 0000000000..12c10f37b3
--- /dev/null
+++ b/site/components/analysis/configs/mock.ts
@@ -0,0 +1,267 @@
+import Mock from 'mockjs';
+
+// 单折线图
+export const singleLineChart = () => {
+ const data = Mock.mock({
+ 'list|9': [
+ {
+ // 生成长度在 100~1000 之间的小写字母
+ yField: '@integer(0,5000)',
+ },
+ ],
+ });
+ return data.list
+ .sort((a, b) => a.yField - b.yField)
+ .map((item, index) => {
+ return {
+ xField: `${index + 1}月`,
+ ...item,
+ };
+ });
+};
+
+// 条形图
+export const barChart = () => {
+ let xField = ['餐饮', '影院', '百货购物中心', '国内旅游', '医疗'];
+ const data = Mock.mock({
+ 'list|5': [
+ {
+ // 生成长度在 100~1000 之间的小写字母
+ yField: '@integer(0,5000)',
+ },
+ ],
+ });
+ return data.list
+ .sort((a, b) => b.yField - a.yField)
+ .map((item, index) => {
+ return {
+ xField: xField[index],
+ ...item,
+ };
+ });
+};
+
+// 多维折线图
+export const multidimensionalChart = () => {
+ const series = ['铺设失败', '铺设中', '铺设成功', '虚假铺设'];
+ const xField = new Array(12).fill('').map((item, index) => {
+ return `${2 * index + 2}:00`;
+ });
+
+ return series
+ .map((a, k) => {
+ return xField.map((b, index) => {
+ return {
+ xField: b,
+ series: a,
+ yField: Number(
+ ((index + 1) * 10 + 20 * Math.random() + k * 20).toFixed(),
+ ),
+ };
+ });
+ })
+ .flat();
+};
+
+// 作业单数
+export const operation = () => {
+ const data = Mock.mock({
+ 'list|15': [
+ {
+ name: '@cname',
+ order_count: '@integer(0,100)',
+ staff_no: '@integer(100000,1000000)',
+ },
+ ],
+ });
+ return data.list;
+};
+
+// 行业市场份额
+export const marketShare = () => {
+ const data = Mock.mock({
+ 'list|3': [
+ {
+ // 生成长度在 100~1000 之间的小写字母
+ xField: '@integer(0,100)',
+ },
+ ],
+ });
+ const yField = ['街电', '怪兽', '小电'];
+ return data.list
+ .sort((a, b) => a.yField - b.yField)
+ .map((item, index) => {
+ return {
+ yField: yField[index],
+ ...item,
+ };
+ });
+};
+
+// 各品牌营收
+export const brandRevenue = () => {
+ const series = ['街电', '来电', '怪兽', '美团', '小电'];
+ const xField = new Array(11).fill('').map((item, index) => {
+ return `${2009 + index}`;
+ });
+
+ return series
+ .map((a, k) => {
+ return xField.map((b, index) => {
+ return {
+ xField: b,
+ series: a,
+ yField: Number(
+ ((index + 1) * 10 + 30 * Math.random() + k * 20).toFixed(),
+ ),
+ };
+ });
+ })
+ .flat();
+};
+
+export function randomData(data: T): Promise {
+ return new Promise((resolve, reject) => {
+ setTimeout(() => {
+ resolve(data);
+ }, 500);
+ });
+}
+
+// 生成范围内的随机数
+export const randomNumBoth = (min: number, max: number) => {
+ const Range = max - min;
+ const Rand = Math.random();
+ const num = min + Math.round(Rand * Range);
+ return num;
+}
+
+export const brandOption = [
+ { label: '全部类型', value: '1' },
+ { label: '街电', value: '2' },
+ { label: '怪兽', value: '3' },
+ { label: '小电', value: '4' },
+];
+
+export const CityList = [
+ {
+ value: '330000',
+ areaLevel: 'province',
+ label: '浙江省',
+ children: [
+ {
+ value: '330100',
+ areaLevel: 'city',
+ label: '杭州市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '110000',
+ areaLevel: 'province',
+ label: '北京市',
+ children: [
+ {
+ value: '110000',
+ areaLevel: 'city',
+ label: '北京市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '120000',
+ areaLevel: 'province',
+ label: '天津市',
+ children: [
+ {
+ value: '120000',
+ areaLevel: 'city',
+ label: '天津市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '310000',
+ areaLevel: 'province',
+ label: '上海市',
+ children: [
+ {
+ value: '310000',
+ areaLevel: 'province',
+ label: '上海市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '440000',
+ areaLevel: 'province',
+ label: '广东省',
+ children: [
+ {
+ value: '440100',
+ areaLevel: 'city',
+ label: '广州市',
+ children: [],
+ },
+ {
+ value: '440300',
+ areaLevel: 'city',
+ label: '深圳市',
+ children: [],
+ },
+ {
+ value: '440400',
+ areaLevel: 'city',
+ label: '珠海市',
+ children: [],
+ },
+ {
+ value: '440600',
+ areaLevel: 'city',
+ label: '佛山市',
+ children: [],
+ },
+ {
+ value: '441300',
+ areaLevel: 'city',
+ label: '惠州市',
+ children: [],
+ },
+ {
+ value: '441900',
+ areaLevel: 'city',
+ label: '东莞市',
+ children: [],
+ },
+ {
+ value: '442000',
+ areaLevel: 'city',
+ label: '中山市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '130000',
+ areaLevel: 'province',
+ label: '河北省',
+ children: [
+ {
+ value: '130100',
+ areaLevel: 'city',
+ label: '石家庄市',
+ children: [],
+ },
+ {
+ value: '131000',
+ areaLevel: 'city',
+ label: '廊坊市',
+ children: [],
+ },
+ ],
+ },
+];
diff --git a/site/components/analysis/index.tsx b/site/components/analysis/index.tsx
new file mode 100644
index 0000000000..7d75f24b9c
--- /dev/null
+++ b/site/components/analysis/index.tsx
@@ -0,0 +1,27 @@
+import { initWidgets } from './widgets';
+import React, { useEffect, useState } from 'react';
+import { config } from './configs/config';
+import { DipperContainer, IConfig } from '@antv/dipper';
+import 'antd/dist/antd.css'
+interface IInitData {
+ areaVOList: any[];
+ sceneCode: string;
+ areaCode: string;
+ filterData: any[];
+}
+
+export default function RumbMap() {
+ const [mapConfig, setMapConfig] = useState>();
+ // 初始化相关数据
+
+ useEffect(() => {
+ initWidgets();
+ setMapConfig(config);
+ }, []);
+
+ return (
+
+ cfg={mapConfig!} />
+
+ );
+}
diff --git a/site/components/analysis/widgets/Filter.tsx b/site/components/analysis/widgets/Filter.tsx
new file mode 100644
index 0000000000..77aa663151
--- /dev/null
+++ b/site/components/analysis/widgets/Filter.tsx
@@ -0,0 +1,42 @@
+import { Select } from 'antd';
+import React from 'react';
+import { useConfigService } from '@antv/dipper';
+import { brandOption } from '../configs/mock';
+
+const { Option } = Select;
+
+export const Filter = () => {
+ const { setWidgetsValue } = useConfigService();
+
+ const onBrandChange = (e: any) => {
+ setWidgetsValue('brand', e);
+ };
+
+ return (
+
+
+
+
+ );
+};
diff --git a/site/components/analysis/widgets/GridLayer.tsx b/site/components/analysis/widgets/GridLayer.tsx
new file mode 100644
index 0000000000..94f560867f
--- /dev/null
+++ b/site/components/analysis/widgets/GridLayer.tsx
@@ -0,0 +1,140 @@
+import {
+ useSceneService,
+ useConfigService,
+ LayerGroupEventEnum,
+ useLayerService,
+} from '@antv/dipper';
+import React, { useEffect, useMemo, useState } from 'react';
+import { GridLayerGroup } from '@antv/dipper';
+import { randomNumBoth } from '../configs/mock';
+const formatLegend = (data: any[]) => {
+ return data.map((item) => {
+ if (Array.isArray(item.value)) {
+ return {
+ ...item,
+ value: item.value.map((v) => v.toFixed(2)),
+ };
+ } else {
+ return {
+ ...item,
+ value: item.value.toFixed(2),
+ };
+ }
+ });
+};
+export function GridLayer() {
+ const { layerService } = useLayerService();
+ const { sceneService } = useSceneService();
+ const { globalConfig, updateLegend, getWidgetsValue } = useConfigService();
+ const { layers } = globalConfig;
+ const [gridLayer, setGridLayer] = useState();
+ const cityValue = getWidgetsValue('citySelect');
+ const brandValue = getWidgetsValue('brand');
+ const [geoData, setGeoData] = useState();
+
+ const layerProps = useMemo(() => {
+ return layers.find((item: any) => item.type === 'gridLayer');
+ }, [layers]);
+
+ const updateLayerLegend = (items: any[]) => {
+ updateLegend('gridLayerLegend', {
+ type: 'classifyColor',
+ display: true,
+ position: 'bottomleft',
+ options: {
+ title: '充电宝投放数量',
+ unkownName: layerProps.options.unkownName,
+ items: items.map((item) => {
+ return {
+ color: item.color,
+ value: item.value.map((v) => {
+ return (v / 10000).toFixed(2);
+ }),
+ };
+ }),
+ },
+ });
+ };
+
+ // 根据筛选器条件请求数据
+ useEffect(() => {
+ // 可以根据业务需求配置接口
+ fetch(
+ `https://gw.alipayobjects.com/os/antvdemo/assets/dipper-city/${cityValue[1]}.json`,
+ )
+ .then((res) => res.json())
+ .then((data) => {
+ const geoDataList =
+ data &&
+ data.features?.map((item) => {
+ return {
+ ...item,
+ properties: {
+ ...item.properties,
+ brand_type: randomNumBoth(1, 4).toString(), // 充电宝品牌
+ },
+ };
+ });
+
+ // 品牌 过滤
+ if (brandValue && geoDataList) {
+ // @ts-ignore
+ const data =
+ brandValue === '1'
+ ? geoDataList
+ : geoDataList.filter(
+ (item) => item.properties.brand_type === brandValue,
+ );
+ if (data.length) {
+ // @ts-ignore
+ setGeoData({ type: 'FeatureCollection', features: data });
+ }
+ } else {
+ // @ts-ignore
+ setGeoData({ type: 'FeatureCollection', features: geoDataList });
+ }
+ });
+ // 切换城市 高德地图方法
+ sceneService.getScene().map?.setCity(cityValue[1]);
+ }, [JSON.stringify(cityValue), brandValue]);
+
+ useEffect(() => {
+ if (!geoData) {
+ return;
+ }
+ if (gridLayer) {
+ gridLayer.setData(geoData);
+ return;
+ }
+ const layer = new GridLayerGroup({
+ name: 'grid',
+ data: geoData,
+ options: layerProps.options,
+ });
+ layerService.addLayer(layer);
+
+ layer.on(LayerGroupEventEnum.DATAUPDATE, () => {
+ layer.getLegendItem().map((item) => {
+ if (Array.isArray(item.value)) {
+ return {
+ ...item,
+ value: item.value.map((v) => v.toFixed(2)),
+ };
+ } else {
+ return {
+ ...item,
+ value: item.value.toFixed(2),
+ };
+ }
+ });
+ updateLayerLegend(formatLegend(layer.getLegendItem()));
+ });
+
+ // 更新图例
+ updateLayerLegend(formatLegend(layer.getLegendItem()));
+
+ setGridLayer(layer);
+ }, [geoData]);
+
+ return <>>;
+}
diff --git a/site/components/analysis/widgets/MeshChart/index.tsx b/site/components/analysis/widgets/MeshChart/index.tsx
new file mode 100644
index 0000000000..8443615146
--- /dev/null
+++ b/site/components/analysis/widgets/MeshChart/index.tsx
@@ -0,0 +1,34 @@
+import React, { useEffect, useState } from 'react';
+import { useLayerGroup } from '@antv/dipper';
+import { brandRevenue, marketShare } from '../../configs/mock';
+import { PieChart } from '../../components/Pie';
+import { LineCahrt } from '../../components/Line';
+
+export function MeshChart() {
+ const { selectFeatures } = useLayerGroup('grid');
+ const [pieData, setPieData] = useState([]);
+ const [lineData, setLineData] = useState([]);
+ const [loding, setLoding] = useState(false);
+
+ useEffect(() => {
+ setLoding(true);
+ setTimeout(() => {
+ setLoding(false);
+ setPieData(marketShare());
+ setLineData(brandRevenue());
+ }, 300);
+ }, [JSON.stringify(selectFeatures)]);
+
+ return (
+
+ );
+}
diff --git a/site/components/analysis/widgets/MeshIndicator.tsx b/site/components/analysis/widgets/MeshIndicator.tsx
new file mode 100644
index 0000000000..ced8182214
--- /dev/null
+++ b/site/components/analysis/widgets/MeshIndicator.tsx
@@ -0,0 +1,33 @@
+import React, { useState, useEffect } from 'react';
+import { useLayerGroup } from '@antv/dipper';
+import { SingleLineCahrt } from '../components/SingleLine';
+import { singleLineChart, barChart } from '../configs/mock';
+import { BarCahrt } from '../components/Bar';
+
+export function MeshIndicator() {
+ const { selectFeatures } = useLayerGroup('grid');
+
+ // lineChart
+ const [lineData, setLineData] = useState([]);
+
+ const [barData, setBarData] = useState([]);
+
+ // lineChart
+ useEffect(() => {
+ setLineData(singleLineChart());
+ setBarData(barChart());
+ }, [JSON.stringify(selectFeatures)]);
+
+ return (
+
+ );
+}
diff --git a/site/components/analysis/widgets/MeshName/index.module.css b/site/components/analysis/widgets/MeshName/index.module.css
new file mode 100644
index 0000000000..a03ab39e9d
--- /dev/null
+++ b/site/components/analysis/widgets/MeshName/index.module.css
@@ -0,0 +1,13 @@
+.meahname {
+ padding: 20px;
+}
+.closeicon {
+ padding: 0 8px;
+}
+.edit {
+ display: flex;
+ align-items: center;
+}
+.edit span:hover {
+ color: #1890ff;
+}
diff --git a/site/components/analysis/widgets/MeshName/index.tsx b/site/components/analysis/widgets/MeshName/index.tsx
new file mode 100644
index 0000000000..0f03f1a034
--- /dev/null
+++ b/site/components/analysis/widgets/MeshName/index.tsx
@@ -0,0 +1,106 @@
+import React, {
+ useRef,
+ useState,
+ useMemo,
+ useCallback,
+ useEffect,
+} from 'react';
+import { CheckOutlined, CloseOutlined, EditOutlined } from '@ant-design/icons';
+import styles from './index.module.css'
+import { Input } from 'antd';
+import { useLayerGroup, useConfigService } from '@antv/dipper';
+import _ from 'loadsh';
+
+export function MeshName() {
+ const { selectFeatures, updateProperties } = useLayerGroup('grid');
+ const [edit, setEdit] = useState(false);
+ const ref = useRef();
+ const { setConfig } = useConfigService();
+
+ /**
+ * get meshname
+ * type []string
+ */
+ const meshName = useMemo(() => {
+ if (!selectFeatures.length) return [];
+ return selectFeatures.map((item) => {
+ // @ts-ignore
+ return item.feature.properties.name;
+ });
+ }, [JSON.stringify(selectFeatures)]);
+
+ // 修改 网格名称
+ const editMeshName = useCallback(() => {
+ // @ts-ignore
+ const value = ref.current.state.value;
+ selectFeatures.forEach((item) => {
+ const properties = {
+ ...item.feature.properties,
+ name: value,
+ };
+ updateProperties(item.feature, properties);
+ });
+ setEdit(false);
+ }, [JSON.stringify(selectFeatures)]);
+
+ // select more meshname 编辑 网格名称
+ const EditMeshName = () => {
+ return (
+ <>
+ {!edit ? (
+ setEdit(!edit)}>
+ {meshName}
+
+
+ ) : (
+
+
+
+ setEdit(false)} />
+
+ )}
+ >
+ );
+ };
+
+ // show 多个网格名称
+ const ShowMeshNames = () => {
+ return (
+
+ {meshName.length >= 2 &&
+ meshName.map((s) => {
+ return
+ {s}、
+ ;
+ })}
+
+ );
+ };
+
+ useEffect(() => {
+ if (selectFeatures.length) {
+ // TODO 报错
+ setConfig(`panel.children.1.display`, false);
+ setConfig(`panel.children.2.display`, true);
+ // setConfig(`panel.children.${findIdMeshchart}.display`, false)
+ } else {
+ setConfig(`panel.children.1.display`, true);
+ setConfig(`panel.children.2.display`, false);
+ }
+ }, [JSON.stringify(selectFeatures)]);
+
+ return (
+ <>
+ {meshName && meshName.length ? (
+
+ {meshName.length === 1 ? : }
+
+ ) : (
+ 所有网格数据概览
+ )}
+ >
+ );
+}
diff --git a/site/components/analysis/widgets/TotalPanel/index.module.css b/site/components/analysis/widgets/TotalPanel/index.module.css
new file mode 100644
index 0000000000..b3f2430e6c
--- /dev/null
+++ b/site/components/analysis/widgets/TotalPanel/index.module.css
@@ -0,0 +1,37 @@
+.teamcontainer {
+ margin: 10px 0;
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+}
+.orderlist {
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+ height: 48px;
+ width: 378px;
+ background: #fafafa;
+ border-radius: 2px;
+ padding: 0 5px;
+}
+.orderlist .leftpart {
+ display: flex;
+ align-items: center;
+}
+.orderlist .leftpart > div {
+ padding-right: 15px;
+}
+.orderlist .leftpart .ordericon {
+ width: 16px;
+ height: 16px;
+ margin-right: 10px;
+}
+.sort:hover {
+ color: #1e73f8;
+}
+.orderCon :global .ant-list-split .ant-list-item {
+ border: none !important;
+}
+.orderCon :global .ant-list-item {
+ padding: 5px 0 !important;
+}
diff --git a/site/components/analysis/widgets/TotalPanel/index.tsx b/site/components/analysis/widgets/TotalPanel/index.tsx
new file mode 100644
index 0000000000..8c0953f95c
--- /dev/null
+++ b/site/components/analysis/widgets/TotalPanel/index.tsx
@@ -0,0 +1,116 @@
+import React, { useState, useEffect } from 'react';
+import { useLayerGroup } from '@antv/dipper'
+import { Button, List } from 'antd';
+import { multidimensionalChart, operation } from '../../configs/mock';
+import styles from './index.module.css'
+import { LineCahrt } from '../../components/Line';
+
+enum Sort {
+ Up,
+ Dowm,
+}
+
+const No1 =
+ 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*grCBQ4izMjcAAAAAAAAAAAAAARQnAQ';
+const No2 =
+ 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*r0DyQIluJ8QAAAAAAAAAAAAAARQnAQ';
+const No3 =
+ 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*5R92QrzHW7YAAAAAAAAAAAAAARQnAQ';
+
+export function TotalPanel() {
+ const { selectFeatures = [] } = useLayerGroup('grid');
+
+ const [lineData, setLineData] = useState([]);
+ const [orderData, setOrderData] = useState([]);
+ const [ordersort, setOrderSort] = useState(1);
+ const [loading, setLoading] = useState(false);
+
+ // lineChart
+ useEffect(() => {
+ setLoading(true)
+ setTimeout(()=>{
+ setLoading(false)
+ setLineData(multidimensionalChart());
+ },300)
+ }, [JSON.stringify(selectFeatures)]);
+
+ useEffect(() => {
+ if (ordersort === undefined) {
+ return setOrderData(operation());
+ }
+ const sortData = operation();
+ if (ordersort === 0) {
+ return setOrderData(
+ sortData.sort((a, b) => a.order_count - b.order_count),
+ );
+ }
+ if (ordersort === 1) {
+ return setOrderData(
+ sortData.sort((a, b) => b.order_count - a.order_count),
+ );
+ }
+ }, [selectFeatures, ordersort]);
+
+ // 排序
+ const sorts = (type: Sort) => {
+ setOrderSort(type);
+ };
+
+ // orderData index 与 icon 映射
+ const iconOrder = { 1: No1, 2: No2, 3: No3 };
+
+ return (
+
+
+
铺设进程
+
+
+
+
+
团队榜单
+
+
+
+
+
+ {orderData && (
+
(
+
+
+
+ {index <= 2 ? (
+
+ ) : (
+
{index + 1}
+ )}
+
+ {item.name}({item.staff_no})
+
+
+
作业成功{item.order_count}单
+
+
+ )}
+ />
+ )}
+
+
+ );
+}
diff --git a/site/components/analysis/widgets/index.ts b/site/components/analysis/widgets/index.ts
new file mode 100644
index 0000000000..6e220dcc52
--- /dev/null
+++ b/site/components/analysis/widgets/index.ts
@@ -0,0 +1,34 @@
+import { registerWidget } from '@antv/dipper-core';
+import {
+ CitySelect,
+ NavBar,
+ ClassifyColor,
+ DiscreteColor,
+ Draw,
+ MapStyle,
+ SearchPlace,
+ Location,
+} from '@antv/dipper-widgets';
+import { GridLayer } from './GridLayer';
+import { MeshIndicator } from './MeshIndicator';
+import { MeshName } from './MeshName';
+import { Filter } from './Filter';
+import { TotalPanel } from './TotalPanel/index';
+import { MeshChart } from './MeshChart';
+
+export function initWidgets() {
+ registerWidget('citySelect', CitySelect);
+ registerWidget('navibar', NavBar);
+ registerWidget('gridLayer', GridLayer);
+ registerWidget('classifyColor', ClassifyColor);
+ registerWidget('discreteColor', DiscreteColor);
+ registerWidget('mapStyle', MapStyle);
+ registerWidget('searchPlaces', SearchPlace);
+ registerWidget('location', Location);
+ registerWidget('filter', Filter);
+ registerWidget('mesh_indicator', MeshIndicator);
+ registerWidget('total_data_panel', TotalPanel);
+ registerWidget('meshchart', MeshChart);
+ registerWidget('draw', Draw);
+ registerWidget('meshName',MeshName)
+}
diff --git a/site/components/rumbling/configs/mock.ts b/site/components/rumbling/configs/mock.ts
deleted file mode 100644
index 584b3b38cd..0000000000
--- a/site/components/rumbling/configs/mock.ts
+++ /dev/null
@@ -1,532 +0,0 @@
-export const geojson = [
- {
- type: 'Feature',
- properties: {
- label: 'A类区域',
- value: 'A',
- featureId: '2021102300040027',
- id: '2021102300040027',
- name: '哈哈6666',
- groupId: '2021102300073562',
- canvasId: '2021102300077947',
- creator: '285869',
- modifier: 'WB904416',
- gmtCreate: '2021-10-23T13:23:53.000+00:00',
- gmtModified: '2021-10-29T08:43:06.000+00:00',
- status: 1,
- bizId: 'ALGO13301000000030038b',
- source: 'INIT',
- extInfo: {
- area_centroid: '[120.200270,30.137812]',
- },
- },
- geometry: {
- type: 'Polygon',
- coordinates: [
- [
- [120.147844, 30.143857],
- [120.146688, 30.144529],
- [120.145292, 30.145769],
- [120.14333, 30.146841],
- [120.138229, 30.153274],
- [120.133322, 30.160392],
- [120.132625, 30.161615],
- [120.135188, 30.16281],
- [120.136067, 30.163429],
- [120.137014, 30.164436],
- [120.138875, 30.167409],
- [120.139576, 30.168271],
- [120.140893, 30.169368],
- [120.141752, 30.169944],
- [120.144082, 30.170827],
- [120.147209, 30.171816],
- [120.151231, 30.172756],
- [120.154113, 30.173337],
- [120.155476, 30.173477],
- [120.158666, 30.173408],
- [120.158813, 30.173182],
- [120.167716, 30.173249],
- [120.167809, 30.173079],
- [120.167644, 30.172555],
- [120.167663, 30.172204],
- [120.168217, 30.171148],
- [120.168583, 30.170715],
- [120.168799, 30.169991],
- [120.16937, 30.169203],
- [120.168394, 30.168113],
- [120.167832, 30.167112],
- [120.170001, 30.162286],
- [120.170393, 30.161163],
- [120.170857, 30.160363],
- [120.171268, 30.159909],
- [120.171843, 30.159472],
- [120.172585, 30.159084],
- [120.173472, 30.158806],
- [120.176516, 30.158457],
- [120.178244, 30.158018],
- [120.181234, 30.156641],
- [120.182546, 30.156143],
- [120.187335, 30.155265],
- [120.188246, 30.155308],
- [120.188949, 30.155505],
- [120.189517, 30.155768],
- [120.190041, 30.156122],
- [120.191852, 30.157747],
- [120.192457, 30.158198],
- [120.199627, 30.161976],
- [120.200393, 30.161113],
- [120.201372, 30.160261],
- [120.204072, 30.158385],
- [120.204474, 30.157992],
- [120.205018, 30.15764],
- [120.205398, 30.157546],
- [120.205887, 30.157658],
- [120.205706, 30.15851],
- [120.206192, 30.158863],
- [120.206058, 30.159513],
- [120.206121, 30.159901],
- [120.207273, 30.160486],
- [120.208006, 30.160419],
- [120.208488, 30.159493],
- [120.208835, 30.158228],
- [120.208544, 30.157534],
- [120.206494, 30.157128],
- [120.207878, 30.156136],
- [120.208276, 30.156082],
- [120.208298, 30.156518],
- [120.209071, 30.157141],
- [120.210222, 30.156577],
- [120.210388, 30.157044],
- [120.210978, 30.157462],
- [120.212571, 30.158131],
- [120.212937, 30.158078],
- [120.213941, 30.157481],
- [120.214887, 30.159206],
- [120.214888, 30.160837],
- [120.215479, 30.161676],
- [120.215645, 30.162161],
- [120.215948, 30.162305],
- [120.218933, 30.162964],
- [120.21947, 30.162984],
- [120.221036, 30.16208],
- [120.221542, 30.161941],
- [120.221799, 30.162783],
- [120.222203, 30.163521],
- [120.222931, 30.164169],
- [120.225012, 30.165453],
- [120.225443, 30.165901],
- [120.226118, 30.16827],
- [120.226124, 30.168557],
- [120.225875, 30.168755],
- [120.226207, 30.170185],
- [120.226446, 30.170469],
- [120.226639, 30.170573],
- [120.227512, 30.170626],
- [120.227522, 30.171242],
- [120.227796, 30.171909],
- [120.229737, 30.172137],
- [120.229916, 30.171461],
- [120.23, 30.170618],
- [120.230569, 30.170018],
- [120.233933, 30.169673],
- [120.23455, 30.165985],
- [120.234458, 30.164828],
- [120.234558, 30.162136],
- [120.234676, 30.16115],
- [120.235118, 30.159612],
- [120.235576, 30.158653],
- [120.235617, 30.15825],
- [120.236053, 30.157277],
- [120.235382, 30.157034],
- [120.235301, 30.156572],
- [120.23496, 30.156239],
- [120.234249, 30.155793],
- [120.233696, 30.155684],
- [120.2332, 30.15573],
- [120.232496, 30.155586],
- [120.23286, 30.154907],
- [120.233495, 30.154176],
- [120.232856, 30.153878],
- [120.232683, 30.153433],
- [120.232879, 30.153278],
- [120.232872, 30.152843],
- [120.232724, 30.152397],
- [120.23234, 30.151877],
- [120.231848, 30.151555],
- [120.231595, 30.151273],
- [120.231185, 30.150624],
- [120.230557, 30.150187],
- [120.230053, 30.149345],
- [120.229281, 30.148778],
- [120.228917, 30.148747],
- [120.228421, 30.14842],
- [120.228184, 30.147479],
- [120.226923, 30.147425],
- [120.226418, 30.147328],
- [120.225486, 30.147388],
- [120.226496, 30.146217],
- [120.225966, 30.145733],
- [120.225583, 30.145521],
- [120.225428, 30.14502],
- [120.224312, 30.14501],
- [120.223858, 30.144788],
- [120.223652, 30.144476],
- [120.223478, 30.144345],
- [120.222825, 30.14418],
- [120.222569, 30.14428],
- [120.221885, 30.144124],
- [120.221396, 30.144273],
- [120.220971, 30.1447],
- [120.220603, 30.144724],
- [120.220295, 30.144623],
- [120.220024, 30.144701],
- [120.219842, 30.144619],
- [120.219654, 30.144693],
- [120.219384, 30.144654],
- [120.218498, 30.144158],
- [120.217793, 30.143521],
- [120.217119, 30.143362],
- [120.216758, 30.14301],
- [120.216674, 30.14272],
- [120.216732, 30.142301],
- [120.217668, 30.141623],
- [120.218151, 30.141431],
- [120.220282, 30.139534],
- [120.220356, 30.140206],
- [120.220619, 30.140315],
- [120.220731, 30.140486],
- [120.221293, 30.140608],
- [120.221736, 30.140936],
- [120.221342, 30.141563],
- [120.22151, 30.141869],
- [120.220996, 30.142466],
- [120.22197, 30.142837],
- [120.223564, 30.142785],
- [120.223847, 30.142422],
- [120.223877, 30.142059],
- [120.223806, 30.141797],
- [120.221855, 30.139726],
- [120.2231, 30.140085],
- [120.223641, 30.140564],
- [120.223948, 30.141129],
- [120.223997, 30.141173],
- [120.224257, 30.141696],
- [120.224258, 30.142105],
- [120.224381, 30.142548],
- [120.224535, 30.142716],
- [120.224726, 30.143188],
- [120.2255, 30.143728],
- [120.226119, 30.144357],
- [120.226434, 30.14455],
- [120.228071, 30.144609],
- [120.229719, 30.144786],
- [120.229908, 30.14485],
- [120.23018, 30.145286],
- [120.230407, 30.145484],
- [120.231237, 30.145853],
- [120.231382, 30.146076],
- [120.231631, 30.146207],
- [120.232288, 30.146322],
- [120.233052, 30.146667],
- [120.23368, 30.14734],
- [120.233786, 30.147891],
- [120.234623, 30.14832],
- [120.234839, 30.148646],
- [120.235314, 30.149087],
- [120.23548, 30.149626],
- [120.235721, 30.149938],
- [120.236457, 30.150391],
- [120.23716, 30.150539],
- [120.237485, 30.150801],
- [120.23803, 30.151477],
- [120.239139, 30.152535],
- [120.23946, 30.153088],
- [120.240229, 30.153121],
- [120.240626, 30.152351],
- [120.241359, 30.151459],
- [120.242314, 30.150725],
- [120.245302, 30.148847],
- [120.24628, 30.147889],
- [120.247034, 30.146693],
- [120.247423, 30.145397],
- [120.247992, 30.145405],
- [120.248012, 30.143993],
- [120.247725, 30.142724],
- [120.247166, 30.142646],
- [120.242305, 30.130879],
- [120.241721, 30.130596],
- [120.240334, 30.12946],
- [120.239997, 30.129042],
- [120.238317, 30.125574],
- [120.237006, 30.123431],
- [120.236783, 30.122886],
- [120.235868, 30.122206],
- [120.236571, 30.122049],
- [120.23665, 30.121468],
- [120.235894, 30.119696],
- [120.235675, 30.118672],
- [120.235701, 30.117587],
- [120.235629, 30.11654],
- [120.235379, 30.116023],
- [120.233483, 30.116034],
- [120.233123, 30.116188],
- [120.232895, 30.116075],
- [120.231727, 30.115965],
- [120.230487, 30.116072],
- [120.230015, 30.116313],
- [120.229969, 30.115245],
- [120.229787, 30.11438],
- [120.229945, 30.113327],
- [120.232144, 30.112345],
- [120.233516, 30.111985],
- [120.235989, 30.111814],
- [120.234895, 30.107582],
- [120.234778, 30.106555],
- [120.234895, 30.104915],
- [120.230596, 30.103151],
- [120.2278, 30.101876],
- [120.226383, 30.101599],
- [120.222325, 30.1023],
- [120.2147, 30.103149],
- [120.212667, 30.103445],
- [120.21219, 30.10365],
- [120.211945, 30.103932],
- [120.210495, 30.107288],
- [120.209991, 30.108123],
- [120.209384, 30.108529],
- [120.208824, 30.10864],
- [120.208085, 30.108556],
- [120.205857, 30.107717],
- [120.205393, 30.107652],
- [120.204861, 30.107693],
- [120.201864, 30.109287],
- [120.20089, 30.109712],
- [120.199973, 30.109881],
- [120.193121, 30.109323],
- [120.191151, 30.109647],
- [120.190646, 30.109835],
- [120.190888, 30.111217],
- [120.190796, 30.111259],
- [120.190086, 30.109884],
- [120.189525, 30.109667],
- [120.18587, 30.107744],
- [120.185064, 30.109015],
- [120.183326, 30.113489],
- [120.18151, 30.11587],
- [120.180172, 30.11726],
- [120.177758, 30.119219],
- [120.174527, 30.121509],
- [120.173028, 30.122505],
- [120.172232, 30.122899],
- [120.171456, 30.123117],
- [120.170975, 30.12361],
- [120.170378, 30.12466],
- [120.166094, 30.128398],
- [120.165454, 30.129692],
- [120.164526, 30.130852],
- [120.163489, 30.131706],
- [120.162161, 30.132556],
- [120.160762, 30.133219],
- [120.158745, 30.134854],
- [120.156354, 30.137038],
- [120.154387, 30.138586],
- [120.152292, 30.139893],
- [120.150055, 30.14083],
- [120.149208, 30.142005],
- [120.148552, 30.143085],
- [120.147844, 30.143857],
- ],
- ],
- },
- },
- {
- type: 'Feature',
- properties: {
- label: 'B类区域',
- value: 'B',
- featureId: '2021102300040027',
- id: '2021102300040027',
- name: '于争光',
- groupId: '2021102300073562',
- canvasId: '2021102300077947',
- creator: '285869',
- modifier: 'WB904416',
- gmtCreate: '2021-10-23T13:23:53.000+00:00',
- gmtModified: '2021-10-29T08:43:06.000+00:00',
- status: 1,
- bizId: 'ALGO13301000000030038b',
- source: 'INIT',
- extInfo: {
- area_centroid: '[120.200270,30.137812]',
- },
- },
- geometry: {
- type: 'Polygon',
- coordinates: [
- [
- [120.1636505126953, 30.24631485403797],
- [120.17704010009766, 30.22970466206658],
- [120.19214630126953, 30.243942141326617],
- [120.1636505126953, 30.24631485403797],
- ],
- ],
- },
- },
- {
- type: 'Feature',
- properties: {
- label: 'C类区域',
- value: 'C',
- featureId: '2021102300040027',
- id: '2021102300040027',
- name: 'ecnevnevnec',
- groupId: '2021102300073562',
- canvasId: '2021102300077947',
- creator: '285869',
- modifier: 'WB904416',
- gmtCreate: '2021-10-23T13:23:53.000+00:00',
- gmtModified: '2021-10-29T08:43:06.000+00:00',
- status: 1,
- bizId: 'ALGO13301000000030038b',
- source: 'INIT',
- extInfo: {
- area_centroid: '[120.200270,30.137812]',
- },
- },
- geometry: {
- type: 'Polygon',
- coordinates: [
- [
- [120.09017944335938, 30.224958377428475],
- [120.08949279785156, 30.18994745521063],
- [120.14751434326172, 30.189353942421295],
- [120.14854431152342, 30.22466172703242],
- [120.09017944335938, 30.224958377428475],
- ],
- ],
- },
- },
-];
-
-export const CityList = [
- {
- value: '330000',
- areaLevel: 'province',
- label: '浙江省',
- children: [
- {
- value: '330100',
- areaLevel: 'city',
- label: '杭州市',
- children: [],
- },
- ],
- },
- {
- value: '110000',
- areaLevel: 'province',
- label: '北京市',
- children: [
- {
- value: '110000',
- areaLevel: 'city',
- label: '北京市',
- children: [],
- },
- ],
- },
- {
- value: '120000',
- areaLevel: 'province',
- label: '天津市',
- children: [
- {
- value: '120000',
- areaLevel: 'city',
- label: '天津市',
- children: [],
- },
- ],
- },
- {
- value: '310000',
- areaLevel: 'province',
- label: '上海市',
- children: [
- {
- value: '310000',
- areaLevel: 'province',
- label: '上海市',
- children: [],
- },
- ],
- },
- {
- value: '440000',
- areaLevel: 'province',
- label: '广东省',
- children: [
- {
- value: '440100',
- areaLevel: 'city',
- label: '广州市',
- children: [],
- },
- {
- value: '440300',
- areaLevel: 'city',
- label: '深圳市',
- children: [],
- },
- {
- value: '440400',
- areaLevel: 'city',
- label: '珠海市',
- children: [],
- },
- {
- value: '440600',
- areaLevel: 'city',
- label: '佛山市',
- children: [],
- },
- {
- value: '441300',
- areaLevel: 'city',
- label: '惠州市',
- children: [],
- },
- {
- value: '441900',
- areaLevel: 'city',
- label: '东莞市',
- children: [],
- },
- {
- value: '442000',
- areaLevel: 'city',
- label: '中山市',
- children: [],
- },
- ],
- },
- {
- value: '130000',
- areaLevel: 'province',
- label: '河北省',
- children: [
- {
- value: '130100',
- areaLevel: 'city',
- label: '石家庄市',
- children: [],
- },
- {
- value: '131000',
- areaLevel: 'city',
- label: '廊坊市',
- children: [],
- },
- ],
- },
-];
diff --git a/site/components/rumbling/widgets/index.ts b/site/components/rumbling/widgets/index.ts
deleted file mode 100644
index a11dfaa89f..0000000000
--- a/site/components/rumbling/widgets/index.ts
+++ /dev/null
@@ -1,20 +0,0 @@
-import { registerWidget } from '@antv/dipper-core';
-import {
- CitySelect,
- SiderBar,
- NavBar,
- ClassifyColor,
- DiscreteColor,
-} from '@antv/dipper-widgets';
-import { GridLayer } from './GridLayer';
-import { MapStyle } from '@antv/dipper-widgets';
-
-export function initWidgets() {
- registerWidget('citySelect', CitySelect);
- registerWidget('siderbartabcontent', SiderBar);
- registerWidget('navibar', NavBar);
- registerWidget('gridLayer', GridLayer);
- registerWidget('classifyColor', ClassifyColor);
- registerWidget('discreteColor', DiscreteColor);
- registerWidget('mapStyle', MapStyle);
-}
diff --git a/site/components/task/components/Bar/index.tsx b/site/components/task/components/Bar/index.tsx
new file mode 100644
index 0000000000..be274f46b8
--- /dev/null
+++ b/site/components/task/components/Bar/index.tsx
@@ -0,0 +1,37 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Bar } from '@antv/g2plot';
+
+export interface ChatData {
+ data: object[];
+}
+
+export function BarChart({ data }: ChatData) {
+ const id = useRef();
+ const [barplot, setBarplot] = useState();
+ useEffect(() => {
+ if (!barplot && id.current) {
+ const bar = new Bar(id.current, {
+ // @ts-ignore
+ data: data.sort((a, b) => b.xField - a.xField),
+ autoFit: true,
+ xField: 'xField',
+ yField: 'yField',
+ xAxis: false,
+ label: {
+ position: 'left',
+ style: {
+ fill: '#fff',
+ },
+ },
+ legend: {
+ position: 'top-left',
+ },
+ });
+
+ bar.render();
+ setBarplot(bar);
+ }
+ }, []);
+
+ return ;
+}
diff --git a/site/components/task/components/Line/index.tsx b/site/components/task/components/Line/index.tsx
new file mode 100644
index 0000000000..0b41073ace
--- /dev/null
+++ b/site/components/task/components/Line/index.tsx
@@ -0,0 +1,42 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Line } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+
+export function LineChart({ data }: ChatData) {
+ const id = useRef();
+ const [lineplot, setLinePlot] = useState();
+ const [list, setData] = useState([]);
+
+ useEffect(() => {
+ fetch(
+ 'https://gw.alipayobjects.com/os/bmw-prod/b21e7336-0b3e-486c-9070-612ede49284e.json',
+ )
+ .then((res) => res.json())
+ .then((data) => {
+ setData(data);
+ });
+ }, []);
+
+ useEffect(() => {
+ if (!lineplot && id.current && list) {
+ const area = new Line(id.current, {
+ data: list,
+ autoFit: true,
+ xField: 'date',
+ yField: 'value',
+ seriesField: 'country',
+ legend: {
+ position: 'top-left',
+ },
+ });
+ area.render();
+ setLinePlot(area);
+ } else {
+ lineplot.update({
+ data: list,
+ });
+ }
+ }, [id.current, list]);
+
+ return ;
+}
diff --git a/site/components/task/components/Pie/index.tsx b/site/components/task/components/Pie/index.tsx
new file mode 100644
index 0000000000..d7c8d0250a
--- /dev/null
+++ b/site/components/task/components/Pie/index.tsx
@@ -0,0 +1,33 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Pie } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+
+export function PieChart({ data }: ChatData) {
+ const id = useRef();
+ const [pieplot, setPiePlot] = useState();
+
+ useEffect(() => {
+ if (!pieplot && id.current && data) {
+ const bar = new Pie(id.current, {
+ data,
+ autoFit: true,
+ angleField: 'xField',
+ colorField: 'yField',
+ radius: 0.7,
+ label: {
+ type: 'spider',
+ labelHeight: 28,
+ content: '{name}\n{percentage}',
+ },
+ legend: {
+ position: 'top-left',
+ },
+ });
+
+ bar.render();
+ setPiePlot(bar);
+ }
+ }, [id.current, data]);
+
+ return ;
+}
diff --git a/site/components/task/components/StackArea/index.tsx b/site/components/task/components/StackArea/index.tsx
new file mode 100644
index 0000000000..4339f6f315
--- /dev/null
+++ b/site/components/task/components/StackArea/index.tsx
@@ -0,0 +1,42 @@
+import React, { useEffect, useRef, useState } from 'react';
+import { Area } from '@antv/g2plot';
+import { ChatData } from '../Bar';
+
+export function StackAreaChart({ data }: ChatData) {
+ const id = useRef();
+ const [pieplot, setAreaPlot] = useState();
+ const [list, setData] = useState([]);
+
+ useEffect(() => {
+ fetch(
+ 'https://gw.alipayobjects.com/os/bmw-prod/b21e7336-0b3e-486c-9070-612ede49284e.json',
+ )
+ .then((res) => res.json())
+ .then((data) => {
+ setData(data);
+ });
+ }, []);
+
+ useEffect(() => {
+ if (!pieplot && id.current && list) {
+ const area = new Area(id.current, {
+ data: list,
+ autoFit: true,
+ xField: 'date',
+ yField: 'value',
+ seriesField: 'country',
+ legend: {
+ position: 'top-left',
+ },
+ });
+ area.render();
+ setAreaPlot(area);
+ } else {
+ pieplot.update({
+ data: list,
+ });
+ }
+ }, [id.current, data]);
+
+ return ;
+}
diff --git a/site/components/task/configs/config.ts b/site/components/task/configs/config.ts
new file mode 100644
index 0000000000..0c3fd1c320
--- /dev/null
+++ b/site/components/task/configs/config.ts
@@ -0,0 +1,168 @@
+import { IConfig, SingleSequentialColorScale } from '@antv/dipper';
+import { CityList } from './mock';
+export const config: Partial = {
+ viewData: {
+ global: {
+ filterData: [],
+ areaCode: '110000',
+ view: 'task',
+ },
+ widgets: {
+ citySelect: {
+ options: CityList,
+ value: ['110000', '110000'],
+ },
+ },
+ },
+ headerbar: {
+ display: true,
+ title: {
+ value: 'XX 管理地图地图',
+ display: true,
+ },
+ children: [
+ {
+ display: true,
+ position: 'left',
+ title: '选择城市',
+ type: 'citySelect',
+ event: {
+ actionType: 'map',
+ action: 'queryArea',
+ },
+ },
+ ],
+ },
+ panel: {
+ display: true,
+
+ position: 'right',
+ options: {
+ enableToggle: true,
+ defaultTitle: '所有网格',
+ opened: true,
+ width: 426,
+ },
+ children: [
+ {
+ display: true,
+ type: 'meshName',
+ title: '网格名称',
+ },
+ {
+ display: true,
+ type: 'activityTask',
+ title: '活动任务',
+ },
+ ],
+ },
+ toolbar: {
+ display: true,
+ children: [
+ {
+ display: true,
+ position: 'left',
+ title: '全部活动',
+ type: 'activity',
+ },
+ {
+ display: true,
+ position: 'left',
+ title: '全部状态',
+ type: 'status',
+ },
+ {
+ display: true,
+ position: 'left',
+ title: '地图展示',
+ type: 'mapExhibit',
+ },
+ {
+ display: true,
+ position: 'left',
+ title: '人员搜索',
+ type: 'searchPerson',
+ },
+ {
+ display: true,
+ position: 'right',
+ title: '保存',
+ type: 'save',
+ },
+ {
+ display: true,
+ position: 'right',
+ type: 'publishbar',
+ title: '发布',
+ event: {
+ actionType: 'map',
+ action: 'publish',
+ },
+ },
+ ],
+ },
+ map: {
+ zoom: 10,
+ center: [120.153576, 30.287459],
+ pitch: 0,
+ style: 'normal',
+ },
+ controls: [
+ {
+ display: true,
+ position: 'bottomright',
+ type: 'mapStyle',
+ title: '地图样式',
+ },
+ {
+ display: true,
+ position: 'rightcenter',
+ type: 'meshTools',
+ title: '网格工具',
+ },
+ {
+ display: true,
+ position: 'bottomright',
+ type: 'location',
+ title: '定位',
+ },
+ ],
+ defaultcontrols: [
+ {
+ type: 'zoom',
+ position: 'bottomright',
+ display: true,
+ },
+ {
+ type: 'scale',
+ position: 'bottomleft',
+ display: true,
+ },
+ ],
+ popup: {
+ enable: false,
+ },
+ layers: [
+ {
+ type: 'gridLayer',
+ options: {
+ label: {
+ field: 'name',
+ size: 12,
+ color: '#000',
+ },
+
+ fill: {
+ field: 'unit_price',
+ color: ['#CFE1B9', '#B0C298', '#90A276', '#718355'],
+ unknownName: '无类型',
+ scale: {
+ type: 'cat',
+ domain: ['C', 'B', 'A'],
+ },
+ },
+ },
+ },
+ ],
+ legends: [],
+};
diff --git a/site/components/task/configs/mock.ts b/site/components/task/configs/mock.ts
new file mode 100644
index 0000000000..f91578ebcf
--- /dev/null
+++ b/site/components/task/configs/mock.ts
@@ -0,0 +1,199 @@
+import Mock from 'mockjs';
+
+export const chartList = Mock.mock({
+ // 生成长度在 0~32 之间的小写字母
+ success: '@string("lower", 0, 32)',
+ // 生成长度在 0~32 之间的小写字母
+ errorMessage: '@string("lower", 0, 32)',
+ data: {
+ 'list|4-7': [
+ {
+ // 生成长度在 100~1000 之间的小写字母
+ xField: '@integer(100,1000)',
+ // 生成长度在 3~5 之间的中文
+ yField: '@ctitle(3, 5)',
+ },
+ ],
+ },
+});
+
+export const personOption = () => {
+ const data = Mock.mock({
+ 'list|10': [
+ {
+ label: '@cname',
+ staffNo: '@integer(100000,1000000)',
+ value: '@integer(100000,1000000)'
+ },
+ ],
+ })
+ return data.list
+}
+
+export const selectActivityItem = [
+ {
+ label: '双十一赢金币',
+ value: '双十一赢金币',
+ icon: 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*JYNuSaNAga8AAAAAAAAAAAAAARQnAQ'
+ },
+ {
+ label: '充电桩铺设',
+ value: '充电桩铺设',
+ icon: 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*eay2Q7nXeG4AAAAAAAAAAAAAARQnAQ'
+ },
+ {
+ label: '1块钱升级月卡',
+ value: '1块钱升级月卡',
+ icon: 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*nA0vQbl_hGMAAAAAAAAAAAAAARQnAQ'
+ },
+ {
+ label: '免费充电1小时',
+ value: '免费充电1小时',
+ icon: 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*snkKRYonMgEAAAAAAAAAAAAAARQnAQ'
+ },
+]
+
+export function randomData(data: T): Promise {
+ return new Promise((resolve, reject) => {
+ setTimeout(() => {
+ resolve(data);
+ }, 500);
+ });
+}
+
+export const ActivityOption = [
+ { label: '全部活动', value: '全部活动' },
+ { label: '双十一赢金币', value: '双十一赢金币' },
+ { label: '充电桩铺设', value: '充电桩铺设' },
+ { label: '1块钱升级月卡', value: '1块钱升级月卡' },
+ { label: '免费充电1小时', value: '免费充电1小时' }
+]
+
+export const StatusOption = [
+ { label: '全部状态', value: '全部状态' },
+ { label: '未拓展', value: '未拓展' },
+ { label: '已拓展', value: '已拓展' },
+]
+
+export const CityList = [
+ {
+ value: '330000',
+ areaLevel: 'province',
+ label: '浙江省',
+ children: [
+ {
+ value: '330100',
+ areaLevel: 'city',
+ label: '杭州市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '110000',
+ areaLevel: 'province',
+ label: '北京市',
+ children: [
+ {
+ value: '110000',
+ areaLevel: 'city',
+ label: '北京市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '120000',
+ areaLevel: 'province',
+ label: '天津市',
+ children: [
+ {
+ value: '120000',
+ areaLevel: 'city',
+ label: '天津市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '310000',
+ areaLevel: 'province',
+ label: '上海市',
+ children: [
+ {
+ value: '310000',
+ areaLevel: 'province',
+ label: '上海市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '440000',
+ areaLevel: 'province',
+ label: '广东省',
+ children: [
+ {
+ value: '440100',
+ areaLevel: 'city',
+ label: '广州市',
+ children: [],
+ },
+ {
+ value: '440300',
+ areaLevel: 'city',
+ label: '深圳市',
+ children: [],
+ },
+ {
+ value: '440400',
+ areaLevel: 'city',
+ label: '珠海市',
+ children: [],
+ },
+ {
+ value: '440600',
+ areaLevel: 'city',
+ label: '佛山市',
+ children: [],
+ },
+ {
+ value: '441300',
+ areaLevel: 'city',
+ label: '惠州市',
+ children: [],
+ },
+ {
+ value: '441900',
+ areaLevel: 'city',
+ label: '东莞市',
+ children: [],
+ },
+ {
+ value: '442000',
+ areaLevel: 'city',
+ label: '中山市',
+ children: [],
+ },
+ ],
+ },
+ {
+ value: '130000',
+ areaLevel: 'province',
+ label: '河北省',
+ children: [
+ {
+ value: '130100',
+ areaLevel: 'city',
+ label: '石家庄市',
+ children: [],
+ },
+ {
+ value: '131000',
+ areaLevel: 'city',
+ label: '廊坊市',
+ children: [],
+ },
+ ],
+ },
+];
diff --git a/site/components/rumbling/index.tsx b/site/components/task/index.tsx
similarity index 86%
rename from site/components/rumbling/index.tsx
rename to site/components/task/index.tsx
index 2727bac06b..a3f5c06962 100644
--- a/site/components/rumbling/index.tsx
+++ b/site/components/task/index.tsx
@@ -2,6 +2,7 @@ import { initWidgets } from './widgets';
import React, { useEffect, useMemo, useState } from 'react';
import { config } from './configs/config';
import { DipperContainer, IConfig } from '@antv/dipper';
+import 'antd/dist/antd.css'
interface IInitData {
areaVOList: any[];
@@ -21,7 +22,7 @@ export default function RumbMap() {
}, []);
return (
-
+
cfg={mapConfig!} />
);
diff --git a/site/components/task/widgets/Activity.tsx b/site/components/task/widgets/Activity.tsx
new file mode 100644
index 0000000000..35964b621a
--- /dev/null
+++ b/site/components/task/widgets/Activity.tsx
@@ -0,0 +1,25 @@
+import { Select } from 'antd';
+import React, { useState,useEffect } from 'react';
+import { ActivityOption } from '../configs/mock';
+
+const { Option } = Select
+
+export function Activity() {
+
+ const [active,setActive] = useState
()
+
+ useEffect(()=>{
+ setActive(ActivityOption[0].value)
+ },[])
+
+ return(
+
+ )
+}
diff --git a/site/components/task/widgets/ActivityTask/index.module.css b/site/components/task/widgets/ActivityTask/index.module.css
new file mode 100644
index 0000000000..6b4818609b
--- /dev/null
+++ b/site/components/task/widgets/ActivityTask/index.module.css
@@ -0,0 +1,54 @@
+.selectactivity {
+ padding: 0 0 20px 20px ;
+}
+.selectactivity .select {
+ display: flex;
+ align-items: center;
+ flex-wrap: wrap;
+}
+.selectactivity .select .selectitem {
+ display: flex;
+ align-items: center;
+ width: 183px;
+ height: 64px;
+ margin: 0 15px 15px 0;
+ position: relative;
+ padding-left: 15px;
+}
+.selectactivity .select .selectitem .icon {
+ width: 40px;
+ height: 40px;
+ margin-right: 10px;
+}
+.selectactivity .select .selectitem .selecticon {
+ width: 21px;
+ height: 21px;
+ position: absolute;
+ right: 6px;
+ top: 6px;
+}
+.empty {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ height: calc(674px - 80px);
+ justify-content: center;
+}
+.empty img {
+ width: 216px;
+ height: 132px;
+ margin-left: 100px;
+}
+.empty span {
+ color: rgba(0, 0, 0, 0.55);
+ margin-top: 20px;
+}
+.submit {
+ position: absolute;
+ bottom: 0;
+ right: 0;
+}
+.task {
+ height: calc(674px - 130px);
+ position: relative;
+}
diff --git a/site/components/task/widgets/ActivityTask/index.tsx b/site/components/task/widgets/ActivityTask/index.tsx
new file mode 100644
index 0000000000..94955be8f8
--- /dev/null
+++ b/site/components/task/widgets/ActivityTask/index.tsx
@@ -0,0 +1,91 @@
+import React, { useState, useMemo } from 'react'
+import { useLayerGroup } from '@antv/dipper'
+import { Alert, Button, Select } from 'antd'
+import { personOption, selectActivityItem } from '../../configs/mock'
+import style from './index.module.css'
+
+const { Option } = Select
+
+export function ActivityTask() {
+ const selecticon = 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*kyI9T7Lrej4AAAAAAAAAAAAAARQnAQ'
+ const emptyicon = 'https://gw.alipayobjects.com/mdn/rms_58ab56/afts/img/A*H9dxSp69pi0AAAAAAAAAAAAAARQnAQ'
+ const { selectFeatures = [] } = useLayerGroup('grid')
+ const [current, setCurrent] = useState(selectActivityItem[0]?.value)
+
+ const selectItem = (item) => {
+ setCurrent(item)
+ }
+
+ const alertMsg = useMemo(() => {
+ if (selectFeatures.length === 2) {
+ return '勾选多个网格中,批量分配后将一起更新数据'
+ }
+ if (selectFeatures.length >= 3) {
+ return '你当前多选网格中包含已分配网格,无法批量分配,建议选择单个网格、或选择多个未分配网格的批量操作'
+ }
+ return '';
+ }, [JSON.stringify(selectFeatures)]);
+
+ const HasSelectFeature = () => {
+ return (
+
+
+ {selectFeatures.length >= 2 &&
}
+
+
+
选择活动
+
+ {selectActivityItem && selectActivityItem.map((item) => {
+ return (
+
selectItem(item.value)}
+ style={{
+ border: current === item.value ? '1px solid #1E73F8' : '1px solid rgba(0,0,0,0.15)',
+ }}
+ className={style.selectitem}>
+
+
{item.label}
+ {current === item.value &&
}
+
+ )
+ })}
+
+
+
+
分配人员
+
+
+
+
+
+
+
+ )
+ }
+
+ const Empty = () => {
+ return (
+
+
+
暂无数据
+
+ )
+ }
+
+ return (
+
+ {!selectFeatures.length ? : }
+
+ )
+}
diff --git a/site/components/rumbling/widgets/GridLayer.tsx b/site/components/task/widgets/GridLayer.tsx
similarity index 71%
rename from site/components/rumbling/widgets/GridLayer.tsx
rename to site/components/task/widgets/GridLayer.tsx
index 138a2a6b67..0ee5096345 100644
--- a/site/components/rumbling/widgets/GridLayer.tsx
+++ b/site/components/task/widgets/GridLayer.tsx
@@ -34,15 +34,43 @@ export function GridLayer() {
return layers.find((item: any) => item.type === 'gridLayer');
}, [layers]);
+ const testData = {
+ title: '图例',
+ items: [
+ {
+ colors: ['#fef0d9', '#fdcc8a', '#fc8d59', '#e34a33', '#b30000'],
+ title: '已分配',
+ },
+ {
+ colors: ['#f1eef6', '#bdc9e1', '#74a9cf', '#2b8cbe', '#045a8d'],
+ title: '未分配',
+ },
+ ],
+ };
+
const updateLayerLegend = (items: any[]) => {
updateLegend('gridLayerLegend', {
- type: 'discreteColor',
+ type: 'multiClassifyColor',
display: true,
position: 'bottomleft',
options: {
- targetName: '区域类型',
+ title: '网格',
unkownName: layerProps.options.unkownName,
- items,
+ items: [
+ {
+ colors: ['#BEC3BD', '#A1A6A0', '#828681', '#646763'],
+ title: '已分配',
+ },
+ {
+ colors: ['#CFE1B9', '#B0C298', '#90A276', '#718355'],
+ title: '未分配',
+ },
+ ],
+ values: items.map((item) => {
+ return item.value.map((v) => {
+ return (v / 10000).toFixed(2);
+ });
+ }),
},
});
};
@@ -70,10 +98,18 @@ export function GridLayer() {
return;
}
+ const color = ['#CFE1B9','#B0C298','#90A276','#718355']
+
const layer = new GridLayerGroup({
name: 'grid',
- geodata: geoData,
- options: layerProps.options,
+ data: geoData,
+ options: {
+ ...layerProps.options,
+ fill:{
+ ...layerProps.options.fill,
+ color
+ }
+ },
});
layerService.addLayer(layer);
diff --git a/site/components/task/widgets/MapExhibit/index.module.css b/site/components/task/widgets/MapExhibit/index.module.css
new file mode 100644
index 0000000000..ac0a3cda7f
--- /dev/null
+++ b/site/components/task/widgets/MapExhibit/index.module.css
@@ -0,0 +1,19 @@
+.exhibititem {
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+}
+.exhibititem :global .ant-switch-checked {
+ background-color: #1E73F8;
+}
+.dropdown {
+ border-left: 1px solid #f3f3f3;
+ border-right: 1px solid #f3f3f3;
+ padding: 0 10px;
+ height: 32px;
+ line-height: 32px;
+}
+.dropicon {
+ padding-left: 8px;
+ color: rgba(0, 0, 0, 0.25);
+}
diff --git a/site/components/task/widgets/MapExhibit/index.tsx b/site/components/task/widgets/MapExhibit/index.tsx
new file mode 100644
index 0000000000..04b974271c
--- /dev/null
+++ b/site/components/task/widgets/MapExhibit/index.tsx
@@ -0,0 +1,29 @@
+import { DownOutlined } from "@ant-design/icons";
+import { Dropdown, Menu, Switch } from "antd";
+import React from "react";
+import style from './index.module.css'
+
+export function MapExhibit() {
+ const onChange = (e) => {
+ // TODO 根据业务实现
+ console.log(e)
+ }
+ const menu = (
+
+ );
+
+ return (
+
+
+ 地图展示
+
+
+ )
+}
diff --git a/site/components/task/widgets/MeshName/index.module.css b/site/components/task/widgets/MeshName/index.module.css
new file mode 100644
index 0000000000..a03ab39e9d
--- /dev/null
+++ b/site/components/task/widgets/MeshName/index.module.css
@@ -0,0 +1,13 @@
+.meahname {
+ padding: 20px;
+}
+.closeicon {
+ padding: 0 8px;
+}
+.edit {
+ display: flex;
+ align-items: center;
+}
+.edit span:hover {
+ color: #1890ff;
+}
diff --git a/site/components/task/widgets/MeshName/index.tsx b/site/components/task/widgets/MeshName/index.tsx
new file mode 100644
index 0000000000..0672803712
--- /dev/null
+++ b/site/components/task/widgets/MeshName/index.tsx
@@ -0,0 +1,83 @@
+import React, { useRef, useState, useMemo, useCallback } from 'react';
+import { CheckOutlined, CloseOutlined, EditOutlined } from '@ant-design/icons';
+import styles from './index.module.css'
+import { Input } from 'antd';
+import { useLayerGroup } from '@antv/dipper';
+
+export function MeshName() {
+ const { selectFeatures, updateProperties } = useLayerGroup('grid');
+ const [edit, setEdit] = useState(false);
+ const ref = useRef();
+
+ /**
+ * get meshname
+ * type []string
+ */
+ const meshName = useMemo(() => {
+ if (!selectFeatures.length) return [];
+ return selectFeatures.map((item) => {
+ // @ts-ignore
+ return item.feature.properties.name;
+ });
+ }, [JSON.stringify(selectFeatures)]);
+
+ // 修改 网格名称
+ const editMeshName = useCallback(() => {
+ // @ts-ignore
+ const value = ref.current.state.value;
+ selectFeatures.forEach((item) => {
+ const properties = {
+ ...item.feature.properties,
+ name: value,
+ };
+ updateProperties(item.feature, properties);
+ });
+ setEdit(false);
+ }, [JSON.stringify(selectFeatures)]);
+
+ // select more meshname 编辑 网格名称
+ const EditMeshName = () => {
+ return (
+ <>
+ {!edit ? (
+ setEdit(!edit)}>
+ {meshName}
+
+
+ ) : (
+
+
+
+ setEdit(false)} />
+
+ )}
+ >
+ );
+ };
+
+ // show 多个网格名称
+ const ShowMeshNames = () => {
+ return (
+
+ {meshName.length >= 2 && meshName.map((s) => {
+ return (
+ {s},
+ )
+ })}
+
+ );
+ };
+
+ return (
+ <>
+ {meshName && meshName.length ? (
+
+ {meshName.length === 1 ? : }
+
+ ) : null}
+ >
+ );
+}
diff --git a/site/components/task/widgets/MeshTools/SvgElement.tsx b/site/components/task/widgets/MeshTools/SvgElement.tsx
new file mode 100644
index 0000000000..e1a2b3551b
--- /dev/null
+++ b/site/components/task/widgets/MeshTools/SvgElement.tsx
@@ -0,0 +1,57 @@
+import React from 'react';
+export function MeshSplitSvg() {
+ return (
+
+ );
+}
+
+export function MeshMergeSvg() {
+ return (
+
+
+
+ );
+}
diff --git a/site/components/task/widgets/MeshTools/index.module.css b/site/components/task/widgets/MeshTools/index.module.css
new file mode 100644
index 0000000000..c378ada7cb
--- /dev/null
+++ b/site/components/task/widgets/MeshTools/index.module.css
@@ -0,0 +1,10 @@
+.meshTools{
+ width: 32px;
+ height: 160px;
+ background: #fff;
+ border-radius: 2px;
+ display: flex;
+ flex-direction: column;
+ justify-content: space-between;
+ padding:15px 5px;
+}
diff --git a/site/components/task/widgets/MeshTools/index.tsx b/site/components/task/widgets/MeshTools/index.tsx
new file mode 100644
index 0000000000..fe0ec54f47
--- /dev/null
+++ b/site/components/task/widgets/MeshTools/index.tsx
@@ -0,0 +1,82 @@
+import React, { useMemo, useState, useRef } from 'react';
+import styles from './index.module.css'
+import { MeshSplitSvg, MeshMergeSvg } from './SvgElement';
+import { useLayerGroup } from '@antv/dipper'
+import { Input, message, Modal, Popconfirm, Tooltip } from 'antd';
+
+
+export function MeshTools() {
+ const { selectFeatures = [] } = useLayerGroup('grid')
+ const [visible, setVisible] = useState(false)
+ const refs = useRef()
+
+ const disable = { cursor: 'pointer', opacity: 1 }
+ const noDisable = { cursor: 'not-allowed', opacity: 0.25 }
+
+ const cssPropsSplit = useMemo(() => {
+ if (selectFeatures.length === 1) return disable;
+ return noDisable;
+ }, [JSON.stringify(selectFeatures)]);
+
+ const cssPropsMerge = useMemo(() => {
+ if (selectFeatures.length >= 2) {
+ return disable
+ }
+ return noDisable;
+ }, [JSON.stringify(selectFeatures)]);
+
+ const splitMesh = () => {
+ // TODO 根据业务实现
+ }
+
+ const mergrMesh = () => {
+ // @ts-ignore
+ const value = refs.current.state.value
+ if (!value) {
+ return message.error('请输入要合并后的名称')
+ }
+ // TODO 根据业务实现
+ setVisible(false)
+ }
+
+ return (
+
+
+
+
+
+
+
+
+
= 2 ? '选择多个网格,可以合并' : null}>
+ setVisible(true)}>
+
+
网格合并
+
+
+
+
setVisible(false)}
+ >
+ 合并后的新网格名称
+
+
+
+
+ )
+}
diff --git a/site/components/task/widgets/Save.tsx b/site/components/task/widgets/Save.tsx
new file mode 100644
index 0000000000..cfaffaef62
--- /dev/null
+++ b/site/components/task/widgets/Save.tsx
@@ -0,0 +1,11 @@
+import { SaveOutlined } from '@ant-design/icons';
+import { Button } from 'antd';
+import React from 'react';
+
+export function Save() {
+ return (
+ }>
+ 保存
+
+ );
+}
diff --git a/site/components/task/widgets/SearchPerson.tsx b/site/components/task/widgets/SearchPerson.tsx
new file mode 100644
index 0000000000..5919b03c50
--- /dev/null
+++ b/site/components/task/widgets/SearchPerson.tsx
@@ -0,0 +1,60 @@
+import React, { useState, useEffect } from "react";
+import { Dropdown, Input, Menu, Select } from 'antd';
+import { SearchOutlined } from "@ant-design/icons";
+import { personOption } from "../configs/mock";
+
+const { Search } = Input
+const { Option } = Select
+
+// 此功能 仅做展示,以实际业务为准
+export function SearchPerson() {
+
+ const [persons, setPersons] = useState([])
+ const [visible, setVisible] = useState(false)
+
+ const onSearch = (e) => {
+ const value = e.target.value
+ setTimeout(() => {
+ if (value) {
+ setPersons(personOption())
+ setVisible(true)
+ } else {
+ setPersons([])
+ setVisible(false)
+ }
+
+ }, 300)
+ }
+
+ // 人员搜索
+ const onSelect = (value) =>{
+ // TODO 根据业务实现
+ }
+
+ const menu = (
+
+ );
+
+ return (
+
+
+ }
+ onChange={onSearch}
+ />
+
+
+ )
+}
diff --git a/site/components/task/widgets/Send.tsx b/site/components/task/widgets/Send.tsx
new file mode 100644
index 0000000000..8375aff6de
--- /dev/null
+++ b/site/components/task/widgets/Send.tsx
@@ -0,0 +1,9 @@
+import { SendOutlined } from '@ant-design/icons';
+import { Button } from 'antd';
+import React from 'react';
+
+export function Send() {
+ return(
+
+ )
+}
diff --git a/site/components/task/widgets/Status.tsx b/site/components/task/widgets/Status.tsx
new file mode 100644
index 0000000000..f43d784f66
--- /dev/null
+++ b/site/components/task/widgets/Status.tsx
@@ -0,0 +1,25 @@
+import { Select } from 'antd';
+import React,{ useState,useEffect } from 'react';
+import { StatusOption } from '../configs/mock';
+
+const { Option } = Select
+
+export function Status() {
+
+ const [status,setStatus] = useState()
+
+ useEffect(()=>{
+ setStatus(StatusOption[0].value)
+ },[])
+
+ return(
+
+ )
+}
diff --git a/site/components/task/widgets/index.ts b/site/components/task/widgets/index.ts
new file mode 100644
index 0000000000..4a21def18e
--- /dev/null
+++ b/site/components/task/widgets/index.ts
@@ -0,0 +1,33 @@
+import { registerWidget } from '@antv/dipper-core';
+import {
+ CitySelect,
+ ClassifyColor,
+ DiscreteColor,
+} from '@antv/dipper-widgets';
+import { Activity } from './Activity';
+import { ActivityTask } from './ActivityTask';
+import { GridLayer } from './GridLayer';
+import { MeshName } from './MeshName/index';
+import { Save } from './Save';
+import { SearchPerson } from './SearchPerson';
+import { Send } from './Send';
+import { Status } from './Status';
+import { MeshTools } from './MeshTools';
+import { MapExhibit } from './MapExhibit/index';
+
+export function initWidgets() {
+ registerWidget('citySelect', CitySelect);
+ registerWidget('gridLayer', GridLayer);
+ registerWidget('classifyColor', ClassifyColor);
+ registerWidget('discreteColor', DiscreteColor);
+ registerWidget('meshName', MeshName);
+ registerWidget('meshTools',MeshTools)
+
+ registerWidget('save', Save);
+ registerWidget('publishbar', Send);
+ registerWidget('activity', Activity);
+ registerWidget('status',Status);
+ registerWidget('mapExhibit', MapExhibit);
+ registerWidget('searchPerson',SearchPerson)
+ registerWidget('activityTask',ActivityTask)
+}
diff --git a/site/css/dipper.css b/site/css/dipper.css
new file mode 100644
index 0000000000..c1b807fd3d
--- /dev/null
+++ b/site/css/dipper.css
@@ -0,0 +1,58 @@
+.dippercontainer {
+ display: flex;
+ align-items: center;
+ flex-direction: column;
+ height: 538px;
+ justify-content: center;
+}
+
+.title {
+ font-size: 30px;
+ font-family: 'PingFangSC-Semibold';
+}
+
+.subtitle {
+ font-size: 16px;
+ color: #697B8C;
+ font-family: 'PingFangSC-Regular';
+ padding-top: 20px;
+}
+
+.dipperdemo {
+ display: flex;
+}
+
+.dipperitem {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ min-width: 400px;
+ max-width: 600px;
+ margin:40px 20px;
+}
+
+.dipperimg {
+ border-radius: 50%;
+ box-shadow: inset 0 0 16px 4px rgba(115, 108, 255, 0.44);
+ background-color: rgba(#746CFF, 0.24);
+ height: 180px;
+ width: 180px;
+ padding: 40px;
+}
+
+.dipperitem:hover .dipperimg{
+ padding: 32px;
+ border: 8px solid rgba(115, 108, 255, 0.08);
+ box-shadow: inset 0 0 16px 4px rgba(115, 108, 255, 0.44);
+}
+
+.dippertitle {
+ font-size: 24px;
+ font-family: 'PingFangSC-Semibold';
+ color: #0D1A26;
+ padding-top: 40px;
+}
+
+.dipperitem:hover .dippertitle {
+ color: #873BF4;
+}
diff --git a/site/css/dippermap.css b/site/css/dippermap.css
new file mode 100644
index 0000000000..dc6a2b634e
--- /dev/null
+++ b/site/css/dippermap.css
@@ -0,0 +1,33 @@
+.dippermapcontainer{
+ /* height: 656px; */
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ justify-content: center;
+ padding-top: 68px;
+}
+
+.title {
+ font-size: 30px;
+ font-family: 'PingFangSC-Semibold';
+}
+
+.subtitle {
+ font-size: 16px;
+ color: #697B8C;
+ font-family: 'PingFangSC-Regular';
+ padding-top: 20px;
+}
+.carousel{
+ width: 80%;
+ padding-top: 36px;
+}
+.carousel img{
+ width: 100%;
+ height: 520px;
+ object-fit: cover;
+}
+.ant-carousel-vertical .slick-dots-right{
+ right: -40px !important;
+ top: 100px;
+}
diff --git a/site/locale.json b/site/locale.json
index abcafcebaf..14bcffb150 100644
--- a/site/locale.json
+++ b/site/locale.json
@@ -16,5 +16,8 @@
"深版精彩案例": "Dark Theme",
"感谢信赖":"WE ARE TRUSTED BY",
"新版发布" : "New Version",
- "一个个真实的地理数据可视化案例,将复杂的地理数据,通过简单,易用的API接口,让用户达到开箱即用的效果。" : "We have summarized a series of story design templates from lots of real geospatial data visualization cases, so that users can use them directly."
+ "一个个真实的地理数据可视化案例,将复杂的地理数据,通过简单,易用的API接口,让用户达到开箱即用的效果。" : "We have summarized a series of story design templates from lots of real geospatial data visualization cases, so that users can use them directly.",
+ "指挥监控场景": "Command monitoring scene",
+ "指挥分配场景": "Command distribution scenario",
+ "可视化配置场景": "Visual configuration scenario"
}
diff --git a/site/pages/apps/home.tsx b/site/pages/apps/home.tsx
deleted file mode 100644
index 0cff196ba5..0000000000
--- a/site/pages/apps/home.tsx
+++ /dev/null
@@ -1,7 +0,0 @@
-import React from 'react';
-
-const Page: React.FC & { noLayout: boolean } = () => 地图
;
-
-Page.noLayout = true;
-
-export default Page;
\ No newline at end of file
diff --git a/site/pages/index.zh.tsx b/site/pages/index.zh.tsx
index 88a079e901..8dacae92fa 100644
--- a/site/pages/index.zh.tsx
+++ b/site/pages/index.zh.tsx
@@ -6,75 +6,15 @@ import Features from '@antv/gatsby-theme-antv/site/components/Features';
import SEO from '@antv/gatsby-theme-antv/site/components/Seo';
import React from 'react';
import { useTranslation } from 'react-i18next';
+import { useConfig } from './useConfig';
+import { Dipper } from '../components/Dipper';
+import { DipperMap } from '../components/DipperMap';
import '../css/home.css';
const IndexPage = () => {
const { t, i18n } = useTranslation();
+ const { L7Case, L7Features,notifications,companies, ecosystems} = useConfig();
- const features = [
- {
- icon:
- 'https://gw.alipayobjects.com/zos/basement_prod/ca2168d1-ae50-4929-8738-c6df62231de3.svg',
- title: t('架构灵活且自由'),
- description: t('支持地图底图,渲染引擎,图层自由定制、扩展,组合'),
- },
- {
- icon:
- 'https://gw.alipayobjects.com/zos/basement_prod/0ccf4dcb-1bac-4f4e-8d8d-f1031c77c9c8.svg',
- title: t('业务专业且通用'),
- description: t(
- '以图形符号学地理设计体系理论基础,易用、易理解、专业、专注',
- ),
- },
- {
- icon:
- 'https://gw.alipayobjects.com/zos/basement_prod/fd232581-14b3-45ec-a85c-fb349c51b376.svg',
- title: t('视觉酷炫且动感'),
- description: t('支持海量数据,2D、3D,动态,可交互,高性能渲染'),
- },
- ];
- const companies = [
- {
- name: '阿里云',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*V_xMRIvw2iwAAAAAAAAAAABkARQnAQ',
- },
- {
- name: '支付宝',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*lYDrRZvcvD4AAAAAAAAAAABkARQnAQ',
- },
- {
- name: '天猫',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*BQrxRK6oemMAAAAAAAAAAABkARQnAQ',
- },
- {
- name: '淘宝网',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*1l8-TqUr7UcAAAAAAAAAAABkARQnAQ',
- },
- {
- name: '网商银行',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*ZAKFQJ5Bz4MAAAAAAAAAAABkARQnAQ',
- },
- {
- name: '盒马',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*ePJMQZCb8vkAAAAAAAAAAABkARQnAQ',
- },
- {
- name: 'yunos',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*_js7SaNosUwAAAAAAAAAAABkARQnAQ',
- },
- {
- name: '菜鸟',
- img:
- 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*TgV-RZDODJIAAAAAAAAAAABkARQnAQ',
- },
- ];
const bannerButtons = [
{
text: t('图表示例'),
@@ -87,43 +27,55 @@ const IndexPage = () => {
},
];
- const notifications = [
+
+ const dipper = [
{
- type: t('推荐'),
- title: t('如何制作不一样的疫情世界地图-酷炫、动感的地理可视化'),
- date: '2020.03.12',
- link: 'https://www.yuque.com/antv/blog/wigku2',
+ title: t('配置化'),
+ image: 'https://gw.alipayobjects.com/zos/bmw-prod/a8d32053-ef9d-485e-ae13-2b49535e6f4f.svg',
+ link: `/${i18n.language}/view`
},
{
- type: t('新版发布'),
- title: t('L7 2.1 正式版'),
- date: '2020.03.12',
- link: ' https://www.yuque.com/antv/blog/ows55v',
+ title: t('组件化'),
+ image: 'https://gw.alipayobjects.com/zos/bmw-prod/4235cc53-ef5f-4a47-a33c-1623df19e4b7.svg',
+ link: `/${i18n.language}/task`
},
+ {
+ title: t('自由定制'),
+ image: 'https://gw.alipayobjects.com/zos/bmw-prod/29cbd68c-86ac-440c-a38d-792dbd8aea61.svg',
+ link: 'https://dippermap.alipay.com'
+ }
];
- const cases = [
+ const dippermap = [
{
- logo:
- 'https://gw.alipayobjects.com/mdn/antv_site/afts/img/A*gjBmT56SDgsAAAAAAAAAAABkARQnAQ',
- title: t('浅版精彩案例'),
- description: t(
- '一个个真实的地理数据可视化案例,将复杂的地理数据,通过简单,易用的API接口,让用户达到开箱即用的效果。',
- ),
- link: `/${i18n.language}/examples/gallery/basic`,
- image:
- 'https://gw.alipayobjects.com/mdn/antv_site/afts/img/A*h1vhT6eSVPkAAAAAAAAAAABkARQnAQ',
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*6S8hQJAUB2oAAAAAAAAAAAAAARQnAQ',
+ alt: 'heat',
+ desc: '3D热力图',
},
{
- logo:
- 'https://gw.alipayobjects.com/mdn/antv_site/afts/img/A*gjBmT56SDgsAAAAAAAAAAABkARQnAQ',
- title: t('深版精彩案例'),
- description: t(
- '一个个真实的地理数据可视化案例,将复杂的地理数据,通过简单,易用的API接口,让用户达到开箱即用的效果。',
- ),
- link: `/${i18n.language}/examples/gallery/basic`,
- image:
- 'https://gw.alipayobjects.com/mdn/antv_site/afts/img/A*-gtxQbUPoGQAAAAAAAAAAABkARQnAQ',
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*R8juSLJc86wAAAAAAAAAAAAAARQnAQ',
+ alt: '3DARC',
+ desc: '3D曲线',
+ },
+ {
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*MDmtT6lRS6EAAAAAAAAAAAAAARQnAQ',
+ alt: 'trip',
+ desc: '路径图',
+ },
+ {
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*lRdLQotjkKsAAAAAAAAAAAAAARQnAQ',
+ alt: 'point',
+ desc: '3D柱图',
+ },
+ {
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*W_DMQ5DVmIsAAAAAAAAAAAAAARQnAQ',
+ alt: 'polygon',
+ desc: '中国3D地图',
+ },
+ {
+ img: 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*InJXT6G-l6UAAAAAAAAAAAAAARQnAQ',
+ alt: 'hex',
+ desc: '六边形图',
},
];
@@ -140,16 +92,19 @@ const IndexPage = () => {
}
title={t('L7 空间数据可视分析')}
description={t(
- '蚂蚁金服 AntV 数据可视化团队推出的基于 WebGL 的开源大规模地理空间数据可视分析开发框架。',
+ '蚂蚁金服 AntV 数据可视化团队推出的基于 WebGL 的开源大规模地理空间数据可视分析引擎。',
)}
buttons={bannerButtons}
notifications={notifications}
className="banner"
githubStarLink="https://github.com/antvis/L7/stargazers"
/>
-
-
+
+
+
+
+
>
);
};
diff --git a/site/pages/map.en.tsx b/site/pages/map.en.tsx
deleted file mode 100644
index 72af948dfc..0000000000
--- a/site/pages/map.en.tsx
+++ /dev/null
@@ -1,2 +0,0 @@
-import Index from './map.zh';
-export default Index;
diff --git a/site/pages/map.zh.tsx b/site/pages/map.zh.tsx
index 6396d0754a..d12c056c84 100644
--- a/site/pages/map.zh.tsx
+++ b/site/pages/map.zh.tsx
@@ -1,6 +1,6 @@
import React from 'react';
import Loadable from "@loadable/component"
-const Map = Loadable(() => import("../components/rumbling"))
+const Map = Loadable(() => import("../components/analysis"))
const Page: React.FC & { noLayout: boolean } = () => ;
Page.noLayout = true;
diff --git a/site/pages/task.en.tsx b/site/pages/task.en.tsx
new file mode 100644
index 0000000000..e5d8e0bba6
--- /dev/null
+++ b/site/pages/task.en.tsx
@@ -0,0 +1,8 @@
+import React from 'react';
+import Loadable from "@loadable/component"
+const Map = Loadable(() => import("../components/task"))
+const Page: React.FC & { noLayout: boolean } = () => ;
+
+Page.noLayout = true;
+
+export default Page;
\ No newline at end of file
diff --git a/site/pages/task.zh.tsx b/site/pages/task.zh.tsx
new file mode 100644
index 0000000000..f02b6a107e
--- /dev/null
+++ b/site/pages/task.zh.tsx
@@ -0,0 +1,2 @@
+import Index from './task.en';
+export default Index;
diff --git a/site/pages/useConfig.ts b/site/pages/useConfig.ts
new file mode 100644
index 0000000000..5c3ecc2dbd
--- /dev/null
+++ b/site/pages/useConfig.ts
@@ -0,0 +1,159 @@
+import { useMemo } from 'react';
+import { useTranslation } from 'react-i18next';
+
+export const useConfig = () => {
+ const { t, i18n } = useTranslation();
+
+ // 通知
+ const notifications = useMemo(() => {
+ return [{
+ type: t('推荐'),
+ title: t('如何制作不一样的疫情世界地图-酷炫、动感的地理可视化'),
+ date: '2020.03.12',
+ link: 'https://www.yuque.com/antv/blog/wigku2',
+ },
+ {
+ type: t('新版发布'),
+ title: t('L7 2.1 正式版'),
+ date: '2020.03.12',
+ link: ' https://www.yuque.com/antv/blog/ows55v',
+ },
+ ];
+ }, []);
+
+ // L7 特性
+ const L7Features = useMemo(() => {
+ return [
+ {
+ icon:
+ 'https://gw.alipayobjects.com/zos/basement_prod/ca2168d1-ae50-4929-8738-c6df62231de3.svg',
+ title: t('架构灵活且自由'),
+ description: t('支持地图底图,渲染引擎,图层自由定制、扩展,组合'),
+ },
+ {
+ icon:
+ 'https://gw.alipayobjects.com/zos/basement_prod/0ccf4dcb-1bac-4f4e-8d8d-f1031c77c9c8.svg',
+ title: t('业务专业且通用'),
+ description: t(
+ '以图形符号学地理设计体系理论基础,易用、易理解、专业、专注',
+ ),
+ },
+ {
+ icon:
+ 'https://gw.alipayobjects.com/zos/basement_prod/fd232581-14b3-45ec-a85c-fb349c51b376.svg',
+ title: t('视觉酷炫且动感'),
+ description: t('支持海量数据,2D、3D,动态,可交互,高性能渲染'),
+ },
+ ];
+
+ }, [])
+
+
+ const L7Case = useMemo(() => {
+ return [
+ {
+ logo:
+ 'https://antv-2018.alipay.com/assets/image/icon/l7.svg',
+ title: t('指挥分配场景'),
+ description: t(
+ '区域化网格化数据管理指挥分配场景',
+ ),
+ link: `/${i18n.language}/task`,
+ image:
+ 'https://gw.alipayobjects.com/mdn/rms_08cc33/afts/img/A*CLJESKDO1g4AAAAAAAAAAAAAARQnAQ',
+ },
+ {
+ logo:
+ 'https://antv-2018.alipay.com/assets/image/icon/l7.svg',
+ title: t('地图数据分析'),
+ description: t(
+ '区域化网格化数据分析场景',
+ ),
+ link: `/${i18n.language}/view`,
+ image:
+ 'https://gw.alipayobjects.com/mdn/rms_08cc33/afts/img/A*jb4tS7BiNo4AAAAAAAAAAAAAARQnAQ',
+ },
+ {
+ logo:
+ 'https://gw.alipayobjects.com/zos/bmw-prod/222865fc-15e9-44b9-b726-444e1512d937.ico',
+ title: t('地理分析工具'),
+ description: t(
+ '地图可视化配置分析类场景',
+ ),
+ link: `/${i18n.language}/examples/gallery/basic`,
+ image:
+ 'https://gw.alipayobjects.com/mdn/rms_e7e1c6/afts/img/A*MPWKQqh54vwAAAAAAAAAAAAAARQnAQ',
+ },
+ ]
+
+ }, [])
+ const companies = useMemo(() => [{
+ name: '阿里云',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*V_xMRIvw2iwAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '支付宝',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*lYDrRZvcvD4AAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '天猫',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*BQrxRK6oemMAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '淘宝网',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*1l8-TqUr7UcAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '网商银行',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*ZAKFQJ5Bz4MAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '盒马',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_f8c6a0/afts/img/A*ePJMQZCb8vkAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: 'yunos',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*_js7SaNosUwAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '菜鸟',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*TgV-RZDODJIAAAAAAAAAAABkARQnAQ',
+ }
+ ], []);
+
+ const ecosystems = useMemo(() => [{
+ name: '阿里云',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*V_xMRIvw2iwAAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '支付宝',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*lYDrRZvcvD4AAAAAAAAAAABkARQnAQ',
+ },
+ {
+ name: '天猫',
+ img:
+ 'https://gw.alipayobjects.com/mdn/rms_2274c3/afts/img/A*BQrxRK6oemMAAAAAAAAAAABkARQnAQ',
+ }
+ ], []);
+
+ return {
+ ecosystems,
+ L7Features,
+ notifications,
+ companies,
+ L7Case,
+ }
+}
+
+
+
diff --git a/site/pages/view.en.tsx b/site/pages/view.en.tsx
new file mode 100644
index 0000000000..300b038621
--- /dev/null
+++ b/site/pages/view.en.tsx
@@ -0,0 +1,2 @@
+import Index from './view.zh';
+export default Index;
diff --git a/site/pages/view.zh.tsx b/site/pages/view.zh.tsx
new file mode 100644
index 0000000000..d12c056c84
--- /dev/null
+++ b/site/pages/view.zh.tsx
@@ -0,0 +1,8 @@
+import React from 'react';
+import Loadable from "@loadable/component"
+const Map = Loadable(() => import("../components/analysis"))
+const Page: React.FC & { noLayout: boolean } = () => ;
+
+Page.noLayout = true;
+
+export default Page;
\ No newline at end of file