layerchart 2.0.0-next.4 → 2.0.0-next.41

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 (180) hide show
  1. package/dist/components/AnnotationLine.svelte +15 -2
  2. package/dist/components/AnnotationPoint.svelte +29 -11
  3. package/dist/components/AnnotationRange.svelte +18 -4
  4. package/dist/components/Arc.svelte +5 -5
  5. package/dist/components/Area.svelte +10 -2
  6. package/dist/components/Axis.svelte +175 -58
  7. package/dist/components/Axis.svelte.d.ts +23 -6
  8. package/dist/components/Bar.svelte +20 -15
  9. package/dist/components/Bar.svelte.d.ts +2 -2
  10. package/dist/components/Bars.svelte +4 -4
  11. package/dist/components/Blur.svelte +7 -6
  12. package/dist/components/Blur.svelte.d.ts +2 -5
  13. package/dist/components/BrushContext.svelte +45 -45
  14. package/dist/components/Calendar.svelte +31 -10
  15. package/dist/components/Calendar.svelte.d.ts +2 -1
  16. package/dist/components/Chart.svelte +76 -27
  17. package/dist/components/Chart.svelte.d.ts +26 -8
  18. package/dist/components/ChartClipPath.svelte +1 -1
  19. package/dist/components/Circle.svelte +44 -3
  20. package/dist/components/CircleClipPath.svelte +8 -1
  21. package/dist/components/ClipPath.svelte +1 -2
  22. package/dist/components/ColorRamp.svelte +1 -1
  23. package/dist/components/ComputedStyles.svelte +9 -2
  24. package/dist/components/Connector.svelte +3 -3
  25. package/dist/components/Connector.svelte.d.ts +1 -1
  26. package/dist/components/Ellipse.svelte +228 -0
  27. package/dist/components/Ellipse.svelte.d.ts +64 -0
  28. package/dist/components/ForceSimulation.svelte +184 -50
  29. package/dist/components/ForceSimulation.svelte.d.ts +95 -21
  30. package/dist/components/Frame.svelte +1 -1
  31. package/dist/components/GeoCircle.svelte +1 -1
  32. package/dist/components/GeoEdgeFade.svelte +1 -1
  33. package/dist/components/GeoPath.svelte +30 -8
  34. package/dist/components/GeoPoint.svelte +4 -5
  35. package/dist/components/GeoSpline.svelte +5 -5
  36. package/dist/components/GeoSpline.svelte.d.ts +1 -1
  37. package/dist/components/GeoTile.svelte +1 -1
  38. package/dist/components/Graticule.svelte +5 -5
  39. package/dist/components/Grid.svelte +60 -63
  40. package/dist/components/Group.svelte +13 -8
  41. package/dist/components/Group.svelte.d.ts +10 -3
  42. package/dist/components/Highlight.svelte +55 -28
  43. package/dist/components/Highlight.svelte.d.ts +4 -0
  44. package/dist/components/Hull.svelte +12 -5
  45. package/dist/components/Labels.svelte +24 -13
  46. package/dist/components/Labels.svelte.d.ts +12 -5
  47. package/dist/components/Legend.svelte +143 -70
  48. package/dist/components/Legend.svelte.d.ts +12 -8
  49. package/dist/components/Line.svelte +40 -3
  50. package/dist/components/LinearGradient.svelte +35 -4
  51. package/dist/components/Link.svelte +1 -1
  52. package/dist/components/Marker.svelte +37 -26
  53. package/dist/components/MonthPath.svelte +26 -12
  54. package/dist/components/MonthPath.svelte.d.ts +4 -3
  55. package/dist/components/MotionPath.svelte +1 -1
  56. package/dist/components/Pack.svelte.d.ts +10 -3
  57. package/dist/components/Partition.svelte.d.ts +10 -3
  58. package/dist/components/Pattern.svelte +5 -5
  59. package/dist/components/Pie.svelte +1 -2
  60. package/dist/components/Points.svelte +11 -72
  61. package/dist/components/Points.svelte.d.ts +1 -8
  62. package/dist/components/Polygon.svelte +309 -0
  63. package/dist/components/Polygon.svelte.d.ts +115 -0
  64. package/dist/components/RadialGradient.svelte +4 -6
  65. package/dist/components/Rect.svelte +55 -5
  66. package/dist/components/Rect.svelte.d.ts +2 -2
  67. package/dist/components/RectClipPath.svelte +4 -3
  68. package/dist/components/RectClipPath.svelte.d.ts +2 -2
  69. package/dist/components/Rule.svelte +167 -77
  70. package/dist/components/Rule.svelte.d.ts +7 -2
  71. package/dist/components/Spline.svelte +59 -28
  72. package/dist/components/Spline.svelte.d.ts +12 -4
  73. package/dist/components/Text.svelte +121 -73
  74. package/dist/components/Text.svelte.d.ts +6 -0
  75. package/dist/components/TileImage.svelte +19 -4
  76. package/dist/components/TransformContext.svelte +9 -3
  77. package/dist/components/TransformControls.svelte +89 -38
  78. package/dist/components/Tree.svelte.d.ts +10 -3
  79. package/dist/components/Treemap.svelte +63 -26
  80. package/dist/components/Treemap.svelte.d.ts +21 -14
  81. package/dist/components/Voronoi.svelte +12 -13
  82. package/dist/components/charts/ArcChart.svelte +43 -71
  83. package/dist/components/charts/ArcChart.svelte.d.ts +10 -3
  84. package/dist/components/charts/AreaChart.svelte +29 -59
  85. package/dist/components/charts/AreaChart.svelte.d.ts +10 -3
  86. package/dist/components/charts/BarChart.svelte +79 -71
  87. package/dist/components/charts/BarChart.svelte.d.ts +10 -3
  88. package/dist/components/charts/DefaultTooltip.svelte +3 -3
  89. package/dist/components/charts/DefaultTooltip.svelte.d.ts +1 -1
  90. package/dist/components/charts/LineChart.svelte +69 -75
  91. package/dist/components/charts/LineChart.svelte.d.ts +21 -8
  92. package/dist/components/charts/PieChart.svelte +44 -71
  93. package/dist/components/charts/PieChart.svelte.d.ts +10 -3
  94. package/dist/components/charts/ScatterChart.svelte +10 -39
  95. package/dist/components/charts/ScatterChart.svelte.d.ts +10 -3
  96. package/dist/components/charts/utils.svelte.d.ts +1 -19
  97. package/dist/components/charts/utils.svelte.js +7 -35
  98. package/dist/components/index.d.ts +4 -0
  99. package/dist/components/index.js +5 -1
  100. package/dist/components/layout/Canvas.svelte +96 -69
  101. package/dist/components/layout/Canvas.svelte.d.ts +6 -0
  102. package/dist/components/layout/Html.svelte +15 -9
  103. package/dist/components/layout/Layer.svelte +6 -4
  104. package/dist/components/layout/Layer.svelte.d.ts +6 -4
  105. package/dist/components/layout/Svg.svelte +19 -11
  106. package/dist/components/layout/WebGL.svelte +26 -6
  107. package/dist/components/layout/WebGL.svelte.d.ts +5 -2
  108. package/dist/components/tooltip/Tooltip.svelte +73 -36
  109. package/dist/components/tooltip/Tooltip.svelte.d.ts +10 -3
  110. package/dist/components/tooltip/TooltipContext.svelte +167 -54
  111. package/dist/components/tooltip/TooltipContext.svelte.d.ts +19 -5
  112. package/dist/components/tooltip/TooltipHeader.svelte +32 -18
  113. package/dist/components/tooltip/TooltipHeader.svelte.d.ts +3 -3
  114. package/dist/components/tooltip/TooltipItem.svelte +46 -37
  115. package/dist/components/tooltip/TooltipItem.svelte.d.ts +3 -3
  116. package/dist/components/tooltip/TooltipList.svelte +12 -10
  117. package/dist/components/tooltip/TooltipSeparator.svelte +18 -10
  118. package/dist/components/tooltip/tooltipMetaContext.d.ts +2 -2
  119. package/dist/docs/Blockquote.svelte +6 -4
  120. package/dist/docs/Blockquote.svelte.d.ts +4 -19
  121. package/dist/docs/Code.svelte +70 -28
  122. package/dist/docs/Code.svelte.d.ts +9 -24
  123. package/dist/docs/Header1.svelte +4 -2
  124. package/dist/docs/Header1.svelte.d.ts +4 -28
  125. package/dist/docs/Json.svelte +11 -3
  126. package/dist/docs/Json.svelte.d.ts +9 -21
  127. package/dist/docs/Layout.svelte +10 -7
  128. package/dist/docs/Layout.svelte.d.ts +4 -19
  129. package/dist/docs/Link.svelte +7 -3
  130. package/dist/docs/Link.svelte.d.ts +4 -38
  131. package/dist/docs/Preview.svelte +22 -23
  132. package/dist/docs/Preview.svelte.d.ts +5 -6
  133. package/dist/docs/TilesetField.svelte +20 -19
  134. package/dist/docs/TilesetField.svelte.d.ts +5 -22
  135. package/dist/docs/ViewSourceButton.svelte +10 -7
  136. package/dist/docs/ViewSourceButton.svelte.d.ts +7 -21
  137. package/dist/states/series.svelte.d.ts +30 -0
  138. package/dist/states/series.svelte.js +54 -0
  139. package/dist/styles/daisyui-5.css +6 -0
  140. package/dist/styles/shadcn-svelte.css +11 -0
  141. package/dist/styles/skeleton-3.css +15 -0
  142. package/dist/utils/arcText.svelte.js +4 -4
  143. package/dist/utils/array.d.ts +11 -0
  144. package/dist/utils/array.js +23 -0
  145. package/dist/utils/array.test.d.ts +1 -0
  146. package/dist/utils/array.test.js +200 -0
  147. package/dist/utils/attributes.d.ts +3 -13
  148. package/dist/utils/attributes.js +4 -18
  149. package/dist/utils/canvas.d.ts +77 -0
  150. package/dist/utils/canvas.js +105 -41
  151. package/dist/utils/common.d.ts +9 -0
  152. package/dist/utils/common.js +18 -1
  153. package/dist/utils/common.test.js +26 -1
  154. package/dist/utils/genData.d.ts +22 -8
  155. package/dist/utils/genData.js +34 -14
  156. package/dist/utils/graph/dagre.d.ts +4 -4
  157. package/dist/utils/graph/dagre.js +5 -7
  158. package/dist/utils/index.d.ts +1 -0
  159. package/dist/utils/index.js +1 -0
  160. package/dist/utils/math.d.ts +17 -0
  161. package/dist/utils/math.js +17 -0
  162. package/dist/utils/motion.svelte.js +1 -1
  163. package/dist/utils/path.d.ts +10 -0
  164. package/dist/utils/path.js +30 -0
  165. package/dist/utils/rect.svelte.d.ts +2 -2
  166. package/dist/utils/rect.svelte.js +73 -1
  167. package/dist/utils/scales.svelte.d.ts +9 -3
  168. package/dist/utils/scales.svelte.js +47 -4
  169. package/dist/utils/shape.d.ts +43 -0
  170. package/dist/utils/shape.js +59 -0
  171. package/dist/utils/stack.js +1 -1
  172. package/dist/utils/string.d.ts +49 -0
  173. package/dist/utils/string.js +4 -2
  174. package/dist/utils/ticks.d.ts +15 -4
  175. package/dist/utils/ticks.js +140 -159
  176. package/dist/utils/ticks.test.js +16 -26
  177. package/dist/utils/treemap.d.ts +1 -1
  178. package/dist/utils/types.d.ts +15 -2
  179. package/package.json +36 -35
  180. package/dist/utils/object.js +0 -2
