@esposter/shared 4.3.3 → 4.5.0
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/README.md +10 -19
- package/dist/index.d.ts +245 -27
- package/dist/index.js +790 -97
- package/package.json +9 -9
package/dist/index.js
CHANGED
|
@@ -105,6 +105,36 @@ let ObjectMethod = /* @__PURE__ */ function(ObjectMethod) {
|
|
|
105
105
|
ObjectMethod["ValueOf"] = "valueOf";
|
|
106
106
|
return ObjectMethod;
|
|
107
107
|
}({});
|
|
108
|
+
// src/models/panzoom/PanzoomContain.ts
|
|
109
|
+
let PanzoomContain = /* @__PURE__ */ function(PanzoomContain) {
|
|
110
|
+
PanzoomContain["Automatic"] = "automatic";
|
|
111
|
+
PanzoomContain["Inside"] = "inside";
|
|
112
|
+
PanzoomContain["Outside"] = "outside";
|
|
113
|
+
return PanzoomContain;
|
|
114
|
+
}({});
|
|
115
|
+
// src/models/panzoom/PanzoomDeltaMode.ts
|
|
116
|
+
let PanzoomDeltaMode = /* @__PURE__ */ function(PanzoomDeltaMode) {
|
|
117
|
+
PanzoomDeltaMode[PanzoomDeltaMode["Pixel"] = 0] = "Pixel";
|
|
118
|
+
PanzoomDeltaMode[PanzoomDeltaMode["Line"] = 1] = "Line";
|
|
119
|
+
PanzoomDeltaMode[PanzoomDeltaMode["Page"] = 2] = "Page";
|
|
120
|
+
return PanzoomDeltaMode;
|
|
121
|
+
}({});
|
|
122
|
+
// src/models/panzoom/PanzoomEventName.ts
|
|
123
|
+
let PanzoomEventName = /* @__PURE__ */ function(PanzoomEventName) {
|
|
124
|
+
PanzoomEventName["Change"] = "panzoomchange";
|
|
125
|
+
PanzoomEventName["End"] = "panzoomend";
|
|
126
|
+
PanzoomEventName["Pan"] = "panzoompan";
|
|
127
|
+
PanzoomEventName["Reset"] = "panzoomreset";
|
|
128
|
+
PanzoomEventName["Start"] = "panzoomstart";
|
|
129
|
+
PanzoomEventName["Zoom"] = "panzoomzoom";
|
|
130
|
+
return PanzoomEventName;
|
|
131
|
+
}({});
|
|
132
|
+
// src/models/panzoom/PanzoomZoomDirection.ts
|
|
133
|
+
let PanzoomZoomDirection = /* @__PURE__ */ function(PanzoomZoomDirection) {
|
|
134
|
+
PanzoomZoomDirection["In"] = "in";
|
|
135
|
+
PanzoomZoomDirection["Out"] = "out";
|
|
136
|
+
return PanzoomZoomDirection;
|
|
137
|
+
}({});
|
|
108
138
|
// src/services/app/constants.ts
|
|
109
139
|
const MAX_READ_LIMIT = 1e3;
|
|
110
140
|
const SITE_NAME = "Esposter";
|
|
@@ -157,6 +187,10 @@ var ItemMetadata = class {
|
|
|
157
187
|
deletedAt = null;
|
|
158
188
|
updatedAt = /* @__PURE__ */ new Date();
|
|
159
189
|
};
|
|
190
|
+
// src/util/object/getPropertyNames.ts
|
|
191
|
+
const getPropertyNames = () => new Proxy({}, { get: (_target, property) => property });
|
|
192
|
+
// src/models/shared/ItemMetadataPropertyNames.ts
|
|
193
|
+
const ItemMetadataPropertyNames = getPropertyNames();
|
|
160
194
|
// src/util/reactivity/getRawData.ts
|
|
161
195
|
const getRawData = (data) => {
|
|
162
196
|
const raw = data && data.__v_raw;
|
|
@@ -209,8 +243,12 @@ const withFinalizer = (callback, finalizer) => {
|
|
|
209
243
|
};
|
|
210
244
|
// src/services/error/withFinalizerAsync.ts
|
|
211
245
|
const withFinalizerAsync = async (callback, finalizer) => {
|
|
212
|
-
const callbackResult = await getResultAsync(async () =>
|
|
213
|
-
|
|
246
|
+
const callbackResult = await getResultAsync(async () => {
|
|
247
|
+
return await callback();
|
|
248
|
+
});
|
|
249
|
+
if (finalizer) await getResultAsync(async () => {
|
|
250
|
+
await finalizer();
|
|
251
|
+
}).match(noop, (error) => {
|
|
214
252
|
reportFinalizerError(callbackResult, error);
|
|
215
253
|
});
|
|
216
254
|
return callbackResult.match((value) => value, (error) => {
|
|
@@ -336,12 +374,23 @@ const wrapUpgradeDatabase = (database) => ({
|
|
|
336
374
|
...wrapDatabase(database),
|
|
337
375
|
createObjectStore: (name, options) => wrapObjectStore(database.createObjectStore(name, options))
|
|
338
376
|
});
|
|
377
|
+
// src/util/function/getSynchronizedFunction.ts
|
|
378
|
+
const pendingPromises = /* @__PURE__ */ new Set();
|
|
379
|
+
const getSynchronizedFunction = (asyncFunction) => (...args) => {
|
|
380
|
+
const promise = withFinalizerAsync(() => asyncFunction(...args), () => {
|
|
381
|
+
pendingPromises.delete(promise);
|
|
382
|
+
});
|
|
383
|
+
pendingPromises.add(promise);
|
|
384
|
+
};
|
|
385
|
+
const waitForSynchronizedFunctions = async () => {
|
|
386
|
+
await Promise.allSettled(pendingPromises);
|
|
387
|
+
};
|
|
339
388
|
// src/services/indexedDb/wrapUpgradeTransaction.ts
|
|
340
389
|
const wrapUpgradeTransaction = (transaction) => {
|
|
341
390
|
const done = getTransactionDone(transaction);
|
|
342
|
-
getResultAsync(() => done).match(noop, (error) => {
|
|
391
|
+
getSynchronizedFunction(() => getResultAsync(() => done).match(noop, (error) => {
|
|
343
392
|
if (transaction.error) console.error(error);
|
|
344
|
-
});
|
|
393
|
+
}))();
|
|
345
394
|
return {
|
|
346
395
|
get done() {
|
|
347
396
|
return done;
|
|
@@ -610,6 +659,10 @@ const CUSTOM_EMOJI_ID_ATTRIBUTE = "data-custom-emoji-id";
|
|
|
610
659
|
const CUSTOM_EMOJI_NAME_ATTRIBUTE = "data-custom-emoji-name";
|
|
611
660
|
const SPOILER_ATTRIBUTE = "data-spoiler";
|
|
612
661
|
const SPOILER_SELECTOR = `span[${SPOILER_ATTRIBUTE}]`;
|
|
662
|
+
// src/services/message/emoji/checkIsOnlyReactor.ts
|
|
663
|
+
const checkIsOnlyReactor = (userIds, userId) => userIds.length === 1 && userIds[0] === userId;
|
|
664
|
+
// src/services/message/emoji/getUpdatedUserIds.ts
|
|
665
|
+
const getUpdatedUserIds = (userIds, newUserId) => userIds.includes(newUserId) ? userIds.filter((id) => id !== newUserId) : [...userIds, newUserId];
|
|
613
666
|
// src/services/message/getMentions.ts
|
|
614
667
|
const getMentions = (message) => parse(message).querySelectorAll(MENTION_SELECTOR);
|
|
615
668
|
// src/services/mime/constants.ts
|
|
@@ -701,6 +754,643 @@ const contentType = (value) => {
|
|
|
701
754
|
};
|
|
702
755
|
// src/services/mime/extension.ts
|
|
703
756
|
const extension = (type) => getMimeTypeEntryMap().get(getMediaType(type).toLowerCase())?.extensions?.[0] ?? false;
|
|
757
|
+
// src/services/panzoom/constants.ts
|
|
758
|
+
const PANZOOM_DEFAULT_MAX_SCALE = 4;
|
|
759
|
+
const PANZOOM_DEFAULT_MIN_SCALE = .125;
|
|
760
|
+
const PANZOOM_DEFAULT_START_SCALE = 1;
|
|
761
|
+
const PANZOOM_DEFAULT_STEP = .3;
|
|
762
|
+
const PANZOOM_WHEEL_STEP_DIVISOR = 3;
|
|
763
|
+
const PANZOOM_WHEEL_NOTCH_PIXELS = 100;
|
|
764
|
+
const PANZOOM_PIXELS_PER_LINE = 16;
|
|
765
|
+
const PANZOOM_PRIMARY_BUTTON = 0;
|
|
766
|
+
const PANZOOM_DEFAULT_CURSOR = "move";
|
|
767
|
+
const PANZOOM_DEFAULT_DURATION = 200;
|
|
768
|
+
const PANZOOM_DEFAULT_EASING = "ease-in-out";
|
|
769
|
+
const PANZOOM_DEFAULT_EXCLUDE_CLASS = "panzoom-exclude";
|
|
770
|
+
const PANZOOM_DEFAULT_OVERFLOW = "hidden";
|
|
771
|
+
const PANZOOM_DEFAULT_PAN_THRESHOLD = 0;
|
|
772
|
+
const PANZOOM_DEFAULT_START_PAN = 0;
|
|
773
|
+
const PANZOOM_DEFAULT_TOUCH_ACTION = "none";
|
|
774
|
+
const PANZOOM_TRANSFORM_ORIGIN = "50% 50%";
|
|
775
|
+
const PANZOOM_SVG_NAMESPACE = "http://www.w3.org/2000/svg";
|
|
776
|
+
const PANZOOM_DEFAULT_OPTIONS = Object.freeze({
|
|
777
|
+
animate: false,
|
|
778
|
+
canvas: false,
|
|
779
|
+
cursor: PANZOOM_DEFAULT_CURSOR,
|
|
780
|
+
disablePan: false,
|
|
781
|
+
disableXAxis: false,
|
|
782
|
+
disableYAxis: false,
|
|
783
|
+
disableZoom: false,
|
|
784
|
+
duration: 200,
|
|
785
|
+
easing: PANZOOM_DEFAULT_EASING,
|
|
786
|
+
excludeClass: PANZOOM_DEFAULT_EXCLUDE_CLASS,
|
|
787
|
+
maxScale: 4,
|
|
788
|
+
minScale: PANZOOM_DEFAULT_MIN_SCALE,
|
|
789
|
+
overflow: PANZOOM_DEFAULT_OVERFLOW,
|
|
790
|
+
panOnlyWhenZoomed: false,
|
|
791
|
+
panThreshold: 0,
|
|
792
|
+
pinchAndPan: false,
|
|
793
|
+
relative: false,
|
|
794
|
+
startScale: 1,
|
|
795
|
+
startX: 0,
|
|
796
|
+
startY: 0,
|
|
797
|
+
step: PANZOOM_DEFAULT_STEP,
|
|
798
|
+
touchAction: PANZOOM_DEFAULT_TOUCH_ACTION
|
|
799
|
+
});
|
|
800
|
+
// src/services/panzoom/getPanzoomTarget.ts
|
|
801
|
+
const getPanzoomTarget = ({ element, options, parent }) => options.canvas ? parent : element;
|
|
802
|
+
// src/services/panzoom/restorePanzoomStyles.ts
|
|
803
|
+
const restorePanzoomStyles = ({ styles }, properties) => {
|
|
804
|
+
for (const [element, values] of styles) {
|
|
805
|
+
const restoredProperties = properties ?? [...values.keys()];
|
|
806
|
+
for (const property of restoredProperties.filter((name) => values.has(name))) {
|
|
807
|
+
const previousValue = values.get(property) ?? "";
|
|
808
|
+
if (previousValue) element.style.setProperty(property, previousValue);
|
|
809
|
+
else element.style.removeProperty(property);
|
|
810
|
+
values.delete(property);
|
|
811
|
+
}
|
|
812
|
+
}
|
|
813
|
+
};
|
|
814
|
+
// src/util/map/getOrCreate.ts
|
|
815
|
+
const getOrCreate = (map, key, create) => {
|
|
816
|
+
if (map.has(key)) return map.get(key);
|
|
817
|
+
const value = create();
|
|
818
|
+
map.set(key, value);
|
|
819
|
+
return value;
|
|
820
|
+
};
|
|
821
|
+
// src/services/panzoom/writePanzoomStyle.ts
|
|
822
|
+
const writePanzoomStyle = ({ isDestroyed, styles }, element, property, value) => {
|
|
823
|
+
if (isDestroyed) return;
|
|
824
|
+
const values = getOrCreate(styles, element, () => /* @__PURE__ */ new Map());
|
|
825
|
+
if (!values.has(property)) values.set(property, element.style.getPropertyValue(property));
|
|
826
|
+
element.style.setProperty(property, value);
|
|
827
|
+
};
|
|
828
|
+
// src/services/panzoom/applyPanzoomStyles.ts
|
|
829
|
+
const applyPanzoomStyles = (context) => {
|
|
830
|
+
const { element, options, parent } = context;
|
|
831
|
+
const touchAction = options.touchAction ?? "none";
|
|
832
|
+
writePanzoomStyle(context, parent, "overflow", options.overflow ?? "hidden");
|
|
833
|
+
writePanzoomStyle(context, parent, "touch-action", touchAction);
|
|
834
|
+
writePanzoomStyle(context, element, "touch-action", touchAction);
|
|
835
|
+
if (options.disablePan) restorePanzoomStyles(context, ["cursor"]);
|
|
836
|
+
else writePanzoomStyle(context, getPanzoomTarget(context), "cursor", options.cursor ?? "move");
|
|
837
|
+
};
|
|
838
|
+
// src/services/panzoom/dispatchPanzoomEvent.ts
|
|
839
|
+
const dispatchPanzoomEvent = ({ element, isDestroyed }, name, detail, { silent }) => {
|
|
840
|
+
if (silent || isDestroyed) return;
|
|
841
|
+
element.dispatchEvent(new CustomEvent(name, { detail }));
|
|
842
|
+
};
|
|
843
|
+
// src/services/panzoom/getPanzoomDrag.ts
|
|
844
|
+
const getPanzoomDrag = (state, point) => ({
|
|
845
|
+
anchorPan: {
|
|
846
|
+
x: state.x,
|
|
847
|
+
y: state.y
|
|
848
|
+
},
|
|
849
|
+
anchorPoint: point,
|
|
850
|
+
downPoint: point,
|
|
851
|
+
isDragging: false
|
|
852
|
+
});
|
|
853
|
+
// src/services/panzoom/getPanzoomEventDetail.ts
|
|
854
|
+
const getPanzoomEventDetail = ({ element, state }, originalEvent) => ({
|
|
855
|
+
isSVG: element.namespaceURI === "http://www.w3.org/2000/svg" && element.localName !== "svg",
|
|
856
|
+
originalEvent,
|
|
857
|
+
scale: state.scale,
|
|
858
|
+
x: state.x,
|
|
859
|
+
y: state.y
|
|
860
|
+
});
|
|
861
|
+
// src/util/array/takeOne.ts
|
|
862
|
+
const takeOne = (values, index = 0) => {
|
|
863
|
+
return values[index];
|
|
864
|
+
};
|
|
865
|
+
// src/services/panzoom/endPanzoomGesture.ts
|
|
866
|
+
const endPanzoomGesture = (context, event) => {
|
|
867
|
+
const { options, pointers, state } = context;
|
|
868
|
+
if (!pointers.has(event.pointerId)) return;
|
|
869
|
+
pointers.delete(event.pointerId);
|
|
870
|
+
if (context.drag?.isDragging && event.type === "pointerup" && event.button === 0) context.isClickSuppressed = true;
|
|
871
|
+
context.drag = void 0;
|
|
872
|
+
context.pinch = void 0;
|
|
873
|
+
const remainingPoints = [...pointers.values()];
|
|
874
|
+
if (remainingPoints.length === 1) context.drag = getPanzoomDrag(state, takeOne(remainingPoints, 0));
|
|
875
|
+
if (pointers.size > 0) return;
|
|
876
|
+
restorePanzoomStyles(context, ["user-select"]);
|
|
877
|
+
applyPanzoomStyles(context);
|
|
878
|
+
dispatchPanzoomEvent(context, "panzoomend", getPanzoomEventDetail(context, event), options);
|
|
879
|
+
};
|
|
880
|
+
// src/services/panzoom/checkIsContainableLength.ts
|
|
881
|
+
const checkIsContainableLength = (length) => Number.isFinite(length) && length > 0;
|
|
882
|
+
// src/services/panzoom/constrainPanzoomAxis.ts
|
|
883
|
+
const constrainPanzoomAxis = (value, axis, scale, contain) => {
|
|
884
|
+
if (!contain || !checkIsContainableLength(axis.parentLength)) return value;
|
|
885
|
+
const halfLength = axis.length / 2;
|
|
886
|
+
const leadingPan = (axis.parentStart - axis.center) / scale + halfLength;
|
|
887
|
+
const trailingPan = (axis.parentStart + axis.parentLength - axis.center) / scale - halfLength;
|
|
888
|
+
const isFitting = axis.length * scale <= axis.parentLength;
|
|
889
|
+
const isInside = contain === "inside" || contain === "automatic" && isFitting;
|
|
890
|
+
return Math.max(Math.min(value, isInside ? trailingPan : leadingPan), isInside ? leadingPan : trailingPan);
|
|
891
|
+
};
|
|
892
|
+
// src/services/panzoom/getPanzoomCoverScale.ts
|
|
893
|
+
const getPanzoomCoverScale = (measure) => Math.max(measure.parent.width / measure.size.width, measure.parent.height / measure.size.height);
|
|
894
|
+
// src/services/panzoom/getPanzoomFitScale.ts
|
|
895
|
+
const getPanzoomFitScale = ({ parent, size }) => {
|
|
896
|
+
const fit = Math.min(checkIsContainableLength(parent.width) ? parent.width / size.width : Number.POSITIVE_INFINITY, checkIsContainableLength(parent.height) ? parent.height / size.height : Number.POSITIVE_INFINITY);
|
|
897
|
+
return Number.isFinite(fit) ? fit : 1;
|
|
898
|
+
};
|
|
899
|
+
// src/services/panzoom/constrainPanzoomScale.ts
|
|
900
|
+
const constrainPanzoomScale = (scale, measure, { contain, maxScale = 4, minScale = PANZOOM_DEFAULT_MIN_SCALE }) => {
|
|
901
|
+
const isParentContainable = checkIsContainableLength(measure.parent.width) || checkIsContainableLength(measure.parent.height);
|
|
902
|
+
if (!contain || !isParentContainable || measure.size.width <= 1 || measure.size.height <= 1) return Math.min(Math.max(scale, minScale), maxScale);
|
|
903
|
+
if (contain === "inside") {
|
|
904
|
+
const cap = Math.max(minScale, Math.min(maxScale, getPanzoomFitScale(measure)));
|
|
905
|
+
return Math.min(Math.max(scale, minScale), cap);
|
|
906
|
+
}
|
|
907
|
+
const floor = contain === "outside" ? getPanzoomCoverScale(measure) : getPanzoomFitScale(measure);
|
|
908
|
+
return Math.min(Math.max(scale, Math.max(minScale, floor)), maxScale);
|
|
909
|
+
};
|
|
910
|
+
// src/services/panzoom/getPanzoomStartScale.ts
|
|
911
|
+
const getPanzoomStartScale = (measure, options) => {
|
|
912
|
+
const { startScale = 1 } = options;
|
|
913
|
+
const scale = startScale === "fit" ? getPanzoomFitScale(measure) : startScale;
|
|
914
|
+
return constrainPanzoomScale(scale, measure, options);
|
|
915
|
+
};
|
|
916
|
+
// src/services/panzoom/constrainPanzoomPan.ts
|
|
917
|
+
const constrainPanzoomPan = (current, requested, toScale, measure, options) => {
|
|
918
|
+
const { contain, disablePan, disableXAxis, disableYAxis, force, panOnlyWhenZoomed, relative, roundPixels } = options;
|
|
919
|
+
const isPanDisabled = disablePan || panOnlyWhenZoomed && current.scale === getPanzoomStartScale(measure, options);
|
|
920
|
+
if (!force && isPanDisabled) return {
|
|
921
|
+
x: current.x,
|
|
922
|
+
y: current.y
|
|
923
|
+
};
|
|
924
|
+
const offsetX = relative ? current.x : 0;
|
|
925
|
+
const offsetY = relative ? current.y : 0;
|
|
926
|
+
const unconstrainedX = disableXAxis ? current.x : offsetX + requested.x;
|
|
927
|
+
const unconstrainedY = disableYAxis ? current.y : offsetY + requested.y;
|
|
928
|
+
const roundedX = roundPixels ? Math.round(unconstrainedX) : unconstrainedX;
|
|
929
|
+
const roundedY = roundPixels ? Math.round(unconstrainedY) : unconstrainedY;
|
|
930
|
+
const axisX = {
|
|
931
|
+
center: measure.center.x,
|
|
932
|
+
length: measure.size.width,
|
|
933
|
+
parentLength: measure.parent.width,
|
|
934
|
+
parentStart: measure.parent.left
|
|
935
|
+
};
|
|
936
|
+
const axisY = {
|
|
937
|
+
center: measure.center.y,
|
|
938
|
+
length: measure.size.height,
|
|
939
|
+
parentLength: measure.parent.height,
|
|
940
|
+
parentStart: measure.parent.top
|
|
941
|
+
};
|
|
942
|
+
return {
|
|
943
|
+
x: constrainPanzoomAxis(roundedX, axisX, toScale, contain),
|
|
944
|
+
y: constrainPanzoomAxis(roundedY, axisY, toScale, contain)
|
|
945
|
+
};
|
|
946
|
+
};
|
|
947
|
+
// src/services/panzoom/dispatchPanzoomChange.ts
|
|
948
|
+
const dispatchPanzoomChange = (context, name, detail, options) => {
|
|
949
|
+
dispatchPanzoomEvent(context, name, detail, options);
|
|
950
|
+
dispatchPanzoomEvent(context, "panzoomchange", detail, options);
|
|
951
|
+
};
|
|
952
|
+
// src/services/panzoom/getPanzoomCallOptions.ts
|
|
953
|
+
const getPanzoomCallOptions = ({ options }, callOptions) => ({
|
|
954
|
+
...options,
|
|
955
|
+
...callOptions
|
|
956
|
+
});
|
|
957
|
+
// src/services/panzoom/getPanzoomMeasure.ts
|
|
958
|
+
const getInset = (border, padding) => Number.parseFloat(border) + Number.parseFloat(padding);
|
|
959
|
+
const getPanzoomMeasure = (element, parent, state) => {
|
|
960
|
+
const rectangle = element.getBoundingClientRect();
|
|
961
|
+
const parentRectangle = parent.getBoundingClientRect();
|
|
962
|
+
const parentStyle = getComputedStyle(parent);
|
|
963
|
+
const insetLeft = getInset(parentStyle.borderLeftWidth, parentStyle.paddingLeft);
|
|
964
|
+
const insetTop = getInset(parentStyle.borderTopWidth, parentStyle.paddingTop);
|
|
965
|
+
const insetRight = getInset(parentStyle.borderRightWidth, parentStyle.paddingRight);
|
|
966
|
+
const insetBottom = getInset(parentStyle.borderBottomWidth, parentStyle.paddingBottom);
|
|
967
|
+
return {
|
|
968
|
+
center: {
|
|
969
|
+
x: rectangle.left + rectangle.width / 2 - state.scale * state.x,
|
|
970
|
+
y: rectangle.top + rectangle.height / 2 - state.scale * state.y
|
|
971
|
+
},
|
|
972
|
+
parent: {
|
|
973
|
+
height: parentRectangle.height - insetTop - insetBottom,
|
|
974
|
+
left: parentRectangle.left + insetLeft,
|
|
975
|
+
top: parentRectangle.top + insetTop,
|
|
976
|
+
width: parentRectangle.width - insetLeft - insetRight
|
|
977
|
+
},
|
|
978
|
+
size: {
|
|
979
|
+
height: rectangle.height / state.scale,
|
|
980
|
+
width: rectangle.width / state.scale
|
|
981
|
+
}
|
|
982
|
+
};
|
|
983
|
+
};
|
|
984
|
+
// src/services/panzoom/writePanzoomState.ts
|
|
985
|
+
const writePanzoomState = (context, state, { animate, duration = 200, easing = PANZOOM_DEFAULT_EASING, setTransform }) => {
|
|
986
|
+
if (context.isDestroyed) return;
|
|
987
|
+
const { element } = context;
|
|
988
|
+
context.state = state;
|
|
989
|
+
writePanzoomStyle(context, element, "transition", animate ? `transform ${duration}ms ${easing}` : "none");
|
|
990
|
+
if (setTransform) setTransform(element, getPanzoomEventDetail(context));
|
|
991
|
+
else writePanzoomStyle(context, element, "transform", `scale(${state.scale}) translate(${state.x}px, ${state.y}px)`);
|
|
992
|
+
writePanzoomStyle(context, element, "--panzoom-scale", `${state.scale}`);
|
|
993
|
+
};
|
|
994
|
+
// src/services/panzoom/panPanzoom.ts
|
|
995
|
+
const panPanzoom = (context, point, callOptions, originalEvent) => {
|
|
996
|
+
const options = getPanzoomCallOptions(context, callOptions);
|
|
997
|
+
const { element, parent, state } = context;
|
|
998
|
+
const measure = getPanzoomMeasure(element, parent, state);
|
|
999
|
+
const pan = constrainPanzoomPan(state, point, state.scale, measure, options);
|
|
1000
|
+
if (pan.x === state.x && pan.y === state.y) return getPanzoomEventDetail(context, originalEvent);
|
|
1001
|
+
writePanzoomState(context, {
|
|
1002
|
+
scale: state.scale,
|
|
1003
|
+
x: pan.x,
|
|
1004
|
+
y: pan.y
|
|
1005
|
+
}, options);
|
|
1006
|
+
const detail = getPanzoomEventDetail(context, originalEvent);
|
|
1007
|
+
dispatchPanzoomChange(context, "panzoompan", detail, options);
|
|
1008
|
+
return detail;
|
|
1009
|
+
};
|
|
1010
|
+
// src/services/panzoom/movePanzoomDrag.ts
|
|
1011
|
+
const movePanzoomDrag = (context, drag, point, event) => {
|
|
1012
|
+
const { options, state } = context;
|
|
1013
|
+
if (!drag.isDragging) {
|
|
1014
|
+
if (Math.hypot(point.x - drag.downPoint.x, point.y - drag.downPoint.y) <= (options.panThreshold ?? 0)) return;
|
|
1015
|
+
drag.isDragging = true;
|
|
1016
|
+
}
|
|
1017
|
+
panPanzoom(context, {
|
|
1018
|
+
x: drag.anchorPan.x + (point.x - drag.anchorPoint.x) / state.scale,
|
|
1019
|
+
y: drag.anchorPan.y + (point.y - drag.anchorPoint.y) / state.scale
|
|
1020
|
+
}, {
|
|
1021
|
+
animate: false,
|
|
1022
|
+
relative: false
|
|
1023
|
+
}, event);
|
|
1024
|
+
};
|
|
1025
|
+
// src/services/panzoom/getPanzoomPinchFrame.ts
|
|
1026
|
+
const getPanzoomPinchFrame = (pointers) => {
|
|
1027
|
+
const points = [...pointers.values()];
|
|
1028
|
+
const first = takeOne(points, 0);
|
|
1029
|
+
const second = takeOne(points, 1);
|
|
1030
|
+
return {
|
|
1031
|
+
distance: Math.hypot(first.x - second.x, first.y - second.y),
|
|
1032
|
+
midpoint: {
|
|
1033
|
+
x: (first.x + second.x) / 2,
|
|
1034
|
+
y: (first.y + second.y) / 2
|
|
1035
|
+
}
|
|
1036
|
+
};
|
|
1037
|
+
};
|
|
1038
|
+
// src/services/panzoom/getPanzoomPinchScale.ts
|
|
1039
|
+
const getPanzoomPinchScale = (startScale, startDistance, distance) => startDistance > 0 ? startScale * distance / startDistance : startScale;
|
|
1040
|
+
// src/services/panzoom/checkIsZoomRefused.ts
|
|
1041
|
+
const checkIsZoomRefused = ({ disableZoom, force }) => Boolean(disableZoom) && !force;
|
|
1042
|
+
// src/services/panzoom/getPanzoomFocalPan.ts
|
|
1043
|
+
const getPanzoomFocalPan = (current, toScale, point, measure) => {
|
|
1044
|
+
const offsetX = point.x - measure.center.x;
|
|
1045
|
+
const offsetY = point.y - measure.center.y;
|
|
1046
|
+
return {
|
|
1047
|
+
x: offsetX / toScale - offsetX / current.scale + current.x,
|
|
1048
|
+
y: offsetY / toScale - offsetY / current.scale + current.y
|
|
1049
|
+
};
|
|
1050
|
+
};
|
|
1051
|
+
// src/services/panzoom/getPanzoomZoomedState.ts
|
|
1052
|
+
const getPanzoomZoomedState = (state, measure, options, scale, focal) => {
|
|
1053
|
+
const toScale = constrainPanzoomScale(scale, measure, options);
|
|
1054
|
+
const requested = focal ? getPanzoomFocalPan(state, toScale, focal, measure) : {
|
|
1055
|
+
x: state.x,
|
|
1056
|
+
y: state.y
|
|
1057
|
+
};
|
|
1058
|
+
const pan = constrainPanzoomPan(state, requested, toScale, measure, {
|
|
1059
|
+
...options,
|
|
1060
|
+
force: true,
|
|
1061
|
+
relative: false
|
|
1062
|
+
});
|
|
1063
|
+
return {
|
|
1064
|
+
scale: toScale,
|
|
1065
|
+
x: pan.x,
|
|
1066
|
+
y: pan.y
|
|
1067
|
+
};
|
|
1068
|
+
};
|
|
1069
|
+
// src/services/panzoom/reanchorPanzoomDrag.ts
|
|
1070
|
+
const reanchorPanzoomDrag = ({ drag, pointers, state }) => {
|
|
1071
|
+
if (!drag) return;
|
|
1072
|
+
drag.anchorPoint = takeOne([...pointers.values()], 0);
|
|
1073
|
+
drag.anchorPan = {
|
|
1074
|
+
x: state.x,
|
|
1075
|
+
y: state.y
|
|
1076
|
+
};
|
|
1077
|
+
};
|
|
1078
|
+
// src/services/panzoom/zoomPanzoom.ts
|
|
1079
|
+
const zoomPanzoom = (context, scale, callOptions, originalEvent) => {
|
|
1080
|
+
const options = getPanzoomCallOptions(context, callOptions);
|
|
1081
|
+
if (checkIsZoomRefused(options)) return getPanzoomEventDetail(context, originalEvent);
|
|
1082
|
+
const { element, parent, state } = context;
|
|
1083
|
+
const measure = getPanzoomMeasure(element, parent, state);
|
|
1084
|
+
writePanzoomState(context, getPanzoomZoomedState(state, measure, options, scale, options.focal), options);
|
|
1085
|
+
const detail = getPanzoomEventDetail(context, originalEvent);
|
|
1086
|
+
dispatchPanzoomChange(context, "panzoomzoom", detail, options);
|
|
1087
|
+
reanchorPanzoomDrag(context);
|
|
1088
|
+
return detail;
|
|
1089
|
+
};
|
|
1090
|
+
// src/services/panzoom/movePanzoomPinch.ts
|
|
1091
|
+
const movePanzoomPinch = (context, pinch, event) => {
|
|
1092
|
+
const frame = getPanzoomPinchFrame(context.pointers);
|
|
1093
|
+
const scale = getPanzoomPinchScale(pinch.startScale, pinch.startDistance, frame.distance);
|
|
1094
|
+
zoomPanzoom(context, scale, {
|
|
1095
|
+
animate: false,
|
|
1096
|
+
focal: pinch.midpoint
|
|
1097
|
+
}, event);
|
|
1098
|
+
if (context.options.pinchAndPan) {
|
|
1099
|
+
const { state } = context;
|
|
1100
|
+
panPanzoom(context, {
|
|
1101
|
+
x: state.x + (frame.midpoint.x - pinch.midpoint.x) / state.scale,
|
|
1102
|
+
y: state.y + (frame.midpoint.y - pinch.midpoint.y) / state.scale
|
|
1103
|
+
}, {
|
|
1104
|
+
animate: false,
|
|
1105
|
+
relative: false
|
|
1106
|
+
}, event);
|
|
1107
|
+
}
|
|
1108
|
+
pinch.midpoint = frame.midpoint;
|
|
1109
|
+
};
|
|
1110
|
+
// src/services/panzoom/movePanzoomGesture.ts
|
|
1111
|
+
const movePanzoomGesture = (context, event) => {
|
|
1112
|
+
const { drag, pinch, pointers } = context;
|
|
1113
|
+
if (!pointers.has(event.pointerId)) return;
|
|
1114
|
+
const point = {
|
|
1115
|
+
x: event.clientX,
|
|
1116
|
+
y: event.clientY
|
|
1117
|
+
};
|
|
1118
|
+
pointers.set(event.pointerId, point);
|
|
1119
|
+
if (pinch) movePanzoomPinch(context, pinch, event);
|
|
1120
|
+
else if (drag && event.pointerId === takeOne([...pointers.keys()], 0)) movePanzoomDrag(context, drag, point, event);
|
|
1121
|
+
};
|
|
1122
|
+
// src/services/panzoom/checkIsPanzoomExcluded.ts
|
|
1123
|
+
const checkIsPanzoomExcluded = (target, { exclude = [], excludeClass = PANZOOM_DEFAULT_EXCLUDE_CLASS }) => exclude.some((excluded) => excluded.contains(target)) || target.closest(`.${CSS.escape(excludeClass)}`) !== null;
|
|
1124
|
+
// src/services/panzoom/startPanzoomGesture.ts
|
|
1125
|
+
const startPanzoomGesture = (context, event) => {
|
|
1126
|
+
const { element, options, pointers, state } = context;
|
|
1127
|
+
context.isClickSuppressed = false;
|
|
1128
|
+
if (pointers.size >= 2) return;
|
|
1129
|
+
if (checkIsPanzoomExcluded(event.target, options)) return;
|
|
1130
|
+
const { filter } = options;
|
|
1131
|
+
if (filter && !filter(event)) return;
|
|
1132
|
+
const point = {
|
|
1133
|
+
x: event.clientX,
|
|
1134
|
+
y: event.clientY
|
|
1135
|
+
};
|
|
1136
|
+
pointers.set(event.pointerId, point);
|
|
1137
|
+
getPanzoomTarget(context).setPointerCapture(event.pointerId);
|
|
1138
|
+
if (options.handleStartEvent) options.handleStartEvent(event);
|
|
1139
|
+
else {
|
|
1140
|
+
event.preventDefault();
|
|
1141
|
+
event.stopPropagation();
|
|
1142
|
+
}
|
|
1143
|
+
if (pointers.size === 1) context.drag = getPanzoomDrag(state, point);
|
|
1144
|
+
if (pointers.size === 2) {
|
|
1145
|
+
const frame = getPanzoomPinchFrame(pointers);
|
|
1146
|
+
if (frame.distance > 0) {
|
|
1147
|
+
context.drag = void 0;
|
|
1148
|
+
context.pinch = {
|
|
1149
|
+
midpoint: frame.midpoint,
|
|
1150
|
+
startDistance: frame.distance,
|
|
1151
|
+
startScale: state.scale
|
|
1152
|
+
};
|
|
1153
|
+
}
|
|
1154
|
+
}
|
|
1155
|
+
writePanzoomStyle(context, element, "user-select", "none");
|
|
1156
|
+
if (!options.disablePan && options.panCursor) writePanzoomStyle(context, getPanzoomTarget(context), "cursor", options.panCursor);
|
|
1157
|
+
dispatchPanzoomEvent(context, "panzoomstart", getPanzoomEventDetail(context, event), options);
|
|
1158
|
+
};
|
|
1159
|
+
// src/services/panzoom/bindPanzoom.ts
|
|
1160
|
+
const bindPanzoom = (context, signal) => {
|
|
1161
|
+
const target = getPanzoomTarget(context);
|
|
1162
|
+
const { ownerDocument } = context.element;
|
|
1163
|
+
target.addEventListener("pointerdown", (event) => {
|
|
1164
|
+
startPanzoomGesture(context, event);
|
|
1165
|
+
}, { signal });
|
|
1166
|
+
target.addEventListener("click", (event) => {
|
|
1167
|
+
if (!context.isClickSuppressed) return;
|
|
1168
|
+
context.isClickSuppressed = false;
|
|
1169
|
+
event.preventDefault();
|
|
1170
|
+
event.stopPropagation();
|
|
1171
|
+
}, {
|
|
1172
|
+
capture: true,
|
|
1173
|
+
signal
|
|
1174
|
+
});
|
|
1175
|
+
ownerDocument.addEventListener("pointermove", (event) => {
|
|
1176
|
+
movePanzoomGesture(context, event);
|
|
1177
|
+
}, {
|
|
1178
|
+
passive: true,
|
|
1179
|
+
signal
|
|
1180
|
+
});
|
|
1181
|
+
ownerDocument.addEventListener("pointerup", (event) => {
|
|
1182
|
+
endPanzoomGesture(context, event);
|
|
1183
|
+
}, {
|
|
1184
|
+
passive: true,
|
|
1185
|
+
signal
|
|
1186
|
+
});
|
|
1187
|
+
ownerDocument.addEventListener("pointercancel", (event) => {
|
|
1188
|
+
endPanzoomGesture(context, event);
|
|
1189
|
+
}, {
|
|
1190
|
+
passive: true,
|
|
1191
|
+
signal
|
|
1192
|
+
});
|
|
1193
|
+
};
|
|
1194
|
+
// src/services/panzoom/checkIsPanzoomElement.ts
|
|
1195
|
+
const checkIsPanzoomElement = (value) => "style" in value;
|
|
1196
|
+
// src/services/panzoom/getPanzoomCentredPan.ts
|
|
1197
|
+
const getPanzoomCentredPan = (scale, measure) => {
|
|
1198
|
+
const parentCentreX = measure.parent.left + measure.parent.width / 2;
|
|
1199
|
+
const parentCentreY = measure.parent.top + measure.parent.height / 2;
|
|
1200
|
+
return {
|
|
1201
|
+
x: (parentCentreX - measure.center.x) / scale,
|
|
1202
|
+
y: (parentCentreY - measure.center.y) / scale
|
|
1203
|
+
};
|
|
1204
|
+
};
|
|
1205
|
+
// src/services/panzoom/fitPanzoom.ts
|
|
1206
|
+
const fitPanzoom = (context, callOptions) => {
|
|
1207
|
+
const options = getPanzoomCallOptions(context, {
|
|
1208
|
+
force: true,
|
|
1209
|
+
...callOptions
|
|
1210
|
+
});
|
|
1211
|
+
const { element, parent, state } = context;
|
|
1212
|
+
const measure = getPanzoomMeasure(element, parent, state);
|
|
1213
|
+
const scale = constrainPanzoomScale(getPanzoomFitScale(measure), measure, options);
|
|
1214
|
+
const pan = constrainPanzoomPan(state, getPanzoomCentredPan(scale, measure), scale, measure, {
|
|
1215
|
+
...options,
|
|
1216
|
+
relative: false
|
|
1217
|
+
});
|
|
1218
|
+
writePanzoomState(context, {
|
|
1219
|
+
scale,
|
|
1220
|
+
x: pan.x,
|
|
1221
|
+
y: pan.y
|
|
1222
|
+
}, options);
|
|
1223
|
+
const detail = getPanzoomEventDetail(context);
|
|
1224
|
+
dispatchPanzoomChange(context, "panzoomzoom", detail, options);
|
|
1225
|
+
reanchorPanzoomDrag(context);
|
|
1226
|
+
return detail;
|
|
1227
|
+
};
|
|
1228
|
+
// src/services/panzoom/getPanzoomParent.ts
|
|
1229
|
+
const getPanzoomParent = (element) => {
|
|
1230
|
+
const { parentNode } = element;
|
|
1231
|
+
if (parentNode?.nodeType === Node.DOCUMENT_FRAGMENT_NODE && "host" in parentNode) {
|
|
1232
|
+
const { host } = parentNode;
|
|
1233
|
+
return checkIsPanzoomElement(host) ? host : null;
|
|
1234
|
+
}
|
|
1235
|
+
return element.parentElement;
|
|
1236
|
+
};
|
|
1237
|
+
// src/services/panzoom/getPanzoomStartState.ts
|
|
1238
|
+
const getPanzoomStartState = (state, measure, options) => {
|
|
1239
|
+
const { startX = 0, startY = 0 } = options;
|
|
1240
|
+
const scale = getPanzoomStartScale(measure, options);
|
|
1241
|
+
const pan = constrainPanzoomPan(state, {
|
|
1242
|
+
x: startX,
|
|
1243
|
+
y: startY
|
|
1244
|
+
}, scale, measure, {
|
|
1245
|
+
...options,
|
|
1246
|
+
force: true,
|
|
1247
|
+
relative: false
|
|
1248
|
+
});
|
|
1249
|
+
return {
|
|
1250
|
+
scale,
|
|
1251
|
+
x: pan.x,
|
|
1252
|
+
y: pan.y
|
|
1253
|
+
};
|
|
1254
|
+
};
|
|
1255
|
+
// src/services/panzoom/getPanzoomWheelScale.ts
|
|
1256
|
+
const getPanzoomWheelScale = (scale, { deltaMode, deltaX, deltaY }, step = PANZOOM_DEFAULT_STEP) => {
|
|
1257
|
+
const delta = deltaY === 0 ? deltaX : deltaY;
|
|
1258
|
+
const pixelDelta = deltaMode === 0 ? delta : delta * 16;
|
|
1259
|
+
const notchFraction = Math.min(Math.abs(pixelDelta) / 100, 1);
|
|
1260
|
+
const direction = -Math.sign(pixelDelta);
|
|
1261
|
+
return scale * Math.exp(direction * step * notchFraction / 3);
|
|
1262
|
+
};
|
|
1263
|
+
// src/services/panzoom/resetPanzoom.ts
|
|
1264
|
+
const resetPanzoom = (context, callOptions) => {
|
|
1265
|
+
const options = getPanzoomCallOptions(context, {
|
|
1266
|
+
animate: true,
|
|
1267
|
+
force: true,
|
|
1268
|
+
...callOptions
|
|
1269
|
+
});
|
|
1270
|
+
const { element, parent, state } = context;
|
|
1271
|
+
const measure = getPanzoomMeasure(element, parent, state);
|
|
1272
|
+
writePanzoomState(context, getPanzoomStartState(state, measure, options), options);
|
|
1273
|
+
const detail = getPanzoomEventDetail(context);
|
|
1274
|
+
dispatchPanzoomChange(context, "panzoomreset", detail, options);
|
|
1275
|
+
reanchorPanzoomDrag(context);
|
|
1276
|
+
return detail;
|
|
1277
|
+
};
|
|
1278
|
+
// src/services/panzoom/getPanzoomStepScale.ts
|
|
1279
|
+
const getPanzoomStepScale = (scale, direction, step = PANZOOM_DEFAULT_STEP) => {
|
|
1280
|
+
const exponent = direction === "in" ? step : -step;
|
|
1281
|
+
return scale * Math.exp(exponent);
|
|
1282
|
+
};
|
|
1283
|
+
// src/services/panzoom/zoomPanzoomStep.ts
|
|
1284
|
+
const zoomPanzoomStep = (context, direction, zoomOptions) => zoomPanzoom(context, getPanzoomStepScale(context.state.scale, direction, context.options.step), {
|
|
1285
|
+
animate: true,
|
|
1286
|
+
...zoomOptions
|
|
1287
|
+
});
|
|
1288
|
+
// src/services/panzoom/createPanzoom.ts
|
|
1289
|
+
const createPanzoom = (element, options = {}) => {
|
|
1290
|
+
if (element.nodeType !== Node.ELEMENT_NODE) throw new InvalidOperationError("Create", createPanzoom.name, "the element is not an Element");
|
|
1291
|
+
if (!element.isConnected) throw new InvalidOperationError("Create", createPanzoom.name, "the element is not attached to a document");
|
|
1292
|
+
const parent = getPanzoomParent(element);
|
|
1293
|
+
if (!parent) throw new InvalidOperationError("Create", createPanzoom.name, "the element has no parent to contain it");
|
|
1294
|
+
const context = {
|
|
1295
|
+
element,
|
|
1296
|
+
isClickSuppressed: false,
|
|
1297
|
+
isDestroyed: false,
|
|
1298
|
+
options: {
|
|
1299
|
+
...PANZOOM_DEFAULT_OPTIONS,
|
|
1300
|
+
...options
|
|
1301
|
+
},
|
|
1302
|
+
parent,
|
|
1303
|
+
pointers: /* @__PURE__ */ new Map(),
|
|
1304
|
+
state: {
|
|
1305
|
+
scale: 1,
|
|
1306
|
+
x: 0,
|
|
1307
|
+
y: 0
|
|
1308
|
+
},
|
|
1309
|
+
styles: /* @__PURE__ */ new Map()
|
|
1310
|
+
};
|
|
1311
|
+
writePanzoomState(context, context.state, { animate: false });
|
|
1312
|
+
const start = getPanzoomStartState(context.state, getPanzoomMeasure(element, parent, context.state), context.options);
|
|
1313
|
+
writePanzoomState(context, start, { animate: false });
|
|
1314
|
+
writePanzoomStyle(context, element, "transform-origin", PANZOOM_TRANSFORM_ORIGIN);
|
|
1315
|
+
applyPanzoomStyles(context);
|
|
1316
|
+
let controller;
|
|
1317
|
+
const bind = () => {
|
|
1318
|
+
if (controller || context.isDestroyed) return;
|
|
1319
|
+
controller = new AbortController();
|
|
1320
|
+
bindPanzoom(context, controller.signal);
|
|
1321
|
+
};
|
|
1322
|
+
const destroy = () => {
|
|
1323
|
+
context.isDestroyed = true;
|
|
1324
|
+
controller?.abort();
|
|
1325
|
+
controller = void 0;
|
|
1326
|
+
context.drag = void 0;
|
|
1327
|
+
context.pinch = void 0;
|
|
1328
|
+
context.pointers.clear();
|
|
1329
|
+
restorePanzoomStyles(context);
|
|
1330
|
+
};
|
|
1331
|
+
const panzoom = {
|
|
1332
|
+
bind,
|
|
1333
|
+
destroy,
|
|
1334
|
+
fit: (fitOptions = {}) => fitPanzoom(context, fitOptions),
|
|
1335
|
+
getOptions: () => ({ ...context.options }),
|
|
1336
|
+
getPan: () => ({
|
|
1337
|
+
x: context.state.x,
|
|
1338
|
+
y: context.state.y
|
|
1339
|
+
}),
|
|
1340
|
+
getScale: () => context.state.scale,
|
|
1341
|
+
pan: (x, y, panOptions = {}) => panPanzoom(context, {
|
|
1342
|
+
x,
|
|
1343
|
+
y
|
|
1344
|
+
}, panOptions),
|
|
1345
|
+
reset: (resetOptions = {}) => resetPanzoom(context, resetOptions),
|
|
1346
|
+
resetStyle: () => {
|
|
1347
|
+
restorePanzoomStyles(context, [
|
|
1348
|
+
"cursor",
|
|
1349
|
+
"overflow",
|
|
1350
|
+
"touch-action",
|
|
1351
|
+
"user-select"
|
|
1352
|
+
]);
|
|
1353
|
+
},
|
|
1354
|
+
setOptions: (newOptions = {}) => {
|
|
1355
|
+
const previousTarget = getPanzoomTarget(context);
|
|
1356
|
+
context.options = {
|
|
1357
|
+
...context.options,
|
|
1358
|
+
...newOptions
|
|
1359
|
+
};
|
|
1360
|
+
if (controller && getPanzoomTarget(context) !== previousTarget) {
|
|
1361
|
+
controller.abort();
|
|
1362
|
+
controller = void 0;
|
|
1363
|
+
restorePanzoomStyles(context, ["cursor"]);
|
|
1364
|
+
bind();
|
|
1365
|
+
}
|
|
1366
|
+
applyPanzoomStyles(context);
|
|
1367
|
+
},
|
|
1368
|
+
zoom: (scale, zoomOptions = {}) => zoomPanzoom(context, scale, zoomOptions),
|
|
1369
|
+
zoomIn: (zoomOptions = {}) => zoomPanzoomStep(context, "in", zoomOptions),
|
|
1370
|
+
zoomOut: (zoomOptions = {}) => zoomPanzoomStep(context, "out", zoomOptions),
|
|
1371
|
+
zoomToPoint: (scale, point, zoomOptions, originalEvent) => zoomPanzoom(context, scale, {
|
|
1372
|
+
...zoomOptions,
|
|
1373
|
+
focal: {
|
|
1374
|
+
x: point.clientX,
|
|
1375
|
+
y: point.clientY
|
|
1376
|
+
}
|
|
1377
|
+
}, originalEvent),
|
|
1378
|
+
zoomWithWheel: (event, zoomOptions = {}) => {
|
|
1379
|
+
const callOptions = getPanzoomCallOptions(context, zoomOptions);
|
|
1380
|
+
if (!checkIsZoomRefused(callOptions)) event.preventDefault();
|
|
1381
|
+
return zoomPanzoom(context, getPanzoomWheelScale(context.state.scale, event, context.options.step), {
|
|
1382
|
+
...zoomOptions,
|
|
1383
|
+
animate: false,
|
|
1384
|
+
focal: {
|
|
1385
|
+
x: event.clientX,
|
|
1386
|
+
y: event.clientY
|
|
1387
|
+
}
|
|
1388
|
+
}, event);
|
|
1389
|
+
}
|
|
1390
|
+
};
|
|
1391
|
+
if (!context.options.noBind) bind();
|
|
1392
|
+
return panzoom;
|
|
1393
|
+
};
|
|
704
1394
|
// src/services/prettier/css.ts
|
|
705
1395
|
const css = String.raw;
|
|
706
1396
|
// src/services/prettier/html.ts
|
|
@@ -1177,10 +1867,6 @@ const checkIsUnsafeUrlCharacter = (character) => {
|
|
|
1177
1867
|
const codePoint = character.codePointAt(0) ?? 0;
|
|
1178
1868
|
return checkIsWhitespaceCharacter(character) || codePoint < FIRST_PRINTABLE_CODE_POINT || codePoint >= DELETE_CODE_POINT && codePoint <= LAST_C1_CONTROL_CODE_POINT || character === GRAVE_ACCENT;
|
|
1179
1869
|
};
|
|
1180
|
-
// src/util/array/takeOne.ts
|
|
1181
|
-
const takeOne = (values, index = 0) => {
|
|
1182
|
-
return values[index];
|
|
1183
|
-
};
|
|
1184
1870
|
// src/services/sanitizeHtml/checkIsAllowedUrl.ts
|
|
1185
1871
|
const PATH_DELIMITER_REGEX = /[/?#]/u;
|
|
1186
1872
|
const NON_SCHEME_CHARACTERS_REGEX = /[^a-z\d+.-]/giu;
|
|
@@ -1193,6 +1879,17 @@ const checkIsAllowedUrl = (url, allowedSchemes) => {
|
|
|
1193
1879
|
const scheme = beforePath.slice(0, separatorIndex).replaceAll(NON_SCHEME_CHARACTERS_REGEX, "").toLowerCase();
|
|
1194
1880
|
return allowedSchemes.includes(scheme);
|
|
1195
1881
|
};
|
|
1882
|
+
// src/services/sanitizeHtml/getTagPolicy.ts
|
|
1883
|
+
const getTagPolicy = (tagPolicies, tagName) => Object.hasOwn(tagPolicies, tagName) ? tagPolicies[tagName] : void 0;
|
|
1884
|
+
// src/services/sanitizeHtml/checkIsSourceAllowed.ts
|
|
1885
|
+
const checkIsSourceAllowed = (element, allowedSources) => {
|
|
1886
|
+
const sourceRules = getTagPolicy(allowedSources, element.tagName);
|
|
1887
|
+
if (!sourceRules) return true;
|
|
1888
|
+
return Object.entries(sourceRules).every(([name, patterns]) => {
|
|
1889
|
+
const attribute = element.attrs.find((attr) => attr.name === name);
|
|
1890
|
+
return attribute !== void 0 && patterns.some((pattern) => pattern.test(attribute.value));
|
|
1891
|
+
});
|
|
1892
|
+
};
|
|
1196
1893
|
// src/services/sanitizeHtml/constants.ts
|
|
1197
1894
|
const HTML_NAMESPACE = html$1.NS.HTML;
|
|
1198
1895
|
const DEFAULT_ALLOWED_TAGS = [
|
|
@@ -1327,7 +2024,7 @@ const MAX_NESTING_DEPTH = 256;
|
|
|
1327
2024
|
const SRCSET_DESCRIPTOR_REGEX = /^(?:\d+w|\d*\.?\d+x|\d+h)$/u;
|
|
1328
2025
|
const ESCAPED_TEXT_CHARACTERS_REGEX = /[&<>]/gu;
|
|
1329
2026
|
const ESCAPED_ATTRIBUTE_CHARACTERS_REGEX = /[&"<>]/gu;
|
|
1330
|
-
const SANITIZER_ADVISORY_WATCH_SINCE = "2026-10-
|
|
2027
|
+
const SANITIZER_ADVISORY_WATCH_SINCE = "2026-10-23";
|
|
1331
2028
|
// src/services/sanitizeHtml/getChildNodes.ts
|
|
1332
2029
|
const getChildNodes = (element) => "content" in element ? element.content.childNodes : element.childNodes;
|
|
1333
2030
|
// src/services/sanitizeHtml/collectText.ts
|
|
@@ -1420,7 +2117,6 @@ const filterStyle = (value, rules) => {
|
|
|
1420
2117
|
return Array.from(declarations, ([property, { important, propertyValue }]) => `${property}${PROPERTY_SEPARATOR}${propertyValue}${important ? IMPORTANT_SUFFIX : ""}`).join(DECLARATION_SEPARATOR);
|
|
1421
2118
|
};
|
|
1422
2119
|
// src/services/sanitizeHtml/filterAttributes.ts
|
|
1423
|
-
const getTagPolicy = (tagPolicies, tagName) => Object.hasOwn(tagPolicies, tagName) ? tagPolicies[tagName] : void 0;
|
|
1424
2120
|
const checkIsMetaRefresh = (tagName, attributes) => tagName === "meta" && attributes["http-equiv"]?.trim().toLowerCase() === "refresh";
|
|
1425
2121
|
const filterAttributes = (element, policy) => {
|
|
1426
2122
|
const { tagName } = element;
|
|
@@ -1451,7 +2147,7 @@ const renderNode = (node, policy, depth) => {
|
|
|
1451
2147
|
if (!("tagName" in node) || depth > 256) return "";
|
|
1452
2148
|
const element = node;
|
|
1453
2149
|
const children = getChildNodes(element).map((child) => renderNode(child, policy, depth + 1)).join("");
|
|
1454
|
-
if (!(element.namespaceURI === HTML_NAMESPACE && !NON_TEXT_TAGS.includes(element.tagName) && policy.allowedTags.includes(element.tagName))) return NON_TEXT_TAGS.includes(element.tagName) ? "" : children;
|
|
2150
|
+
if (!(element.namespaceURI === HTML_NAMESPACE && !NON_TEXT_TAGS.includes(element.tagName) && policy.allowedTags.includes(element.tagName) && checkIsSourceAllowed(element, policy.allowedSources))) return NON_TEXT_TAGS.includes(element.tagName) ? "" : children;
|
|
1455
2151
|
const attributes = Object.entries(filterAttributes(element, policy)).map(([name, value]) => ` ${name}="${escapeAttribute(value)}"`).join("");
|
|
1456
2152
|
const opening = `<${element.tagName}${attributes}>`;
|
|
1457
2153
|
return VOID_TAGS.includes(element.tagName) ? opening : `${opening}${children}</${element.tagName}>`;
|
|
@@ -1502,6 +2198,7 @@ const sanitizeHtml = (html, options) => filterHtml(html, {
|
|
|
1502
2198
|
},
|
|
1503
2199
|
allowedClasses: options?.allowedClasses ?? {},
|
|
1504
2200
|
allowedSchemes: DEFAULT_ALLOWED_SCHEMES,
|
|
2201
|
+
allowedSources: options?.allowedSources ?? {},
|
|
1505
2202
|
allowedStyles: {
|
|
1506
2203
|
...options?.allowedStyles,
|
|
1507
2204
|
...TABLE_ALLOWED_STYLES
|
|
@@ -1521,47 +2218,54 @@ const COLOR_REGEXES = [
|
|
|
1521
2218
|
/^rgba?\(\d{1,3},\s*\d{1,3},\s*\d{1,3}(?:,\s*[\d.]+)?\)$/u,
|
|
1522
2219
|
/^[a-z]+$/iu
|
|
1523
2220
|
];
|
|
1524
|
-
const
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
"type"
|
|
1530
|
-
],
|
|
1531
|
-
li: ["data-checked", "data-type"],
|
|
1532
|
-
span: [
|
|
1533
|
-
CUSTOM_EMOJI_ID_ATTRIBUTE,
|
|
1534
|
-
CUSTOM_EMOJI_NAME_ATTRIBUTE,
|
|
1535
|
-
MENTION_ID_ATTRIBUTE,
|
|
1536
|
-
MENTION_ITEM_TYPE_ATTRIBUTE,
|
|
1537
|
-
MENTION_LABEL_ATTRIBUTE,
|
|
1538
|
-
MENTION_TYPE_ATTRIBUTE,
|
|
1539
|
-
SPOILER_ATTRIBUTE,
|
|
1540
|
-
"style"
|
|
1541
|
-
],
|
|
1542
|
-
ul: ["data-type"]
|
|
1543
|
-
},
|
|
1544
|
-
allowedClasses: {
|
|
1545
|
-
code: ["language-*"],
|
|
1546
|
-
pre: ["language-*"],
|
|
1547
|
-
span: ["hljs*"]
|
|
1548
|
-
},
|
|
1549
|
-
allowedStyles: { span: {
|
|
1550
|
-
"background-color": COLOR_REGEXES,
|
|
1551
|
-
"border-radius": [/^[\d.]+(?<unit>px|em|rem|%)$/u],
|
|
1552
|
-
color: COLOR_REGEXES
|
|
1553
|
-
} },
|
|
1554
|
-
allowedTags: [
|
|
1555
|
-
...DEFAULT_ALLOWED_TAGS,
|
|
1556
|
-
"input",
|
|
1557
|
-
"label"
|
|
2221
|
+
const KIT_ALLOWED_ATTRIBUTES = {
|
|
2222
|
+
input: [
|
|
2223
|
+
"checked",
|
|
2224
|
+
"disabled",
|
|
2225
|
+
"type"
|
|
1558
2226
|
],
|
|
1559
|
-
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
2227
|
+
li: ["data-checked", "data-type"],
|
|
2228
|
+
span: [
|
|
2229
|
+
CUSTOM_EMOJI_ID_ATTRIBUTE,
|
|
2230
|
+
CUSTOM_EMOJI_NAME_ATTRIBUTE,
|
|
2231
|
+
MENTION_ID_ATTRIBUTE,
|
|
2232
|
+
MENTION_ITEM_TYPE_ATTRIBUTE,
|
|
2233
|
+
MENTION_LABEL_ATTRIBUTE,
|
|
2234
|
+
MENTION_TYPE_ATTRIBUTE,
|
|
2235
|
+
SPOILER_ATTRIBUTE,
|
|
2236
|
+
"style"
|
|
2237
|
+
],
|
|
2238
|
+
ul: ["data-type"]
|
|
2239
|
+
};
|
|
2240
|
+
const sanitizeTextHtml = (html, allowance = {}) => {
|
|
2241
|
+
const allowedAttributes = { ...KIT_ALLOWED_ATTRIBUTES };
|
|
2242
|
+
for (const [tagName, attributes] of Object.entries(allowance.allowedAttributes ?? {})) allowedAttributes[tagName] = [.../* @__PURE__ */ new Set([...allowedAttributes[tagName] ?? [], ...attributes])];
|
|
2243
|
+
return sanitizeHtml(html, {
|
|
2244
|
+
allowedAttributes,
|
|
2245
|
+
allowedClasses: {
|
|
2246
|
+
code: ["language-*"],
|
|
2247
|
+
pre: ["language-*"],
|
|
2248
|
+
span: ["hljs*"]
|
|
2249
|
+
},
|
|
2250
|
+
allowedSources: allowance.allowedSources,
|
|
2251
|
+
allowedStyles: { span: {
|
|
2252
|
+
"background-color": COLOR_REGEXES,
|
|
2253
|
+
"border-radius": [/^[\d.]+(?<unit>px|em|rem|%)$/u],
|
|
2254
|
+
color: COLOR_REGEXES
|
|
2255
|
+
} },
|
|
2256
|
+
allowedTags: [
|
|
2257
|
+
...DEFAULT_ALLOWED_TAGS,
|
|
2258
|
+
"input",
|
|
2259
|
+
"label",
|
|
2260
|
+
...allowance.allowedTags ?? []
|
|
2261
|
+
],
|
|
2262
|
+
transformAttributes: { input: ({ checked }) => ({
|
|
2263
|
+
...checked === void 0 ? {} : { checked },
|
|
2264
|
+
disabled: "",
|
|
2265
|
+
type: "checkbox"
|
|
2266
|
+
}) }
|
|
2267
|
+
});
|
|
2268
|
+
};
|
|
1565
2269
|
// src/services/shared/applyItemMetadataMixin.ts
|
|
1566
2270
|
const applyItemMetadataMixin = (Base) => class ItemWithMetadata extends Base {
|
|
1567
2271
|
createdAt = /* @__PURE__ */ new Date();
|
|
@@ -1572,6 +2276,8 @@ const applyItemMetadataMixin = (Base) => class ItemWithMetadata extends Base {
|
|
|
1572
2276
|
const normalizeString = (value) => value?.trim() ?? "";
|
|
1573
2277
|
// src/services/zod/createNormalizedStringSchema.ts
|
|
1574
2278
|
const createNormalizedStringSchema = (maxLength, schema = z.string()) => schema.transform(normalizeString).pipe(z.string().max(maxLength));
|
|
2279
|
+
// src/services/zod/createRecordSchema.ts
|
|
2280
|
+
const createRecordSchema = (keySchema, valueSchema, maxEntries) => z.record(keySchema, valueSchema).refine((record) => Object.keys(record).length <= maxEntries, { error: `Record must have at most ${maxEntries} entries` }).meta({ maxProperties: maxEntries });
|
|
1575
2281
|
// src/util/id/constants.ts
|
|
1576
2282
|
const ID_SEPARATOR = "|";
|
|
1577
2283
|
// src/services/zod/createUniqueArraySchema.ts
|
|
@@ -1714,26 +2420,8 @@ const downloadFile = (filename, blobPart, type) => {
|
|
|
1714
2420
|
};
|
|
1715
2421
|
// src/util/environment/checkIsServer.ts
|
|
1716
2422
|
const checkIsServer = () => typeof window === "undefined";
|
|
1717
|
-
// src/util/function/getSynchronizedFunction.ts
|
|
1718
|
-
const pendingPromises = /* @__PURE__ */ new Set();
|
|
1719
|
-
const getSynchronizedFunction = (asyncFunction) => (...args) => {
|
|
1720
|
-
const promise = asyncFunction(...args).finally(() => {
|
|
1721
|
-
pendingPromises.delete(promise);
|
|
1722
|
-
});
|
|
1723
|
-
pendingPromises.add(promise);
|
|
1724
|
-
};
|
|
1725
|
-
const waitForSynchronizedFunctions = async () => {
|
|
1726
|
-
await Promise.allSettled(pendingPromises);
|
|
1727
|
-
};
|
|
1728
2423
|
// src/util/id/uuid/constants.ts
|
|
1729
2424
|
const UUIDV4_REGEX = /^[0-9A-F]{8}-[0-9A-F]{4}-[4][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/iu;
|
|
1730
|
-
// src/util/map/getOrCreate.ts
|
|
1731
|
-
const getOrCreate = (map, key, create) => {
|
|
1732
|
-
if (map.has(key)) return map.get(key);
|
|
1733
|
-
const value = create();
|
|
1734
|
-
map.set(key, value);
|
|
1735
|
-
return value;
|
|
1736
|
-
};
|
|
1737
2425
|
// src/util/object/clonePlainDeep.ts
|
|
1738
2426
|
const clone = (data, copies) => {
|
|
1739
2427
|
if (!Array.isArray(data) && !checkIsPlainObject(data)) return data;
|
|
@@ -1751,8 +2439,6 @@ const clone = (data, copies) => {
|
|
|
1751
2439
|
}
|
|
1752
2440
|
};
|
|
1753
2441
|
const clonePlainDeep = (data) => clone(data, /* @__PURE__ */ new WeakMap());
|
|
1754
|
-
// src/util/object/getPropertyNames.ts
|
|
1755
|
-
const getPropertyNames = () => new Proxy({}, { get: (_target, property) => property });
|
|
1756
2442
|
// src/util/object/jsonDateParse.ts
|
|
1757
2443
|
const ISO_DATE_REGEX = /^(?<year>\d{4})-(?<month>\d{2})-(?<day>\d{2})T(?<hours>\d{2}):(?<minutes>\d{2}):(?<seconds>\d{2}(?:\.{0,1}\d*))(?:Z|(?<sign>\+|-)(?<offset>[\d|:]*))?$/u;
|
|
1758
2444
|
const MS_AJAX_DATE_REGEX = /^\/Date\((?<timestamp>-?\d+(?:[-+]\d+)?)\)[/\\]$/u;
|
|
@@ -1789,17 +2475,22 @@ const createEvictingPromiseCache = (getKey, load) => {
|
|
|
1789
2475
|
});
|
|
1790
2476
|
};
|
|
1791
2477
|
};
|
|
2478
|
+
// src/util/promise/rethrowRejections.ts
|
|
2479
|
+
const rethrowRejections = (reasons) => {
|
|
2480
|
+
if (reasons.length === 1) throw takeOne(reasons);
|
|
2481
|
+
else if (reasons.length > 1) throw new AggregateError(reasons, toAppError(takeOne(reasons)).message);
|
|
2482
|
+
};
|
|
1792
2483
|
// src/util/promise/settleAll.ts
|
|
1793
2484
|
const settleAll = async (tasks, concurrencyLimit = tasks.length) => {
|
|
1794
2485
|
if (tasks.length === 0) return [];
|
|
2486
|
+
if (!Number.isInteger(concurrencyLimit) || concurrencyLimit < 1) throw new InvalidOperationError("Read", settleAll.name, "the concurrency limit is not a whole number of at least one");
|
|
1795
2487
|
const values = [];
|
|
1796
2488
|
for (const tasksChunk of chunk(tasks, concurrencyLimit)) {
|
|
1797
2489
|
const results = await Promise.allSettled(tasksChunk.map((task) => Promise.try(task)));
|
|
1798
2490
|
const reasons = [];
|
|
1799
2491
|
for (const result of results) if (result.status === "rejected") reasons.push(result.reason);
|
|
1800
2492
|
else values.push(result.value);
|
|
1801
|
-
|
|
1802
|
-
else if (reasons.length > 1) throw new AggregateError(reasons, toAppError(takeOne(reasons)).message);
|
|
2493
|
+
rethrowRejections(reasons);
|
|
1803
2494
|
}
|
|
1804
2495
|
return values;
|
|
1805
2496
|
};
|
|
@@ -2015,6 +2706,8 @@ const EncodedSubDelimiterMap = {
|
|
|
2015
2706
|
const encodeUrlSubDelimiters = (value) => Object.entries(EncodedSubDelimiterMap).reduce((encoded, [subDelimiter, encodedSubDelimiter]) => encoded.replaceAll(subDelimiter, encodedSubDelimiter), value);
|
|
2016
2707
|
// src/util/text/getDecodedUriComponent.ts
|
|
2017
2708
|
const getDecodedUriComponent = (value, fallback) => getResult(() => decodeURIComponent(value)).unwrapOr(fallback);
|
|
2709
|
+
// src/util/text/padWithZeros.ts
|
|
2710
|
+
const padWithZeros = (value, length) => String(value).padStart(length, "0");
|
|
2018
2711
|
// src/util/text/streamToText.ts
|
|
2019
2712
|
const streamToText = async (readable) => {
|
|
2020
2713
|
readable.setEncoding("utf8");
|
|
@@ -2035,33 +2728,33 @@ const truncate = (string, length) => {
|
|
|
2035
2728
|
const uncapitalize = (string) => `${string.charAt(0).toLowerCase()}${string.slice(1)}`;
|
|
2036
2729
|
// src/util/time/constants.ts
|
|
2037
2730
|
const MILLISECONDS_PER_SECOND = 1e3;
|
|
2038
|
-
// src/util/time/
|
|
2039
|
-
const
|
|
2040
|
-
if (checkIsServer()) return process.hrtime(previousHrTime);
|
|
2041
|
-
const clocktime = performance.now() * .001;
|
|
2042
|
-
let seconds = Math.floor(clocktime);
|
|
2043
|
-
let nanoseconds = Math.floor(clocktime % 1 * 1e9);
|
|
2044
|
-
if (previousHrTime) {
|
|
2045
|
-
seconds -= previousHrTime[0];
|
|
2046
|
-
nanoseconds -= previousHrTime[1];
|
|
2047
|
-
if (nanoseconds < 0) {
|
|
2048
|
-
seconds--;
|
|
2049
|
-
nanoseconds += 1e9;
|
|
2050
|
-
}
|
|
2051
|
-
}
|
|
2052
|
-
return [seconds, nanoseconds];
|
|
2053
|
-
};
|
|
2054
|
-
// src/util/time/now.ts
|
|
2055
|
-
const loadNanoseconds = hrtime();
|
|
2056
|
-
const loadMilliseconds = Date.now();
|
|
2057
|
-
const now = () => {
|
|
2058
|
-
const [seconds, nanoseconds] = hrtime(loadNanoseconds);
|
|
2059
|
-
return (BigInt(loadMilliseconds) * 10n ** 6n + (BigInt(seconds) * 10n ** 9n + BigInt(nanoseconds))).toString();
|
|
2060
|
-
};
|
|
2731
|
+
// src/util/time/getExponentialBackoffDelayMs.ts
|
|
2732
|
+
const getExponentialBackoffDelayMs = (attempt, baseDelayMs, maxDelayMs) => Math.min(baseDelayMs * 2 ** attempt, maxDelayMs);
|
|
2061
2733
|
// src/util/time/sleep.ts
|
|
2062
2734
|
const sleep = (durationMs) => new Promise((resolve) => {
|
|
2063
2735
|
setTimeout(() => {
|
|
2064
2736
|
resolve();
|
|
2065
2737
|
}, durationMs);
|
|
2066
2738
|
});
|
|
2067
|
-
|
|
2739
|
+
// src/util/time/createExponentialBackoff.ts
|
|
2740
|
+
const createExponentialBackoff = (baseDelayMs, maxDelayMs) => {
|
|
2741
|
+
let failureCount = 0;
|
|
2742
|
+
return async (operation) => {
|
|
2743
|
+
if (failureCount > 0) await sleep(getExponentialBackoffDelayMs(failureCount - 1, baseDelayMs, maxDelayMs));
|
|
2744
|
+
return getResultAsync(operation).match((value) => {
|
|
2745
|
+
failureCount = 0;
|
|
2746
|
+
return value;
|
|
2747
|
+
}, (error) => {
|
|
2748
|
+
failureCount += 1;
|
|
2749
|
+
throw error;
|
|
2750
|
+
});
|
|
2751
|
+
};
|
|
2752
|
+
};
|
|
2753
|
+
// src/util/time/now.ts
|
|
2754
|
+
let latestNanoseconds = 0n;
|
|
2755
|
+
const now = () => {
|
|
2756
|
+
const nanoseconds = BigInt(Math.round(performance.timeOrigin * 1e3)) * 1000n + BigInt(Math.round(performance.now() * 1e6));
|
|
2757
|
+
latestNanoseconds = nanoseconds > latestNanoseconds ? nanoseconds : latestNanoseconds + 1n;
|
|
2758
|
+
return latestNanoseconds.toString();
|
|
2759
|
+
};
|
|
2760
|
+
export { ALL_SPECIAL_VALUES, APPEND_SEGMENT, CHARSET_PARAMETER_REGEX, CUSTOM_EMOJI_ID_ATTRIBUTE, CUSTOM_EMOJI_NAME_ATTRIBUTE, DEFAULT_ALLOWED_ATTRIBUTES, DEFAULT_ALLOWED_SCHEMES, DEFAULT_ALLOWED_TAGS, DEFAULT_COMPRESSION_LEVEL, DEFAULT_FACET_SCORE, DEFAULT_LINK_ATTRIBUTES, DEFAULT_SOURCE_SCORE, DEFAULT_TEXT_CHARSET, DEFAULT_TYPE_SCORE, ESCAPED_ATTRIBUTE_CHARACTERS_REGEX, ESCAPED_TEXT_CHARACTERS_REGEX, FacetScoreMap, ForbiddenError, GIBIBYTE, HTML_NAMESPACE, ID_SEPARATOR, IMPORTANT_REGEX, InvalidOperationError, ItemMetadata, ItemMetadataPropertyNames, JSON_POINTER_REGEX, JsonPatchOperationType, KIBIBYTE, MAX_NESTING_DEPTH, MAX_READ_LIMIT, MAX_WINDOW_LOG, MEDIA_TYPE_REGEX, MENTION_EVERYONE_ID, MENTION_HERE_ID, MENTION_ID_ATTRIBUTE, MENTION_ITEM_TYPE_ATTRIBUTE, MENTION_LABEL_ATTRIBUTE, MENTION_SELECTOR, MENTION_TYPE, MENTION_TYPE_ATTRIBUTE, MILLISECONDS_PER_SECOND, MIN_WINDOW_LOG, MentionType, NON_TEXT_TAGS, NotFoundError, NotInitializedError, ObjectMethod, Operation, PANZOOM_DEFAULT_CURSOR, PANZOOM_DEFAULT_DURATION, PANZOOM_DEFAULT_EASING, PANZOOM_DEFAULT_EXCLUDE_CLASS, PANZOOM_DEFAULT_MAX_SCALE, PANZOOM_DEFAULT_MIN_SCALE, PANZOOM_DEFAULT_OPTIONS, PANZOOM_DEFAULT_OVERFLOW, PANZOOM_DEFAULT_PAN_THRESHOLD, PANZOOM_DEFAULT_START_PAN, PANZOOM_DEFAULT_START_SCALE, PANZOOM_DEFAULT_STEP, PANZOOM_DEFAULT_TOUCH_ACTION, PANZOOM_PIXELS_PER_LINE, PANZOOM_PRIMARY_BUTTON, PANZOOM_SVG_NAMESPACE, PANZOOM_TRANSFORM_ORIGIN, PANZOOM_WHEEL_NOTCH_PIXELS, PANZOOM_WHEEL_STEP_DIVISOR, PATH_SEPARATOR_REGEX, PanzoomContain, PanzoomDeltaMode, PanzoomEventName, PanzoomZoomDirection, RoutePath, SANITIZER_ADVISORY_WATCH_SINCE, SITE_NAME, SPOILER_ATTRIBUTE, SPOILER_SELECTOR, SRCSET_ATTRIBUTE, SRCSET_DESCRIPTOR_REGEX, Serializable, SourceScoreMap, TEXT_MEDIA_TYPE_REGEX, TypeScoreMap, TypedEventEmitter, URL_ATTRIBUTES, UUIDV4_REGEX, VOID_TAGS, WordFilteredError, addJsonValue, applyItemMetadataMixin, applyPanzoomStyles, applyPatch, applyPatches, bindPanzoom, capitalize, charset, checkContainsProfanity, checkIsAllowedUrl, checkIsContainableLength, checkIsCustomMethod, checkIsDeepEqual, checkIsNestedControl, checkIsNestedInteraction, checkIsOnlyReactor, checkIsPanzoomElement, checkIsPanzoomExcluded, checkIsPlainObject, checkIsSameBytes, checkIsSameValueZero, checkIsServer, checkIsSourceAllowed, checkIsUnsafeUrlCharacter, checkIsWhitespaceCharacter, checkIsZoomRefused, chunk, chunkBySerializedSize, clonePlainDeep, collectText, constrainPanzoomAxis, constrainPanzoomPan, constrainPanzoomScale, contentType, createEvictingPromiseCache, createExponentialBackoff, createHistory, createItemEntityTypeSchema, createNormalizedStringSchema, createPanzoom, createRecordSchema, createUniqueArraySchema, css, dedent, dispatchPanzoomChange, dispatchPanzoomEvent, downloadFile, downloadUrl, encodeUrlSubDelimiters, endPanzoomGesture, englishProfaneWords, escapeAttribute, escapeCharacters, escapeText, exhaustiveGuard, extension, filterAttributes, filterClasses, filterHtml, filterSrcset, filterStyle, fitPanzoom, getChildNodes, getDecodedUriComponent, getEndOfDay, getEnumerableKeys, getExponentialBackoffDelayMs, getExtensionMimeTypeMap, getMediaType, getMentions, getMimeScore, getMimeTypeEntryMap, getOrCreate, getPanzoomCallOptions, getPanzoomCentredPan, getPanzoomCoverScale, getPanzoomDrag, getPanzoomEventDetail, getPanzoomFitScale, getPanzoomFocalPan, getPanzoomMeasure, getPanzoomParent, getPanzoomPinchFrame, getPanzoomPinchScale, getPanzoomStartScale, getPanzoomStartState, getPanzoomStepScale, getPanzoomTarget, getPanzoomWheelScale, getPanzoomZoomedState, getPropertyNames, getRawData, getRequestError, getResult, getResultAsync, getSynchronizedFunction, getTagPolicy, getTransactionDone, getTransactionObjectStore, getUpdatedUserIds, getWindowLog, getZonedDateTime, html, jsonDateParse, lookup, matchesClassPattern, mergeObjectsStrict, movePanzoomDrag, movePanzoomGesture, movePanzoomPinch, noop, normalizeString, now, omitDeep, openDatabase, padWithZeros, panPanzoom, parseArrayIndex, parseJsonPointer, pushHistory, readJsonValue, reanchorPanzoomDrag, redoHistory, removeJsonValue, renderNode, reportFinalizerError, requestToPromise, resetPanzoom, restorePanzoomStyles, rethrowRejections, sanitizeHtml, sanitizeTextHtml, settleAll, sleep, startPanzoomGesture, streamToText, takeOne, takeRandom, toAppError, toJsonPointer, toKebabCase, toRawDeep, truncate, uncapitalize, undoHistory, updateJsonValue, waitForSynchronizedFunctions, withFinalizer, withFinalizerAsync, wrapDatabase, wrapIndex, wrapObjectStore, wrapTransaction, wrapUpgradeDatabase, wrapUpgradeTransaction, writePanzoomState, writePanzoomStyle, zoomPanzoom, zoomPanzoomStep };
|