@flogeez/angular-tiptap-editor 3.5.2 → 3.5.3
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 +11 -0
- package/esm2022/lib/components/editor/angular-tiptap-editor.component.mjs +10 -2
- package/esm2022/lib/extensions/ate-pasted-image.extension.mjs +156 -0
- package/esm2022/lib/models/ate-image.model.mjs +1 -1
- package/esm2022/lib/services/ate-editor-commands.service.mjs +7 -1
- package/esm2022/lib/services/ate-image.service.mjs +63 -36
- package/esm2022/public-api.mjs +3 -1
- package/fesm2022/flogeez-angular-tiptap-editor.mjs +231 -37
- package/fesm2022/flogeez-angular-tiptap-editor.mjs.map +1 -1
- package/lib/components/editor/angular-tiptap-editor.component.d.ts +4 -2
- package/lib/extensions/ate-pasted-image.extension.d.ts +33 -0
- package/lib/models/ate-image.model.d.ts +9 -0
- package/lib/services/ate-editor-commands.service.d.ts +2 -0
- package/lib/services/ate-image.service.d.ts +7 -0
- package/package.json +1 -1
- package/public-api.d.ts +1 -0
|
@@ -13,6 +13,7 @@ import { Color } from '@tiptap/extension-color';
|
|
|
13
13
|
import OfficePaste from '@intevation/tiptap-extension-office-paste';
|
|
14
14
|
import { Plugin, PluginKey, TextSelection, NodeSelection } from '@tiptap/pm/state';
|
|
15
15
|
import { DecorationSet, Decoration } from '@tiptap/pm/view';
|
|
16
|
+
import { Fragment, Slice } from '@tiptap/pm/model';
|
|
16
17
|
import { Table, TableRow, TableHeader, TableCell } from '@tiptap/extension-table';
|
|
17
18
|
import { Subscription, isObservable, firstValueFrom, concat, defer, of, tap } from 'rxjs';
|
|
18
19
|
import tippy, { sticky } from 'tippy.js';
|
|
@@ -681,6 +682,159 @@ const AteUploadProgress = Extension.create({
|
|
|
681
682
|
},
|
|
682
683
|
});
|
|
683
684
|
|
|
685
|
+
const IMAGE_NODE_NAMES = new Set(["resizableImage", "image"]);
|
|
686
|
+
const REMOTE_SRC = /^(https?:)?\/\//i;
|
|
687
|
+
const INLINE_SRC = /^data:(image\/[\w.+-]+);base64,(.*)$/is;
|
|
688
|
+
const PASTED_IMAGE_BASENAME = "pasted-image";
|
|
689
|
+
/**
|
|
690
|
+
* Classifies the `src` of an image found in pasted HTML.
|
|
691
|
+
* `unreachable` sources (e.g. `attachment:`, `file:`, `cid:`, foreign `blob:`) cannot be fetched by the page.
|
|
692
|
+
*/
|
|
693
|
+
function classifyPastedImageSrc(src, origin = typeof location !== "undefined" ? location.origin : "") {
|
|
694
|
+
if (!src) {
|
|
695
|
+
return "unreachable";
|
|
696
|
+
}
|
|
697
|
+
if (REMOTE_SRC.test(src) || (src.startsWith("/") && !src.startsWith("//"))) {
|
|
698
|
+
return "remote";
|
|
699
|
+
}
|
|
700
|
+
if (origin && src.startsWith(`blob:${origin}/`)) {
|
|
701
|
+
return "remote";
|
|
702
|
+
}
|
|
703
|
+
return INLINE_SRC.test(src) ? "inline" : "unreachable";
|
|
704
|
+
}
|
|
705
|
+
/** Decodes a base64 image data URI into a `File`, or returns `null` when it is malformed */
|
|
706
|
+
function dataUriToFile(src) {
|
|
707
|
+
const match = INLINE_SRC.exec(src);
|
|
708
|
+
if (!match) {
|
|
709
|
+
return null;
|
|
710
|
+
}
|
|
711
|
+
const mimeType = match[1].toLowerCase();
|
|
712
|
+
try {
|
|
713
|
+
const binary = atob(match[2].replace(/\s/g, ""));
|
|
714
|
+
const bytes = Uint8Array.from(binary, char => char.codePointAt(0) ?? 0);
|
|
715
|
+
const extension = mimeType.split("/")[1].split("+")[0];
|
|
716
|
+
return new File([bytes], `${PASTED_IMAGE_BASENAME}.${extension}`, { type: mimeType });
|
|
717
|
+
}
|
|
718
|
+
catch {
|
|
719
|
+
return null;
|
|
720
|
+
}
|
|
721
|
+
}
|
|
722
|
+
function isImageNode(node) {
|
|
723
|
+
return IMAGE_NODE_NAMES.has(node.type.name);
|
|
724
|
+
}
|
|
725
|
+
/** Removes unreachable images from a pasted slice and lists the base64 sources it keeps */
|
|
726
|
+
function sanitizePastedImages(slice) {
|
|
727
|
+
const inlineSources = new Set();
|
|
728
|
+
const droppedSources = [];
|
|
729
|
+
const sanitize = (fragment) => {
|
|
730
|
+
const kept = [];
|
|
731
|
+
fragment.forEach(child => {
|
|
732
|
+
if (isImageNode(child)) {
|
|
733
|
+
const src = child.attrs["src"];
|
|
734
|
+
const source = classifyPastedImageSrc(src);
|
|
735
|
+
if (source === "unreachable") {
|
|
736
|
+
droppedSources.push(src ?? "");
|
|
737
|
+
return;
|
|
738
|
+
}
|
|
739
|
+
if (source === "inline" && src) {
|
|
740
|
+
inlineSources.add(src);
|
|
741
|
+
}
|
|
742
|
+
kept.push(child);
|
|
743
|
+
return;
|
|
744
|
+
}
|
|
745
|
+
kept.push(child.isLeaf ? child : child.copy(sanitize(child.content)));
|
|
746
|
+
});
|
|
747
|
+
return Fragment.fromArray(kept);
|
|
748
|
+
};
|
|
749
|
+
const content = sanitize(slice.content);
|
|
750
|
+
if (!droppedSources.length) {
|
|
751
|
+
return { slice, inlineSources: [...inlineSources], droppedSources };
|
|
752
|
+
}
|
|
753
|
+
const openStart = content.firstChild === slice.content.firstChild ? slice.openStart : 0;
|
|
754
|
+
const openEnd = content.lastChild === slice.content.lastChild ? slice.openEnd : 0;
|
|
755
|
+
return {
|
|
756
|
+
slice: new Slice(content, openStart, openEnd),
|
|
757
|
+
inlineSources: [...inlineSources],
|
|
758
|
+
droppedSources,
|
|
759
|
+
};
|
|
760
|
+
}
|
|
761
|
+
function replaceImageSrc(editor, previousSrc, nextSrc) {
|
|
762
|
+
if (editor.isDestroyed) {
|
|
763
|
+
return;
|
|
764
|
+
}
|
|
765
|
+
const { state } = editor;
|
|
766
|
+
const matches = [];
|
|
767
|
+
state.doc.descendants((node, pos) => {
|
|
768
|
+
if (isImageNode(node) && node.attrs["src"] === previousSrc) {
|
|
769
|
+
matches.push({ pos, node });
|
|
770
|
+
}
|
|
771
|
+
});
|
|
772
|
+
if (!matches.length) {
|
|
773
|
+
return;
|
|
774
|
+
}
|
|
775
|
+
const tr = state.tr;
|
|
776
|
+
for (const { pos, node } of [...matches].reverse()) {
|
|
777
|
+
if (nextSrc) {
|
|
778
|
+
tr.setNodeMarkup(pos, undefined, { ...node.attrs, src: nextSrc });
|
|
779
|
+
}
|
|
780
|
+
else {
|
|
781
|
+
tr.delete(pos, pos + node.nodeSize);
|
|
782
|
+
}
|
|
783
|
+
}
|
|
784
|
+
editor.view.dispatch(tr);
|
|
785
|
+
}
|
|
786
|
+
/**
|
|
787
|
+
* Cleans images coming from pasted HTML (e.g. Notion, Google Docs, Office):
|
|
788
|
+
* - drops images whose source the page cannot load, instead of inserting broken images;
|
|
789
|
+
* - sends base64 images through the upload handler (when one is configured) and swaps in the hosted URL.
|
|
790
|
+
*
|
|
791
|
+
* File-based clipboard images keep going through the regular paste upload flow.
|
|
792
|
+
*/
|
|
793
|
+
const AtePastedImage = Extension.create({
|
|
794
|
+
name: "atePastedImage",
|
|
795
|
+
addOptions() {
|
|
796
|
+
return {
|
|
797
|
+
shouldRehost: () => false,
|
|
798
|
+
rehost: () => Promise.reject(new Error("No upload handler configured")),
|
|
799
|
+
onRejected: () => undefined,
|
|
800
|
+
};
|
|
801
|
+
},
|
|
802
|
+
addProseMirrorPlugins() {
|
|
803
|
+
const editor = this.editor;
|
|
804
|
+
const options = this.options;
|
|
805
|
+
const rehost = (src) => {
|
|
806
|
+
const file = dataUriToFile(src);
|
|
807
|
+
if (!file) {
|
|
808
|
+
replaceImageSrc(editor, src, null);
|
|
809
|
+
options.onRejected({ reason: "unreachable", src });
|
|
810
|
+
return;
|
|
811
|
+
}
|
|
812
|
+
options
|
|
813
|
+
.rehost(file)
|
|
814
|
+
.then(url => replaceImageSrc(editor, src, url))
|
|
815
|
+
.catch(() => {
|
|
816
|
+
replaceImageSrc(editor, src, null);
|
|
817
|
+
options.onRejected({ reason: "upload-failed", src });
|
|
818
|
+
});
|
|
819
|
+
};
|
|
820
|
+
return [
|
|
821
|
+
new Plugin({
|
|
822
|
+
key: new PluginKey("atePastedImage"),
|
|
823
|
+
props: {
|
|
824
|
+
transformPasted: slice => {
|
|
825
|
+
const { slice: sanitized, inlineSources, droppedSources } = sanitizePastedImages(slice);
|
|
826
|
+
droppedSources.forEach(src => options.onRejected({ reason: "unreachable", src }));
|
|
827
|
+
if (inlineSources.length && options.shouldRehost()) {
|
|
828
|
+
queueMicrotask(() => inlineSources.forEach(rehost));
|
|
829
|
+
}
|
|
830
|
+
return sanitized;
|
|
831
|
+
},
|
|
832
|
+
},
|
|
833
|
+
}),
|
|
834
|
+
];
|
|
835
|
+
},
|
|
836
|
+
});
|
|
837
|
+
|
|
684
838
|
const AteTableExtension = Extension.create({
|
|
685
839
|
name: "tableExtension",
|
|
686
840
|
addExtensions() {
|
|
@@ -3341,43 +3495,15 @@ class AteImageService {
|
|
|
3341
3495
|
this.uploadProgress.set(10);
|
|
3342
3496
|
this.uploadMessage.set(this.t().validating);
|
|
3343
3497
|
this.forceEditorUpdate();
|
|
3344
|
-
const
|
|
3345
|
-
|
|
3346
|
-
|
|
3347
|
-
});
|
|
3348
|
-
if (!validation.valid) {
|
|
3349
|
-
throw new Error(validation.error);
|
|
3350
|
-
}
|
|
3351
|
-
this.uploadProgress.set(30);
|
|
3352
|
-
this.uploadMessage.set(this.t().compressing);
|
|
3353
|
-
this.forceEditorUpdate();
|
|
3354
|
-
const result = await this.compressImage(file, options?.quality || 0.8, options?.maxWidth || 1920, options?.maxHeight || 1200);
|
|
3355
|
-
this.uploadProgress.set(70);
|
|
3356
|
-
// Handle custom upload if handler is provided
|
|
3357
|
-
if (this.uploadHandler) {
|
|
3358
|
-
this.uploadMessage.set(this.t().uploadingToServer);
|
|
3359
|
-
this.forceEditorUpdate();
|
|
3360
|
-
try {
|
|
3361
|
-
const handlerResponse = this.uploadHandler({
|
|
3362
|
-
file,
|
|
3363
|
-
width: result.width || 0,
|
|
3364
|
-
height: result.height || 0,
|
|
3365
|
-
type: result.type,
|
|
3366
|
-
base64: result.src,
|
|
3367
|
-
});
|
|
3368
|
-
const handlerResult = isObservable(handlerResponse)
|
|
3369
|
-
? await firstValueFrom(handlerResponse)
|
|
3370
|
-
: await handlerResponse;
|
|
3371
|
-
result.src = handlerResult.src;
|
|
3372
|
-
if (handlerResult.alt) {
|
|
3373
|
-
result.name = handlerResult.alt;
|
|
3374
|
-
}
|
|
3498
|
+
const result = await this.processImage(file, options, (progress, message) => {
|
|
3499
|
+
if (progress !== undefined) {
|
|
3500
|
+
this.uploadProgress.set(progress);
|
|
3375
3501
|
}
|
|
3376
|
-
|
|
3377
|
-
|
|
3378
|
-
|
|
3502
|
+
if (message !== undefined) {
|
|
3503
|
+
this.uploadMessage.set(message);
|
|
3504
|
+
this.forceEditorUpdate();
|
|
3379
3505
|
}
|
|
3380
|
-
}
|
|
3506
|
+
});
|
|
3381
3507
|
this.uploadProgress.set(90);
|
|
3382
3508
|
this.uploadMessage.set(actionMessage);
|
|
3383
3509
|
this.forceEditorUpdate();
|
|
@@ -3394,6 +3520,61 @@ class AteImageService {
|
|
|
3394
3520
|
throw error;
|
|
3395
3521
|
}
|
|
3396
3522
|
}
|
|
3523
|
+
/** Validate, compress and (when configured) send an image to the upload handler */
|
|
3524
|
+
async processImage(file, options, onStep) {
|
|
3525
|
+
const validation = this.validateImage(file, {
|
|
3526
|
+
maxSize: options?.maxSize,
|
|
3527
|
+
allowedTypes: options?.allowedTypes,
|
|
3528
|
+
});
|
|
3529
|
+
if (!validation.valid) {
|
|
3530
|
+
throw new Error(validation.error);
|
|
3531
|
+
}
|
|
3532
|
+
onStep?.(30, this.t().compressing);
|
|
3533
|
+
const result = await this.compressImage(file, options?.quality || 0.8, options?.maxWidth || 1920, options?.maxHeight || 1200);
|
|
3534
|
+
onStep?.(70);
|
|
3535
|
+
// Handle custom upload if handler is provided
|
|
3536
|
+
if (this.uploadHandler) {
|
|
3537
|
+
onStep?.(undefined, this.t().uploadingToServer);
|
|
3538
|
+
try {
|
|
3539
|
+
const handlerResponse = this.uploadHandler({
|
|
3540
|
+
file,
|
|
3541
|
+
width: result.width || 0,
|
|
3542
|
+
height: result.height || 0,
|
|
3543
|
+
type: result.type,
|
|
3544
|
+
base64: result.src,
|
|
3545
|
+
});
|
|
3546
|
+
const handlerResult = isObservable(handlerResponse)
|
|
3547
|
+
? await firstValueFrom(handlerResponse)
|
|
3548
|
+
: await handlerResponse;
|
|
3549
|
+
result.src = handlerResult.src;
|
|
3550
|
+
if (handlerResult.alt) {
|
|
3551
|
+
result.name = handlerResult.alt;
|
|
3552
|
+
}
|
|
3553
|
+
}
|
|
3554
|
+
catch (handlerError) {
|
|
3555
|
+
console.error(this.t().uploadError, handlerError);
|
|
3556
|
+
throw handlerError;
|
|
3557
|
+
}
|
|
3558
|
+
}
|
|
3559
|
+
return result;
|
|
3560
|
+
}
|
|
3561
|
+
/**
|
|
3562
|
+
* Run an image that is already in the document (e.g. base64 from pasted HTML)
|
|
3563
|
+
* through validation, compression and the upload handler, and resolve to its new `src`.
|
|
3564
|
+
*/
|
|
3565
|
+
async rehostImage(file, options) {
|
|
3566
|
+
try {
|
|
3567
|
+
const result = await this.processImage(file, options);
|
|
3568
|
+
if (this.onImageUploadedCallback) {
|
|
3569
|
+
this.onImageUploadedCallback(result);
|
|
3570
|
+
}
|
|
3571
|
+
return result.src;
|
|
3572
|
+
}
|
|
3573
|
+
catch (error) {
|
|
3574
|
+
console.error(this.t().uploadError, error);
|
|
3575
|
+
throw error;
|
|
3576
|
+
}
|
|
3577
|
+
}
|
|
3397
3578
|
resetUploadState() {
|
|
3398
3579
|
this.isUploading.set(false);
|
|
3399
3580
|
this.uploadProgress.set(0);
|
|
@@ -4635,6 +4816,12 @@ class AteEditorCommandsService {
|
|
|
4635
4816
|
handleImagePaste(editor, event, options) {
|
|
4636
4817
|
return this.imageService.handlePaste(editor, event, options);
|
|
4637
4818
|
}
|
|
4819
|
+
rehostImage(file, options) {
|
|
4820
|
+
return this.imageService.rehostImage(file, options);
|
|
4821
|
+
}
|
|
4822
|
+
get hasUploadHandler() {
|
|
4823
|
+
return this.imageService.uploadHandler !== null;
|
|
4824
|
+
}
|
|
4638
4825
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteEditorCommandsService, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
4639
4826
|
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AteEditorCommandsService }); }
|
|
4640
4827
|
}
|
|
@@ -8723,6 +8910,8 @@ class AngularTiptapEditorComponent {
|
|
|
8723
8910
|
this.editorBlur = output();
|
|
8724
8911
|
this.editableChange = output();
|
|
8725
8912
|
this.imageUploaded = output();
|
|
8913
|
+
/** Emitted when an image from pasted HTML is dropped (unreachable source or failed upload) */
|
|
8914
|
+
this.pastedImageRejected = output();
|
|
8726
8915
|
// ViewChild with signal
|
|
8727
8916
|
this.editorElement = viewChild.required("editorElement");
|
|
8728
8917
|
// Private signals for internal state
|
|
@@ -9071,6 +9260,11 @@ class AngularTiptapEditorComponent {
|
|
|
9071
9260
|
class: "ate-image",
|
|
9072
9261
|
},
|
|
9073
9262
|
}),
|
|
9263
|
+
AtePastedImage.configure({
|
|
9264
|
+
shouldRehost: () => this.editorCommandsService.hasUploadHandler,
|
|
9265
|
+
rehost: file => this.editorCommandsService.rehostImage(file, this.getImageUploadOptions()),
|
|
9266
|
+
onRejected: rejection => this.pastedImageRejected.emit(rejection),
|
|
9267
|
+
}),
|
|
9074
9268
|
AteUploadProgress.configure({
|
|
9075
9269
|
isUploading: () => this.editorCommandsService.isUploading(),
|
|
9076
9270
|
uploadProgress: () => this.editorCommandsService.uploadProgress(),
|
|
@@ -9353,7 +9547,7 @@ class AngularTiptapEditorComponent {
|
|
|
9353
9547
|
}
|
|
9354
9548
|
}
|
|
9355
9549
|
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: AngularTiptapEditorComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
9356
|
-
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: AngularTiptapEditorComponent, isStandalone: true, selector: "angular-tiptap-editor", inputs: { config: { classPropertyName: "config", publicName: "config", isSignal: true, isRequired: false, transformFunction: null }, content: { classPropertyName: "content", publicName: "content", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, editable: { classPropertyName: "editable", publicName: "editable", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, minHeight: { classPropertyName: "minHeight", publicName: "minHeight", isSignal: true, isRequired: false, transformFunction: null }, height: { classPropertyName: "height", publicName: "height", isSignal: true, isRequired: false, transformFunction: null }, maxHeight: { classPropertyName: "maxHeight", publicName: "maxHeight", isSignal: true, isRequired: false, transformFunction: null }, fillContainer: { classPropertyName: "fillContainer", publicName: "fillContainer", isSignal: true, isRequired: false, transformFunction: null }, showToolbar: { classPropertyName: "showToolbar", publicName: "showToolbar", isSignal: true, isRequired: false, transformFunction: null }, showFooter: { classPropertyName: "showFooter", publicName: "showFooter", isSignal: true, isRequired: false, transformFunction: null }, showCharacterCount: { classPropertyName: "showCharacterCount", publicName: "showCharacterCount", isSignal: true, isRequired: false, transformFunction: null }, showWordCount: { classPropertyName: "showWordCount", publicName: "showWordCount", isSignal: true, isRequired: false, transformFunction: null }, maxCharacters: { classPropertyName: "maxCharacters", publicName: "maxCharacters", isSignal: true, isRequired: false, transformFunction: null }, enableOfficePaste: { classPropertyName: "enableOfficePaste", publicName: "enableOfficePaste", isSignal: true, isRequired: false, transformFunction: null }, enableSlashCommands: { classPropertyName: "enableSlashCommands", publicName: "enableSlashCommands", isSignal: true, isRequired: false, transformFunction: null }, slashCommands: { classPropertyName: "slashCommands", publicName: "slashCommands", isSignal: true, isRequired: false, transformFunction: null }, customSlashCommands: { classPropertyName: "customSlashCommands", publicName: "customSlashCommands", isSignal: true, isRequired: false, transformFunction: null }, blockControls: { classPropertyName: "blockControls", publicName: "blockControls", isSignal: true, isRequired: false, transformFunction: null }, locale: { classPropertyName: "locale", publicName: "locale", isSignal: true, isRequired: false, transformFunction: null }, autofocus: { classPropertyName: "autofocus", publicName: "autofocus", isSignal: true, isRequired: false, transformFunction: null }, mode: { classPropertyName: "mode", publicName: "mode", isSignal: true, isRequired: false, transformFunction: null }, seamless: { classPropertyName: "seamless", publicName: "seamless", isSignal: true, isRequired: false, transformFunction: null }, floatingToolbar: { classPropertyName: "floatingToolbar", publicName: "floatingToolbar", isSignal: true, isRequired: false, transformFunction: null }, showEditToggle: { classPropertyName: "showEditToggle", publicName: "showEditToggle", isSignal: true, isRequired: false, transformFunction: null }, spellcheck: { classPropertyName: "spellcheck", publicName: "spellcheck", isSignal: true, isRequired: false, transformFunction: null }, tiptapExtensions: { classPropertyName: "tiptapExtensions", publicName: "tiptapExtensions", isSignal: true, isRequired: false, transformFunction: null }, tiptapOptions: { classPropertyName: "tiptapOptions", publicName: "tiptapOptions", isSignal: true, isRequired: false, transformFunction: null }, showBubbleMenu: { classPropertyName: "showBubbleMenu", publicName: "showBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, bubbleMenu: { classPropertyName: "bubbleMenu", publicName: "bubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, showImageBubbleMenu: { classPropertyName: "showImageBubbleMenu", publicName: "showImageBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, imageBubbleMenu: { classPropertyName: "imageBubbleMenu", publicName: "imageBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, toolbar: { classPropertyName: "toolbar", publicName: "toolbar", isSignal: true, isRequired: false, transformFunction: null }, showTableBubbleMenu: { classPropertyName: "showTableBubbleMenu", publicName: "showTableBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, tableBubbleMenu: { classPropertyName: "tableBubbleMenu", publicName: "tableBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, showCellBubbleMenu: { classPropertyName: "showCellBubbleMenu", publicName: "showCellBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, cellBubbleMenu: { classPropertyName: "cellBubbleMenu", publicName: "cellBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, stateCalculators: { classPropertyName: "stateCalculators", publicName: "stateCalculators", isSignal: true, isRequired: false, transformFunction: null }, imageUpload: { classPropertyName: "imageUpload", publicName: "imageUpload", isSignal: true, isRequired: false, transformFunction: null }, imageUploadHandler: { classPropertyName: "imageUploadHandler", publicName: "imageUploadHandler", isSignal: true, isRequired: false, transformFunction: null }, editorId: { classPropertyName: "editorId", publicName: "editorId", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { contentChange: "contentChange", editorCreated: "editorCreated", editorUpdate: "editorUpdate", editorFocus: "editorFocus", editorBlur: "editorBlur", editableChange: "editableChange", imageUploaded: "imageUploaded" }, host: { properties: { "class.fill-container": "finalFillContainer()", "class.floating-toolbar": "finalFloatingToolbar()", "class.is-readonly": "!finalEditable() && !mergedDisabled()", "class.is-disabled": "mergedDisabled()", "style.--ate-border-width": "finalSeamless() || mergedDisabled() ? '0' : null", "style.--ate-background": "finalSeamless() ? 'transparent' : (mergedDisabled() ? 'var(--ate-surface-tertiary)' : null)", "style.--ate-toolbar-border-color": "finalSeamless() ? 'transparent' : null", "style.--ate-counter-background": "finalSeamless() ? 'transparent' : null", "style.--ate-counter-border-color": "finalSeamless() ? 'transparent' : null", "class.dark": "config().theme === 'dark'", "class.ate-blocks-inside": "finalBlockControls() === 'inside'", "class.ate-blocks-outside": "finalBlockControls() === 'outside'", "attr.data-theme": "config().theme" } }, providers: [
|
|
9550
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "18.2.14", type: AngularTiptapEditorComponent, isStandalone: true, selector: "angular-tiptap-editor", inputs: { config: { classPropertyName: "config", publicName: "config", isSignal: true, isRequired: false, transformFunction: null }, content: { classPropertyName: "content", publicName: "content", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, editable: { classPropertyName: "editable", publicName: "editable", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, minHeight: { classPropertyName: "minHeight", publicName: "minHeight", isSignal: true, isRequired: false, transformFunction: null }, height: { classPropertyName: "height", publicName: "height", isSignal: true, isRequired: false, transformFunction: null }, maxHeight: { classPropertyName: "maxHeight", publicName: "maxHeight", isSignal: true, isRequired: false, transformFunction: null }, fillContainer: { classPropertyName: "fillContainer", publicName: "fillContainer", isSignal: true, isRequired: false, transformFunction: null }, showToolbar: { classPropertyName: "showToolbar", publicName: "showToolbar", isSignal: true, isRequired: false, transformFunction: null }, showFooter: { classPropertyName: "showFooter", publicName: "showFooter", isSignal: true, isRequired: false, transformFunction: null }, showCharacterCount: { classPropertyName: "showCharacterCount", publicName: "showCharacterCount", isSignal: true, isRequired: false, transformFunction: null }, showWordCount: { classPropertyName: "showWordCount", publicName: "showWordCount", isSignal: true, isRequired: false, transformFunction: null }, maxCharacters: { classPropertyName: "maxCharacters", publicName: "maxCharacters", isSignal: true, isRequired: false, transformFunction: null }, enableOfficePaste: { classPropertyName: "enableOfficePaste", publicName: "enableOfficePaste", isSignal: true, isRequired: false, transformFunction: null }, enableSlashCommands: { classPropertyName: "enableSlashCommands", publicName: "enableSlashCommands", isSignal: true, isRequired: false, transformFunction: null }, slashCommands: { classPropertyName: "slashCommands", publicName: "slashCommands", isSignal: true, isRequired: false, transformFunction: null }, customSlashCommands: { classPropertyName: "customSlashCommands", publicName: "customSlashCommands", isSignal: true, isRequired: false, transformFunction: null }, blockControls: { classPropertyName: "blockControls", publicName: "blockControls", isSignal: true, isRequired: false, transformFunction: null }, locale: { classPropertyName: "locale", publicName: "locale", isSignal: true, isRequired: false, transformFunction: null }, autofocus: { classPropertyName: "autofocus", publicName: "autofocus", isSignal: true, isRequired: false, transformFunction: null }, mode: { classPropertyName: "mode", publicName: "mode", isSignal: true, isRequired: false, transformFunction: null }, seamless: { classPropertyName: "seamless", publicName: "seamless", isSignal: true, isRequired: false, transformFunction: null }, floatingToolbar: { classPropertyName: "floatingToolbar", publicName: "floatingToolbar", isSignal: true, isRequired: false, transformFunction: null }, showEditToggle: { classPropertyName: "showEditToggle", publicName: "showEditToggle", isSignal: true, isRequired: false, transformFunction: null }, spellcheck: { classPropertyName: "spellcheck", publicName: "spellcheck", isSignal: true, isRequired: false, transformFunction: null }, tiptapExtensions: { classPropertyName: "tiptapExtensions", publicName: "tiptapExtensions", isSignal: true, isRequired: false, transformFunction: null }, tiptapOptions: { classPropertyName: "tiptapOptions", publicName: "tiptapOptions", isSignal: true, isRequired: false, transformFunction: null }, showBubbleMenu: { classPropertyName: "showBubbleMenu", publicName: "showBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, bubbleMenu: { classPropertyName: "bubbleMenu", publicName: "bubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, showImageBubbleMenu: { classPropertyName: "showImageBubbleMenu", publicName: "showImageBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, imageBubbleMenu: { classPropertyName: "imageBubbleMenu", publicName: "imageBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, toolbar: { classPropertyName: "toolbar", publicName: "toolbar", isSignal: true, isRequired: false, transformFunction: null }, showTableBubbleMenu: { classPropertyName: "showTableBubbleMenu", publicName: "showTableBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, tableBubbleMenu: { classPropertyName: "tableBubbleMenu", publicName: "tableBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, showCellBubbleMenu: { classPropertyName: "showCellBubbleMenu", publicName: "showCellBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, cellBubbleMenu: { classPropertyName: "cellBubbleMenu", publicName: "cellBubbleMenu", isSignal: true, isRequired: false, transformFunction: null }, stateCalculators: { classPropertyName: "stateCalculators", publicName: "stateCalculators", isSignal: true, isRequired: false, transformFunction: null }, imageUpload: { classPropertyName: "imageUpload", publicName: "imageUpload", isSignal: true, isRequired: false, transformFunction: null }, imageUploadHandler: { classPropertyName: "imageUploadHandler", publicName: "imageUploadHandler", isSignal: true, isRequired: false, transformFunction: null }, editorId: { classPropertyName: "editorId", publicName: "editorId", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { contentChange: "contentChange", editorCreated: "editorCreated", editorUpdate: "editorUpdate", editorFocus: "editorFocus", editorBlur: "editorBlur", editableChange: "editableChange", imageUploaded: "imageUploaded", pastedImageRejected: "pastedImageRejected" }, host: { properties: { "class.fill-container": "finalFillContainer()", "class.floating-toolbar": "finalFloatingToolbar()", "class.is-readonly": "!finalEditable() && !mergedDisabled()", "class.is-disabled": "mergedDisabled()", "style.--ate-border-width": "finalSeamless() || mergedDisabled() ? '0' : null", "style.--ate-background": "finalSeamless() ? 'transparent' : (mergedDisabled() ? 'var(--ate-surface-tertiary)' : null)", "style.--ate-toolbar-border-color": "finalSeamless() ? 'transparent' : null", "style.--ate-counter-background": "finalSeamless() ? 'transparent' : null", "style.--ate-counter-border-color": "finalSeamless() ? 'transparent' : null", "class.dark": "config().theme === 'dark'", "class.ate-blocks-inside": "finalBlockControls() === 'inside'", "class.ate-blocks-outside": "finalBlockControls() === 'outside'", "attr.data-theme": "config().theme" } }, providers: [
|
|
9357
9551
|
AteEditorCommandsService,
|
|
9358
9552
|
AteImageService,
|
|
9359
9553
|
AteColorPickerService,
|
|
@@ -9849,5 +10043,5 @@ const ATE_DEFAULT_TOC_CONFIG = {
|
|
|
9849
10043
|
* Generated bundle index. Do not edit.
|
|
9850
10044
|
*/
|
|
9851
10045
|
|
|
9852
|
-
export { ATE_BUBBLE_MENU_KEYS, ATE_CELL_BUBBLE_MENU_KEYS, ATE_DEFAULT_BUBBLE_MENU_CONFIG, ATE_DEFAULT_CELL_MENU_CONFIG, ATE_DEFAULT_CONFIG, ATE_DEFAULT_ICONS, ATE_DEFAULT_IMAGE_BUBBLE_MENU_CONFIG, ATE_DEFAULT_IMAGE_UPLOAD_CONFIG, ATE_DEFAULT_SLASH_COMMANDS_CONFIG, ATE_DEFAULT_TABLE_MENU_CONFIG, ATE_DEFAULT_TOC_CONFIG, ATE_DEFAULT_TOOLBAR_CONFIG, ATE_GLOBAL_CONFIG, ATE_ICONS, ATE_IMAGE_BUBBLE_MENU_KEYS, ATE_INITIAL_EDITOR_STATE, ATE_MATERIAL_SYMBOLS_VIEWBOX, ATE_SLASH_COMMAND_KEYS, ATE_STROKE_ICONS, ATE_TABLE_BUBBLE_MENU_KEYS, ATE_TOOLBAR_KEYS, AngularTiptapEditorComponent, AteAngularNodeView, AteColorPickerService, AteDiscoveryCalculator, AteEditorCommandsService, AteEditorRef, AteEditorRegistry, AteExportService, AteI18nService, AteIconComponent, AteIconRegistry, AteImageCalculator, AteImageService, AteLinkService, AteMarksCalculator, AteNodeViewRenderer, AteNoopValueAccessorDirective, AteSelectionCalculator, AteStructureCalculator, AteTableCalculator, AteTableOfContentsComponent, AteTocNodeComponent, AteTocNodeOptions, AteTooltipDirective, createAngularComponentExtension, createDefaultSlashCommands, filterSlashCommands, getAteTocNodeExtension, provideAteEditor, provideAteIcons, registerAngularComponent };
|
|
10046
|
+
export { ATE_BUBBLE_MENU_KEYS, ATE_CELL_BUBBLE_MENU_KEYS, ATE_DEFAULT_BUBBLE_MENU_CONFIG, ATE_DEFAULT_CELL_MENU_CONFIG, ATE_DEFAULT_CONFIG, ATE_DEFAULT_ICONS, ATE_DEFAULT_IMAGE_BUBBLE_MENU_CONFIG, ATE_DEFAULT_IMAGE_UPLOAD_CONFIG, ATE_DEFAULT_SLASH_COMMANDS_CONFIG, ATE_DEFAULT_TABLE_MENU_CONFIG, ATE_DEFAULT_TOC_CONFIG, ATE_DEFAULT_TOOLBAR_CONFIG, ATE_GLOBAL_CONFIG, ATE_ICONS, ATE_IMAGE_BUBBLE_MENU_KEYS, ATE_INITIAL_EDITOR_STATE, ATE_MATERIAL_SYMBOLS_VIEWBOX, ATE_SLASH_COMMAND_KEYS, ATE_STROKE_ICONS, ATE_TABLE_BUBBLE_MENU_KEYS, ATE_TOOLBAR_KEYS, AngularTiptapEditorComponent, AteAngularNodeView, AteColorPickerService, AteDiscoveryCalculator, AteEditorCommandsService, AteEditorRef, AteEditorRegistry, AteExportService, AteI18nService, AteIconComponent, AteIconRegistry, AteImageCalculator, AteImageService, AteLinkService, AteMarksCalculator, AteNodeViewRenderer, AteNoopValueAccessorDirective, AtePastedImage, AteSelectionCalculator, AteStructureCalculator, AteTableCalculator, AteTableOfContentsComponent, AteTocNodeComponent, AteTocNodeOptions, AteTooltipDirective, classifyPastedImageSrc, createAngularComponentExtension, createDefaultSlashCommands, dataUriToFile, filterSlashCommands, getAteTocNodeExtension, provideAteEditor, provideAteIcons, registerAngularComponent, sanitizePastedImages };
|
|
9853
10047
|
//# sourceMappingURL=flogeez-angular-tiptap-editor.mjs.map
|