@oanda/labs-crowd-view-widget 1.0.54 → 1.0.55

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 (168) hide show
  1. package/CHANGELOG.md +224 -0
  2. package/dist/main/CrowdViewWidget/components/Chart/Chart.js +37 -56
  3. package/dist/main/CrowdViewWidget/components/Chart/Chart.js.map +1 -1
  4. package/dist/main/CrowdViewWidget/components/Chart/ChartWithData.js +20 -7
  5. package/dist/main/CrowdViewWidget/components/Chart/ChartWithData.js.map +1 -1
  6. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.js +15 -9
  7. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.js.map +1 -1
  8. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getGridConfig.js +6 -6
  9. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getGridConfig.js.map +1 -1
  10. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getGridLines.js +41 -13
  11. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getGridLines.js.map +1 -1
  12. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.js +159 -0
  13. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.js.map +1 -0
  14. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.js +7 -14
  15. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.js.map +1 -1
  16. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.js +20 -2
  17. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.js.map +1 -1
  18. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.js +13 -5
  19. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.js.map +1 -1
  20. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.js +10 -3
  21. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.js.map +1 -1
  22. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getXAxisConfig.js +20 -5
  23. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getXAxisConfig.js.map +1 -1
  24. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.js +19 -28
  25. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.js.map +1 -1
  26. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/index.js +11 -0
  27. package/dist/main/CrowdViewWidget/components/Chart/chartOptions/index.js.map +1 -1
  28. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.js +18 -0
  29. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.js.map +1 -0
  30. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/getLabelData.js +1 -20
  31. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/getLabelData.js.map +1 -1
  32. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.js +21 -9
  33. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.js.map +1 -1
  34. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.js +59 -0
  35. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.js.map +1 -0
  36. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.js +34 -0
  37. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.js.map +1 -0
  38. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/index.js +33 -0
  39. package/dist/main/CrowdViewWidget/components/Chart/chartUtils/index.js.map +1 -1
  40. package/dist/main/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.js +19 -0
  41. package/dist/main/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.js.map +1 -0
  42. package/dist/main/CrowdViewWidget/components/Chart/dataUtils/index.js +11 -0
  43. package/dist/main/CrowdViewWidget/components/Chart/dataUtils/index.js.map +1 -1
  44. package/dist/main/CrowdViewWidget/components/Chart/getOption.js +33 -21
  45. package/dist/main/CrowdViewWidget/components/Chart/getOption.js.map +1 -1
  46. package/dist/main/CrowdViewWidget/components/Chart/types.js.map +1 -1
  47. package/dist/main/CrowdViewWidget/components/Chart/useCrowdViewData.js +7 -4
  48. package/dist/main/CrowdViewWidget/components/Chart/useCrowdViewData.js.map +1 -1
  49. package/dist/main/CrowdViewWidget/components/Legend/Legend.js +1 -1
  50. package/dist/main/CrowdViewWidget/components/Legend/Legend.js.map +1 -1
  51. package/dist/main/CrowdViewWidget/components/Legend/LegendBar.js +11 -1
  52. package/dist/main/CrowdViewWidget/components/Legend/LegendBar.js.map +1 -1
  53. package/dist/main/CrowdViewWidget/constants.js +13 -5
  54. package/dist/main/CrowdViewWidget/constants.js.map +1 -1
  55. package/dist/main/CrowdViewWidget/selectConfig.js +0 -6
  56. package/dist/main/CrowdViewWidget/selectConfig.js.map +1 -1
  57. package/dist/main/translations/sources/en.json +2 -1
  58. package/dist/module/CrowdViewWidget/components/Chart/Chart.js +38 -56
  59. package/dist/module/CrowdViewWidget/components/Chart/Chart.js.map +1 -1
  60. package/dist/module/CrowdViewWidget/components/Chart/ChartWithData.js +19 -6
  61. package/dist/module/CrowdViewWidget/components/Chart/ChartWithData.js.map +1 -1
  62. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.js +15 -9
  63. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.js.map +1 -1
  64. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getGridConfig.js +6 -6
  65. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getGridConfig.js.map +1 -1
  66. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getGridLines.js +41 -13
  67. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getGridLines.js.map +1 -1
  68. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.js +151 -0
  69. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.js.map +1 -0
  70. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.js +7 -14
  71. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.js.map +1 -1
  72. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.js +20 -2
  73. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.js.map +1 -1
  74. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.js +13 -5
  75. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.js.map +1 -1
  76. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.js +10 -3
  77. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.js.map +1 -1
  78. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getXAxisConfig.js +21 -6
  79. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getXAxisConfig.js.map +1 -1
  80. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.js +19 -28
  81. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.js.map +1 -1
  82. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/index.js +1 -0
  83. package/dist/module/CrowdViewWidget/components/Chart/chartOptions/index.js.map +1 -1
  84. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.js +11 -0
  85. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.js.map +1 -0
  86. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/getLabelData.js +1 -20
  87. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/getLabelData.js.map +1 -1
  88. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.js +21 -9
  89. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.js.map +1 -1
  90. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.js +52 -0
  91. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.js.map +1 -0
  92. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.js +27 -0
  93. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.js.map +1 -0
  94. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/index.js +3 -0
  95. package/dist/module/CrowdViewWidget/components/Chart/chartUtils/index.js.map +1 -1
  96. package/dist/module/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.js +12 -0
  97. package/dist/module/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.js.map +1 -0
  98. package/dist/module/CrowdViewWidget/components/Chart/dataUtils/index.js +1 -0
  99. package/dist/module/CrowdViewWidget/components/Chart/dataUtils/index.js.map +1 -1
  100. package/dist/module/CrowdViewWidget/components/Chart/getOption.js +34 -22
  101. package/dist/module/CrowdViewWidget/components/Chart/getOption.js.map +1 -1
  102. package/dist/module/CrowdViewWidget/components/Chart/types.js.map +1 -1
  103. package/dist/module/CrowdViewWidget/components/Chart/useCrowdViewData.js +8 -5
  104. package/dist/module/CrowdViewWidget/components/Chart/useCrowdViewData.js.map +1 -1
  105. package/dist/module/CrowdViewWidget/components/Legend/Legend.js +1 -1
  106. package/dist/module/CrowdViewWidget/components/Legend/Legend.js.map +1 -1
  107. package/dist/module/CrowdViewWidget/components/Legend/LegendBar.js +11 -1
  108. package/dist/module/CrowdViewWidget/components/Legend/LegendBar.js.map +1 -1
  109. package/dist/module/CrowdViewWidget/constants.js +13 -5
  110. package/dist/module/CrowdViewWidget/constants.js.map +1 -1
  111. package/dist/module/CrowdViewWidget/selectConfig.js +0 -6
  112. package/dist/module/CrowdViewWidget/selectConfig.js.map +1 -1
  113. package/dist/module/translations/sources/en.json +2 -1
  114. package/dist/types/CrowdViewWidget/components/Chart/Chart.d.ts +1 -1
  115. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.d.ts +5 -1
  116. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getGridLines.d.ts +2 -1
  117. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.d.ts +8 -0
  118. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.d.ts +2 -3
  119. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.d.ts +2 -1
  120. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.d.ts +2 -1
  121. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.d.ts +3 -1
  122. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.d.ts +1 -3
  123. package/dist/types/CrowdViewWidget/components/Chart/chartOptions/index.d.ts +1 -0
  124. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.d.ts +1 -0
  125. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/getLabelData.d.ts +1 -16
  126. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.d.ts +3 -1
  127. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.d.ts +4 -0
  128. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.d.ts +3 -0
  129. package/dist/types/CrowdViewWidget/components/Chart/chartUtils/index.d.ts +3 -0
  130. package/dist/types/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.d.ts +2 -0
  131. package/dist/types/CrowdViewWidget/components/Chart/dataUtils/index.d.ts +1 -0
  132. package/dist/types/CrowdViewWidget/components/Chart/types.d.ts +5 -0
  133. package/dist/types/CrowdViewWidget/constants.d.ts +12 -4
  134. package/package.json +3 -3
  135. package/src/CrowdViewWidget/components/Chart/Chart.tsx +70 -79
  136. package/src/CrowdViewWidget/components/Chart/ChartWithData.tsx +31 -13
  137. package/src/CrowdViewWidget/components/Chart/chartOptions/getDataZoomConfig.ts +11 -2
  138. package/src/CrowdViewWidget/components/Chart/chartOptions/getGridConfig.ts +6 -6
  139. package/src/CrowdViewWidget/components/Chart/chartOptions/getGridLines.ts +48 -6
  140. package/src/CrowdViewWidget/components/Chart/chartOptions/getLabelsConfig.ts +191 -0
  141. package/src/CrowdViewWidget/components/Chart/chartOptions/getSeriesCandlestickConfig.ts +7 -15
  142. package/src/CrowdViewWidget/components/Chart/chartOptions/getSeriesHeatmapConfig.ts +22 -1
  143. package/src/CrowdViewWidget/components/Chart/chartOptions/getSeriesSentimentConfig.ts +13 -4
  144. package/src/CrowdViewWidget/components/Chart/chartOptions/getTooltipConfig.ts +12 -1
  145. package/src/CrowdViewWidget/components/Chart/chartOptions/getXAxisConfig.ts +55 -30
  146. package/src/CrowdViewWidget/components/Chart/chartOptions/getYAxisConfig.ts +13 -30
  147. package/src/CrowdViewWidget/components/Chart/chartOptions/index.ts +1 -0
  148. package/src/CrowdViewWidget/components/Chart/chartUtils/formatXAxisAdditionalLabel.ts +13 -0
  149. package/src/CrowdViewWidget/components/Chart/chartUtils/getLabelData.ts +11 -35
  150. package/src/CrowdViewWidget/components/Chart/chartUtils/getTooltipFormatter.ts +40 -11
  151. package/src/CrowdViewWidget/components/Chart/chartUtils/handleLabelUpdate.ts +75 -0
  152. package/src/CrowdViewWidget/components/Chart/chartUtils/handleTooltipUpdate.ts +37 -0
  153. package/src/CrowdViewWidget/components/Chart/chartUtils/index.ts +3 -0
  154. package/src/CrowdViewWidget/components/Chart/dataUtils/getMultiplayerForTimeSpan.ts +13 -0
  155. package/src/CrowdViewWidget/components/Chart/dataUtils/index.ts +1 -0
  156. package/src/CrowdViewWidget/components/Chart/getOption.ts +41 -17
  157. package/src/CrowdViewWidget/components/Chart/types.ts +5 -0
  158. package/src/CrowdViewWidget/components/Chart/useCrowdViewData.ts +12 -5
  159. package/src/CrowdViewWidget/components/Legend/Legend.tsx +1 -1
  160. package/src/CrowdViewWidget/components/Legend/LegendBar.tsx +17 -1
  161. package/src/CrowdViewWidget/constants.ts +12 -4
  162. package/src/CrowdViewWidget/selectConfig.ts +0 -8
  163. package/src/translations/sources/en.json +2 -1
  164. package/test/components/Chart/utils/chartUtils.test.ts +13 -2
  165. package/test/components/Chart/utils/handleLabelUpdate.test.ts +419 -0
  166. package/test/components/Chart/utils/handleTooltipUpdate.test.ts +140 -0
  167. package/test/components/Legend.test.tsx +3 -3
  168. package/test/components/LegendBar.test.tsx +22 -20