@@ -0,0 +1,115 @@
1
+ import type { CommonStyleProps, Without } from '../utils/types.js';
2
+ export type PolygonPropsWithoutHTML = {
3
+ /**
4
+ * The center x position of the polygon.
5
+ *
6
+ * @default 0
7
+ */
8
+ cx?: number;
9
+ /**
10
+ * The initial center x position of the polygon.
11
+ *
12
+ * @default cx
13
+ */
14
+ initialCx?: number;
15
+ /**
16
+ * The center y position of the polygon.
17
+ *
18
+ * @default 0
19
+ */
20
+ cy?: number;
21
+ /**
22
+ * The initial center y position of the polygon.
23
+ *
24
+ * @default cy
25
+ */
26
+ initialCy?: number;
27
+ /**
28
+ * The radius of the polygon.
29
+ *
30
+ * @default 1
31
+ */
32
+ r?: number;
33
+ /**
34
+ * The initial radius of the polygon.
35
+ *
36
+ * @default r
37
+ */
38
+ initialR?: number;
39
+ /**
40
+ * The number of points or explicit points to create the polygon.
41
+ *
42
+ * @default 4
43
+ */
44
+ points?: number | {
45
+ x: number;
46
+ y: number;
47
+ }[];
48
+ /**
49
+ * The radius of the curve for rounded corners.
50
+ *
51
+ * @default 0
52
+ */
53
+ cornerRadius?: number;
54
+ /**
55
+ * The rotation of the polygon.
56
+ *
57
+ * @default 0
58
+ */
59
+ rotate?: number;
60
+ /**
61
+ * The percent to inset the odd points of the star (<1 inset, >1 outset)
62
+ *
63
+ * @default 0
64
+ */
65
+ inset?: number;
66
+ /**
67
+ * The horizontal stretch factor of the polygon.
68
+ *
69
+ * @default 1
70
+ */
71
+ scaleX?: number;
72
+ /**
73
+ * The vertical stretch factor of the polygon.
74
+ *
75
+ * @default 1
76
+ */
77
+ scaleY?: number;
78
+ /**
79
+ * The skew angle in degrees along the X axis.
80
+ *
81
+ * @default 0
82
+ */
83
+ skewX?: number;
84
+ /**
85
+ * The skew angle in degrees along the Y axis.
86
+ *
87
+ * @default 0
88
+ */
89
+ skewY?: number;
90
+ /**
91
+ * The tilt factor for x-coordinates.
92
+ *
93
+ * @default 1
94
+ */
95
+ tiltX?: number;
96
+ /**
97
+ * The tilt factor for y-coordinates.
98
+ *
99
+ * @default 1
100
+ */
101
+ tiltY?: number;
102
+ /**
103
+ * A bindable reference to the `<path>` element
104
+ *
105
+ * @bindable
106
+ */
107
+ ref?: SVGPathElement;
108
+ motion?: MotionProp;
109
+ } & CommonStyleProps;
110
+ export type PolygonProps = PolygonPropsWithoutHTML & Without<SVGAttributes<Element>, PolygonPropsWithoutHTML>;
111
+ import type { SVGAttributes } from 'svelte/elements';
112
+ import { type MotionProp } from '../utils/motion.svelte.js';
113
+ declare const Polygon: import("svelte").Component<PolygonProps, {}, "ref">;
114
+ type Polygon = ReturnType<typeof Polygon>;
115
+ export default Polygon;
@@ -89,7 +89,7 @@
89
89
  import { parsePercent } from '../utils/math.js';
