@contentful/field-editor-rich-text 2.0.0-next.30 → 2.0.0-next.33

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.
@@ -2,7 +2,7 @@ import React__default, { createContext, useContext, useMemo, createElement, useE
2
2
  import { useEntities, ScheduledIconWithTooltip, MissingEntityCard, AssetThumbnail, EntityProvider, getScheduleTooltipContent } from '@contentful/field-editor-reference';
3
3
  import { entityHelpers, shortenStorageUnit, isValidImage, ModalDialogLauncher, FieldConnector } from '@contentful/field-editor-shared';
4
4
  import { BLOCKS, INLINES, TEXT_CONTAINERS, HEADINGS, LIST_ITEM_BLOCKS, MARKS, CONTAINERS, TOP_LEVEL_BLOCKS, VOID_BLOCKS, EMPTY_DOCUMENT } from '@contentful/rich-text-types';
5
- import { usePlateEditorRef, usePlateEditorState, getNodes, toggleNodeType, getText, getAbove, setNodes, isAncestorEmpty, match, getLastChildPath, wrapNodes, getPluginType, unwrapNodes, isCollapsed, isRangeAcrossBlocks, ELEMENT_DEFAULT, findNode, getParent, getBlockAbove, isSelectionAtBlockStart, isSelectionAtBlockEnd, isFirstChild, insertNodes, moveChildren, isBlockAboveEmpty, mockPlugin, deleteFragment, isMarkActive, toggleMark, someHtmlElement, KEY_DESERIALIZE_HTML, hasSingleChild, isLastChild, getChildren as getChildren$1, someNode, createDeserializeHtmlPlugin, createDeserializeAstPlugin, createPlateEditor, getPlateSelectors, getPlateActions, Plate } from '@udecode/plate-core';
5
+ import { usePlateEditorRef, usePlateEditorState, getNodes, toggleNodeType, getText, getAbove, setNodes, isAncestorEmpty, match, getLastChildPath, wrapNodes, getPluginType, unwrapNodes, isCollapsed, isRangeAcrossBlocks, ELEMENT_DEFAULT, findNode, getParent, getBlockAbove, isSelectionAtBlockStart, isSelectionAtBlockEnd, isFirstChild, insertNodes, moveChildren, isBlockAboveEmpty, mockPlugin, deleteFragment, isMarkActive, toggleMark, someHtmlElement, KEY_DESERIALIZE_HTML, hasSingleChild, isLastChild, someNode, getChildren as getChildren$1, createDeserializeHtmlPlugin, createDeserializeAstPlugin, createPlateEditor, getPlateSelectors, getPlateActions, Plate } from '@udecode/plate-core';
6
6
  import { css, cx } from 'emotion';
7
7
  import deepEquals from 'fast-deep-equal';
8
8
  import noop from 'lodash-es/noop';
@@ -26,7 +26,7 @@ import { createBoldPlugin as createBoldPlugin$1, createCodePlugin as createCodeP
26
26
  import isPlainObject from 'is-plain-obj';
27
27
  import { createParagraphPlugin as createParagraphPlugin$1 } from '@udecode/plate-paragraph';
28
28
  import { createSelectOnBackspacePlugin as createSelectOnBackspacePlugin$1 } from '@udecode/plate-select';
29
- import { ELEMENT_TABLE, ELEMENT_TH, ELEMENT_TR, ELEMENT_TD, insertTable, getEmptyRowNode, getEmptyCellNode, deleteRow, deleteColumn, deleteTable, onKeyDownTable as onKeyDownTable$1, getTableCellEntry, createTablePlugin as createTablePlugin$1, withTable } from '@udecode/plate-table';
29
+ import { ELEMENT_TABLE, ELEMENT_TR, getEmptyRowNode, ELEMENT_TD, ELEMENT_TH, getEmptyCellNode, insertTable, deleteRow, deleteColumn, deleteTable, onKeyDownTable as onKeyDownTable$1, getTableCellEntry, createTablePlugin as createTablePlugin$1, withTable } from '@udecode/plate-table';
30
30
  import { toContentfulDocument, toSlatejsDocument } from '@contentful/contentful-slatejs-adapter';
31
31
  import { documentToPlainTextString } from '@contentful/rich-text-plain-text-renderer';
32
32
  import { createTrailingBlockPlugin } from '@udecode/plate-trailing-block';
@@ -5621,210 +5621,6 @@ function SlashCommandsPalette(_ref2) {
5621
5621
  }, /*#__PURE__*/createElement(Card, null, /*#__PURE__*/createElement(Text$1, null, "Slash commands are temporarily unavailable.")));
5622
5622
  }
5623
5623
 
