@colijnit/corecomponents_v12 261.20.19 → 261.20.20

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.
@@ -1,6 +1,6 @@
1
1
  import { __decorate } from 'tslib';
2
2
  import * as i0 from '@angular/core';
3
- import { Input, Injectable, HostBinding, ViewEncapsulation, Component, Directive, ElementRef, Pipe, EventEmitter, Output, ViewChildren, ViewContainerRef, HostListener, ViewChild, Optional, NgModule, SkipSelf, InjectionToken, Inject, forwardRef, ChangeDetectionStrategy, ContentChildren, LOCALE_ID, NO_ERRORS_SCHEMA, Injector, QueryList } from '@angular/core';
3
+ import { Input, Injectable, HostBinding, ViewEncapsulation, Component, Directive, ElementRef, Pipe, EventEmitter, Output, ViewChildren, ViewContainerRef, HostListener, ViewChild, Optional, NgModule, SkipSelf, InjectionToken, Inject, forwardRef, ChangeDetectionStrategy, ContentChildren, LOCALE_ID, NO_ERRORS_SCHEMA, Injector, RendererStyleFlags2, QueryList } from '@angular/core';
4
4
  import * as i5 from '@angular/forms';
5
5
  import { NgModel, UntypedFormGroup, FormsModule, ReactiveFormsModule } from '@angular/forms';
6
6
  import * as i1 from '@angular/platform-browser';
@@ -18046,6 +18046,16 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
18046
18046
  }]
18047
18047
  }] });
18048
18048
 
