@king-design/vue 3.8.0-beta.0 → 3.8.0-beta.2

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 (54) hide show
  1. package/__tests__/__snapshots__/Vue Next Demos.md +74 -74
  2. package/components/bubble/bubble.d.ts +3 -0
  3. package/components/bubble/bubble.vdt.js +6 -2
  4. package/components/bubble/index.spec.js +231 -5
  5. package/components/bubble/styles.js +1 -1
  6. package/components/bubble/useBubbleDisplay.d.ts +1 -0
  7. package/components/bubble/useBubbleDisplay.js +68 -22
  8. package/components/bubbleList/bubbleList.vdt.js +3 -1
  9. package/components/bubbleList/index.spec.js +378 -237
  10. package/components/bubbleList/styles.js +2 -2
  11. package/components/bubbleList/useBubbleList.js +7 -0
  12. package/components/fileCard/fileCard.vdt.js +4 -4
  13. package/components/fileCard/index.spec.js +179 -107
  14. package/components/fileCard/list.d.ts +2 -1
  15. package/components/fileCard/list.vdt.js +7 -5
  16. package/components/fileCard/styles.js +10 -8
  17. package/components/fileCard/useFileCard.d.ts +1 -1
  18. package/components/fileCard/useFileCard.js +6 -35
  19. package/components/media/index.spec.js +774 -585
  20. package/components/media/media.vdt.js +17 -6
  21. package/components/media/mediaAssets.d.ts +2 -0
  22. package/components/media/mediaAssets.js +4 -0
  23. package/components/media/styles.js +5 -3
  24. package/components/media/useMedia.d.ts +6 -2
  25. package/components/media/useMedia.js +28 -6
  26. package/components/sender/index.spec.js +1146 -476
  27. package/components/sender/sender.d.ts +28 -5
  28. package/components/sender/sender.js +17 -6
  29. package/components/sender/sender.vdt.js +121 -49
  30. package/components/sender/styles.js +18 -9
  31. package/components/sender/useAutoResize.js +7 -6
  32. package/components/sender/useSenderDrag.js +12 -3
  33. package/components/sender/useSenderInput.d.ts +3 -0
  34. package/components/sender/useSenderInput.js +20 -3
  35. package/components/sender/useSenderPaste.js +1 -1
  36. package/components/sender/useSenderUpload.js +38 -29
  37. package/components/xmarkdown/index.spec.js +492 -263
  38. package/components/xmarkdown/markdown/streaming.js +41 -8
  39. package/components/xmarkdown/styles.js +2 -2
  40. package/components/xmarkdown/useXMarkdownDisplay.d.ts +1 -0
  41. package/components/xmarkdown/useXMarkdownDisplay.js +69 -24
  42. package/components/xmarkdown/xmarkdown.d.ts +3 -0
  43. package/components/xmarkdown/xmarkdown.vdt.js +6 -2
  44. package/dist/i18n/en-US.js +1 -0
  45. package/dist/i18n/en-US.js.map +1 -1
  46. package/dist/i18n/en-US.min.js +1 -1
  47. package/dist/index.js +795 -512
  48. package/dist/index.js.map +1 -1
  49. package/dist/index.min.js +2 -2
  50. package/i18n/en-US.d.ts +1 -0
  51. package/i18n/en-US.js +1 -0
  52. package/index.d.ts +2 -2
  53. package/index.js +2 -2
  54. package/package.json +1 -1
@@ -75,13 +75,17 @@ describe('Bubble', function () {
75
75
  Demo.template = "\n const { Bubble } = this;\n <div>\n <Bubble shape=\"corner\" placement=\"start\" content=\"left\" />\n <Bubble shape=\"corner\" placement=\"end\" content=\"right\" />\n <Bubble shape=\"corner\" placement=\"middle\" content=\"center\" />\n </div>\n ";
76
76
  _mount2 = mount(Demo), element = _mount2[1];
77
77
  contents = element.querySelectorAll('.k-bubble-content');
78
- expect(getComputedStyle(contents[0]).borderBottomLeftRadius).to.eql('0px');
79
- expect(getComputedStyle(contents[0]).borderBottomRightRadius).not.to.eql('0px');
80
- expect(getComputedStyle(contents[1]).borderBottomRightRadius).to.eql('0px');
81
- expect(getComputedStyle(contents[1]).borderBottomLeftRadius).not.to.eql('0px');
78
+ expect(getComputedStyle(contents[0]).borderTopLeftRadius).to.eql('0px');
79
+ expect(getComputedStyle(contents[0]).borderTopRightRadius).not.to.eql('0px');
80
+ expect(getComputedStyle(contents[0]).borderBottomLeftRadius).not.to.eql('0px');
81
+ expect(getComputedStyle(contents[1]).borderTopRightRadius).to.eql('0px');
82
+ expect(getComputedStyle(contents[1]).borderTopLeftRadius).not.to.eql('0px');
83
+ expect(getComputedStyle(contents[1]).borderBottomRightRadius).not.to.eql('0px');
84
+ expect(getComputedStyle(contents[2]).borderTopLeftRadius).to.eql('0px');
85
+ expect(getComputedStyle(contents[2]).borderTopRightRadius).to.eql('0px');
82
86
  expect(getComputedStyle(contents[2]).borderBottomLeftRadius).not.to.eql('0px');
83
87
  expect(getComputedStyle(contents[2]).borderBottomRightRadius).not.to.eql('0px');
84
- case 10:
88
+ case 14:
85
89
  case "end":
86
90
  return _context4.stop();
87
91
  }
@@ -768,4 +772,226 @@ describe('Bubble', function () {
768
772
  }
769
773
  }, _callee19);
770
774
  })));
