Tables total (#2586)

Signed-off-by: Denis Bykhov <bykhov.denis@gmail.com>
This commit is contained in:
Denis Bykhov 2023-02-03 15:51:01 +06:00 committed by GitHub
parent 3186d18d57
commit 31c5504be4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
12 changed files with 113 additions and 54 deletions

View File

@ -459,11 +459,24 @@
.scroller-thead { .scroller-thead {
position: sticky; position: sticky;
top: 0;
z-index: 2; z-index: 2;
top: 0;
height: 2.5rem;
background-color: var(--body-color); background-color: var(--body-color);
} }
.scroller-tfoot {
position: sticky;
z-index: 2;
bottom: 0;
height: 2.5rem;
background-color: var(--body-color);
tr {
box-shadow: inset 0 1px 0 0 var(--divider-color);
}
}
// THead background-color in Tooltip and Popups // THead background-color in Tooltip and Popups
.popup-tooltip .antiTable .scroller-thead, .popup-tooltip .antiTable .scroller-thead,
.popup .antiTable .scroller-thead { background-color: var(--accent-bg-color); } .popup .antiTable .scroller-thead { background-color: var(--accent-bg-color); }

View File

@ -227,7 +227,7 @@ export interface FadeOptions {
multipler?: Sides<number> multipler?: Sides<number>
} }
export const defaultSP: FadeOptions = { multipler: { top: 0, bottom: 0 } } export const defaultSP: FadeOptions = { multipler: { top: 0, bottom: 0 } }
export const tableSP: FadeOptions = { offset: { top: true }, multipler: { top: 2.5, bottom: 0 } } export const tableSP: FadeOptions = { offset: { top: true, bottom: true }, multipler: { top: 2.5, bottom: 2.5 } }
export const tableHRscheduleY: FadeOptions = { offset: { top: true }, multipler: { top: 5, bottom: 0 } } export const tableHRscheduleY: FadeOptions = { offset: { top: true }, multipler: { top: 5, bottom: 0 } }
export const issueSP: FadeOptions = { offset: { top: true }, multipler: { top: 3, bottom: 0 } } export const issueSP: FadeOptions = { offset: { top: true }, multipler: { top: 3, bottom: 0 } }
export const emojiSP: FadeOptions = { offset: { top: true }, multipler: { top: 1.5, bottom: 0 } } export const emojiSP: FadeOptions = { offset: { top: true }, multipler: { top: 1.5, bottom: 0 } }

View File

@ -23,6 +23,7 @@
day as getDay, day as getDay,
daysInMonth, daysInMonth,
eventToHTMLElement, eventToHTMLElement,
FadeOptions,
floorFractionDigits, floorFractionDigits,
getWeekDayName, getWeekDayName,
isWeekend, isWeekend,
@ -97,10 +98,18 @@
3 3
) )
} }
const fade: FadeOptions = {
...tableSP,
multipler: {
...tableSP.multipler,
bottom: 3.5
}
}
</script> </script>
{#if departmentStaff.length} {#if departmentStaff.length}
<Scroller fade={tableSP} horizontal> <Scroller {fade} horizontal>
<table> <table>
<thead class="scroller-thead"> <thead class="scroller-thead">
<tr class="scroller-thead__tr"> <tr class="scroller-thead__tr">
@ -184,6 +193,8 @@
{/each} {/each}
</tr> </tr>
{/each} {/each}
</tbody>
<tfoot class="scroller-tfoot">
<tr> <tr>
<td class="summary"> <td class="summary">
<Label label={hr.string.Summary} /> <Label label={hr.string.Summary} />
@ -218,7 +229,7 @@
</td> </td>
{/each} {/each}
</tr> </tr>
</tbody> </tfoot>
</table> </table>
</Scroller> </Scroller>
{:else} {:else}
@ -289,9 +300,13 @@
td:not(:last-child) { td:not(:last-child) {
border-right: 1px solid var(--divider-color); border-right: 1px solid var(--divider-color);
} }
tr:not(.scroller-thead__tr) {
border-bottom: 1px solid var(--divider-color); tbody {
tr {
border-bottom: 1px solid var(--divider-color);
}
} }
tr.scroller-thead__tr:not(:last-child) { tr.scroller-thead__tr:not(:last-child) {
border-right: 1px solid var(--divider-color); border-right: 1px solid var(--divider-color);
} }

View File

@ -62,6 +62,8 @@
"NewFilteredView": "New filtered view", "NewFilteredView": "New filtered view",
"FilteredViewName": "Filtered view name", "FilteredViewName": "Filtered view name",
"Then": "Then", "Then": "Then",
"ShowPreviewOnClick": "Please click to show document index preview..." "ShowPreviewOnClick": "Please click to show document index preview...",
"Showed": "Showed",
"Total": "Total"
} }
} }