90
90
  import { getChartContext } from './Chart.svelte';
91
91
  import { createId } from '../utils/createId.js';
92
- import { extractLayerProps, layerClass } from '../utils/attributes.js';
92
+ import { extractLayerProps } from '../utils/attributes.js';
93
93
  import { cls } from '@layerstack/tailwind';
94
94
 
95
95
  const uid = $props.id();
@@ -102,6 +102,7 @@
102
102
  fx = cx,
103
103
  fy = cy,
104
104
  r = '50%',
105
+ // fr = '0%'; // TODO: Svelte / Typescript does not know `<radialRadiant fr="...">`
105
106
  spreadMethod = 'pad',
106
107
  transform = undefined,
107
108
  units = 'objectBoundingBox',
@@ -111,9 +112,6 @@
111
112
  ...restProps
112
113
  }: RadialGradientProps = $props();
113
114
 
114
- // TODO: Svelte / Typescript does not know `<radialRadiant fr="...">`
115
- // export let fr = '0%';
116
-
117
115
  const ctx = getChartContext();
118
116
 
119
117
  const renderCtx = getRenderContext();
@@ -169,12 +167,12 @@
169
167
  {spreadMethod}
170
168
  gradientTransform={transform}
171
169
  gradientUnits={units}
172
- {...extractLayerProps({ ...restProps, class: className }, 'radial-gradient')}
170
+ {...extractLayerProps({ ...restProps, class: className }, 'lc-radial-gradient')}
173
171
  >
