@spectric/ui 0.0.20 → 0.0.22
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.
- package/dist/components/Banner.d.ts +1 -1
- package/dist/components/dialog/dialog.d.ts +2 -1
- package/dist/components/pagination/pagination.d.ts +1 -1
- package/dist/components/query_bar/QueryBar.d.ts +31 -11
- package/dist/components/query_bar/dateTimePopup.d.ts +2 -0
- package/dist/components/query_bar/geojsonPopup.d.ts +2 -0
- package/dist/components/query_bar/querylanguage/kuery/functions/geospatial.d.ts +19 -0
- package/dist/components/query_bar/querylanguage/outputTypes/toCQL.d.ts +2 -1
- package/dist/components/query_bar/querylanguage/outputTypes/toMongo.d.ts +6 -1
- package/dist/components/symbols.d.ts +6 -0
- package/dist/components/table/cell.d.ts +2 -2
- package/dist/components/table/header.d.ts +2 -1
- package/dist/components/table/table.d.ts +14 -7
- package/dist/custom-elements.json +8 -8
- package/dist/index.d.ts +4 -0
- package/dist/index.es.js +4556 -2834
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +424 -248
- package/dist/index.umd.js.map +1 -1
- package/dist/style.css +1 -1
- package/package.json +6 -1
- package/src/components/Banner.ts +46 -31
- package/src/components/dialog/dialog.css.ts +29 -29
- package/src/components/dialog/dialog.ts +165 -135
- package/src/components/input.ts +49 -39
- package/src/components/pagination/pagination.ts +167 -113
- package/src/components/query_bar/QueryBar.ts +441 -185
- package/src/components/query_bar/dateTimePopup.ts +54 -0
- package/src/components/query_bar/geojsonPopup.ts +44 -0
- package/src/components/query_bar/querylanguage/kuery/ast/_generated_/kuery.js +1836 -2745
- package/src/components/query_bar/querylanguage/kuery/ast/ast.ts +15 -13
- package/src/components/query_bar/querylanguage/kuery/ast/kuery.peg +92 -126
- package/src/components/query_bar/querylanguage/kuery/functions/geospatial.ts +25 -0
- package/src/components/query_bar/querylanguage/kuery/functions/index.ts +9 -7
- package/src/components/query_bar/querylanguage/outputTypes/toCQL.ts +56 -34
- package/src/components/query_bar/querylanguage/outputTypes/toMongo.ts +46 -34
- package/src/components/symbols.ts +6 -0
- package/src/components/table/__tests__/table.spec.ts +143 -55
- package/src/components/table/cell.ts +188 -145
- package/src/components/table/header.ts +163 -152
- package/src/components/table/table.css +4 -2
- package/src/components/table/table.ts +415 -262
- package/src/components/table/virtualBody.ts +170 -115
- package/src/components/tooltip/popover.ts +263 -225
- package/src/stories/Dialog.stories.ts +59 -0
- package/src/stories/QueryBar.stories.ts +46 -37
- package/src/stories/fixtures/data.ts +195 -36
- package/src/stories/table.stories.ts +70 -22
|
@@ -1,177 +1,220 @@
|
|
|
1
|
-
import { html, LitElement, PropertyValues } from
|
|
2
|
-
import { customElement, property, query, state
|
|
3
|
-
import {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
1
|
+
import { html, LitElement, PropertyValues } from "lit";
|
|
2
|
+
import { customElement, property, query, state } from "lit/decorators.js";
|
|
3
|
+
import {
|
|
4
|
+
HTMLElementTagWithEvents,
|
|
5
|
+
ReactElementWithPropsAndEvents,
|
|
6
|
+
} from "../types";
|
|
7
|
+
export const TableCellElementTag = "spectric-table-cell";
|
|
8
|
+
import { ColumnSettings, DomRenderable, SpectricTableElement } from "./table";
|
|
9
|
+
import { cache } from "lit/directives/cache.js";
|
|
10
|
+
import { StyleInfo, styleMap } from "lit/directives/style-map.js";
|
|
8
11
|
|
|
9
12
|
interface CellProps<T> {
|
|
10
|
-
|
|
11
|
-
|
|
13
|
+
column: ColumnSettings<T>;
|
|
14
|
+
row: T;
|
|
12
15
|
}
|
|
13
16
|
|
|
14
17
|
export type FilterEvent<T> = {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
}
|
|
18
|
+
value?: T;
|
|
19
|
+
include: boolean;
|
|
20
|
+
column: ColumnSettings<T>;
|
|
21
|
+
row: T;
|
|
22
|
+
};
|
|
20
23
|
|
|
21
24
|
/**
|
|
22
25
|
* Pagination Element
|
|
23
26
|
*/
|
|
24
27
|
@customElement(TableCellElementTag)
|
|
25
28
|
export class TableCellElement<T> extends LitElement implements CellProps<T> {
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
@property({ type: Number, attribute: false })
|
|
30
|
-
index!: number;
|
|
31
|
-
@property({ type: Object, attribute: false })
|
|
32
|
-
column!: ColumnSettings<T>;
|
|
33
|
-
columns!: ColumnSettings<T>[];
|
|
34
|
-
table!: SpectricTableElement<T>
|
|
29
|
+
@property({ type: Object, attribute: false })
|
|
30
|
+
row!: T;
|
|
35
31
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
}
|
|
44
|
-
protected updated(_changedProperties: PropertyValues): void {
|
|
32
|
+
@property({ type: Number, attribute: false })
|
|
33
|
+
index!: number;
|
|
34
|
+
@property({ type: Object, attribute: false })
|
|
35
|
+
column!: ColumnSettings<T>;
|
|
36
|
+
columns!: ColumnSettings<T>[];
|
|
37
|
+
@property({ type: Object, attribute: false })
|
|
38
|
+
table!: SpectricTableElement<T>;
|
|
45
39
|
|
|
40
|
+
@state()
|
|
41
|
+
overflow: DomRenderable = "";
|
|
42
|
+
@query("td")
|
|
43
|
+
td!: HTMLTableCellElement;
|
|
44
|
+
styleRules: StyleInfo = { whiteSpace: "", width: "" };
|
|
45
|
+
protected createRenderRoot(): HTMLElement | DocumentFragment {
|
|
46
|
+
return this;
|
|
47
|
+
}
|
|
48
|
+
protected updated(_changedProperties: PropertyValues): void {}
|
|
49
|
+
_emitFilter(filter: FilterEvent<T>) {
|
|
50
|
+
this.dispatchEvent(
|
|
51
|
+
new CustomEvent<FilterEvent<T>>("filter", {
|
|
52
|
+
composed: true,
|
|
53
|
+
bubbles: true,
|
|
54
|
+
detail: filter,
|
|
55
|
+
})
|
|
56
|
+
);
|
|
57
|
+
}
|
|
58
|
+
_handleFilterOut = () => {
|
|
59
|
+
let value = undefined;
|
|
60
|
+
if (this.column.key && typeof this.row === "object") {
|
|
61
|
+
value = rowGetValue(this.row as Record<any, any>, this.column.key);
|
|
46
62
|
}
|
|
47
|
-
_emitFilter(
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
63
|
+
this._emitFilter({
|
|
64
|
+
include: false,
|
|
65
|
+
row: this.row,
|
|
66
|
+
value,
|
|
67
|
+
column: this.column,
|
|
68
|
+
});
|
|
69
|
+
};
|
|
70
|
+
_handleFilterFor = () => {
|
|
71
|
+
let value = undefined;
|
|
72
|
+
if (this.column.key && typeof this.row === "object") {
|
|
73
|
+
value = rowGetValue(this.row as Record<any, any>, this.column.key);
|
|
53
74
|
}
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
}
|
|
67
|
-
_handleFilterFor = () => {
|
|
68
|
-
let value = undefined;
|
|
69
|
-
if (this.column.key && typeof this.row === "object") {
|
|
70
|
-
value = rowGetValue(this.row as Record<any, any>, this.column.key)
|
|
71
|
-
}
|
|
72
|
-
this._emitFilter({
|
|
73
|
-
include: true,
|
|
74
|
-
row: this.row,
|
|
75
|
-
value,
|
|
76
|
-
column: this.column
|
|
77
|
-
})
|
|
75
|
+
this._emitFilter({
|
|
76
|
+
include: true,
|
|
77
|
+
row: this.row,
|
|
78
|
+
value,
|
|
79
|
+
column: this.column,
|
|
80
|
+
});
|
|
81
|
+
};
|
|
82
|
+
_displayOverflowTooltip = () => {
|
|
83
|
+
if (this.column.disableCellOverflowTooltip) {
|
|
84
|
+
this.overflow = null;
|
|
85
|
+
return;
|
|
78
86
|
}
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
}
|
|
87
|
+
let div = this.querySelector("div.cell-contents");
|
|
88
|
+
let span = this.querySelector("span");
|
|
89
|
+
if (div && span) {
|
|
90
|
+
let spanBounds = span.getBoundingClientRect();
|
|
91
|
+
let divBounds = div.getBoundingClientRect();
|
|
92
|
+
if (
|
|
93
|
+
spanBounds.width * spanBounds.height >
|
|
94
|
+
divBounds.width * divBounds.height
|
|
95
|
+
) {
|
|
96
|
+
console.log(
|
|
97
|
+
"We need to show a tooltip with the content because we are overflowing"
|
|
98
|
+
);
|
|
99
|
+
this.overflow = this.getRenderedValue();
|
|
100
|
+
this.updateComplete.then(() => {
|
|
101
|
+
let tooltip = this.querySelector("spectric-tooltip");
|
|
102
|
+
if (tooltip) {
|
|
103
|
+
tooltip.showToolTip();
|
|
104
|
+
}
|
|
105
|
+
});
|
|
106
|
+
} else {
|
|
107
|
+
this.overflow = "";
|
|
108
|
+
}
|
|
98
109
|
}
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
return rendered
|
|
110
|
+
};
|
|
111
|
+
getRenderedValue() {
|
|
112
|
+
let rendered;
|
|
113
|
+
if (this.column.render) {
|
|
114
|
+
rendered = this.column.render(this.row, this.index, this.table);
|
|
115
|
+
} else if (this.column.key && typeof this.row === "object") {
|
|
116
|
+
rendered = rowGetValue(this.row as any, this.column.key);
|
|
117
|
+
} else {
|
|
118
|
+
rendered = html`error`;
|
|
109
119
|
}
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
let filterButtons = cache(this.column.filterable
|
|
118
|
-
? html`<div class="table-cell-actions">
|
|
119
|
-
<spectric-button @click=${this._handleFilterOut} size="tiny" variant="text" icon tooltip="Filter Out Value">-</spectric-button>
|
|
120
|
-
<spectric-button @click=${this._handleFilterFor} size="tiny" variant="text" icon tooltip="Filter For Value">+</spectric-button></div>`
|
|
121
|
-
: null
|
|
122
|
-
)
|
|
123
|
-
this.styleRules = {
|
|
124
|
-
width: this.column.width ? this.column.width + "px" : null,
|
|
125
|
-
whiteSpace: this.column.whiteSpace || null
|
|
126
|
-
}
|
|
127
|
-
return html`
|
|
128
|
-
<td style=${styleMap(this.styleRules)} @mouseenter=${this._displayTooltip}>
|
|
129
|
-
${filterButtons}
|
|
130
|
-
<div class=${classes.join(" ")}>${this.overflow ? html`<spectric-tooltip .text=${this.overflow}></spectric-tooltip>` : null}<span>${rendered}</span></div>
|
|
131
|
-
</td>
|
|
132
|
-
`
|
|
120
|
+
return rendered;
|
|
121
|
+
}
|
|
122
|
+
protected render(): unknown {
|
|
123
|
+
let rendered = this.getRenderedValue();
|
|
124
|
+
let classes = ["cell-contents"];
|
|
125
|
+
if (this.column.filterable) {
|
|
126
|
+
classes.push("filterable");
|
|
133
127
|
}
|
|
134
128
|
|
|
129
|
+
let filterButtons = cache(
|
|
130
|
+
this.column.filterable
|
|
131
|
+
? html`<div class="table-cell-actions">
|
|
132
|
+
<spectric-button
|
|
133
|
+
@click=${this._handleFilterOut}
|
|
134
|
+
size="tiny"
|
|
135
|
+
variant="text"
|
|
136
|
+
icon
|
|
137
|
+
tooltip="Filter Out Value"
|
|
138
|
+
>-</spectric-button
|
|
139
|
+
>
|
|
140
|
+
<spectric-button
|
|
141
|
+
@click=${this._handleFilterFor}
|
|
142
|
+
size="tiny"
|
|
143
|
+
variant="text"
|
|
144
|
+
icon
|
|
145
|
+
tooltip="Filter For Value"
|
|
146
|
+
>+</spectric-button
|
|
147
|
+
>
|
|
148
|
+
</div>`
|
|
149
|
+
: null
|
|
150
|
+
);
|
|
151
|
+
this.styleRules = {
|
|
152
|
+
width: this.column.width ? this.column.width + "px" : null,
|
|
153
|
+
whiteSpace: this.column.whiteSpace || null,
|
|
154
|
+
};
|
|
155
|
+
return html`
|
|
156
|
+
<td
|
|
157
|
+
style=${styleMap(this.styleRules)}
|
|
158
|
+
@mouseenter=${this._displayOverflowTooltip}
|
|
159
|
+
>
|
|
160
|
+
${filterButtons}
|
|
161
|
+
<div class=${classes.join(" ")}>
|
|
162
|
+
${this.overflow
|
|
163
|
+
? html`<spectric-tooltip .text=${this.overflow}></spectric-tooltip>`
|
|
164
|
+
: null}<span>${rendered}</span>
|
|
165
|
+
</div>
|
|
166
|
+
</td>
|
|
167
|
+
`;
|
|
168
|
+
}
|
|
135
169
|
}
|
|
136
170
|
|
|
137
171
|
interface TableBodyEvents {
|
|
138
|
-
|
|
172
|
+
filter: (event: CustomEvent<ColumnSettings<any>>) => void; //TODO filter events
|
|
139
173
|
}
|
|
140
174
|
|
|
141
175
|
declare global {
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
176
|
+
interface HTMLElementTagNameMap {
|
|
177
|
+
[TableCellElementTag]: HTMLElementTagWithEvents<
|
|
178
|
+
TableCellElement<any>,
|
|
179
|
+
TableBodyEvents
|
|
180
|
+
>;
|
|
181
|
+
}
|
|
182
|
+
namespace JSX {
|
|
183
|
+
interface IntrinsicElements {
|
|
184
|
+
/**
|
|
185
|
+
* @see {@link DialogElement}
|
|
186
|
+
*/
|
|
187
|
+
[TableCellElementTag]: ReactElementWithPropsAndEvents<
|
|
188
|
+
TableCellElement<any>,
|
|
189
|
+
CellProps<any>,
|
|
190
|
+
TableBodyEvents
|
|
191
|
+
>;
|
|
145
192
|
}
|
|
193
|
+
}
|
|
194
|
+
namespace React {
|
|
146
195
|
namespace JSX {
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
/**
|
|
158
|
-
* @see {@link DialogElement}
|
|
159
|
-
*/
|
|
160
|
-
[TableCellElementTag]: ReactElementWithPropsAndEvents<TableCellElement<any>, CellProps<any>, TableBodyEvents>
|
|
161
|
-
}
|
|
162
|
-
}
|
|
196
|
+
interface IntrinsicElements {
|
|
197
|
+
/**
|
|
198
|
+
* @see {@link DialogElement}
|
|
199
|
+
*/
|
|
200
|
+
[TableCellElementTag]: ReactElementWithPropsAndEvents<
|
|
201
|
+
TableCellElement<any>,
|
|
202
|
+
CellProps<any>,
|
|
203
|
+
TableBodyEvents
|
|
204
|
+
>;
|
|
205
|
+
}
|
|
163
206
|
}
|
|
207
|
+
}
|
|
164
208
|
}
|
|
165
209
|
|
|
166
|
-
|
|
167
210
|
export const rowGetValue = (context: Record<string, any>, key: string) => {
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
}
|
|
211
|
+
let path = key.split(".");
|
|
212
|
+
let value = context[path[0]];
|
|
213
|
+
if (value === null || value === undefined) {
|
|
214
|
+
return value;
|
|
215
|
+
}
|
|
216
|
+
if (path.length > 1) {
|
|
217
|
+
value = rowGetValue(value, path.slice(1).join("."));
|
|
218
|
+
}
|
|
219
|
+
return value;
|
|
220
|
+
};
|