775
+ it('should resume typing from previous rendered content after remount', /*#__PURE__*/_asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee20() {
776
+ var Demo, _mount20, element, text, nextText, i;
777
+ return _regeneratorRuntime.wrap(function _callee20$(_context40) {
778
+ while (1) switch (_context40.prev = _context40.next) {
779
+ case 0:
780
+ Demo = /*#__PURE__*/function (_Component20) {
781
+ _inheritsLoose(Demo, _Component20);
782
+ function Demo() {
783
+ var _context39;
784
+ var _this20;
785
+ for (var _len20 = arguments.length, args = new Array(_len20), _key20 = 0; _key20 < _len20; _key20++) {
786
+ args[_key20] = arguments[_key20];
787
+ }
788
+ _this20 = _Component20.call.apply(_Component20, _concatInstanceProperty(_context39 = [this]).call(_context39, args)) || this;
789
+ _this20.Bubble = Bubble;
790
+ return _this20;
791
+ }
792
+ return Demo;
793
+ }(Component);
794
+ Demo.template = "\n const { Bubble } = this;\n <div>\n <Bubble\n content=\"hello world\"\n streaming={true}\n typing={{interval: 16, step: 2, resumeFrom: 'hello'}}\n />\n </div>\n ";
795
+ _mount20 = mount(Demo), element = _mount20[1];
796
+ text = element.querySelector('.k-bubble-text').textContent || '';
797
+ expect(text).to.eql('hello');
798
+ nextText = text;
799
+ i = 0;
800
+ case 7:
801
+ if (!(i < 6)) {
802
+ _context40.next = 16;
803
+ break;
804
+ }
805
+ _context40.next = 10;
806
+ return wait(20);
807
+ case 10:
808
+ nextText = element.querySelector('.k-bubble-text').textContent || '';
809
+ if (!(nextText.length > text.length)) {
810
+ _context40.next = 13;
811
+ break;
812
+ }
813
+ return _context40.abrupt("break", 16);
814
+ case 13:
815
+ i++;
816
+ _context40.next = 7;
817
+ break;
818
+ case 16:
819
+ expect(_startsWithInstanceProperty(nextText).call(nextText, 'hello')).to.be.true;
820
+ expect(nextText.length).to.be.greaterThan(text.length);
821
+ case 18:
822
+ case "end":
823
+ return _context40.stop();
824
+ }
825
+ }, _callee20);
826
+ })));
827
+ it('should support content resume mode without replaying existing content', /*#__PURE__*/_asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee21() {
828
+ var Demo, _mount21, instance, element, text;
829
+ return _regeneratorRuntime.wrap(function _callee21$(_context42) {
830
+ while (1) switch (_context42.prev = _context42.next) {
831
+ case 0:
832
+ Demo = /*#__PURE__*/function (_Component21) {
833
+ _inheritsLoose(Demo, _Component21);
834
+ function Demo() {
835
+ var _context41;
836
+ var _this21;
837
+ for (var _len21 = arguments.length, args = new Array(_len21), _key21 = 0; _key21 < _len21; _key21++) {
838
+ args[_key21] = arguments[_key21];
839
+ }
840
+ _this21 = _Component21.call.apply(_Component21, _concatInstanceProperty(_context41 = [this]).call(_context41, args)) || this;
841
+ _this21.Bubble = Bubble;
842
+ return _this21;
843
+ }
844
+ Demo.defaults = function defaults() {
845
+ return {
846
+ content: 'already rendered'
847
+ };
848
+ };
849
+ return Demo;
850
+ }(Component);
851
+ Demo.template = "\n const { Bubble } = this;\n <div>\n <Bubble\n content={this.get('content')}\n streaming={true}\n typing={{interval: 16, step: 2, resumeFrom: 'content'}}\n />\n </div>\n ";
852
+ _mount21 = mount(Demo), instance = _mount21[0], element = _mount21[1];
853
+ expect(element.querySelector('.k-bubble-text').textContent).to.eql('already rendered');
854
+ instance.set('content', 'already rendered and more');
855
+ _context42.next = 7;
856
+ return wait(20);
857
+ case 7:
858
+ text = element.querySelector('.k-bubble-text').textContent || '';
859
+ expect(_startsWithInstanceProperty(text).call(text, 'already rendered')).to.be.true;
860
+ expect(text.length).to.be.lessThan('already rendered and more'.length);
861
+ case 10:
862
+ case "end":
863
+ return _context42.stop();
864
+ }
865
+ }, _callee21);
866
+ })));
867
+ it('should restart typing from empty when keepPrefix is false', /*#__PURE__*/_asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee22() {
868
+ var Demo, _mount22, instance, element, initialText, i, _element$querySelecto, text, _i2, _element$querySelecto2;
869
+ return _regeneratorRuntime.wrap(function _callee22$(_context44) {
870
+ while (1) switch (_context44.prev = _context44.next) {
871
+ case 0:
872
+ Demo = /*#__PURE__*/function (_Component22) {
873
+ _inheritsLoose(Demo, _Component22);
874
+ function Demo() {
875
+ var _context43;
876
+ var _this22;
877
+ for (var _len22 = arguments.length, args = new Array(_len22), _key22 = 0; _key22 < _len22; _key22++) {
878
+ args[_key22] = arguments[_key22];
879
+ }
880
+ _this22 = _Component22.call.apply(_Component22, _concatInstanceProperty(_context43 = [this]).call(_context43, args)) || this;
881
+ _this22.Bubble = Bubble;
882
+ return _this22;
883
+ }
884
+ Demo.defaults = function defaults() {
885
+ return {
886
+ content: 'hello world'
887
+ };
888
+ };
889
+ return Demo;
890
+ }(Component);
891
+ Demo.template = "\n const { Bubble } = this;\n <div>\n <Bubble\n content={this.get('content')}\n streaming={true}\n typing={{interval: 16, step: 2, keepPrefix: false}}\n />\n </div>\n ";
892
+ _mount22 = mount(Demo), instance = _mount22[0], element = _mount22[1];
893
+ initialText = '';
894
+ i = 0;
895
+ case 5:
896
+ if (!(i < 12)) {
897
+ _context44.next = 14;
898
+ break;
899
+ }
900
+ initialText = ((_element$querySelecto = element.querySelector('.k-bubble-text')) == null ? void 0 : _element$querySelecto.textContent) || '';
901
+ if (!_includesInstanceProperty(initialText).call(initialText, 'hello')) {
902
+ _context44.next = 9;
903
+ break;
904
+ }
905
+ return _context44.abrupt("break", 14);
906
+ case 9:
907
+ _context44.next = 11;
908
+ return wait(20);
909
+ case 11:
910
+ i++;
911
+ _context44.next = 5;
912
+ break;
913
+ case 14:
914
+ expect(initialText).to.contain('hello');
915
+ instance.set('content', 'hello there');
916
+ _context44.next = 18;
917
+ return wait();
918
+ case 18:
919
+ text = '';
920
+ _i2 = 0;
921
+ case 20:
922
+ if (!(_i2 < 6)) {
923
+ _context44.next = 29;
924
+ break;
925
+ }
926
+ _context44.next = 23;
927
+ return wait(20);
928
+ case 23:
929
+ text = ((_element$querySelecto2 = element.querySelector('.k-bubble-text')) == null ? void 0 : _element$querySelecto2.textContent) || '';
930
+ if (!text) {
931
+ _context44.next = 26;
932
+ break;
933
+ }
934
+ return _context44.abrupt("break", 29);
935
+ case 26:
936
+ _i2++;
937
+ _context44.next = 20;
938
+ break;
939
+ case 29:
940
+ expect(text).not.to.contain('hello');
941
+ expect(text.length).to.be.lessThan('hello'.length);
942
+ case 31:
943
+ case "end":
944
+ return _context44.stop();
945
+ }
946
+ }, _callee22);
947
+ })));
948
+ it('should render typing suffix only when enabled', /*#__PURE__*/_asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee23() {
949
+ var Demo, _mount23, element, i, enabledSuffix;
950
+ return _regeneratorRuntime.wrap(function _callee23$(_context46) {
951
+ while (1) switch (_context46.prev = _context46.next) {
952
+ case 0:
953
+ Demo = /*#__PURE__*/function (_Component23) {
954
+ _inheritsLoose(Demo, _Component23);
955
+ function Demo() {
956
+ var _context45;
957
+ var _this23;
958
+ for (var _len23 = arguments.length, args = new Array(_len23), _key23 = 0; _key23 < _len23; _key23++) {
959
+ args[_key23] = arguments[_key23];
960
+ }
961
+ _this23 = _Component23.call.apply(_Component23, _concatInstanceProperty(_context45 = [this]).call(_context45, args)) || this;
962
+ _this23.Bubble = Bubble;
963
+ return _this23;
964
+ }
965
+ return Demo;
966
+ }(Component);
967
+ Demo.template = "\n const { Bubble } = this;\n <div>\n <Bubble\n className=\"suffix-enabled\"\n content=\"hello\"\n typing={{interval: 16, step: 2, suffix: true}}\n streaming={true}\n />\n <Bubble\n className=\"suffix-default\"\n content=\"hello\"\n typing={{interval: 16, step: 2}}\n streaming={true}\n />\n </div>\n ";
968
+ _mount23 = mount(Demo), element = _mount23[1];
969
+ i = 0;
970
+ case 4:
971
+ if (!(i < 10)) {
972
+ _context46.next = 12;
973
+ break;
974
+ }
975
+ if (!element.querySelector('.suffix-enabled .k-bubble-typing-suffix')) {
976
+ _context46.next = 7;
977
+ break;
978
+ }
979
+ return _context46.abrupt("break", 12);
980
+ case 7:
981
+ _context46.next = 9;
982
+ return wait(20);
983
+ case 9:
984
+ i++;
985
+ _context46.next = 4;
986
+ break;
987
+ case 12:
988
+ enabledSuffix = element.querySelector('.suffix-enabled .k-bubble-typing-suffix');
989
+ expect(enabledSuffix.querySelectorAll('span').length).to.eql(3);
990
+ expect(element.querySelector('.suffix-default .k-bubble-typing-suffix')).to.eql(null);
991
+ case 15:
992
+ case "end":
993
+ return _context46.stop();
994
+ }
995
+ }, _callee23);
996
+ })));
771
997
  });
