@simplysm/angular 14.0.6 → 14.0.8
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/core/directives/sd-router-link.directive.d.ts.map +1 -1
- package/dist/core/directives/sd-router-link.directive.js +5 -10
- package/dist/core/plugins/events/sd-resize-event.plugin.d.ts.map +1 -1
- package/dist/core/plugins/events/sd-resize-event.plugin.js +3 -0
- package/dist/core/plugins/sd-global-error-handler.plugin.d.ts +1 -0
- package/dist/core/plugins/sd-global-error-handler.plugin.d.ts.map +1 -1
- package/dist/core/plugins/sd-global-error-handler.plugin.js +4 -0
- package/dist/core/providers/sd-app-structure.provider.d.ts.map +1 -1
- package/dist/core/providers/sd-app-structure.provider.js +4 -1
- package/dist/core/providers/sd-navigate-window.provider.d.ts +2 -1
- package/dist/core/providers/sd-navigate-window.provider.d.ts.map +1 -1
- package/dist/core/providers/sd-navigate-window.provider.js +13 -10
- package/dist/core/utils/injectParent.d.ts +7 -0
- package/dist/core/utils/injectParent.d.ts.map +1 -0
- package/dist/core/utils/injectParent.js +26 -0
- package/dist/core/utils/setups/setupCanDeactivate.d.ts.map +1 -1
- package/dist/core/utils/setups/setupCanDeactivate.js +9 -2
- package/dist/core/utils/setups/setupInvalid.d.ts.map +1 -1
- package/dist/core/utils/setups/setupInvalid.js +4 -0
- package/dist/core/utils/setups/setupModelHook.d.ts +1 -1
- package/dist/core/utils/setups/setupModelHook.d.ts.map +1 -1
- package/dist/core/utils/setups/setupModelHook.js +5 -1
- package/dist/core/utils/setups/setupRipple.d.ts.map +1 -1
- package/dist/core/utils/setups/setupRipple.js +3 -2
- package/dist/core/utils/useExpandingManager.d.ts.map +1 -1
- package/dist/core/utils/useExpandingManager.js +2 -1
- package/dist/core/utils/useSdSystemConfigResource.d.ts.map +1 -1
- package/dist/core/utils/useSdSystemConfigResource.js +6 -3
- package/dist/features/base/sd-base-container.control.d.ts +26 -0
- package/dist/features/base/sd-base-container.control.d.ts.map +1 -0
- package/dist/features/base/sd-base-container.control.js +183 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -0
- package/dist/ui/data/list/sd-list-item.control.js +1 -1
- package/dist/ui/data/sheet/sd-sheet.control.d.ts +2 -1
- package/dist/ui/data/sheet/sd-sheet.control.d.ts.map +1 -1
- package/dist/ui/data/sheet/sd-sheet.control.js +16 -13
- package/dist/ui/data/sheet/useSheetCellAgent.d.ts.map +1 -1
- package/dist/ui/data/sheet/useSheetCellAgent.js +1 -2
- package/dist/ui/data/sheet/useSheetLayoutEngine.d.ts.map +1 -1
- package/dist/ui/data/sheet/useSheetLayoutEngine.js +1 -0
- package/dist/ui/form/editor/sd-tiptap-editor.control.d.ts +5 -5
- package/dist/ui/form/editor/sd-tiptap-editor.control.d.ts.map +1 -1
- package/dist/ui/form/editor/sd-tiptap-editor.control.js +79 -78
- package/dist/ui/form/input/sd-date-range.picker.d.ts.map +1 -1
- package/dist/ui/form/input/sd-date-range.picker.js +4 -3
- package/dist/ui/form/input/sd-textfield-type-handlers.d.ts.map +1 -1
- package/dist/ui/form/input/sd-textfield-type-handlers.js +21 -2
- package/dist/ui/form/input/sd-textfield.control.d.ts.map +1 -1
- package/dist/ui/form/input/sd-textfield.control.js +1 -0
- package/dist/ui/layout/dock/sd-dock.control.d.ts +2 -0
- package/dist/ui/layout/dock/sd-dock.control.d.ts.map +1 -1
- package/dist/ui/layout/dock/sd-dock.control.js +13 -4
- package/dist/ui/layout/kanban/sd-kanban-lane.control.d.ts.map +1 -1
- package/dist/ui/layout/kanban/sd-kanban-lane.control.js +7 -1
- package/dist/ui/layout/sd-gap.control.d.ts +2 -2
- package/dist/ui/navigation/pagination/sd-pagination.control.d.ts.map +1 -1
- package/dist/ui/navigation/pagination/sd-pagination.control.js +7 -3
- package/dist/ui/navigation/sidebar/sd-sidebar-container.control.js +1 -1
- package/dist/ui/overlay/dropdown/sd-dropdown-popup.control.js +1 -1
- package/dist/ui/overlay/modal/sd-modal.control.d.ts +1 -0
- package/dist/ui/overlay/modal/sd-modal.control.d.ts.map +1 -1
- package/dist/ui/overlay/modal/sd-modal.control.js +11 -3
- package/dist/ui/overlay/modal/sd-modal.provider.d.ts +1 -1
- package/dist/ui/overlay/modal/sd-modal.provider.js +1 -1
- package/dist/ui/overlay/toast/sd-toast.provider.d.ts.map +1 -1
- package/dist/ui/overlay/toast/sd-toast.provider.js +7 -3
- package/dist/ui/visual/sd-progress.control.d.ts +1 -0
- package/dist/ui/visual/sd-progress.control.d.ts.map +1 -1
- package/dist/ui/visual/sd-progress.control.js +5 -4
- package/docs/providers.md +1 -1
- package/docs/setup-functions.md +1 -1
- package/package.json +7 -10
- package/src/core/directives/sd-router-link.directive.ts +5 -13
- package/src/core/plugins/events/sd-resize-event.plugin.ts +3 -0
- package/src/core/plugins/sd-global-error-handler.plugin.ts +4 -0
- package/src/core/providers/sd-app-structure.provider.ts +4 -1
- package/src/core/providers/sd-navigate-window.provider.ts +12 -13
- package/src/core/utils/injectParent.ts +41 -0
- package/src/core/utils/setups/setupCanDeactivate.ts +10 -2
- package/src/core/utils/setups/setupInvalid.ts +5 -0
- package/src/core/utils/setups/setupModelHook.ts +5 -2
- package/src/core/utils/setups/setupRipple.ts +3 -2
- package/src/core/utils/useExpandingManager.ts +2 -1
- package/src/core/utils/useSdSystemConfigResource.ts +6 -3
- package/src/features/base/sd-base-container.control.ts +113 -0
- package/src/index.ts +4 -0
- package/src/ui/data/list/sd-list-item.control.ts +1 -1
- package/src/ui/data/sheet/sd-sheet.control.ts +17 -13
- package/src/ui/data/sheet/useSheetCellAgent.ts +1 -2
- package/src/ui/data/sheet/useSheetLayoutEngine.ts +1 -0
- package/src/ui/form/editor/sd-tiptap-editor.control.ts +64 -61
- package/src/ui/form/input/sd-date-range.picker.ts +4 -3
- package/src/ui/form/input/sd-textfield-type-handlers.ts +25 -5
- package/src/ui/form/input/sd-textfield.control.ts +1 -0
- package/src/ui/layout/dock/sd-dock.control.ts +15 -2
- package/src/ui/layout/kanban/sd-kanban-lane.control.ts +6 -3
- package/src/ui/navigation/pagination/sd-pagination.control.ts +5 -3
- package/src/ui/navigation/sidebar/sd-sidebar-container.control.ts +1 -1
- package/src/ui/overlay/dropdown/sd-dropdown-popup.control.ts +1 -1
- package/src/ui/overlay/modal/sd-modal.control.ts +10 -1
- package/src/ui/overlay/modal/sd-modal.provider.ts +1 -1
- package/src/ui/overlay/toast/sd-toast.provider.ts +9 -3
- package/src/ui/visual/sd-progress.control.ts +4 -1
|
@@ -2,7 +2,8 @@ import { Injectable } from "@angular/core";
|
|
|
2
2
|
|
|
3
3
|
@Injectable({ providedIn: "root" })
|
|
4
4
|
export class SdNavigateWindowProvider {
|
|
5
|
-
private
|
|
5
|
+
private readonly _openedWindows = new Set<Window>();
|
|
6
|
+
private _beforeUnloadRegistered = false;
|
|
6
7
|
|
|
7
8
|
get isWindow(): boolean {
|
|
8
9
|
const urlSearchParams = new URLSearchParams(
|
|
@@ -19,21 +20,19 @@ export class SdNavigateWindowProvider {
|
|
|
19
20
|
features,
|
|
20
21
|
);
|
|
21
22
|
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
this._beforeUnloadController.abort();
|
|
23
|
+
if (newWindow) {
|
|
24
|
+
this._openedWindows.add(newWindow);
|
|
25
25
|
}
|
|
26
|
-
this._beforeUnloadController = new AbortController();
|
|
27
26
|
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
() => {
|
|
31
|
-
|
|
32
|
-
|
|
27
|
+
if (!this._beforeUnloadRegistered) {
|
|
28
|
+
this._beforeUnloadRegistered = true;
|
|
29
|
+
window.addEventListener("beforeunload", () => {
|
|
30
|
+
for (const w of this._openedWindows) {
|
|
31
|
+
w.close();
|
|
33
32
|
}
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
33
|
+
this._openedWindows.clear();
|
|
34
|
+
});
|
|
35
|
+
}
|
|
37
36
|
} else {
|
|
38
37
|
window.open(
|
|
39
38
|
`${location.pathname}#${navigate};${new URLSearchParams(params).toString()}`,
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
import { type AbstractType, inject, Injector, ViewContainerRef } from "@angular/core";
|
|
2
|
+
|
|
3
|
+
export function injectParent<T = object>(): T;
|
|
4
|
+
export function injectParent<T = object>(type: AbstractType<T>): T;
|
|
5
|
+
export function injectParent<T = object>(
|
|
6
|
+
type: AbstractType<T>,
|
|
7
|
+
options: { optional: true },
|
|
8
|
+
): T | undefined;
|
|
9
|
+
export function injectParent<T = object>(
|
|
10
|
+
type?: AbstractType<T>,
|
|
11
|
+
options?: { optional: true },
|
|
12
|
+
): T | undefined {
|
|
13
|
+
let currentInjector: Injector | undefined = inject(ViewContainerRef).injector;
|
|
14
|
+
while (currentInjector != null) {
|
|
15
|
+
// Angular internal: NodeInjector._lView[CONTEXT=8]에 컴포넌트 인스턴스 저장
|
|
16
|
+
const lView: unknown[] | undefined = (
|
|
17
|
+
currentInjector as unknown as { _lView?: unknown[] }
|
|
18
|
+
)._lView;
|
|
19
|
+
if (lView == null) {
|
|
20
|
+
break;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const comp = lView[8] as object;
|
|
24
|
+
if (type == null) {
|
|
25
|
+
return comp as T;
|
|
26
|
+
}
|
|
27
|
+
if (comp instanceof type) {
|
|
28
|
+
return comp as T;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
currentInjector = currentInjector.get(Injector, undefined, {
|
|
32
|
+
skipSelf: true,
|
|
33
|
+
optional: true,
|
|
34
|
+
}) as Injector | undefined;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
if (options?.optional) {
|
|
38
|
+
return undefined;
|
|
39
|
+
}
|
|
40
|
+
throw new Error("부모 컴포넌트를 찾을 수 없습니다.");
|
|
41
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ElementRef, inject, reflectComponentType } from "@angular/core";
|
|
1
|
+
import { DestroyRef, ElementRef, inject, reflectComponentType } from "@angular/core";
|
|
2
2
|
import { ActivatedRoute, type CanDeactivateFn } from "@angular/router";
|
|
3
3
|
import { SdActivatedModalProvider } from "../../../ui/overlay/modal/sd-modal.provider";
|
|
4
4
|
|
|
@@ -8,7 +8,7 @@ export function setupCanDeactivate(fn: () => boolean): void {
|
|
|
8
8
|
const elRef = inject(ElementRef);
|
|
9
9
|
|
|
10
10
|
if (activatedModal != null) {
|
|
11
|
-
activatedModal.
|
|
11
|
+
activatedModal.canDeactiveFn = fn;
|
|
12
12
|
return;
|
|
13
13
|
}
|
|
14
14
|
|
|
@@ -30,5 +30,13 @@ export function setupCanDeactivate(fn: () => boolean): void {
|
|
|
30
30
|
activatedRoute.routeConfig.canDeactivate = [];
|
|
31
31
|
}
|
|
32
32
|
activatedRoute.routeConfig.canDeactivate.push(canDeactivateFn);
|
|
33
|
+
|
|
34
|
+
const destroyRef = inject(DestroyRef);
|
|
35
|
+
destroyRef.onDestroy(() => {
|
|
36
|
+
const idx = activatedRoute.routeConfig!.canDeactivate!.indexOf(canDeactivateFn);
|
|
37
|
+
if (idx !== -1) {
|
|
38
|
+
activatedRoute.routeConfig!.canDeactivate!.splice(idx, 1);
|
|
39
|
+
}
|
|
40
|
+
});
|
|
33
41
|
}
|
|
34
42
|
}
|
|
@@ -26,6 +26,11 @@ export function setupInvalid(getInvalidMessage: () => string): void {
|
|
|
26
26
|
setSafeStyle(renderer, indicatorEl, { display: isInvalid ? "block" : "none" });
|
|
27
27
|
});
|
|
28
28
|
|
|
29
|
+
destroyRef.onDestroy(() => {
|
|
30
|
+
indicatorEl.remove();
|
|
31
|
+
inputEl.remove();
|
|
32
|
+
});
|
|
33
|
+
|
|
29
34
|
const formEl = inputEl.form;
|
|
30
35
|
if (formEl == null) return;
|
|
31
36
|
|
|
@@ -1,9 +1,10 @@
|
|
|
1
|
-
import type
|
|
1
|
+
import { ErrorHandler, inject, type Signal, type WritableSignal } from "@angular/core";
|
|
2
2
|
|
|
3
3
|
export function setupModelHook<T, S extends WritableSignal<T>>(
|
|
4
4
|
model: S,
|
|
5
5
|
canFn: Signal<(item: T) => boolean | Promise<boolean>>,
|
|
6
6
|
): void {
|
|
7
|
+
const errorHandler = inject(ErrorHandler);
|
|
7
8
|
const orgSet = model.set;
|
|
8
9
|
model.set = (value) => {
|
|
9
10
|
const canSet = canFn()(value);
|
|
@@ -21,6 +22,8 @@ export function setupModelHook<T, S extends WritableSignal<T>>(
|
|
|
21
22
|
if (allowed !== false) {
|
|
22
23
|
orgSet(value);
|
|
23
24
|
}
|
|
24
|
-
}).catch(() => {
|
|
25
|
+
}).catch((err) => {
|
|
26
|
+
errorHandler.handleError(err);
|
|
27
|
+
});
|
|
25
28
|
};
|
|
26
29
|
}
|
|
@@ -44,9 +44,10 @@ export function setupRipple(enableFn?: () => boolean): void {
|
|
|
44
44
|
});
|
|
45
45
|
el.appendChild(indicatorEl);
|
|
46
46
|
|
|
47
|
-
indicatorEl.ontransitionend = () => {
|
|
48
|
-
if (
|
|
47
|
+
indicatorEl.ontransitionend = (ev: TransitionEvent) => {
|
|
48
|
+
if (ev.propertyName === "opacity" && indicatorEl !== undefined) {
|
|
49
49
|
indicatorEl.remove();
|
|
50
|
+
indicatorEl = undefined;
|
|
50
51
|
}
|
|
51
52
|
};
|
|
52
53
|
|
|
@@ -86,9 +86,10 @@ export function useExpandingManager<T>(binding: {
|
|
|
86
86
|
const itemDef = map.get(item);
|
|
87
87
|
if (itemDef == null) return false;
|
|
88
88
|
|
|
89
|
+
const expandedSet = new Set(binding.expandedItems());
|
|
89
90
|
let current = itemDef.parentDef;
|
|
90
91
|
while (current != null) {
|
|
91
|
-
if (!
|
|
92
|
+
if (!expandedSet.has(current.item)) {
|
|
92
93
|
return false;
|
|
93
94
|
}
|
|
94
95
|
current = current.parentDef;
|
|
@@ -1,9 +1,10 @@
|
|
|
1
|
-
import { ElementRef, inject, type ResourceRef, resource, type Signal } from "@angular/core";
|
|
1
|
+
import { ElementRef, ErrorHandler, inject, type ResourceRef, resource, type Signal } from "@angular/core";
|
|
2
2
|
import { SdSystemConfigProvider } from "../providers/sd-system-config.provider";
|
|
3
3
|
|
|
4
4
|
export function useSdSystemConfigResource<T>(options: { key: Signal<string | undefined> }) {
|
|
5
5
|
const sdSystemConfig = inject<SdSystemConfigProvider<Record<string, T>>>(SdSystemConfigProvider);
|
|
6
6
|
const elRef = inject(ElementRef);
|
|
7
|
+
const errorHandler = inject(ErrorHandler);
|
|
7
8
|
|
|
8
9
|
const elTag = elRef.nativeElement.tagName.toLowerCase();
|
|
9
10
|
|
|
@@ -24,8 +25,10 @@ export function useSdSystemConfigResource<T>(options: { key: Signal<string | und
|
|
|
24
25
|
res.set(value);
|
|
25
26
|
const key = options.key();
|
|
26
27
|
if (key == null) return;
|
|
27
|
-
queueMicrotask(
|
|
28
|
-
|
|
28
|
+
queueMicrotask(() => {
|
|
29
|
+
sdSystemConfig.setAsync(`${elTag}.${key}`, value as T).catch((err) => {
|
|
30
|
+
errorHandler.handleError(err);
|
|
31
|
+
});
|
|
29
32
|
});
|
|
30
33
|
},
|
|
31
34
|
update(fn: (prev: T | undefined) => T | undefined) {
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
import { NgTemplateOutlet } from "@angular/common";
|
|
2
|
+
import {
|
|
3
|
+
booleanAttribute,
|
|
4
|
+
ChangeDetectionStrategy,
|
|
5
|
+
Component,
|
|
6
|
+
computed,
|
|
7
|
+
contentChild,
|
|
8
|
+
inject,
|
|
9
|
+
input,
|
|
10
|
+
TemplateRef,
|
|
11
|
+
ViewEncapsulation,
|
|
12
|
+
} from "@angular/core";
|
|
13
|
+
import { SdBusyContainerControl } from "../../ui/overlay/busy/sd-busy-container.control";
|
|
14
|
+
import { SdTopbarContainerControl } from "../../ui/navigation/topbar/sd-topbar-container.control";
|
|
15
|
+
import { SdTopbarControl } from "../../ui/navigation/topbar/sd-topbar.control";
|
|
16
|
+
import { SdAppStructureProvider } from "../../core/providers/sd-app-structure.provider";
|
|
17
|
+
import { SdActivatedModalProvider } from "../../ui/overlay/modal/sd-modal.provider";
|
|
18
|
+
import { useCurrentPageCodeSignal } from "../../core/utils/useCurrentPageCodeSignal";
|
|
19
|
+
import { useFullPageCodeSignal } from "../../core/utils/useFullPageCodeSignal";
|
|
20
|
+
import {
|
|
21
|
+
useViewTypeSignal,
|
|
22
|
+
type TSdViewType,
|
|
23
|
+
} from "../../core/utils/useViewTypeSignal";
|
|
24
|
+
import { injectParent } from "../../core/utils/injectParent";
|
|
25
|
+
import { NgIcon } from "@ng-icons/core";
|
|
26
|
+
import { tablerAlertTriangle } from "@ng-icons/tabler-icons";
|
|
27
|
+
|
|
28
|
+
@Component({
|
|
29
|
+
selector: "sd-base-container",
|
|
30
|
+
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
31
|
+
encapsulation: ViewEncapsulation.None,
|
|
32
|
+
standalone: true,
|
|
33
|
+
imports: [
|
|
34
|
+
SdBusyContainerControl,
|
|
35
|
+
SdTopbarContainerControl,
|
|
36
|
+
SdTopbarControl,
|
|
37
|
+
NgTemplateOutlet,
|
|
38
|
+
NgIcon,
|
|
39
|
+
],
|
|
40
|
+
template: `
|
|
41
|
+
<sd-busy-container [busy]="busy()" [message]="busyMessage()">
|
|
42
|
+
@if (initialized() === undefined || initialized()) {
|
|
43
|
+
@if (restricted()) {
|
|
44
|
+
<div class="fill tx-theme-gray-light p-xxl tx-center">
|
|
45
|
+
<br />
|
|
46
|
+
<ng-icon [svg]="tablerAlertTriangle" [size]="'5em'" />
|
|
47
|
+
<br />
|
|
48
|
+
<br />
|
|
49
|
+
'{{ modalOrPageTitle() }}'에 대한 사용권한이 없습니다. 시스템 관리자에게 문의하세요.
|
|
50
|
+
</div>
|
|
51
|
+
} @else if (currViewType() === "page") {
|
|
52
|
+
<sd-topbar-container>
|
|
53
|
+
<sd-topbar>
|
|
54
|
+
<h4>{{ modalOrPageTitle() }}</h4>
|
|
55
|
+
|
|
56
|
+
<ng-template [ngTemplateOutlet]="pageTopbarTplRef() ?? null" />
|
|
57
|
+
</sd-topbar>
|
|
58
|
+
|
|
59
|
+
<div class="fill">
|
|
60
|
+
<ng-template [ngTemplateOutlet]="contentTplRef()" />
|
|
61
|
+
</div>
|
|
62
|
+
</sd-topbar-container>
|
|
63
|
+
} @else if (currViewType() === "modal") {
|
|
64
|
+
<div class="flex-column fill">
|
|
65
|
+
<div class="flex-fill">
|
|
66
|
+
<ng-template [ngTemplateOutlet]="contentTplRef()" />
|
|
67
|
+
</div>
|
|
68
|
+
@if (modalBottomTplRef()) {
|
|
69
|
+
<div class="bdt bdt-theme-gray-lightest">
|
|
70
|
+
<ng-template [ngTemplateOutlet]="modalBottomTplRef() ?? null" />
|
|
71
|
+
</div>
|
|
72
|
+
}
|
|
73
|
+
</div>
|
|
74
|
+
} @else {
|
|
75
|
+
<ng-template [ngTemplateOutlet]="contentTplRef()" />
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
</sd-busy-container>
|
|
79
|
+
`,
|
|
80
|
+
})
|
|
81
|
+
export class SdBaseContainerControl {
|
|
82
|
+
private readonly _sdActivatedModal = inject(SdActivatedModalProvider, { optional: true });
|
|
83
|
+
private readonly _sdAppStructure = inject(SdAppStructureProvider);
|
|
84
|
+
|
|
85
|
+
private readonly _parent = injectParent();
|
|
86
|
+
|
|
87
|
+
private readonly _fullPageCode = useFullPageCodeSignal();
|
|
88
|
+
private readonly _currPageCode = useCurrentPageCodeSignal();
|
|
89
|
+
|
|
90
|
+
contentTplRef = contentChild.required("contentTpl", { read: TemplateRef });
|
|
91
|
+
|
|
92
|
+
pageTopbarTplRef = contentChild("pageTopbarTpl", { read: TemplateRef });
|
|
93
|
+
modalBottomTplRef = contentChild("modalBottomTpl", { read: TemplateRef });
|
|
94
|
+
|
|
95
|
+
private readonly _parentViewType = useViewTypeSignal(() => this._parent);
|
|
96
|
+
viewType = input<TSdViewType>();
|
|
97
|
+
currViewType = computed(() => this.viewType() ?? this._parentViewType());
|
|
98
|
+
|
|
99
|
+
header = input<string>();
|
|
100
|
+
modalOrPageTitle = computed(
|
|
101
|
+
() =>
|
|
102
|
+
this.header() ??
|
|
103
|
+
this._sdActivatedModal?.modalComponent()?.title() ??
|
|
104
|
+
this._sdAppStructure.getTitleByFullCode(this._currPageCode?.() ?? this._fullPageCode()),
|
|
105
|
+
);
|
|
106
|
+
|
|
107
|
+
initialized = input<boolean | undefined>(undefined);
|
|
108
|
+
restricted = input(false, { transform: booleanAttribute });
|
|
109
|
+
busy = input(false, { transform: booleanAttribute });
|
|
110
|
+
busyMessage = input<string>();
|
|
111
|
+
|
|
112
|
+
protected readonly tablerAlertTriangle = tablerAlertTriangle;
|
|
113
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -62,6 +62,10 @@ export {
|
|
|
62
62
|
type IExpandItemDef,
|
|
63
63
|
} from "./core/utils/useExpandingManager";
|
|
64
64
|
export { useSelectionManager } from "./core/utils/useSelectionManager";
|
|
65
|
+
export { injectParent } from "./core/utils/injectParent";
|
|
66
|
+
|
|
67
|
+
// features
|
|
68
|
+
export { SdBaseContainerControl } from "./features/base/sd-base-container.control";
|
|
65
69
|
|
|
66
70
|
// ui/layout
|
|
67
71
|
export { SdDockContainerControl } from "./ui/layout/dock/sd-dock-container.control";
|
|
@@ -131,7 +131,7 @@ export class SdListItemControl {
|
|
|
131
131
|
});
|
|
132
132
|
|
|
133
133
|
constructor() {
|
|
134
|
-
setupRipple(() => !this.readonly() &&
|
|
134
|
+
setupRipple(() => !this.readonly() && this.layout() !== "flat");
|
|
135
135
|
}
|
|
136
136
|
|
|
137
137
|
onContentClick(): void {
|
|
@@ -384,7 +384,7 @@ export class SdSheetControl<T> {
|
|
|
384
384
|
// Resizing state
|
|
385
385
|
_isResizing = signal(false);
|
|
386
386
|
_resizeIndicatorLeft = signal(0);
|
|
387
|
-
private
|
|
387
|
+
private _lastResizeEndTimeStamp = 0;
|
|
388
388
|
private _resizingCleanup: (() => void) | null = null;
|
|
389
389
|
|
|
390
390
|
// Config resource
|
|
@@ -478,13 +478,21 @@ export class SdSheetControl<T> {
|
|
|
478
478
|
getItemSelectableFn: this.getItemSelectableFn,
|
|
479
479
|
});
|
|
480
480
|
|
|
481
|
+
private readonly _columnControlMap = computed(() => {
|
|
482
|
+
const map = new Map<string, SdSheetColumnDirective>();
|
|
483
|
+
for (const col of this.columnControls()) {
|
|
484
|
+
map.set(col.key(), col);
|
|
485
|
+
}
|
|
486
|
+
return map;
|
|
487
|
+
});
|
|
488
|
+
|
|
481
489
|
getColumnCellTpl(key: string) {
|
|
482
|
-
const col = this.
|
|
490
|
+
const col = this._columnControlMap().get(key);
|
|
483
491
|
return col?.cellTplRef() ?? null;
|
|
484
492
|
}
|
|
485
493
|
|
|
486
494
|
getColumnSummaryTpl(key: string) {
|
|
487
|
-
const col = this.
|
|
495
|
+
const col = this._columnControlMap().get(key);
|
|
488
496
|
return col?.summaryTplRef() ?? null;
|
|
489
497
|
}
|
|
490
498
|
|
|
@@ -513,9 +521,8 @@ export class SdSheetControl<T> {
|
|
|
513
521
|
if (fixedStyle != null) {
|
|
514
522
|
parts.push(fixedStyle);
|
|
515
523
|
}
|
|
516
|
-
const
|
|
517
|
-
|
|
518
|
-
: undefined;
|
|
524
|
+
const styleFn = this.getItemCellStyleFn();
|
|
525
|
+
const customStyle = styleFn != null ? styleFn(item, colDef.key) : undefined;
|
|
519
526
|
if (customStyle != null) {
|
|
520
527
|
parts.push(customStyle);
|
|
521
528
|
}
|
|
@@ -556,7 +563,7 @@ export class SdSheetControl<T> {
|
|
|
556
563
|
}
|
|
557
564
|
|
|
558
565
|
onHeaderClick(event: MouseEvent, cell: ISdSheetHeaderDef): void {
|
|
559
|
-
if (this.
|
|
566
|
+
if (event.timeStamp - this._lastResizeEndTimeStamp < 50) return;
|
|
560
567
|
if (cell.colDef == null) return;
|
|
561
568
|
if (cell.colDef.disableSorting) return;
|
|
562
569
|
this.sorting.toggle(cell.colDef.key, event.shiftKey);
|
|
@@ -642,7 +649,8 @@ export class SdSheetControl<T> {
|
|
|
642
649
|
|
|
643
650
|
getDataCellClass(item: T, colDef: ISdSheetColumnDef, r: number, c: number): string | null {
|
|
644
651
|
const parts: string[] = [];
|
|
645
|
-
const
|
|
652
|
+
const classFn = this.getItemCellClassFn();
|
|
653
|
+
const customClass = classFn != null ? classFn(item, colDef.key) : undefined;
|
|
646
654
|
if (customClass != null) {
|
|
647
655
|
parts.push(customClass);
|
|
648
656
|
}
|
|
@@ -700,7 +708,6 @@ export class SdSheetControl<T> {
|
|
|
700
708
|
const startWidth = th.offsetWidth;
|
|
701
709
|
|
|
702
710
|
this._isResizing.set(true);
|
|
703
|
-
this._isOnResizing = true;
|
|
704
711
|
this._resizeIndicatorLeft.set(
|
|
705
712
|
th.offsetLeft + th.offsetWidth - container.scrollLeft,
|
|
706
713
|
);
|
|
@@ -724,10 +731,7 @@ export class SdSheetControl<T> {
|
|
|
724
731
|
this._isResizing.set(false);
|
|
725
732
|
this._saveColumnConfig(colDef.key, { width: `${newWidth}px` });
|
|
726
733
|
|
|
727
|
-
|
|
728
|
-
setTimeout(() => {
|
|
729
|
-
this._isOnResizing = false;
|
|
730
|
-
}, 300);
|
|
734
|
+
this._lastResizeEndTimeStamp = e.timeStamp;
|
|
731
735
|
};
|
|
732
736
|
|
|
733
737
|
document.addEventListener("mousemove", onMouseMove);
|