18049
+ const ARROW_CENTER_PROPERTY = '--co-tooltip-arrow-center';
18050
+ const ARROW_EDGE_INSET_PX = 15;
18051
+ const VIEWPORT_MARGIN_PX = 5;
18052
+ const ORIENTATIONS = [CoDirection.Up, CoDirection.Down, CoDirection.Left, CoDirection.Right];
18053
+ const OPPOSITE_ORIENTATION = new Map([
18054
+ [CoDirection.Up, CoDirection.Down],
18055
+ [CoDirection.Down, CoDirection.Up],
18056
+ [CoDirection.Left, CoDirection.Right],
18057
+ [CoDirection.Right, CoDirection.Left]
18058
+ ]);
18049
18059
  class TooltipComponent {
18050
18060
  _elementRef;
18051
18061
  _changeDetector;
@@ -18058,14 +18068,27 @@ class TooltipComponent {
18058
18068
  return this._hostElement;
18059
18069
  }
18060
18070
  toolTip;
18071
+ orientation = CoDirection.Up;
18061
18072
  tooltipClosed = new EventEmitter();
18062
18073
  showClass() {
18063
18074
  return true;
18064
18075
  }
18065
18076
  top = -100;
18066
18077
  left = -100;
18067
- bottom = false;
18078
+ get isTop() {
18079
+ return this._resolvedOrientation === CoDirection.Up;
18080
+ }
18081
+ get isBottom() {
18082
+ return this._resolvedOrientation === CoDirection.Down;
18083
+ }
18084
+ get isLeft() {
18085
+ return this._resolvedOrientation === CoDirection.Left;
18086
+ }
18087
+ get isRight() {
18088
+ return this._resolvedOrientation === CoDirection.Right;
18089
+ }
18068
18090
  animate = true;
18091
+ _resolvedOrientation = CoDirection.Up;
18069
18092
  _hostElement;
18070
18093
  _documentClickListener;
18071
18094
  constructor(_elementRef, _changeDetector, _renderer) {
@@ -18090,31 +18113,103 @@ class TooltipComponent {
18090
18113
  }
18091
18114
  }
18092
18115
  _positionTooltip() {
18093
- if (this.hostElement && this._elementRef && this._elementRef.nativeElement) {
18094
- const rect = this.hostElement.getBoundingClientRect();
18095
- const ownRect = this._elementRef.nativeElement.getBoundingClientRect();
18096
- let wantedLeft = rect.left;
18097
- let wantedTop = rect.top - ownRect.height;
18098
- if (wantedTop < 0) { // out of view, move to bottom
18099
- this.bottom = true;
18100
- wantedTop = rect.bottom;
18101
- }
18102
- else {
18103
- this.bottom = false;
18104
- }
18105
- this.left = wantedLeft;
18106
- this.top = wantedTop;
18107
- this._changeDetector.markForCheck();
18108
- this._changeDetector.detectChanges();
18116
+ if (!this.hostElement || !this._elementRef || !this._elementRef.nativeElement) {
18117
+ return;
18118
+ }
18119
+ const element = this._elementRef.nativeElement;
18120
+ const hostRect = this.hostElement.getBoundingClientRect();
18121
+ this._resolvedOrientation = this._resolveOrientation(hostRect, element.getBoundingClientRect());
18122
+ // Apply the horizontal position first: it determines the available width, and therefore the height.
18123
+ this.left = this._calculateLeft(hostRect, element.getBoundingClientRect());
18124
+ this._changeDetector.detectChanges();
18125
+ const ownRect = element.getBoundingClientRect();
18126
+ this.top = this._calculateTop(hostRect, ownRect);
18127
+ this._positionArrow(hostRect, ownRect);
18128
+ this._changeDetector.markForCheck();
18129
+ this._changeDetector.detectChanges();
18130
+ }
18131
+ _resolveOrientation(hostRect, ownRect) {
18132
+ const preferred = ORIENTATIONS.indexOf(this.orientation) < 0 ? CoDirection.Up : this.orientation;
18133
+ const opposite = OPPOSITE_ORIENTATION.get(preferred);
18134
+ const candidates = [
18135
+ preferred,
18136
+ opposite,
18137
+ ...ORIENTATIONS.filter((orientation) => orientation !== preferred && orientation !== opposite)
18138
+ ];
18139
+ const fitting = candidates.find((orientation) => this._fits(orientation, hostRect, ownRect));
18140
+ if (fitting) {
18141
+ return fitting;
18142
+ }
18143
+ // Nothing fits: fall back to the side with the most room, so the tooltip overlaps the host as little as possible.
18144
+ return candidates.reduce((best, orientation) => this._availableSpace(orientation, hostRect) > this._availableSpace(best, hostRect) ? orientation : best, preferred);
18145
+ }
18146
+ _fits(orientation, hostRect, ownRect) {
18147
+ switch (orientation) {
18148
+ case CoDirection.Up:
18149
+ return (hostRect.top - ownRect.height) >= VIEWPORT_MARGIN_PX;
18150
+ case CoDirection.Down:
18151
+ return (hostRect.bottom + ownRect.height) <= (document.documentElement.clientHeight - VIEWPORT_MARGIN_PX);
18152
+ case CoDirection.Left:
18153
+ return (hostRect.left - ownRect.width) >= VIEWPORT_MARGIN_PX;
18154
+ default:
18155
+ return (hostRect.right + ownRect.width) <= (document.documentElement.clientWidth - VIEWPORT_MARGIN_PX);
18156
+ }
18157
+ }
18158
+ _availableSpace(orientation, hostRect) {
18159
+ switch (orientation) {
18160
+ case CoDirection.Up:
18161
+ return hostRect.top;
18162
+ case CoDirection.Down:
18163
+ return document.documentElement.clientHeight - hostRect.bottom;
18164
+ case CoDirection.Left:
18165
+ return hostRect.left;
18166
+ default:
18167
+ return document.documentElement.clientWidth - hostRect.right;
18168
+ }
18169
+ }
18170
+ _calculateLeft(hostRect, ownRect) {
18171
+ let wantedLeft = hostRect.left; // aligned with the host for the vertical orientations
18172
+ if (this._resolvedOrientation === CoDirection.Left) {
18173
+ wantedLeft = hostRect.left - ownRect.width;
18174
+ }
18175
+ else if (this._resolvedOrientation === CoDirection.Right) {
18176
+ wantedLeft = hostRect.right;
18177
+ }
18178
+ const maxLeft = document.documentElement.clientWidth - ownRect.width - VIEWPORT_MARGIN_PX;
18179
+ return Math.max(VIEWPORT_MARGIN_PX, Math.min(wantedLeft, maxLeft));
18180
+ }
18181
+ _calculateTop(hostRect, ownRect) {
18182
+ // Centred on the host for the horizontal orientations, so the arrow lands halfway up the edge
18183
+ // instead of being clamped against the top corner by hosts that are shorter than the tooltip.
18184
+ let wantedTop = hostRect.top + ((hostRect.height - ownRect.height) / 2);
18185
+ if (this._resolvedOrientation === CoDirection.Up) {
18186
+ wantedTop = hostRect.top - ownRect.height;
18109
18187
  }
18188
+ else if (this._resolvedOrientation === CoDirection.Down) {
18189
+ wantedTop = hostRect.bottom;
18190
+ }
18191
+ const maxTop = document.documentElement.clientHeight - ownRect.height - VIEWPORT_MARGIN_PX;
18192
+ return Math.max(VIEWPORT_MARGIN_PX, Math.min(wantedTop, maxTop));
18193
+ }
18194
+ _positionArrow(hostRect, ownRect) {
18195
+ const element = this._elementRef.nativeElement;
18196
+ const alongVerticalEdge = this.isLeft || this.isRight;
18197
+ const borderWidth = alongVerticalEdge ? element.clientTop : element.clientLeft;
18198
+ const paddingBoxSize = (alongVerticalEdge ? ownRect.height : ownRect.width) - (2 * borderWidth);
18199
+ const hostCenter = alongVerticalEdge
18200
+ ? (hostRect.top + (hostRect.height / 2)) - this.top - borderWidth
18201
+ : (hostRect.left + (hostRect.width / 2)) - this.left - borderWidth;
18202
+ const maxCenter = Math.max(ARROW_EDGE_INSET_PX, paddingBoxSize - ARROW_EDGE_INSET_PX);
18203
+ const arrowCenter = Math.min(Math.max(hostCenter, ARROW_EDGE_INSET_PX), maxCenter);
18204
+ this._renderer.setStyle(element, ARROW_CENTER_PROPERTY, `${arrowCenter}px`, RendererStyleFlags2.DashCase);
18110
18205
  }
18111
18206
  closeTooltip() {
18112
18207
  this.tooltipClosed.emit();
18113
18208
  }
18114
18209
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: TooltipComponent, deps: [{ token: i0.ElementRef }, { token: i0.ChangeDetectorRef }, { token: i0.Renderer2 }], target: i0.ɵɵFactoryTarget.Component });
18115
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.16", type: TooltipComponent, isStandalone: false, selector: "co-tooltip", inputs: { hostElement: "hostElement", toolTip: "toolTip" }, outputs: { tooltipClosed: "tooltipClosed" }, host: { properties: { "class.co-tooltip": "this.showClass", "style.top.px": "this.top", "style.left.px": "this.left", "class.bottom": "this.bottom", "@showHide": "this.animate" } }, ngImport: i0, template: `
18116
- <div class="tooltip" [innerHTML]="toolTip"></div>
18117
- `, isInline: true, animations: [
18210
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.16", type: TooltipComponent, isStandalone: false, selector: "co-tooltip", inputs: { hostElement: "hostElement", toolTip: "toolTip", orientation: "orientation" }, outputs: { tooltipClosed: "tooltipClosed" }, host: { properties: { "class.co-tooltip": "this.showClass", "style.top.px": "this.top", "style.left.px": "this.left", "class.top": "this.isTop", "class.bottom": "this.isBottom", "class.left": "this.isLeft", "class.right": "this.isRight", "@showHide": "this.animate" } }, ngImport: i0, template: `
18211
+ <div class="tooltip" [innerHTML]="toolTip"></div>
18212
+ `, isInline: true, animations: [
18118
18213
  trigger("showHide", [
18119
18214
  state("void", style({ opacity: 0 })),
18120
18215
  state("*", style({ opacity: 1 })),
@@ -18127,8 +18222,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
18127
18222
  args: [{
18128
18223
  selector: 'co-tooltip',
18129
18224
  template: `
