@flogeez/angular-tiptap-editor 3.1.3 → 3.1.4
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/CHANGELOG.md +18 -0
- package/README.md +2 -2
- package/esm2022/flogeez-angular-tiptap-editor.mjs +5 -0
- package/esm2022/lib/ate-editor.provider.mjs +38 -0
- package/esm2022/lib/components/bubble-menus/base/ate-base-bubble-menu.mjs +207 -0
- package/esm2022/lib/components/bubble-menus/base/ate-base-sub-bubble-menu.mjs +137 -0
- package/esm2022/lib/components/bubble-menus/color/ate-color-bubble-menu.component.mjs +365 -0
- package/esm2022/lib/components/bubble-menus/image/ate-image-bubble-menu.component.mjs +309 -0
- package/esm2022/lib/components/bubble-menus/link/ate-link-bubble-menu.component.mjs +247 -0
- package/esm2022/lib/components/bubble-menus/table/ate-cell-bubble-menu.component.mjs +126 -0
- package/esm2022/lib/components/bubble-menus/table/ate-table-bubble-menu.component.mjs +271 -0
- package/esm2022/lib/components/bubble-menus/text/ate-bubble-menu.component.mjs +272 -0
- package/esm2022/lib/components/color-picker/ate-color-picker.component.mjs +123 -0
- package/esm2022/lib/components/edit-toggle/ate-edit-toggle.component.mjs +42 -0
- package/esm2022/lib/components/editor/angular-tiptap-editor.component.mjs +1031 -0
- package/esm2022/lib/components/editor/ate-block-controls.component.mjs +256 -0
- package/esm2022/lib/components/slash-commands/ate-slash-commands.component.mjs +328 -0
- package/esm2022/lib/components/toolbar/ate-toolbar.component.mjs +531 -0
- package/esm2022/lib/components/ui/ate-button.component.mjs +91 -0
- package/esm2022/lib/components/ui/ate-separator.component.mjs +11 -0
- package/esm2022/lib/config/ate-editor.config.mjs +133 -0
- package/esm2022/lib/config/ate-global-config.token.mjs +6 -0
- package/esm2022/lib/config/ate-slash-commands.config.mjs +130 -0
- package/esm2022/lib/directives/ate-noop-value-accessor.directive.mjs +40 -0
- package/esm2022/lib/directives/ate-tooltip.directive.mjs +138 -0
- package/esm2022/lib/extensions/ate-block-controls.extension.mjs +156 -0
- package/esm2022/lib/extensions/ate-link-click-behavior.extension.mjs +32 -0
- package/esm2022/lib/extensions/ate-resizable-image.extension.mjs +277 -0
- package/esm2022/lib/extensions/ate-table.extension.mjs +27 -0
- package/esm2022/lib/extensions/ate-tiptap-state.extension.mjs +85 -0
- package/esm2022/lib/extensions/ate-upload-progress.extension.mjs +195 -0
- package/esm2022/lib/extensions/calculators/ate-discovery.calculator.mjs +62 -0
- package/esm2022/lib/extensions/calculators/ate-image.calculator.mjs +8 -0
- package/esm2022/lib/extensions/calculators/ate-marks.calculator.mjs +75 -0
- package/esm2022/lib/extensions/calculators/ate-selection.calculator.mjs +35 -0
- package/esm2022/lib/extensions/calculators/ate-structure.calculator.mjs +34 -0
- package/esm2022/lib/extensions/calculators/ate-table.calculator.mjs +38 -0
- package/esm2022/lib/models/ate-bubble-menu.model.mjs +53 -0
- package/esm2022/lib/models/ate-editor-config.model.mjs +2 -0
- package/esm2022/lib/models/ate-editor-state.model.mjs +90 -0
- package/esm2022/lib/models/ate-image.model.mjs +2 -0
- package/esm2022/lib/models/ate-slash-command.model.mjs +2 -0
- package/esm2022/lib/models/ate-toolbar.model.mjs +35 -0
- package/esm2022/lib/node-view/ate-angular-node-view.mjs +97 -0
- package/esm2022/lib/node-view/ate-injector.registry.mjs +16 -0
- package/esm2022/lib/node-view/ate-node-view.factory.mjs +125 -0
- package/esm2022/lib/node-view/ate-node-view.models.mjs +2 -0
- package/esm2022/lib/node-view/ate-node-view.renderer.mjs +154 -0
- package/esm2022/lib/node-view/ate-register-angular-component.mjs +49 -0
- package/esm2022/lib/services/ate-color-picker.service.mjs +194 -0
- package/esm2022/lib/services/ate-editor-commands.service.mjs +474 -0
- package/esm2022/lib/services/ate-i18n.service.mjs +422 -0
- package/esm2022/lib/services/ate-image.service.mjs +459 -0
- package/esm2022/lib/services/ate-link.service.mjs +99 -0
- package/esm2022/lib/utils/ate-color.utils.mjs +60 -0
- package/esm2022/public-api.mjs +40 -0
- package/fesm2022/flogeez-angular-tiptap-editor.mjs +319 -352
- package/fesm2022/flogeez-angular-tiptap-editor.mjs.map +1 -1
- package/index.d.ts +3 -1734
- package/lib/ate-editor.provider.d.ts +21 -0
- package/lib/components/bubble-menus/base/ate-base-bubble-menu.d.ts +71 -0
- package/lib/components/bubble-menus/base/ate-base-sub-bubble-menu.d.ts +60 -0
- package/lib/components/bubble-menus/color/ate-color-bubble-menu.component.d.ts +77 -0
- package/lib/components/bubble-menus/image/ate-image-bubble-menu.component.d.ts +49 -0
- package/lib/components/bubble-menus/link/ate-link-bubble-menu.component.d.ts +55 -0
- package/lib/components/bubble-menus/table/ate-cell-bubble-menu.component.d.ts +16 -0
- package/lib/components/bubble-menus/table/ate-table-bubble-menu.component.d.ts +25 -0
- package/lib/components/bubble-menus/text/ate-bubble-menu.component.d.ts +53 -0
- package/lib/components/color-picker/ate-color-picker.component.d.ts +54 -0
- package/lib/components/edit-toggle/ate-edit-toggle.component.d.ts +13 -0
- package/lib/components/editor/angular-tiptap-editor.component.d.ts +242 -0
- package/lib/components/editor/ate-block-controls.component.d.ts +44 -0
- package/lib/components/slash-commands/ate-slash-commands.component.d.ts +34 -0
- package/lib/components/toolbar/ate-toolbar.component.d.ts +47 -0
- package/lib/components/ui/ate-button.component.d.ts +25 -0
- package/lib/components/ui/ate-separator.component.d.ts +5 -0
- package/lib/config/ate-editor.config.d.ts +19 -0
- package/lib/config/ate-global-config.token.d.ts +6 -0
- package/lib/config/ate-slash-commands.config.d.ts +41 -0
- package/lib/directives/ate-noop-value-accessor.directive.d.ts +13 -0
- package/lib/directives/ate-tooltip.directive.d.ts +30 -0
- package/lib/extensions/ate-block-controls.extension.d.ts +10 -0
- package/lib/extensions/ate-link-click-behavior.extension.d.ts +2 -0
- package/lib/extensions/ate-resizable-image.extension.d.ts +27 -0
- package/lib/extensions/ate-table.extension.d.ts +2 -0
- package/lib/extensions/ate-tiptap-state.extension.d.ts +7 -0
- package/lib/extensions/ate-upload-progress.extension.d.ts +7 -0
- package/lib/extensions/calculators/ate-discovery.calculator.d.ts +7 -0
- package/lib/extensions/calculators/ate-image.calculator.d.ts +2 -0
- package/lib/extensions/calculators/ate-marks.calculator.d.ts +2 -0
- package/lib/extensions/calculators/ate-selection.calculator.d.ts +2 -0
- package/lib/extensions/calculators/ate-structure.calculator.d.ts +2 -0
- package/lib/extensions/calculators/ate-table.calculator.d.ts +2 -0
- package/lib/models/ate-bubble-menu.model.d.ts +33 -0
- package/lib/models/ate-editor-config.model.d.ts +113 -0
- package/lib/models/ate-editor-state.model.d.ts +109 -0
- package/lib/models/ate-image.model.d.ts +104 -0
- package/lib/models/ate-slash-command.model.d.ts +17 -0
- package/lib/models/ate-toolbar.model.d.ts +18 -0
- package/lib/node-view/ate-angular-node-view.d.ts +115 -0
- package/lib/node-view/ate-injector.registry.d.ts +3 -0
- package/lib/node-view/ate-node-view.factory.d.ts +10 -0
- package/lib/node-view/ate-node-view.models.d.ts +138 -0
- package/lib/node-view/ate-node-view.renderer.d.ts +23 -0
- package/lib/node-view/ate-register-angular-component.d.ts +35 -0
- package/lib/services/ate-color-picker.service.d.ts +65 -0
- package/lib/services/ate-editor-commands.service.d.ts +75 -0
- package/lib/services/ate-i18n.service.d.ts +406 -0
- package/lib/services/ate-image.service.d.ts +82 -0
- package/lib/services/ate-link.service.d.ts +42 -0
- package/lib/utils/ate-color.utils.d.ts +12 -0
- package/package.json +3 -1
- package/public-api.d.ts +31 -0
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,15 @@ All notable changes to `@flogeez/angular-tiptap-editor` will be documented in th
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html), with the exception that the major version is specifically aligned with the major version of [Tiptap](https://tiptap.dev).
|
|
7
7
|
|
|
8
|
+
## [3.1.4] - 2026-05-20
|
|
9
|
+
|
|
10
|
+
### Fixed
|
|
11
|
+
|
|
12
|
+
- **Angular 18 Compatibility**: Reverted library APIs from Angular 19+ back to Angular 18 standards:
|
|
13
|
+
- Replaced `provideEnvironmentInitializer()` with `APP_INITIALIZER` in `provideAteEditor()` to prevent crashes on Angular 18 environments.
|
|
14
|
+
- Added `{ allowSignalWrites: true }` to all `effect()` blocks to fix signal write errors at runtime.
|
|
15
|
+
- Fixed TypeScript compiler and builder errors under TypeScript 5.4.
|
|
16
|
+
|
|
8
17
|
## [3.1.3] - 2026-04-27
|
|
9
18
|
|
|
10
19
|
### Added
|
|
@@ -85,6 +94,15 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
85
94
|
- **Removal of Deprecated Aliases**: Definitive removal of legacy exported names (without the `Ate` prefix) that were deprecated in v2.2.0.
|
|
86
95
|
- **Office Paste**: Updated `@intevation/tiptap-extension-office-paste` to `^0.1.2` for Tiptap v3 compatibility.
|
|
87
96
|
|
|
97
|
+
## [2.4.1] - 2026-05-19
|
|
98
|
+
|
|
99
|
+
### Fixed
|
|
100
|
+
|
|
101
|
+
- **Angular 18 Compatibility**: Reverted library APIs from Angular 19+ back to Angular 18 standards:
|
|
102
|
+
- Replaced `provideEnvironmentInitializer()` with `APP_INITIALIZER` in `provideAteEditor()` to prevent crashes on Angular 18 environments.
|
|
103
|
+
- Added `{ allowSignalWrites: true }` to all `effect()` blocks to fix signal write errors at runtime.
|
|
104
|
+
- Fixed TypeScript compiler and builder errors under TypeScript 5.4.
|
|
105
|
+
|
|
88
106
|
## [2.4.0] - 2026-01-29
|
|
89
107
|
|
|
90
108
|
### Added
|
package/README.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# Angular Tiptap Editor
|
|
2
2
|
|
|
3
3
|
> [!IMPORTANT]
|
|
4
|
-
> **^v3.0.0 uses Tiptap v3**. If you need to stay on Tiptap v2, please use version `^2.4.
|
|
4
|
+
> **^v3.0.0 uses Tiptap v3**. If you need to stay on Tiptap v2, please use version `^2.4.1`.
|
|
5
5
|
|
|
6
6
|
A modern, customizable Angular rich-text editor, built with **Tiptap**.
|
|
7
7
|
|
|
@@ -22,8 +22,8 @@ Yet, I've worked to keep it fully customizable: you can easily configure the edi
|
|
|
22
22
|
- 🌍 **Built-in i18n**: Support for English and French out of the box.
|
|
23
23
|
- 📎 **Office-Ready**: Clean pasting from Word and Excel.
|
|
24
24
|
- 🎨 **Highly Customizable**: Easily configure toolbars, bubble menus, and slash command items.
|
|
25
|
-
|
|
26
25
|
- 🛠️ **Extensible**: Easily add custom Tiptap extensions and reactive state calculators.
|
|
26
|
+
- 🧩 **Angular 18+ Support**: Uses Angular 18's signals and esbuild for optimal performance.
|
|
27
27
|
|
|
28
28
|
## 📦 Installation
|
|
29
29
|
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Generated bundle index. Do not edit.
|
|
3
|
+
*/
|
|
4
|
+
export * from './public-api';
|
|
5
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZmxvZ2Vlei1hbmd1bGFyLXRpcHRhcC1lZGl0b3IuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi9wcm9qZWN0cy9hbmd1bGFyLXRpcHRhcC1lZGl0b3Ivc3JjL2Zsb2dlZXotYW5ndWxhci10aXB0YXAtZWRpdG9yLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOztHQUVHO0FBRUgsY0FBYyxjQUFjLENBQUMiLCJzb3VyY2VzQ29udGVudCI6WyIvKipcbiAqIEdlbmVyYXRlZCBidW5kbGUgaW5kZXguIERvIG5vdCBlZGl0LlxuICovXG5cbmV4cG9ydCAqIGZyb20gJy4vcHVibGljLWFwaSc7XG4iXX0=
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { makeEnvironmentProviders, APP_INITIALIZER, Injector, } from "@angular/core";
|
|
2
|
+
import { setGlobalInjector } from "./node-view/ate-injector.registry";
|
|
3
|
+
import { ATE_GLOBAL_CONFIG } from "./config/ate-global-config.token";
|
|
4
|
+
/**
|
|
5
|
+
* Provides the necessary configuration and initialization for the Angular TipTap Editor.
|
|
6
|
+
* This should be called in your app.config.ts (for standalone) or main.ts.
|
|
7
|
+
*
|
|
8
|
+
* This provider is essential for 'Angular Nodes' to work correctly, as it captures the
|
|
9
|
+
* root Injector required to instantiate custom Angular components within the editor.
|
|
10
|
+
* @example
|
|
11
|
+
* ```ts
|
|
12
|
+
* bootstrapApplication(AppComponent, {
|
|
13
|
+
* providers: [
|
|
14
|
+
* provideAteEditor({
|
|
15
|
+
* theme: 'dark',
|
|
16
|
+
* mode: 'seamless'
|
|
17
|
+
* })
|
|
18
|
+
* ]
|
|
19
|
+
* });
|
|
20
|
+
* ```
|
|
21
|
+
*/
|
|
22
|
+
export function provideAteEditor(config) {
|
|
23
|
+
return makeEnvironmentProviders([
|
|
24
|
+
{
|
|
25
|
+
provide: ATE_GLOBAL_CONFIG,
|
|
26
|
+
useValue: config || {},
|
|
27
|
+
},
|
|
28
|
+
{
|
|
29
|
+
provide: APP_INITIALIZER,
|
|
30
|
+
useFactory: (injector) => () => {
|
|
31
|
+
setGlobalInjector(injector);
|
|
32
|
+
},
|
|
33
|
+
deps: [Injector],
|
|
34
|
+
multi: true,
|
|
35
|
+
},
|
|
36
|
+
]);
|
|
37
|
+
}
|
|
38
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXRlLWVkaXRvci5wcm92aWRlci5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3Byb2plY3RzL2FuZ3VsYXItdGlwdGFwLWVkaXRvci9zcmMvbGliL2F0ZS1lZGl0b3IucHJvdmlkZXIudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUVMLHdCQUF3QixFQUN4QixlQUFlLEVBQ2YsUUFBUSxHQUNULE1BQU0sZUFBZSxDQUFDO0FBQ3ZCLE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLG1DQUFtQyxDQUFDO0FBRXRFLE9BQU8sRUFBRSxpQkFBaUIsRUFBRSxNQUFNLGtDQUFrQyxDQUFDO0FBR3JFOzs7Ozs7Ozs7Ozs7Ozs7OztHQWlCRztBQUNILE1BQU0sVUFBVSxnQkFBZ0IsQ0FBQyxNQUF3QjtJQUN2RCxPQUFPLHdCQUF3QixDQUFDO1FBQzlCO1lBQ0UsT0FBTyxFQUFFLGlCQUFpQjtZQUMxQixRQUFRLEVBQUUsTUFBTSxJQUFJLEVBQUU7U0FDdkI7UUFDRDtZQUNFLE9BQU8sRUFBRSxlQUFlO1lBQ3hCLFVBQVUsRUFBRSxDQUFDLFFBQWtCLEVBQUUsRUFBRSxDQUFDLEdBQUcsRUFBRTtnQkFDdkMsaUJBQWlCLENBQUMsUUFBUSxDQUFDLENBQUM7WUFDOUIsQ0FBQztZQUNELElBQUksRUFBRSxDQUFDLFFBQVEsQ0FBQztZQUNoQixLQUFLLEVBQUUsSUFBSTtTQUNaO0tBQ0YsQ0FBQyxDQUFDO0FBQ0wsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIEVudmlyb25tZW50UHJvdmlkZXJzLFxuICBtYWtlRW52aXJvbm1lbnRQcm92aWRlcnMsXG4gIEFQUF9JTklUSUFMSVpFUixcbiAgSW5qZWN0b3IsXG59IGZyb20gXCJAYW5ndWxhci9jb3JlXCI7XG5pbXBvcnQgeyBzZXRHbG9iYWxJbmplY3RvciB9IGZyb20gXCIuL25vZGUtdmlldy9hdGUtaW5qZWN0b3IucmVnaXN0cnlcIjtcblxuaW1wb3J0IHsgQVRFX0dMT0JBTF9DT05GSUcgfSBmcm9tIFwiLi9jb25maWcvYXRlLWdsb2JhbC1jb25maWcudG9rZW5cIjtcbmltcG9ydCB7IEF0ZUVkaXRvckNvbmZpZyB9IGZyb20gXCIuL21vZGVscy9hdGUtZWRpdG9yLWNvbmZpZy5tb2RlbFwiO1xuXG4vKipcbiAqIFByb3ZpZGVzIHRoZSBuZWNlc3NhcnkgY29uZmlndXJhdGlvbiBhbmQgaW5pdGlhbGl6YXRpb24gZm9yIHRoZSBBbmd1bGFyIFRpcFRhcCBFZGl0b3IuXG4gKiBUaGlzIHNob3VsZCBiZSBjYWxsZWQgaW4geW91ciBhcHAuY29uZmlnLnRzIChmb3Igc3RhbmRhbG9uZSkgb3IgbWFpbi50cy5cbiAqXG4gKiBUaGlzIHByb3ZpZGVyIGlzIGVzc2VudGlhbCBmb3IgJ0FuZ3VsYXIgTm9kZXMnIHRvIHdvcmsgY29ycmVjdGx5LCBhcyBpdCBjYXB0dXJlcyB0aGVcbiAqIHJvb3QgSW5qZWN0b3IgcmVxdWlyZWQgdG8gaW5zdGFudGlhdGUgY3VzdG9tIEFuZ3VsYXIgY29tcG9uZW50cyB3aXRoaW4gdGhlIGVkaXRvci5cbiAqIEBleGFtcGxlXG4gKiBgYGB0c1xuICogYm9vdHN0cmFwQXBwbGljYXRpb24oQXBwQ29tcG9uZW50LCB7XG4gKiAgIHByb3ZpZGVyczogW1xuICogICAgIHByb3ZpZGVBdGVFZGl0b3Ioe1xuICogICAgICAgdGhlbWU6ICdkYXJrJyxcbiAqICAgICAgIG1vZGU6ICdzZWFtbGVzcydcbiAqICAgICB9KVxuICogICBdXG4gKiB9KTtcbiAqIGBgYFxuICovXG5leHBvcnQgZnVuY3Rpb24gcHJvdmlkZUF0ZUVkaXRvcihjb25maWc/OiBBdGVFZGl0b3JDb25maWcpOiBFbnZpcm9ubWVudFByb3ZpZGVycyB7XG4gIHJldHVybiBtYWtlRW52aXJvbm1lbnRQcm92aWRlcnMoW1xuICAgIHtcbiAgICAgIHByb3ZpZGU6IEFURV9HTE9CQUxfQ09ORklHLFxuICAgICAgdXNlVmFsdWU6IGNvbmZpZyB8fCB7fSxcbiAgICB9LFxuICAgIHtcbiAgICAgIHByb3ZpZGU6IEFQUF9JTklUSUFMSVpFUixcbiAgICAgIHVzZUZhY3Rvcnk6IChpbmplY3RvcjogSW5qZWN0b3IpID0+ICgpID0+IHtcbiAgICAgICAgc2V0R2xvYmFsSW5qZWN0b3IoaW5qZWN0b3IpO1xuICAgICAgfSxcbiAgICAgIGRlcHM6IFtJbmplY3Rvcl0sXG4gICAgICBtdWx0aTogdHJ1ZSxcbiAgICB9LFxuICBdKTtcbn1cbiJdfQ==
|
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
import { Directive, input, viewChild, inject, effect, } from "@angular/core";
|
|
2
|
+
import tippy, { sticky } from "tippy.js";
|
|
3
|
+
import { AteEditorCommandsService } from "../../../services/ate-editor-commands.service";
|
|
4
|
+
import { AteI18nService } from "../../../services/ate-i18n.service";
|
|
5
|
+
import * as i0 from "@angular/core";
|
|
6
|
+
/**
|
|
7
|
+
* Base abstract class for all Bubble Menus (Text, Image, Table, Cell).
|
|
8
|
+
* Handles common logic for Tippy.js initialization, positioning, and visibility.
|
|
9
|
+
*/
|
|
10
|
+
export class AteBaseBubbleMenu {
|
|
11
|
+
constructor() {
|
|
12
|
+
this.i18nService = inject(AteI18nService);
|
|
13
|
+
this.editorCommands = inject(AteEditorCommandsService);
|
|
14
|
+
// Core Inputs
|
|
15
|
+
this.editor = input.required();
|
|
16
|
+
// Required viewChild for the menu container
|
|
17
|
+
this.menuRef = viewChild.required("menuRef");
|
|
18
|
+
// Internal State
|
|
19
|
+
this.tippyInstance = null;
|
|
20
|
+
this.updateTimeout = null;
|
|
21
|
+
// Toolbar interaction state (from centralized service)
|
|
22
|
+
this.isToolbarInteracting = this.editorCommands.isToolbarInteracting;
|
|
23
|
+
// Reactive state alias for templates
|
|
24
|
+
this.state = this.editorCommands.editorState;
|
|
25
|
+
/**
|
|
26
|
+
* Core logic to decide whether to show or hide the menu.
|
|
27
|
+
*/
|
|
28
|
+
this.updateMenu = () => {
|
|
29
|
+
if (this.updateTimeout) {
|
|
30
|
+
clearTimeout(this.updateTimeout);
|
|
31
|
+
}
|
|
32
|
+
this.updateTimeout = window.setTimeout(() => {
|
|
33
|
+
const ed = this.editor();
|
|
34
|
+
if (!ed) {
|
|
35
|
+
return;
|
|
36
|
+
}
|
|
37
|
+
// Hide when interacting with the main toolbar
|
|
38
|
+
if (this.isToolbarInteracting()) {
|
|
39
|
+
this.hideTippy();
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
if (this.shouldShow()) {
|
|
43
|
+
this.showTippy();
|
|
44
|
+
}
|
|
45
|
+
else {
|
|
46
|
+
this.hideTippy();
|
|
47
|
+
}
|
|
48
|
+
}, 10);
|
|
49
|
+
};
|
|
50
|
+
// Effect to reactively update the menu when editor state
|
|
51
|
+
// or toolbar interaction changes.
|
|
52
|
+
effect(() => {
|
|
53
|
+
this.state();
|
|
54
|
+
this.isToolbarInteracting();
|
|
55
|
+
// Also react to link/color edit modes to hide when sub-menus activate
|
|
56
|
+
this.editorCommands.linkEditMode();
|
|
57
|
+
this.editorCommands.colorEditMode();
|
|
58
|
+
this.updateMenu();
|
|
59
|
+
}, { allowSignalWrites: true });
|
|
60
|
+
}
|
|
61
|
+
ngAfterViewInit() {
|
|
62
|
+
this.initTippy();
|
|
63
|
+
}
|
|
64
|
+
ngOnDestroy() {
|
|
65
|
+
if (this.updateTimeout) {
|
|
66
|
+
clearTimeout(this.updateTimeout);
|
|
67
|
+
}
|
|
68
|
+
if (this.tippyInstance) {
|
|
69
|
+
this.tippyInstance.destroy();
|
|
70
|
+
this.tippyInstance = null;
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* Initializes the Tippy instance.
|
|
75
|
+
* Can be overridden for specific Tippy configurations.
|
|
76
|
+
*/
|
|
77
|
+
initTippy() {
|
|
78
|
+
const nativeElement = this.menuRef().nativeElement;
|
|
79
|
+
if (!nativeElement) {
|
|
80
|
+
return;
|
|
81
|
+
}
|
|
82
|
+
const ed = this.editor();
|
|
83
|
+
if (this.tippyInstance) {
|
|
84
|
+
this.tippyInstance.destroy();
|
|
85
|
+
}
|
|
86
|
+
this.tippyInstance = tippy(document.body, {
|
|
87
|
+
content: nativeElement,
|
|
88
|
+
trigger: "manual",
|
|
89
|
+
placement: "top-start",
|
|
90
|
+
theme: "ate-bubble-menu",
|
|
91
|
+
appendTo: () => ed?.options?.element || document.body,
|
|
92
|
+
interactive: true,
|
|
93
|
+
hideOnClick: false,
|
|
94
|
+
arrow: false,
|
|
95
|
+
offset: [0, 8],
|
|
96
|
+
plugins: [sticky],
|
|
97
|
+
sticky: false,
|
|
98
|
+
getReferenceClientRect: () => this.getSelectionRect(),
|
|
99
|
+
popperOptions: {
|
|
100
|
+
modifiers: [
|
|
101
|
+
{
|
|
102
|
+
name: "preventOverflow",
|
|
103
|
+
options: {
|
|
104
|
+
boundary: this.editor().options.element || document.body,
|
|
105
|
+
padding: 8,
|
|
106
|
+
},
|
|
107
|
+
},
|
|
108
|
+
{
|
|
109
|
+
name: "flip",
|
|
110
|
+
options: {
|
|
111
|
+
fallbackPlacements: ["bottom-start", "top-end", "bottom-end"],
|
|
112
|
+
},
|
|
113
|
+
},
|
|
114
|
+
],
|
|
115
|
+
},
|
|
116
|
+
onShow: instance => this.onTippyShow(instance),
|
|
117
|
+
onHide: instance => this.onTippyHide(instance),
|
|
118
|
+
});
|
|
119
|
+
this.updateMenu();
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* Helper to show the Tippy instance with updated positioning.
|
|
123
|
+
*/
|
|
124
|
+
showTippy() {
|
|
125
|
+
if (!this.tippyInstance) {
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
// Update position before showing
|
|
129
|
+
this.tippyInstance.setProps({
|
|
130
|
+
getReferenceClientRect: () => this.getSelectionRect(),
|
|
131
|
+
sticky: "reference",
|
|
132
|
+
});
|
|
133
|
+
this.tippyInstance.show();
|
|
134
|
+
}
|
|
135
|
+
/**
|
|
136
|
+
* Helper to hide the Tippy instance.
|
|
137
|
+
*/
|
|
138
|
+
hideTippy() {
|
|
139
|
+
if (this.tippyInstance) {
|
|
140
|
+
this.tippyInstance.setProps({ sticky: false });
|
|
141
|
+
this.tippyInstance.hide();
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Common command handler for buttons in the menu.
|
|
146
|
+
*/
|
|
147
|
+
onCommand(command, event) {
|
|
148
|
+
if (event) {
|
|
149
|
+
event.preventDefault();
|
|
150
|
+
event.stopPropagation();
|
|
151
|
+
}
|
|
152
|
+
const ed = this.editor();
|
|
153
|
+
if (ed) {
|
|
154
|
+
this.executeCommand(ed, command);
|
|
155
|
+
this.updateMenu();
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
/**
|
|
159
|
+
* Shared helper to get the bounding rect of the current selection.
|
|
160
|
+
* Uses a combination of native selection and ProseMirror coordinates.
|
|
161
|
+
*/
|
|
162
|
+
getRectForSelection(ed) {
|
|
163
|
+
if (!ed) {
|
|
164
|
+
return new DOMRect(0, 0, 0, 0);
|
|
165
|
+
}
|
|
166
|
+
const { from, to, empty } = ed.state.selection;
|
|
167
|
+
if (empty) {
|
|
168
|
+
return new DOMRect(-9999, -9999, 0, 0);
|
|
169
|
+
}
|
|
170
|
+
// 1. Try native selection for multi-line accuracy
|
|
171
|
+
const selection = window.getSelection();
|
|
172
|
+
if (selection && selection.rangeCount > 0) {
|
|
173
|
+
const range = selection.getRangeAt(0);
|
|
174
|
+
const rect = range.getBoundingClientRect();
|
|
175
|
+
// Ensure the rect is valid and belongs to the editor
|
|
176
|
+
if (rect.width > 0 && rect.height > 0) {
|
|
177
|
+
return rect;
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
// 2. Fallback to Tiptap coordinates for precision (single line / edge cases)
|
|
181
|
+
const start = ed.view.coordsAtPos(from);
|
|
182
|
+
const end = ed.view.coordsAtPos(to);
|
|
183
|
+
const top = Math.min(start.top, end.top);
|
|
184
|
+
const bottom = Math.max(start.bottom, end.bottom);
|
|
185
|
+
const left = Math.min(start.left, end.left);
|
|
186
|
+
const right = Math.max(start.right, end.right);
|
|
187
|
+
return new DOMRect(left, top, right - left, bottom - top);
|
|
188
|
+
}
|
|
189
|
+
/**
|
|
190
|
+
* Optional hook called when Tippy is about to be shown.
|
|
191
|
+
*/
|
|
192
|
+
onTippyShow(_instance) {
|
|
193
|
+
/* empty */
|
|
194
|
+
}
|
|
195
|
+
/**
|
|
196
|
+
* Optional hook called when Tippy is about to be hidden.
|
|
197
|
+
*/
|
|
198
|
+
onTippyHide(_instance) {
|
|
199
|
+
/* empty */
|
|
200
|
+
}
|
|
201
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteBaseBubbleMenu, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
202
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.2.0", version: "18.2.14", type: AteBaseBubbleMenu, inputs: { editor: { classPropertyName: "editor", publicName: "editor", isSignal: true, isRequired: true, transformFunction: null } }, viewQueries: [{ propertyName: "menuRef", first: true, predicate: ["menuRef"], descendants: true, isSignal: true }], ngImport: i0 }); }
|
|
203
|
+
}
|
|
204
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteBaseBubbleMenu, decorators: [{
|
|
205
|
+
type: Directive
|
|
206
|
+
}], ctorParameters: () => [] });
|
|
207
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXRlLWJhc2UtYnViYmxlLW1lbnUuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi8uLi9wcm9qZWN0cy9hbmd1bGFyLXRpcHRhcC1lZGl0b3Ivc3JjL2xpYi9jb21wb25lbnRzL2J1YmJsZS1tZW51cy9iYXNlL2F0ZS1iYXNlLWJ1YmJsZS1tZW51LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFDTCxTQUFTLEVBQ1QsS0FBSyxFQUNMLFNBQVMsRUFHVCxNQUFNLEVBQ04sTUFBTSxHQUVQLE1BQU0sZUFBZSxDQUFDO0FBQ3ZCLE9BQU8sS0FBSyxFQUFFLEVBQTZCLE1BQU0sRUFBRSxNQUFNLFVBQVUsQ0FBQztBQUVwRSxPQUFPLEVBQUUsd0JBQXdCLEVBQUUsTUFBTSwrQ0FBK0MsQ0FBQztBQUN6RixPQUFPLEVBQUUsY0FBYyxFQUFFLE1BQU0sb0NBQW9DLENBQUM7O0FBRXBFOzs7R0FHRztBQUVILE1BQU0sT0FBZ0IsaUJBQWlCO0lBb0JyQztRQW5CbUIsZ0JBQVcsR0FBRyxNQUFNLENBQUMsY0FBYyxDQUFDLENBQUM7UUFDckMsbUJBQWMsR0FBRyxNQUFNLENBQUMsd0JBQXdCLENBQUMsQ0FBQztRQUVyRSxjQUFjO1FBQ2QsV0FBTSxHQUFHLEtBQUssQ0FBQyxRQUFRLEVBQVUsQ0FBQztRQUVsQyw0Q0FBNEM7UUFDNUMsWUFBTyxHQUFHLFNBQVMsQ0FBQyxRQUFRLENBQTZCLFNBQVMsQ0FBQyxDQUFDO1FBRXBFLGlCQUFpQjtRQUNQLGtCQUFhLEdBQXlCLElBQUksQ0FBQztRQUMzQyxrQkFBYSxHQUFrQixJQUFJLENBQUM7UUFFOUMsdURBQXVEO1FBQ3BDLHlCQUFvQixHQUFHLElBQUksQ0FBQyxjQUFjLENBQUMsb0JBQW9CLENBQUM7UUFFbkYscUNBQXFDO1FBQzVCLFVBQUssR0FBRyxJQUFJLENBQUMsY0FBYyxDQUFDLFdBQVcsQ0FBQztRQWdGakQ7O1dBRUc7UUFDSCxlQUFVLEdBQUcsR0FB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QUFqQixpQkFBaUI7OzRGQUFqQixpQkFBaUI7a0JBRHRDLFNBQVMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQge1xuICBEaXJlY3RpdmUsXG4gIGlucHV0LFxuICB2aWV3Q2hpbGQsXG4gIEVsZW1lbnRSZWYsXG4gIE9uRGVzdHJveSxcbiAgaW5qZWN0LFxuICBlZmZlY3QsXG4gIEFmdGVyVmlld0luaXQsXG59IGZyb20gXCJAYW5ndWxhci9jb3JlXCI7XG5pbXBvcnQgdGlwcHksIHsgSW5zdGFuY2UgYXMgVGlwcHlJbnN0YW5jZSwgc3RpY2t5IH0gZnJvbSBcInRpcHB5LmpzXCI7XG5pbXBvcnQgeyBFZGl0b3IgfSBmcm9tIFwiQHRpcHRhcC9jb3JlXCI7XG5pbXBvcnQgeyBBdGVFZGl0b3JDb21tYW5kc1NlcnZpY2UgfSBmcm9tIFwiLi4vLi4vLi4vc2VydmljZXMvYXRlLWVkaXRvci1jb21tYW5kcy5zZXJ2aWNlXCI7XG5pbXBvcnQgeyBBdGVJMThuU2VydmljZSB9IGZyb20gXCIuLi8uLi8uLi9zZXJ2aWNlcy9hdGUtaTE4bi5zZXJ2aWNlXCI7XG5cbi8qKlxuICogQmFzZSBhYnN0cmFjdCBjbGFzcyBmb3IgYWxsIEJ1YmJsZSBNZW51cyAoVGV4dCwgSW1hZ2UsIFRhYmxlLCBDZWxsKS5cbiAqIEhhbmRsZXMgY29tbW9uIGxvZ2ljIGZvciBUaXBweS5qcyBpbml0aWFsaXphdGlvbiwgcG9zaXRpb25pbmcsIGFuZCB2aXNpYmlsaXR5LlxuICovXG5ARGlyZWN0aXZlKClcbmV4cG9ydCBhYnN0cmFjdCBjbGFzcyBBdGVCYXNlQnViYmxlTWVudSBpbXBsZW1lbnRzIEFmdGVyVmlld0luaXQsIE9uRGVzdHJveSB7XG4gIHByb3RlY3RlZCByZWFkb25seSBpMThuU2VydmljZSA9IGluamVjdChBdGVJMThuU2VydmljZSk7XG4gIHByb3RlY3RlZCByZWFkb25seSBlZGl0b3JDb21tYW5kcyA9IGluamVjdChBdGVFZGl0b3JDb21tYW5kc1NlcnZpY2UpO1xuXG4gIC8vIENvcmUgSW5wdXRzXG4gIGVkaXRvciA9IGlucHV0LnJlcXVpcmVkPEVkaXRvcj4oKTtcblxuICAvLyBSZXF1aXJlZCB2aWV3Q2hpbGQgZm9yIHRoZSBtZW51IGNvbnRhaW5lclxuICBtZW51UmVmID0gdmlld0NoaWxkLnJlcXVpcmVkPEVsZW1lbnRSZWY8SFRNTERpdkVsZW1lbnQ+PihcIm1lbnVSZWZcIik7XG5cbiAgLy8gSW50ZXJuYWwgU3RhdGVcbiAgcHJvdGVjdGVkIHRpcHB5SW5zdGFuY2U6IFRpcHB5SW5zdGFuY2UgfCBudWxsID0gbnVsbDtcbiAgcHJvdGVjdGVkIHVwZGF0ZVRpbWVvdXQ6IG51bWJlciB8IG51bGwgPSBudWxsO1xuXG4gIC8vIFRvb2xiYXIgaW50ZXJhY3Rpb24gc3RhdGUgKGZyb20gY2VudHJhbGl6ZWQgc2VydmljZSlcbiAgcHJvdGVjdGVkIHJlYWRvbmx5IGlzVG9vbGJhckludGVyYWN0aW5nID0gdGhpcy5lZGl0b3JDb21tYW5kcy5pc1Rvb2xiYXJJbnRlcmFjdGluZztcblxuICAvLyBSZWFjdGl2ZSBzdGF0ZSBhbGlhcyBmb3IgdGVtcGxhdGVzXG4gIHJlYWRvbmx5IHN0YXRlID0gdGhpcy5lZGl0b3JDb21tYW5kcy5lZGl0b3JTdGF0ZTtcblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICAvLyBFZmZlY3QgdG8gcmVhY3RpdmVseSB1cGRhdGUgdGhlIG1lbnUgd2hlbiBlZGl0b3Igc3RhdGVcbiAgICAvLyBvciB0b29sYmFyIGludGVyYWN0aW9uIGNoYW5nZXMuXG4gICAgZWZmZWN0KCgpID0+IHtcbiAgICAgIHRoaXMuc3RhdGUoKTtcbiAgICAgIHRoaXMuaXNUb29sYmFySW50ZXJhY3RpbmcoKTtcbiAgICAgIC8vIEFsc28gcmVhY3QgdG8gbGluay9jb2xvciBlZGl0IG1vZGVzIHRvIGhpZGUgd2hlbiBzdWItbWVudXMgYWN0aXZhdGVcbiAgICAgIHRoaXMuZWRpdG9yQ29tbWFuZHMubGlua0VkaXRNb2RlKCk7XG4gICAgICB0aGlzLmVkaXRvckNvbW1hbmRzLmNvbG9yRWRpdE1vZGUoKTtcblxuICAgICAgdGhpcy51cGRhdGVNZW51KCk7XG4gICAgfSwgeyBhbGxvd1NpZ25hbFdyaXRlczogdHJ1ZSB9KTtcbiAgfVxuXG4gIG5nQWZ0ZXJWaWV3SW5pdCgpIHtcbiAgICB0aGlzLmluaXRUaXBweSgpO1xuICB9XG5cbiAgbmdPbkRlc3Ryb3koKSB7XG4gICAgaWYgKHRoaXMudXBkYXRlVGltZW91dCkge1xuICAgICAgY2xlYXJUaW1lb3V0KHRoaXMudXBkYXRlVGltZW91dCk7XG4gICAgfVxuICAgIGlmICh0aGlzLnRpcHB5SW5zdGFuY2UpIHtcbiAgICAgIHRoaXMudGlwcHlJbnN0YW5jZS5kZXN0cm95KCk7XG4gICAgICB0aGlzLnRpcHB5SW5zdGFuY2UgPSBudWxsO1xuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBJbml0aWFsaXplcyB0aGUgVGlwcHkgaW5zdGFuY2UuXG4gICAqIENhbiBiZSBvdmVycmlkZGVuIGZvciBzcGVjaWZpYyBUaXBweSBjb25maWd1cmF0aW9ucy5cbiAgICovXG4gIHByb3RlY3RlZCBpbml0VGlwcHkoKSB7XG4gICAgY29uc3QgbmF0aXZlRWxlbWVudCA9IHRoaXMubWVudVJlZigpLm5hdGl2ZUVsZW1lbnQ7XG4gICAgaWYgKCFuYXRpdmVFbGVtZW50KSB7cmV0dXJuO31cblxuICAgIGNvbnN0IGVkID0gdGhpcy5lZGl0b3IoKTtcbiAgICBpZiAodGhpcy50aXBweUluc3RhbmNlKSB7XG4gICAgICB0aGlzLnRpcHB5SW5zdGFuY2UuZGVzdHJveSgpO1xuICAgIH1cblxuICAgIHRoaXMudGlwcHlJbnN0YW5jZSA9IHRpcHB5KGRvY3VtZW50LmJvZHksIHtcbiAgICAgIGNvbnRlbnQ6IG5hdGl2ZUVsZW1lbnQsXG4gICAgICB0cmlnZ2VyOiBcIm1hbnVhbFwiLFxuICAgICAgcGxhY2VtZW50OiBcInRvcC1zdGFydFwiLFxuICAgICAgdGhlbWU6IFwiYXRlLWJ1YmJsZS1tZW51XCIsXG4gICAgICBhcHBlbmRUbzogKCkgPT4gKGVkPy5vcHRpb25zPy5lbGVtZW50IGFzIEhUTUxFbGVtZW50KSB8fCBkb2N1bWVudC5ib2R5LFxuICAgICAgaW50ZXJhY3RpdmU6IHRydWUsXG4gICAgICBoaWRlT25DbGljazogZmFsc2UsXG4gICAgICBhcnJvdzogZmFsc2UsXG4gICAgICBvZmZzZXQ6IFswLCA4XSxcbiAgICAgIHBsdWdpbnM6IFtzdGlja3ldLFxuICAgICAgc3RpY2t5OiBmYWxzZSxcbiAgICAgIGdldFJlZmVyZW5jZUNsaWVudFJlY3Q6ICgpID0+IHRoaXMuZ2V0U2VsZWN0aW9uUmVjdCgpLFxuICAgICAgcG9wcGVyT3B0aW9uczoge1xuICAgICAgICBtb2RpZmllcnM6IFtcbiAgICAgICAgICB7XG4gICAgICAgICAgICBuYW1lOiBcInByZXZlbnRPdmVyZmxvd1wiLFxuICAgICAgICAgICAgb3B0aW9uczoge1xuICAgICAgICAgICAgICBib3VuZGFyeTogKHRoaXMuZWRpdG9yKCkub3B0aW9ucy5lbGVtZW50IGFzIEhUTUxFbGVtZW50KSB8fCBkb2N1bWVudC5ib2R5LFxuICAgICAgICAgICAgICBwYWRkaW5nOiA4LFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIG5hbWU6IFwiZmxpcFwiLFxuICAgICAgICAgICAgb3B0aW9uczoge1xuICAgICAgICAgICAgICBmYWxsYmFja1BsYWNlbWVudHM6IFtcImJvdHRvbS1zdGFydFwiLCBcInRvcC1lbmRcIiwgXCJib3R0b20tZW5kXCJdLFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9LFxuICAgICAgICBdLFxuICAgICAgfSxcbiAgICAgIG9uU2hvdzogaW5zdGFuY2UgPT4gdGhpcy5vblRpcHB5U2hvdyhpbnN0YW5jZSksXG4gICAgICBvbkhpZGU6IGluc3RhbmNlID0+IHRoaXMub25UaXBweUhpZGUoaW5zdGFuY2UpLFxuICAgIH0pO1xuXG4gICAgdGhpcy51cGRhdGVNZW51KCk7XG4gIH1cblxuICAvKipcbiAgICogQ29yZSBsb2dpYyB0byBkZWNpZGUgd2hldGhlciB0byBzaG93IG9yIGhpZGUgdGhlIG1lbnUuXG4gICAqL1xuICB1cGRhdGVNZW51ID0gKCkgPT4ge1xuICAgIGlmICh0aGlzLnVwZGF0ZVRpbWVvdXQpIHtcbiAgICAgIGNsZWFyVGltZW91dCh0aGlzLnVwZGF0ZVRpbWVvdXQpO1xuICAgIH1cblxuICAgIHRoaXMudXBkYXRlVGltZW91dCA9IHdpbmRvdy5zZXRUaW1lb3V0KCgpID0+IHtcbiAgICAgIGNvbnN0IGVkID0gdGhpcy5lZGl0b3IoKTtcbiAgICAgIGlmICghZWQpIHtcbiAgICAgICAgcmV0dXJuO1xuICAgICAgfVxuXG4gICAgICAvLyBIaWRlIHdoZW4gaW50ZXJhY3Rpbmcgd2l0aCB0aGUgbWFpbiB0b29sYmFyXG4gICAgICBpZiAodGhpcy5pc1Rvb2xiYXJJbnRlcmFjdGluZygpKSB7XG4gICAgICAgIHRoaXMuaGlkZVRpcHB5KCk7XG4gICAgICAgIHJldHVybjtcbiAgICAgIH1cblxuICAgICAgaWYgKHRoaXMuc2hvdWxkU2hvdygpKSB7XG4gICAgICAgIHRoaXMuc2hvd1RpcHB5KCk7XG4gICAgICB9IGVsc2Uge1xuICAgICAgICB0aGlzLmhpZGVUaXBweSgpO1xuICAgICAgfVxuICAgIH0sIDEwKTtcbiAgfTtcblxuICAvKipcbiAgICogSGVscGVyIHRvIHNob3cgdGhlIFRpcHB5IGluc3RhbmNlIHdpdGggdXBkYXRlZCBwb3NpdGlvbmluZy5cbiAgICovXG4gIHNob3dUaXBweSgpIHtcbiAgICBpZiAoIXRoaXMudGlwcHlJbnN0YW5jZSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIC8vIFVwZGF0ZSBwb3NpdGlvbiBiZWZvcmUgc2hvd2luZ1xuICAgIHRoaXMudGlwcHlJbnN0YW5jZS5zZXRQcm9wcyh7XG4gICAgICBnZXRSZWZlcmVuY2VDbGllbnRSZWN0OiAoKSA9PiB0aGlzLmdldFNlbGVjdGlvblJlY3QoKSxcbiAgICAgIHN0aWNreTogXCJyZWZlcmVuY2VcIixcbiAgICB9KTtcbiAgICB0aGlzLnRpcHB5SW5zdGFuY2Uuc2hvdygpO1xuICB9XG5cbiAgLyoqXG4gICAqIEhlbHBlciB0byBoaWRlIHRoZSBUaXBweSBpbnN0YW5jZS5cbiAgICovXG4gIGhpZGVUaXBweSgpIHtcbiAgICBpZiAodGhpcy50aXBweUluc3RhbmNlKSB7XG4gICAgICB0aGlzLnRpcHB5SW5zdGFuY2Uuc2V0UHJvcHMoeyBzdGlja3k6IGZhbHNlIH0pO1xuICAgICAgdGhpcy50aXBweUluc3RhbmNlLmhpZGUoKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogQ29tbW9uIGNvbW1hbmQgaGFuZGxlciBmb3IgYnV0dG9ucyBpbiB0aGUgbWVudS5cbiAgICovXG4gIG9uQ29tbWFuZChjb21tYW5kOiBzdHJpbmcsIGV2ZW50PzogRXZlbnQpIHtcbiAgICBpZiAoZXZlbnQpIHtcbiAgICAgIGV2ZW50LnByZXZlbnREZWZhdWx0KCk7XG4gICAgICBldmVudC5zdG9wUHJvcGFnYXRpb24oKTtcbiAgICB9XG4gICAgY29uc3QgZWQgPSB0aGlzLmVkaXRvcigpO1xuICAgIGlmIChlZCkge1xuICAgICAgdGhpcy5leGVjdXRlQ29tbWFuZChlZCwgY29tbWFuZCk7XG4gICAgICB0aGlzLnVwZGF0ZU1lbnUoKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogU2hhcmVkIGhlbHBlciB0byBnZXQgdGhlIGJvdW5kaW5nIHJlY3Qgb2YgdGhlIGN1cnJlbnQgc2VsZWN0aW9uLlxuICAgKiBVc2VzIGEgY29tYmluYXRpb24gb2YgbmF0aXZlIHNlbGVjdGlvbiBhbmQgUHJvc2VNaXJyb3IgY29vcmRpbmF0ZXMuXG4gICAqL1xuICBwcm90ZWN0ZWQgZ2V0UmVjdEZvclNlbGVjdGlvbihlZDogRWRpdG9yKTogRE9NUmVjdCB7XG4gICAgaWYgKCFlZCkge1xuICAgICAgcmV0dXJuIG5ldyBET01SZWN0KDAsIDAsIDAsIDApO1xuICAgIH1cblxuICAgIGNvbnN0IHsgZnJvbSwgdG8sIGVtcHR5IH0gPSBlZC5zdGF0ZS5zZWxlY3Rpb247XG4gICAgaWYgKGVtcHR5KSB7XG4gICAgICByZXR1cm4gbmV3IERPTVJlY3QoLTk5OTksIC05OTk5LCAwLCAwKTtcbiAgICB9XG5cbiAgICAvLyAxLiBUcnkgbmF0aXZlIHNlbGVjdGlvbiBmb3IgbXVsdGktbGluZSBhY2N1cmFjeVxuICAgIGNvbnN0IHNlbGVjdGlvbiA9IHdpbmRvdy5nZXRTZWxlY3Rpb24oKTtcbiAgICBpZiAoc2VsZWN0aW9uICYmIHNlbGVjdGlvbi5yYW5nZUNvdW50ID4gMCkge1xuICAgICAgY29uc3QgcmFuZ2UgPSBzZWxlY3Rpb24uZ2V0UmFuZ2VBdCgwKTtcbiAgICAgIGNvbnN0IHJlY3QgPSByYW5nZS5nZXRCb3VuZGluZ0NsaWVudFJlY3QoKTtcblxuICAgICAgLy8gRW5zdXJlIHRoZSByZWN0IGlzIHZhbGlkIGFuZCBiZWxvbmdzIHRvIHRoZSBlZGl0b3JcbiAgICAgIGlmIChyZWN0LndpZHRoID4gMCAmJiByZWN0LmhlaWdodCA+IDApIHtcbiAgICAgICAgcmV0dXJuIHJlY3Q7XG4gICAgICB9XG4gICAgfVxuXG4gICAgLy8gMi4gRmFsbGJhY2sgdG8gVGlwdGFwIGNvb3JkaW5hdGVzIGZvciBwcmVjaXNpb24gKHNpbmdsZSBsaW5lIC8gZWRnZSBjYXNlcylcbiAgICBjb25zdCBzdGFydCA9IGVkLnZpZXcuY29vcmRzQXRQb3MoZnJvbSk7XG4gICAgY29uc3QgZW5kID0gZWQudmlldy5jb29yZHNBdFBvcyh0byk7XG5cbiAgICBjb25zdCB0b3AgPSBNYXRoLm1pbihzdGFydC50b3AsIGVuZC50b3ApO1xuICAgIGNvbnN0IGJvdHRvbSA9IE1hdGgubWF4KHN0YXJ0LmJvdHRvbSwgZW5kLmJvdHRvbSk7XG4gICAgY29uc3QgbGVmdCA9IE1hdGgubWluKHN0YXJ0LmxlZnQsIGVuZC5sZWZ0KTtcbiAgICBjb25zdCByaWdodCA9IE1hdGgubWF4KHN0YXJ0LnJpZ2h0LCBlbmQucmlnaHQpO1xuXG4gICAgcmV0dXJuIG5ldyBET01SZWN0KGxlZnQsIHRvcCwgcmlnaHQgLSBsZWZ0LCBib3R0b20gLSB0b3ApO1xuICB9XG5cbiAgLy8gLS0tIEFic3RyYWN0IG1ldGhvZHMgdG8gYmUgaW1wbGVtZW50ZWQgYnkgc3ViLWNvbXBvbmVudHMgLS0tXG5cbiAgLyoqXG4gICAqIFJldHVybnMgdGhlIFJlY3QgcmVwcmVzZW50aW5nIHRoZSB0YXJnZXQgZm9yIHBvc2l0aW9uaW5nIHRoZSBtZW51LlxuICAgKi9cbiAgYWJzdHJhY3QgZ2V0U2VsZWN0aW9uUmVjdCgpOiBET01SZWN0O1xuXG4gIC8qKlxuICAgKiBSZXR1cm5zIHdoZXRoZXIgdGhlIG1lbnUgc2hvdWxkIGJlIGRpc3BsYXllZCBiYXNlZCBvbiBjdXJyZW50IHN0YXRlLlxuICAgKi9cbiAgYWJzdHJhY3Qgc2hvdWxkU2hvdygpOiBib29sZWFuO1xuXG4gIC8qKlxuICAgKiBFeGVjdXRlcyB0aGUgZ2l2ZW4gY29tbWFuZCBvbiB0aGUgZWRpdG9yLlxuICAgKi9cbiAgcHJvdGVjdGVkIGFic3RyYWN0IGV4ZWN1dGVDb21tYW5kKGVkaXRvcjogRWRpdG9yLCBjb21tYW5kOiBzdHJpbmcsIC4uLmFyZ3M6IHVua25vd25bXSk6IHZvaWQ7XG5cbiAgLyoqXG4gICAqIE9wdGlvbmFsIGhvb2sgY2FsbGVkIHdoZW4gVGlwcHkgaXMgYWJvdXQgdG8gYmUgc2hvd24uXG4gICAqL1xuICBwcm90ZWN0ZWQgb25UaXBweVNob3coX2luc3RhbmNlOiBUaXBweUluc3RhbmNlKSB7XG4gICAgLyogZW1wdHkgKi9cbiAgfVxuXG4gIC8qKlxuICAgKiBPcHRpb25hbCBob29rIGNhbGxlZCB3aGVuIFRpcHB5IGlzIGFib3V0IHRvIGJlIGhpZGRlbi5cbiAgICovXG4gIHByb3RlY3RlZCBvblRpcHB5SGlkZShfaW5zdGFuY2U6IFRpcHB5SW5zdGFuY2UpIHtcbiAgICAvKiBlbXB0eSAqL1xuICB9XG59XG4iXX0=
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
import { Directive, input, viewChild, inject, effect, } from "@angular/core";
|
|
2
|
+
import tippy, { sticky } from "tippy.js";
|
|
3
|
+
import { AteEditorCommandsService } from "../../../services/ate-editor-commands.service";
|
|
4
|
+
import { AteI18nService } from "../../../services/ate-i18n.service";
|
|
5
|
+
import * as i0 from "@angular/core";
|
|
6
|
+
/**
|
|
7
|
+
* Base abstract class for Sub-Bubble Menus (Link, Color).
|
|
8
|
+
* These menus are "sub-menus" of the main bubble menu or triggered/anchored by specific UI elements.
|
|
9
|
+
*/
|
|
10
|
+
export class AteBaseSubBubbleMenu {
|
|
11
|
+
constructor() {
|
|
12
|
+
this.i18nService = inject(AteI18nService);
|
|
13
|
+
this.editorCommands = inject(AteEditorCommandsService);
|
|
14
|
+
// Core Inputs
|
|
15
|
+
this.editor = input.required();
|
|
16
|
+
// Required viewChild for the menu container
|
|
17
|
+
this.menuRef = viewChild.required("menuRef");
|
|
18
|
+
// Internal State
|
|
19
|
+
this.tippyInstance = null;
|
|
20
|
+
this.updateTimeout = null;
|
|
21
|
+
// Reactive state alias for templates
|
|
22
|
+
this.state = this.editorCommands.editorState;
|
|
23
|
+
/**
|
|
24
|
+
* Core logic to decide whether to show or hide the menu.
|
|
25
|
+
*/
|
|
26
|
+
this.updateMenu = () => {
|
|
27
|
+
if (this.updateTimeout) {
|
|
28
|
+
clearTimeout(this.updateTimeout);
|
|
29
|
+
}
|
|
30
|
+
this.updateTimeout = setTimeout(() => {
|
|
31
|
+
if (this.shouldShow()) {
|
|
32
|
+
this.showTippy();
|
|
33
|
+
}
|
|
34
|
+
else {
|
|
35
|
+
this.hideTippy();
|
|
36
|
+
}
|
|
37
|
+
}, 10);
|
|
38
|
+
};
|
|
39
|
+
// Reactive effect for menu updates (re-positioning)
|
|
40
|
+
effect(() => {
|
|
41
|
+
// Monitor editor state and specific sub-menu states
|
|
42
|
+
this.state();
|
|
43
|
+
this.onStateChange();
|
|
44
|
+
this.updateMenu();
|
|
45
|
+
}, { allowSignalWrites: true });
|
|
46
|
+
}
|
|
47
|
+
ngAfterViewInit() {
|
|
48
|
+
this.initTippy();
|
|
49
|
+
}
|
|
50
|
+
ngOnDestroy() {
|
|
51
|
+
if (this.updateTimeout) {
|
|
52
|
+
clearTimeout(this.updateTimeout);
|
|
53
|
+
}
|
|
54
|
+
if (this.tippyInstance) {
|
|
55
|
+
this.tippyInstance.destroy();
|
|
56
|
+
this.tippyInstance = null;
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
/**
|
|
60
|
+
* Initializes the Tippy instance with sub-menu defaults.
|
|
61
|
+
*/
|
|
62
|
+
initTippy() {
|
|
63
|
+
const nativeElement = this.menuRef().nativeElement;
|
|
64
|
+
if (!nativeElement) {
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
const ed = this.editor();
|
|
68
|
+
if (this.tippyInstance) {
|
|
69
|
+
this.tippyInstance.destroy();
|
|
70
|
+
}
|
|
71
|
+
this.tippyInstance = tippy(document.body, {
|
|
72
|
+
content: nativeElement,
|
|
73
|
+
trigger: "manual",
|
|
74
|
+
placement: "bottom-start",
|
|
75
|
+
theme: "ate-bubble-menu",
|
|
76
|
+
appendTo: () => ed?.options?.element || document.body,
|
|
77
|
+
interactive: true,
|
|
78
|
+
arrow: false,
|
|
79
|
+
offset: [0, 8],
|
|
80
|
+
hideOnClick: true,
|
|
81
|
+
plugins: [sticky],
|
|
82
|
+
sticky: false,
|
|
83
|
+
getReferenceClientRect: () => this.getSelectionRect(),
|
|
84
|
+
popperOptions: {
|
|
85
|
+
modifiers: [
|
|
86
|
+
{
|
|
87
|
+
name: "preventOverflow",
|
|
88
|
+
options: {
|
|
89
|
+
boundary: ed?.options?.element || document.body,
|
|
90
|
+
padding: 8,
|
|
91
|
+
},
|
|
92
|
+
},
|
|
93
|
+
{
|
|
94
|
+
name: "flip",
|
|
95
|
+
options: { fallbackPlacements: ["top-start", "bottom-end", "top-end"] },
|
|
96
|
+
},
|
|
97
|
+
],
|
|
98
|
+
},
|
|
99
|
+
onShow: instance => this.onTippyShow(instance),
|
|
100
|
+
onHide: instance => this.onTippyHide(instance),
|
|
101
|
+
});
|
|
102
|
+
this.updateMenu();
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Helper to show the Tippy instance with updated positioning.
|
|
106
|
+
*/
|
|
107
|
+
showTippy() {
|
|
108
|
+
if (this.tippyInstance) {
|
|
109
|
+
this.tippyInstance.setProps({ getReferenceClientRect: () => this.getSelectionRect() });
|
|
110
|
+
this.tippyInstance.show();
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* Helper to hide the Tippy instance.
|
|
115
|
+
*/
|
|
116
|
+
hideTippy() {
|
|
117
|
+
this.tippyInstance?.hide();
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* Optional hook called when Tippy is about to be shown.
|
|
121
|
+
*/
|
|
122
|
+
onTippyShow(_instance) {
|
|
123
|
+
/* empty */
|
|
124
|
+
}
|
|
125
|
+
/**
|
|
126
|
+
* Optional hook called when Tippy is about to be hidden.
|
|
127
|
+
*/
|
|
128
|
+
onTippyHide(_instance) {
|
|
129
|
+
/* empty */
|
|
130
|
+
}
|
|
131
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteBaseSubBubbleMenu, deps: [], target: i0.ɵɵFactoryTarget.Directive }); }
|
|
132
|
+
static { this.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.2.0", version: "18.2.14", type: AteBaseSubBubbleMenu, inputs: { editor: { classPropertyName: "editor", publicName: "editor", isSignal: true, isRequired: true, transformFunction: null } }, viewQueries: [{ propertyName: "menuRef", first: true, predicate: ["menuRef"], descendants: true, isSignal: true }], ngImport: i0 }); }
|
|
133
|
+
}
|
|
134
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteBaseSubBubbleMenu, decorators: [{
|
|
135
|
+
type: Directive
|
|
136
|
+
}], ctorParameters: () => [] });
|
|
137
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXRlLWJhc2Utc3ViLWJ1YmJsZS1tZW51LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvYW5ndWxhci10aXB0YXAtZWRpdG9yL3NyYy9saWIvY29tcG9uZW50cy9idWJibGUtbWVudXMvYmFzZS9hdGUtYmFzZS1zdWItYnViYmxlLW1lbnUudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUNMLFNBQVMsRUFDVCxLQUFLLEVBQ0wsU0FBUyxFQUdULE1BQU0sRUFDTixNQUFNLEdBRVAsTUFBTSxlQUFlLENBQUM7QUFDdkIsT0FBTyxLQUFLLEVBQUUsRUFBNkIsTUFBTSxFQUFFLE1BQU0sVUFBVSxDQUFDO0FBRXBFLE9BQU8sRUFBRSx3QkFBd0IsRUFBRSxNQUFNLCtDQUErQyxDQUFDO0FBQ3pGLE9BQU8sRUFBRSxjQUFjLEVBQUUsTUFBTSxvQ0FBb0MsQ0FBQzs7QUFFcEU7OztHQUdHO0FBRUgsTUFBTSxPQUFnQixvQkFBb0I7SUFpQnhDO1FBaEJtQixnQkFBVyxHQUFHLE1BQU0sQ0FBQyxjQUFjLENBQUMsQ0FBQztRQUNyQyxtQkFBYyxHQUFHLE1BQU0sQ0FBQyx3QkFBd0IsQ0FBQyxDQUFDO1FBRXJFLGNBQWM7UUFDZCxXQUFNLEdBQUcsS0FBSyxDQUFDLFFBQVEsRUFBVSxDQUFDO1FBRWxDLDRDQUE0QztRQUM1QyxZQUFPLEdBQUcsU0FBUyxDQUFDLFFBQVEsQ0FBNkIsU0FBUyxDQUFDLENBQUM7UUFFcEUsaUJBQWlCO1FBQ1Asa0JBQWEsR0FBeUIsSUFBSSxDQUFDO1FBQzNDLGtCQUFhLEdBQWtCLElBQUksQ0FBQztRQUU5QyxxQ0FBcUM7UUFDNUIsVUFBSyxHQUFHLElBQUksQ0FBQyxjQUFjLENBQUMsV0FBVyxDQUFDO1FBMEVqRDs7V0FFRztRQUNILGVBQVUsR0FBRyxHQUFHLEVBQUU7WUFDaEIsSUFBSSxJQUFJLENBQUMsYUFBYSxFQUFFLENBQUM7Z0JBQ3ZCLFlBQVksQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLENBQUM7WUFDbkMsQ0FBQztZQUNELElBQUksQ0FBQyxhQUFhLEdBQUcsVUFBVSxDQUFDLEdBQUcsRUFBRTtnQkFDbkMsSUFBSSxJQUFJLENBQUMsVUFBVSxFQUFFLEVBQUUsQ0FBQztvQkFDdEIsSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO2dCQUNuQixDQUFDO3FCQUFNLENBQUM7b0JBQ04sSUFBSSxDQUFDLFNBQVMsRUFBRSxDQUFDO2dCQUNuQixDQUFDO1lBQ0gsQ0FBQyxFQUFFLEVBQUUsQ0FBQyxDQUFDO1FBQ1QsQ0FBQyxDQUFDO1FBckZBLG9EQUFvRDtRQUNwRCxNQUFNLENBQUMsR0FBRyxFQUFFO1lBQ1Ysb0RBQW9EO1lBQ3BELElBQUksQ0FBQyxLQUFLLEVBQUUsQ0FBQztZQUNiLElBQUksQ0FBQyxhQUFhLEVBQUUsQ0FBQztZQUVyQixJQUFJLENBQUMsVUFBVSxFQUFFLENBQUM7UUFDcEIsQ0FBQyxFQUFFLEVBQUUsaUJBQWlCLEVBQUUsSUFBSSxFQUFFLENBQUMsQ0FBQztJQUNsQyxDQUFDO0lBRUQsZUFBZTtRQUNiLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQztJQUNuQixDQUFDO0lBRUQsV0FBVztRQUNULElBQUksSUFBSSxDQUFDLGFBQWEsRUFBRSxDQUFDO1lBQ3ZCLFlBQVksQ0FBQyxJQUFJLENBQUMsYUFBYSxDQUFDLENBQUM7UUFDbkMsQ0FBQztRQUNELElBQUksSUFBSSxDQUFDLGFBQWEsRUFBRSxDQUFDO1lBQ3ZCLElBQUksQ0FBQyxhQUFhLENBQUMsT0FBTyxFQUFFLENBQUM7WUFDN0IsSUFBSSxDQUFDLGFBQWEsR0FBRyxJQUFJLENBQUM7UUFDNUIsQ0FBQztJQUNILENBQUM7SUFFRDs7T0FFRztJQUNPLFNBQVM7UUFDakIsTUFBTSxhQUFhLEdBQUcsSUFBSSxDQUFDLE9BQU8sRUFBRSxDQUFDLGFBQWEsQ0FBQztRQUNuRCxJQUFJLENBQUMsYUFBYSxFQUFFLENBQUM7WUFBQSxPQUFPO1FBQUEsQ0FBQztRQUU3QixNQUFNLEVBQUUsR0FBRyxJQUFJLENBQUMsTUFBTSxFQUFFLENBQUM7UUFDekIsSUFBSSxJQUFJLENBQUMsYUFBYSxFQUFFLENBQUM7WUFDdkIsSUFBSSxDQUFDLGFBQWEsQ0FBQyxPQUFPLEVBQUUsQ0FBQztRQUMvQixDQUFDO1FBRUQsSUFBSSxDQUFDLGFBQWEsR0FBRyxLQUFLLENBQUMsUUFBUSxDQUFDLElBQUksRUFBRTtZQUN4QyxPQUFPLEVBQUUsYUFBYTtZQUN0QixPQUFPLEVBQUUsUUFBUTtZQUNqQixTQUFTLEVBQUUsY0FBYztZQUN6QixLQUFLLEVBQUUsaUJBQWlCO1lBQ3hCLFFBQVEsRUFBRSxHQUFHLEVBQUUsQ0FBRSxFQUFFLEVBQUUsT0FBTyxFQUFFLE9BQXVCLElBQUksUUFBUSxDQUFDLElBQUk7WUFDdEUsV0FBVyxFQUFFLElBQUk7WUFDakIsS0FBSyxFQUFFLEtBQUs7WUFDWixNQUFNLEVBQUUsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDO1lBQ2QsV0FBVyxFQUFFLElBQUk7WUFDakIsT0FBTyxFQUFFLENBQUMsTUFBTSxDQUFDO1lBQ2pCLE1BQU0sRUFBRSxLQUFLO1lBQ2Isc0JBQXNCLEVBQUUsR0FBRyxFQUFFLENBQUMsSUFBSSxDQUFDLGdCQUFnQixFQUFFO1lBQ3JELGFBQWEsRUFBRTtnQkFDYixTQUFTLEVBQUU7b0JBQ1Q7d0JBQ0UsSUFBSSxFQUFFLGlCQUFpQjt3QkFDdkIsT0FBTyxFQUFFOzRCQUNQLFFBQVEsRUFBRyxFQUFFLEVBQUUsT0FBTyxFQUFFLE9BQXVCLElBQUksUUFBUSxDQUFDLElBQUk7NEJBQ2hFLE9BQU8sRUFBRSxDQUFDO3lCQUNYO3FCQUNGO29CQUNEO3dCQUNFLElBQUksRUFBRSxNQUFNO3dCQUNaLE9BQU8sRUFBRSxFQUFFLGtCQUFrQixFQUFFLENBQUMsV0FBVyxFQUFFLFlBQVksRUFBRSxTQUFTLENBQUMsRUFBRTtxQkFDeEU7aUJBQ0Y7YUFDRjtZQUNELE1BQU0sRUFBRSxRQUFRLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDO1lBQzlDLE1BQU0sRUFBRSxRQUFRLENBQUMsRUFBRSxDQUFDLElBQUksQ0FBQyxXQUFXLENBQUMsUUFBUSxDQUFDO1NBQy9DLENBQUMsQ0FBQztRQUVILElBQUksQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNwQixDQUFDO0lBa0JEOztPQUVHO0lBQ08sU0FBUztRQUNqQixJQUFJLElBQUksQ0FBQyxhQUFhLEVBQUUsQ0FBQztZQUN2QixJQUFJLENBQUMsYUFBYSxDQUFDLFFBQVEsQ0FBQyxFQUFFLHNCQUFzQixFQUFFLEdBQUcsRUFBRSxDQUFDLElBQUksQ0FBQyxnQkFBZ0IsRUFBRSxFQUFFLENBQUMsQ0FBQztZQUN2RixJQUFJLENBQUMsYUFBYSxDQUFDLElBQUksRUFBRSxDQUFDO1FBQzVCLENBQUM7SUFDSCxDQUFDO0lBRUQ7O09BRUc7SUFDTyxTQUFTO1FBQ2pCLElBQUksQ0FBQyxhQUFhLEVBQUUsSUFBSSxFQUFFLENBQUM7SUFDN0IsQ0FBQztJQW1CRDs7T0FFRztJQUNPLFdBQVcsQ0FBQyxTQUF3QjtRQUM1QyxXQUFXO0lBQ2IsQ0FBQztJQUVEOztPQUVHO0lBQ08sV0FBVyxDQUFDLFNBQXdCO1FBQzVDLFdBQVc7SUFDYixDQUFDOytHQXZKbUIsb0JBQW9CO21HQUFwQixvQkFBb0I7OzRGQUFwQixvQkFBb0I7a0JBRHpDLFNBQVMiLCJzb3VyY2VzQ29udGVudCI6WyJpbXBvcnQge1xuICBEaXJlY3RpdmUsXG4gIGlucHV0LFxuICB2aWV3Q2hpbGQsXG4gIEVsZW1lbnRSZWYsXG4gIE9uRGVzdHJveSxcbiAgaW5qZWN0LFxuICBlZmZlY3QsXG4gIEFmdGVyVmlld0luaXQsXG59IGZyb20gXCJAYW5ndWxhci9jb3JlXCI7XG5pbXBvcnQgdGlwcHksIHsgSW5zdGFuY2UgYXMgVGlwcHlJbnN0YW5jZSwgc3RpY2t5IH0gZnJvbSBcInRpcHB5LmpzXCI7XG5pbXBvcnQgeyBFZGl0b3IgfSBmcm9tIFwiQHRpcHRhcC9jb3JlXCI7XG5pbXBvcnQgeyBBdGVFZGl0b3JDb21tYW5kc1NlcnZpY2UgfSBmcm9tIFwiLi4vLi4vLi4vc2VydmljZXMvYXRlLWVkaXRvci1jb21tYW5kcy5zZXJ2aWNlXCI7XG5pbXBvcnQgeyBBdGVJMThuU2VydmljZSB9IGZyb20gXCIuLi8uLi8uLi9zZXJ2aWNlcy9hdGUtaTE4bi5zZXJ2aWNlXCI7XG5cbi8qKlxuICogQmFzZSBhYnN0cmFjdCBjbGFzcyBmb3IgU3ViLUJ1YmJsZSBNZW51cyAoTGluaywgQ29sb3IpLlxuICogVGhlc2UgbWVudXMgYXJlIFwic3ViLW1lbnVzXCIgb2YgdGhlIG1haW4gYnViYmxlIG1lbnUgb3IgdHJpZ2dlcmVkL2FuY2hvcmVkIGJ5IHNwZWNpZmljIFVJIGVsZW1lbnRzLlxuICovXG5ARGlyZWN0aXZlKClcbmV4cG9ydCBhYnN0cmFjdCBjbGFzcyBBdGVCYXNlU3ViQnViYmxlTWVudSBpbXBsZW1lbnRzIEFmdGVyVmlld0luaXQsIE9uRGVzdHJveSB7XG4gIHByb3RlY3RlZCByZWFkb25seSBpMThuU2VydmljZSA9IGluamVjdChBdGVJMThuU2VydmljZSk7XG4gIHByb3RlY3RlZCByZWFkb25seSBlZGl0b3JDb21tYW5kcyA9IGluamVjdChBdGVFZGl0b3JDb21tYW5kc1NlcnZpY2UpO1xuXG4gIC8vIENvcmUgSW5wdXRzXG4gIGVkaXRvciA9IGlucHV0LnJlcXVpcmVkPEVkaXRvcj4oKTtcblxuICAvLyBSZXF1aXJlZCB2aWV3Q2hpbGQgZm9yIHRoZSBtZW51IGNvbnRhaW5lclxuICBtZW51UmVmID0gdmlld0NoaWxkLnJlcXVpcmVkPEVsZW1lbnRSZWY8SFRNTERpdkVsZW1lbnQ+PihcIm1lbnVSZWZcIik7XG5cbiAgLy8gSW50ZXJuYWwgU3RhdGVcbiAgcHJvdGVjdGVkIHRpcHB5SW5zdGFuY2U6IFRpcHB5SW5zdGFuY2UgfCBudWxsID0gbnVsbDtcbiAgcHJvdGVjdGVkIHVwZGF0ZVRpbWVvdXQ6IG51bWJlciB8IG51bGwgPSBudWxsO1xuXG4gIC8vIFJlYWN0aXZlIHN0YXRlIGFsaWFzIGZvciB0ZW1wbGF0ZXNcbiAgcmVhZG9ubHkgc3RhdGUgPSB0aGlzLmVkaXRvckNvbW1hbmRzLmVkaXRvclN0YXRlO1xuXG4gIGNvbnN0cnVjdG9yKCkge1xuICAgIC8vIFJlYWN0aXZlIGVmZmVjdCBmb3IgbWVudSB1cGRhdGVzIChyZS1wb3NpdGlvbmluZylcbiAgICBlZmZlY3QoKCkgPT4ge1xuICAgICAgLy8gTW9uaXRvciBlZGl0b3Igc3RhdGUgYW5kIHNwZWNpZmljIHN1Yi1tZW51IHN0YXRlc1xuICAgICAgdGhpcy5zdGF0ZSgpO1xuICAgICAgdGhpcy5vblN0YXRlQ2hhbmdlKCk7XG5cbiAgICAgIHRoaXMudXBkYXRlTWVudSgpO1xuICAgIH0sIHsgYWxsb3dTaWduYWxXcml0ZXM6IHRydWUgfSk7XG4gIH1cblxuICBuZ0FmdGVyVmlld0luaXQoKSB7XG4gICAgdGhpcy5pbml0VGlwcHkoKTtcbiAgfVxuXG4gIG5nT25EZXN0cm95KCkge1xuICAgIGlmICh0aGlzLnVwZGF0ZVRpbWVvdXQpIHtcbiAgICAgIGNsZWFyVGltZW91dCh0aGlzLnVwZGF0ZVRpbWVvdXQpO1xuICAgIH1cbiAgICBpZiAodGhpcy50aXBweUluc3RhbmNlKSB7XG4gICAgICB0aGlzLnRpcHB5SW5zdGFuY2UuZGVzdHJveSgpO1xuICAgICAgdGhpcy50aXBweUluc3RhbmNlID0gbnVsbDtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICogSW5pdGlhbGl6ZXMgdGhlIFRpcHB5IGluc3RhbmNlIHdpdGggc3ViLW1lbnUgZGVmYXVsdHMuXG4gICAqL1xuICBwcm90ZWN0ZWQgaW5pdFRpcHB5KCkge1xuICAgIGNvbnN0IG5hdGl2ZUVsZW1lbnQgPSB0aGlzLm1lbnVSZWYoKS5uYXRpdmVFbGVtZW50O1xuICAgIGlmICghbmF0aXZlRWxlbWVudCkge3JldHVybjt9XG5cbiAgICBjb25zdCBlZCA9IHRoaXMuZWRpdG9yKCk7XG4gICAgaWYgKHRoaXMudGlwcHlJbnN0YW5jZSkge1xuICAgICAgdGhpcy50aXBweUluc3RhbmNlLmRlc3Ryb3koKTtcbiAgICB9XG5cbiAgICB0aGlzLnRpcHB5SW5zdGFuY2UgPSB0aXBweShkb2N1bWVudC5ib2R5LCB7XG4gICAgICBjb250ZW50OiBuYXRpdmVFbGVtZW50LFxuICAgICAgdHJpZ2dlcjogXCJtYW51YWxcIixcbiAgICAgIHBsYWNlbWVudDogXCJib3R0b20tc3RhcnRcIixcbiAgICAgIHRoZW1lOiBcImF0ZS1idWJibGUtbWVudVwiLFxuICAgICAgYXBwZW5kVG86ICgpID0+IChlZD8ub3B0aW9ucz8uZWxlbWVudCBhcyBIVE1MRWxlbWVudCkgfHwgZG9jdW1lbnQuYm9keSxcbiAgICAgIGludGVyYWN0aXZlOiB0cnVlLFxuICAgICAgYXJyb3c6IGZhbHNlLFxuICAgICAgb2Zmc2V0OiBbMCwgOF0sXG4gICAgICBoaWRlT25DbGljazogdHJ1ZSxcbiAgICAgIHBsdWdpbnM6IFtzdGlja3ldLFxuICAgICAgc3RpY2t5OiBmYWxzZSxcbiAgICAgIGdldFJlZmVyZW5jZUNsaWVudFJlY3Q6ICgpID0+IHRoaXMuZ2V0U2VsZWN0aW9uUmVjdCgpLFxuICAgICAgcG9wcGVyT3B0aW9uczoge1xuICAgICAgICBtb2RpZmllcnM6IFtcbiAgICAgICAgICB7XG4gICAgICAgICAgICBuYW1lOiBcInByZXZlbnRPdmVyZmxvd1wiLFxuICAgICAgICAgICAgb3B0aW9uczoge1xuICAgICAgICAgICAgICBib3VuZGFyeTogKGVkPy5vcHRpb25zPy5lbGVtZW50IGFzIEhUTUxFbGVtZW50KSB8fCBkb2N1bWVudC5ib2R5LFxuICAgICAgICAgICAgICBwYWRkaW5nOiA4LFxuICAgICAgICAgICAgfSxcbiAgICAgICAgICB9LFxuICAgICAgICAgIHtcbiAgICAgICAgICAgIG5hbWU6IFwiZmxpcFwiLFxuICAgICAgICAgICAgb3B0aW9uczogeyBmYWxsYmFja1BsYWNlbWVudHM6IFtcInRvcC1zdGFydFwiLCBcImJvdHRvbS1lbmRcIiwgXCJ0b3AtZW5kXCJdIH0sXG4gICAgICAgICAgfSxcbiAgICAgICAgXSxcbiAgICAgIH0sXG4gICAgICBvblNob3c6IGluc3RhbmNlID0+IHRoaXMub25UaXBweVNob3coaW5zdGFuY2UpLFxuICAgICAgb25IaWRlOiBpbnN0YW5jZSA9PiB0aGlzLm9uVGlwcHlIaWRlKGluc3RhbmNlKSxcbiAgICB9KTtcblxuICAgIHRoaXMudXBkYXRlTWVudSgpO1xuICB9XG5cbiAgLyoqXG4gICAqIENvcmUgbG9naWMgdG8gZGVjaWRlIHdoZXRoZXIgdG8gc2hvdyBvciBoaWRlIHRoZSBtZW51LlxuICAgKi9cbiAgdXBkYXRlTWVudSA9ICgpID0+IHtcbiAgICBpZiAodGhpcy51cGRhdGVUaW1lb3V0KSB7XG4gICAgICBjbGVhclRpbWVvdXQodGhpcy51cGRhdGVUaW1lb3V0KTtcbiAgICB9XG4gICAgdGhpcy51cGRhdGVUaW1lb3V0ID0gc2V0VGltZW91dCgoKSA9PiB7XG4gICAgICBpZiAodGhpcy5zaG91bGRTaG93KCkpIHtcbiAgICAgICAgdGhpcy5zaG93VGlwcHkoKTtcbiAgICAgIH0gZWxzZSB7XG4gICAgICAgIHRoaXMuaGlkZVRpcHB5KCk7XG4gICAgICB9XG4gICAgfSwgMTApO1xuICB9O1xuXG4gIC8qKlxuICAgKiBIZWxwZXIgdG8gc2hvdyB0aGUgVGlwcHkgaW5zdGFuY2Ugd2l0aCB1cGRhdGVkIHBvc2l0aW9uaW5nLlxuICAgKi9cbiAgcHJvdGVjdGVkIHNob3dUaXBweSgpIHtcbiAgICBpZiAodGhpcy50aXBweUluc3RhbmNlKSB7XG4gICAgICB0aGlzLnRpcHB5SW5zdGFuY2Uuc2V0UHJvcHMoeyBnZXRSZWZlcmVuY2VDbGllbnRSZWN0OiAoKSA9PiB0aGlzLmdldFNlbGVjdGlvblJlY3QoKSB9KTtcbiAgICAgIHRoaXMudGlwcHlJbnN0YW5jZS5zaG93KCk7XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIEhlbHBlciB0byBoaWRlIHRoZSBUaXBweSBpbnN0YW5jZS5cbiAgICovXG4gIHByb3RlY3RlZCBoaWRlVGlwcHkoKSB7XG4gICAgdGhpcy50aXBweUluc3RhbmNlPy5oaWRlKCk7XG4gIH1cblxuICAvLyAtLS0gQWJzdHJhY3QgbWV0aG9kcyAmIEhvb2tzIC0tLVxuXG4gIC8qKlxuICAgKiBSZXR1cm5zIHRoZSBSZWN0IHJlcHJlc2VudGluZyB0aGUgdGFyZ2V0IGZvciBwb3NpdGlvbmluZyB0aGUgbWVudS5cbiAgICovXG4gIGFic3RyYWN0IGdldFNlbGVjdGlvblJlY3QoKTogRE9NUmVjdDtcblxuICAvKipcbiAgICogUmV0dXJucyB3aGV0aGVyIHRoZSBtZW51IHNob3VsZCBiZSBkaXNwbGF5ZWQgYmFzZWQgb24gY3VycmVudCBzdGF0ZS5cbiAgICovXG4gIGFic3RyYWN0IHNob3VsZFNob3coKTogYm9vbGVhbjtcblxuICAvKipcbiAgICogSG9vayB0byBhZGQgcmVhY3RpdmUgZGVwZW5kZW5jaWVzIHRvIHRoZSB1cGRhdGUgY3ljbGUuXG4gICAqL1xuICBwcm90ZWN0ZWQgYWJzdHJhY3Qgb25TdGF0ZUNoYW5nZSgpOiB2b2lkO1xuXG4gIC8qKlxuICAgKiBPcHRpb25hbCBob29rIGNhbGxlZCB3aGVuIFRpcHB5IGlzIGFib3V0IHRvIGJlIHNob3duLlxuICAgKi9cbiAgcHJvdGVjdGVkIG9uVGlwcHlTaG93KF9pbnN0YW5jZTogVGlwcHlJbnN0YW5jZSkge1xuICAgIC8qIGVtcHR5ICovXG4gIH1cblxuICAvKipcbiAgICogT3B0aW9uYWwgaG9vayBjYWxsZWQgd2hlbiBUaXBweSBpcyBhYm91dCB0byBiZSBoaWRkZW4uXG4gICAqL1xuICBwcm90ZWN0ZWQgb25UaXBweUhpZGUoX2luc3RhbmNlOiBUaXBweUluc3RhbmNlKSB7XG4gICAgLyogZW1wdHkgKi9cbiAgfVxufVxuIl19
|