@@ -49,5 +49,5 @@ setDefault(function () {
49
49
  makeStyles == null || makeStyles.clearCache();
50
50
  });
51
51
  export var makeStyles = cache(function makeStyles(k) {
52
- return /*#__PURE__*/css("display:flex;flex-direction:column;align-items:flex-start;width:100%;.", k, "-bubble-main{display:flex;flex-direction:column;gap:8px;min-width:0;align-items:flex-start;}.", k, "-bubble-meta{display:flex;align-items:center;gap:8px;min-width:0;}.", k, "-bubble-header{color:", bubble.roleNameColor, ";font-size:14px;font-weight:500;min-width:0;text-align:left;}.", k, "-bubble-content{display:flex;flex-direction:column;gap:8px;min-width:0;max-width:100%;padding:", bubble.padding, ";box-sizing:border-box;line-height:1.6;word-break:break-word;overflow-wrap:anywhere;transition:background ", theme.transition.small, ",border-color ", theme.transition.small, ";}.", k, "-bubble-content>*{min-width:0;max-width:100%;}.", k, "-bubble-attachments{display:flex;flex-direction:column;gap:12px;min-width:0;max-width:100%;}.", k, "-bubble-before-content{min-width:0;width:100%;}.", k, "-bubble-text{white-space:pre-wrap;}.", k, "-bubble-loading{display:inline-flex;align-items:center;gap:8px;color:", bubble.loadingTextColor, ";min-height:20px;}.", k, "-bubble-loading-dot{width:", bubble.loadingDotSize, ";height:", bubble.loadingDotSize, ";border-radius:50%;background:", bubble.loadingDotColor, ";display:inline-block;animation:", k, "-bubble-loading-bounce 1s ease-in-out infinite;box-shadow:0 0 0 1px ", setAlpha(theme.color.primary, 0.04), ";}.", k, "-bubble-loading-dot:nth-of-type(2){animation-delay:0.14s;}.", k, "-bubble-loading-dot:nth-of-type(3){animation-delay:0.28s;}.", k, "-bubble-footer{display:flex;align-items:center;gap:4px;}.", k, "-bubble-extra{color:", bubble.extraColor, ";font-size:12px;line-height:1.5;}.", k, "-bubble-avatar{width:", bubble.avatarSize, ";height:", bubble.avatarSize, ";flex:0 0 ", bubble.avatarSize, ";border-radius:50%;overflow:hidden;display:inline-flex;align-items:center;justify-content:center;background:", bubble.avatarBg, ";color:", bubble.avatarColor, ";font-size:", bubble.avatarFontSize, ";font-weight:600;}.", k, "-bubble-avatar-image{width:100%;height:100%;object-fit:cover;display:block;}.", k, "-bubble-markdown{color:inherit;overflow-x:auto;}.", k, "-bubble-markdown>:first-child{margin-top:0;}.", k, "-bubble-markdown>:last-child{margin-bottom:0;}.", k, "-bubble-markdown [data-kpc-bubble-markdown-tail]{display:inline;white-space:pre-wrap;word-break:break-word;overflow-wrap:anywhere;}.", k, "-bubble-markdown p,.", k, "-bubble-markdown ul,.", k, "-bubble-markdown ol,.", k, "-bubble-markdown blockquote,.", k, "-bubble-markdown pre,.", k, "-bubble-markdown table,.", k, "-bubble-markdown hr,.", k, "-bubble-markdown h1,.", k, "-bubble-markdown h2,.", k, "-bubble-markdown h3,.", k, "-bubble-markdown h4,.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{margin:0 0 10px;}.", k, "-bubble-markdown ul,.", k, "-bubble-markdown ol{padding-left:20px;list-style-position:outside;}.", k, "-bubble-markdown ul{list-style-type:disc;}.", k, "-bubble-markdown ul ul{list-style-type:circle;}.", k, "-bubble-markdown ul ul ul{list-style-type:square;}.", k, "-bubble-markdown ol{list-style-type:decimal;}.", k, "-bubble-markdown ol ol{list-style-type:lower-alpha;}.", k, "-bubble-markdown li{margin:6px 0;}.", k, "-bubble-markdown li>p{margin:6px 0 0;}.", k, "-bubble-markdown h1,.", k, "-bubble-markdown h2,.", k, "-bubble-markdown h3,.", k, "-bubble-markdown h4,.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{color:", bubble.markdownHeadingColor, ";font-weight:600;line-height:1.35;}.", k, "-bubble-markdown h1{font-size:22px;}.", k, "-bubble-markdown h2{font-size:18px;}.", k, "-bubble-markdown h3{font-size:16px;}.", k, "-bubble-markdown h4{font-size:14px;}.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{font-size:13px;}.", k, "-bubble-markdown a{color:", bubble.markdownLinkColor, ";text-decoration:underline;text-decoration-thickness:1px;text-underline-offset:2px;}.", k, "-bubble-markdown a:hover{opacity:0.88;}.", k, "-bubble-markdown code{display:inline-block;padding:0 6px;border-radius:4px;background:", bubble.markdownCodeBg, ";color:", bubble.markdownCodeColor, ";font-family:SFMono-Regular,Consolas,'Liberation Mono',Menlo,monospace;font-size:12px;white-space:break-spaces;}.", k, "-bubble-markdown strong,.", k, "-bubble-markdown b{font-weight:600;}.", k, "-bubble-markdown img{display:block;max-width:100%;height:auto;margin:12px 0;border-radius:12px;}.", k, "-bubble-markdown hr{height:1px;border:0;background:", bubble.markdownBorderColor, ";}.", k, "-bubble-markdown pre{padding:0px;overflow:auto;background:", bubble.markdownPreBg, ";color:", bubble.markdownPreColor, ";border:1px solid ", setAlpha('#ffffff', 0.06), ";}.", k, "-bubble-markdown pre code{display:block;padding:4px;background:transparent;color:inherit;white-space:pre;word-break:normal;overflow-wrap:normal;}.", k, "-bubble-markdown .hljs{background:transparent;color:inherit;}.", k, "-bubble-markdown .hljs-comment,.", k, "-bubble-markdown .hljs-quote{color:#8fa1b3;}.", k, "-bubble-markdown .hljs-keyword,.", k, "-bubble-markdown .hljs-selector-tag,.", k, "-bubble-markdown .hljs-literal,.", k, "-bubble-markdown .hljs-section,.", k, "-bubble-markdown .hljs-link{color:#ffb86c;}.", k, "-bubble-markdown .hljs-string,.", k, "-bubble-markdown .hljs-title,.", k, "-bubble-markdown .hljs-name,.", k, "-bubble-markdown .hljs-type,.", k, "-bubble-markdown .hljs-attribute,.", k, "-bubble-markdown .hljs-symbol,.", k, "-bubble-markdown .hljs-bullet,.", k, "-bubble-markdown .hljs-addition{color:#7ee787;}.", k, "-bubble-markdown .hljs-number,.", k, "-bubble-markdown .hljs-built_in,.", k, "-bubble-markdown .hljs-builtin-name,.", k, "-bubble-markdown .hljs-variable,.", k, "-bubble-markdown .hljs-template-variable{color:#79c0ff;}.", k, "-bubble-markdown .hljs-deletion{color:#ff7b72;}.", k, "-bubble-markdown table{width:100%;border-collapse:collapse;border-spacing:0;border:1px solid ", bubble.markdownBorderColor, ";border-radius:10px;overflow:hidden;font-size:12px;background:transparent;}.", k, "-bubble-markdown th,.", k, "-bubble-markdown td{padding:8px 12px;border:1px solid ", bubble.markdownBorderColor, ";text-align:left;vertical-align:top;}.", k, "-bubble-markdown th{font-weight:600;background:", bubble.markdownTableHeadBg, ";}.", k, "-bubble-markdown blockquote{padding-left:12px;border-left:3px solid ", setAlpha(theme.color.text, 0.16), ";background:", bubble.markdownBlockquoteBg, ";border-radius:0 10px 10px 0;padding:8px 12px;opacity:0.96;}.", k, "-bubble-markdown blockquote>:last-child{margin-bottom:0;}&.", k, "-bubble-start{align-items:flex-start;}&.", k, "-bubble-start .", k, "-bubble-main{align-items:flex-start;}&.", k, "-bubble-end{align-items:flex-end;}&.", k, "-bubble-end .", k, "-bubble-main{align-items:flex-end;}&.", k, "-bubble-end .", k, "-bubble-meta{flex-direction:row-reverse;justify-content:flex-end;}&.", k, "-bubble-end .", k, "-bubble-header{text-align:right;}&.", k, "-bubble-middle{align-items:center;}&.", k, "-bubble-middle .", k, "-bubble-main{align-items:center;}&.", k, "-bubble-middle .", k, "-bubble-meta{justify-content:center;}&.", k, "-bubble-middle .", k, "-bubble-header{text-align:center;}&.", k, "-bubble-filled .", k, "-bubble-content{background:", bubble.filledBg, ";color:", bubble.filledColor, ";border:", bubble.filledBorder, ";}&.", k, "-bubble-outlined .", k, "-bubble-content{background:", bubble.outlinedBg, ";color:", bubble.outlinedColor, ";border:", bubble.outlinedBorder, ";}&.", k, "-bubble-plain .", k, "-bubble-content{background:", bubble.plainBg, ";color:", bubble.plainColor, ";border:", bubble.plainBorder, ";padding:0;}&.", k, "-bubble-round .", k, "-bubble-content{border-radius:", bubble.roundBorderRadius, ";}&.", k, "-bubble-corner.", k, "-bubble-start .", k, "-bubble-content{border-radius:", bubble.borderRadius, " ", bubble.borderRadius, " ", bubble.borderRadius, " 0;}&.", k, "-bubble-corner.", k, "-bubble-end .", k, "-bubble-content{border-radius:", bubble.borderRadius, " ", bubble.borderRadius, " 0 ", bubble.borderRadius, ";}&.", k, "-bubble-corner.", k, "-bubble-middle .", k, "-bubble-content{border-radius:", bubble.borderRadius, ";}&.", k, "-bubble-square .", k, "-bubble-content{border-radius:", bubble.borderRadius, ";}@keyframes ", k, "-bubble-loading-bounce{0%,80%,100%{transform:translateY(0) scale(0.9);opacity:0.45;}40%{transform:translateY(-5px) scale(1);opacity:1;}}");
52
+ return /*#__PURE__*/css("display:flex;flex-direction:column;align-items:flex-start;width:100%;.", k, "-bubble-main{display:flex;flex-direction:column;gap:8px;min-width:0;align-items:flex-start;}.", k, "-bubble-meta{display:flex;align-items:center;gap:8px;min-width:0;}.", k, "-bubble-header{color:", bubble.roleNameColor, ";font-size:14px;font-weight:500;min-width:0;text-align:left;}.", k, "-bubble-content{display:flex;flex-direction:column;gap:8px;min-width:0;max-width:100%;padding:", bubble.padding, ";box-sizing:border-box;line-height:1.6;word-break:break-word;overflow-wrap:anywhere;transition:background ", theme.transition.small, ",border-color ", theme.transition.small, ";}.", k, "-bubble-content>*{min-width:0;max-width:100%;}.", k, "-bubble-attachments{display:flex;flex-direction:column;gap:12px;min-width:0;max-width:100%;}.", k, "-bubble-before-content{min-width:0;width:100%;}.", k, "-bubble-text{white-space:pre-wrap;}.", k, "-bubble-typing-suffix{display:inline-flex;align-items:center;gap:4px;width:26px;height:6px;line-height:0;}.", k, "-bubble-typing-suffix span{width:6px;height:6px;border-radius:50%;background:radial-gradient(circle at center, #F8F9FA 0%, #D0D5D9 100%);animation:", k, "-bubble-typing-suffix-pulse 1.2s ease-in-out infinite;}.", k, "-bubble-typing-suffix span:nth-child(2){animation-delay:0.16s;}.", k, "-bubble-typing-suffix span:nth-child(3){animation-delay:0.32s;}.", k, "-bubble-loading{display:inline-flex;align-items:center;gap:8px;color:", bubble.loadingTextColor, ";min-height:20px;}.", k, "-bubble-loading-dot{width:", bubble.loadingDotSize, ";height:", bubble.loadingDotSize, ";border-radius:50%;background:", bubble.loadingDotColor, ";display:inline-block;animation:", k, "-bubble-loading-bounce 1s ease-in-out infinite;box-shadow:0 0 0 1px ", setAlpha(theme.color.primary, 0.04), ";}.", k, "-bubble-loading-dot:nth-of-type(2){animation-delay:0.14s;}.", k, "-bubble-loading-dot:nth-of-type(3){animation-delay:0.28s;}.", k, "-bubble-footer{display:flex;align-items:center;gap:4px;}.", k, "-bubble-extra{color:", bubble.extraColor, ";font-size:12px;line-height:1.5;}.", k, "-bubble-avatar{width:", bubble.avatarSize, ";height:", bubble.avatarSize, ";flex:0 0 ", bubble.avatarSize, ";border-radius:50%;overflow:hidden;display:inline-flex;align-items:center;justify-content:center;background:", bubble.avatarBg, ";color:", bubble.avatarColor, ";font-size:", bubble.avatarFontSize, ";font-weight:600;}.", k, "-bubble-avatar-image{width:100%;height:100%;object-fit:cover;display:block;}.", k, "-bubble-markdown{color:inherit;overflow-x:auto;}.", k, "-bubble-markdown>:first-child{margin-top:0;}.", k, "-bubble-markdown>:last-child{margin-bottom:0;}.", k, "-bubble-markdown [data-kpc-bubble-markdown-tail]{display:inline;white-space:pre-wrap;word-break:break-word;overflow-wrap:anywhere;}.", k, "-bubble-markdown p,.", k, "-bubble-markdown ul,.", k, "-bubble-markdown ol,.", k, "-bubble-markdown blockquote,.", k, "-bubble-markdown pre,.", k, "-bubble-markdown table,.", k, "-bubble-markdown hr,.", k, "-bubble-markdown h1,.", k, "-bubble-markdown h2,.", k, "-bubble-markdown h3,.", k, "-bubble-markdown h4,.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{margin:0 0 10px;}.", k, "-bubble-markdown ul,.", k, "-bubble-markdown ol{padding-left:20px;list-style-position:outside;}.", k, "-bubble-markdown ul{list-style-type:disc;}.", k, "-bubble-markdown ul ul{list-style-type:circle;}.", k, "-bubble-markdown ul ul ul{list-style-type:square;}.", k, "-bubble-markdown ol{list-style-type:decimal;}.", k, "-bubble-markdown ol ol{list-style-type:lower-alpha;}.", k, "-bubble-markdown li{margin:6px 0;}.", k, "-bubble-markdown li>p{margin:6px 0 0;}.", k, "-bubble-markdown h1,.", k, "-bubble-markdown h2,.", k, "-bubble-markdown h3,.", k, "-bubble-markdown h4,.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{color:", bubble.markdownHeadingColor, ";font-weight:600;line-height:1.35;}.", k, "-bubble-markdown h1{font-size:22px;}.", k, "-bubble-markdown h2{font-size:18px;}.", k, "-bubble-markdown h3{font-size:16px;}.", k, "-bubble-markdown h4{font-size:14px;}.", k, "-bubble-markdown h5,.", k, "-bubble-markdown h6{font-size:13px;}.", k, "-bubble-markdown a{color:", bubble.markdownLinkColor, ";text-decoration:underline;text-decoration-thickness:1px;text-underline-offset:2px;}.", k, "-bubble-markdown a:hover{opacity:0.88;}.", k, "-bubble-markdown code{display:inline-block;padding:0 6px;border-radius:4px;background:", bubble.markdownCodeBg, ";color:", bubble.markdownCodeColor, ";font-family:SFMono-Regular,Consolas,'Liberation Mono',Menlo,monospace;font-size:12px;white-space:break-spaces;}.", k, "-bubble-markdown strong,.", k, "-bubble-markdown b{font-weight:600;}.", k, "-bubble-markdown img{display:block;max-width:100%;height:auto;margin:12px 0;border-radius:12px;}.", k, "-bubble-markdown hr{height:1px;border:0;background:", bubble.markdownBorderColor, ";}.", k, "-bubble-markdown pre{padding:0px;overflow:auto;background:", bubble.markdownPreBg, ";color:", bubble.markdownPreColor, ";border:1px solid ", setAlpha('#ffffff', 0.06), ";}.", k, "-bubble-markdown pre code{display:block;padding:4px;background:transparent;color:inherit;white-space:pre;word-break:normal;overflow-wrap:normal;}.", k, "-bubble-markdown .hljs{background:transparent;color:inherit;}.", k, "-bubble-markdown .hljs-comment,.", k, "-bubble-markdown .hljs-quote{color:#8fa1b3;}.", k, "-bubble-markdown .hljs-keyword,.", k, "-bubble-markdown .hljs-selector-tag,.", k, "-bubble-markdown .hljs-literal,.", k, "-bubble-markdown .hljs-section,.", k, "-bubble-markdown .hljs-link{color:#ffb86c;}.", k, "-bubble-markdown .hljs-string,.", k, "-bubble-markdown .hljs-title,.", k, "-bubble-markdown .hljs-name,.", k, "-bubble-markdown .hljs-type,.", k, "-bubble-markdown .hljs-attribute,.", k, "-bubble-markdown .hljs-symbol,.", k, "-bubble-markdown .hljs-bullet,.", k, "-bubble-markdown .hljs-addition{color:#7ee787;}.", k, "-bubble-markdown .hljs-number,.", k, "-bubble-markdown .hljs-built_in,.", k, "-bubble-markdown .hljs-builtin-name,.", k, "-bubble-markdown .hljs-variable,.", k, "-bubble-markdown .hljs-template-variable{color:#79c0ff;}.", k, "-bubble-markdown .hljs-deletion{color:#ff7b72;}.", k, "-bubble-markdown table{width:100%;border-collapse:collapse;border-spacing:0;border:1px solid ", bubble.markdownBorderColor, ";border-radius:10px;overflow:hidden;font-size:12px;background:transparent;}.", k, "-bubble-markdown th,.", k, "-bubble-markdown td{padding:8px 12px;border:1px solid ", bubble.markdownBorderColor, ";text-align:left;vertical-align:top;}.", k, "-bubble-markdown th{font-weight:600;background:", bubble.markdownTableHeadBg, ";}.", k, "-bubble-markdown blockquote{padding-left:12px;border-left:3px solid ", setAlpha(theme.color.text, 0.16), ";background:", bubble.markdownBlockquoteBg, ";border-radius:0 10px 10px 0;padding:8px 12px;opacity:0.96;}.", k, "-bubble-markdown blockquote>:last-child{margin-bottom:0;}&.", k, "-bubble-start{align-items:flex-start;}&.", k, "-bubble-start .", k, "-bubble-main{align-items:flex-start;}&.", k, "-bubble-end{align-items:flex-end;}&.", k, "-bubble-end .", k, "-bubble-main{align-items:flex-end;}&.", k, "-bubble-end .", k, "-bubble-meta{flex-direction:row-reverse;justify-content:flex-end;}&.", k, "-bubble-end .", k, "-bubble-header{text-align:right;}&.", k, "-bubble-middle{align-items:center;}&.", k, "-bubble-middle .", k, "-bubble-main{align-items:center;}&.", k, "-bubble-middle .", k, "-bubble-meta{justify-content:center;}&.", k, "-bubble-middle .", k, "-bubble-header{text-align:center;}&.", k, "-bubble-filled .", k, "-bubble-content{background:", bubble.filledBg, ";color:", bubble.filledColor, ";border:", bubble.filledBorder, ";}&.", k, "-bubble-outlined .", k, "-bubble-content{background:", bubble.outlinedBg, ";color:", bubble.outlinedColor, ";border:", bubble.outlinedBorder, ";}&.", k, "-bubble-plain .", k, "-bubble-content{background:", bubble.plainBg, ";color:", bubble.plainColor, ";border:", bubble.plainBorder, ";padding:0;}&.", k, "-bubble-round .", k, "-bubble-content{border-radius:", bubble.roundBorderRadius, ";}&.", k, "-bubble-corner.", k, "-bubble-start .", k, "-bubble-content{border-radius:0 ", bubble.borderRadius, " ", bubble.borderRadius, " ", bubble.borderRadius, ";}&.", k, "-bubble-corner.", k, "-bubble-end .", k, "-bubble-content{border-radius:", bubble.borderRadius, " 0 ", bubble.borderRadius, " ", bubble.borderRadius, ";}&.", k, "-bubble-corner.", k, "-bubble-middle .", k, "-bubble-content{border-radius:0 0 ", bubble.borderRadius, " ", bubble.borderRadius, ";}&.", k, "-bubble-square .", k, "-bubble-content{border-radius:", bubble.borderRadius, ";}@keyframes ", k, "-bubble-loading-bounce{0%,80%,100%{transform:translateY(0) scale(0.9);opacity:0.45;}40%{transform:translateY(-5px) scale(1);opacity:1;}}@keyframes ", k, "-bubble-typing-suffix-pulse{0%,80%,100%{background:radial-gradient(circle at center, #F8F9FA 0%, #D0D5D9 100%);transform:translateY(0);}40%{background:radial-gradient(circle at center, ", setAlpha(theme.color.primary, 0.45), " 0%, ", theme.color.primary, " 100%);transform:translateY(-1px);}}");
53
53
  });