174
172
  {#if stopsContent}
175
173
  {@render stopsContent()}
176
174
  {:else if stops}
177
- {@const stopClass = cls(layerClass('radial-gradient-stop'), className)}
175
+ {@const stopClass = cls('lc-radial-gradient-stop', className)}
178
176
  {#each stops as stop, i}
179
177
  {#if Array.isArray(stop)}
180
178
  <stop offset={stop[0]} stop-color={stop[1]} class={stopClass} />
@@ -1,5 +1,5 @@
1
1
  <script lang="ts" module>
2
- import type { CommonStyleProps, Without } from '../utils/types.js';
2
+ import type { CommonEvents, CommonStyleProps, Without } from '../utils/types.js';
3
3
  import type { SVGAttributes } from 'svelte/elements';
4
4
  import { createMotion, parseMotionProp, type MotionProp } from '../utils/motion.svelte.js';
5
5
  import { renderRect, type ComputedStylesOptions } from '../utils/canvas.js';
@@ -39,7 +39,8 @@
39
39
  } & CommonStyleProps;
40
40
 
41
41
  export type RectProps = RectPropsWithoutHTML &
42
- Without<SVGAttributes<SVGRectElement>, RectPropsWithoutHTML>;
42
+ Without<SVGAttributes<SVGRectElement>, RectPropsWithoutHTML> &
43
+ CommonEvents;
43
44
  </script>
44
45
 
45
46
  <script lang="ts">
@@ -49,7 +50,6 @@
49
50
  import { getRenderContext } from './Chart.svelte';
50
51
  import { registerCanvasComponent } from './layout/Canvas.svelte';
51
52
  import { createKey } from '../utils/key.svelte.js';
52
- import { layerClass } from '../utils/attributes.js';
53
53
 
54
54
  let {
55
55
  height,
@@ -107,7 +107,7 @@
107
107
  ? merge({ styles: { strokeWidth } }, styleOverrides)
108
108
  : {
109
109
  styles: { fill, fillOpacity, stroke, strokeWidth, opacity },
110
- classes: className,
110
+ classes: cls('lc-rect', className),
111
111
  }
112
112
  );
113
113
  }
@@ -155,7 +155,7 @@
155
155
  {stroke}
156
156
  stroke-width={strokeWidth}
157
157
  {opacity}
158
- class={cls(layerClass('rect'), fill == null && 'fill-surface-content', className)}
158
+ class={cls('lc-rect', className)}
159
159
  {...restProps}
160
160
  {onclick}
161
161
  {ondblclick}
@@ -166,4 +166,54 @@
166
166
  {onpointerout}
167
167
  bind:this={ref}
168
168
  />
169
+ {:else if renderCtx === 'html'}
170
+ <!-- svelte-ignore a11y_click_events_have_key_events -->
171
+ <!-- svelte-ignore a11y_no_static_element_interactions -->
172
+ <div
173
+ style:position="absolute"
174
+ style:left="{motionX.current}px"
175
+ style:top="{motionY.current}px"
176
+ style:width="{motionWidth.current}px"
177
+ style:height="{motionHeight.current}px"
178
+ style:background={fill}
179
+ style:background-opacity={opacity}
180
+ style:border-width="{strokeWidth}px"
181
+ style:border-style="solid"
182
+ style:border-color={stroke}
183
+ style:border-radius="{restProps.rx}px"
184
+ class={cls('lc-rect', className)}
185
+ {...restProps as any}
186
+ {onclick}
187
+ {ondblclick}
188
+ {onpointerenter}
189
+ {onpointermove}
190
+ {onpointerleave}
191
+ {onpointerover}
192
+ {onpointerout}
193
+ ></div>
169
194
  {/if}
195
+
196
+ <style>
197
+ @layer base {
198
+ :global(:where(.lc-rect)) {
199
+ --fill-color: var(--color-surface-content, currentColor);
200
+ --stroke-color: initial;
201
+ }
202
+
203
+ /* Svg | Canvas layers */
204
+ :global(:where(.lc-layout-svg .lc-rect, svg.lc-rect):not([fill])) {
205
+ fill: var(--fill-color);
206
+ }
207
+ :global(:where(.lc-layout-svg .lc-rect, svg.lc-rect):not([stroke])) {
208
+ stroke: var(--stroke-color);
209
+ }
210
+
211
+ /* Html layers */
212
+ :global(:where(.lc-layout-html .lc-rect):not([background])) {
213
+ background: var(--fill-color);
214
+ }
215
+ :global(:where(.lc-layout-html .lc-rect):not([border-color])) {
216
+ border-color: var(--stroke-color);
217
+ }
218
+ }
219
+ </style>
@@ -1,4 +1,4 @@
1
- import type { CommonStyleProps, Without } from '../utils/types.js';
1
+ import type { CommonEvents, CommonStyleProps, Without } from '../utils/types.js';
2
2
  import type { SVGAttributes } from 'svelte/elements';
3
3
  import { type MotionProp } from '../utils/motion.svelte.js';
4
4
  export type RectPropsWithoutHTML = {
@@ -30,7 +30,7 @@ export type RectPropsWithoutHTML = {
30
30
  ref?: SVGRectElement;
31
31
  motion?: MotionProp<'x' | 'y' | 'width' | 'height'>;
32
32
  } & CommonStyleProps;
33
- export type RectProps = RectPropsWithoutHTML & Without<SVGAttributes<SVGRectElement>, RectPropsWithoutHTML>;
33
+ export type RectProps = RectPropsWithoutHTML & Without<SVGAttributes<SVGRectElement>, RectPropsWithoutHTML> & CommonEvents;
34
34
  declare const Rect: import("svelte").Component<RectProps, {}, "ref">;
35
35
  type Rect = ReturnType<typeof Rect>;
36
36
  export default Rect;
@@ -1,6 +1,6 @@
1
1
  <script lang="ts" module>
2
2
  import Rect, { type RectPropsWithoutHTML } from './Rect.svelte';
3
- import type { Without } from '../utils/types.js';
3
+ import type { CommonEvents, Without } from '../utils/types.js';
4
4
  import type { SVGAttributes } from 'svelte/elements';
5
5
  import type { Snippet } from 'svelte';
6
6
 
@@ -58,7 +58,8 @@
58
58
  Without<RectPropsWithoutHTML, BaseRectClipPathPropsWithoutHTML>;
59
59
 
60
60
  export type RectClipPathProps = RectClipPathPropsWithoutHTML &
61
- Without<SVGAttributes<SVGElement>, RectClipPathPropsWithoutHTML>;
61
+ Without<SVGAttributes<SVGElement>, RectClipPathPropsWithoutHTML> &
62
+ CommonEvents;
62
63
  </script>
63
64
 
64
65
  <script lang="ts">
@@ -81,7 +82,7 @@
81
82
 
82
83
  <ClipPath {id} {disabled}>
83
84
  {#snippet clip()}
84
- <Rect {x} {y} {...extractLayerProps(restProps, 'clip-path-rect')} />
85
+ <Rect {x} {y} {...extractLayerProps(restProps, 'lc-clip-path-rect')} />
85
86
  {/snippet}
86
87
  {#snippet children({ url })}
87
88
  {@render childrenProp?.({ id, url })}
@@ -1,5 +1,5 @@
1
1
  import { type RectPropsWithoutHTML } from './Rect.svelte';
2
- import type { Without } from '../utils/types.js';
2
+ import type { CommonEvents, Without } from '../utils/types.js';
3
3
  import type { SVGAttributes } from 'svelte/elements';
4
4
  import type { Snippet } from 'svelte';
5
5
  export type BaseRectClipPathPropsWithoutHTML = {
@@ -48,7 +48,7 @@ export type BaseRectClipPathPropsWithoutHTML = {
48
48
  motion?: MotionProp<'x' | 'y' | 'width' | 'height'>;
49
49
  };
50
50
  export type RectClipPathPropsWithoutHTML = BaseRectClipPathPropsWithoutHTML & Without<RectPropsWithoutHTML, BaseRectClipPathPropsWithoutHTML>;
51
- export type RectClipPathProps = RectClipPathPropsWithoutHTML & Without<SVGAttributes<SVGElement>, RectClipPathPropsWithoutHTML>;
51
+ export type RectClipPathProps = RectClipPathPropsWithoutHTML & Without<SVGAttributes<SVGElement>, RectClipPathPropsWithoutHTML> & CommonEvents;
52
52
  import type { MotionProp } from '../utils/motion.svelte.js';
53
53
  declare const RectClipPath: import("svelte").Component<RectClipPathProps, {}, "">;
54
54
  type RectClipPath = ReturnType<typeof RectClipPath>;
@@ -3,6 +3,11 @@
3
3
  import type { SVGAttributes } from 'svelte/elements';
4
4
 
5
5
  export type BaseRulePropsWithoutHTML = {
6
+ /**
7
+ * Override the data from the context.
8
+ */
9
+ data?: any;
10
+
6
11
  /**
7
12
  * Create a vertical `x` line
8
13
  * - If true or 'left', will draw at chart left (xRange[0])
@@ -12,7 +17,7 @@
12
17
  *
13
18
  * @default false
14
19
  */
15
- x?: number | Date | boolean | 'left' | 'right';
20
+ x?: number | Date | boolean | '$left' | '$right' | Accessor;
16
21
 
17
22
  /**
18
23
  * Pixel offset to apply to `x` coordinate
@@ -30,7 +35,7 @@
30
35
  *
31
36
  * @default false
32
37
  */
33
- y?: number | Date | boolean | 'top' | 'bottom';
38
+ y?: number | Date | boolean | '$top' | '$bottom' | Accessor;
34
39
 
35
40
  /**
36
41
  * Pixel offset to apply to `y` coordinate
@@ -55,13 +60,16 @@
55
60
  import Group from './Group.svelte';
56
61
  import Line, { type LinePropsWithoutHTML } from './Line.svelte';
57
62
  import { getChartContext } from './Chart.svelte';
58
- import { layerClass } from '../utils/attributes.js';
63
+ import { accessor, chartDataArray, type Accessor } from '../utils/common.js';
64
+ import { isScaleBand, isScaleNumeric } from '../utils/scales.svelte.js';
59
65
 
60
66
  let {
67
+ data: dataProp,
61
68
  x = false,
62
69
  xOffset = 0,
63
70
  y = false,
64
71
  yOffset = 0,
72
+ stroke: strokeProp,
65
73
  class: className,
66
74
  children,
67
75
  ...restProps
@@ -69,89 +77,171 @@
69
77
 
70
78
  const ctx = getChartContext();
71
79
 
72
- const xRangeMinMax = $derived(extent<number | Date>(ctx.xRange));
73
- const yRangeMinMax = $derived(extent<number | Date>(ctx.yRange));
74
-
75
- function showRule(value: typeof x | typeof y, axis: 'x' | 'y') {
76
- switch (typeof value) {
77
- case 'boolean':
78
- return value;
79
- case 'string':
80
- return true;
81
- default:
82
- if (axis === 'x') {
83
- return ctx.xScale(value) >= xRangeMinMax[0]! && ctx.xScale(value) <= xRangeMinMax[1]!;
84
- } else {
85
- return ctx.yScale(value) >= yRangeMinMax[0]! && ctx.yScale(value) <= yRangeMinMax[1]!;
86
- }
80
+ const data = $derived(chartDataArray(dataProp ?? ctx.data));
81
+
82
+ const singleX = $derived(
83
+ typeof x === 'number' ||
84
+ x instanceof Date ||
85
+ x === true ||
86
+ x === '$left' ||
87
+ x === '$right' ||
88
+ (isScaleBand(ctx.xScale) && ctx.xDomain.includes(x as any))
89
+ );
90
+ const singleY = $derived(
91
+ typeof y === 'number' ||
92
+ y instanceof Date ||
93
+ y === true ||
94
+ y === '$bottom' ||
95
+ y === '$top' ||
96
+ (isScaleBand(ctx.yScale) && ctx.yDomain.includes(y as any))
97
+ );
98
+
99
+ const xRangeMinMax = $derived(extent<number>(ctx.xRange));
100
+ const yRangeMinMax = $derived(extent<number>(ctx.yRange));
101
+
102
+ const lines = $derived.by(() => {
103
+ const result: {
104
+ x1: number;
105
+ y1: number;
106
+ x2: number;
107
+ y2: number;
108
+ axis: 'x' | 'y';
109
+ stroke?: string;
110
+ }[] = [];
111
+
112
+ // Single x line
113
+ if (singleX) {
114
+ const _x =
115
+ x === true || x === '$left'
116
+ ? xRangeMinMax[0]!
117
+ : x === '$right'
118
+ ? xRangeMinMax[1]!
119
+ : ctx.xScale(x) + xOffset;
120
+
121
+ result.push({
122
+ x1: _x,
123
+ y1: ctx.yRange[0] || 0,
124
+ x2: _x,
125
+ y2: ctx.yRange[1] || 0,
126
+ axis: 'x',
127
+ });
87
128
  }
88
- }
89
- </script>
90
129
 
91
- <Group class={layerClass('rule-g')}>
92
- {#if showRule(x, 'x')}
93
- {@const xCoord =
94
- x === true || x === 'left'
95
- ? xRangeMinMax[0]
96
- : x === 'right'
97
- ? xRangeMinMax[1]
98
- : ctx.xScale(x) + xOffset}
130
+ // Single y line
131
+ if (singleY) {
132
+ const _y =
133
+ y === true || y === '$bottom'
134
+ ? yRangeMinMax[1]!
135
+ : y === '$top'
136
+ ? yRangeMinMax[0]!
137
+ : ctx.yScale(y) + yOffset;
138
+
139
+ result.push({
140
+ x1: ctx.xRange[0] || 0,
141
+ y1: _y,
142
+ x2: ctx.xRange[1] || 0,
143
+ y2: _y,
144
+ axis: 'y',
145
+ });
146
+ }
99
147
 
100
- {#if ctx.radial}
101
- {@const [x1, y1] = pointRadial(xCoord, Number(yRangeMinMax[0]))}
102
- {@const [x2, y2] = pointRadial(xCoord, Number(yRangeMinMax[1]))}
148
+ // Data driven lines
149
+ if (!singleX && !singleY) {
150
+ const xAccessor = x !== false ? accessor(x as Accessor) : ctx.x;
151
+ const yAccessor = y !== false ? accessor(y as Accessor) : ctx.y;
152
+
153
+ const xBandOffset = isScaleBand(ctx.xScale) ? ctx.xScale.bandwidth() / 2 : 0;
154
+ const yBandOffset = isScaleBand(ctx.yScale) ? ctx.yScale.bandwidth() / 2 : 0;
155
+
156
+ for (const d of data) {
157
+ const xValue = xAccessor(d);
158
+ const yValue = yAccessor(d);
159
+
160
+ const x1Value = Array.isArray(xValue) ? xValue[0] : isScaleNumeric(ctx.xScale) ? 0 : xValue;
161
+ const x2Value = Array.isArray(xValue) ? xValue[1] : xValue;
162
+ const y1Value = Array.isArray(yValue) ? yValue[0] : isScaleNumeric(ctx.yScale) ? 0 : yValue;
163
+ const y2Value = Array.isArray(yValue) ? yValue[1] : yValue;
164
+
165
+ result.push({
166
+ x1: ctx.xScale(x1Value) + xBandOffset + xOffset,
167
+ y1: ctx.yScale(y1Value) + yBandOffset + yOffset,
168
+ x2: ctx.xScale(x2Value) + xBandOffset + xOffset,
169
+ y2: ctx.yScale(y2Value) + yBandOffset + yOffset,
170
+ axis: Array.isArray(yValue) || isScaleBand(ctx.xScale) ? 'x' : 'y', // TODO: what about single prop like lollipop?
171
+ stroke: (strokeProp ?? ctx.config.c) ? ctx.cGet(d) : null, // use color scale, if available
172
+ });
173
+ }
174
+ }
103
175
 
104
- <Line
105
- {...restProps}
106
- {x1}
107
- {y1}
108
- {x2}
109
- {y2}
110
- class={cls(layerClass('rule-x-radial-line'), 'stroke-surface-content/10', className)}
111
- />
112
- {:else}
113
- <Line
114
- {...restProps}
115
- x1={xCoord}
116
- x2={xCoord}
117
- y1={ctx.yRange[0] || 0}
118
- y2={ctx.yRange[1] || 0}
119
- class={cls(layerClass('rule-x-line'), 'stroke-surface-content/50', className)}
120
- />
121
- {/if}
122
- {/if}
176
+ // Remove lines if out of range of chart (non-0 baseline, brushing, etc)
177
+ return result.filter((line) => {
178
+ return (
179
+ line.x1 >= xRangeMinMax[0]! &&
180
+ line.x2 <= xRangeMinMax[1]! &&
181
+ line.y1 >= yRangeMinMax[0]! &&
182
+ line.y2 <= yRangeMinMax[1]!
183
+ );
184
+ });
185
+ });
186
+
187
+ // $inspect({ lines });
188
+ </script>
189
+
190
+ <Group class="lc-rule-g">
191
+ {#each lines as line}
192
+ {@const stroke = line.stroke ?? strokeProp}
123
193
 
124
- {#if showRule(y, 'y')}
125
194
  {#if ctx.radial}
126
- <Circle
127
- r={y === true || y === 'bottom'
128
- ? yRangeMinMax[1]
129
- : y === 'top'
130
- ? yRangeMinMax[0]
131
- : ctx.yScale(y) + yOffset}
132
- class={cls(
133
- layerClass('rule-y-radial-circle'),
134
- 'fill-none stroke-surface-content/50',
135
- className
136
- )}
137
- />
195
+ {#if line.axis === 'x'}
196
+ {@const [x1, y1] = pointRadial(line.x1, line.y1)}
197
+ {@const [x2, y2] = pointRadial(line.x2, line.y2)}
198
+ <Line
199
+ {...restProps}
200
+ {x1}
201
+ {y1}
202
+ {x2}
203
+ {y2}
204
+ {stroke}
205
+ class={cls('lc-rule-x-radial-line', className)}
206
+ />
207
+ {:else if line.axis === 'y'}
208
+ <Circle r={line.y1} {stroke} class={cls('lc-rule-y-radial-circle', className)} />
209
+ {/if}
138
210
  {:else}
139
211
  <Line
140
212
  {...restProps}
141
- x1={ctx.xRange[0] || 0}
142
- x2={ctx.xRange[1] || 0}
143
- y1={y === true || y === 'bottom'
144
- ? yRangeMinMax[1]
145
- : y === 'top'
146
- ? yRangeMinMax[0]
147
- : ctx.yScale(y) + yOffset}
148
- y2={y === true || y === 'bottom'
149
- ? yRangeMinMax[1]
150
- : y === 'top'
151
- ? yRangeMinMax[0]
152
- : ctx.yScale(y) + yOffset}
153
- class={cls(layerClass('rule-y-line'), 'stroke-surface-content/50', className)}
213
+ x1={line.x1}
214
+ y1={line.y1}
215
+ x2={line.x2}
216
+ y2={line.y2}
217
+ {stroke}
218
+ class={cls(line.axis === 'x' ? 'lc-rule-x-line' : 'lc-rule-y-line', className)}
154
219
  />
155
220
  {/if}
156
- {/if}
221
+ {/each}
157
222
  </Group>
223
+
224
+ <style>
225
+ @layer components {
226
+ /* TODO: better way to handle this without affecting other components? */
227
+ /* Could add a layer between "components" and "base" but would require more setup (and not alignw with TW layers) */
228
+ :global(
229
+ :where(
230
+ .lc-rule-x-line,
231
+ .lc-rule-y-line,
232
+ .lc-rule-x-radial-line,
233
+ .lc-rule-y-radial-circle
234
+ ):not([class*='lc-axis'], [class*='lc-grid'])
235
+ ) {
236
+ --stroke-color: color-mix(
237
+ in oklab,
238
+ var(--color-surface-content, currentColor) 50%,
239
+ transparent
240
+ );
241
+ }
242
+
243
+ :global(:where(.lc-rule-y-radial-circle)) {
244
+ --fill-color: none;
245
+ }
246
+ }
247
+ </style>
@@ -1,6 +1,10 @@
1
1
  import type { Without } from '../utils/types.js';
2
2
  import type { SVGAttributes } from 'svelte/elements';
3
3
  export type BaseRulePropsWithoutHTML = {
4
+ /**
5
+ * Override the data from the context.
6
+ */
7
+ data?: any;
4
8
  /**
5
9
  * Create a vertical `x` line
6
10
  * - If true or 'left', will draw at chart left (xRange[0])
@@ -10,7 +14,7 @@ export type BaseRulePropsWithoutHTML = {
10
14
  *
11
15
  * @default false
12
16
  */
13
- x?: number | Date | boolean | 'left' | 'right';
17
+ x?: number | Date | boolean | '$left' | '$right' | Accessor;
14
18
  /**
15
19
  * Pixel offset to apply to `x` coordinate
16
20
  *
@@ -26,7 +30,7 @@ export type BaseRulePropsWithoutHTML = {
26
30
  *
27
31
  * @default false
28
32
  */
29
- y?: number | Date | boolean | 'top' | 'bottom';
33
+ y?: number | Date | boolean | '$top' | '$bottom' | Accessor;
30
34
  /**
31
35
  * Pixel offset to apply to `y` coordinate
32
36
  * @default 0
@@ -36,6 +40,7 @@ export type BaseRulePropsWithoutHTML = {
36
40
  export type RulePropsWithoutHTML = BaseRulePropsWithoutHTML & Without<Partial<LinePropsWithoutHTML>, BaseRulePropsWithoutHTML>;
37
41
  export type RuleProps = RulePropsWithoutHTML & Without<SVGAttributes<SVGElement>, RulePropsWithoutHTML>;
38
42
  import { type LinePropsWithoutHTML } from './Line.svelte';
43
+ import { type Accessor } from '../utils/common.js';
39
44
  declare const Rule: import("svelte").Component<RuleProps, {}, "">;
40
45
  type Rule = ReturnType<typeof Rule>;
41
46
  export default Rule;