View File

@ -59,6 +59,8 @@
"NewFilteredView": "Новое фильтрованное отображение", "NewFilteredView": "Новое фильтрованное отображение",
"FilteredViewName": "Имя фильтрованного отображения", "FilteredViewName": "Имя фильтрованного отображения",
"Then": "Затем", "Then": "Затем",
"ShowPreviewOnClick": "Пожалуйста нажмите чтобы увидеть предпросмотр..." "ShowPreviewOnClick": "Пожалуйста нажмите чтобы увидеть предпросмотр...",
"Showed": "Показано",
"Total": "Всего"
} }
} }

View File

@ -33,6 +33,7 @@
import { createEventDispatcher } from 'svelte' import { createEventDispatcher } from 'svelte'
import { buildConfigLookup, buildModel, LoadingProps } from '../utils' import { buildConfigLookup, buildModel, LoadingProps } from '../utils'
import Menu from './Menu.svelte' import Menu from './Menu.svelte'
import view from '../plugin'
export let _class: Ref<Class<Doc>> export let _class: Ref<Class<Doc>>
export let query: DocumentQuery<Doc> export let query: DocumentQuery<Doc>
@ -45,6 +46,7 @@
export let config: (BuildModelKey | string)[] export let config: (BuildModelKey | string)[]
export let tableId: string | undefined = undefined export let tableId: string | undefined = undefined
export let readonly = false export let readonly = false
export let showFooter = false
export let prefferedSorting: string = 'modifiedOn' export let prefferedSorting: string = 'modifiedOn'
@ -70,6 +72,7 @@
let userSorting = false let userSorting = false
let objects: Doc[] = [] let objects: Doc[] = []
let total: number
let objectsRecieved = false let objectsRecieved = false
const refs: HTMLElement[] = [] const refs: HTMLElement[] = []
@ -101,6 +104,7 @@
query, query,
(result) => { (result) => {
objects = result objects = result
total = result.total
objectsRecieved = true objectsRecieved = true
if (sortingFunction !== undefined) { if (sortingFunction !== undefined) {
const sf = sortingFunction const sf = sortingFunction
@ -259,28 +263,11 @@
} }
}} }}
> >
{#each model as attribute, cell} {#if enableChecking || showNotification}
{#if !cell} <td class="relative">
{#if enableChecking || showNotification} {#if showNotification}
<td class="relative"> <div class="antiTable-cells__notifyCell">
{#if showNotification} {#if enableChecking}
<div class="antiTable-cells__notifyCell">
{#if enableChecking}
<div class="antiTable-cells__checkCell">
<CheckBox
checked={checkedSet.has(object._id)}
on:value={(event) => {
check([object], event.detail)
}}
/>
</div>
{/if}
<Component
is={notification.component.NotificationPresenter}
props={{ value: object, kind: enableChecking ? 'table' : 'block' }}
/>
</div>
{:else}
<div class="antiTable-cells__checkCell"> <div class="antiTable-cells__checkCell">
<CheckBox <CheckBox
checked={checkedSet.has(object._id)} checked={checkedSet.has(object._id)}
@ -290,33 +277,33 @@
/> />
</div> </div>
{/if} {/if}
</td> <Component
{/if} is={notification.component.NotificationPresenter}
<td> props={{ value: object, kind: enableChecking ? 'table' : 'block' }}
<div class="antiTable-cells__firstCell">
<svelte:component
this={attribute.presenter}
value={getValue(attribute, object) ?? ''}
{...joinProps(attribute.collectionAttr, object, attribute.props)}
/> />
<!-- <div
id="context-menu"
class="antiTable-cells__firstCell-menuRow"
on:click={(ev) => showMenu(ev, object, row)}
>
<MoreV size={'small'} />
</div> -->
</div> </div>
</td> {:else}
{:else} <div class="antiTable-cells__checkCell">
<td> <CheckBox
checked={checkedSet.has(object._id)}
on:value={(event) => {
check([object], event.detail)
}}
/>
</div>
{/if}
</td>
{/if}
{#each model as attribute, cell}
<td>
<div class:antiTable-cells__firstCell={!cell}>
<svelte:component <svelte:component
this={attribute.presenter} this={attribute.presenter}
value={getValue(attribute, object) ?? ''} value={getValue(attribute, object) ?? ''}
{...joinProps(attribute.collectionAttr, object, attribute.props)} {...joinProps(attribute.collectionAttr, object, attribute.props)}
/> />
</td> </div>
{/if} </td>
{/each} {/each}
</tr> </tr>
{/each} {/each}
@ -346,3 +333,36 @@
</table> </table>
{#if loading > 0}<Loading />{/if} {#if loading > 0}<Loading />{/if}
{/await} {/await}
{#if showFooter && total}
<div class="footer">
<div class="content" class:padding={showNotification || enableChecking}>
<Label label={view.string.Total} />: {total}
{#if objects.length > 0 && objects.length < total}
<Label label={view.string.Showed} />: {objects.length}
{/if}
</div>
</div>
{/if}
<style lang="scss">
.footer {
background-color: var(--body-color);
display: flex;
align-items: flex-end;
height: 100%;
z-index: 2;
position: sticky;
bottom: 0;
.content {
display: flex;
align-items: center;
width: 100%;
box-shadow: inset 0 1px 0 0 var(--divider-color);
height: 2.5rem;
&.padding {
padding-left: 2.5rem;
}
}
}
</style>

View File

@ -93,6 +93,7 @@
{loadingProps} {loadingProps}
highlightRows={true} highlightRows={true}
enableChecking enableChecking
showFooter
checked={$selectionStore ?? []} checked={$selectionStore ?? []}
{prefferedSorting} {prefferedSorting}
selection={listProvider.current($focusStore)} selection={listProvider.current($focusStore)}

View File

@ -62,6 +62,8 @@ export default mergeIds(viewId, view, {
Ordering: '' as IntlString, Ordering: '' as IntlString,
Manual: '' as IntlString, Manual: '' as IntlString,
Then: '' as IntlString, Then: '' as IntlString,
ShowPreviewOnClick: '' as IntlString ShowPreviewOnClick: '' as IntlString,
Showed: '' as IntlString,
Total: '' as IntlString
} }
}) })

View File

@ -65,6 +65,8 @@
options: viewlet.options, options: viewlet.options,
config: preference?.config ?? viewlet.config, config: preference?.config ?? viewlet.config,
viewlet, viewlet,
viewOptions,
viewOptionsConfig: viewlet.viewOptions?.other,
createItemDialog, createItemDialog,
createItemLabel, createItemLabel,
query: resultQuery query: resultQuery

View File

@ -97,7 +97,7 @@
{viewlets} {viewlets}
{createItemDialog} {createItemDialog}
{createItemLabel} {createItemLabel}
{viewOptions} bind:viewOptions
bind:search bind:search
bind:viewlet bind:viewlet
/> />

View File

@ -141,6 +141,7 @@
config: preference?.config ?? viewlet.config, config: preference?.config ?? viewlet.config,
viewlet, viewlet,
viewOptions, viewOptions,
viewOptionsConfig: viewlet.viewOptions?.other,
createItemDialog: createComponent, createItemDialog: createComponent,
createItemLabel: createLabel, createItemLabel: createLabel,
query: resultQuery query: resultQuery

View File

@ -441,7 +441,8 @@ abstract class MongoAdapterBase extends TxProcessor {
} }
const domain = this.hierarchy.getDomain(_class) const domain = this.hierarchy.getDomain(_class)
const coll = this.db.collection(domain) const coll = this.db.collection(domain)
let cursor = coll.find<T>(this.translateQuery(_class, query)) const mongoQuery = this.translateQuery(_class, query)
let cursor = coll.find<T>(mongoQuery)
if (options?.projection !== undefined) { if (options?.projection !== undefined) {
const projection: Projection<T> = {} const projection: Projection<T> = {}
@ -463,7 +464,7 @@ abstract class MongoAdapterBase extends TxProcessor {
cursor = cursor.sort(sort) cursor = cursor.sort(sort)
} }
if (options.limit !== undefined) { if (options.limit !== undefined) {
total = await coll.estimatedDocumentCount() total = await coll.countDocuments(mongoQuery)
cursor = cursor.limit(options.limit) cursor = cursor.limit(options.limit)
} }
} }