@tsingroc/tsingroc-components 5.0.0-alpha.11 → 5.0.0-alpha.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (150) hide show
  1. package/dist/components/Auth.d.ts +310 -0
  2. package/dist/components/Auth.js +267 -0
  3. package/dist/components/AutoResizedECharts.d.ts +21 -0
  4. package/dist/components/AutoResizedECharts.js +98 -0
  5. package/dist/components/Calendar.d.ts +50 -0
  6. package/dist/components/Calendar.js +130 -0
  7. package/dist/components/CircularProgress.d.ts +21 -0
  8. package/dist/components/CircularProgress.js +34 -0
  9. package/dist/components/ConnectedECharts.d.ts +31 -0
  10. package/dist/components/ConnectedECharts.js +100 -0
  11. package/dist/components/ECharts.d.ts +57 -0
  12. package/dist/components/ECharts.js +255 -0
  13. package/dist/components/Header.d.ts +67 -0
  14. package/dist/components/Header.js +171 -0
  15. package/dist/components/ImageBackground.d.ts +32 -0
  16. package/dist/components/ImageBackground.js +76 -0
  17. package/dist/components/IndicatorLight.d.ts +44 -0
  18. package/dist/components/IndicatorLight.js +124 -0
  19. package/dist/components/LeftAlignedECharts.d.ts +42 -0
  20. package/dist/components/LeftAlignedECharts.js +270 -0
  21. package/dist/components/LineChartEditor.d.ts +74 -0
  22. package/dist/components/LineChartEditor.js +458 -0
  23. package/dist/components/LineChartTable.d.ts +38 -0
  24. package/dist/components/LineChartTable.js +245 -0
  25. package/dist/components/LinkedLineChart.d.ts +45 -0
  26. package/dist/components/LinkedLineChart.js +159 -0
  27. package/dist/components/QuickDateRangePicker.d.ts +30 -0
  28. package/dist/components/QuickDateRangePicker.js +58 -0
  29. package/dist/components/SegmentedButtons.d.ts +22 -0
  30. package/dist/components/SegmentedButtons.js +86 -0
  31. package/dist/components/SelectableECharts.d.ts +22 -0
  32. package/dist/components/SelectableECharts.js +402 -0
  33. package/dist/components/Sidebar.d.ts +79 -0
  34. package/dist/components/Sidebar.js +178 -0
  35. package/dist/components/TsingrocDatePicker.d.ts +38 -0
  36. package/dist/components/TsingrocDatePicker.js +64 -0
  37. package/dist/components/TsingrocTheme.d.ts +15 -0
  38. package/dist/components/TsingrocTheme.js +72 -0
  39. package/dist/components/UserButton.d.ts +42 -0
  40. package/dist/components/UserButton.js +105 -0
  41. package/dist/components/VerticalColorLegend.d.ts +7 -0
  42. package/dist/components/VerticalColorLegend.js +208 -0
  43. package/dist/components/WeatherMap.d.ts +18 -0
  44. package/dist/components/WeatherMap.js +658 -0
  45. package/dist/deckgl/TiandituLayer.d.ts +13 -0
  46. package/dist/deckgl/TiandituLayer.js +44 -0
  47. package/dist/deckgl/WeatherData.d.ts +53 -0
  48. package/dist/deckgl/WeatherData.js +94 -0
  49. package/dist/deckgl/index.d.ts +1 -0
  50. package/dist/deckgl/index.js +1 -0
  51. package/dist/echarts/coordinateSystems/grid.d.ts +43 -0
  52. package/dist/echarts/coordinateSystems/grid.js +108 -0
  53. package/dist/echarts/coordinateSystems/index.js +2 -0
  54. package/dist/echarts/coordinateSystems/polar.d.ts +45 -0
  55. package/dist/echarts/coordinateSystems/polar.js +96 -0
  56. package/dist/echarts/gl-types.d.js +0 -0
  57. package/dist/echarts/gl.d.ts +115 -0
  58. package/dist/echarts/gl.js +47 -0
  59. package/dist/echarts/index.d.ts +46 -0
  60. package/dist/echarts/index.js +46 -0
  61. package/dist/echarts/legend.d.ts +17 -0
  62. package/dist/echarts/legend.js +15 -0
  63. package/dist/echarts/radar.d.ts +24 -0
  64. package/dist/echarts/radar.js +22 -0
  65. package/dist/echarts/series/barSeries.d.ts +23 -0
  66. package/dist/echarts/series/barSeries.js +18 -0
  67. package/dist/echarts/series/boxplotSeries.d.ts +21 -0
  68. package/dist/echarts/series/boxplotSeries.js +40 -0
  69. package/dist/echarts/series/index.js +7 -0
  70. package/dist/echarts/series/intervalSeries.d.ts +32 -0
  71. package/dist/echarts/series/intervalSeries.js +55 -0
  72. package/dist/echarts/series/lineSeries.d.ts +36 -0
  73. package/dist/echarts/series/lineSeries.js +45 -0
  74. package/dist/echarts/series/maxBarSeries.d.ts +18 -0
  75. package/dist/echarts/series/maxBarSeries.js +39 -0
  76. package/dist/echarts/series/pieSeries.d.ts +31 -0
  77. package/dist/echarts/series/pieSeries.js +47 -0
  78. package/dist/echarts/series/windLineSeries.d.ts +47 -0
  79. package/dist/echarts/series/windLineSeries.js +51 -0
  80. package/{src/echarts/tooltip.ts → dist/echarts/tooltip.d.ts} +1 -5
  81. package/dist/echarts/tooltip.js +22 -0
  82. package/dist/env.d.js +0 -0
  83. package/dist/index.d.ts +21 -0
  84. package/dist/index.js +21 -0
  85. package/dist/utils/debug.d.ts +1 -0
  86. package/dist/utils/debug.js +25 -0
  87. package/dist/utils/destructureLineDataItem.d.ts +6 -0
  88. package/dist/utils/destructureLineDataItem.js +17 -0
  89. package/dist/utils/filterMap.d.ts +1 -0
  90. package/dist/utils/filterMap.js +11 -0
  91. package/dist/utils/index.d.ts +8 -0
  92. package/dist/utils/index.js +8 -0
  93. package/dist/utils/math.d.ts +9 -0
  94. package/{src/utils/math.ts → dist/utils/math.js} +2 -2
  95. package/dist/utils/mock.d.ts +8 -0
  96. package/dist/utils/mock.js +40 -0
  97. package/dist/utils/normalizeIntoArray.d.ts +1 -0
  98. package/dist/utils/normalizeIntoArray.js +3 -0
  99. package/dist/utils/startOfQuarter.d.ts +2 -0
  100. package/dist/utils/startOfQuarter.js +4 -0
  101. package/dist/utils/timeAxisLabel.d.ts +5 -0
  102. package/dist/utils/timeAxisLabel.js +18 -0
  103. package/package.json +26 -14
  104. package/src/components/Auth.tsx +0 -623
  105. package/src/components/AutoResizedECharts.tsx +0 -70
  106. package/src/components/Calendar.tsx +0 -182
  107. package/src/components/CircularProgress.tsx +0 -38
  108. package/src/components/ConnectedECharts.tsx +0 -62
  109. package/src/components/ECharts.tsx +0 -206
  110. package/src/components/Header.tsx +0 -136
  111. package/src/components/ImageBackground.tsx +0 -58
  112. package/src/components/IndicatorLight.tsx +0 -106
  113. package/src/components/LeftAlignedECharts.tsx +0 -190
  114. package/src/components/LineChartEditor.tsx +0 -558
  115. package/src/components/LineChartTable.tsx +0 -286
  116. package/src/components/LinkedECharts.tsx +0 -51
  117. package/src/components/LinkedLineChart.tsx +0 -144
  118. package/src/components/QuickDateRangePicker.tsx +0 -84
  119. package/src/components/SegmentedButtons.tsx +0 -46
  120. package/src/components/Sidebar.tsx +0 -271
  121. package/src/components/StrictECharts.d.ts +0 -47
  122. package/src/components/StrictECharts.js +0 -1
  123. package/src/components/TsingrocDatePicker.tsx +0 -103
  124. package/src/components/TsingrocTheme.tsx +0 -48
  125. package/src/components/UserButton.tsx +0 -165
  126. package/src/components/VerticalColorLegend.tsx +0 -73
  127. package/src/components/WeatherMap.tsx +0 -522
  128. package/src/deckgl/TiandituLayer.ts +0 -56
  129. package/src/deckgl/WeatherData.ts +0 -157
  130. package/src/deckgl/index.ts +0 -4
  131. package/src/echarts/coordinateSystems/grid.ts +0 -143
  132. package/src/echarts/coordinateSystems/polar.ts +0 -148
  133. package/src/echarts/gl.ts +0 -159
  134. package/src/echarts/index.ts +0 -129
  135. package/src/echarts/legend.ts +0 -36
  136. package/src/echarts/radar.ts +0 -46
  137. package/src/echarts/series/barSeries.ts +0 -37
  138. package/src/echarts/series/boxplotSeries.ts +0 -62
  139. package/src/echarts/series/intervalSeries.ts +0 -70
  140. package/src/echarts/series/lineSeries.ts +0 -78
  141. package/src/echarts/series/maxBarSeries.ts +0 -55
  142. package/src/echarts/series/pieSeries.ts +0 -76
  143. package/src/echarts/series/windLineSeries.ts +0 -113
  144. package/src/index.ts +0 -120
  145. package/src/types.d.ts +0 -5
  146. package/src/utils/debug.ts +0 -39
  147. package/src/utils/mock.ts +0 -69
  148. package/src/utils/startOfQuarter.ts +0 -6
  149. /package/{src/echarts/coordinateSystems/index.ts → dist/echarts/coordinateSystems/index.d.ts} +0 -0
  150. /package/{src/echarts/series/index.ts → dist/echarts/series/index.d.ts} +0 -0
