diff --git a/packages/builder/yarn.lock b/packages/builder/yarn.lock
index 56bfd6ee8c..7035ca1765 100644
--- a/packages/builder/yarn.lock
+++ b/packages/builder/yarn.lock
@@ -1467,11 +1467,6 @@
dependencies:
"@sinonjs/commons" "^1.7.0"
-"@socket.io/component-emitter@~3.1.0":
- version "3.1.0"
- resolved "https://registry.yarnpkg.com/@socket.io/component-emitter/-/component-emitter-3.1.0.tgz#96116f2a912e0c02817345b3c10751069920d553"
- integrity sha512-+9jVqKhRSpsc591z5vX+X5Yyw+he/HCB4iQ/RYxw35CEPaY1gnsNE43nf9n9AaYjAQrTiI/mOwKUKdUs9vf7Xg==
-
"@spectrum-css/accordion@^3.0.24":
version "3.0.30"
resolved "https://registry.yarnpkg.com/@spectrum-css/accordion/-/accordion-3.0.30.tgz#0893a6db28bab984bf5adaf7e1ba194e741db615"
@@ -2586,7 +2581,7 @@ dayjs@^1.10.4, dayjs@^1.11.2:
resolved "https://registry.yarnpkg.com/dayjs/-/dayjs-1.11.7.tgz#4b296922642f70999544d1144a2c25730fce63e2"
integrity sha512-+Yw9U6YO5TQohxLcIkrXBeY73WP3ejHWVvx8XCk3gxvQDCTEmS48ZrSZCKciI7Bhl/uCMyxYtE9UqRILmFphkQ==
-debug@4, debug@4.3.4, debug@^4.1.0, debug@^4.1.1, debug@^4.3.2, debug@^4.3.4, debug@~4.3.1, debug@~4.3.2:
+debug@4, debug@4.3.4, debug@^4.1.0, debug@^4.1.1, debug@^4.3.2, debug@^4.3.4:
version "4.3.4"
resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865"
integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ==
@@ -2779,22 +2774,6 @@ end-of-stream@^1.1.0:
dependencies:
once "^1.4.0"
-engine.io-client@~6.4.0:
- version "6.4.0"
- resolved "https://registry.yarnpkg.com/engine.io-client/-/engine.io-client-6.4.0.tgz#88cd3082609ca86d7d3c12f0e746d12db4f47c91"
- integrity sha512-GyKPDyoEha+XZ7iEqam49vz6auPnNJ9ZBfy89f+rMMas8AuiMWOZ9PVzu8xb9ZC6rafUqiGHSCfu22ih66E+1g==
- dependencies:
- "@socket.io/component-emitter" "~3.1.0"
- debug "~4.3.1"
- engine.io-parser "~5.0.3"
- ws "~8.11.0"
- xmlhttprequest-ssl "~2.0.0"
-
-engine.io-parser@~5.0.3:
- version "5.0.6"
- resolved "https://registry.yarnpkg.com/engine.io-parser/-/engine.io-parser-5.0.6.tgz#7811244af173e157295dec9b2718dfe42a64ef45"
- integrity sha512-tjuoZDMAdEhVnSFleYPCtdL2GXwVTGtNjoeJd9IhIG3C1xs9uwxqRNEu5WpnDZCaozwVlK/nuQhpodhXSIMaxw==
-
enquirer@^2.3.6:
version "2.3.6"
resolved "https://registry.yarnpkg.com/enquirer/-/enquirer-2.3.6.tgz#2a7fe5dd634a1e4125a975ec994ff5456dc3734d"
@@ -5917,24 +5896,6 @@ snapdragon@^0.8.1:
source-map-resolve "^0.5.0"
use "^3.1.0"
-socket.io-client@^4.6.1:
- version "4.6.1"
- resolved "https://registry.yarnpkg.com/socket.io-client/-/socket.io-client-4.6.1.tgz#80d97d5eb0feca448a0fb6d69a7b222d3d547eab"
- integrity sha512-5UswCV6hpaRsNg5kkEHVcbBIXEYoVbMQaHJBXJCyEQ+CiFPV1NIOY0XOFWG4XR4GZcB8Kn6AsRs/9cy9TbqVMQ==
- dependencies:
- "@socket.io/component-emitter" "~3.1.0"
- debug "~4.3.2"
- engine.io-client "~6.4.0"
- socket.io-parser "~4.2.1"
-
-socket.io-parser@~4.2.1:
- version "4.2.2"
- resolved "https://registry.yarnpkg.com/socket.io-parser/-/socket.io-parser-4.2.2.tgz#1dd384019e25b7a3d374877f492ab34f2ad0d206"
- integrity sha512-DJtziuKypFkMMHCm2uIshOYC7QaylbtzQwiMYDuCKy3OPkjLzu4B2vAhTlqipRHHzrI0NJeBAizTK7X+6m1jVw==
- dependencies:
- "@socket.io/component-emitter" "~3.1.0"
- debug "~4.3.1"
-
source-map-js@^1.0.2:
version "1.0.2"
resolved "https://registry.yarnpkg.com/source-map-js/-/source-map-js-1.0.2.tgz#adbc361d9c62df380125e7f161f71c826f1e490c"
@@ -6752,11 +6713,6 @@ ws@^7.4.6:
resolved "https://registry.yarnpkg.com/ws/-/ws-7.5.9.tgz#54fa7db29f4c7cec68b1ddd3a89de099942bb591"
integrity sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==
-ws@~8.11.0:
- version "8.11.0"
- resolved "https://registry.yarnpkg.com/ws/-/ws-8.11.0.tgz#6a0d36b8edfd9f96d8b25683db2f8d7de6e8e143"
- integrity sha512-HPG3wQd9sNQoT9xHyNCXoDUa+Xw/VevmY9FoHyQ+g+rrMn4j6FB4np7Z0OhdTgjx6MgQLK7jwSy1YecU1+4Asg==
-
xml-name-validator@^3.0.0:
version "3.0.0"
resolved "https://registry.yarnpkg.com/xml-name-validator/-/xml-name-validator-3.0.0.tgz#6ae73e06de4d8c6e47f9fb181f78d648ad457c6a"
@@ -6767,11 +6723,6 @@ xmlchars@^2.2.0:
resolved "https://registry.yarnpkg.com/xmlchars/-/xmlchars-2.2.0.tgz#060fe1bcb7f9c76fe2a17db86a9bc3ab894210cb"
integrity sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==
-xmlhttprequest-ssl@~2.0.0:
- version "2.0.0"
- resolved "https://registry.yarnpkg.com/xmlhttprequest-ssl/-/xmlhttprequest-ssl-2.0.0.tgz#91360c86b914e67f44dce769180027c0da618c67"
- integrity sha512-QKxVRxiRACQcVuQEYFsI1hhkrMlrXHPegbbd1yn9UHOmRxY+si12nQYzri3vbzt8VdTTRviqcKxcyllFas5z2A==
-
y18n@^4.0.0:
version "4.0.3"
resolved "https://registry.yarnpkg.com/y18n/-/y18n-4.0.3.tgz#b5f259c82cd6e336921efd7bfd8bf560de9eeedf"
diff --git a/packages/frontend-core/src/components/sheet/AddRowButton.svelte b/packages/frontend-core/src/components/sheet/AddRowButton.svelte
index 3c7c023d89..25a721e8f1 100644
--- a/packages/frontend-core/src/components/sheet/AddRowButton.svelte
+++ b/packages/frontend-core/src/components/sheet/AddRowButton.svelte
@@ -2,12 +2,14 @@
import { Icon } from "@budibase/bbui"
import { getContext } from "svelte"
- const { dispatch } = getContext("sheet")
+ const { dispatch, columns } = getContext("sheet")
-
dispatch("add-row")}>
-
-
+{#if $columns.length}
+ dispatch("add-row")}>
+
+
+{/if}
diff --git a/packages/frontend-core/src/components/sheet/controls/SortButton.svelte b/packages/frontend-core/src/components/sheet/controls/SortButton.svelte
index 42e09380c9..2e44dcdc35 100644
--- a/packages/frontend-core/src/components/sheet/controls/SortButton.svelte
+++ b/packages/frontend-core/src/components/sheet/controls/SortButton.svelte
@@ -2,7 +2,7 @@
import { getContext } from "svelte"
import { ActionButton, Popover, Select } from "@budibase/bbui"
- const { sort, columns, stickyColumn } = getContext("sheet")
+ const { sort, visibleColumns, stickyColumn } = getContext("sheet")
const orderOptions = [
{ label: "A-Z", value: "ascending" },
{ label: "Z-A", value: "descending" },
@@ -11,7 +11,8 @@
let open = false
let anchor
- $: columnOptions = getColumnOptions($stickyColumn, $columns)
+ $: columnOptions = getColumnOptions($stickyColumn, $visibleColumns)
+ $: checkValidSortColumn($sort.column, $stickyColumn, $visibleColumns)
const getColumnOptions = (stickyColumn, columns) => {
let options = []
@@ -20,6 +21,29 @@
}
return [...options, ...columns.map(col => col.name)]
}
+
+ // Ensure we never have a sort column selected that is not visible
+ const checkValidSortColumn = (sortColumn, stickyColumn, visibleColumns) => {
+ if (!sortColumn) {
+ return
+ }
+ if (
+ sortColumn !== stickyColumn?.name &&
+ !visibleColumns.some(col => col.name === sortColumn)
+ ) {
+ if (stickyColumn) {
+ sort.update(state => ({
+ ...state,
+ column: stickyColumn.name,
+ }))
+ } else {
+ sort.update(state => ({
+ ...state,
+ column: visibleColumns[0]?.name,
+ }))
+ }
+ }
+ }
@@ -28,7 +52,8 @@
quiet
size="M"
on:click={() => (open = !open)}
- selected={!!$sort.order}
+ selected={!!$sort.column}
+ disabled={!$visibleColumns.length}
>
Sort
diff --git a/packages/frontend-core/src/components/sheet/stores/columns.js b/packages/frontend-core/src/components/sheet/stores/columns.js
index b648f7dd32..a878c51c69 100644
--- a/packages/frontend-core/src/components/sheet/stores/columns.js
+++ b/packages/frontend-core/src/components/sheet/stores/columns.js
@@ -10,17 +10,23 @@ export const createColumnsStores = context => {
// automatically calculated
const enrichedColumns = derived(columns, $columns => {
let offset = 0
- return $columns.map((column, idx) => {
+ return $columns.map(column => {
const enriched = {
...column,
- idx,
left: offset,
}
- offset += column.width
+ if (column.visible) {
+ offset += column.width
+ }
return enriched
})
})
+ // Derived list of columns which have not been explicitly hidden
+ const visibleColumns = derived(enrichedColumns, $columns => {
+ return $columns.filter(col => col.visible)
+ })
+
// Merge new schema fields with existing schema in order to preserve widths
schema.subscribe($schema => {
const currentColumns = get(columns)
@@ -45,6 +51,7 @@ export const createColumnsStores = context => {
name: field,
width: existing?.width || defaultWidth,
schema: $schema[field],
+ visible: existing?.visible ?? true,
}
})
)
@@ -75,5 +82,6 @@ export const createColumnsStores = context => {
subscribe: enrichedColumns.subscribe,
},
stickyColumn,
+ visibleColumns,
}
}
diff --git a/packages/frontend-core/src/components/sheet/stores/resize.js b/packages/frontend-core/src/components/sheet/stores/resize.js
index 0ca16dac13..d67a112c40 100644
--- a/packages/frontend-core/src/components/sheet/stores/resize.js
+++ b/packages/frontend-core/src/components/sheet/stores/resize.js
@@ -5,12 +5,13 @@ export const createResizeStores = context => {
const initialState = {
initialMouseX: null,
initialWidth: null,
+ column: null,
columnIdx: null,
width: 0,
left: 0,
}
const resize = writable(initialState)
- const isResizing = derived(resize, $resize => $resize.columnIdx != null)
+ const isResizing = derived(resize, $resize => $resize.column != null)
const MinColumnWidth = 100
// Starts resizing a certain column
@@ -18,12 +19,20 @@ export const createResizeStores = context => {
// Prevent propagation to stop reordering triggering
e.stopPropagation()
+ // Find and cache index
+ let columnIdx = get(columns).findIndex(col => col.name === column.name)
+ if (columnIdx === -1) {
+ columnIdx = "sticky"
+ }
+
+ // Set initial store state
resize.set({
width: column.width,
left: column.left,
initialWidth: column.width,
initialMouseX: e.clientX,
- columnIdx: column.idx,
+ column: column.name,
+ columnIdx,
})
// Add mouse event listeners to handle resizing
diff --git a/packages/frontend-core/src/components/sheet/stores/scroll.js b/packages/frontend-core/src/components/sheet/stores/scroll.js
index 5d5dbfe1cc..e708fbd3d6 100644
--- a/packages/frontend-core/src/components/sheet/stores/scroll.js
+++ b/packages/frontend-core/src/components/sheet/stores/scroll.js
@@ -17,7 +17,7 @@ export const createScrollStores = context => {
const width = derived(bounds, $bounds => $bounds.width, 0)
const contentHeight = derived(
rows,
- $rows => ($rows.length + 1) * cellHeight + padding,
+ $rows => $rows.length * cellHeight + padding,
0
)
const maxScrollTop = derived(
diff --git a/packages/frontend-core/src/components/sheet/stores/viewport.js b/packages/frontend-core/src/components/sheet/stores/viewport.js
index 63880ada06..f47e8e0ee0 100644
--- a/packages/frontend-core/src/components/sheet/stores/viewport.js
+++ b/packages/frontend-core/src/components/sheet/stores/viewport.js
@@ -1,7 +1,7 @@
import { derived, get } from "svelte/store"
export const createViewportStores = context => {
- const { cellHeight, columns, rows, scroll, bounds } = context
+ const { cellHeight, visibleColumns, rows, scroll, bounds } = context
const scrollTop = derived(scroll, $scroll => $scroll.top, 0)
const scrollLeft = derived(scroll, $scroll => $scroll.left, 0)
@@ -15,53 +15,59 @@ export const createViewportStores = context => {
const firstRowIdx = derived(scrollTop, $scrollTop => {
return Math.floor($scrollTop / cellHeight)
})
- const visibleRowCount = derived(height, $height => {
+ const renderedRowCount = derived(height, $height => {
return Math.ceil($height / cellHeight)
})
- const visibleRows = derived(
- [rows, firstRowIdx, visibleRowCount],
+ const renderedRows = derived(
+ [rows, firstRowIdx, renderedRowCount],
([$rows, $firstRowIdx, $visibleRowCount]) => {
return $rows.slice($firstRowIdx, $firstRowIdx + $visibleRowCount)
}
)
// Derive visible columns
- const visibleColumns = derived(
- [columns, scrollLeft, width],
- ([$columns, $scrollLeft, $width]) => {
- if (!$columns.length) {
+ const renderedColumns = derived(
+ [visibleColumns, scrollLeft, width],
+ ([$visibleColumns, $scrollLeft, $width]) => {
+ if (!$visibleColumns.length) {
return []
}
let startColIdx = 0
- let rightEdge = $columns[0].width
- while (rightEdge < $scrollLeft && startColIdx < $columns.length - 1) {
+ let rightEdge = $visibleColumns[0].width
+ while (
+ rightEdge < $scrollLeft &&
+ startColIdx < $visibleColumns.length - 1
+ ) {
startColIdx++
- rightEdge += $columns[startColIdx].width
+ rightEdge += $visibleColumns[startColIdx].width
}
let endColIdx = startColIdx + 1
let leftEdge = rightEdge
- while (leftEdge < $width + $scrollLeft && endColIdx < $columns.length) {
- leftEdge += $columns[endColIdx].width
+ while (
+ leftEdge < $width + $scrollLeft &&
+ endColIdx < $visibleColumns.length
+ ) {
+ leftEdge += $visibleColumns[endColIdx].width
endColIdx++
}
- const nextVisibleColumns = $columns.slice(startColIdx, endColIdx)
+ const nextRenderedColumns = $visibleColumns.slice(startColIdx, endColIdx)
// Cautiously shrink the number of rendered columns.
// This is to avoid rapidly shrinking and growing the visible column count
// which results in remounting cells
- const currentCount = get(visibleColumns).length
- if (currentCount === nextVisibleColumns.length + 1) {
- return $columns.slice(startColIdx, endColIdx + 1)
+ const currentCount = get(renderedColumns).length
+ if (currentCount === nextRenderedColumns.length + 1) {
+ return $visibleColumns.slice(startColIdx, endColIdx + 1)
} else {
- return nextVisibleColumns
+ return nextRenderedColumns
}
},
[]
)
// Fetch next page when approaching end of data
- visibleRows.subscribe($visibleRows => {
- const lastVisible = $visibleRows[$visibleRows.length - 1]
+ renderedRows.subscribe($renderedRows => {
+ const lastVisible = $renderedRows[$renderedRows.length - 1]
const $rows = get(rows)
const lastRow = $rows[$rows.length - 1]
if (lastVisible && lastRow && lastVisible._id === lastRow._id) {
@@ -69,5 +75,5 @@ export const createViewportStores = context => {
}
})
- return { visibleRows, visibleColumns }
+ return { renderedRows, renderedColumns }
}