@dialpad/dialtone 9.34.4 → 9.34.5

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 (68) hide show
  1. package/dist/css/dialtone.css +2 -2
  2. package/dist/tokens/css/variables-dark.css +1 -1
  3. package/dist/tokens/css/variables-expressive-dark.css +1 -1
  4. package/dist/tokens/css/variables-expressive-light.css +1 -1
  5. package/dist/tokens/css/variables-expressive-sm-dark.css +1 -1
  6. package/dist/tokens/css/variables-expressive-sm-light.css +1 -1
  7. package/dist/tokens/css/variables-light.css +1 -1
  8. package/dist/tokens/css/variables-tmo-dark.css +1 -1
  9. package/dist/tokens/css/variables-tmo-light.css +1 -1
  10. package/dist/tokens/less/variables-dark.less +1 -1
  11. package/dist/tokens/less/variables-expressive-dark.less +1 -1
  12. package/dist/tokens/less/variables-expressive-light.less +1 -1
  13. package/dist/tokens/less/variables-expressive-sm-dark.less +1 -1
  14. package/dist/tokens/less/variables-expressive-sm-light.less +1 -1
  15. package/dist/tokens/less/variables-light.less +1 -1
  16. package/dist/tokens/less/variables-tmo-dark.less +1 -1
  17. package/dist/tokens/less/variables-tmo-light.less +1 -1
  18. package/dist/vue2/common/emoji.cjs +4 -1
  19. package/dist/vue2/common/emoji.cjs.map +1 -1
  20. package/dist/vue2/common/emoji.js +4 -1
  21. package/dist/vue2/common/emoji.js.map +1 -1
  22. package/dist/vue2/dialtone-vue.cjs +1 -0
  23. package/dist/vue2/dialtone-vue.cjs.map +1 -1
  24. package/dist/vue2/dialtone-vue.js +2 -1
  25. package/dist/vue2/lib/rich-text-editor.cjs +22 -9
  26. package/dist/vue2/lib/rich-text-editor.cjs.map +1 -1
  27. package/dist/vue2/lib/rich-text-editor.js +22 -9
  28. package/dist/vue2/lib/rich-text-editor.js.map +1 -1
  29. package/dist/vue2/types/common/emoji/index.d.ts +11 -2
  30. package/dist/vue2/types/common/emoji/index.d.ts.map +1 -1
  31. package/dist/vue2/types/components/rich_text_editor/extensions/emoji/emoji.d.ts +0 -1
  32. package/dist/vue2/types/components/rich_text_editor/extensions/emoji/emoji.d.ts.map +1 -1
  33. package/dist/vue2/types/components/rich_text_editor/rich_text_editor.vue.d.ts +1 -1
  34. package/dist/vue2/types/components/rich_text_editor/rich_text_editor.vue.d.ts.map +1 -1
  35. package/dist/vue3/common/emoji.cjs +4 -1
  36. package/dist/vue3/common/emoji.cjs.map +1 -1
  37. package/dist/vue3/common/emoji.js +4 -1
  38. package/dist/vue3/common/emoji.js.map +1 -1
  39. package/dist/vue3/dialtone-vue.cjs +1 -0
  40. package/dist/vue3/dialtone-vue.cjs.map +1 -1
  41. package/dist/vue3/dialtone-vue.js +2 -1
  42. package/dist/vue3/lib/message-input.cjs +32 -3
  43. package/dist/vue3/lib/message-input.cjs.map +1 -1
  44. package/dist/vue3/lib/message-input.js +32 -3
  45. package/dist/vue3/lib/message-input.js.map +1 -1
  46. package/dist/vue3/lib/rich-text-editor.cjs +271 -35
  47. package/dist/vue3/lib/rich-text-editor.cjs.map +1 -1
  48. package/dist/vue3/lib/rich-text-editor.js +272 -36
  49. package/dist/vue3/lib/rich-text-editor.js.map +1 -1
  50. package/dist/vue3/types/common/emoji/index.d.ts +1 -0
  51. package/dist/vue3/types/common/emoji/index.d.ts.map +1 -1
  52. package/dist/vue3/types/components/rich_text_editor/extensions/emoji/emoji.d.ts +0 -1
  53. package/dist/vue3/types/components/rich_text_editor/extensions/emoji/emoji.d.ts.map +1 -1
  54. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/SlashCommandComponent.vue.d.ts +73 -0
  55. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/SlashCommandComponent.vue.d.ts.map +1 -0
  56. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/SlashCommandSuggestion.vue.d.ts +17 -0
  57. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/SlashCommandSuggestion.vue.d.ts.map +1 -0
  58. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/slash_command.d.ts +2 -0
  59. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/slash_command.d.ts.map +1 -0
  60. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/suggestion.d.ts +12 -0
  61. package/dist/vue3/types/components/rich_text_editor/extensions/slash_command/suggestion.d.ts.map +1 -0
  62. package/dist/vue3/types/components/rich_text_editor/rich_text_editor.vue.d.ts +38 -1
  63. package/dist/vue3/types/components/rich_text_editor/rich_text_editor.vue.d.ts.map +1 -1
  64. package/dist/vue3/types/components/rich_text_editor/slash_command_suggestion.d.ts +15 -0
  65. package/dist/vue3/types/components/rich_text_editor/slash_command_suggestion.d.ts.map +1 -0
  66. package/dist/vue3/types/recipes/conversation_view/message_input/message_input.vue.d.ts +38 -1
  67. package/dist/vue3/types/recipes/conversation_view/message_input/message_input.vue.d.ts.map +1 -1
  68. package/package.json +1 -1
