jodit 4.17.1 → 4.17.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.
Files changed (71) hide show
  1. package/.nvmrc +1 -0
  2. package/CHANGELOG.md +12 -0
  3. package/es2015/jodit.css +1 -1
  4. package/es2015/jodit.fat.min.js +4 -4
  5. package/es2015/jodit.js +182 -7
  6. package/es2015/jodit.min.js +4 -4
  7. package/es2015/plugins/debug/debug.css +1 -1
  8. package/es2015/plugins/debug/debug.js +1 -1
  9. package/es2015/plugins/debug/debug.min.js +1 -1
  10. package/es2015/plugins/speech-recognize/speech-recognize.css +1 -1
  11. package/es2015/plugins/speech-recognize/speech-recognize.js +1 -1
  12. package/es2015/plugins/speech-recognize/speech-recognize.min.js +1 -1
  13. package/es2018/jodit.fat.min.js +4 -4
  14. package/es2018/jodit.min.js +4 -4
  15. package/es2018/plugins/debug/debug.min.js +1 -1
  16. package/es2018/plugins/speech-recognize/speech-recognize.min.js +1 -1
  17. package/es2021/jodit.css +1 -1
  18. package/es2021/jodit.fat.min.js +6 -6
  19. package/es2021/jodit.js +182 -7
  20. package/es2021/jodit.min.js +6 -6
  21. package/es2021/plugins/debug/debug.css +1 -1
  22. package/es2021/plugins/debug/debug.js +1 -1
  23. package/es2021/plugins/debug/debug.min.js +1 -1
  24. package/es2021/plugins/speech-recognize/speech-recognize.css +1 -1
  25. package/es2021/plugins/speech-recognize/speech-recognize.js +1 -1
  26. package/es2021/plugins/speech-recognize/speech-recognize.min.js +1 -1
  27. package/es2021.en/jodit.css +1 -1
  28. package/es2021.en/jodit.fat.min.js +24 -24
  29. package/es2021.en/jodit.js +182 -7
  30. package/es2021.en/jodit.min.js +6 -6
  31. package/es2021.en/plugins/debug/debug.css +1 -1
  32. package/es2021.en/plugins/debug/debug.js +1 -1
  33. package/es2021.en/plugins/debug/debug.min.js +1 -1
  34. package/es2021.en/plugins/speech-recognize/speech-recognize.css +1 -1
  35. package/es2021.en/plugins/speech-recognize/speech-recognize.js +1 -1
  36. package/es2021.en/plugins/speech-recognize/speech-recognize.min.js +1 -1
  37. package/es5/jodit.css +2 -2
  38. package/es5/jodit.fat.min.js +2 -2
  39. package/es5/jodit.js +217 -7
  40. package/es5/jodit.min.css +2 -2
  41. package/es5/jodit.min.js +2 -2
  42. package/es5/plugins/debug/debug.css +1 -1
  43. package/es5/plugins/debug/debug.js +1 -1
  44. package/es5/plugins/debug/debug.min.js +1 -1
  45. package/es5/plugins/speech-recognize/speech-recognize.css +1 -1
  46. package/es5/plugins/speech-recognize/speech-recognize.js +1 -1
  47. package/es5/plugins/speech-recognize/speech-recognize.min.js +1 -1
  48. package/es5/polyfills.fat.min.js +1 -1
  49. package/es5/polyfills.js +1 -1
  50. package/es5/polyfills.min.js +1 -1
  51. package/esm/core/constants.js +1 -1
  52. package/esm/core/helpers/html/safe-html.js +15 -0
  53. package/esm/core/selection/helpers/composed-ranges.d.ts +21 -0
  54. package/esm/core/selection/helpers/composed-ranges.js +45 -0
  55. package/esm/core/selection/helpers/index.d.ts +1 -0
  56. package/esm/core/selection/helpers/index.js +1 -0
  57. package/esm/core/selection/selection.d.ts +23 -0
  58. package/esm/core/selection/selection.js +80 -4
  59. package/esm/jodit.js +5 -0
  60. package/esm/plugins/clean-html/clean-html.d.ts +8 -0
  61. package/esm/plugins/clean-html/clean-html.js +13 -0
  62. package/examples/build/es2015/jodit.min.css +1 -0
  63. package/examples/build/es2015/jodit.min.js +10 -0
  64. package/examples/build/es2015/plugins/debug/debug.min.js +10 -0
  65. package/examples/build/es2015/plugins/speech-recognize/speech-recognize.min.css +1 -0
  66. package/examples/build/es2015/plugins/speech-recognize/speech-recognize.min.js +10 -0
  67. package/package.json +1 -1
  68. package/types/core/selection/helpers/composed-ranges.d.ts +21 -0
  69. package/types/core/selection/helpers/index.d.ts +1 -0
  70. package/types/core/selection/selection.d.ts +23 -0
  71. package/types/plugins/clean-html/clean-html.d.ts +8 -0