@@ -1,73 +0,0 @@
1
- import { theme } from "antd";
2
- import type { HTMLAttributes } from "react";
3
-
4
- export interface VerticalColorLegendProps
5
- extends HTMLAttributes<HTMLDivElement> {
6
- title?: string;
7
- palette: [number, [number, number, number]][];
8
- }
9
-
10
- function VerticalColorLegend(props: VerticalColorLegendProps) {
11
- const { title, palette, ...rest } = props;
12
- const { token } = theme.useToken();
13
- const max = (palette.at(-1) as [number, [number, number, number]])[0];
14
- const min = palette[0][0];
15
- const range = max - min;
16
- return (
17
- <div
18
- {...rest}
19
- style={{
20
- display: "flex",
21
- flexDirection: "column",
22
- userSelect: "none",
23
- fontSize: token.fontSizeSM,
24
- color: token.colorText,
25
- textShadow:
26
- "-1px -1px white, 0px -1px white, 1px -1px white, 1px 0px white, " +
27
- "1px 1px white, 0px 1px white, -1px 1px white, -1px 0px white",
28
- ...rest.style,
29
- }}
30
- >
31
- <div style={{ fontWeight: "bold" }}>{title}</div>
32
- <div
33
- style={{
34
- display: "flex",
35
- flexBasis: "100%",
36
- alignItems: "stretch",
37
- gap: token.paddingXXS,
38
- paddingBlock: "0.5em",
39
- }}
40
- >
41
- <div
42
- style={{
43
- width: 24,
44
- background: `linear-gradient(
45
- to top,
46
- ${palette
47
- .map(
48
- ([value, color]) =>
49
- `rgb(${color.join(", ")}) ${((value - min) / range) * 100}%`,
50
- )
51
- .join(", ")}
52
- )`,
53
- }}
54
- />
55
- <div style={{ lineHeight: 0, verticalAlign: "middle" }}>
56
- {palette.map(([value], i) => (
57
- <div
58
- key={i}
59
- style={{
60
- position: "relative",
61
- top: `${((max - value) / range) * 100}%`,
62
- }}
63
- >
64
- {value.toFixed(1)}
65
- </div>
66
- ))}
67
- </div>
68
- </div>
69
- </div>
70
- );
71
- }
72
-
73
- export default VerticalColorLegend;
@@ -1,522 +0,0 @@
1
- import { Button, Flex, Slider, Spin, theme, type ButtonProps } from "antd";
2
- import { createStyles } from "antd-style";
3
- import dayjs from "dayjs";
4
- import DeckGL from "deck.gl";
5
- import {
6
- useMemo,
7
- useState,
8
- type CSSProperties,
9
- type HTMLAttributes,
10
- type ReactNode,
11
- } from "react";
12
- import { MdDewPoint, MdThermostat } from "react-icons/md";
13
- import {
14
- WiBarometer,
15
- WiCloudy,
16
- WiHumidity,
17
- WiRain,
18
- WiStrongWind,
19
- } from "react-icons/wi";
20
- import * as wl from "weatherlayers-gl";
21
-
22
- import { TiandituLayer } from "../deckgl";
23
- import {
24
- extractMagnitudeData,
25
- extractScalarData,
26
- extractVectorData,
27
- getBounds,
28
- type WeatherData,
29
- } from "../deckgl/WeatherData";
30
- import TsingrocTheme from "./TsingrocTheme";
31
- import VerticalColorLegend from "./VerticalColorLegend";
32
-
33
- export { type WeatherData };
34
-
35
- export interface WeatherMapProps extends HTMLAttributes<HTMLDivElement> {
36
- /** 天地图平台的 token。*/
37
- tiandituTk: string;
38
- /** 要显示的天气数据。如果为 `undefined`,则会显示加载界面。*/
39
- data: WeatherData | undefined;
40
- }
41
-
42
- /**
43
- * 一张显示各类天气信息的地图。
44
- *
45
- * 多余的属性会被传递给组件最外层的 [`div` 元素][1]。
46
- *
47
- * [1]: https://developer.mozilla.org/en-US/docs/Web/HTML/Element/div
48
- */
49
- function WeatherMap(props: WeatherMapProps) {
50
- const { tiandituTk, data, ...rest } = props;
51
- const { token } = theme.useToken();
52
- const boundingBox = data ? getBounds(data) : undefined;
53
- const [selectedScalar, setSelectedScalar] = useState(SCALAR_VARIABLES[0]);
54
- const hasWind = !!(
55
- data &&
56
- data.data_vars.wind_component_u_10m &&
57
- data.data_vars.wind_component_v_10m
58
- );
59
- const scalarFrames = useMemo(() => {
60
- if (!data) return undefined;
61
- if (
62
- selectedScalar.key === "wind_speed_10m" &&
63
- !data.data_vars.wind_speed_10m &&
64
- hasWind
65
- ) {
66
- return extractMagnitudeData(
67
- data,
68
- "wind_component_u_10m",
69
- "wind_component_v_10m",
70
- );
71
- }
72
- return extractScalarData(data, selectedScalar.key);
73
- }, [data, selectedScalar, hasWind]);
74
- const [showWind, setShowWind] = useState(true);
75
- const windFrames = useMemo(() => {
76
- if (!(hasWind && showWind)) return undefined;
77
- return extractVectorData(
78
- data,
79
- "wind_component_u_10m",
80
- "wind_component_v_10m",
81
- );
82
- }, [data, hasWind, showWind]);
83
- const [timeIdx, setTimeIdx] = useState(0);
84
- const scalarFrame = scalarFrames?.[timeIdx];
85
- const windFrame = windFrames?.[timeIdx];
86
- const palette = useMemo(() => {
87
- if (!scalarFrame) return undefined;
88
- return adaptiveColorCoding(
89
- scalarFrame.min,
90
- scalarFrame.max,
91
- selectedScalar.adaptivePalette,
92
- );
93
- }, [selectedScalar, scalarFrame]);
94
- return (
95
- <TsingrocTheme>
96
- <div {...rest} style={{ position: "relative", ...rest.style }}>
97
- <DeckGL
98
- initialViewState={{ longitude: 0, latitude: 0, zoom: 0, maxPitch: 0 }}
99
- controller={{ dragRotate: false }}
100
- layers={[
101
- new TiandituLayer({ id: "base", tiandituTk }),
102
- new TiandituLayer({ id: "ann", tiandituTk, layer: "annotation" }),
103
- scalarFrame
104
- ? new wl.RasterLayer({
105
- id: "scalar",
106
- opacity: 0.5,
107
- bounds: boundingBox,
108
- image: scalarFrame.image,
109
- palette,
110
- })
111
- : null,
112
- windFrame
113
- ? new wl.ParticleLayer({
114
- id: "wind",
115
- opacity: 0.5,
116
- bounds: boundingBox,
117
- image: windFrame,
118
- numParticles: 1000,
119
- maxAge: 30,
120
- speedFactor: 10,
121
- width: window.devicePixelRatio,
122
- })
123
- : null,
124
- ]}
125
- />
126
- {data && (
127
- <div
128
- style={{
129
- position: "absolute",
130
- inset: "auto 0 0 0",
131
- padding: "4px 8px 0 8px",
132
- background: "linear-gradient(to bottom, transparent, #0007)",
133
- }}
134
- >
135
- <Slider
136
- value={timeIdx}
137
- min={0}
138
- max={data.dims.time - 1}
139
- step={1}
140
- onChange={setTimeIdx}
141
- tooltip={{
142
- formatter: (value) =>
143
- dayjs
144
- .unix(data.coords.time[value as number])
145
- .format("YYYY-MM-DD HH:mm:ss"),
146
- }}
147
- />
148
- </div>
149
- )}
150
- <Flex
151
- vertical
152
- style={{
153
- position: "absolute",
154
- inset: "8px 8px auto auto",
155
- borderRadius: token.borderRadius,
156
- padding: token.paddingXXS,
157
- background: token.colorBgMask,
158
- }}
159
- >
160
- {SCALAR_VARIABLES.filter(
161
- (scalar) =>
162
- !data ||
163
- scalar.key in data.data_vars ||
164
- (scalar.key === "wind_speed_10m" && hasWind),
165
- ).map((scalar) => (
166
- <ToolbarButton
167
- key={scalar.key}
168
- icon={scalar.icon}
169
- selected={selectedScalar.key === scalar.key}
170
- onClick={() => setSelectedScalar(scalar)}
171
- >
172
- {scalar.name}
173
- </ToolbarButton>
174
- ))}
175
- <hr style={{ margin: token.marginXXS }} />
176
- {(!data || hasWind) && (
177
- <ToolbarButton
178
- icon={<WiStrongWind />}
179
- selected={showWind}
180
- onClick={() => setShowWind((b) => !b)}
181
- >
182
- 风力轨迹
183
- </ToolbarButton>
184
- )}
185
- </Flex>
186
- {palette && (
187
- <VerticalColorLegend
188
- title={selectedScalar.name + "(" + selectedScalar.unit + ")"}
189
- palette={palette}
190
- style={{
191
- position: "absolute",
192
- inset: "auto auto 32px 13px",
193
- height: 135,
194
- pointerEvents: "none",
195
- }}
196
- />
197
- )}
198
- {!data && (
199
- <Spin
200
- size="large"
201
- style={{
202
- position: "absolute",
203
- inset: 0,
204
- background: token.colorFillSecondary,
205
- display: "flex",
206
- alignItems: "center",
207
- justifyContent: "center",
208
- }}
209
- />
210
- )}
211
- </div>
212
- </TsingrocTheme>
213
- );
214
- }
215
-
216
- export default WeatherMap;
217
-
218
- function ToolbarButton(props: ButtonProps & { selected: boolean }) {
219
- const { selected, className, children, ...rest } = props;
220
- const { cx, styles } = useStyles();
221
- return (
222
- <Button
223
- color="default"
224
- variant="text"
225
- className={cx(
226
- styles.toolbarButton,
227
- { [styles.toolbarButtonSelected]: selected },
228
- className,
229
- )}
230
- {...rest}
231
- >
232
- <span className={styles.toolbarButtonText}>{children}</span>
233
- </Button>
234
- );
235
- }
236
-
237
- const useStyles = createStyles(({ token, css, prefixCls }) => {
238
- return {
239
- toolbarButton: css`
240
- padding: 0 ${token.paddingXS}px;
241
- background: transparent;
242
-
243
- &:hover:hover:hover {
244
- background: ${token.colorFillSecondary};
245
- }
246
-
247
- &:active:active:active {
248
- background: ${token.colorFill};
249
- }
250
-
251
- &,
252
- &:hover:hover:hover {
253
- color: ${token.colorWhite};
254
- }
255
-
256
- > .${prefixCls}-btn-icon {
257
- font-size: 18px;
258
- }
259
- `,
260
- toolbarButtonSelected: css`
261
- &,
262
- &:hover:hover:hover {
263
- background: ${token.colorBgContainer};
264
- color: ${token.colorText};
265
- }
266
-
267
- &::before {
268
- content: "";
269
- position: absolute;
270
- inset: -1px;
271
- border: inherit;
272
- border-radius: inherit;
273
- transition: inherit;
274
- }
275
-
276
- &:hover:hover:hover::before {
277
- background: ${token.colorFillSecondary};
278
- }
279
-
280
- &:active:active:active::before {
281
- background: ${token.colorFill};
282
- }
283
- `,
284
- toolbarButtonText: css`
285
- flex-basis: 100%;
286
- text-align: left;
287
- `,
288
- };
289
- });
290
-
291
- interface ScalarInfo {
292
- key: keyof WeatherData["data_vars"];
293
- name: string;
294
- unit: string;
295
- icon: ReactNode;
296
- adaptivePalette: AdaptivePalette;
297
- fixedPalette?: [number, Vec3][];
298
- }
299
-
300
- const iconSizeFix = (ratio: number): CSSProperties => ({
301
- fontSize: `${ratio}em`,
302
- margin: `${-(1 - 1 / ratio) / 3}em ${-(1 - 1 / ratio) / 2}em`,
303
- });
304
-
305
- const TEMPERATURE_ADAPTIVE_PALETTE: AdaptivePalette = {
306
- min: [128, 65, 157],
307
- zero: [239, 255, 45],
308
- max: [254, 19, 12],
309
- };
310
-
311
- const TEMPERATURE_FIXED_PALETTE: [number, Vec3][] = [
312
- [-18, [78, 138, 221]],
313
- [-17, [87, 144, 222]],
314
- [-16, [97, 150, 224]],
315
- [-15, [106, 156, 225]],
316
- [-14, [116, 163, 226]],
317
- [-13, [125, 169, 227]],
318
- [-12, [135, 175, 229]],
319
- [-11, [145, 181, 230]],
320
- [-10, [155, 188, 232]],
321
- [-9, [154, 192, 226]],
322
- [-8, [154, 196, 220]],
323
- [-7, [154, 200, 214]],
324
- [-6, [154, 205, 208]],
325
- [-5, [153, 209, 202]],
326
- [-4, [152, 214, 196]],
327
- [-3, [151, 223, 184]],
328
- [-2, [151, 232, 173]],
329
- [-1, [183, 227, 149]],
330
- [0, [215, 222, 125]],
331
- [1, [224, 220, 118]],
332
- [2, [234, 219, 112]],
333
- [3, [239, 218, 105]],
334
- [4, [244, 217, 99]],
335
- [5, [247, 210, 89]],
336
- [6, [250, 204, 79]],
337
- [7, [248, 192, 62]],
338
- [8, [247, 180, 45]],
339
- [9, [244, 167, 22]],
340
- [10, [242, 155, 0]],
341
- [11, [241, 151, 1]],
342
- [12, [241, 147, 3]],
343
- [13, [240, 140, 6]],
344
- [14, [240, 133, 10]],
345
- [15, [239, 125, 13]],
346
- [16, [239, 117, 17]],
347
- [17, [238, 109, 20]],
348
- [18, [238, 101, 24]],
349
- [19, [238, 94, 27]],
350
- [20, [238, 88, 31]],
351
- [21, [234, 81, 28]],
352
- [22, [231, 75, 26]],
353
- [23, [227, 69, 24]],
354
- [24, [224, 63, 22]],
355
- [25, [220, 57, 20]],
356
- [26, [217, 51, 18]],
357
- [27, [212, 43, 16]],
358
- [28, [208, 36, 14]],
359
- [29, [201, 18, 8]],
360
- [30, [194, 0, 3]],
361
- [31, [187, 0, 6]],
362
- [32, [181, 1, 9]],
363
- [33, [175, 1, 12]],
364
- [34, [169, 2, 16]],
365
- [35, [153, 3, 20]],
366
- [36, [138, 5, 25]],
367
- [37, [124, 2, 23]],
368
- [38, [111, 0, 21]],
369
- [39, [95, 0, 18]],
370
- [40, [80, 0, 15]],
371
- [41, [70, 0, 15]],
372
- [42, [60, 0, 15]],
373
- [43, [50, 0, 15]],
374
- [44, [40, 0, 15]],
375
- [45, [30, 0, 15]],
376
- [46, [20, 0, 15]],
377
- ];
378
-
379
- const SCALAR_VARIABLES: ScalarInfo[] = [
380
- {
381
- key: "temperature_2m",
382
- name: "温度",
383
- unit: "℃",
384
- icon: <MdThermostat />,
385
- adaptivePalette: TEMPERATURE_ADAPTIVE_PALETTE,
386
- fixedPalette: TEMPERATURE_FIXED_PALETTE,
387
- },
388
- {
389
- key: "surface_pressure",
390
- name: "气压",
391
- unit: "hPa",
392
- icon: <WiBarometer style={iconSizeFix(1.4)} />,
393
- adaptivePalette: {
394
- min: [80, 202, 75],
395
- max: [254, 19, 12],
396
- },
397
- },
398
- {
399
- key: "cloud_cover",
400
- name: "云量",
401
- unit: "%",
402
- icon: <WiCloudy style={iconSizeFix(1.2)} />,
403
- adaptivePalette: {
404
- min: [239, 255, 45],
405
- max: [255, 255, 255],
406
- },
407
- },
408
- {
409
- key: "dew_point_2m",
410
- name: "露点",
411
- unit: "℃",
412
- icon: <MdDewPoint />,
413
- adaptivePalette: TEMPERATURE_ADAPTIVE_PALETTE,
414
- fixedPalette: TEMPERATURE_FIXED_PALETTE,
415
- },
416
- {
417
- key: "relative_humidity_2m",
418
- name: "相对湿度",
419
- unit: "%",
420
- icon: <WiHumidity style={iconSizeFix(1.3)} />,
421
- adaptivePalette: {
422
- min: [128, 65, 157],
423
- zero: [239, 255, 45],
424
- zeroPoint: 0.5,
425
- max: [254, 19, 12],
426
- },
427
- },
428
- {
429
- key: "wind_speed_10m",
430
- name: "风速",
431
- unit: "m/s",
432
- icon: <WiStrongWind />,
433
- adaptivePalette: {
434
- min: [239, 255, 45],
435
- max: [128, 65, 157],
436
- },
437
- },
438
- {
439
- key: "rain",
440
- name: "降雨量",
441
- unit: "mm",
442
- icon: <WiRain style={iconSizeFix(1.1)} />,
443
- adaptivePalette: {
444
- min: [80, 202, 75],
445
- max: [254, 19, 12],
446
- },
447
- },
448
- ];
449
-
450
- function lerpVec<T extends number[]>(min: T, max: T, pos: number) {
451
- return min.map((min, i) => min + pos * (max[i] - min)) as T;
452
- }
453
-
454
- type Vec3 = [number, number, number];
455
-
456
- interface AdaptivePalette {
457
- min: Vec3;
458
- zero?: Vec3;
459
- zeroPoint?: number;
460
- max: Vec3;
461
- }
462
-
463
- // 参考 https://www.cma.gov.cn/zfxxgk/gknr/flfgbz/bz/202209/P020220921555079517928.pdf
464
- function adaptiveColorCoding(
465
- min: number,
466
- max: number,
467
- base: AdaptivePalette,
468
- ): [number, Vec3][] {
469
- if (base.zero) {
470
- const palette: [number, Vec3][] = [];
471
- const zeroPoint = base.zeroPoint ?? 0;
472
- if (min < zeroPoint) {
473
- palette.push([
474
- min,
475
- lerpVec(
476
- base.zero,
477
- base.min,
478
- Math.min(1, Math.abs((min - zeroPoint) / (max - zeroPoint))),
479
- ),
480
- ]);
481
- } else {
482
- palette.push([min, base.zero]);
483
- }
484
- if (min < zeroPoint && max > zeroPoint) {
485
- palette.push([zeroPoint, base.zero]);
486
- }
487
- if (max > zeroPoint) {
488
- palette.push([
489
- max,
490
- lerpVec(
491
- base.zero,
492
- base.max,
493
- Math.min(1, Math.abs((max - zeroPoint) / (min - zeroPoint))),
494
- ),
495
- ]);
496
- } else {
497
- palette.push([max, base.zero]);
498
- }
499
- return palette;
500
- } else {
501
- return [
502
- [min, base.min],
503
- [max, base.max],
504
- ];
505
- }
506
- }
507
-
508
- // 参考 https://dbba.sacinfo.org.cn/attachment/downloadStdFile?pk=dda6960be9435ed7ab01e336e197cd67a072a28725f03685bfbdaf19cbfeb267
509
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
510
- function fixedColorCoding<T>(min: number, max: number, palette: [number, T][]) {
511
- let minIdx = palette.findIndex(([value]) => value > min) - 1;
512
- if (minIdx < -1) {
513
- minIdx = palette.length - 1;
514
- } else if (minIdx === -1) {
515
- minIdx = 0;
516
- }
517
- let maxIdx = palette.findIndex(([value]) => value >= max);
518
- if (maxIdx < 0) {
519
- maxIdx = 0;
520
- }
521
- return palette.slice(minIdx, maxIdx + 1);
522
- }
@@ -1,56 +0,0 @@
1
- import { BitmapLayer, CompositeLayer } from "deck.gl";
2
- import type { DefaultProps } from "@deck.gl/core";
3
- import { TileLayer, type TileLayerProps } from "@deck.gl/geo-layers";
4
-
5
- export interface TiandituLayerProps {
6
- tiandituTk: string;
7
- type: "vec" | "img" | "ter";
8
- layer: "base" | "annotation";
9
- }
10
-
11
- export default class TiandituLayer extends CompositeLayer<TiandituLayerProps> {
12
- static readonly layerName = "TiandituLayer";
13
- static readonly defaultProps: DefaultProps<TiandituLayerProps> = {
14
- type: { type: "object", value: "vec" },
15
- layer: { type: "object", value: "base" },
16
- };
17
- renderLayers(): TileLayer {
18
- const { tiandituTk, type, layer } = this.props;
19
- const actualType = layer === "base" ? type : "c" + type[0] + "a";
20
- return new TileLayer(
21
- this.getSubLayerProps({
22
- id: actualType,
23
- data: makeUrlTemplate(tiandituTk, actualType),
24
- maxZoom: 18,
25
- zoomOffset: 1,
26
- renderSubLayers,
27
- }) as TileLayerProps,
28
- );
29
- }
30
- }
31
-
32
- const makeUrlTemplate = (tiandituTk: string, type: string) =>
33
- Array.from(
34
- { length: 8 },
35
- (_, i) =>
36
- `https://t${i}.tianditu.gov.cn/${type}_w/wmts` +
37
- `?SERVICE=WMTS&REQUEST=GetTile&VERSION=1.0.0` +
38
- `&LAYER=${type}&STYLE=default&TILEMATRIXSET=w&FORMAT=tiles` +
39
- `&TILEMATRIX={z}&TILEROW={y}&TILECOL={x}` +
40
- `&tk=${tiandituTk}`,
41
- );
42
-
43
- const renderSubLayers: TileLayerProps["renderSubLayers"] = (props) => {
44
- const { boundingBox } = props.tile;
45
- return new BitmapLayer({
46
- ...props,
47
- data: undefined,
48
- image: props.data as string | null,
49
- bounds: [
50
- boundingBox[0][0],
51
- boundingBox[0][1],
52
- boundingBox[1][0],
53
- boundingBox[1][1],
54
- ],
55
- });
56
- };