@@ -46,7 +46,7 @@ require("../chunks/stack_constants-SMzMWnAQ.js");
46
46
  require("../common/constants.cjs");
47
47
  require("../chunks/link_constants-Huj7D_hm.js");
48
48
  require("./presence.cjs");
49
- const _sfc_main$7 = {
49
+ const _sfc_main$9 = {
50
50
  name: "EmojiComponent",
51
51
  components: {
52
52
  NodeViewWrapper: vue3.NodeViewWrapper,
@@ -54,7 +54,7 @@ const _sfc_main$7 = {
54
54
  },
55
55
  props: vue3.nodeViewProps
56
56
  };
57
- function _sfc_render$7(_ctx, _cache, $props, $setup, $data, $options) {
57
+ function _sfc_render$9(_ctx, _cache, $props, $setup, $data, $options) {
58
58
  const _component_dt_emoji = vue.resolveComponent("dt-emoji");
59
59
  const _component_node_view_wrapper = vue.resolveComponent("node-view-wrapper");
60
60
  return vue.openBlock(), vue.createBlock(_component_node_view_wrapper, { class: "d-d-inline-block d-va-bottom d-lh0" }, {
@@ -67,8 +67,8 @@ function _sfc_render$7(_ctx, _cache, $props, $setup, $data, $options) {
67
67
  _: 1
68
68
  });
69
69
  }
70
- const EmojiComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$7, [["render", _sfc_render$7]]);
71
- const _sfc_main$6 = {
70
+ const EmojiComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$9, [["render", _sfc_render$9]]);
71
+ const _sfc_main$8 = {
72
72
  name: "SuggestionList",
73
73
  components: {
74
74
  DtListItem: lib_listItem.DtListItem
@@ -151,19 +151,22 @@ const _sfc_main$6 = {
151
151
  case "channel":
152
152
  this.command({ name: item.name, id: item.id });
153
153
  break;
154
+ case "slash-command":
155
+ this.command({ command: item.command });
156
+ break;
154
157
  }
155
158
  }
156
159
  }
157
160
  };
158
- const _hoisted_1 = { class: "d-popover__dialog" };
159
- const _hoisted_2 = {
161
+ const _hoisted_1$1 = { class: "d-popover__dialog" };
162
+ const _hoisted_2$1 = {
160
163
  ref: "suggestionList",
161
164
  class: "dt-suggestion-list"
162
165
  };
163
- function _sfc_render$6(_ctx, _cache, $props, $setup, $data, $options) {
166
+ function _sfc_render$8(_ctx, _cache, $props, $setup, $data, $options) {
164
167
  const _component_dt_list_item = vue.resolveComponent("dt-list-item");
165
- return vue.openBlock(), vue.createElementBlock("div", _hoisted_1, [
166
- vue.withDirectives(vue.createElementVNode("ul", _hoisted_2, [
168
+ return vue.openBlock(), vue.createElementBlock("div", _hoisted_1$1, [
169
+ vue.withDirectives(vue.createElementVNode("ul", _hoisted_2$1, [
167
170
  (vue.openBlock(true), vue.createElementBlock(vue.Fragment, null, vue.renderList($props.items, (item, index) => {
168
171
  return vue.openBlock(), vue.createBlock(_component_dt_list_item, {
169
172
  key: item.id,
@@ -186,8 +189,8 @@ function _sfc_render$6(_ctx, _cache, $props, $setup, $data, $options) {
186
189
  ])
187
190
  ]);
188
191
  }
189
- const SuggestionList = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$6, [["render", _sfc_render$6]]);
190
- const _sfc_main$5 = {
192
+ const SuggestionList = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$8, [["render", _sfc_render$8]]);
193
+ const _sfc_main$7 = {
191
194
  name: "EmojiSuggestion",
192
195
  components: {
193
196
  DtEmoji: lib_emoji.DtEmoji,
@@ -200,7 +203,7 @@ const _sfc_main$5 = {
200
203
  }
201
204
  }
202
205
  };
203
- function _sfc_render$5(_ctx, _cache, $props, $setup, $data, $options) {
206
+ function _sfc_render$7(_ctx, _cache, $props, $setup, $data, $options) {
204
207
  const _component_dt_emoji = vue.resolveComponent("dt-emoji");
205
208
  const _component_dt_stack = vue.resolveComponent("dt-stack");
206
209
  return vue.openBlock(), vue.createBlock(_component_dt_stack, {
@@ -217,7 +220,7 @@ function _sfc_render$5(_ctx, _cache, $props, $setup, $data, $options) {
217
220
  _: 1
218
221
  });
219
222
  }
220
- const EmojiSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$5, [["render", _sfc_render$5]]);
223
+ const EmojiSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$7, [["render", _sfc_render$7]]);
221
224
  const suggestionOptions = {
222
225
  items: ({ query }) => {
223
226
  if (query.length < 2) {
@@ -306,21 +309,21 @@ const suggestionOptions = {
306
309
  }
307
310
  };
308
311
  const EmojiPluginKey = new state.PluginKey("emoji");
309
- const inputShortCodeRegex = /:\w+:$/;
310
- const emojiShortCodeRegex = /:\w+:/g;
312
+ const inputShortCodeRegex = new RegExp("(^| |(?<=:))(:\\w+:)$");
311
313
  const inputUnicodeRegex = /(\u00a9|\u00ae|[\u2000-\u3300]|\ud83c[\ud000-\udfff]|\ud83d[\ud000-\udfff]|\ud83e[\ud000-\udfff])$/;
312
314
  const pasteUnicodeRegex = /(\u00a9|\u00ae|[\u2000-\u3300]|\ud83c[\ud000-\udfff]|\ud83d[\ud000-\udfff]|\ud83e[\ud000-\udfff])/g;
313
315
  const inputRuleMatch = (match) => {
314
316
  if (match && common_emoji.codeToEmojiData(match[0])) {
317
+ const text = match[2] || match[0];
315
318
  return {
316
319
  index: match.index,
317
- text: match[0],
320
+ text,
318
321
  match
319
322
  };
320
323
  }
321
324
  };
322
325
  const shortCodePasteMatch = (text) => {
323
- const matches = [...text.matchAll(emojiShortCodeRegex)];
326
+ const matches = [...text.matchAll(common_emoji.emojiShortCodeRegex)];
324
327
  return matches.filter((match) => common_emoji.codeToEmojiData(match[0])).map((match) => ({
325
328
  index: match.index,
326
329
  text: match[0],
@@ -373,6 +376,8 @@ const Emoji = core.Node.create({
373
376
  core.nodeInputRule({
374
377
  find: (text) => {
375
378
  const match = text.match(inputShortCodeRegex);
379
+ if (!match)
380
+ return;
376
381
  return inputRuleMatch(match);
377
382
  },
378
383
  type: this.type,
@@ -385,6 +390,8 @@ const Emoji = core.Node.create({
385
390
  core.nodeInputRule({
386
391
  find: (text) => {
387
392
  const match = text.match(inputUnicodeRegex);
393
+ if (!match)
394
+ return;
388
395
  return inputRuleMatch(match);
389
396
  },
390
397
  type: this.type,
@@ -592,7 +599,7 @@ const Link = core.Mark.create({
592
599
  ];
593
600
  }
594
601
  });
595
- const _sfc_main$4 = {
602
+ const _sfc_main$6 = {
596
603
  name: "MentionComponent",
597
604
  components: {
598
605
  NodeViewWrapper: vue3.NodeViewWrapper,
@@ -605,7 +612,7 @@ const _sfc_main$4 = {
605
612
  }
606
613
  }
607
614
  };
608
- function _sfc_render$4(_ctx, _cache, $props, $setup, $data, $options) {
615
+ function _sfc_render$6(_ctx, _cache, $props, $setup, $data, $options) {
609
616
  const _component_dt_link = vue.resolveComponent("dt-link");
610
617
  const _component_node_view_wrapper = vue.resolveComponent("node-view-wrapper");
611
618
  return vue.openBlock(), vue.createBlock(_component_node_view_wrapper, { class: "d-d-inline-block" }, {
@@ -620,7 +627,7 @@ function _sfc_render$4(_ctx, _cache, $props, $setup, $data, $options) {
620
627
  _: 1
621
628
  });
622
629
  }
623
- const MentionComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$4, [["render", _sfc_render$4]]);
630
+ const MentionComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$6, [["render", _sfc_render$6]]);
624
631
  const mentionRegex = /@([\w.-]+)[^\w.-]?/g;
625
632
  const mentionPasteMatch = (text, suggestions) => {
626
633
  const matches = [...text.matchAll(mentionRegex)];
@@ -707,7 +714,7 @@ const MentionPlugin = Mention.extend({
707
714
  pluginKey: new state.PluginKey("mentionSuggestion")
708
715
  }
709
716
  });
710
- const _sfc_main$3 = {
717
+ const _sfc_main$5 = {
711
718
  name: "ChannelComponent",
712
719
  components: {
713
720
  NodeViewWrapper: vue3.NodeViewWrapper,
@@ -720,7 +727,7 @@ const _sfc_main$3 = {
720
727
  }
721
728
  }
722
729
  };
723
- function _sfc_render$3(_ctx, _cache, $props, $setup, $data, $options) {
730
+ function _sfc_render$5(_ctx, _cache, $props, $setup, $data, $options) {
724
731
  const _component_dt_link = vue.resolveComponent("dt-link");
725
732
  const _component_node_view_wrapper = vue.resolveComponent("node-view-wrapper");
726
733
  return vue.openBlock(), vue.createBlock(_component_node_view_wrapper, { class: "d-d-inline-block" }, {
@@ -735,7 +742,7 @@ function _sfc_render$3(_ctx, _cache, $props, $setup, $data, $options) {
735
742
  _: 1
736
743
  });
737
744
  }
738
- const ChannelComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$3, [["render", _sfc_render$3]]);
745
+ const ChannelComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$5, [["render", _sfc_render$5]]);
739
746
  const channelRegex = /#([\w-]+)[^\w-]?/g;
740
747
  const channelPasteMatch = (text, suggestions) => {
741
748
  const matches = [...text.matchAll(channelRegex)];
@@ -825,6 +832,112 @@ const ChannelPlugin = Mention.extend({
825
832
  pluginKey: new state.PluginKey("channelSuggestion")
826
833
  }
827
834
  });
835
+ const _sfc_main$4 = {
836
+ name: "SlashCommandsComponent",
837
+ components: {
838
+ NodeViewWrapper: vue3.NodeViewWrapper
839
+ },
840
+ props: vue3.nodeViewProps,
841
+ emits: ["selected-command"],
842
+ computed: {
843
+ text() {
844
+ return "/" + this.$props.node.attrs.command;
845
+ }
846
+ },
847
+ created() {
848
+ this.$parent.$emit("selected-command", this.$props.node.attrs.command);
849
+ }
850
+ };
851
+ function _sfc_render$4(_ctx, _cache, $props, $setup, $data, $options) {
852
+ const _component_node_view_wrapper = vue.resolveComponent("node-view-wrapper");
853
+ return vue.openBlock(), vue.createBlock(_component_node_view_wrapper, { class: "d-d-inline-block" }, {
854
+ default: vue.withCtx(() => [
855
+ vue.createTextVNode(vue.toDisplayString($options.text), 1)
856
+ ]),
857
+ _: 1
858
+ });
859
+ }
860
+ const SlashCommandComponent = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$4, [["render", _sfc_render$4]]);
861
+ const slashCommandPasteMatch = (text, slashCommandRegex) => {
862
+ const matches = [...text.matchAll(slashCommandRegex)];
863
+ return matches.map((match) => {
864
+ let slashCommand = match[2];
865
+ if (!slashCommand.endsWith(" "))
866
+ slashCommand += " ";
867
+ return {
868
+ index: match.index,
869
+ text: slashCommand,
870
+ match
871
+ };
872
+ });
873
+ };
874
+ const SlashCommandPlugin = Mention.extend({
875
+ name: "slash-commands",
876
+ group: "inline",
877
+ inline: true,
878
+ addNodeView() {
879
+ return vue3.VueNodeViewRenderer(SlashCommandComponent);
880
+ },
881
+ parseHTML() {
882
+ return [
883
+ {
884
+ tag: "command-component"
885
+ }
886
+ ];
887
+ },
888
+ addAttributes() {
889
+ return {
890
+ command: {
891
+ default: ""
892
+ },
893
+ parametersExample: {
894
+ default: ""
895
+ },
896
+ description: {
897
+ default: ""
898
+ }
899
+ };
900
+ },
901
+ renderText({ node }) {
902
+ return `/${node.attrs.command}`;
903
+ },
904
+ renderHTML({ HTMLAttributes }) {
905
+ return ["command-component", core.mergeAttributes(this.options.HTMLAttributes, HTMLAttributes)];
906
+ },
907
+ addInputRules() {
908
+ var _a;
909
+ const suggestions = (_a = this.options.suggestion) == null ? void 0 : _a.items({ query: "" }).map((suggestion) => suggestion.command);
910
+ const slashCommandRegex = new RegExp(`^((?:\\/)(${suggestions.join("|")})) $`);
911
+ return [
912
+ core.nodeInputRule({
913
+ find: slashCommandRegex,
914
+ type: this.type,
915
+ getAttributes(attrs) {
916
+ return { command: attrs[2] };
917
+ }
918
+ })
919
+ ];
920
+ },
921
+ addPasteRules() {
922
+ var _a;
923
+ const suggestions = (_a = this.options.suggestion) == null ? void 0 : _a.items({ query: "" }).map((suggestion) => suggestion.command);
924
+ const slashCommandRegex = new RegExp(`^((?:\\/)(${suggestions.join("|")})) ?$`, "g");
925
+ return [
926
+ core.nodePasteRule({
927
+ find: (text) => slashCommandPasteMatch(text, slashCommandRegex),
928
+ type: this.type,
929
+ getAttributes(attrs) {
930
+ return { command: attrs[0].trim() };
931
+ }
932
+ })
933
+ ];
934
+ }
935
+ }).configure({
936
+ suggestion: {
937
+ char: "/",
938
+ pluginKey: new state.PluginKey("slashCommandSuggestion")
939
+ }
940
+ });
828
941
  const RICH_TEXT_EDITOR_OUTPUT_FORMATS = [
829
942
  "text",
830
943
  "json",
@@ -843,7 +956,7 @@ const RICH_TEXT_EDITOR_SUPPORTED_LINK_PROTOCOLS = [
843
956
  "sftp",
844
957
  "mailto"
845
958
  ];
846
- const _sfc_main$2 = {
959
+ const _sfc_main$3 = {
847
960
  name: "MentionSuggestion",
848
961
  components: {
849
962
  DtAvatar: lib_avatar.DtAvatar,
@@ -864,7 +977,7 @@ const _sfc_main$2 = {
864
977
  }
865
978
  }
866
979
  };
867
- function _sfc_render$2(_ctx, _cache, $props, $setup, $data, $options) {
980
+ function _sfc_render$3(_ctx, _cache, $props, $setup, $data, $options) {
868
981
  const _component_dt_avatar = vue.resolveComponent("dt-avatar");
869
982
  const _component_dt_stack = vue.resolveComponent("dt-stack");
870
983
  return vue.openBlock(), vue.createBlock(_component_dt_stack, {
@@ -883,7 +996,7 @@ function _sfc_render$2(_ctx, _cache, $props, $setup, $data, $options) {
883
996
  _: 1
884
997
  });
885
998
  }
886
- const MentionSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$2, [["render", _sfc_render$2]]);
999
+ const MentionSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$3, [["render", _sfc_render$3]]);
887
1000
  const mentionSuggestion = {
888
1001
  // This function comes from the user and passed to the editor directly.
889
1002
  // This will also activate the mention plugin on the editor
@@ -938,7 +1051,7 @@ const mentionSuggestion = {
938
1051
  };
939
1052
  }
940
1053
  };
941
- const _sfc_main$1 = {
1054
+ const _sfc_main$2 = {
942
1055
  name: "ChannelSuggestion",
943
1056
  components: {
944
1057
  DtStack: lib_stack.DtStack,
@@ -957,7 +1070,7 @@ const _sfc_main$1 = {
957
1070
  }
958
1071
  }
959
1072
  };
960
- function _sfc_render$1(_ctx, _cache, $props, $setup, $data, $options) {
1073
+ function _sfc_render$2(_ctx, _cache, $props, $setup, $data, $options) {
961
1074
  const _component_dt_icon_hash = vue.resolveComponent("dt-icon-hash");
962
1075
  const _component_dt_icon_lock = vue.resolveComponent("dt-icon-lock");
963
1076
  const _component_dt_stack = vue.resolveComponent("dt-stack");
@@ -978,7 +1091,7 @@ function _sfc_render$1(_ctx, _cache, $props, $setup, $data, $options) {
978
1091
  _: 1
979
1092
  });
980
1093
  }
981
- const ChannelSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$1, [["render", _sfc_render$1]]);
1094
+ const ChannelSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$2, [["render", _sfc_render$2]]);
982
1095
  const channelSuggestion = {
983
1096
  // This function comes from the user and passed to the editor directly.
984
1097
  // This will also activate the mention plugin on the editor
@@ -1033,6 +1146,95 @@ const channelSuggestion = {
1033
1146
  };
1034
1147
  }
1035
1148
  };
1149
+ const _sfc_main$1 = {
1150
+ name: "SlashCommandSuggestion",
1151
+ props: {
1152
+ item: {
1153
+ type: Object,
1154
+ required: true
1155
+ }
1156
+ },
1157
+ computed: {
1158
+ command() {
1159
+ return this.item.command;
1160
+ },
1161
+ description() {
1162
+ return this.item.description;
1163
+ },
1164
+ parametersExample() {
1165
+ return this.item.parametersExample;
1166
+ }
1167
+ }
1168
+ };
1169
+ const _hoisted_1 = { class: "d-body--md-compact" };
1170
+ const _hoisted_2 = { key: 0 };
1171
+ const _hoisted_3 = { class: "d-body--sm" };
1172
+ function _sfc_render$1(_ctx, _cache, $props, $setup, $data, $options) {
1173
+ return vue.openBlock(), vue.createElementBlock("div", null, [
1174
+ vue.createElementVNode("div", _hoisted_1, [
1175
+ vue.createElementVNode("span", null, "/" + vue.toDisplayString($options.command), 1),
1176
+ $options.parametersExample ? (vue.openBlock(), vue.createElementBlock("span", _hoisted_2, vue.toDisplayString($options.parametersExample), 1)) : vue.createCommentVNode("", true)
1177
+ ]),
1178
+ vue.createElementVNode("div", _hoisted_3, vue.toDisplayString($options.description), 1)
1179
+ ]);
1180
+ }
1181
+ const SlashCommandSuggestion = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main$1, [["render", _sfc_render$1]]);
1182
+ const slashCommandSuggestion = {
1183
+ // This function comes from the user and passed to the editor directly.
1184
+ // This will also activate the mention plugin on the editor
1185
+ // items: ({ query }) => { return [] },
1186
+ allowSpaces: true,
1187
+ startOfLine: true,
1188
+ render: () => {
1189
+ let component;
1190
+ let popup;
1191
+ return {
1192
+ onStart: (props) => {
1193
+ component = new vue3.VueRenderer(SuggestionList, {
1194
+ parent: void 0,
1195
+ props: {
1196
+ itemComponent: vue.markRaw(SlashCommandSuggestion),
1197
+ itemType: "slash-command",
1198
+ ...props
1199
+ },
1200
+ editor: props.editor
1201
+ });
1202
+ if (!props.clientRect) {
1203
+ return;
1204
+ }
1205
+ popup = tippy("body", {
1206
+ getReferenceClientRect: props.clientRect,
1207
+ appendTo: () => document.body,
1208
+ content: component.element,
1209
+ showOnCreate: true,
1210
+ interactive: true,
1211
+ trigger: "manual",
1212
+ placement: "top-start"
1213
+ });
1214
+ },
1215
+ onUpdate(props) {
1216
+ component.updateProps(props);
1217
+ if (!props.clientRect) {
1218
+ return;
1219
+ }
1220
+ popup[0].setProps({
1221
+ getReferenceClientRect: props.clientRect
1222
+ });
1223
+ },
1224
+ onKeyDown(props) {
1225
+ if (props.event.key === "Escape") {
1226
+ popup[0].hide();
1227
+ return true;
1228
+ }
1229
+ return component == null ? void 0 : component.ref.onKeyDown(props);
1230
+ },
1231
+ onExit() {
1232
+ popup[0].destroy();
1233
+ component.destroy();
1234
+ }
1235
+ };
1236
+ }
1237
+ };
1036
1238
  const _sfc_main = {
1037
1239
  name: "DtRichTextEditor",
1038
1240
  components: {
@@ -1155,6 +1357,23 @@ const _sfc_main = {
1155
1357
  type: Object,
1156
1358
  default: null
1157
1359
  },
1360
+ /**
1361
+ * suggestion object containing the items query function.
1362
+ * The valid keys passed into this object can be found here: https://tiptap.dev/api/utilities/suggestion
1363
+ *
1364
+ * The only required key is the items function which is used to query the slash commands for suggestion.
1365
+ * items({ query }) => { return [SlashCommandObject]; }
1366
+ * SlashCommandObject format:
1367
+ * { command: string, description: string, parametersExample?: string }
1368
+ * The "parametersExample" parameter is optional, and describes an example
1369
+ * of the parameters that command can take.
1370
+ *
1371
+ * When null, it does not add the plugin.
1372
+ */
1373
+ slashCommandSuggestion: {
1374
+ type: Object,
1375
+ default: null
1376
+ },
1158
1377
  /**
1159
1378
  * Whether the input allows for block quote.
1160
1379
  */
@@ -1222,7 +1441,14 @@ const _sfc_main = {
1222
1441
  * @event focus
1223
1442
  * @type {FocusEvent}
1224
1443
  */
1225
- "focus"
1444
+ "focus",
1445
+ /**
1446
+ * Fires when a slash command is selected
1447
+ *
1448
+ * @event selected-command
1449
+ * @type {String}
1450
+ */
1451
+ "selected-command"
1226
1452
  ],
1227
1453
  data() {
1228
1454
  return {
@@ -1292,6 +1518,10 @@ const _sfc_main = {
1292
1518
  const suggestionObject = { ...this.channelSuggestion, ...channelSuggestion };
1293
1519
  extensions.push(ChannelPlugin.configure({ suggestion: suggestionObject }));
1294
1520
  }
1521
+ if (this.slashCommandSuggestion) {
1522
+ const suggestionObject = { ...this.slashCommandSuggestion, ...slashCommandSuggestion };
1523
+ extensions.push(SlashCommandPlugin.configure({ suggestion: suggestionObject }));
1524
+ }
1295
1525
  extensions.push(Emoji);
1296
1526
  extensions.push(TextAlign.configure({
1297
1527
  types: ["paragraph"],
@@ -1356,6 +1586,9 @@ const _sfc_main = {
1356
1586
  this.destroyEditor();
1357
1587
  },
1358
1588
  methods: {
1589
+ onSelectedCommand(command) {
1590
+ this.$emit("selected-command", command);
1591
+ },
1359
1592
  createEditor() {
1360
1593
  this.editor = new vue3.Editor({
1361
1594
  autofocus: this.autoFocus,
@@ -1384,14 +1617,16 @@ const _sfc_main = {
1384
1617
  this.editor.commands.setContent(this.internalValue, true);
1385
1618
  },
1386
1619
  parseEmojis() {
1387
- const matches = [...this.modelValue.matchAll(emojiRegex()), ...this.modelValue.matchAll(emojiShortCodeRegex)];
1620
+ const matches = new Set(
1621
+ [...this.modelValue.matchAll(emojiRegex()), ...this.modelValue.matchAll(common_emoji.emojiShortCodeRegex)].map((match) => match[0].trim())
1622
+ );
1388
1623
  if (!matches)
1389
1624
  return;
1390
1625
  matches.forEach((match) => {
1391
- const emoji = common_emoji.codeToEmojiData(match[0]);
1626
+ const emoji = common_emoji.codeToEmojiData(match);
1392
1627
  if (!emoji)
1393
1628
  return;
1394
- this.internalValue = this.internalValue.replace(new RegExp(` ${match[0]}`), ` <emoji-component code="${emoji.shortname}"></emoji-component>`);
1629
+ this.internalValue = this.internalValue.replace(new RegExp(`${match}`, "g"), `<emoji-component code="${emoji.shortname}"></emoji-component>`);
1395
1630
  });
1396
1631
  },
1397
1632
  parseChannels() {
@@ -1475,8 +1710,9 @@ function _sfc_render(_ctx, _cache, $props, $setup, $data, $options) {
1475
1710
  return vue.openBlock(), vue.createBlock(_component_editor_content, {
1476
1711
  editor: $data.editor,
1477
1712
  "data-qa": "dt-rich-text-editor",
1478
- class: "dt-rich-text-editor"
1479
- }, null, 8, ["editor"]);
1713
+ class: "dt-rich-text-editor",
1714
+ onSelectedCommand: $options.onSelectedCommand
1715
+ }, null, 8, ["editor", "onSelectedCommand"]);
1480
1716
  }
1481
1717
  const DtRichTextEditor = /* @__PURE__ */ _pluginVue_exportHelper._export_sfc(_sfc_main, [["render", _sfc_render]]);
1482
1718
  exports.DtRichTextEditor = DtRichTextEditor;