@@ -1,7 +1,7 @@
1
1
  /*!
2
2
  * jodit - Jodit is an awesome and useful wysiwyg editor with filebrowser
3
3
  * Author: Chupurnov <chupurnov@gmail.com> (https://xdsoft.net/jodit/)
4
- * Version: v4.17.1
4
+ * Version: v4.17.3
5
5
  * Url: https://xdsoft.net/jodit/
6
6
  * License(s): MIT
7
7
  */
@@ -1799,7 +1799,7 @@ __webpack_require__.r(__webpack_exports__);
1799
1799
  * ```
1800
1800
  * @packageDocumentation
1801
1801
  * @module constants
1802
- */ const APP_VERSION = "4.17.1";
1802
+ */ const APP_VERSION = "4.17.3";
1803
1803
  // prettier-ignore
1804
1804
  const ES = "es2021";
1805
1805
  const IS_ES_MODERN = true;
@@ -6197,6 +6197,21 @@ function isSmuggledForeignHtml(elm) {
6197
6197
  jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_0__.Dom.safeRemove(elm);
6198
6198
  }
6199
6199
  }
6200
+ // `<noscript>` is parsed as markup in a document with scripting off (the
6201
+ // inert document the value is sanitized in) and as raw text in one with
6202
+ // scripting on (the live editor). The same serialized bytes therefore
6203
+ // describe two different trees, and markup hidden as inert text in the
6204
+ // first comes alive as elements in the second. The element has no use in
6205
+ // editor content, so it goes, together with everything it carried.
6206
+ const noscript = [];
6207
+ jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_0__.Dom.each(box, (node)=>{
6208
+ if (jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_0__.Dom.isElement(node) && node.nodeName === 'NOSCRIPT') {
6209
+ noscript.push(node);
6210
+ }
6211
+ });
6212
+ for (const elm of noscript){
6213
+ jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_0__.Dom.safeRemove(elm);
6214
+ }
6200
6215
  const removeEvents = options.removeEventAttributes ?? options.removeOnError;
6201
6216
  // Single synchronous traversal of the subtree. Besides removing event
6202
6217
  // handlers and `javascript:` links, `sanitizeHTMLElement` neutralises
@@ -10541,6 +10556,70 @@ class Response {
10541
10556
  }
10542
10557
 
10543
10558
 
10559
+ /***/ }),
10560
+
10561
+ /***/ 43134:
10562
+ /***/ (function(__unused_webpack_module, __webpack_exports__, __webpack_require__) {
10563
+
10564
+ "use strict";
10565
+ /* harmony export */ __webpack_require__.d(__webpack_exports__, {
10566
+ /* harmony export */ composedRanges: function() { return /* binding */ composedRanges; }
10567
+ /* harmony export */ });
10568
+ /* harmony import */ var jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(28686);
10569
+ /*!
10570
+ * Jodit Editor (https://xdsoft.net/jodit/)
10571
+ * Released under MIT see LICENSE.txt in the project root for license information.
10572
+ * Copyright (c) 2013-2026 Valerii Chupurnov. All rights reserved. https://xdsoft.net
10573
+ */ /**
10574
+ * @module selection
10575
+ */
10576
+ function isInside(node, shadowRoot) {
10577
+ return node === shadowRoot || shadowRoot.contains(node);
10578
+ }
10579
+ function usable(ranges, shadowRoot) {
10580
+ return Array.isArray(ranges) && ranges.length > 0 && ranges.every((range)=>isInside(range.startContainer, shadowRoot));
10581
+ }
10582
+ /**
10583
+ * Ranges of a selection that lies inside the given shadow tree.
10584
+ *
10585
+ * `window.getSelection()` stops at the shadow boundary and reports the host
10586
+ * instead of the node the caret is really in. `getComposedRanges` is the
10587
+ * standard way to ask past that boundary.
10588
+ *
10589
+ * @returns `null` when the browser has no `getComposedRanges`, or when neither
10590
+ * call shape returned ranges that point inside the shadow tree — in which case
10591
+ * there is nothing better to offer than the plain window selection.
10592
+ */ function composedRanges(selection, shadowRoot) {
10593
+ const getComposedRanges = selection.getComposedRanges;
10594
+ if (!(0,jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_0__.isFunction)(getComposedRanges)) {
10595
+ return null;
10596
+ }
10597
+ for (const args of [
10598
+ [
10599
+ {
10600
+ shadowRoots: [
10601
+ shadowRoot
10602
+ ]
10603
+ }
10604
+ ],
10605
+ [
10606
+ shadowRoot
10607
+ ]
10608
+ ]){
10609
+ let ranges;
10610
+ try {
10611
+ ranges = getComposedRanges.apply(selection, args);
10612
+ } catch {
10613
+ continue;
10614
+ }
10615
+ if (usable(ranges, shadowRoot)) {
10616
+ return ranges;
10617
+ }
10618
+ }
10619
+ return null;
10620
+ }
10621
+
10622
+
10544
10623
  /***/ }),
10545
10624
 
10546
10625
  /***/ 42259:
@@ -10548,14 +10627,16 @@ class Response {
10548
10627
 
10549
10628
  "use strict";
10550
10629
  /* harmony export */ __webpack_require__.d(__webpack_exports__, {
10630
+ /* harmony export */ composedRanges: function() { return /* reexport safe */ _composed_ranges__WEBPACK_IMPORTED_MODULE_2__.composedRanges; },
10551
10631
  /* harmony export */ cursorInTheEdgeOfString: function() { return /* binding */ cursorInTheEdgeOfString; },
10552
10632
  /* harmony export */ findCorrectCurrentNode: function() { return /* binding */ findCorrectCurrentNode; },
10553
- /* harmony export */ moveNodeInsideStart: function() { return /* reexport safe */ _move_node_inside_start__WEBPACK_IMPORTED_MODULE_2__.moveNodeInsideStart; }
10633
+ /* harmony export */ moveNodeInsideStart: function() { return /* reexport safe */ _move_node_inside_start__WEBPACK_IMPORTED_MODULE_3__.moveNodeInsideStart; }
10554
10634
  /* harmony export */ });
10555
10635
  /* harmony import */ var jodit_core_constants__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(81937);
10556
10636
  /* harmony import */ var jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(23211);
10557
- /* harmony import */ var _move_node_inside_start__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(89817);
10558
- /* harmony import */ var _move_the_node_along_the_edge_outward__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(7470);
10637
+ /* harmony import */ var _composed_ranges__WEBPACK_IMPORTED_MODULE_2__ = __webpack_require__(43134);
10638
+ /* harmony import */ var _move_node_inside_start__WEBPACK_IMPORTED_MODULE_3__ = __webpack_require__(89817);
10639
+ /* harmony import */ var _move_the_node_along_the_edge_outward__WEBPACK_IMPORTED_MODULE_4__ = __webpack_require__(7470);
10559
10640
  /*!
10560
10641
  * Jodit Editor (https://xdsoft.net/jodit/)
10561
10642
  * Released under MIT see LICENSE.txt in the project root for license information.
@@ -10566,6 +10647,7 @@ class Response {
10566
10647
 
10567
10648
 
10568
10649
 
10650
+
10569
10651
  /**
10570
10652
  * Despite the name, returns `true` when the cursor is NOT at the checked edge
10571
10653
  * of the text node: there is significant (non invisible-space) text between
@@ -10794,11 +10876,87 @@ class Selection {
10794
10876
  /**
10795
10877
  * Return current selection object
10796
10878
  */ get sel() {
10797
- if (this.j.o.shadowRoot && (0,jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_6__.isFunction)(this.j.o.shadowRoot.getSelection)) {
10798
- return this.j.o.shadowRoot.getSelection();
10879
+ const { shadowRoot } = this.j.o;
10880
+ if (shadowRoot) {
10881
+ if ((0,jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_6__.isFunction)(shadowRoot.getSelection)) {
10882
+ return shadowRoot.getSelection();
10883
+ }
10884
+ const composed = this.__composedSelection(shadowRoot);
10885
+ if (composed) {
10886
+ return composed;
10887
+ }
10799
10888
  }
10800
10889
  return this.win.getSelection();
10801
10890
  }
10891
+ /**
10892
+ * Selection of a shadow tree in a browser without `ShadowRoot.getSelection`.
10893
+ *
10894
+ * `ShadowRoot.getSelection()` is a non-standard method that WebKit never
10895
+ * implemented, and `window.getSelection()` stops at the shadow boundary: for
10896
+ * a caret inside the shadow tree it reports the host, or the document
10897
+ * itself. Everything downstream then works on the wrong tree, which is why
10898
+ * Backspace used to throw `HierarchyRequestError` and Enter did nothing when
10899
+ * the editor lived in a shadow root in Safari.
10900
+ *
10901
+ * The standard replacement is `Selection.getComposedRanges()`, which does
10902
+ * reach into a shadow tree it is given. It hands back `StaticRange`s, and
10903
+ * the editor mutates ranges constantly, so they are turned into live ones.
10904
+ *
10905
+ * Reads are answered from those ranges; everything else, including the
10906
+ * writes (`addRange`, `removeAllRanges`, `setBaseAndExtent`), goes to the
10907
+ * real selection, which does accept nodes inside a shadow tree. Reading is
10908
+ * the only side the browser blocks.
10909
+ *
10910
+ * @returns `null` when the browser offers neither API, so the caller falls
10911
+ * back to the plain window selection.
10912
+ */ __composedSelection(shadowRoot) {
10913
+ const selection = this.win.getSelection();
10914
+ if (!selection) {
10915
+ return null;
10916
+ }
10917
+ // Firefox has no `ShadowRoot.getSelection` either, but its window
10918
+ // selection does see into a shadow tree. Where the plain selection
10919
+ // already points at the right node there is nothing to work around, and
10920
+ // taking it over would change behaviour that works today.
10921
+ const { anchorNode } = selection;
10922
+ if (anchorNode && jodit_core_dom_dom__WEBPACK_IMPORTED_MODULE_4__.Dom.isOrContains(shadowRoot, anchorNode)) {
10923
+ return null;
10924
+ }
10925
+ const ranges = (0,_helpers__WEBPACK_IMPORTED_MODULE_11__.composedRanges)(selection, shadowRoot);
10926
+ if (!ranges) {
10927
+ return null;
10928
+ }
10929
+ const live = ranges.map((staticRange)=>{
10930
+ const range = this.createRange();
10931
+ range.setStart(staticRange.startContainer, staticRange.startOffset);
10932
+ range.setEnd(staticRange.endContainer, staticRange.endOffset);
10933
+ return range;
10934
+ });
10935
+ const first = live[0];
10936
+ const overrides = {
10937
+ rangeCount: live.length,
10938
+ getRangeAt: (index)=>live[index],
10939
+ isCollapsed: live.every((range)=>range.collapsed),
10940
+ // Without these the editor asks the window selection where the
10941
+ // caret is, is told "outside the editable area", and resets the
10942
+ // caret to the start of it — which is the focus loss that shows up
10943
+ // right after a successful Backspace.
10944
+ anchorNode: first ? first.startContainer : null,
10945
+ anchorOffset: first ? first.startOffset : 0,
10946
+ focusNode: first ? first.endContainer : null,
10947
+ focusOffset: first ? first.endOffset : 0,
10948
+ toString: ()=>live.map((range)=>range.toString()).join('')
10949
+ };
10950
+ return new Proxy(selection, {
10951
+ get (target, property) {
10952
+ if ((0,jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_6__.isString)(property) && property in overrides) {
10953
+ return overrides[property];
10954
+ }
10955
+ const value = Reflect.get(target, property, target);
10956
+ return (0,jodit_core_helpers_checker__WEBPACK_IMPORTED_MODULE_6__.isFunction)(value) ? value.bind(target) : value;
10957
+ }
10958
+ });
10959
+ }
10802
10960
  /**
10803
10961
  * Return first selected range or create new
10804
10962
  */ get range() {
@@ -17828,6 +17986,11 @@ class Jodit extends jodit_modules__WEBPACK_IMPORTED_MODULE_10__.ViewWithToolbar
17828
17986
  }
17829
17987
  if (this.editor) {
17830
17988
  this.editor.innerHTML = data.value;
17989
+ // Fired synchronously, before any task can run: the value was
17990
+ // sanitized in an inert document and re-parsed here with scripting
17991
+ // on, and the two parsers do not always agree. Listeners get to
17992
+ // look at the tree that actually exists.
17993
+ this.e.fire('afterSetNativeEditorValue');
17831
17994
  }
17832
17995
  }
17833
17996
  /**
@@ -28535,6 +28698,15 @@ class cleanHtml extends jodit_core_plugin_plugin__WEBPACK_IMPORTED_MODULE_7__.Pl
28535
28698
  return false;
28536
28699
  }
28537
28700
  }
28701
+ /**
28702
+ * The value was sanitized in an inert document and has just been re-parsed
28703
+ * into the live editor with scripting on. Where the two parsers disagree
28704
+ * (`<noscript>`, raw-text elements), markup that was inert text a moment
28705
+ * ago is a real element now, so the live tree is sanitized once more, in
28706
+ * the same call stack, before any handler it might carry can fire.
28707
+ */ onAfterSetNativeEditorValue() {
28708
+ ;(0,jodit_core_helpers_html_safe_html__WEBPACK_IMPORTED_MODULE_6__.safeHTML)(this.j.editor, this.j.o.cleanHTML);
28709
+ }
28538
28710
  /**
28539
28711
  * Event handler when manually assigning a value to the HTML editor.
28540
28712
  */ onBeforeSetNativeEditorValue(data) {
@@ -28660,6 +28832,9 @@ class cleanHtml extends jodit_core_plugin_plugin__WEBPACK_IMPORTED_MODULE_7__.Pl
28660
28832
  (0,_swc_helpers_ts_decorate__WEBPACK_IMPORTED_MODULE_1__.__decorate)([
28661
28833
  (0,jodit_core_decorators__WEBPACK_IMPORTED_MODULE_2__.watch)(':beforeCommand')
28662
28834
  ], cleanHtml.prototype, "beforeCommand", null);
28835
+ (0,_swc_helpers_ts_decorate__WEBPACK_IMPORTED_MODULE_1__.__decorate)([
28836
+ (0,jodit_core_decorators__WEBPACK_IMPORTED_MODULE_2__.watch)(':afterSetNativeEditorValue')
28837
+ ], cleanHtml.prototype, "onAfterSetNativeEditorValue", null);
28663
28838
  (0,_swc_helpers_ts_decorate__WEBPACK_IMPORTED_MODULE_1__.__decorate)([
28664
28839
  (0,jodit_core_decorators__WEBPACK_IMPORTED_MODULE_2__.watch)(':beforeSetNativeEditorValue')
28665
28840
  ], cleanHtml.prototype, "onBeforeSetNativeEditorValue", null);