18130
- <div class="tooltip" [innerHTML]="toolTip"></div>
18131
- `,
18225
+ <div class="tooltip" [innerHTML]="toolTip"></div>
18226
+ `,
18132
18227
  animations: [
18133
18228
  trigger("showHide", [
18134
18229
  state("void", style({ opacity: 0 })),
@@ -18144,6 +18239,8 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
18144
18239
  type: Input
18145
18240
  }], toolTip: [{
18146
18241
  type: Input
18242
+ }], orientation: [{
18243
+ type: Input
18147
18244
  }], tooltipClosed: [{
18148
18245
  type: Output
18149
18246
  }], showClass: [{
@@ -18155,14 +18252,27 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
18155
18252
  }], left: [{
18156
18253
  type: HostBinding,
18157
18254
  args: ["style.left.px"]
18158
- }], bottom: [{
18255
+ }], isTop: [{
18256
+ type: HostBinding,
18257
+ args: ["class.top"]
18258
+ }], isBottom: [{
18159
18259
  type: HostBinding,
18160
18260
  args: ["class.bottom"]
18261
+ }], isLeft: [{
18262
+ type: HostBinding,
18263
+ args: ["class.left"]
18264
+ }], isRight: [{
18265
+ type: HostBinding,
18266
+ args: ["class.right"]
18161
18267
  }], animate: [{
18162
18268
  type: HostBinding,
18163
18269
  args: ['@showHide']
18164
18270
  }] } });