@@ -5,7 +5,8 @@ import {
5
5
  SpinnerSize,
6
6
  useLayoutProvider,
7
7
  } from '@oanda/labs-widget-common';
8
- import React from 'react';
8
+ import React, { useEffect, useState } from 'react';
9
+ import { useDebounceCallback } from 'usehooks-ts';
9
10
 
10
11
  import { Chart } from './Chart';
11
12
  import type { ChartWithDataProps } from './types';
@@ -18,14 +19,30 @@ const ChartWithData = ({
18
19
  granularity,
19
20
  }: ChartWithDataProps) => {
20
21
  const { size } = useLayoutProvider();
22
+ const [debouncedLoading, setDebouncedLoading] = useState(true);
21
23
  const isDesktop = size === Size.DESKTOP;
22
24
 
23
- const { mainData, additionalData, loading, error } = useCrowdViewData({
24
- instrument,
25
- bookType,
26
- division,
27
- granularity,
28
- });
25
+ const { mainData, additionalData, loading, priceCandlesLoading, error } =
26
+ useCrowdViewData({
27
+ instrument,
28
+ bookType,
29
+ division,
30
+ granularity,
31
+ });
32
+
33
+ const hideLoading = useDebounceCallback(
34
+ () => setDebouncedLoading(false),
35
+ 500
36
+ );
37
+
38
+ useEffect(() => {
39
+ if (loading === false) {
40
+ hideLoading();
41
+ }
42
+ if (loading === true) {
43
+ setDebouncedLoading(true);
44
+ }
45
+ }, [loading, hideLoading]);
29
46
 
30
47
  return (
31
48
  <>
@@ -35,20 +52,21 @@ const ChartWithData = ({
35
52
  <ChartError />
36
53
  </div>
37
54
  )}
38
- {loading && (
39
- <div className="lw-absolute lw-left-0 lw-top-0 lw-flex lw-h-full lw-w-full lw-items-center lw-justify-center lw-border lw-border-solid lw-border-border-primary">
40
- <Spinner size={SpinnerSize.lg} />
41
- </div>
42
- )}
43
- {!loading && !error && !!mainData && !!additionalData && (
55
+ {!priceCandlesLoading && !error && !!mainData && !!additionalData && (
44
56
  <div className="lw-absolute lw-left-0 lw-top-0 lw-flex lw-h-full lw-w-full">
45
57
  <Chart
46
58
  additionalData={additionalData}
47
59
  isDesktop={isDesktop}
60
+ isLoading={debouncedLoading}
48
61
  mainData={mainData}
49
62
  />
50
63
  </div>
51
64
  )}
65
+ {loading && (
66
+ <div className="lw-absolute lw-left-0 lw-top-0 lw-flex lw-h-full lw-w-full lw-items-center lw-justify-center lw-border lw-border-solid lw-border-border-primary lw-bg-bg-transparent-50">
67
+ <Spinner size={SpinnerSize.lg} />
68
+ </div>
69
+ )}
52
70
  </div>
53
71
  </>
54
72
  );
@@ -2,12 +2,21 @@ import type { DataZoomComponentOption } from 'echarts';
2
2
 
3
3
  import { CHART_CONFIG } from '../../../constants';
4
4
 
5
- export const getDataZoomConfig = (): DataZoomComponentOption => ({
5
+ interface GetDataZoomConfigParams {
6
+ isDesktop: boolean;
7
+ }
8
+
9
+ export const getDataZoomConfig = ({
10
+ isDesktop,
11
+ }: GetDataZoomConfigParams): DataZoomComponentOption => ({
6
12
  type: 'inside',
7
13
  id: 'main',
8
14
  xAxisIndex: [0, 1],
9
- start: CHART_CONFIG.INITIAL_START_ZOOM,
15
+ start: isDesktop
16
+ ? CHART_CONFIG.INITIAL_START_ZOOM_DESKTOP
17
+ : CHART_CONFIG.INITIAL_START_ZOOM_MOBILE,
10
18
  end: CHART_CONFIG.INITIAL_END_ZOOM,
11
19
  filterMode: 'filter',
12
20
  minSpan: 10,
21
+ preventDefaultMouseMove: true,
13
22
  });
@@ -12,18 +12,18 @@ export const getGridConfig = ({
12
12
  {
13
13
  id: 'main-grid',
14
14
  name: 'main-grid',
15
- left: `${CHART_CONFIG.Y_SENTIMENT_LABEL_SIZE}px`,
15
+ left: `${isDesktop ? CHART_CONFIG.Y_SENTIMENT_LABEL_DESKTOP_SIZE : CHART_CONFIG.Y_SENTIMENT_LABEL_MOBILE_SIZE}px`,
16
16
  right: `${isDesktop ? CHART_CONFIG.Y_LABEL_SIZE_DESKTOP : CHART_CONFIG.Y_LABEL_SIZE_MOBILE}px`,
17
- top: '0px',
17
+ top: `${isDesktop ? CHART_CONFIG.TOP_MARGIN_DESKTOP : CHART_CONFIG.TOP_MARGIN_MOBILE}px`,
18
18
  bottom: `${CHART_CONFIG.X_LABEL_SIZE}px`,
19
- height: `${CHART_CONFIG.MAIN_HEIGHT}px`,
19
+ height: `${isDesktop ? CHART_CONFIG.MAIN_HEIGHT - CHART_CONFIG.TOP_MARGIN_DESKTOP : CHART_CONFIG.MAIN_HEIGHT - CHART_CONFIG.TOP_MARGIN_MOBILE}px`,
20
20
  },
21
21
  {
22
22
  id: 'sentiment-grid',
23
23
  name: 'sentiment-grid',
24
- left: `${CHART_CONFIG.Y_SENTIMENT_LABEL_SIZE}px`,
24
+ left: `${isDesktop ? CHART_CONFIG.Y_SENTIMENT_LABEL_DESKTOP_SIZE : CHART_CONFIG.Y_SENTIMENT_LABEL_MOBILE_SIZE}px`,
25
25
  right: `${isDesktop ? CHART_CONFIG.Y_LABEL_SIZE_DESKTOP : CHART_CONFIG.Y_LABEL_SIZE_MOBILE}px`,
26
- top: `0px`,
27
- height: `${CHART_CONFIG.MAIN_HEIGHT}px`,
26
+ top: `${isDesktop ? CHART_CONFIG.TOP_MARGIN_DESKTOP : CHART_CONFIG.TOP_MARGIN_MOBILE}px`,
27
+ height: `${isDesktop ? CHART_CONFIG.MAIN_HEIGHT - CHART_CONFIG.TOP_MARGIN_DESKTOP : CHART_CONFIG.MAIN_HEIGHT - CHART_CONFIG.TOP_MARGIN_MOBILE}px`,
28
28
  },
29
29
  ];
@@ -5,13 +5,24 @@ import { CHART_CONFIG } from '../../../constants';
5
5
 
6
6
  interface GetGridLinesParams {
7
7
  isDark: boolean;
8
+ isDesktop: boolean;
8
9
  }
9
10
 
10
11
  export const getGridLines = ({
11
12
  isDark,
13
+ isDesktop,
12
14
  }: GetGridLinesParams): GraphicComponentOption[] => {
13
- const { WIDTH, MAIN_HEIGHT, X_LABEL_SIZE, Y_SENTIMENT_LABEL_SIZE } =
14
- CHART_CONFIG;
15
+ const { WIDTH, MAIN_HEIGHT, X_LABEL_SIZE } = CHART_CONFIG;
16
+ const ySentimentLabelSize = isDesktop
17
+ ? CHART_CONFIG.Y_SENTIMENT_LABEL_DESKTOP_SIZE
18
+ : CHART_CONFIG.Y_SENTIMENT_LABEL_MOBILE_SIZE;
19
+
20
+ const yLabelSize = isDesktop
21
+ ? CHART_CONFIG.Y_LABEL_SIZE_DESKTOP
22
+ : CHART_CONFIG.Y_LABEL_SIZE_MOBILE;
23
+
24
+ const topMargin = isDesktop ? 0 : CHART_CONFIG.TOP_MARGIN_MOBILE;
25
+
15
26
  return [
16
27
  // Top
17
28
  {
@@ -23,6 +34,7 @@ export const getGridLines = ({
23
34
  x2: WIDTH,
24
35
  y2: 0,
25
36
  },
37
+ z: 30,
26
38
  },
27
39
  // Right
28
40
  {
@@ -34,6 +46,7 @@ export const getGridLines = ({
34
46
  x2: 0,
35
47
  y2: MAIN_HEIGHT + X_LABEL_SIZE + 2,
36
48
  },
49
+ z: 30,
37
50
  },
38
51
  // Bottom
39
52
  {
@@ -45,6 +58,7 @@ export const getGridLines = ({
45
58
  x2: WIDTH,
46
59
  y2: 0,
47
60
  },
61
+ z: 30,
48
62
  },
49
63
  // Left
50
64
  {
@@ -56,29 +70,57 @@ export const getGridLines = ({
56
70
  x2: 0,
57
71
  y2: MAIN_HEIGHT + X_LABEL_SIZE + 2,
58
72
  },
73
+ z: 30,
74
+ },
75
+ // Y Label
76
+ {
77
+ ...getLineCommons(isDark),
78
+ right: yLabelSize - 3,
79
+ top: topMargin - 2,
80
+ shape: {
81
+ x1: 0,
82
+ y1: 0,
83
+ x2: 0,
84
+ y2: MAIN_HEIGHT - topMargin,
85
+ },
86
+ z: 30,
59
87
  },
60
88
  // Y Sentiment Label
61
89
  {
62
90
  ...getLineCommons(isDark),
63
- left: Y_SENTIMENT_LABEL_SIZE - 2,
64
- top: -2,
91
+ left: ySentimentLabelSize - 2,
92
+ top: topMargin - 2,
65
93
  shape: {
66
94
  x1: 0,
67
95
  y1: 0,
68
96
  x2: 0,
69
- y2: MAIN_HEIGHT,
97
+ y2: MAIN_HEIGHT - topMargin,
70
98
  },
99
+ z: 30,
71
100
  },
72
101
  // X Label
73
102
  {
74
103
  ...getLineCommons(isDark),
75
- top: MAIN_HEIGHT - 2,
104
+ bottom: X_LABEL_SIZE - 3,
105
+ shape: {
106
+ x1: 0,
107
+ y1: 0,
108
+ x2: WIDTH,
109
+ y2: 0,
110
+ },
111
+ z: 30,
112
+ },
113
+ // X Mobile Label
114
+ {
115
+ ...getLineCommons(isDark),
116
+ top: topMargin - 3,
76
117
  shape: {
77
118
  x1: 0,
78
119
  y1: 0,
79
120
  x2: WIDTH,
80
121
  y2: 0,
81
122
  },
123
+ z: 30,
82
124
  },
83
125
  ];
84
126
  };
@@ -0,0 +1,191 @@
1
+ import { colorPalette } from '@oanda/labs-widget-common';
2
+ import chroma from 'chroma-js';
3
+ import type { GraphicComponentOption } from 'echarts';
4
+
5
+ import { CHART_CONFIG } from '../../../constants';
6
+
7
+ interface getLabelsConfigParams {
8
+ isDark: boolean;
9
+ isDesktop: boolean;
10
+ labelCallback: (key: string, params?: Record<string, unknown>) => string;
11
+ }
12
+
13
+ export const getLabelsConfig = ({
14
+ isDark,
15
+ isDesktop,
16
+ labelCallback,
17
+ }: getLabelsConfigParams): GraphicComponentOption[] => {
18
+ const ySentimentLabelSize = isDesktop
19
+ ? CHART_CONFIG.Y_SENTIMENT_LABEL_DESKTOP_SIZE
20
+ : CHART_CONFIG.Y_SENTIMENT_LABEL_MOBILE_SIZE;
21
+
22
+ const yMainLabelSize = isDesktop
23
+ ? CHART_CONFIG.Y_LABEL_SIZE_DESKTOP
24
+ : CHART_CONFIG.Y_LABEL_SIZE_MOBILE;
25
+
26
+ const textColor = isDark ? colorPalette.white : colorPalette.black;
27
+ const labelBackgroundColor = isDark
28
+ ? colorPalette.darkGray
29
+ : colorPalette.white;
30
+ const backgroundColor = isDark ? colorPalette.black : colorPalette.white;
31
+ const shadowColor = chroma(colorPalette.black).alpha(0.1).hex();
32
+
33
+ // Estimate text width for centering rotated text
34
+ // Approximate: fontSize * characterCount * 0.65 (typical character width ratio)
35
+ const sentimentText = labelCallback('sentiment').toUpperCase();
36
+ const priceText = labelCallback('price').toUpperCase();
37
+ const sentimentEstimatedWidth = 10 * sentimentText.length * 0.65;
38
+ const priceEstimatedWidth = 10 * priceText.length * 0.65;
39
+ const sentimentVerticalOffset = sentimentEstimatedWidth / 2;
40
+ const priceVerticalOffset = priceEstimatedWidth / 2;
41
+
42
+ const topMargin = isDesktop
43
+ ? CHART_CONFIG.TOP_MARGIN_DESKTOP
44
+ : CHART_CONFIG.TOP_MARGIN_MOBILE;
45
+
46
+ return [
47
+ {
48
+ type: 'group',
49
+ left: `${ySentimentLabelSize + 5}px'`,
50
+ top: `${topMargin + 5}px`,
51
+ silent: true,
52
+ children: [
53
+ {
54
+ type: 'rect',
55
+ z: 100,
56
+ right: 'center',
57
+ top: 'middle',
58
+ shape: {
59
+ width: 50,
60
+ height: 24,
61
+ },
62
+ style: {
63
+ fill: labelBackgroundColor,
64
+ shadowBlur: 8,
65
+ shadowOffsetX: 0,
66
+ shadowOffsetY: 1,
67
+ shadowColor: shadowColor,
68
+ },
69
+ },
70
+ {
71
+ type: 'text',
72
+ z: 100,
73
+ right: 'center',
74
+ top: 'middle',
75
+ style: {
76
+ fontSize: 11,
77
+ fontFamily: 'Sofia W03',
78
+ fontWeight: 500,
79
+ fill: textColor,
80
+ width: 70,
81
+ height: 30,
82
+ text: labelCallback('short'),
83
+ },
84
+ },
85
+ ],
86
+ },
87
+ {
88
+ type: 'group',
89
+ left: `${ySentimentLabelSize + 5}px'`,
90
+ top: `${CHART_CONFIG.MAIN_HEIGHT - 24 - 5}px`,
91
+ silent: true,
92
+ children: [
93
+ {
94
+ type: 'rect',
95
+ z: 100,
96
+ right: 'center',
97
+ top: 'middle',
98
+ shape: {
99
+ width: 50,
100
+ height: 24,
101
+ },
102
+ style: {
103
+ fill: labelBackgroundColor,
104
+ shadowBlur: 8,
105
+ shadowOffsetX: 0,
106
+ shadowOffsetY: 1,
107
+ shadowColor: shadowColor,
108
+ },
109
+ },
110
+ {
111
+ type: 'text',
112
+ z: 100,
113
+ right: 'center',
114
+ top: 'middle',
115
+ style: {
116
+ fontSize: 11,
117
+ fontFamily: 'Sofia W03',
118
+ fontWeight: 500,
119
+ fill: textColor,
120
+ width: 70,
121
+ height: 30,
122
+ text: labelCallback('long'),
123
+ },
124
+ },
125
+ ],
126
+ },
127
+
128
+ {
129
+ type: 'text',
130
+ z: 30,
131
+ rotation: isDesktop ? Math.PI / 2 : 0,
132
+ left: `5px`,
133
+ top: isDesktop
134
+ ? `${topMargin + CHART_CONFIG.MAIN_HEIGHT / 2 - sentimentVerticalOffset}px`
135
+ : `${topMargin - 18}px`,
136
+ silent: true,
137
+ style: {
138
+ fontSize: 10,
139
+ fontFamily: 'Sofia W03',
140
+ fontWeight: 300,
141
+ fill: textColor,
142
+ text: sentimentText,
143
+ },
144
+ },
145
+ {
146
+ type: 'text',
147
+ z: 30,
148
+ rotation: isDesktop ? -Math.PI / 2 : 0,
149
+ right: `5px`,
150
+ top: isDesktop
151
+ ? `${topMargin + CHART_CONFIG.MAIN_HEIGHT / 2 - priceVerticalOffset}px`
152
+ : `${topMargin - 18}px`,
153
+ silent: true,
154
+ style: {
155
+ fontSize: 10,
156
+ fontFamily: 'Sofia W03',
157
+ fontWeight: 300,
158
+ fill: textColor,
159
+ text: priceText,
160
+ },
161
+ },
162
+ {
163
+ type: 'rect',
164
+ z: 20,
165
+ right: '0px',
166
+ top: '0px',
167
+ shape: {
168
+ width: yMainLabelSize,
169
+ height: CHART_CONFIG.MAIN_HEIGHT,
170
+ },
171
+ silent: true,
172
+ style: {
173
+ fill: backgroundColor,
174
+ },
175
+ },
176
+ {
177
+ type: 'rect',
178
+ z: 20,
179
+ left: '0px',
180
+ top: '0px',
181
+ shape: {
182
+ width: ySentimentLabelSize,
183
+ height: CHART_CONFIG.MAIN_HEIGHT,
184
+ },
185
+ silent: true,
186
+ style: {
187
+ fill: backgroundColor,
188
+ },
189
+ },
190
+ ];
191
+ };
@@ -1,31 +1,28 @@
1
1
  import chroma from 'chroma-js';
2
2
  import type { CandlestickSeriesOption } from 'echarts';
3
3
 
4
- import { getLabelData } from '../chartUtils';
5
4
  import type { ChartStyles } from '../chartUtils/getChartStyles';
6
5
 
7
6
  interface GetSeriesCandlestickConfigParams {
8
- dates: string[];
9
- isGreaterThanTwoWeeks: boolean;
10
7
  styles: ChartStyles;
8
+ isLoading: boolean;
11
9
  }
12
10
 
13
11
  export const getSeriesCandlestickConfig = ({
14
- dates,
15
- isGreaterThanTwoWeeks,
16
12
  styles,
13
+ isLoading,
17
14
  }: GetSeriesCandlestickConfigParams): CandlestickSeriesOption => {
18
15
  const { candleLongColor, candleShortColor } = styles;
19
- const labelsData = getLabelData({
20
- dates,
21
- isGreaterThanTwoWeeks,
22
- });
23
16
 
24
17
  return {
18
+ animation: isLoading,
25
19
  type: 'candlestick',
26
20
  id: 'candlestick',
27
21
  xAxisIndex: 0,
28
22
  yAxisIndex: 0,
23
+ silent: true,
24
+ clip: true,
25
+ large: true,
29
26
  encode: {
30
27
  x: 'dates',
31
28
  y: ['open', 'close', 'low', 'high'],
@@ -42,11 +39,6 @@ export const getSeriesCandlestickConfig = ({
42
39
  color0: candleShortColor,
43
40
  },
44
41
  },
45
- markPoint: {
46
- data: labelsData,
47
- symbol: 'circle',
48
- symbolSize: 0,
49
- },
50
- z: 2,
42
+ z: 3,
51
43
  };
52
44
  };
@@ -13,6 +13,7 @@ interface GetSeriesHeatmapConfigParams {
13
13
  isDark: boolean;
14
14
  sentimentThresholdMax: number;
15
15
  sentimentThresholdMin: number;
16
+ isLoading: boolean;
16
17
  }
17
18
 
18
19
  export const getSeriesHeatmapConfig = ({
@@ -21,8 +22,10 @@ export const getSeriesHeatmapConfig = ({
21
22
  isDark,
22
23
  sentimentThresholdMax,
23
24
  sentimentThresholdMin,
25
+ isLoading,
24
26
  }: GetSeriesHeatmapConfigParams): CustomSeriesOption => {
25
27
  return {
28
+ animation: isLoading,
26
29
  type: 'custom',
27
30
  id: 'heatmap',
28
31
  name: 'heatmap',
@@ -35,9 +38,11 @@ export const getSeriesHeatmapConfig = ({
35
38
  dimensions: ['dates', 'bookPrices', 'bookIndexes'],
36
39
  clip: true,
37
40
  renderItem: (
38
- _params: CustomSeriesRenderItemParams,
41
+ params: CustomSeriesRenderItemParams,
39
42
  api: CustomSeriesRenderItemAPI
40
43
  ) => {
44
+ const animationDelay =
45
+ (350 * params.dataIndexInside) / params.dataInsideLength;
41
46
  const xVal = api.value(0);
42
47
  const bucketIndex = api.value(2) as number;
43
48
 
@@ -47,12 +52,17 @@ export const getSeriesHeatmapConfig = ({
47
52
 
48
53
  const metaValues = buckets[bucketIndex];
49
54
 
55
+ if (!metaValues) {
56
+ return null;
57
+ }
58
+
50
59
  const [rectWidth, rectHeight] = api.size!([0, bucketWidth]) as number[];
51
60
 
52
61
  const items = metaValues.map(({ price, sentiment }: Bucket) => {
53
62
  const start = api.coord([xVal, price]);
54
63
 
55
64
  return {
65
+ silent: true,
56
66
  shape: {
57
67
  height: rectHeight,
58
68
  width: rectWidth + 1,
@@ -67,6 +77,16 @@ export const getSeriesHeatmapConfig = ({
67
77
  sentimentThresholdMax
68
78
  ),
69
79
  },
80
+ enterFrom: {
81
+ shape: {},
82
+ style: {
83
+ opacity: 0,
84
+ },
85
+ },
86
+ enterAnimation: {
87
+ duration: 150,
88
+ delay: animationDelay,
89
+ },
70
90
  type: 'rect' as const,
71
91
  };
72
92
  });
@@ -74,6 +94,7 @@ export const getSeriesHeatmapConfig = ({
74
94
  return {
75
95
  children: items,
76
96
  emphasisDisabled: true,
97
+ silent: true,
77
98
  type: 'group' as const,
78
99
  };
79
100
  },
@@ -5,12 +5,16 @@ import type { ChartStyles } from '../chartUtils';
5
5
 
6
6
  interface GetSeriesSentimentConfigParams {
7
7
  styles: ChartStyles;
8
+ isLoading: boolean;
8
9
  }
9
10
 
10
11
  export const getSeriesSentimentConfig = ({
11
12
  styles,
13
+ isLoading,
12
14
  }: GetSeriesSentimentConfigParams): LineSeriesOption => {
13
15
  return {
16
+ animation: isLoading,
17
+ animationDelay: 350,
14
18
  type: 'line',
15
19
  id: 'sentiment',
16
20
  name: 'sentiment',
@@ -18,9 +22,9 @@ export const getSeriesSentimentConfig = ({
18
22
  yAxisIndex: 1,
19
23
  encode: {
20
24
  x: 'dates',
21
- y: 'sentimentShorts',
25
+ y: 'sentimentLongs',
22
26
  },
23
- dimensions: ['dates', 'sentimentShorts', 'sentimentLongs'],
27
+ dimensions: ['dates', 'sentimentLongs', 'sentimentShorts'],
24
28
  lineStyle: {
25
29
  width: styles.sentimentOutlineWidth,
26
30
  opacity: 1,
@@ -30,7 +34,11 @@ export const getSeriesSentimentConfig = ({
30
34
  emphasis: {
31
35
  disabled: true,
32
36
  },
37
+ tooltip: {
38
+ show: false,
39
+ },
33
40
  markLine: {
41
+ animation: isLoading,
34
42
  silent: true,
35
43
  symbol: ['none', 'none'],
36
44
  label: {
@@ -55,9 +63,10 @@ export const getSeriesSentimentConfig = ({
55
63
  },
56
64
  ],
57
65
  },
58
- stack: 'sentiment',
59
66
  showSymbol: false,
60
67
  symbol: 'none',
61
- z: 3,
68
+ z: 2,
69
+ connectNulls: true,
70
+ silent: true,
62
71
  };
63
72
  };
@@ -1,6 +1,7 @@
1
1
  import type { TooltipComponentOption } from 'echarts';
2
2
 
3
3
  import type { BookType } from '../../../../gql/types/graphql';
4
+ import { CHART_CONFIG } from '../../../constants';
4
5
  import { getTooltipFormatter } from '../chartUtils';
5
6
  import type { Bucket, TooltipParam } from '../types';
6
7
 
@@ -12,6 +13,8 @@ interface GetTooltipConfigParams {
12
13
  labelCallback: (key: string, params?: Record<string, unknown>) => string;
13
14
  selectedPriceRef: { current: number };
14
15
  tooltipLinesColor: string;
16
+ sentimentLongs: (number | null)[];
17
+ sentimentShorts: (number | null)[];
15
18
  }
16
19
 
17
20
  export const getTooltipConfig = ({
@@ -22,6 +25,8 @@ export const getTooltipConfig = ({
22
25
  labelCallback,
23
26
  selectedPriceRef,
24
27
  tooltipLinesColor,
28
+ sentimentLongs,
29
+ sentimentShorts,
25
30
  }: GetTooltipConfigParams): TooltipComponentOption => ({
26
31
  trigger: 'axis' as const,
27
32
  formatter: (params) =>
@@ -32,8 +37,10 @@ export const getTooltipConfig = ({
32
37
  labelCallback,
33
38
  params: params as unknown as TooltipParam[],
34
39
  selectedPrice: selectedPriceRef.current,
40
+ sentimentLongs,
41
+ sentimentShorts,
35
42
  }),
36
-
43
+ hideDelay: 0,
37
44
  axisPointer: {
38
45
  type: 'cross' as const,
39
46
  axis: 'x' as const,
@@ -60,4 +67,8 @@ export const getTooltipConfig = ({
60
67
  },
61
68
  },
62
69
  confine: true,
70
+ position: (point) => [
71
+ point[0] + CHART_CONFIG.TOOLTIP_OFFSET,
72
+ point[1] + CHART_CONFIG.TOOLTIP_OFFSET,
73
+ ],
63
74
  });