cx 24.4.5 → 24.4.6

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.
@@ -1,148 +1,150 @@
1
- import { Widget, VDOM } from "../ui/Widget";
2
- import { HtmlElement } from "../widgets/HtmlElement";
3
- import { PureContainer } from "../ui/PureContainer";
4
- import { getShape } from "./shapes";
5
- import { isUndefined } from "../util/isUndefined";
6
- import { isArray } from "../util/isArray";
7
- import { withHoverSync } from "../ui/HoverSync";
8
-
9
- export class Legend extends HtmlElement {
10
- prepareData(context, instance) {
11
- let { data } = instance;
12
- data.stateMods = Object.assign(data.stateMods || {}, {
13
- vertical: this.vertical,
14
- });
15
- super.prepareData(context, instance);
16
- }
17
-
18
- declareData() {
19
- super.declareData(...arguments, {
20
- shape: undefined,
21
- });
22
- }
23
-
24
- isValidHtmlAttribute(attrName) {
25
- switch (attrName) {
26
- case "shapeSize":
27
- case "svgSize":
28
- return false;
29
-
30
- default:
31
- return super.isValidHtmlAttribute(attrName);
32
- }
33
- }
34
-
35
- explore(context, instance) {
36
- if (!context.legends) context.legends = {};
37
-
38
- instance.legends = context.legends;
39
-
40
- context.addLegendEntry = (legendName, entry) => {
41
- //case when all legends are scoped and new entry is added outside the scope
42
- if (!context.legends) return;
43
-
44
- let legend = context.legends[legendName];
45
- if (!legend)
46
- legend = context.legends[legendName] = {
47
- entries: [],
48
- names: {},
49
- };
50
-
51
- if (!legend.names[entry.name]) {
52
- legend.entries.push(entry);
53
- legend.names[entry.name] = entry;
54
- }
55
- };
56
-
57
- super.explore(context, instance);
58
- }
59
-
60
- renderChildren(context, instance) {
61
- const CSS = this.CSS;
62
-
63
- let entries = instance.legends[this.name] && instance.legends[this.name].entries,
64
- list;
65
-
66
- if (isArray(entries) && entries.length > 0) {
67
- list = (
68
- <div key="wrap" className={CSS.element(this.baseClass, "wrap")}>
69
- {entries.map((e, i) =>
70
- withHoverSync(i, e.hoverSync, e.hoverChannel, e.hoverId, ({ onMouseMove, onMouseLeave, hover }) => (
71
- <div
72
- key={i}
73
- className={CSS.element(this.baseClass, "entry", {
74
- "color-root": true,
75
- hover,
76
- disabled: e.disabled,
77
- selected: e.selected,
78
- })}
79
- onClick={e.onClick}
80
- onMouseMove={onMouseMove}
81
- onMouseLeave={onMouseLeave}
82
- >
83
- {this.renderShape(e, instance.data.shape)}
84
- {e.name}
85
- </div>
86
- ))
87
- )}
88
- </div>
89
- );
90
- }
91
-
92
- return [list, super.renderChildren(context, instance)];
93
- }
94
-
95
- renderShape(entry, legendEntriesShape) {
96
- const className = this.CSS.element(this.baseClass, "shape", {
97
- [`color-${entry.colorIndex}`]: entry.colorIndex != null && (isUndefined(entry.active) || entry.active),
98
- });
99
- const shape = getShape(legendEntriesShape || entry.shape || "square");
100
-
101
- return (
102
- <svg
103
- className={this.CSS.element(this.baseClass, "svg")}
104
- style={{
105
- width: `${this.svgSize}px`,
106
- height: `${this.svgSize}px`,
107
- marginTop: `${-this.svgSize / 2}px`,
108
- }}
109
- >
110
- {shape(this.svgSize / 2, this.svgSize / 2, entry.shapeSize || this.shapeSize, {
111
- style: entry.style,
112
- className: className,
113
- })}
114
- </svg>
115
- );
116
- }
117
- }
118
-
119
- Legend.prototype.name = "legend";
120
- Legend.prototype.baseClass = "legend";
121
- Legend.prototype.vertical = false;
122
- Legend.prototype.memoize = false;
123
- Legend.prototype.shapeSize = 18;
124
- Legend.prototype.shape = null;
125
- Legend.prototype.svgSize = 20;
126
-
127
- Widget.alias("legend", Legend);
128
-
129
- Legend.Scope = class extends PureContainer {
130
- explore(context, instance) {
131
- context.push("legends", (instance.legends = {}));
132
- super.explore(context, instance);
133
- }
134
-
135
- exploreCleanup(context, instance) {
136
- context.pop("legends");
137
- }
138
-
139
- prepare(context, instance) {
140
- context.push("legends", instance.legends);
141
- }
142
-
143
- prepareCleanup(context, instance) {
144
- context.pop("legends");
145
- }
146
- };
147
-
148
- export const LegendScope = Legend.Scope;
1
+ import { Widget, VDOM } from "../ui/Widget";
2
+ import { HtmlElement } from "../widgets/HtmlElement";
3
+ import { PureContainer } from "../ui/PureContainer";
4
+ import { getShape } from "./shapes";
5
+ import { isUndefined } from "../util/isUndefined";
6
+ import { isArray } from "../util/isArray";
7
+ import { withHoverSync } from "../ui/HoverSync";
8
+
9
+ export class Legend extends HtmlElement {
10
+ prepareData(context, instance) {
11
+ let { data } = instance;
12
+ data.stateMods = Object.assign(data.stateMods || {}, {
13
+ vertical: this.vertical,
14
+ });
15
+ super.prepareData(context, instance);
16
+ }
17
+
18
+ declareData() {
19
+ super.declareData(...arguments, {
20
+ shape: undefined,
21
+ });
22
+ }
23
+
24
+ isValidHtmlAttribute(attrName) {
25
+ switch (attrName) {
26
+ case "shapeSize":
27
+ case "svgSize":
28
+ return false;
29
+
30
+ default:
31
+ return super.isValidHtmlAttribute(attrName);
32
+ }
33
+ }
34
+
35
+ explore(context, instance) {
36
+ if (!context.legends) context.legends = {};
37
+
38
+ instance.legends = context.legends;
39
+
40
+ context.addLegendEntry = (legendName, entry) => {
41
+ if (!legendName) return;
42
+
43
+ //case when all legends are scoped and new entry is added outside the scope
44
+ if (!context.legends) return;
45
+
46
+ let legend = context.legends[legendName];
47
+ if (!legend)
48
+ legend = context.legends[legendName] = {
49
+ entries: [],
50
+ names: {},
51
+ };
52
+
53
+ if (!legend.names[entry.name]) {
54
+ legend.entries.push(entry);
55
+ legend.names[entry.name] = entry;
56
+ }
57
+ };
58
+
59
+ super.explore(context, instance);
60
+ }
61
+
62
+ renderChildren(context, instance) {
63
+ const CSS = this.CSS;
64
+
65
+ let entries = instance.legends[this.name] && instance.legends[this.name].entries,
66
+ list;
67
+
68
+ if (isArray(entries) && entries.length > 0) {
69
+ list = (
70
+ <div key="wrap" className={CSS.element(this.baseClass, "wrap")}>
71
+ {entries.map((e, i) =>
72
+ withHoverSync(i, e.hoverSync, e.hoverChannel, e.hoverId, ({ onMouseMove, onMouseLeave, hover }) => (
73
+ <div
74
+ key={i}
75
+ className={CSS.element(this.baseClass, "entry", {
76
+ "color-root": true,
77
+ hover,
78
+ disabled: e.disabled,
79
+ selected: e.selected,
80
+ })}
81
+ onClick={e.onClick}
82
+ onMouseMove={onMouseMove}
83
+ onMouseLeave={onMouseLeave}
84
+ >
85
+ {this.renderShape(e, instance.data.shape)}
86
+ {e.name}
87
+ </div>
88
+ )),
89
+ )}
90
+ </div>
91
+ );
92
+ }
93
+
94
+ return [list, super.renderChildren(context, instance)];
95
+ }
96
+
97
+ renderShape(entry, legendEntriesShape) {
98
+ const className = this.CSS.element(this.baseClass, "shape", {
99
+ [`color-${entry.colorIndex}`]: entry.colorIndex != null && (isUndefined(entry.active) || entry.active),
100
+ });
101
+ const shape = getShape(legendEntriesShape || entry.shape || "square");
102
+
103
+ return (
104
+ <svg
105
+ className={this.CSS.element(this.baseClass, "svg")}
106
+ style={{
107
+ width: `${this.svgSize}px`,
108
+ height: `${this.svgSize}px`,
109
+ marginTop: `${-this.svgSize / 2}px`,
110
+ }}
111
+ >
112
+ {shape(this.svgSize / 2, this.svgSize / 2, entry.shapeSize || this.shapeSize, {
113
+ style: entry.style,
114
+ className: className,
115
+ })}
116
+ </svg>
117
+ );
118
+ }
119
+ }
120
+
121
+ Legend.prototype.name = "legend";
122
+ Legend.prototype.baseClass = "legend";
123
+ Legend.prototype.vertical = false;
124
+ Legend.prototype.memoize = false;
125
+ Legend.prototype.shapeSize = 18;
126
+ Legend.prototype.shape = null;
127
+ Legend.prototype.svgSize = 20;
128
+
129
+ Widget.alias("legend", Legend);
130
+
131
+ Legend.Scope = class extends PureContainer {
132
+ explore(context, instance) {
133
+ context.push("legends", (instance.legends = {}));
134
+ super.explore(context, instance);
135
+ }
136
+
137
+ exploreCleanup(context, instance) {
138
+ context.pop("legends");
139
+ }
140
+
141
+ prepare(context, instance) {
142
+ context.push("legends", instance.legends);
143
+ }
144
+
145
+ prepareCleanup(context, instance) {
146
+ context.pop("legends");
147
+ }
148
+ };
149
+
150
+ export const LegendScope = Legend.Scope;
@@ -1,92 +1,92 @@
1
- import * as Cx from "../core";
2
-
3
- interface LineGraphProps extends Cx.WidgetProps {
4
- /**
5
- * Data for the graph. Each entry should be an object with at least two properties
6
- * whose names should match the `xField` and `yField` values.
7
- */
8
- data?: Cx.RecordsProp;
9
-
10
- /** Index of a color from the standard palette of colors. 0-15. */
11
- colorIndex?: Cx.NumberProp;
12
-
13
- /** Used to automatically assign a color based on the `name` and the contextual `ColorMap` widget. */
14
- colorMap?: Cx.StringProp;
15
-
16
- /** Name used to resolve the color. If not provided, `name` is used instead. */
17
- colorName?: Cx.StringProp;
18
-
19
- /**
20
- * Additional CSS classes to be applied to the field.
21
- * If an object is provided, all keys with a "truthy" value will be added to the CSS class list.
22
- */
23
- class?: Cx.ClassProp;
24
-
25
- /**
26
- * Additional CSS classes to be applied to the field.
27
- * If an object is provided, all keys with a "truthy" value will be added to the CSS class list.
28
- */
29
- className?: Cx.ClassProp;
30
-
31
- /** Additional styles to be applied to the line element. */
32
- lineStyle?: Cx.StyleProp;
33
-
34
- /** Additional styles to be applied to the area below the line. */
35
- areaStyle?: Cx.StyleProp;
36
-
37
- /** Area switch. Default value is `false`. */
38
- area?: Cx.BooleanProp;
39
-
40
- /** Line switch. By default, the line is shown. Set to `false` to hide the line and draw only the area. */
41
- line?: Cx.BooleanProp;
42
-
43
- /** Base value used for area charts. Default value is `0`. */
44
- y0?: Cx.NumberProp;
45
-
46
- /** Name of the item as it will appear in the legend. */
47
- name?: Cx.StringProp;
48
-
49
- /** Used to indicate if an item is active or not. Inactive items are shown only in the legend. */
50
- active?: Cx.BooleanProp;
51
-
52
- /** Name of the stack. If multiple stacks are used, each should have a unique name. Default value is `stack`. */
53
- stack?: Cx.StringProp;
54
-
55
- /** Indicate that columns should be stacked on top of the other columns. Default value is `false`. */
56
- stacked?: Cx.BooleanProp;
57
-
58
- /**
59
- * Name of the horizontal axis. The value should match one of the horizontal axes set
60
- * in the `axes` configuration of the parent `Chart` component. Default value is `x`.
61
- */
62
- xAxis?: string;
63
-
64
- /**
65
- * Name of the vertical axis. The value should match one of the vertical axes set
66
- * in the `axes` configuration if the parent `Chart` component. Default value is `y`.
67
- */
68
- yAxis?: string;
69
-
70
- /** Name of the property which holds the x value. Default value is `x`. */
71
- xField?: string;
72
-
73
- /** Name of the property which holds the y value. Default value is `y`. */
74
- yField?: string;
75
-
76
- /** Base CSS class to be applied to the element. Defaults to `linegraph`. */
77
- baseClass?: string;
78
-
79
- /** Name of the property which holds the y0 value. Default value is `false`, which means y0 value is not read from the data array. */
80
- y0Field?: string | false;
81
-
82
- /** Name of the legend to be used. Default is `legend`. */
83
- legend?: string;
84
-
85
- legendAction?: string;
86
- legendShape?: string;
87
-
88
- /** Set to true to avoid forcing the vertical axis to accommodate y0 values. */
89
- hiddenBase?: boolean;
90
- }
91
-
92
- export class LineGraph extends Cx.Widget<LineGraphProps> {}
1
+ import * as Cx from "../core";
2
+
3
+ interface LineGraphProps extends Cx.WidgetProps {
4
+ /**
5
+ * Data for the graph. Each entry should be an object with at least two properties
6
+ * whose names should match the `xField` and `yField` values.
7
+ */
8
+ data?: Cx.RecordsProp;
9
+
10
+ /** Index of a color from the standard palette of colors. 0-15. */
11
+ colorIndex?: Cx.NumberProp;
12
+
13
+ /** Used to automatically assign a color based on the `name` and the contextual `ColorMap` widget. */
14
+ colorMap?: Cx.StringProp;
15
+
16
+ /** Name used to resolve the color. If not provided, `name` is used instead. */
17
+ colorName?: Cx.StringProp;
18
+
19
+ /**
20
+ * Additional CSS classes to be applied to the field.
21
+ * If an object is provided, all keys with a "truthy" value will be added to the CSS class list.
22
+ */
23
+ class?: Cx.ClassProp;
24
+
25
+ /**
26
+ * Additional CSS classes to be applied to the field.
27
+ * If an object is provided, all keys with a "truthy" value will be added to the CSS class list.
28
+ */
29
+ className?: Cx.ClassProp;
30
+
31
+ /** Additional styles to be applied to the line element. */
32
+ lineStyle?: Cx.StyleProp;
33
+
34
+ /** Additional styles to be applied to the area below the line. */
35
+ areaStyle?: Cx.StyleProp;
36
+
37
+ /** Area switch. Default value is `false`. */
38
+ area?: Cx.BooleanProp;
39
+
40
+ /** Line switch. By default, the line is shown. Set to `false` to hide the line and draw only the area. */
41
+ line?: Cx.BooleanProp;
42
+
43
+ /** Base value used for area charts. Default value is `0`. */
44
+ y0?: Cx.NumberProp;
45
+
46
+ /** Name of the item as it will appear in the legend. */
47
+ name?: Cx.StringProp;
48
+
49
+ /** Used to indicate if an item is active or not. Inactive items are shown only in the legend. */
50
+ active?: Cx.BooleanProp;
51
+
52
+ /** Name of the stack. If multiple stacks are used, each should have a unique name. Default value is `stack`. */
53
+ stack?: Cx.StringProp;
54
+
55
+ /** Indicate that columns should be stacked on top of the other columns. Default value is `false`. */
56
+ stacked?: Cx.BooleanProp;
57
+
58
+ /**
59
+ * Name of the horizontal axis. The value should match one of the horizontal axes set
60
+ * in the `axes` configuration of the parent `Chart` component. Default value is `x`.
61
+ */
62
+ xAxis?: string;
63
+
64
+ /**
65
+ * Name of the vertical axis. The value should match one of the vertical axes set
66
+ * in the `axes` configuration if the parent `Chart` component. Default value is `y`.
67
+ */
68
+ yAxis?: string;
69
+
70
+ /** Name of the property which holds the x value. Default value is `x`. */
71
+ xField?: string;
72
+
73
+ /** Name of the property which holds the y value. Default value is `y`. */
74
+ yField?: string;
75
+
76
+ /** Base CSS class to be applied to the element. Defaults to `linegraph`. */
77
+ baseClass?: string;
78
+
79
+ /** Name of the property which holds the y0 value. Default value is `false`, which means y0 value is not read from the data array. */
80
+ y0Field?: string | false;
81
+
82
+ /** Name of the legend to be used. Default is `legend`. Set to `false` to hide the legend entry. */
83
+ legend?: string | false;
84
+
85
+ legendAction?: string;
86
+ legendShape?: string;
87
+
88
+ /** Set to true to avoid forcing the vertical axis to accommodate y0 values. */
89
+ hiddenBase?: boolean;
90
+ }
91
+
92
+ export class LineGraph extends Cx.Widget<LineGraphProps> {}
@@ -1,71 +1,71 @@
1
- import { VDOM } from "../ui/Widget";
2
- import { BoundedObject } from "../svg/BoundedObject";
3
- import { Rect } from "../svg/util/Rect";
4
- import { parseStyle } from "../util/parseStyle";
5
-
6
- export class PieLabel extends BoundedObject {
7
- init() {
8
- this.lineStyle = parseStyle(this.lineStyle);
9
- super.init();
10
- }
11
-
12
- declareData(...args) {
13
- super.declareData(...args, {
14
- distance: undefined,
15
- lineStyle: { structured: true },
16
- lineStroke: undefined,
17
- lineClass: { structured: true },
18
- lineColorIndex: undefined,
19
- });
20
- }
21
-
22
- calculateBounds(context, instance) {
23
- var { data } = instance;
24
- var bounds = Rect.add(Rect.add(Rect.multiply(instance.parentRect, data.anchors), data.offset), data.margin);
25
- instance.originalBounds = bounds;
26
- instance.actualBounds = context.placePieLabel(bounds, data.distance);
27
- return new Rect({ t: 0, r: bounds.width(), b: bounds.height(), l: 0 });
28
- }
29
-
30
- prepare(context, instance) {
31
- super.prepare(context, instance);
32
- if (!context.registerPieLabel)
33
- throw new Error("PieLabel components are allowed only within PieLabelsContainer components.");
34
- let right = instance.parentRect.r > instance.parentRect.l;
35
- context.push("textDirection", right ? "right" : "left");
36
- context.registerPieLabel(instance);
37
- }
38
-
39
- prepareCleanup(context, instance) {
40
- context.pop("textDirection");
41
- }
42
-
43
- render(context, instance, key) {
44
- let { originalBounds, actualBounds, data } = instance;
45
-
46
- return (
47
- <g key={key} className={data.classNames}>
48
- <line
49
- className={this.CSS.element(
50
- this.baseClass,
51
- "line",
52
- data.lineColorIndex != null && "color-" + data.lineColorIndex
53
- )}
54
- x1={actualBounds.l < originalBounds.l ? actualBounds.r : actualBounds.l}
55
- y1={(actualBounds.t + actualBounds.b) / 2}
56
- x2={(originalBounds.l + originalBounds.r) / 2}
57
- y2={(originalBounds.t + originalBounds.b) / 2}
58
- stroke={data.lineStroke}
59
- style={data.lineStyle}
60
- />
61
- <g transform={`translate(${instance.actualBounds.l} ${instance.actualBounds.t})`}>
62
- {this.renderChildren(context, instance)}
63
- </g>
64
- </g>
65
- );
66
- }
67
- }
68
-
69
- PieLabel.prototype.distance = 100;
70
- PieLabel.prototype.baseClass = "pielabel";
71
- PieLabel.prototype.styled = true;
1
+ import { VDOM } from "../ui/Widget";
2
+ import { BoundedObject } from "../svg/BoundedObject";
3
+ import { Rect } from "../svg/util/Rect";
4
+ import { parseStyle } from "../util/parseStyle";
5
+
6
+ export class PieLabel extends BoundedObject {
7
+ init() {
8
+ this.lineStyle = parseStyle(this.lineStyle);
9
+ super.init();
10
+ }
11
+
12
+ declareData(...args) {
13
+ super.declareData(...args, {
14
+ distance: undefined,
15
+ lineStyle: { structured: true },
16
+ lineStroke: undefined,
17
+ lineClass: { structured: true },
18
+ lineColorIndex: undefined,
19
+ });
20
+ }
21
+
22
+ calculateBounds(context, instance) {
23
+ var { data } = instance;
24
+ var bounds = Rect.add(Rect.add(Rect.multiply(instance.parentRect, data.anchors), data.offset), data.margin);
25
+ instance.originalBounds = bounds;
26
+ instance.actualBounds = context.placePieLabel(bounds, data.distance);
27
+ return new Rect({ t: 0, r: bounds.width(), b: bounds.height(), l: 0 });
28
+ }
29
+
30
+ prepare(context, instance) {
31
+ super.prepare(context, instance);
32
+ if (!context.registerPieLabel)
33
+ throw new Error("PieLabel components are allowed only within PieLabelsContainer components.");
34
+ let right = instance.parentRect.r > instance.parentRect.l;
35
+ context.push("textDirection", right ? "right" : "left");
36
+ context.registerPieLabel(instance);
37
+ }
38
+
39
+ prepareCleanup(context, instance) {
40
+ context.pop("textDirection");
41
+ }
42
+
43
+ render(context, instance, key) {
44
+ let { originalBounds, actualBounds, data } = instance;
45
+
46
+ return (
47
+ <g key={key} className={data.classNames}>
48
+ <line
49
+ className={this.CSS.element(
50
+ this.baseClass,
51
+ "line",
52
+ data.lineColorIndex != null && "color-" + data.lineColorIndex
53
+ )}
54
+ x1={actualBounds.l < originalBounds.l ? actualBounds.r : actualBounds.l}
55
+ y1={(actualBounds.t + actualBounds.b) / 2}
56
+ x2={(originalBounds.l + originalBounds.r) / 2}
57
+ y2={(originalBounds.t + originalBounds.b) / 2}
58
+ stroke={data.lineStroke}
59
+ style={data.lineStyle}
60
+ />
61
+ <g transform={`translate(${instance.actualBounds.l} ${instance.actualBounds.t})`}>
62
+ {this.renderChildren(context, instance)}
63
+ </g>
64
+ </g>
65
+ );
66
+ }
67
+ }
68
+
69
+ PieLabel.prototype.distance = 100;
70
+ PieLabel.prototype.baseClass = "pielabel";
71
+ PieLabel.prototype.styled = true;