18165
18271
 
18272
+ const SHOW_DELAY_PROPERTY = '--co-tooltip-show-delay';
18273
+ const AUTO_HIDE_DELAY_PROPERTY = '--co-tooltip-auto-hide-delay';
18274
+ const DEFAULT_SHOW_DELAY_MS = 400;
18275
+ const DEFAULT_AUTO_HIDE_DELAY_MS = 10000;
18166
18276
  class TooltipDirective {
18167
18277
  _compFactoryResolver;
18168
18278
  _appRef;
@@ -18171,9 +18281,15 @@ class TooltipDirective {
18171
18281
  set tooltip(str) {
18172
18282
  this._tooltipMessage = str;
18173
18283
  }
18284
+ orientation = CoDirection.Up;
18174
18285
  _elementRef;
18175
18286
  _tooltipMessage;
18176
18287
  _componentRef;
18288
+ _showTimeoutId = undefined;
18289
+ _autoHideTimeoutId = undefined;
18290
+ _mouseEnterHandler = () => this._startShowTimeout();
18291
+ _mouseLeaveHandler = () => this._removeTooltip();
18292
+ _scrollHandler = () => this._handleScroll();
18177
18293
  constructor(elementRef, _compFactoryResolver, _appRef, _injector, _sanitizer) {
18178
18294
  this._compFactoryResolver = _compFactoryResolver;
18179
18295
  this._appRef = _appRef;
@@ -18182,37 +18298,79 @@ class TooltipDirective {
18182
18298
  this._elementRef = elementRef;
18183
18299
  }
18184
18300
  ngOnDestroy() {
18301
+ this._removeTooltip();
18185
18302
  if (this._elementRef && this._elementRef.nativeElement) {
18186
- this._elementRef.nativeElement.removeEventListener('mouseenter', (event) => this._handleMouseMove(event));
18187
- this._elementRef.nativeElement.removeEventListener('mouseleave', () => this._removeTooltip());
18303
+ this._elementRef.nativeElement.removeEventListener('mouseenter', this._mouseEnterHandler);
18304
+ this._elementRef.nativeElement.removeEventListener('mouseleave', this._mouseLeaveHandler);
18188
18305
  }
18189
- window.removeEventListener("scroll", (event) => this._handleScroll);
18306
+ window.removeEventListener("scroll", this._scrollHandler);
18190
18307
  this._elementRef = undefined;
18191
18308
  }
18192
18309
  ngOnInit() {
18193
- window.addEventListener("scroll", (event) => this._handleScroll);
18310
+ window.addEventListener("scroll", this._scrollHandler);
18194
18311
  if (this._elementRef && this._elementRef.nativeElement) {
18195
- this._elementRef.nativeElement.addEventListener('mouseenter', (event) => this._handleMouseMove(event));
18196
- this._elementRef.nativeElement.addEventListener('mouseleave', () => this._removeTooltip());
18312
+ this._elementRef.nativeElement.addEventListener('mouseenter', this._mouseEnterHandler);
18313
+ this._elementRef.nativeElement.addEventListener('mouseleave', this._mouseLeaveHandler);
18197
18314
  }
18198
18315
  }
18199
18316
  _handleScroll() {
18200
18317
  this._removeTooltip();
18201
18318
  }
18202
- _handleMouseMove(event) {
18203
- this._showTooltip(event.clientY, event.clientX);
18319
+ _startShowTimeout() {
18320
+ this._clearShowTimeout();
18321
+ this._showTimeoutId = window.setTimeout(() => {
18322
+ this._showTimeoutId = undefined;
18323
+ this._createTooltipComponent();
18324
+ }, this._resolveDelay(SHOW_DELAY_PROPERTY, DEFAULT_SHOW_DELAY_MS));
18204
18325
  }
18205
- _showTooltip(top, left) {
18206
- this._createTooltipComponent(top, left);
18326
+ // Delays come from custom properties, read from the host so a scoped override wins over the
18327
+ // :root default; falls back when the stylesheet is absent. A bare number is read as milliseconds.
18328
+ _resolveDelay(property, fallback) {
18329
+ if (!this._elementRef || !this._elementRef.nativeElement) {
18330
+ return fallback;
18331
+ }
18332
+ const raw = window.getComputedStyle(this._elementRef.nativeElement)
18333
+ .getPropertyValue(property)
18334
+ .trim();
18335
+ const value = parseFloat(raw);
18336
+ if (isNaN(value)) {
18337
+ return fallback;
18338
+ }
18339
+ return Math.max(0, raw.endsWith('ms') || !raw.endsWith('s') ? value : value * 1000);
18340
+ }
18341
+ _clearShowTimeout() {
18342
+ if (this._showTimeoutId !== undefined) {
18343
+ window.clearTimeout(this._showTimeoutId);
18344
+ this._showTimeoutId = undefined;
18345
+ }
18207
18346
  }
18208
18347
  _removeTooltip() {
18348
+ this._clearShowTimeout();
18349
+ this._clearAutoHideTimeout();
18209
18350
  if (this._componentRef) {
18210
18351
  this._appRef.detachView(this._componentRef.hostView);
18211
18352
  this._componentRef.destroy();
18212
18353
  this._componentRef = undefined;
18213
18354
  }
18214
18355
  }
18215
- _createTooltipComponent(top, left) {
18356
+ _startAutoHideTimeout() {
18357
+ this._clearAutoHideTimeout();
18358
+ const delay = this._resolveDelay(AUTO_HIDE_DELAY_PROPERTY, DEFAULT_AUTO_HIDE_DELAY_MS);
18359
+ if (delay <= 0) { // guard switched off by the consumer
18360
+ return;
18361
+ }
18362
+ this._autoHideTimeoutId = window.setTimeout(() => {
18363
+ this._autoHideTimeoutId = undefined;
18364
+ this._removeTooltip();
18365
+ }, delay);
18366
+ }
18367
+ _clearAutoHideTimeout() {
18368
+ if (this._autoHideTimeoutId !== undefined) {
18369
+ window.clearTimeout(this._autoHideTimeoutId);
18370
+ this._autoHideTimeoutId = undefined;
18371
+ }
18372
+ }
18373
+ _createTooltipComponent() {
18216
18374
  if (!this._tooltipMessage) {
18217
18375
  return;
18218
18376
  }
@@ -18223,13 +18381,15 @@ class TooltipDirective {
18223
18381
  .resolveComponentFactory(TooltipComponent)
18224
18382
  .create(this._injector);
18225
18383
  this._componentRef.instance.hostElement = this._elementRef.nativeElement;
18384
+ this._componentRef.instance.orientation = this.orientation;
18226
18385
  this._componentRef.instance.toolTip = this._sanitizer.bypassSecurityTrustHtml(this._tooltipMessage);
18227
18386
  this._appRef.attachView(this._componentRef.hostView);
18228
18387
  const domElem = this._componentRef.hostView.rootNodes[0];
18229
18388
  document.body.appendChild(domElem);
18389
+ this._startAutoHideTimeout();
18230
18390
  }
18231
18391
  static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: TooltipDirective, deps: [{ token: i0.ElementRef }, { token: i0.ComponentFactoryResolver }, { token: i0.ApplicationRef }, { token: i0.Injector }, { token: i1.DomSanitizer }], target: i0.ɵɵFactoryTarget.Directive });
18232
- static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.16", type: TooltipDirective, isStandalone: false, selector: "[tooltip]", inputs: { tooltip: "tooltip" }, ngImport: i0 });
18392
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "20.3.16", type: TooltipDirective, isStandalone: false, selector: "[tooltip]", inputs: { tooltip: "tooltip", orientation: ["tooltipOrientation", "orientation"] }, ngImport: i0 });
18233
18393
  }
18234
18394
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImport: i0, type: TooltipDirective, decorators: [{
18235
18395
  type: Directive,
@@ -18240,6 +18400,9 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.16", ngImpo
18240
18400
  }], ctorParameters: () => [{ type: i0.ElementRef }, { type: i0.ComponentFactoryResolver }, { type: i0.ApplicationRef }, { type: i0.Injector }, { type: i1.DomSanitizer }], propDecorators: { tooltip: [{
18241
18401
  type: Input,
18242
18402
  args: ["tooltip"]
18403
+ }], orientation: [{
18404
+ type: Input,
18405
+ args: ["tooltipOrientation"]
18243
18406
  }] } });
18244
18407
 
18245
18408
  class TooltipModule {