@@ -7,6 +7,7 @@ export declare function useBubbleDisplay(): {
7
7
  shouldShowContentBlock: () => boolean;
8
8
  shouldShowLoadingShell: () => boolean;
9
9
  getDisplayedContent: () => string;
10
+ shouldShowTypingSuffix: () => boolean;
10
11
  isTypingActive: () => boolean;
11
12
  getBubbleStyle: () => {
12
13
  maxWidth: string;
@@ -10,6 +10,7 @@ export function useBubbleDisplay() {
10
10
  var previousLoading = !!instance.get('loading');
11
11
  var previousStreaming = !!instance.get('streaming');
12
12
  var hasPendingCompletion = previousLoading || previousStreaming;
13
+ var typingTargetKey = '';
13
14
  function setDisplayContent(value) {
14
15
  if (instance.get('$displayContent') === value) return false;
15
16
  instance.set('$displayContent', value);
@@ -24,12 +25,16 @@ export function useBubbleDisplay() {
24
25
  if (typing && typeof typing === 'object') {
25
26
  return {
26
27
  interval: Math.max(typing.interval || 24, 16),
27
- step: Math.max(typing.step || 2, 1)
28
+ step: Math.max(typing.step || 2, 1),
29
+ keepPrefix: typing.keepPrefix !== false,
30
+ resumeFrom: typing.resumeFrom
28
31
  };
29
32
  }
30
33
  return {
31
34
  interval: 24,
32
- step: 2
35
+ step: 2,
36
+ keepPrefix: true,
37
+ resumeFrom: undefined
33
38
  };
34
39
  }
35
40
  function stopTyping() {
@@ -71,18 +76,49 @@ export function useBubbleDisplay() {
71
76
  function getDisplayedContent() {
72
77
  return instance.get('$displayContent') || '';
73
78
  }
79
+ function getSafeContentPrefix(content, prefix) {
80
+ if (!prefix) return '';
81
+ if (_sliceInstanceProperty(content).call(content, 0, prefix.length) === prefix) return prefix;
82
+ var i = 0;
83
+ while (i < prefix.length && i < content.length && prefix[i] === content[i]) {
84
+ i++;
85
+ }
86
+ return _sliceInstanceProperty(prefix).call(prefix, 0, i);
87
+ }
88
+ function getResumePrefix(content) {
89
+ var _getTypingOptions = getTypingOptions(),
90
+ resumeFrom = _getTypingOptions.resumeFrom;
91
+ if (resumeFrom === undefined || resumeFrom === null) return '';
92
+ if (resumeFrom === 'content') return content;
93
+ if (typeof resumeFrom === 'number') return _sliceInstanceProperty(content).call(content, 0, Math.max(0, resumeFrom));
94
+ return getSafeContentPrefix(content, String(resumeFrom));
95
+ }
96
+ function getTypingTargetKey(content) {
97
+ var _getTypingOptions2 = getTypingOptions(),
98
+ keepPrefix = _getTypingOptions2.keepPrefix,
99
+ resumeFrom = _getTypingOptions2.resumeFrom;
100
+ return (keepPrefix ? '1' : '0') + "\0" + String(resumeFrom) + "\0" + content;
101
+ }
102
+ function syncTypingStart(content) {
103
+ var targetKey = getTypingTargetKey(content);
104
+ if (targetKey === typingTargetKey) return;
105
+ typingTargetKey = targetKey;
106
+ var sharedPrefix = getSharedPrefix(content);
107
+ if (sharedPrefix !== getDisplayedContent()) {
108
+ resetTypingComplete();
109
+ setDisplayContent(sharedPrefix);
110
+ }
111
+ }
74
112
  // 获取共享前缀
75
113
  function getSharedPrefix(content) {
76
114
  var displayedContent = getDisplayedContent();
115
+ if (!displayedContent) return getResumePrefix(content);
116
+ if (!getTypingOptions().keepPrefix) return '';
77
117
  // 避免 startsWith 依赖,兼容旧运行环境。
78
118
  if (!displayedContent || _sliceInstanceProperty(content).call(content, 0, displayedContent.length) === displayedContent) {
79
119
  return displayedContent;
80
120
  }
81
- var i = 0;
82
- while (i < displayedContent.length && i < content.length && displayedContent[i] === content[i]) {
83
- i++;
84
- }
85
- return _sliceInstanceProperty(displayedContent).call(displayedContent, 0, i);
121
+ return getSafeContentPrefix(content, displayedContent);
86
122
  }
87
123
  // 开始打字动画
88
124
  function startTyping(immediate) {
@@ -95,8 +131,8 @@ export function useBubbleDisplay() {
95
131
  runTyping();
96
132
  return;
97
133
  }
98
- var _getTypingOptions = getTypingOptions(),
99
- interval = _getTypingOptions.interval;
134
+ var _getTypingOptions3 = getTypingOptions(),
135
+ interval = _getTypingOptions3.interval;
100
136
  setTypingActive(true);
101
137
  typingTimer = window.setTimeout(function () {
102
138
  typingTimer = null;
@@ -111,26 +147,24 @@ export function useBubbleDisplay() {
111
147
  if (instance.get('loading')) {
112
148
  stopTyping();
113
149
  resetTypingComplete();
150
+ typingTargetKey = '';
114
151
  setDisplayContent('');
115
152
  return;
116
153
  }
117
154
  if (!instance.get('typing') || !nextValue) {
118
155
  stopTyping();
156
+ typingTargetKey = '';
119
157
  setDisplayContent(nextValue);
120
158
  if (!instance.get('streaming') && shouldEmitTypingComplete(nextValue)) {
121
159
  triggerTypingComplete(nextValue);
122
160
  }
123
161
  return;
124
162
  }
125
- var sharedPrefix = getSharedPrefix(nextValue);
126
- if (sharedPrefix !== getDisplayedContent()) {
127
- resetTypingComplete();
128
- setDisplayContent(sharedPrefix);
129
- }
163
+ syncTypingStart(nextValue);
130
164
  var currentValue = getDisplayedContent();
131
- var _getTypingOptions2 = getTypingOptions(),
132
- interval = _getTypingOptions2.interval,
133
- step = _getTypingOptions2.step;
165
+ var _getTypingOptions4 = getTypingOptions(),
166
+ interval = _getTypingOptions4.interval,
167
+ step = _getTypingOptions4.step;
134
168
  if (currentValue !== nextValue) {
135
169
  var nextLength = Math.min(currentValue.length + step, nextValue.length);
136
170
  var renderedContent = _sliceInstanceProperty(nextValue).call(nextValue, 0, nextLength);
@@ -157,6 +191,7 @@ export function useBubbleDisplay() {
157
191
  if (instance.get('loading')) {
158
192
  stopTyping();
159
193
  resetTypingComplete();
194
+ typingTargetKey = '';
160
195
  setDisplayContent('');
161
196
  return;
162
197
  }
@@ -166,6 +201,7 @@ export function useBubbleDisplay() {
166
201
  var streaming = instance.get('streaming');
167
202
  if (!nextValue) {
168
203
  stopTyping();
204
+ typingTargetKey = '';
169
205
  setDisplayContent(nextValue);
170
206
  if (!streaming && shouldEmitTypingComplete(nextValue)) {
171
207
  triggerTypingComplete(nextValue);
@@ -174,18 +210,18 @@ export function useBubbleDisplay() {
174
210
  }
175
211
  if (!typing) {
176
212
  stopTyping();
213
+ typingTargetKey = '';
177
214
  setDisplayContent(nextValue);
178
215
  if (!streaming && shouldEmitTypingComplete(nextValue)) {
179
216
  triggerTypingComplete(nextValue);
180
217
  }
181
218
  return;
182
219
  }
183
- var sharedPrefix = getSharedPrefix(nextValue);
184
- if (sharedPrefix !== getDisplayedContent()) {
220
+ var previousDisplayContent = getDisplayedContent();
221
+ syncTypingStart(nextValue);
222
+ if (getDisplayedContent() !== previousDisplayContent) {
185
223
  // 内容被修订时保留共享前缀,避免流式修正时整段闪烁。
186
224
  stopTyping();
187
- resetTypingComplete();
188
- setDisplayContent(sharedPrefix);
189
225
  }
190
226
  if (getDisplayedContent() === nextValue) {
191
227
  if (!streaming) {
@@ -200,8 +236,10 @@ export function useBubbleDisplay() {
200
236
  // 初始化状态和绑定监听器
201
237
  function bootstrap() {
202
238
  var content = instance.get('content');
239
+ var nextValue = content === undefined || content === null ? '' : String(content);
203
240
  setTypingActive(false);
204
- setDisplayContent(!instance.get('loading') && !instance.get('typing') && content !== undefined && content !== null ? String(content) : '');
241
+ var initialDisplayContent = !instance.get('loading') && nextValue ? instance.get('typing') ? getResumePrefix(nextValue) : nextValue : '';
242
+ setDisplayContent(initialDisplayContent);
205
243
  instance.watch('content', function () {
206
244
  return syncDisplayContent();
207
245
  }, {
@@ -252,6 +290,13 @@ export function useBubbleDisplay() {
252
290
  function isTypingActive() {
253
291
  return !!instance.get('$typingActive');
254
292
  }
293
+ function shouldShowTypingSuffix() {
294
+ var typing = instance.get('typing');
295
+ if (!typing) return false;
296
+ if (typeof typing === 'boolean') return false;
297
+ if (typing.suffix !== true) return false;
298
+ return !instance.get('loading') && (isTypingActive() || !!instance.get('streaming'));
299
+ }
255
300
  function getBubbleStyle() {
256
301
  var maxWidthString = instance.get('maxWidthString');
257
302
  if (!maxWidthString) return;
@@ -290,6 +335,7 @@ export function useBubbleDisplay() {
290
335
  shouldShowContentBlock: shouldShowContentBlock,
291
336
  shouldShowLoadingShell: shouldShowLoadingShell,
292
337
  getDisplayedContent: getDisplayedContent,
338
+ shouldShowTypingSuffix: shouldShowTypingSuffix,
293
339
  isTypingActive: isTypingActive,
294
340
  getBubbleStyle: getBubbleStyle,
295
341
  getRoleNameText: getRoleNameText,
@@ -8,6 +8,7 @@ import { Icon } from '../icon';
8
8
  import { isInvalid, isNumber, noop } from 'intact-shared';
9
9
  export default function ($props, $blocks, $__proto__) {
10
10
  var _classNameObj,
11
+ _$cn2,
11
12
  _this = this;
12
13
  $blocks || ($blocks = {});
13
14
  $props || ($props = {});
@@ -27,6 +28,7 @@ export default function ($props, $blocks, $__proto__) {
27
28
  shouldShowScrollToBottom = _this$bubbleList.shouldShowScrollToBottom,
28
29
  getDefaultHistoryLoadingText = _this$bubbleList.getDefaultHistoryLoadingText,
29
30
  onScrollToBottomClick = _this$bubbleList.onScrollToBottomClick;
31
+ var hasScrollbar = this.get('$hasScrollbar');
30
32
  var _this$get = this.get(),
31
33
  className = _this$get.className,
32
34
  style = _this$get.style,
@@ -116,7 +118,7 @@ export default function ($props, $blocks, $__proto__) {
116
118
  'list': this,
117
119
  'slotRenderers': getSlotRenderers($value, $key)
118
120
  }), 2, null, null, getItemKey($value, $key), getItemRef($value, $key));
119
- }, $this), 8, _$cn(k + "-bubble-list-items"))], 0, _$cn(k + "-bubble-list-scroll-content"), null, null, scrollContentRef), 2, _$cn(k + "-bubble-list-scroll"), {
121
+ }, $this), 8, _$cn(k + "-bubble-list-items"))], 0, _$cn(k + "-bubble-list-scroll-content"), null, null, scrollContentRef), 2, _$cn((_$cn2 = {}, _$cn2[k + "-bubble-list-scroll"] = true, _$cn2[k + "-bubble-list-scroll-has-scrollbar"] = hasScrollbar, _$cn2)), {
120
122
  'ev-scroll': handleScroll
121
123
  }, null, scrollBoxRef), hasListFooterSlot ? _$ce(2, 'div', listFooterSlot, 0, _$cn(k + "-bubble-list-footer")) : undefined, shouldShowScrollToBottom() ? _$ce(2, 'div', $blocks.scrollToBottom ? (_$blocks['scrollToBottom'] = function ($super) {
122
124
  return null;