Browse Source

Merge pull request #7063 from nocodb/nc-fix/skelton-fix

Nc fix/skelton fix
pull/7057/head
Raju Udava 1 year ago committed by GitHub
parent
commit
a8c6085c00
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 15
      packages/nc-gui/components/dashboard/TreeView/TableNode.vue
  2. 8
      packages/nc-gui/components/smartsheet/Pagination.vue
  3. 38
      packages/nc-gui/components/smartsheet/grid/Table.vue
  4. 14
      packages/nc-gui/components/tabs/Smartsheet.vue
  5. 59
      packages/nc-gui/composables/useTableNew.ts
  6. 2
      packages/nc-gui/composables/useViewData.ts
  7. 8
      packages/nc-gui/lib/types.ts
  8. 3
      packages/nc-gui/store/tables.ts
  9. 8
      packages/nc-gui/store/views.ts

15
packages/nc-gui/components/dashboard/TreeView/TableNode.vue

@ -5,11 +5,12 @@ import { message } from 'ant-design-vue'
import { storeToRefs } from 'pinia' import { storeToRefs } from 'pinia'
import { ProjectRoleInj, TreeViewInj, useNuxtApp, useRoles, useTabs } from '#imports' import { ProjectRoleInj, TreeViewInj, useNuxtApp, useRoles, useTabs } from '#imports'
import type { SidebarTableNode } from '~/lib'
const props = withDefaults( const props = withDefaults(
defineProps<{ defineProps<{
base: BaseType base: BaseType
table: TableType table: SidebarTableNode
sourceIndex: number sourceIndex: number
}>(), }>(),
{ sourceIndex: 0 }, { sourceIndex: 0 },
@ -44,7 +45,7 @@ provide(SidebarTableInj, table)
const { setMenuContext, openRenameTableDialog, duplicateTable } = inject(TreeViewInj)! const { setMenuContext, openRenameTableDialog, duplicateTable } = inject(TreeViewInj)!
const { loadViews: _loadViews } = useViewsStore() const { loadViews: _loadViews } = useViewsStore()
const { activeView } = storeToRefs(useViewsStore()) const { activeView, activeViewTitleOrId } = storeToRefs(useViewsStore())
const { isLeftSidebarOpen } = storeToRefs(useSidebarStore()) const { isLeftSidebarOpen } = storeToRefs(useSidebarStore())
// todo: temp // todo: temp
@ -135,7 +136,7 @@ watch(
) )
const isTableOpened = computed(() => { const isTableOpened = computed(() => {
return openedTableId.value === table.value?.id && activeView.value?.is_default return openedTableId.value === table.value?.id && (activeView.value?.is_default || !activeViewTitleOrId.value)
}) })
</script> </script>
@ -174,7 +175,15 @@ const isTableOpened = computed(() => {
class="nc-sidebar-node-btn nc-sidebar-expand" class="nc-sidebar-node-btn nc-sidebar-expand"
@click.stop="onExpand" @click.stop="onExpand"
> >
<GeneralLoader
v-if="table.isViewsLoading"
class="flex w-4 h-4 !text-gray-600 !mt-0.75"
:class="{
'!visible': !isExpanded,
}"
/>
<GeneralIcon <GeneralIcon
v-else
icon="triangleFill" icon="triangleFill"
class="nc-sidebar-source-node-btns group-hover:visible invisible cursor-pointer transform transition-transform duration-500 h-1.5 w-1.5 !text-gray-600 rotate-90" class="nc-sidebar-source-node-btns group-hover:visible invisible cursor-pointer transform transition-transform duration-500 h-1.5 w-1.5 !text-gray-600 rotate-90"
:class="{ '!rotate-180': isExpanded }" :class="{ '!rotate-180': isExpanded }"

8
packages/nc-gui/components/smartsheet/Pagination.vue

@ -48,15 +48,15 @@ const size = computed(() => vPaginationData.value?.pageSize ?? 25)
const page = computed({ const page = computed({
get: () => vPaginationData?.value?.page ?? 1, get: () => vPaginationData?.value?.page ?? 1,
set: async (p) => { set: async (p) => {
isViewDataLoading.value = true isPaginationLoading.value = true
try { try {
await changePage?.(p) await changePage?.(p)
isViewDataLoading.value = false isPaginationLoading.value = false
} catch (e) { } catch (e) {
if (axios.isCancel(e)) { if (axios.isCancel(e)) {
return return
} }
isViewDataLoading.value = false isPaginationLoading.value = false
} }
}, },
}) })
@ -100,7 +100,7 @@ const renderAltOrOptlKey = () => {
'ml-8': alignLeft, 'ml-8': alignLeft,
}" }"
> >
<div v-if="isPaginationLoading" class="flex flex-row justify-center item-center min-h-10 min-w-42"> <div v-if="isViewDataLoading" class="flex flex-row justify-center item-center min-h-10 min-w-42">
<a-skeleton :active="true" :title="true" :paragraph="false" class="-mt-1 max-w-60" /> <a-skeleton :active="true" :title="true" :paragraph="false" class="-mt-1 max-w-60" />
</div> </div>
<NcPagination <NcPagination

38
packages/nc-gui/components/smartsheet/grid/Table.vue

@ -142,7 +142,12 @@ const { getMeta } = useMetas()
const { addUndo, clone, defineViewScope } = useUndoRedo() const { addUndo, clone, defineViewScope } = useUndoRedo()
const { isViewColumnsLoading, updateGridViewColumn, gridViewCols, resizingColOldWith } = useViewColumnsOrThrow() const {
isViewColumnsLoading: _isViewColumnsLoading,
updateGridViewColumn,
gridViewCols,
resizingColOldWith,
} = useViewColumnsOrThrow()
const { isExpandedFormCommentMode } = storeToRefs(useConfigStore()) const { isExpandedFormCommentMode } = storeToRefs(useConfigStore())
@ -179,6 +184,8 @@ const fillHandle = ref<HTMLElement>()
const gridRect = useElementBounding(gridWrapper) const gridRect = useElementBounding(gridWrapper)
const isViewColumnsLoading = computed(() => _isViewColumnsLoading.value || !meta.value)
// #Permissions // #Permissions
const { isUIAllowed } = useRoles() const { isUIAllowed } = useRoles()
const hasEditPermission = computed(() => isUIAllowed('dataEdit') && !isLocked.value) const hasEditPermission = computed(() => isUIAllowed('dataEdit') && !isLocked.value)
@ -409,7 +416,9 @@ const dummyRowDataForLoading = computed(() => {
}) })
const showSkeleton = computed( const showSkeleton = computed(
() => disableSkeleton !== true && (isViewDataLoading.value || isPaginationLoading.value || isViewColumnsLoading.value), () =>
(disableSkeleton !== true && (isViewDataLoading.value || isPaginationLoading.value || isViewColumnsLoading.value)) ||
!meta.value,
) )
// #Grid // #Grid
@ -1111,22 +1120,6 @@ onBeforeUnmount(async () => {
reloadViewDataHook?.on(reloadViewDataHandler) reloadViewDataHook?.on(reloadViewDataHandler)
openNewRecordFormHook?.on(openNewRecordHandler) openNewRecordFormHook?.on(openNewRecordHandler)
// TODO: Use CSS animations
const showLoaderAfterDelay = ref(false)
watch([isViewDataLoading, showSkeleton, isPaginationLoading], () => {
if (!isViewDataLoading.value && !showSkeleton.value && !isPaginationLoading.value) {
showLoaderAfterDelay.value = false
return
}
showLoaderAfterDelay.value = false
setTimeout(() => {
showLoaderAfterDelay.value = true
}, 500)
})
// #Watchers // #Watchers
// reset context menu target on hide // reset context menu target on hide
@ -1217,7 +1210,7 @@ const handleCellClick = (event: MouseEvent, row: number, col: number) => {
} }
const loaderText = computed(() => { const loaderText = computed(() => {
if (isViewDataLoading.value) { if (isPaginationLoading.value) {
if (paginationDataRef.value?.totalRows && paginationDataRef.value?.pageSize) { if (paginationDataRef.value?.totalRows && paginationDataRef.value?.pageSize) {
return `Loading page<br/>${paginationDataRef.value.page} of ${Math.ceil( return `Loading page<br/>${paginationDataRef.value.page} of ${Math.ceil(
paginationDataRef.value?.totalRows / paginationDataRef.value?.pageSize, paginationDataRef.value?.totalRows / paginationDataRef.value?.pageSize,
@ -1256,10 +1249,7 @@ onKeyStroke('ArrowDown', onDown)
></div> ></div>
</div> </div>
<div ref="gridWrapper" class="nc-grid-wrapper min-h-0 flex-1 relative" :class="gridWrapperClass"> <div ref="gridWrapper" class="nc-grid-wrapper min-h-0 flex-1 relative" :class="gridWrapperClass">
<div <div v-show="isPaginationLoading" class="flex items-center justify-center absolute l-0 t-0 w-full h-full z-10 pb-10">
v-show="showSkeleton && !isPaginationLoading && showLoaderAfterDelay"
class="flex items-center justify-center absolute l-0 t-0 w-full h-full z-10 pb-10"
>
<div class="flex flex-col justify-center gap-2"> <div class="flex flex-col justify-center gap-2">
<GeneralLoader size="xlarge" /> <GeneralLoader size="xlarge" />
<span class="text-center" v-html="loaderText"></span> <span class="text-center" v-html="loaderText"></span>
@ -1784,7 +1774,7 @@ onKeyStroke('ArrowDown', onDown)
:extra-style="paginationStyleRef?.extraStyle" :extra-style="paginationStyleRef?.extraStyle"
> >
<template #add-record> <template #add-record>
<div v-if="isAddingEmptyRowAllowed" class="flex ml-1"> <div v-if="isAddingEmptyRowAllowed && !showSkeleton && !isPaginationLoading" class="flex ml-1">
<NcButton <NcButton
v-if="isMobileMode" v-if="isMobileMode"
v-e="[isAddNewRecordGridMode ? 'c:row:add:grid' : 'c:row:add:form']" v-e="[isAddNewRecordGridMode ? 'c:row:add:grid' : 'c:row:add:form']"

14
packages/nc-gui/components/tabs/Smartsheet.vue

@ -171,21 +171,21 @@ watch([activeViewTitleOrId, activeTableId], () => {
<LazySmartsheetToolbar v-if="!isForm" /> <LazySmartsheetToolbar v-if="!isForm" />
<div class="flex flex-row w-full" style="height: calc(100% - var(--topbar-height))"> <div class="flex flex-row w-full" style="height: calc(100% - var(--topbar-height))">
<Transition name="layout" mode="out-in"> <Transition name="layout" mode="out-in">
<template v-if="meta"> <div class="flex flex-1 min-h-0 w-3/4">
<div class="flex flex-1 min-h-0 w-3/4"> <div class="h-full flex-1 min-w-0 min-h-0 bg-white">
<div v-if="activeView" class="h-full flex-1 min-w-0 min-h-0 bg-white"> <LazySmartsheetGrid v-if="isGrid || !meta || !activeView" ref="grid" />
<LazySmartsheetGrid v-if="isGrid" ref="grid" />
<LazySmartsheetGallery v-else-if="isGallery" /> <template v-if="activeView && meta">
<LazySmartsheetGallery v-if="isGallery" />
<LazySmartsheetForm v-else-if="isForm && !$route.query.reload" /> <LazySmartsheetForm v-else-if="isForm && !$route.query.reload" />
<LazySmartsheetKanban v-else-if="isKanban" /> <LazySmartsheetKanban v-else-if="isKanban" />
<LazySmartsheetMap v-else-if="isMap" /> <LazySmartsheetMap v-else-if="isMap" />
</div> </template>
</div> </div>
</template> </div>
</Transition> </Transition>
</div> </div>
</div> </div>

59
packages/nc-gui/composables/useTableNew.ts

@ -1,5 +1,7 @@
import type { ColumnType, LinkToAnotherRecordType, TableType } from 'nocodb-sdk' import type { ColumnType, LinkToAnotherRecordType, TableType } from 'nocodb-sdk'
import { UITypes, isSystemColumn } from 'nocodb-sdk' import { UITypes, isSystemColumn } from 'nocodb-sdk'
import type { SidebarTableNode } from '~/lib'
import { import {
Modal, Modal,
SYSTEM_COLUMNS, SYSTEM_COLUMNS,
@ -58,7 +60,7 @@ export function useTableNew(param: { onTableCreate?: (tableMeta: TableType) => v
const tables = computed(() => baseTables.value.get(param.baseId) || []) const tables = computed(() => baseTables.value.get(param.baseId) || [])
const base = computed(() => bases.value.get(param.baseId)) const base = computed(() => bases.value.get(param.baseId))
const openTable = async (table: TableType) => { const openTable = async (table: SidebarTableNode) => {
if (!table.base_id) return if (!table.base_id) return
let base = bases.value.get(table.base_id) let base = bases.value.get(table.base_id)
@ -82,24 +84,49 @@ export function useTableNew(param: { onTableCreate?: (tableMeta: TableType) => v
baseIdOrBaseId = route.value.params.baseId as string baseIdOrBaseId = route.value.params.baseId as string
} }
await getMeta(table.id as string, (route.value.params?.viewId as string) !== table.id) const navigateToTable = async () => {
if (openedViewsTab.value === 'view') {
await navigateTo({
path: `/${workspaceIdOrType}/${baseIdOrBaseId}/${table?.id}`,
query: route.value.query,
})
}
await loadViews({ tableId: table.id as string }) table.isViewsLoading = true
const views = viewsByTable.value.get(table.id as string) ?? [] try {
if (openedViewsTab.value !== 'view' && views.length && views[0].id) { await loadViews({ tableId: table.id as string })
// find the default view and navigate to it, if not found navigate to the first one
const defaultView = views.find((v) => v.is_default) || views[0]
await navigateTo({ const views = viewsByTable.value.get(table.id as string) ?? []
path: `/${workspaceIdOrType}/${baseIdOrBaseId}/${table?.id}/${defaultView.id}/${openedViewsTab.value}`, if (openedViewsTab.value !== 'view' && views.length && views[0].id) {
query: route.value.query, // find the default view and navigate to it, if not found navigate to the first one
}) const defaultView = views.find((v) => v.is_default) || views[0]
} else
await navigateTo({ await navigateTo({
path: `/${workspaceIdOrType}/${baseIdOrBaseId}/${table?.id}`, path: `/${workspaceIdOrType}/${baseIdOrBaseId}/${table?.id}/${defaultView.id}/${openedViewsTab.value}`,
query: route.value.query, query: route.value.query,
}) })
}
} catch (e) {
console.error(e)
} finally {
table.isViewsLoading = false
}
}
const loadTableMeta = async () => {
table.isMetaLoading = true
try {
await getMeta(table.id as string)
} catch (e) {
console.error(e)
} finally {
table.isMetaLoading = false
}
}
await Promise.all([navigateToTable(), loadTableMeta()])
} }
const createTable = async () => { const createTable = async () => {

2
packages/nc-gui/composables/useViewData.ts

@ -190,6 +190,8 @@ export function useViewData(
controller.value = CancelToken.source() controller.value = CancelToken.source()
isPaginationLoading.value = true
const response = !isPublic.value const response = !isPublic.value
? await api.dbViewRow.list( ? await api.dbViewRow.list(
'noco', 'noco',

8
packages/nc-gui/lib/types.ts

@ -1,4 +1,4 @@
import type { BaseType, ColumnType, FilterType, MetaType, PaginatedType, Roles, RolesObj, ViewTypes } from 'nocodb-sdk' import type { BaseType, ColumnType, FilterType, MetaType, PaginatedType, Roles, RolesObj, TableType, ViewTypes } from 'nocodb-sdk'
import type { I18n } from 'vue-i18n' import type { I18n } from 'vue-i18n'
import type { Theme as AntTheme } from 'ant-design-vue/es/config-provider' import type { Theme as AntTheme } from 'ant-design-vue/es/config-provider'
import type { UploadFile } from 'ant-design-vue' import type { UploadFile } from 'ant-design-vue'
@ -171,6 +171,11 @@ type ViewPageType = 'view' | 'webhook' | 'api' | 'field' | 'relation'
type NcButtonSize = 'xxsmall' | 'xsmall' | 'small' | 'medium' type NcButtonSize = 'xxsmall' | 'xsmall' | 'small' | 'medium'
interface SidebarTableNode extends TableType {
isMetaLoading?: boolean
isViewsLoading?: boolean
}
export { export {
User, User,
ProjectMetaInfo, ProjectMetaInfo,
@ -195,4 +200,5 @@ export {
Users, Users,
ViewPageType, ViewPageType,
NcButtonSize, NcButtonSize,
SidebarTableNode,
} }

3
packages/nc-gui/store/tables.ts

@ -1,6 +1,7 @@
import { acceptHMRUpdate, defineStore } from 'pinia' import { acceptHMRUpdate, defineStore } from 'pinia'
import type { TableType } from 'nocodb-sdk' import type { TableType } from 'nocodb-sdk'
import { useTitle } from '@vueuse/core' import { useTitle } from '@vueuse/core'
import type { SidebarTableNode } from '~/lib'
export const useTablesStore = defineStore('tablesStore', () => { export const useTablesStore = defineStore('tablesStore', () => {
const { includeM2M, ncNavigateTo } = useGlobal() const { includeM2M, ncNavigateTo } = useGlobal()
@ -12,7 +13,7 @@ export const useTablesStore = defineStore('tablesStore', () => {
const router = useRouter() const router = useRouter()
const route = router.currentRoute const route = router.currentRoute
const baseTables = ref<Map<string, TableType[]>>(new Map()) const baseTables = ref<Map<string, SidebarTableNode[]>>(new Map())
const basesStore = useBases() const basesStore = useBases()
// const baseStore = useBase() // const baseStore = useBase()

8
packages/nc-gui/store/views.ts

@ -184,9 +184,13 @@ export const useViewsStore = defineStore('viewsStore', () => {
isViewDataLoading.value = true isViewDataLoading.value = true
try { try {
if (tablesStore.activeTable) tablesStore.activeTable.isViewsLoading = true
await loadViews() await loadViews()
} catch (e) { } catch (e) {
console.error(e) console.error(e)
} finally {
if (tablesStore.activeTable) tablesStore.activeTable.isViewsLoading = false
} }
}, },
{ immediate: true }, { immediate: true },
@ -271,10 +275,6 @@ export const useViewsStore = defineStore('viewsStore', () => {
} }
} }
watch(activeViewTitleOrId, () => {
isPaginationLoading.value = true
})
watch(activeView, (view) => { watch(activeView, (view) => {
if (!view) return if (!view) return
if (!view.base_id) return if (!view.base_id) return

Loading…
Cancel
Save