@xeplr/ui-table 1.0.1 → 1.0.3

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.
@@ -21,6 +21,9 @@
21
21
  /* ── Toolbar ── */
22
22
  .xeplr-table-toolbar {
23
23
  display: flex;
24
+ /* Centred so arbitrary host content in the leading slot sits on the same
25
+ line as the buttons instead of stretching to the row's full height. */
26
+ align-items: center;
24
27
  gap: 8px;
25
28
  padding: 8px 12px;
26
29
  border-bottom: 1px solid var(--xeplr-border-primary, #2a2a4a);
@@ -54,17 +57,149 @@
54
57
  table-layout: auto;
55
58
  }
56
59
 
60
+ /* ── Content sizing (columnSizing="content") ──
61
+ Everything here is scoped to .xeplr-table-sized, so the default fill-the-
62
+ container behaviour is untouched for tables that don't opt in.
63
+
64
+ `fixed` is what makes the measured widths binding — under `auto` the
65
+ browser re-negotiates them against the content and the colgroup becomes a
66
+ suggestion. Wrapping is the trade for that: a column short of its natural
67
+ width has to put the overflow somewhere, and wrapped text stays readable
68
+ where a truncated cell just hides data. `anywhere` is the last resort for a
69
+ single unbreakable token wider than its whole column. */
70
+ .xeplr-table-sized {
71
+ table-layout: fixed;
72
+ }
73
+
74
+ .xeplr-table-sized .xeplr-table-th {
75
+ white-space: normal;
76
+ }
77
+
78
+ .xeplr-table-sized .xeplr-table-td,
79
+ .xeplr-table-sized .xeplr-table-header-label {
80
+ overflow-wrap: anywhere;
81
+ }
82
+
83
+ /* ── Styled tables (cellStyle) ──
84
+ Separated borders, on purpose. Under the default `collapse`, adjacent cells
85
+ share one border and CSS picks the winner by width, then style — so a thin
86
+ border set on one cell next to a thicker neighbour never appears at all.
87
+ Per-side control would be dishonest: you'd set it, see nothing, and
88
+ reasonably call it broken.
89
+
90
+ `separate` with zero spacing renders identically to today for the default
91
+ borders (only bottoms are set, and horizontal neighbours don't share those),
92
+ but every border a user sets now actually draws. The trade is that two
93
+ adjacent cells each carrying a border on the SAME shared edge will show 2px
94
+ where collapse would have merged to 1px — style one side rather than all
95
+ four and it doesn't arise. */
96
+ .xeplr-table-styled {
97
+ border-collapse: separate;
98
+ border-spacing: 0;
99
+ }
100
+
101
+ /* ── Cell zoom (cellZoom) ──
102
+ Sized in em so it scales off whatever font the cell itself is using: a
103
+ compact theme's 11px cell zooms proportionally, rather than to some fixed
104
+ size that would be a huge jump from one table and barely a change in
105
+ another.
106
+
107
+ No cursor change on a zoomable cell, deliberately: a magnifier cursor
108
+ obscures the very text you're trying to aim at, which is backwards for a
109
+ reading aid. The plain arrow stays, so you can point precisely. */
110
+ .xeplr-table-cell-zoom {
111
+ position: fixed;
112
+ z-index: 300;
113
+ max-width: min(560px, 90vw);
114
+ max-height: 60vh;
115
+ overflow: auto;
116
+ padding: 12px 16px;
117
+ border-radius: 10px;
118
+ background: var(--xeplr-bg-secondary, #16162a);
119
+ border: 1px solid var(--xeplr-border-primary, #2a2a4a);
120
+ box-shadow: 0 12px 32px -8px rgba(0, 0, 0, .45);
121
+ /* Selectable on purpose — reading it is the point, and copying it out is
122
+ the next thing anyone wants to do. */
123
+ user-select: text;
124
+ }
125
+
126
+ .xeplr-table-cell-zoom:focus {
127
+ outline: none;
128
+ }
129
+
130
+ .xeplr-table-cell-zoom-label {
131
+ font-size: .75em;
132
+ text-transform: uppercase;
133
+ letter-spacing: .05em;
134
+ opacity: .6;
135
+ margin-bottom: 6px;
136
+ }
137
+
138
+ .xeplr-table-cell-zoom-value {
139
+ font-size: 1.9em;
140
+ line-height: 1.35;
141
+ overflow-wrap: anywhere;
142
+ }
143
+
57
144
  /* ── Header ── */
58
145
  .xeplr-table-th {
59
146
  padding: 0;
60
147
  background: var(--xeplr-bg-secondary, #16162a);
61
148
  border-bottom: 2px solid var(--xeplr-border-primary, #2a2a4a);
149
+ /* Thin by default between every header cell — a grouped table (a pivoted
150
+ date over several measures) reads as one solid block without SOME line
151
+ between its own columns, not just at the group's outer edge. */
152
+ border-right: 1px solid var(--xeplr-border-secondary, #2a2a4a);
62
153
  text-align: left;
63
154
  font-weight: 600;
64
155
  white-space: nowrap;
65
156
  color: var(--xeplr-text-secondary, inherit);
66
157
  }
67
158
 
159
+ /* A darkened version of the SAME light-gray line already drawn everywhere
160
+ else in this table (--xeplr-border-secondary), not a separate color —
161
+ the group boundary is meant to read as "more of this table's own grid,"
162
+ not as a different, unrelated UI element sitting on top of it. */
163
+ .xeplr-table-th-group,
164
+ .xeplr-table-th-group-start,
165
+ .xeplr-table-th-group-end,
166
+ .xeplr-table-td-group-start,
167
+ .xeplr-table-td-group-end {
168
+ --xeplr-table-group-border: #f1eaea;
169
+ }
170
+
171
+ /* The spanning cell itself (the date, not the measures under it) — centered
172
+ over what it covers, the way a merged cell reads in Excel. Top border
173
+ closes the frame's roof. */
174
+ .xeplr-table-th-group .xeplr-table-header-cell {
175
+ justify-content: center;
176
+ }
177
+ .xeplr-table-th-group {
178
+ text-align: center;
179
+ border-top: 2px solid var(--xeplr-table-group-border);
180
+ }
181
+
182
+ /* Every header cell in a row that ISN'T the last one gets the divider under
183
+ it — a real group (the date) AND a plain column beside it (Category Name)
184
+ alike — so the line drawn under "2025-05-01" runs the full width of the
185
+ header instead of stopping wherever a non-grouped column happens to sit. */
186
+ .xeplr-table-th-row-divider {
187
+ border-bottom: 1px solid var(--xeplr-border-secondary, #ccc);
188
+ }
189
+
190
+ /* The frame's sides — one continuous line from the group's own header cell,
191
+ down through the measure-label row, down through every data row, so the
192
+ whole block reads as one unit instead of columns that happen to sit next
193
+ to each other. */
194
+ .xeplr-table-th-group-start,
195
+ .xeplr-table-td-group-start {
196
+ border-left: 2px solid var(--xeplr-table-group-border);
197
+ }
198
+ .xeplr-table-th-group-end,
199
+ .xeplr-table-td-group-end {
200
+ border-right: 2px solid var(--xeplr-table-group-border);
201
+ }
202
+
68
203
  .xeplr-table-header-cell {
69
204
  display: flex;
70
205
  align-items: center;
@@ -137,13 +272,16 @@
137
272
  }
138
273
 
139
274
  /* ── Filter panel ── */
275
+ /* PORTALLED — see FilterWrapper. `top`/`left` are set inline from the
276
+ trigger's rect; everything here is appearance only. It sits on document.body
277
+ so no table's `overflow: auto` can clip it. */
140
278
  .xeplr-table-filter-panel {
141
- position: absolute;
142
- top: 100%;
143
- right: 0;
144
- z-index: 100;
279
+ position: fixed;
280
+ z-index: 3000;
145
281
  min-width: 220px;
146
282
  max-width: 300px;
283
+ max-height: 60vh;
284
+ overflow: auto;
147
285
  background: var(--xeplr-bg-tertiary, #1e1e38);
148
286
  border: 1px solid var(--xeplr-border-primary, #3a3a5a);
149
287
  border-radius: 6px;
@@ -910,3 +1048,12 @@
910
1048
 
911
1049
  .xeplr-r-avatar-img { object-fit: cover; }
912
1050
  .xeplr-r-chip-avatar-img { object-fit: cover; }
1051
+
1052
+ /* ── Host-marked columns (columnClassName) ──
1053
+ Nothing here styles a specific mark — the class is the host's and so is its
1054
+ meaning. This only makes the header label clickable when the host has taken
1055
+ the click, so the cursor says so before anybody guesses. */
1056
+ .xeplr-table-header-label.clickable {
1057
+ cursor: pointer;
1058
+ user-select: none;
1059
+ }