5624
- function insertTableAndFocusFirstCell(editor) {
5625
- insertTable(editor, {
5626
- header: true
5627
- });
5628
- replaceEmptyParagraphWithTable(editor);
5629
- }
5630
- function isTableActive(editor) {
5631
- var tableElements = [ELEMENT_TABLE, ELEMENT_TH, ELEMENT_TR, ELEMENT_TD];
5632
- return tableElements.some(function (el) {
5633
- return isBlockSelected(editor, el);
5634
- });
5635
- }
5636
- function isTableHeaderEnabled(editor) {
5637
- var tableItem = getAbove(editor, {
5638
- match: {
5639
- type: BLOCKS.TABLE
5640
- }
5641
- });
5642
-
5643
- if (!tableItem) {
5644
- return false;
5645
- }
5646
-
5647
- var firstRow = getChildren$1(tableItem)[0];
5648
-
5649
- if (!firstRow) {
5650
- return false;
5651
- }
5652
-
5653
- return getChildren$1(firstRow).every(function (_ref) {
5654
- var node = _ref[0];
5655
- return node.type === BLOCKS.TABLE_HEADER_CELL;
5656
- });
5657
- }
5658
- function replaceEmptyParagraphWithTable(editor) {
5659
- var tablePath = getAncestorPathFromSelection(editor);
5660
- if (!tablePath || isFirstChild(tablePath)) return;
5661
- var previousPath = Path.previous(tablePath);
5662
- if (!previousPath) return;
5663
-
5664
- var _Editor$nodes = Editor.nodes(editor, {
5665
- at: previousPath,
5666
- match: function match(node) {
5667
- return node.type === BLOCKS.PARAGRAPH;
5668
- }
5669
- }),
5670
- nodes = _Editor$nodes[0];
5671
-
5672
- if (!nodes) return;
5673
- var previousNode = nodes[0];
5674
- var isPreviousNodeTextEmpty = isAncestorEmpty(editor, previousNode);
5675
-
5676
- if (isPreviousNodeTextEmpty) {
5677
- // Switch table with previous empty paragraph
5678
- Transforms.moveNodes(editor, {
5679
- at: tablePath,
5680
- to: previousPath
5681
- }); // Remove previous paragraph that now is under the table
5682
-
5683
- Transforms.removeNodes(editor, {
5684
- at: tablePath
5685
- });
5686
- }
5687
- }
5688
- /**
5689
- * Returns the number of cells in a given row vs the table width
5690
- *
5691
- * Note: We should only get different table rows cell counts in between
5692
- * normalization cycles.
5693
- */
5694
-
5695
- var getNoOfMissingTableCellsInRow = function getNoOfMissingTableCellsInRow(editor, _ref2) {
5696
- var rowPath = _ref2[1];
5697
- var parent = getParent(editor, rowPath); // This is ensured by normalization. The error is here just in case
5698
-
5699
- if (!parent) {
5700
- throw new Error('table rows must be wrapped in a table node');
5701
- }
5702
-
5703
- var tablePath = parent[1]; // The longest table row determines its width
5704
-
5705
- var tableWidth = Math.max.apply(Math, Array.from(Node.children(editor, tablePath)).map(function (_ref3) {
5706
- var path = _ref3[1];
5707
- return Array.from(Node.children(editor, path)).length;
5708
- }));
5709
- var rowWidth = Array.from(Node.children(editor, rowPath)).length;
5710
- return tableWidth - rowWidth;
5711
- };
5712
- var createEmptyTableCells = function createEmptyTableCells(count) {
5713
- var emptyTableCell = {
5714
- type: BLOCKS.TABLE_CELL,
5715
- data: {},
5716
- children: [{
5717
- type: BLOCKS.PARAGRAPH,
5718
- data: {},
5719
- children: [{
5720
- text: ''
5721
- }]
5722
- }]
5723
- };
5724
- return new Array(count).fill(emptyTableCell);
5725
- };
5726
- var isNotEmpty = function isNotEmpty(editor, _ref4) {
5727
- var path = _ref4[1];
5728
- return Array.from(Node.children(editor, path)).length !== 0;
5729
- };
5730
- var isTable = function isTable(node) {
5731
- return Element.isElement(node) && node.type === BLOCKS.TABLE;
5732
- };
5733
-
5734
- function hasTables(nodes) {
5735
- return nodes.some(function (_ref) {
5736
- var type = _ref.type;
5737
- return type === BLOCKS.TABLE;
5738
- });
5739
- }
5740
-
5741
- var isTableHeaderCell = function isTableHeaderCell(_ref2) {
5742
- var type = _ref2.type;
5743
- return type === BLOCKS.TABLE_HEADER_CELL;
5744
- };
5745
-
5746
- var isTableCellOrHeader = function isTableCellOrHeader(node) {
5747
- return Element.isElement(node) && [BLOCKS.TABLE_HEADER_CELL, BLOCKS.TABLE_CELL].includes(node.type);
5748
- };
5749
-
5750
- function hasHeadersOutsideFirstRow(nodes) {
5751
- return nodes.filter(function (_ref3) {
5752
- var type = _ref3.type;
5753
- return type === BLOCKS.TABLE;
5754
- }).flatMap(function (_ref4) {
5755
- var children = _ref4.children;
5756
- return children.slice(1);
5757
- }).some(function (_ref5) {
5758
- var children = _ref5.children;
5759
- return children.some(isTableHeaderCell);
5760
- });
5761
- }
5762
-
5763
- function trackInvalidTableCellChildren(editor, table) {
5764
- var cells = table.children.flatMap(function (row) {
5765
- var _row$children;
5766
-
5767
- return (_row$children = row.children) != null ? _row$children : [];
5768
- }).filter(isTableCellOrHeader); // get invalid direct children
5769
-
5770
- var invalidNodeTypes = cells.flatMap(function (cell) {
5771
- // Only paragraphs are allowed inside tables at the moment
5772
- return cell.children.filter(function (node) {
5773
- return Element.isElement(node) && node.type !== BLOCKS.PARAGRAPH;
5774
- }).map(function (node) {
5775
- return node.type;
5776
- });
5777
- });
5778
-
5779
- for (var _iterator = _createForOfIteratorHelperLoose(new Set(invalidNodeTypes)), _step; !(_step = _iterator()).done;) {
5780
- var _editor$tracking;
5781
-
5782
- var nodeType = _step.value;
5783
- (_editor$tracking = editor.tracking) == null ? void 0 : _editor$tracking.onViewportAction('invalidTablePaste', {
5784
- nodeType: nodeType
5785
- });
5786
- }
5787
- }
5788
-
5789
- function addTableTrackingEvents(editor) {
5790
- var insertData = editor.insertData;
5791
-
5792
- editor.insertData = function (data) {
5793
- var html = data.getData('text/html');
5794
-
5795
- if (html) {
5796
- var markupBefore = editor.children;
5797
- insertData(data);
5798
- var markupAfter = editor.children;
5799
- setTimeout(function () {
5800
- if (hasTables(markupBefore)) return;
5801
-
5802
- if (hasTables(markupAfter)) {
5803
- editor.tracking.onViewportAction('paste', {
5804
- tablePasted: true,
5805
- hasHeadersOutsideFirstRow: hasHeadersOutsideFirstRow(markupAfter)
5806
- });
5807
- }
5808
- }, 1);
5809
- } else {
5810
- insertData(data);
5811
- }
5812
- };
5813
-
5814
- var insertFragment = editor.insertFragment;
5815
-
5816
- editor.insertFragment = function (fragment) {
5817
- var tables = fragment.filter(isTable);
5818
-
5819
- for (var _iterator2 = _createForOfIteratorHelperLoose(tables), _step2; !(_step2 = _iterator2()).done;) {
5820
- var table = _step2.value;
5821
- trackInvalidTableCellChildren(editor, table);
5822
- }
5823
-
5824
- return insertFragment(fragment);
5825
- };
5826
- }
5827
-
5828
5624
  var addRow = function addRow(editor, getNextRowPath) {
5829
5625
  if (someNode(editor, {
5830
5626
  match: {
@@ -5944,47 +5740,157 @@ var setHeader = function setHeader(editor, enable) {
5944
5740
  });
5945
5741
  };
5946
5742
 
5947
- var styles$i = {
5948
- topRight: /*#__PURE__*/css({
5949
- position: 'absolute',
5950
- top: '6px',
5951
- right: '5px'
5952
- })
5953
- };
5954
-
5955
- var getCurrentTableSize = function getCurrentTableSize(editor) {
5956
- var _getNodeEntryFromSele = getNodeEntryFromSelection(editor, BLOCKS.TABLE),
5957
- table = _getNodeEntryFromSele[0];
5743
+ function insertTableAndFocusFirstCell(editor) {
5744
+ insertTable(editor, {
5745
+ header: true
5746
+ });
5747
+ replaceEmptyParagraphWithTable(editor);
5748
+ }
5749
+ function isTableActive(editor) {
5750
+ var tableElements = [ELEMENT_TABLE, ELEMENT_TH, ELEMENT_TR, ELEMENT_TD];
5751
+ return tableElements.some(function (el) {
5752
+ return isBlockSelected(editor, el);
5753
+ });
5754
+ }
5755
+ function isTableHeaderEnabled(editor) {
5756
+ var tableItem = getAbove(editor, {
5757
+ match: {
5758
+ type: BLOCKS.TABLE
5759
+ }
5760
+ });
5958
5761
 
5959
- return table ? getTableSize(table) : null;
5960
- };
5762
+ if (!tableItem) {
5763
+ return false;
5764
+ }
5961
5765
 
5962
- var TableActions = function TableActions() {
5963
- var editor = useContentfulEditor();
5964
- var isDisabled = useReadOnly();
5766
+ var firstRow = getChildren$1(tableItem)[0];
5965
5767
 
5966
- var _React$useState = React__default.useState(false),
5967
- isOpen = _React$useState[0],
5968
- setOpen = _React$useState[1];
5768
+ if (!firstRow) {
5769
+ return false;
5770
+ }
5969
5771
 
5970
- var _React$useState2 = React__default.useState(false),
5971
- isHeaderEnabled = _React$useState2[0],
5972
- setHeaderEnabled = _React$useState2[1];
5772
+ return getChildren$1(firstRow).every(function (_ref) {
5773
+ var node = _ref[0];
5774
+ return node.type === BLOCKS.TABLE_HEADER_CELL;
5775
+ });
5776
+ }
5777
+ function replaceEmptyParagraphWithTable(editor) {
5778
+ var tablePath = getAncestorPathFromSelection(editor);
5779
+ if (!tablePath || isFirstChild(tablePath)) return;
5780
+ var previousPath = Path.previous(tablePath);
5781
+ if (!previousPath) return;
5973
5782
 
5974
- var close = React__default.useCallback(function () {
5975
- setOpen(false);
5976
- }, []);
5977
- React__default.useEffect(function () {
5978
- setHeaderEnabled(Boolean(editor && isTableHeaderEnabled(editor)));
5979
- }, [editor]);
5980
- var canInsertRowAbove = React__default.useMemo(function () {
5981
- if (!editor) {
5982
- return false;
5783
+ var _Editor$nodes = Editor.nodes(editor, {
5784
+ at: previousPath,
5785
+ match: function match(node) {
5786
+ return node.type === BLOCKS.PARAGRAPH;
5983
5787
  }
5788
+ }),
5789
+ nodes = _Editor$nodes[0];
5984
5790
 
5985
- var headerCell = getAbove(editor, {
5986
- match: {
5987
- type: BLOCKS.TABLE_HEADER_CELL
5791
+ if (!nodes) return;
5792
+ var previousNode = nodes[0];
5793
+ var isPreviousNodeTextEmpty = isAncestorEmpty(editor, previousNode);
5794
+
5795
+ if (isPreviousNodeTextEmpty) {
5796
+ // Switch table with previous empty paragraph
5797
+ Transforms.moveNodes(editor, {
5798
+ at: tablePath,
5799
+ to: previousPath
5800
+ }); // Remove previous paragraph that now is under the table
5801
+
5802
+ Transforms.removeNodes(editor, {
5803
+ at: tablePath
5804
+ });
5805
+ }
5806
+ }
5807
+ /**
5808
+ * Returns the number of cells in a given row vs the table width
5809
+ *
5810
+ * Note: We should only get different table rows cell counts in between
5811
+ * normalization cycles.
5812
+ */
5813
+
5814
+ var getNoOfMissingTableCellsInRow = function getNoOfMissingTableCellsInRow(editor, _ref2) {
5815
+ var rowPath = _ref2[1];
5816
+ var parent = getParent(editor, rowPath); // This is ensured by normalization. The error is here just in case
5817
+
5818
+ if (!parent) {
5819
+ throw new Error('table rows must be wrapped in a table node');
5820
+ }
5821
+
5822
+ var tablePath = parent[1]; // The longest table row determines its width
5823
+
5824
+ var tableWidth = Math.max.apply(Math, Array.from(Node.children(editor, tablePath)).map(function (_ref3) {
5825
+ var path = _ref3[1];
5826
+ return Array.from(Node.children(editor, path)).length;
5827
+ }));
5828
+ var rowWidth = Array.from(Node.children(editor, rowPath)).length;
5829
+ return tableWidth - rowWidth;
5830
+ };
5831
+ var createEmptyTableCells = function createEmptyTableCells(count) {
5832
+ var emptyTableCell = {
5833
+ type: BLOCKS.TABLE_CELL,
5834
+ data: {},
5835
+ children: [{
5836
+ type: BLOCKS.PARAGRAPH,
5837
+ data: {},
5838
+ children: [{
5839
+ text: ''
5840
+ }]
5841
+ }]
5842
+ };
5843
+ return new Array(count).fill(emptyTableCell);
5844
+ };
5845
+ var isNotEmpty = function isNotEmpty(editor, _ref4) {
5846
+ var path = _ref4[1];
5847
+ return Array.from(Node.children(editor, path)).length !== 0;
5848
+ };
5849
+ var isTable = function isTable(node) {
5850
+ return Element.isElement(node) && node.type === BLOCKS.TABLE;
5851
+ };
5852
+
5853
+ var styles$i = {
5854
+ topRight: /*#__PURE__*/css({
5855
+ position: 'absolute',
5856
+ top: '6px',
5857
+ right: '5px'
5858
+ })
5859
+ };
5860
+
5861
+ var getCurrentTableSize = function getCurrentTableSize(editor) {
5862
+ var _getNodeEntryFromSele = getNodeEntryFromSelection(editor, BLOCKS.TABLE),
5863
+ table = _getNodeEntryFromSele[0];
5864
+
5865
+ return table ? getTableSize(table) : null;
5866
+ };
5867
+
5868
+ var TableActions = function TableActions() {
5869
+ var editor = useContentfulEditor();
5870
+ var isDisabled = useReadOnly();
5871
+
5872
+ var _React$useState = React__default.useState(false),
5873
+ isOpen = _React$useState[0],
5874
+ setOpen = _React$useState[1];
5875
+
5876
+ var _React$useState2 = React__default.useState(false),
5877
+ isHeaderEnabled = _React$useState2[0],
5878
+ setHeaderEnabled = _React$useState2[1];
5879
+
5880
+ var close = React__default.useCallback(function () {
5881
+ setOpen(false);
5882
+ }, []);
5883
+ React__default.useEffect(function () {
5884
+ setHeaderEnabled(Boolean(editor && isTableHeaderEnabled(editor)));
5885
+ }, [editor]);
5886
+ var canInsertRowAbove = React__default.useMemo(function () {
5887
+ if (!editor) {
5888
+ return false;
5889
+ }
5890
+
5891
+ var headerCell = getAbove(editor, {
5892
+ match: {
5893
+ type: BLOCKS.TABLE_HEADER_CELL
5988
5894
  }
5989
5895
  });
5990
5896
  return !headerCell;
@@ -6067,7 +5973,7 @@ var Cell = function Cell(props) {
6067
5973
  };
6068
5974
 
6069
5975
  var _templateObject$8;
6070
- var style$4 = /*#__PURE__*/css(_templateObject$8 || (_templateObject$8 = /*#__PURE__*/_taggedTemplateLiteralLoose(["\n background-color: ", ";\n border: 1px solid ", ";\n border-collapse: collapse;\n padding: 10px 12px;\n font-weight: ", ";\n text-align: left;\n min-width: 48px;\n position: relative;\n\n div:last-child {\n margin-bottom: 0;\n }\n"])), tokens.gray200, tokens.gray400, tokens.fontWeightNormal);
5976
+ var style$4 = /*#__PURE__*/css(_templateObject$8 || (_templateObject$8 = /*#__PURE__*/_taggedTemplateLiteralLoose(["\n background-clip: padding-box;\n background-color: ", ";\n border: 1px solid ", ";\n border-collapse: collapse;\n padding: 10px 12px;\n font-weight: ", ";\n text-align: left;\n min-width: 48px;\n position: relative;\n\n div:last-child {\n margin-bottom: 0;\n }\n"])), tokens.gray200, tokens.gray400, tokens.fontWeightNormal);
6071
5977
  var HeaderCell = function HeaderCell(props) {
6072
5978
  var isSelected = useSelected();
6073
5979
  return /*#__PURE__*/createElement("th", Object.assign({}, props.attributes, props.element.data, {
@@ -6105,18 +6011,20 @@ var Table = function Table(props) {
6105
6011
  */
6106
6012
 
6107
6013
  var trimUnnecessaryTableWrapper = function trimUnnecessaryTableWrapper(node) {
6014
+ var _node$children, _row$children;
6015
+
6108
6016
  if (!Element.isElement(node)) {
6109
6017
  return [node];
6110
6018
  } // must be a table with a single row
6111
6019
 
6112
6020
 
6113
- if (node.type !== BLOCKS.TABLE || node.children.length !== 1) {
6021
+ if (node.type !== BLOCKS.TABLE || ((_node$children = node.children) == null ? void 0 : _node$children.length) !== 1) {
6114
6022
  return [node];
6115
6023
  }
6116
6024
 
6117
6025
  var row = node.children[0]; // the row must contain a single cell
6118
6026
 
6119
- if (row.children.length !== 1) {
6027
+ if ((row == null ? void 0 : (_row$children = row.children) == null ? void 0 : _row$children.length) !== 1) {
6120
6028
  return [node];
6121
6029
  }
6122
6030
 
@@ -6158,57 +6066,347 @@ var onKeyDownTable = function onKeyDownTable(editor, plugin) {
6158
6066
  // This fixes `Cannot resolve a Slate point from DOM point: [object HTMLDivElement]` when typing while the cursor is before table
6159
6067
  var windowSelection = window.getSelection();
6160
6068
 
6161
- if (windowSelection) {
6162
- var _windowSelection$anch, _windowSelection$anch2;
6069
+ if (windowSelection) {
6070
+ var _windowSelection$anch, _windowSelection$anch2;
6071
+
6072
+ // @ts-expect-error
6073
+ var blockType = (_windowSelection$anch = windowSelection.anchorNode.attributes) == null ? void 0 : (_windowSelection$anch2 = _windowSelection$anch['data-block-type']) == null ? void 0 : _windowSelection$anch2.value; // this attribute comes from `plugins/Table/components/Table.tsx`
6074
+
6075
+ var isBeforeTable = blockType === BLOCKS.TABLE;
6076
+
6077
+ if (isBeforeTable) {
6078
+ if (event.key === 'Enter') {
6079
+ var above = getAbove(editor, {
6080
+ match: {
6081
+ type: BLOCKS.TABLE
6082
+ }
6083
+ });
6084
+ if (!above) return;
6085
+ var tablePath = above[1];
6086
+ insertEmptyParagraph(editor, {
6087
+ at: tablePath,
6088
+ select: true
6089
+ });
6090
+ }
6091
+
6092
+ event.preventDefault();
6093
+ event.stopPropagation();
6094
+ return;
6095
+ }
6096
+ } // Pressing Tab on the last cell creates a new row
6097
+ // Otherwise, jumping between cells is handled in the defaultKeyDownTable
6098
+
6099
+
6100
+ if (event.key === 'Tab' && !event.shiftKey) {
6101
+ event.preventDefault();
6102
+ var res = getTableCellEntry(editor, {});
6103
+
6104
+ if (res) {
6105
+ var tableElement = res.tableElement,
6106
+ tableRow = res.tableRow,
6107
+ tableCell = res.tableCell;
6108
+ var isLastCell = isLastChild(tableRow, tableCell[1]);
6109
+ var isLastRow = isLastChild(tableElement, tableRow[1]);
6110
+
6111
+ if (isLastRow && isLastCell) {
6112
+ addRowBelow(editor); // skip default handler
6113
+
6114
+ return;
6115
+ }
6116
+ }
6117
+ }
6118
+
6119
+ defaultHandler(event);
6120
+ };
6121
+ };
6122
+
6123
+ var _extends2, _extends4, _inlines;
6124
+ var inlines = /*#__PURE__*/Object.values(INLINES).map(function (type) {
6125
+ return {
6126
+ type: type
6127
+ };
6128
+ });
6129
+ var schema = {
6130
+ document: {
6131
+ nodes: [{
6132
+ types: /*#__PURE__*/TOP_LEVEL_BLOCKS.map(function (type) {
6133
+ return {
6134
+ type: type
6135
+ };
6136
+ })
6137
+ }]
6138
+ },
6139
+ blocks: /*#__PURE__*/_extends((_extends2 = {}, _extends2[BLOCKS.PARAGRAPH] = {
6140
+ nodes: [{
6141
+ match: /*#__PURE__*/[].concat(inlines, [{
6142
+ object: 'text'
6143
+ }])
6144
+ }]
6145
+ }, _extends2[BLOCKS.HEADING_1] = {
6146
+ nodes: [{
6147
+ match: /*#__PURE__*/[].concat(inlines, [{
6148
+ object: 'text'
6149
+ }])
6150
+ }]
6151
+ }, _extends2[BLOCKS.HEADING_2] = {
6152
+ nodes: [{
6153
+ match: /*#__PURE__*/[].concat(inlines, [{
6154
+ object: 'text'
6155
+ }])
6156
+ }]
6157
+ }, _extends2[BLOCKS.HEADING_3] = {
6158
+ nodes: [{
6159
+ match: /*#__PURE__*/[].concat(inlines, [{
6160
+ object: 'text'
6161
+ }])
6162
+ }]
6163
+ }, _extends2[BLOCKS.HEADING_4] = {
6164
+ nodes: [{
6165
+ match: /*#__PURE__*/[].concat(inlines, [{
6166
+ object: 'text'
6167
+ }])
6168
+ }]
6169
+ }, _extends2[BLOCKS.HEADING_5] = {
6170
+ nodes: [{
6171
+ match: /*#__PURE__*/[].concat(inlines, [{
6172
+ object: 'text'
6173
+ }])
6174
+ }]
6175
+ }, _extends2[BLOCKS.HEADING_6] = {
6176
+ nodes: [{
6177
+ match: /*#__PURE__*/[].concat(inlines, [{
6178
+ object: 'text'
6179
+ }])
6180
+ }]
6181
+ }, _extends2), /*#__PURE__*/VOID_BLOCKS.reduce(function (blocks, nodeType) {
6182
+ var _extends3;
6183
+
6184
+ return _extends({}, blocks, (_extends3 = {}, _extends3[nodeType] = {
6185
+ isVoid: true
6186
+ }, _extends3));
6187
+ }, {}), (_extends4 = {}, _extends4[BLOCKS.QUOTE] = {
6188
+ nodes: [{
6189
+ match: [/*#__PURE__*/CONTAINERS[BLOCKS.QUOTE].map(function (type) {
6190
+ return {
6191
+ type: type
6192
+ };
6193
+ })],
6194
+ min: 1
6195
+ }],
6196
+ normalize: function normalize(editor, error) {
6197
+ if (error.code === 'child_type_invalid') {
6198
+ return editor.unwrapBlockByKey(error.node.key, BLOCKS.QUOTE);
6199
+ }
6200
+ }
6201
+ }, _extends4)),
6202
+ inlines: (_inlines = {}, _inlines[INLINES.HYPERLINK] = {
6203
+ nodes: [{
6204
+ match: [{
6205
+ object: 'text'
6206
+ }]
6207
+ }]
6208
+ }, _inlines[INLINES.ENTRY_HYPERLINK] = {
6209
+ nodes: [{
6210
+ match: [{
6211
+ object: 'text'
6212
+ }]
6213
+ }]
6214
+ }, _inlines[INLINES.ASSET_HYPERLINK] = {
6215
+ nodes: [{
6216
+ match: [{
6217
+ object: 'text'
6218
+ }]
6219
+ }]
6220
+ }, _inlines[INLINES.EMBEDDED_ENTRY] = {
6221
+ isVoid: true
6222
+ }, _inlines)
6223
+ };
6224
+
6225
+ function getCharacterCount(editor) {
6226
+ var document = toContentfulDocument({
6227
+ document: editor.children,
6228
+ schema: schema
6229
+ });
6230
+ return documentToPlainTextString(document).length;
6231
+ }
6232
+
6233
+ var actionOrigin = {
6234
+ TOOLBAR: 'toolbar-icon',
6235
+ SHORTCUT: 'shortcut',
6236
+ VIEWPORT: 'viewport-interaction',
6237
+ COMMAND_PALETTE: 'command-palette'
6238
+ };
6239
+ function getPastingSource(data) {
6240
+ var textHtml = data.getData('text/html');
6241
+ var doc = new DOMParser().parseFromString(textHtml, 'text/html');
6242
+
6243
+ if (doc.querySelector('[id*="docs-internal-guid"]')) {
6244
+ return 'Google Docs';
6245
+ }
6246
+
6247
+ if (doc.querySelector('google-sheets-html-origin') || doc.querySelector('[data-sheets-value]')) {
6248
+ return 'Google Spreadsheets';
6249
+ }
6250
+
6251
+ if (doc.querySelector('meta[content*="Microsoft Excel"]')) {
6252
+ return 'Microsoft Excel';
6253
+ }
6254
+
6255
+ if (doc.querySelector('meta[content*="Microsoft Word"]')) {
6256
+ return 'Microsoft Word';
6257
+ } // TODO: MS Word Online doesn't give us specific tags, we might need to have a closer look at its tracking result since we are using generic values to identify it
6258
+
6259
+
6260
+ if (doc.querySelector('[style*="Arial_MSFontService"]') && (doc.querySelector('.TextRun') || doc.querySelector('.OutlineElement'))) {
6261
+ return 'Microsoft Word Online';
6262
+ }
6263
+
6264
+ if (doc.querySelector('meta[content="Cocoa HTML Writer"]')) {
6265
+ return 'Apple Notes';
6266
+ }
6267
+
6268
+ if (doc.querySelector('[style*="Slack-Lato, Slack-Fractions"]')) {
6269
+ return 'Slack';
6270
+ }
6271
+
6272
+ return 'Unknown';
6273
+ }
6274
+ var createTrackingPlugin = function createTrackingPlugin(onAction) {
6275
+ var trackingActions = {
6276
+ onViewportAction: function onViewportAction(actionName, data) {
6277
+ if (data === void 0) {
6278
+ data = {};
6279
+ }
6280
+
6281
+ return onAction(actionName, _extends({
6282
+ origin: actionOrigin.VIEWPORT
6283
+ }, data));
6284
+ },
6285
+ onShortcutAction: function onShortcutAction(actionName, data) {
6286
+ if (data === void 0) {
6287
+ data = {};
6288
+ }
6289
+
6290
+ return onAction(actionName, _extends({
6291
+ origin: actionOrigin.SHORTCUT
6292
+ }, data));
6293
+ },
6294
+ onToolbarAction: function onToolbarAction(actionName, data) {
6295
+ if (data === void 0) {
6296
+ data = {};
6297
+ }
6298
+
6299
+ return onAction(actionName, _extends({
6300
+ origin: actionOrigin.TOOLBAR
6301
+ }, data));
6302
+ },
6303
+ onCommandPaletteAction: function onCommandPaletteAction(actionName, data) {
6304
+ if (data === void 0) {
6305
+ data = {};
6306
+ }
6307
+
6308
+ return onAction(actionName, _extends({
6309
+ origin: actionOrigin.COMMAND_PALETTE
6310
+ }, data));
6311
+ }
6312
+ };
6313
+ return {
6314
+ key: 'TrackingPlugin',
6315
+ withOverrides: function withOverrides(editor) {
6316
+ var insertData = editor.insertData;
6317
+ editor.tracking = trackingActions;
6318
+
6319
+ editor.insertData = function (data) {
6320
+ var isCopyAndPaste = data.types.length !== 0;
6321
+
6322
+ if (isCopyAndPaste) {
6323
+ var _window$getSelection;
6324
+
6325
+ var characterCountSelection = (_window$getSelection = window.getSelection()) == null ? void 0 : _window$getSelection.toString().length;
6326
+ var characterCountBefore = getCharacterCount(editor);
6327
+ setTimeout(function () {
6328
+ var characterCountAfter = getCharacterCount(editor);
6329
+ trackingActions.onShortcutAction('paste', {
6330
+ characterCountAfter: characterCountAfter,
6331
+ characterCountBefore: characterCountBefore,
6332
+ characterCountSelection: characterCountSelection,
6333
+ source: getPastingSource(data)
6334
+ });
6335
+ });
6336
+ }
6337
+
6338
+ insertData(data);
6339
+ };
6340
+
6341
+ return editor;
6342
+ }
6343
+ };
6344
+ };
6345
+
6346
+ function hasTables(nodes) {
6347
+ return nodes.some(function (_ref) {
6348
+ var type = _ref.type;
6349
+ return type === BLOCKS.TABLE;
6350
+ });
6351
+ }
6352
+
6353
+ var isTableHeaderCell = function isTableHeaderCell(_ref2) {
6354
+ var type = _ref2.type;
6355
+ return type === BLOCKS.TABLE_HEADER_CELL;
6356
+ };
6357
+
6358
+ function hasHeadersOutsideFirstRow(nodes) {
6359
+ return nodes.filter(function (_ref3) {
6360
+ var type = _ref3.type;
6361
+ return type === BLOCKS.TABLE;
6362
+ }).flatMap(function (_ref4) {
6363
+ var children = _ref4.children;
6364
+ return children.slice(1);
6365
+ }).some(function (_ref5) {
6366
+ var children = _ref5.children;
6367
+ return children.some(isTableHeaderCell);
6368
+ });
6369
+ }
6370
+
6371
+ function addTableTrackingEvents(editor) {
6372
+ var insertData = editor.insertData;
6163
6373
 
6164
- // @ts-expect-error
6165
- var blockType = (_windowSelection$anch = windowSelection.anchorNode.attributes) == null ? void 0 : (_windowSelection$anch2 = _windowSelection$anch['data-block-type']) == null ? void 0 : _windowSelection$anch2.value; // this attribute comes from `plugins/Table/components/Table.tsx`
6374
+ editor.insertData = function (data) {
6375
+ var html = data.getData('text/html');
6166
6376
 
6167
- var isBeforeTable = blockType === BLOCKS.TABLE;
6377
+ if (html) {
6378
+ var markupBefore = editor.children;
6379
+ insertData(data);
6380
+ var markupAfter = editor.children;
6381
+ setTimeout(function () {
6382
+ if (hasTables(markupBefore)) return;
6168
6383
 
6169
- if (isBeforeTable) {
6170
- if (event.key === 'Enter') {
6171
- var above = getAbove(editor, {
6172
- match: {
6173
- type: BLOCKS.TABLE
6174
- }
6175
- });
6176
- if (!above) return;
6177
- var tablePath = above[1];
6178
- insertEmptyParagraph(editor, {
6179
- at: tablePath,
6180
- select: true
6384
+ if (hasTables(markupAfter)) {
6385
+ editor.tracking.onViewportAction('paste', {
6386
+ tablePasted: true,
6387
+ source: getPastingSource(data),
6388
+ hasHeadersOutsideFirstRow: hasHeadersOutsideFirstRow(markupAfter)
6181
6389
  });
6182
6390
  }
6391
+ }, 1);
6392
+ } else {
6393
+ insertData(data);
6394
+ }
6395
+ };
6396
+ }
6397
+ var withInvalidCellChildrenTracking = function withInvalidCellChildrenTracking(transformer) {
6398
+ return function (editor, childEntry) {
6399
+ var node = childEntry[0];
6183
6400
 
6184
- event.preventDefault();
6185
- event.stopPropagation();
6186
- return;
6187
- }
6188
- } // Pressing Tab on the last cell creates a new row
6189
- // Otherwise, jumping between cells is handled in the defaultKeyDownTable
6190
-
6191
-
6192
- if (event.key === 'Tab' && !event.shiftKey) {
6193
- event.preventDefault();
6194
- var res = getTableCellEntry(editor, {});
6195
-
6196
- if (res) {
6197
- var tableElement = res.tableElement,
6198
- tableRow = res.tableRow,
6199
- tableCell = res.tableCell;
6200
- var isLastCell = isLastChild(tableRow, tableCell[1]);
6201
- var isLastRow = isLastChild(tableElement, tableRow[1]);
6202
-
6203
- if (isLastRow && isLastCell) {
6204
- addRowBelow(editor); // skip default handler
6401
+ if (Element.isElement(node)) {
6402
+ var _editor$tracking;
6205
6403
 
6206
- return;
6207
- }
6208
- }
6404
+ (_editor$tracking = editor.tracking) == null ? void 0 : _editor$tracking.onViewportAction('invalidTablePaste', {
6405
+ nodeType: node.type
6406
+ });
6209
6407
  }
6210
6408
 
6211
- defaultHandler(event);
6409
+ return transformer(editor, childEntry);
6212
6410
  };
6213
6411
  };
6214
6412
 
@@ -6285,14 +6483,14 @@ var createTablePlugin = function createTablePlugin() {
6285
6483
  component: HeaderCell,
6286
6484
  normalizer: [{
6287
6485
  validChildren: CONTAINERS[BLOCKS.TABLE_HEADER_CELL],
6288
- transform: transformParagraphs
6486
+ transform: withInvalidCellChildrenTracking(transformParagraphs)
6289
6487
  }]
6290
6488
  }, _overrideByKey[ELEMENT_TD] = {
6291
6489
  type: BLOCKS.TABLE_CELL,
6292
6490
  component: Cell,
6293
6491
  normalizer: [{
6294
6492
  validChildren: CONTAINERS[BLOCKS.TABLE_CELL],
6295
- transform: transformParagraphs
6493
+ transform: withInvalidCellChildrenTracking(transformParagraphs)
6296
6494
  }]
6297
6495
  }, _overrideByKey)
6298
6496
  });
@@ -6440,193 +6638,6 @@ function deleteFirstEmptyParagraph(unit, editor, deleteFunction) {
6440
6638
  }
6441
6639
  }
6442
6640
 
6443
- var _extends2, _extends4, _inlines;
6444
- var inlines = /*#__PURE__*/Object.values(INLINES).map(function (type) {
6445
- return {
6446
- type: type
6447
- };
6448
- });
6449
- var schema = {
6450
- document: {
6451
- nodes: [{
6452
- types: /*#__PURE__*/TOP_LEVEL_BLOCKS.map(function (type) {
6453
- return {
6454
- type: type
6455
- };
6456
- })
6457
- }]
6458
- },
6459
- blocks: /*#__PURE__*/_extends((_extends2 = {}, _extends2[BLOCKS.PARAGRAPH] = {
6460
- nodes: [{
6461
- match: /*#__PURE__*/[].concat(inlines, [{
6462
- object: 'text'
6463
- }])
6464
- }]
6465
- }, _extends2[BLOCKS.HEADING_1] = {
6466
- nodes: [{
6467
- match: /*#__PURE__*/[].concat(inlines, [{
6468
- object: 'text'
6469
- }])
6470
- }]
6471
- }, _extends2[BLOCKS.HEADING_2] = {
6472
- nodes: [{
6473
- match: /*#__PURE__*/[].concat(inlines, [{
6474
- object: 'text'
6475
- }])
6476
- }]
6477
- }, _extends2[BLOCKS.HEADING_3] = {
6478
- nodes: [{
6479
- match: /*#__PURE__*/[].concat(inlines, [{
6480
- object: 'text'
6481
- }])
6482
- }]
6483
- }, _extends2[BLOCKS.HEADING_4] = {
6484
- nodes: [{
6485
- match: /*#__PURE__*/[].concat(inlines, [{
6486
- object: 'text'
6487
- }])
6488
- }]
6489
- }, _extends2[BLOCKS.HEADING_5] = {
6490
- nodes: [{
6491
- match: /*#__PURE__*/[].concat(inlines, [{
6492
- object: 'text'
6493
- }])
6494
- }]
6495
- }, _extends2[BLOCKS.HEADING_6] = {
6496
- nodes: [{
6497
- match: /*#__PURE__*/[].concat(inlines, [{
6498
- object: 'text'
6499
- }])
6500
- }]
6501
- }, _extends2), /*#__PURE__*/VOID_BLOCKS.reduce(function (blocks, nodeType) {
6502
- var _extends3;
6503
-
6504
- return _extends({}, blocks, (_extends3 = {}, _extends3[nodeType] = {
6505
- isVoid: true
6506
- }, _extends3));
6507
- }, {}), (_extends4 = {}, _extends4[BLOCKS.QUOTE] = {
6508
- nodes: [{
6509
- match: [/*#__PURE__*/CONTAINERS[BLOCKS.QUOTE].map(function (type) {
6510
- return {
6511
- type: type
6512
- };
6513
- })],
6514
- min: 1
6515
- }],
6516
- normalize: function normalize(editor, error) {
6517
- if (error.code === 'child_type_invalid') {
6518
- return editor.unwrapBlockByKey(error.node.key, BLOCKS.QUOTE);
6519
- }
6520
- }
6521
- }, _extends4)),
6522
- inlines: (_inlines = {}, _inlines[INLINES.HYPERLINK] = {
6523
- nodes: [{
6524
- match: [{
6525
- object: 'text'
6526
- }]
6527
- }]
6528
- }, _inlines[INLINES.ENTRY_HYPERLINK] = {
6529
- nodes: [{
6530
- match: [{
6531
- object: 'text'
6532
- }]
6533
- }]
6534
- }, _inlines[INLINES.ASSET_HYPERLINK] = {
6535
- nodes: [{
6536
- match: [{
6537
- object: 'text'
6538
- }]
6539
- }]
6540
- }, _inlines[INLINES.EMBEDDED_ENTRY] = {
6541
- isVoid: true
6542
- }, _inlines)
6543
- };
6544
-
6545
- function getCharacterCount(editor) {
6546
- var document = toContentfulDocument({
6547
- document: editor.children,
6548
- schema: schema
6549
- });
6550
- return documentToPlainTextString(document).length;
6551
- }
6552
-
6553
- var actionOrigin = {
6554
- TOOLBAR: 'toolbar-icon',
6555
- SHORTCUT: 'shortcut',
6556
- VIEWPORT: 'viewport-interaction',
6557
- COMMAND_PALETTE: 'command-palette'
6558
- };
6559
- var createTrackingPlugin = function createTrackingPlugin(onAction) {
6560
- var trackingActions = {
6561
- onViewportAction: function onViewportAction(actionName, data) {
6562
- if (data === void 0) {
6563
- data = {};
6564
- }
6565
-
6566
- return onAction(actionName, _extends({
6567
- origin: actionOrigin.VIEWPORT
6568
- }, data));
6569
- },
6570
- onShortcutAction: function onShortcutAction(actionName, data) {
6571
- if (data === void 0) {
6572
- data = {};
6573
- }
6574
-
6575
- return onAction(actionName, _extends({
6576
- origin: actionOrigin.SHORTCUT
6577
- }, data));
6578
- },
6579
- onToolbarAction: function onToolbarAction(actionName, data) {
6580
- if (data === void 0) {
6581
- data = {};
6582
- }
6583
-
6584
- return onAction(actionName, _extends({
6585
- origin: actionOrigin.TOOLBAR
6586
- }, data));
6587
- },
6588
- onCommandPaletteAction: function onCommandPaletteAction(actionName, data) {
6589
- if (data === void 0) {
6590
- data = {};
6591
- }
6592
-
6593
- return onAction(actionName, _extends({
6594
- origin: actionOrigin.COMMAND_PALETTE
6595
- }, data));
6596
- }
6597
- };
6598
- return {
6599
- key: 'TrackingPlugin',
6600
- withOverrides: function withOverrides(editor) {
6601
- var insertData = editor.insertData;
6602
- editor.tracking = trackingActions;
6603
-
6604
- editor.insertData = function (data) {
6605
- var isCopyAndPaste = data.types.length !== 0;
6606
-
6607
- if (isCopyAndPaste) {
6608
- var _window$getSelection;
6609
-
6610
- var characterCountSelection = (_window$getSelection = window.getSelection()) == null ? void 0 : _window$getSelection.toString().length;
6611
- var characterCountBefore = getCharacterCount(editor);
6612
- setTimeout(function () {
6613
- var characterCountAfter = getCharacterCount(editor);
6614
- trackingActions.onShortcutAction('paste', {
6615
- characterCountAfter: characterCountAfter,
6616
- characterCountBefore: characterCountBefore,
6617
- characterCountSelection: characterCountSelection
6618
- });
6619
- });
6620
- }
6621
-
6622
- insertData(data);
6623
- };
6624
-
6625
- return editor;
6626
- }
6627
- };
6628
- };
6629
-
6630
6641
  var createTrailingParagraphPlugin = function createTrailingParagraphPlugin() {
6631
6642
  return createTrailingBlockPlugin({
6632
6643
  options: {