@taiga-ui/core 5.24.0 → 5.25.0-canary.405e17f
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/classes/accessors.d.ts +6 -1
- package/components/cell/cell-stretch.directive.d.ts +1 -1
- package/components/data-list/option.directive.d.ts +1 -1
- package/components/scrollbar/scroll-controls.component.d.ts +1 -1
- package/components/scrollbar/scroll-ref.directive.d.ts +2 -0
- package/components/scrollbar/scrollbar.component.d.ts +0 -1
- package/fesm2022/taiga-ui-core-classes.mjs +23 -7
- package/fesm2022/taiga-ui-core-classes.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-button.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-button.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-calendar.mjs +1 -1
- package/fesm2022/taiga-ui-core-components-calendar.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-carousel.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-carousel.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-cell.mjs +6 -9
- package/fesm2022/taiga-ui-core-components-cell.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-checkbox.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-checkbox.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-data-list.mjs +7 -7
- package/fesm2022/taiga-ui-core-components-data-list.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-icon.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-icon.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-label.mjs +3 -3
- package/fesm2022/taiga-ui-core-components-label.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-link.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-link.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-notification.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-notification.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-radio.mjs +2 -2
- package/fesm2022/taiga-ui-core-components-radio.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-root.mjs +3 -3
- package/fesm2022/taiga-ui-core-components-root.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-scrollbar.mjs +31 -47
- package/fesm2022/taiga-ui-core-components-scrollbar.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-textfield.mjs +6 -5
- package/fesm2022/taiga-ui-core-components-textfield.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-components-title.mjs +3 -3
- package/fesm2022/taiga-ui-core-components-title.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-directives-appearance.mjs +3 -3
- package/fesm2022/taiga-ui-core-directives-appearance.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-directives-group.mjs +3 -3
- package/fesm2022/taiga-ui-core-directives-group.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-directives-icons.mjs +3 -3
- package/fesm2022/taiga-ui-core-directives-icons.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-portals-alert.mjs +3 -3
- package/fesm2022/taiga-ui-core-portals-alert.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-portals-dialog.mjs +2 -2
- package/fesm2022/taiga-ui-core-portals-dialog.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-portals-dropdown.mjs +145 -104
- package/fesm2022/taiga-ui-core-portals-dropdown.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-portals-hint.mjs +26 -14
- package/fesm2022/taiga-ui-core-portals-hint.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-portals-modal.mjs +3 -3
- package/fesm2022/taiga-ui-core-portals-modal.mjs.map +1 -1
- package/fesm2022/taiga-ui-core-tokens.mjs +30 -8
- package/fesm2022/taiga-ui-core-tokens.mjs.map +1 -1
- package/package.json +4 -4
- package/portals/dropdown/dropdown-anchor.directive.d.ts +5 -1
- package/portals/dropdown/dropdown.component.d.ts +4 -5
- package/portals/dropdown/dropdown.directive.d.ts +1 -0
- package/portals/dropdown/dropdown.providers.d.ts +1 -1
- package/portals/hint/hint-anchor.directive.d.ts +5 -1
- package/portals/hint/hint.d.ts +1 -2
- package/tokens/date-format.d.ts +19 -0
- package/tokens/number-format.d.ts +18 -8
|
@@ -1,20 +1,20 @@
|
|
|
1
1
|
import { tuiProvide, tuiDirectiveBinding, tuiCreateOptions } from '@taiga-ui/cdk/utils/di';
|
|
2
2
|
import { coerceArray } from '@angular/cdk/coercion';
|
|
3
3
|
import * as i0 from '@angular/core';
|
|
4
|
-
import { Injectable, Directive, InjectionToken, Optional, Self, SkipSelf, inject,
|
|
5
|
-
import {
|
|
4
|
+
import { Injectable, Directive, InjectionToken, Optional, Self, SkipSelf, inject, computed, ChangeDetectionStrategy, Component, input, effect, ElementRef, INJECTOR, ChangeDetectorRef, signal, TemplateRef, contentChild, model, PLATFORM_ID, ViewContainerRef, afterNextRender } from '@angular/core';
|
|
5
|
+
import { takeUntilDestroyed, outputFromObservable, toObservable } from '@angular/core/rxjs-interop';
|
|
6
6
|
import { tuiZonefreeScheduler, tuiIfMap, tuiCloseWatcher, tuiTypedFromEvent, tuiStopPropagation, tuiZoneOptimized } from '@taiga-ui/cdk/observables';
|
|
7
7
|
import { tuiInjectElement, tuiGetActualTarget, tuiIsElement, tuiIsElementEditable, tuiIsHTMLElement, tuiPointToClientRect, tuiIsTextNode, tuiIsTextfield } from '@taiga-ui/cdk/utils/dom';
|
|
8
|
-
import { TuiDriverDirective,
|
|
8
|
+
import { TuiDriverDirective, TuiRectAccessor, tuiProvideAccessor, TuiPositionAccessor, tuiAsRectAccessor, tuiInjectAccessor, tuiAsPositionAccessor, tuiAsVehicle, tuiAsDriver, TuiDriver } from '@taiga-ui/core/classes';
|
|
9
9
|
import { TuiPopupService } from '@taiga-ui/core/portals/popup';
|
|
10
10
|
import { tuiCheckFixedPosition, tuiGetWordRange } from '@taiga-ui/core/utils/dom';
|
|
11
11
|
import { PolymorpheusOutlet, PolymorpheusComponent, PolymorpheusTemplate } from '@taiga-ui/polymorpheus';
|
|
12
|
-
import { BehaviorSubject,
|
|
12
|
+
import { BehaviorSubject, takeWhile, map, Subject, distinctUntilChanged, throttleTime, merge, filter, EMPTY, switchMap, delay, startWith, takeUntil, fromEvent, of, tap, share, combineLatest } from 'rxjs';
|
|
13
13
|
import * as i1 from '@taiga-ui/cdk/directives/active-zone';
|
|
14
14
|
import { TuiActiveZone } from '@taiga-ui/cdk/directives/active-zone';
|
|
15
15
|
import * as i2 from '@taiga-ui/cdk/directives/animated';
|
|
16
16
|
import { TuiAnimated } from '@taiga-ui/cdk/directives/animated';
|
|
17
|
-
import { TuiScrollbar } from '@taiga-ui/core/components/scrollbar';
|
|
17
|
+
import { TuiScrollbar, TuiScrollControls, TUI_SCROLL_REF } from '@taiga-ui/core/components/scrollbar';
|
|
18
18
|
import { TUI_VIEWPORT, TUI_DARK_MODE, TUI_SELECTION_STREAM } from '@taiga-ui/core/tokens';
|
|
19
19
|
import { EMPTY_CLIENT_RECT, TUI_TRUE_HANDLER, CHAR_ZERO_WIDTH_SPACE, CHAR_NO_BREAK_SPACE } from '@taiga-ui/cdk/constants';
|
|
20
20
|
import { tuiClamp } from '@taiga-ui/cdk/utils/math';
|
|
@@ -99,84 +99,12 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
|
|
|
99
99
|
}]
|
|
100
100
|
}] });
|
|
101
101
|
|
|
102
|
-
class TuiDropdownPosition extends TuiPositionAccessor {
|
|
103
|
-
constructor() {
|
|
104
|
-
super(...arguments);
|
|
105
|
-
this.el = tuiInjectElement();
|
|
106
|
-
this.options = inject(TUI_DROPDOWN_OPTIONS);
|
|
107
|
-
this.viewport = inject(TUI_VIEWPORT);
|
|
108
|
-
this.direction = new Subject();
|
|
109
|
-
this.type = 'dropdown';
|
|
110
|
-
this.accessor = tuiFallbackAccessor('dropdown')(inject(TuiRectAccessor, { self: true, optional: true }), { getClientRect: () => this.el.getBoundingClientRect() });
|
|
111
|
-
this.tuiDropdownDirectionChange = outputFromObservable(this.direction.pipe(distinctUntilChanged()));
|
|
112
|
-
}
|
|
113
|
-
getPosition({ width, height }) {
|
|
114
|
-
if (!width && !height) {
|
|
115
|
-
this.previous = undefined;
|
|
116
|
-
}
|
|
117
|
-
const hostRect = this.accessor.getClientRect();
|
|
118
|
-
const viewportRect = this.viewport.getClientRect();
|
|
119
|
-
const { minHeight, direction, offset, limitWidth } = this.options;
|
|
120
|
-
const align = this.getAlign(this.options.align);
|
|
121
|
-
const viewport = {
|
|
122
|
-
top: viewportRect.top - offset,
|
|
123
|
-
bottom: viewportRect.bottom + offset,
|
|
124
|
-
right: viewportRect.right - offset,
|
|
125
|
-
left: viewportRect.left + offset,
|
|
126
|
-
};
|
|
127
|
-
const previous = this.previous || direction || 'bottom';
|
|
128
|
-
const available = {
|
|
129
|
-
top: hostRect.top - 2 * offset - viewport.top,
|
|
130
|
-
bottom: viewport.bottom - hostRect.bottom - 2 * offset,
|
|
131
|
-
};
|
|
132
|
-
const rectWidth = limitWidth === 'fixed' ? hostRect.width : width;
|
|
133
|
-
const right = Math.max(hostRect.right - rectWidth, offset);
|
|
134
|
-
const left = hostRect.left + width < viewport.right ? hostRect.left : right;
|
|
135
|
-
const position = {
|
|
136
|
-
top: hostRect.top - offset - height,
|
|
137
|
-
bottom: hostRect.bottom + offset,
|
|
138
|
-
right: Math.max(viewport.left, right),
|
|
139
|
-
center: hostRect.left + hostRect.width / 2 + width / 2 < viewport.right
|
|
140
|
-
? hostRect.left + hostRect.width / 2 - width / 2
|
|
141
|
-
: right,
|
|
142
|
-
left: Math.max(viewport.left, left),
|
|
143
|
-
};
|
|
144
|
-
const better = available.top > available.bottom ? 'top' : 'bottom';
|
|
145
|
-
if ((available[previous] > minHeight && direction) ||
|
|
146
|
-
available[previous] > height) {
|
|
147
|
-
this.direction.next(previous);
|
|
148
|
-
return [position[align], position[previous]];
|
|
149
|
-
}
|
|
150
|
-
this.previous = better;
|
|
151
|
-
this.direction.next(better);
|
|
152
|
-
return [position[align], position[better]];
|
|
153
|
-
}
|
|
154
|
-
getAlign(align) {
|
|
155
|
-
const rtl = this.el.matches('[dir="rtl"] :scope');
|
|
156
|
-
if (rtl && align === 'start') {
|
|
157
|
-
return 'right';
|
|
158
|
-
}
|
|
159
|
-
if (rtl && align === 'end') {
|
|
160
|
-
return 'left';
|
|
161
|
-
}
|
|
162
|
-
if (align === 'center') {
|
|
163
|
-
return 'center';
|
|
164
|
-
}
|
|
165
|
-
return align === 'end' ? 'right' : 'left';
|
|
166
|
-
}
|
|
167
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPosition, deps: null, target: i0.ɵɵFactoryTarget.Directive }); }
|
|
168
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownPosition, isStandalone: true, outputs: { tuiDropdownDirectionChange: "tuiDropdownDirectionChange" }, usesInheritance: true, ngImport: i0 }); }
|
|
169
|
-
}
|
|
170
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPosition, decorators: [{
|
|
171
|
-
type: Directive
|
|
172
|
-
}] });
|
|
173
|
-
|
|
174
102
|
const MAX_WIDTH_GAP = 16; // 8px min gap from each side
|
|
175
103
|
class TuiDropdownAnchored {
|
|
176
104
|
constructor() {
|
|
177
105
|
this.el = tuiInjectElement();
|
|
178
106
|
this.directive = inject(TuiDropdownDirective);
|
|
179
|
-
this.accessor =
|
|
107
|
+
this.accessor = inject(TuiRectAccessor);
|
|
180
108
|
this.viewport = inject(TUI_VIEWPORT);
|
|
181
109
|
this.vvs = inject(TuiVisualViewportService);
|
|
182
110
|
this.options = inject(TUI_DROPDOWN_OPTIONS);
|
|
@@ -218,8 +146,8 @@ class TuiDropdownAnchored {
|
|
|
218
146
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownAnchored, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
219
147
|
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownAnchored, isStandalone: true, providers: [
|
|
220
148
|
TuiPositionService,
|
|
221
|
-
|
|
222
|
-
|
|
149
|
+
tuiProvideAccessor(TuiPositionAccessor, 'dropdown'),
|
|
150
|
+
tuiProvideAccessor(TuiRectAccessor, 'dropdown'),
|
|
223
151
|
], ngImport: i0 }); }
|
|
224
152
|
}
|
|
225
153
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownAnchored, decorators: [{
|
|
@@ -227,35 +155,66 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
|
|
|
227
155
|
args: [{
|
|
228
156
|
providers: [
|
|
229
157
|
TuiPositionService,
|
|
230
|
-
|
|
231
|
-
|
|
158
|
+
tuiProvideAccessor(TuiPositionAccessor, 'dropdown'),
|
|
159
|
+
tuiProvideAccessor(TuiRectAccessor, 'dropdown'),
|
|
232
160
|
],
|
|
233
161
|
}]
|
|
234
162
|
}] });
|
|
235
163
|
|
|
236
164
|
/**
|
|
237
|
-
*
|
|
238
|
-
* This component is used to show template in a portal
|
|
239
|
-
* using default style of white rounded box with a shadow
|
|
165
|
+
* TODO: Remove extends TuiScrollbar in v6 when TuiScrollable is dropped
|
|
240
166
|
*/
|
|
241
|
-
class TuiDropdownComponent {
|
|
167
|
+
class TuiDropdownComponent extends TuiScrollbar {
|
|
242
168
|
constructor() {
|
|
243
|
-
|
|
169
|
+
super(...arguments);
|
|
170
|
+
this.appearance = inject(TUI_DROPDOWN_OPTIONS).appearance;
|
|
244
171
|
this.directive = inject(TuiDropdownDirective);
|
|
245
172
|
this.context = inject(TUI_DROPDOWN_CONTEXT, { optional: true });
|
|
246
173
|
this.darkMode = inject(TUI_DARK_MODE);
|
|
247
174
|
this.theme = computed((_ = this.darkMode()) => this.directive.el.closest('[tuiTheme]')?.getAttribute('tuiTheme'));
|
|
248
175
|
this.close = () => this.directive.toggle(false);
|
|
249
176
|
}
|
|
250
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownComponent, deps:
|
|
251
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownComponent, isStandalone: true, selector: "tui-dropdown", host: { properties: { "attr.data-appearance": "
|
|
177
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownComponent, deps: null, target: i0.ɵɵFactoryTarget.Component }); }
|
|
178
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownComponent, isStandalone: true, selector: "tui-dropdown", host: { properties: { "attr.data-appearance": "appearance", "attr.tuiTheme": "theme()" } }, providers: [
|
|
179
|
+
{
|
|
180
|
+
provide: TUI_SCROLL_REF,
|
|
181
|
+
useFactory: () => inject(TuiDropdownComponent).browserScrollRef,
|
|
182
|
+
},
|
|
183
|
+
], usesInheritance: true, hostDirectives: [{ directive: i1.TuiActiveZone }, { directive: i2.TuiAnimated }, { directive: TuiDropdownAnchored }], ngImport: i0, template: `
|
|
184
|
+
<tui-scroll-controls />
|
|
185
|
+
<div class="t-wrapper">
|
|
186
|
+
<div
|
|
187
|
+
*polymorpheusOutlet="
|
|
188
|
+
directive.content() as text;
|
|
189
|
+
context: {$implicit: close}
|
|
190
|
+
"
|
|
191
|
+
[innerHTML]="text"
|
|
192
|
+
></div>
|
|
193
|
+
</div>
|
|
194
|
+
`, isInline: true, styles: [":host{position:absolute;display:flex;box-shadow:var(--tui-shadow-medium);color:var(--tui-text-primary);background:var(--tui-background-elevation-1);border-radius:var(--tui-radius-m);overflow:auto;isolation:isolate;pointer-events:auto;outline-offset:-1px;outline:1px solid color-mix(in srgb,rgb(from var(--tui-border-normal) r g b / 1) 12%,var(--tui-background-elevation-1));overscroll-behavior:none;position-try-fallbacks:flip-block,flip-inline,flip-block flip-inline;--tui-from: translateY(-1rem)}:host:has(tui-data-list[data-size=l]){border-radius:var(--tui-radius-l)}:host.tui-enter,:host.tui-leave{animation-name:tuiFade,tuiSlide;animation-duration:calc(var(--tui-duration) / 2);pointer-events:none}:host:not([style*=top]){visibility:hidden}:host._delegated{scroll-timeline:none}.t-wrapper{z-index:-1;flex:1}.t-wrapper>*{padding:1rem}\n"], dependencies: [{ kind: "directive", type: PolymorpheusOutlet, selector: "[polymorpheusOutlet]", inputs: ["polymorpheusOutlet", "polymorpheusOutletContext"] }, { kind: "component", type: TuiScrollControls, selector: "tui-scroll-controls" }], changeDetection: i0.ChangeDetectionStrategy.Default }); }
|
|
252
195
|
}
|
|
253
196
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownComponent, decorators: [{
|
|
254
197
|
type: Component,
|
|
255
|
-
args: [{ selector: 'tui-dropdown', imports: [PolymorpheusOutlet,
|
|
256
|
-
|
|
198
|
+
args: [{ selector: 'tui-dropdown', imports: [PolymorpheusOutlet, TuiScrollControls], template: `
|
|
199
|
+
<tui-scroll-controls />
|
|
200
|
+
<div class="t-wrapper">
|
|
201
|
+
<div
|
|
202
|
+
*polymorpheusOutlet="
|
|
203
|
+
directive.content() as text;
|
|
204
|
+
context: {$implicit: close}
|
|
205
|
+
"
|
|
206
|
+
[innerHTML]="text"
|
|
207
|
+
></div>
|
|
208
|
+
</div>
|
|
209
|
+
`, changeDetection: ChangeDetectionStrategy.Default, providers: [
|
|
210
|
+
{
|
|
211
|
+
provide: TUI_SCROLL_REF,
|
|
212
|
+
useFactory: () => inject(TuiDropdownComponent).browserScrollRef,
|
|
213
|
+
},
|
|
214
|
+
], hostDirectives: [TuiActiveZone, TuiAnimated, TuiDropdownAnchored], host: {
|
|
215
|
+
'[attr.data-appearance]': 'appearance',
|
|
257
216
|
'[attr.tuiTheme]': 'theme()',
|
|
258
|
-
},
|
|
217
|
+
}, styles: [":host{position:absolute;display:flex;box-shadow:var(--tui-shadow-medium);color:var(--tui-text-primary);background:var(--tui-background-elevation-1);border-radius:var(--tui-radius-m);overflow:auto;isolation:isolate;pointer-events:auto;outline-offset:-1px;outline:1px solid color-mix(in srgb,rgb(from var(--tui-border-normal) r g b / 1) 12%,var(--tui-background-elevation-1));overscroll-behavior:none;position-try-fallbacks:flip-block,flip-inline,flip-block flip-inline;--tui-from: translateY(-1rem)}:host:has(tui-data-list[data-size=l]){border-radius:var(--tui-radius-l)}:host.tui-enter,:host.tui-leave{animation-name:tuiFade,tuiSlide;animation-duration:calc(var(--tui-duration) / 2);pointer-events:none}:host:not([style*=top]){visibility:hidden}:host._delegated{scroll-timeline:none}.t-wrapper{z-index:-1;flex:1}.t-wrapper>*{padding:1rem}\n"] }]
|
|
259
218
|
}] });
|
|
260
219
|
|
|
261
220
|
/**
|
|
@@ -297,20 +256,28 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
|
|
|
297
256
|
args: [{ selector: '[tuiDropdownA11y]' }]
|
|
298
257
|
}] });
|
|
299
258
|
|
|
300
|
-
class TuiDropdownAnchor {
|
|
259
|
+
class TuiDropdownAnchor extends TuiRectAccessor {
|
|
301
260
|
constructor() {
|
|
261
|
+
super(...arguments);
|
|
262
|
+
this.el = tuiInjectElement();
|
|
302
263
|
this.anchor = `--${tuiGenerateId()}`;
|
|
264
|
+
this.type = 'dropdown';
|
|
303
265
|
}
|
|
304
|
-
|
|
266
|
+
getClientRect() {
|
|
267
|
+
return this.el.getBoundingClientRect();
|
|
268
|
+
}
|
|
269
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownAnchor, deps: null, target: i0.ɵɵFactoryTarget.Directive }); }
|
|
305
270
|
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownAnchor, isStandalone: true, host: { properties: { "attr.data-tui-anchor": "anchor", "style.anchor-name": "anchor" } }, providers: [
|
|
271
|
+
tuiAsRectAccessor(TuiDropdownAnchor),
|
|
306
272
|
tuiProvide(TUI_DROPDOWN_HOST, ElementRef),
|
|
307
273
|
tuiProvide(TUI_DROPDOWN_ANCHOR, ElementRef),
|
|
308
|
-
], ngImport: i0 }); }
|
|
274
|
+
], usesInheritance: true, ngImport: i0 }); }
|
|
309
275
|
}
|
|
310
276
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownAnchor, decorators: [{
|
|
311
277
|
type: Directive,
|
|
312
278
|
args: [{
|
|
313
279
|
providers: [
|
|
280
|
+
tuiAsRectAccessor(TuiDropdownAnchor),
|
|
314
281
|
tuiProvide(TUI_DROPDOWN_HOST, ElementRef),
|
|
315
282
|
tuiProvide(TUI_DROPDOWN_ANCHOR, ElementRef),
|
|
316
283
|
],
|
|
@@ -321,6 +288,79 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImpo
|
|
|
321
288
|
}]
|
|
322
289
|
}] });
|
|
323
290
|
|
|
291
|
+
class TuiDropdownPosition extends TuiPositionAccessor {
|
|
292
|
+
constructor() {
|
|
293
|
+
super(...arguments);
|
|
294
|
+
this.el = tuiInjectElement();
|
|
295
|
+
this.options = inject(TUI_DROPDOWN_OPTIONS);
|
|
296
|
+
this.viewport = inject(TUI_VIEWPORT);
|
|
297
|
+
this.direction = new Subject();
|
|
298
|
+
this.type = 'dropdown';
|
|
299
|
+
this.accessor = tuiInjectAccessor(TuiRectAccessor, 'dropdown');
|
|
300
|
+
this.tuiDropdownDirectionChange = outputFromObservable(this.direction.pipe(distinctUntilChanged()));
|
|
301
|
+
}
|
|
302
|
+
getPosition({ width, height }) {
|
|
303
|
+
if (!width && !height) {
|
|
304
|
+
this.previous = undefined;
|
|
305
|
+
}
|
|
306
|
+
const hostRect = this.accessor.getClientRect();
|
|
307
|
+
const viewportRect = this.viewport.getClientRect();
|
|
308
|
+
const { minHeight, direction, offset, limitWidth } = this.options;
|
|
309
|
+
const align = this.getAlign(this.options.align);
|
|
310
|
+
const viewport = {
|
|
311
|
+
top: viewportRect.top - offset,
|
|
312
|
+
bottom: viewportRect.bottom + offset,
|
|
313
|
+
right: viewportRect.right - offset,
|
|
314
|
+
left: viewportRect.left + offset,
|
|
315
|
+
};
|
|
316
|
+
const previous = this.previous || direction || 'bottom';
|
|
317
|
+
const available = {
|
|
318
|
+
top: hostRect.top - 2 * offset - viewport.top,
|
|
319
|
+
bottom: viewport.bottom - hostRect.bottom - 2 * offset,
|
|
320
|
+
};
|
|
321
|
+
const rectWidth = limitWidth === 'fixed' ? hostRect.width : width;
|
|
322
|
+
const right = Math.max(hostRect.right - rectWidth, offset);
|
|
323
|
+
const left = hostRect.left + width < viewport.right ? hostRect.left : right;
|
|
324
|
+
const position = {
|
|
325
|
+
top: hostRect.top - offset - height,
|
|
326
|
+
bottom: hostRect.bottom + offset,
|
|
327
|
+
right: Math.max(viewport.left, right),
|
|
328
|
+
center: hostRect.left + hostRect.width / 2 + width / 2 < viewport.right
|
|
329
|
+
? hostRect.left + hostRect.width / 2 - width / 2
|
|
330
|
+
: right,
|
|
331
|
+
left: Math.max(viewport.left, left),
|
|
332
|
+
};
|
|
333
|
+
const better = available.top > available.bottom ? 'top' : 'bottom';
|
|
334
|
+
if ((available[previous] > minHeight && direction) ||
|
|
335
|
+
available[previous] > height) {
|
|
336
|
+
this.direction.next(previous);
|
|
337
|
+
return [position[align], position[previous]];
|
|
338
|
+
}
|
|
339
|
+
this.previous = better;
|
|
340
|
+
this.direction.next(better);
|
|
341
|
+
return [position[align], position[better]];
|
|
342
|
+
}
|
|
343
|
+
getAlign(align) {
|
|
344
|
+
const rtl = this.el.matches('[dir="rtl"] :scope');
|
|
345
|
+
if (rtl && align === 'start') {
|
|
346
|
+
return 'right';
|
|
347
|
+
}
|
|
348
|
+
if (rtl && align === 'end') {
|
|
349
|
+
return 'left';
|
|
350
|
+
}
|
|
351
|
+
if (align === 'center') {
|
|
352
|
+
return 'center';
|
|
353
|
+
}
|
|
354
|
+
return align === 'end' ? 'right' : 'left';
|
|
355
|
+
}
|
|
356
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPosition, deps: null, target: i0.ɵɵFactoryTarget.Directive }); }
|
|
357
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.25", type: TuiDropdownPosition, isStandalone: true, outputs: { tuiDropdownDirectionChange: "tuiDropdownDirectionChange" }, providers: [tuiAsPositionAccessor(TuiDropdownPosition)], usesInheritance: true, ngImport: i0 }); }
|
|
358
|
+
}
|
|
359
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPosition, decorators: [{
|
|
360
|
+
type: Directive,
|
|
361
|
+
args: [{ providers: [tuiAsPositionAccessor(TuiDropdownPosition)] }]
|
|
362
|
+
}] });
|
|
363
|
+
|
|
324
364
|
class TuiDropdownDirective {
|
|
325
365
|
constructor() {
|
|
326
366
|
this.injector = inject(INJECTOR);
|
|
@@ -350,11 +390,12 @@ class TuiDropdownDirective {
|
|
|
350
390
|
: content,
|
|
351
391
|
});
|
|
352
392
|
}
|
|
393
|
+
/** @deprecated remove in v6 */
|
|
353
394
|
get accessor() {
|
|
354
395
|
const accessors = this.injector.get(TuiRectAccessor, null, {
|
|
355
396
|
self: true,
|
|
356
397
|
});
|
|
357
|
-
return
|
|
398
|
+
return ([...(accessors || [])].reverse().find(({ type }) => type === 'dropdown') || this);
|
|
358
399
|
}
|
|
359
400
|
get position() {
|
|
360
401
|
return tuiCheckFixedPosition(this.el) ? 'fixed' : 'absolute';
|
|
@@ -770,21 +811,21 @@ class TuiDropdownPositionSided extends TuiPositionAccessor {
|
|
|
770
811
|
super(...arguments);
|
|
771
812
|
this.options = inject(TUI_DROPDOWN_OPTIONS);
|
|
772
813
|
this.viewport = inject(TUI_VIEWPORT);
|
|
773
|
-
this.vertical = inject(TuiDropdownPosition);
|
|
814
|
+
this.vertical = inject(TuiDropdownPosition, { optional: true });
|
|
774
815
|
this.previous = this.options.direction || 'bottom';
|
|
775
816
|
this.tuiDropdownSided = input('');
|
|
776
817
|
this.tuiDropdownSidedOffset = input(4);
|
|
777
818
|
this.type = 'dropdown';
|
|
778
819
|
}
|
|
779
820
|
getPosition(rect) {
|
|
780
|
-
if (this.tuiDropdownSided() === false) {
|
|
821
|
+
if (this.tuiDropdownSided() === false && this.vertical) {
|
|
781
822
|
return this.vertical.getPosition(rect);
|
|
782
823
|
}
|
|
783
824
|
const { height, width } = rect;
|
|
784
|
-
const hostRect = this.vertical.
|
|
825
|
+
const hostRect = this.vertical?.accessor.getClientRect() ?? EMPTY_CLIENT_RECT;
|
|
785
826
|
const viewport = this.viewport.getClientRect();
|
|
786
827
|
const { direction, offset } = this.options;
|
|
787
|
-
const adjusted = this.vertical
|
|
828
|
+
const adjusted = this.vertical?.getAlign(this.options.align) || 'center';
|
|
788
829
|
const align = adjusted === 'center' ? 'left' : adjusted;
|
|
789
830
|
const available = {
|
|
790
831
|
top: hostRect.bottom - viewport.top,
|
|
@@ -803,21 +844,21 @@ class TuiDropdownPositionSided extends TuiPositionAccessor {
|
|
|
803
844
|
const left = available[align] > width ? position[align] : maxLeft;
|
|
804
845
|
if ((available[this.previous] > height && direction) ||
|
|
805
846
|
this.previous === better) {
|
|
806
|
-
this.vertical
|
|
847
|
+
this.vertical?.direction.next(this.previous);
|
|
807
848
|
return [left, position[this.previous]];
|
|
808
849
|
}
|
|
809
850
|
this.previous = better;
|
|
810
|
-
this.vertical
|
|
851
|
+
this.vertical?.direction.next(better);
|
|
811
852
|
return [left, position[better]];
|
|
812
853
|
}
|
|
813
854
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPositionSided, deps: null, target: i0.ɵɵFactoryTarget.Directive }); }
|
|
814
|
-
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "19.2.25", type: TuiDropdownPositionSided, isStandalone: true, selector: "[tuiDropdownSided]", inputs: { tuiDropdownSided: { classPropertyName: "tuiDropdownSided", publicName: "tuiDropdownSided", isSignal: true, isRequired: false, transformFunction: null }, tuiDropdownSidedOffset: { classPropertyName: "tuiDropdownSidedOffset", publicName: "tuiDropdownSidedOffset", isSignal: true, isRequired: false, transformFunction: null } }, providers: [
|
|
855
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "19.2.25", type: TuiDropdownPositionSided, isStandalone: true, selector: "[tuiDropdownSided]", inputs: { tuiDropdownSided: { classPropertyName: "tuiDropdownSided", publicName: "tuiDropdownSided", isSignal: true, isRequired: false, transformFunction: null }, tuiDropdownSidedOffset: { classPropertyName: "tuiDropdownSidedOffset", publicName: "tuiDropdownSidedOffset", isSignal: true, isRequired: false, transformFunction: null } }, providers: [tuiAsPositionAccessor(TuiDropdownPositionSided)], usesInheritance: true, ngImport: i0 }); }
|
|
815
856
|
}
|
|
816
857
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.25", ngImport: i0, type: TuiDropdownPositionSided, decorators: [{
|
|
817
858
|
type: Directive,
|
|
818
859
|
args: [{
|
|
819
860
|
selector: '[tuiDropdownSided]',
|
|
820
|
-
providers: [
|
|
861
|
+
providers: [tuiAsPositionAccessor(TuiDropdownPositionSided)],
|
|
821
862
|
}]
|
|
822
863
|
}] });
|
|
823
864
|
|