@linktr.ee/messaging-react 3.9.0-rc-1783472582 → 3.9.0-rc-1783568295

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 (88) hide show
  1. package/dist/Card-B8Zz3GRL.js +132 -0
  2. package/dist/Card-B8Zz3GRL.js.map +1 -0
  3. package/dist/Card-BmYSOINp.cjs +2 -0
  4. package/dist/Card-BmYSOINp.cjs.map +1 -0
  5. package/dist/Card-BnJLBTl6.js +163 -0
  6. package/dist/Card-BnJLBTl6.js.map +1 -0
  7. package/dist/Card-DWT-IkeK.cjs +2 -0
  8. package/dist/Card-DWT-IkeK.cjs.map +1 -0
  9. package/dist/Card-Gapf9yEL.js +107 -0
  10. package/dist/Card-Gapf9yEL.js.map +1 -0
  11. package/dist/Card-WoQGTJ5n.cjs +2 -0
  12. package/dist/Card-WoQGTJ5n.cjs.map +1 -0
  13. package/dist/LockedThumbnail-Cu3qwKAd.js +220 -0
  14. package/dist/LockedThumbnail-Cu3qwKAd.js.map +1 -0
  15. package/dist/LockedThumbnail-DFByBLYS.cjs +2 -0
  16. package/dist/LockedThumbnail-DFByBLYS.cjs.map +1 -0
  17. package/dist/assets/index.css +1 -1
  18. package/dist/{index-B8gqCioX.js → index-Bv79lb0u.js} +1114 -1154
  19. package/dist/index-Bv79lb0u.js.map +1 -0
  20. package/dist/index-C1Zaiccm.cjs +2 -0
  21. package/dist/index-C1Zaiccm.cjs.map +1 -0
  22. package/dist/index.cjs +1 -1
  23. package/dist/index.d.ts +55 -98
  24. package/dist/index.js +1 -1
  25. package/dist/testing.d.ts +0 -1
  26. package/package.json +2 -2
  27. package/src/components/CustomMessage/CustomMessage.stories.tsx +1 -54
  28. package/src/components/CustomMessage/MessageTag.tsx +0 -8
  29. package/src/components/CustomMessage/index.tsx +22 -61
  30. package/src/components/CustomMessageInput/index.tsx +3 -0
  31. package/src/components/LockedAttachment/LockedAttachment.stories.tsx +340 -422
  32. package/src/components/LockedAttachment/components/Composer/Card.tsx +120 -100
  33. package/src/components/LockedAttachment/components/Composer/index.ts +2 -0
  34. package/src/components/LockedAttachment/components/Received/Card.tsx +191 -0
  35. package/src/components/LockedAttachment/components/{Media → Received}/CardActions.tsx +1 -3
  36. package/src/components/LockedAttachment/components/Received/index.ts +2 -0
  37. package/src/components/LockedAttachment/components/Sent/Card.tsx +177 -0
  38. package/src/components/LockedAttachment/components/Sent/index.ts +2 -0
  39. package/src/components/LockedAttachment/components/_shared/CardBody.tsx +3 -3
  40. package/src/components/LockedAttachment/components/_shared/GalleryThumbnail.tsx +38 -30
  41. package/src/components/LockedAttachment/components/_shared/LockBadge.tsx +19 -43
  42. package/src/components/LockedAttachment/components/_shared/{MediaShell.tsx → LockedCardShell.tsx} +7 -6
  43. package/src/components/LockedAttachment/components/_shared/{SingleThumbnail.tsx → LockedThumbnail.tsx} +6 -10
  44. package/src/components/LockedAttachment/index.tsx +28 -17
  45. package/src/components/LockedAttachment/types.ts +4 -28
  46. package/src/index.ts +5 -2
  47. package/src/stream-custom-data.ts +0 -1
  48. package/src/styles.css +0 -5
  49. package/dist/Card-BVZM0-06.js +0 -108
  50. package/dist/Card-BVZM0-06.js.map +0 -1
  51. package/dist/Card-D0hLrOxX.js +0 -221
  52. package/dist/Card-D0hLrOxX.js.map +0 -1
  53. package/dist/Card-DIr1UnfC.cjs +0 -2
  54. package/dist/Card-DIr1UnfC.cjs.map +0 -1
  55. package/dist/Card-DeSgaRTL.cjs +0 -2
  56. package/dist/Card-DeSgaRTL.cjs.map +0 -1
  57. package/dist/Card-DnaXMVrT.cjs +0 -2
  58. package/dist/Card-DnaXMVrT.cjs.map +0 -1
  59. package/dist/Card-xv52Ug43.js +0 -61
  60. package/dist/Card-xv52Ug43.js.map +0 -1
  61. package/dist/LoadingDots-Cn2y7g7L.cjs +0 -2
  62. package/dist/LoadingDots-Cn2y7g7L.cjs.map +0 -1
  63. package/dist/LoadingDots-nW6r0-Kg.js +0 -62
  64. package/dist/LoadingDots-nW6r0-Kg.js.map +0 -1
  65. package/dist/TextShell-CKQOFxoH.cjs +0 -2
  66. package/dist/TextShell-CKQOFxoH.cjs.map +0 -1
  67. package/dist/TextShell-DIyj9zQ7.js +0 -40
  68. package/dist/TextShell-DIyj9zQ7.js.map +0 -1
  69. package/dist/index-B8gqCioX.js.map +0 -1
  70. package/dist/index-IkikzyWM.cjs +0 -2
  71. package/dist/index-IkikzyWM.cjs.map +0 -1
  72. package/dist/usePreviewToggle-B0B8cfxy.cjs +0 -2
  73. package/dist/usePreviewToggle-B0B8cfxy.cjs.map +0 -1
  74. package/dist/usePreviewToggle-DRhRTUou.js +0 -357
  75. package/dist/usePreviewToggle-DRhRTUou.js.map +0 -1
  76. package/src/components/LockedAttachment/LockedAttachment.test.tsx +0 -104
  77. package/src/components/LockedAttachment/components/Media/Card.tsx +0 -235
  78. package/src/components/LockedAttachment/components/Text/Card.tsx +0 -177
  79. package/src/components/LockedAttachment/components/_shared/CardThumbnail.tsx +0 -92
  80. package/src/components/LockedAttachment/components/_shared/LoadingDots.tsx +0 -36
  81. package/src/components/LockedAttachment/components/_shared/PreviewToggle.tsx +0 -58
  82. package/src/components/LockedAttachment/components/_shared/PriceLockRow.tsx +0 -21
  83. package/src/components/LockedAttachment/components/_shared/PurchaseStatusBadge.tsx +0 -86
  84. package/src/components/LockedAttachment/components/_shared/SkeletonTextLines.tsx +0 -39
  85. package/src/components/LockedAttachment/components/_shared/TextShell.tsx +0 -19
  86. package/src/components/LockedAttachment/components/_shared/usePreviewToggle.test.ts +0 -67
  87. package/src/components/LockedAttachment/components/_shared/usePreviewToggle.ts +0 -89
  88. package/src/components/LockedAttachment/components/_shared/useReceivedSource.ts +0 -83
package/dist/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("./index-IkikzyWM.cjs");exports.ActionButton=e.ActionButton;exports.Avatar=e.Avatar;exports.ChannelEmptyState=e.ChannelEmptyState;exports.ChannelList=e.ChannelList;exports.ChannelView=e.ChannelView;exports.CustomMessageProvider=e.CustomMessageProvider;exports.FaqList=e.FaqList;exports.FaqListItem=e.FaqListItem;exports.LinkAttachment=e.LinkAttachment;exports.LockedAttachment=e.LockedAttachment;exports.MediaMessage=e.MediaMessage;exports.MessageAttachment=e.MessageAttachment;exports.MessageVoteButtons=e.MessageVoteButtons;exports.MessagingProvider=e.MessagingProvider;exports.MessagingShell=e.MessagingShell;exports.buildCompactMetaLabel=e.buildCompactMetaLabel;exports.formatFileSize=e.formatFileSize;exports.formatRelativeTime=e.formatRelativeTime;exports.getFileExtensionLabel=e.getFileExtensionLabel;exports.getMessageDisplayText=e.getMessageDisplayText;exports.isLinkAttachment=e.isLinkAttachment;exports.isUuidLike=e.isUuidLike;exports.messageAttachmentGroupPositionFromStream=e.bubbleGroupPositionFromStream;exports.normalizeLanguageCode=e.normalizeLanguageCode;exports.resolveConversationParticipant=e.resolveConversationParticipant;exports.resolveLinkAttachment=e.resolveLinkAttachment;exports.resolveMediaFromMessage=e.resolveMediaFromMessage;exports.resolveParticipantDisplayName=e.resolveParticipantDisplayName;exports.useComposerLocked=e.useComposerLocked;exports.useCustomMessage=e.useCustomMessage;exports.useMessageVote=e.useMessageVote;exports.useMessaging=e.useMessaging;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("./index-C1Zaiccm.cjs");exports.ActionButton=e.ActionButton;exports.Avatar=e.Avatar;exports.ChannelEmptyState=e.ChannelEmptyState;exports.ChannelList=e.ChannelList;exports.ChannelView=e.ChannelView;exports.CustomMessageProvider=e.CustomMessageProvider;exports.FaqList=e.FaqList;exports.FaqListItem=e.FaqListItem;exports.LinkAttachment=e.LinkAttachment;exports.LockedAttachment=e.LockedAttachment;exports.MediaMessage=e.MediaMessage;exports.MessageAttachment=e.MessageAttachment;exports.MessageVoteButtons=e.MessageVoteButtons;exports.MessagingProvider=e.MessagingProvider;exports.MessagingShell=e.MessagingShell;exports.buildCompactMetaLabel=e.buildCompactMetaLabel;exports.formatFileSize=e.formatFileSize;exports.formatRelativeTime=e.formatRelativeTime;exports.getFileExtensionLabel=e.getFileExtensionLabel;exports.getMessageDisplayText=e.getMessageDisplayText;exports.isLinkAttachment=e.isLinkAttachment;exports.isUuidLike=e.isUuidLike;exports.messageAttachmentGroupPositionFromStream=e.bubbleGroupPositionFromStream;exports.normalizeLanguageCode=e.normalizeLanguageCode;exports.resolveConversationParticipant=e.resolveConversationParticipant;exports.resolveLinkAttachment=e.resolveLinkAttachment;exports.resolveMediaFromMessage=e.resolveMediaFromMessage;exports.resolveParticipantDisplayName=e.resolveParticipantDisplayName;exports.useComposerLocked=e.useComposerLocked;exports.useCustomMessage=e.useCustomMessage;exports.useMessageVote=e.useMessageVote;exports.useMessaging=e.useMessaging;
2
2
  //# sourceMappingURL=index.cjs.map
package/dist/index.d.ts CHANGED
@@ -405,18 +405,13 @@ export declare interface ChannelViewProps {
405
405
  }
406
406
 
407
407
  export declare interface ComposerCardProps extends LockedAttachmentBaseProps {
408
- /**
409
- * The message's own text, shown as-is (not redacted yet — the message
410
- * hasn't been sent). Only used when `contentType` is `"text"`.
411
- */
412
- text?: string;
408
+ /** Placeholder shown in the title slot before the composer types one. */
409
+ placeholderTitle?: string;
413
410
  /** Placeholder shown in the amount slot before one is configured. */
414
411
  placeholderAmountText?: string;
415
412
  /**
416
- * Renders a persistent dismiss X on the thumbnail (media) or next to the
417
- * text (text mode); called to remove the draft attachment. Unrelated to
418
- * `TextCardProps.onDismiss`, which only appears for `isMine` after a
419
- * failed payment.
413
+ * When provided, renders a dismiss X in the thumbnail corner. Called when
414
+ * the composer clicks it to remove the attachment.
420
415
  */
421
416
  onDismiss?: () => void;
422
417
  /** Fired the first time the composer taps the thumbnail to preview. */
@@ -425,9 +420,8 @@ export declare interface ComposerCardProps extends LockedAttachmentBaseProps {
425
420
  * Lazily loads the underlying source so the composer can preview the
426
421
  * attachment they're about to send. Called the first time the thumbnail is
427
422
  * tapped; the returned source is cached and reused on subsequent toggles.
428
- * Ignored when `contentType` is `"text"`.
429
423
  */
430
- onFetchSource?: FetchSourceHandler;
424
+ onFetchSource?: () => Promise<LockedAttachmentSource | void>;
431
425
  /**
432
426
  * When provided, renders a pencil button in the body bottom-right that the
433
427
  * composer can use to edit the attachment metadata (e.g. open the price /
@@ -442,6 +436,12 @@ declare interface ComposerExtras {
442
436
  onDismiss?: () => void;
443
437
  }
444
438
 
439
+ /**
440
+ * @deprecated Renamed to `SentCardProps`. Drafting usages (with `onDismiss`)
441
+ * should migrate to `ComposerCardProps`.
442
+ */
443
+ export declare type CreatorCardProps = SentCardProps;
444
+
445
445
  export declare const CustomMessageProvider: Provider<Partial<CustomMessageRegistry>>;
446
446
 
447
447
  export declare interface CustomMessageRegistry {
@@ -479,13 +479,6 @@ export declare interface FaqListProps {
479
479
  avatarName?: string;
480
480
  }
481
481
 
482
- /**
483
- * Lazily fetches the underlying source (URL/thumbnail) for a locked
484
- * attachment. Returns `void` to signal "no source available" — the card
485
- * stays locked. Shared by `ComposerCardProps`/`MediaCardProps.onFetchSource`.
486
- */
487
- declare type FetchSourceHandler = () => Promise<LockedAttachmentSource | void>;
488
-
489
482
  declare interface FileAttachmentSharedProps extends MessageAttachmentBaseProps {
490
483
  /** Source URL of the file (used as the download target). */
491
484
  src?: string;
@@ -737,45 +730,33 @@ export declare interface LinkAttachmentSentCardProps extends LinkAttachmentBaseP
737
730
 
738
731
  export declare const LockedAttachment: {
739
732
  Composer: (props: ComposerCardProps) => JSX_2.Element;
740
- Text: (props: LockedAttachmentTextCardProps) => JSX_2.Element;
741
- Media: (props: LockedAttachmentMediaCardProps) => JSX_2.Element;
733
+ Sent: (props: SentCardProps) => JSX_2.Element;
734
+ Received: (props: ReceivedCardProps) => JSX_2.Element;
735
+ Creator: (props: SentCardProps) => JSX_2.Element;
736
+ Visitor: (props: ReceivedCardProps) => JSX_2.Element;
742
737
  };
743
738
 
744
739
  declare interface LockedAttachmentBaseProps {
745
740
  title?: string;
746
- /** Dimmed fallback shown in the title slot when `title` is unset (no attachment metadata yet — still drafting). */
747
- placeholderTitle?: string;
748
741
  mimeType?: string;
749
742
  thumbnailUrl?: string;
750
743
  detail?: string;
751
744
  amountText?: string;
745
+ paymentStatus?: PaymentStatus;
752
746
  /**
753
747
  * When provided with 2+ items, the card renders as a mixed-media carousel
754
748
  * (e.g. a couple of photos + a video) instead of a single thumbnail. Each
755
749
  * item brings its own thumbnail and optional source so that
756
- * `LockedAttachment.Composer` / `.Media` can share the same carousel
757
- * chrome.
750
+ * `LockedAttachment.Composer` / `.Sent` / `.Received` can all share the
751
+ * same carousel chrome.
758
752
  */
759
753
  gallery?: LockedAttachmentGalleryItem[];
760
- /**
761
- * "text" renders the card as a locked/plain chat bubble showing the
762
- * message's own text (skeleton-blurred until purchased) instead of a media
763
- * thumbnail card — for a paid text-only message. Media-only props
764
- * (`mimeType`, `thumbnailUrl`, `title`, `detail`, `gallery`) are ignored in
765
- * this mode. Defaults to `"media"`.
766
- */
767
- contentType?: 'text' | 'media';
768
754
  }
769
755
 
770
756
  export declare interface LockedAttachmentContextValue {
771
757
  isUnlocking: (id: string) => boolean;
772
758
  onUnlockClick?: (message: LocalMessage, channel: Channel) => void;
773
759
  onDownloadClick?: (message: LocalMessage, channel: Channel) => void;
774
- /**
775
- * Reveal the locked media's underlying source (URL/thumbnail). Not used
776
- * for a paid text message — the backend writes the real text directly onto
777
- * the message on purchase and `message.text` alone drives that reveal.
778
- */
779
760
  onFetchSource?: (message: LocalMessage, channel: Channel) => Promise<LockedAttachmentSource | void>;
780
761
  }
781
762
 
@@ -788,31 +769,6 @@ export declare interface LockedAttachmentGalleryItem {
788
769
  sourceUrl?: string;
789
770
  }
790
771
 
791
- export declare type LockedAttachmentMediaCardProps = (MediaCardSharedProps & {
792
- isMine: true;
793
- /** Dimmed fallback shown in the title slot when `title` is unset. */
794
- placeholderTitle?: string;
795
- /** Fired the first time the sender taps the thumbnail to preview their own attachment. */
796
- onPreviewClick?: () => void;
797
- }) | (MediaCardSharedProps & {
798
- isMine: false;
799
- /**
800
- * When true, shows a loading spinner on the Unlock button. Driven by
801
- * the LockedAttachmentContext (e.g. checkout in progress).
802
- */
803
- isUnlocking?: boolean;
804
- /**
805
- * Called when the recipient clicks Unlock on an unpaid attachment.
806
- * Use this to open a checkout flow. Omit to hide the Unlock button.
807
- */
808
- onUnlockClick?: () => void;
809
- /**
810
- * Called when the recipient clicks Download on an unlocked card.
811
- * Omit to hide the Download button.
812
- */
813
- onDownloadClick?: () => void;
814
- });
815
-
816
772
  export declare interface LockedAttachmentSource {
817
773
  /** Proxied URL used by the media player for in-app playback. */
818
774
  sourceUrl: string;
@@ -822,33 +778,6 @@ export declare interface LockedAttachmentSource {
822
778
  thumbnailUrl?: string;
823
779
  }
824
780
 
825
- export declare type LockedAttachmentTextCardProps = (TextCardSharedProps & {
826
- isMine: true;
827
- }) | (TextCardSharedProps & {
828
- isMine: false;
829
- /**
830
- * Called when the recipient clicks Unlock on an unpaid attachment.
831
- * Use this to open a checkout flow. Omit to hide the Unlock button.
832
- */
833
- onUnlockClick?: () => void;
834
- /**
835
- * When true, shows a loading spinner on the Unlock button. Driven by
836
- * the LockedAttachmentContext (e.g. checkout in progress).
837
- */
838
- isUnlocking?: boolean;
839
- });
840
-
841
- declare interface MediaCardSharedProps {
842
- title?: string;
843
- mimeType?: string;
844
- thumbnailUrl?: string;
845
- detail?: string;
846
- amountText?: string;
847
- paymentStatus?: PaymentStatus;
848
- gallery?: LockedAttachmentGalleryItem[];
849
- onFetchSource?: FetchSourceHandler;
850
- }
851
-
852
781
  export declare const MediaMessage: default_2.FC<MediaMessageProps> & {
853
782
  Creator: default_2.FC<{
854
783
  message: LocalMessage;
@@ -1255,7 +1184,6 @@ export declare interface MessageMetadata {
1255
1184
  amount_text?: string;
1256
1185
  payment_status?: PaymentStatus;
1257
1186
  attachment_title?: string;
1258
- attachment_content_type?: 'text' | 'media';
1259
1187
  attachment_mime_type?: string;
1260
1188
  attachment_thumbnail?: string;
1261
1189
  attachment_detail?: string;
@@ -1468,6 +1396,31 @@ declare interface PdfAttachmentSharedProps extends MessageAttachmentBaseProps {
1468
1396
  onClick?: (index: number) => boolean | void;
1469
1397
  }
1470
1398
 
1399
+ export declare interface ReceivedCardProps extends LockedAttachmentBaseProps {
1400
+ /**
1401
+ * Called when the recipient clicks Unlock on an unpaid attachment.
1402
+ * Use this to open a checkout flow. Omit to hide the Unlock button.
1403
+ */
1404
+ onUnlockClick?: () => void;
1405
+ /**
1406
+ * Called to fetch the attachment source — fired automatically when
1407
+ * `paymentStatus` transitions to `'paid'`, or immediately on click when
1408
+ * `paymentStatus` is already `'paid'`. Return a `LockedAttachmentSource`
1409
+ * to unlock the card.
1410
+ */
1411
+ onFetchSource?: () => Promise<LockedAttachmentSource | void>;
1412
+ /**
1413
+ * Called when the recipient clicks Download on an unlocked card.
1414
+ * Omit to hide the Download button.
1415
+ */
1416
+ onDownloadClick?: () => void;
1417
+ /**
1418
+ * When true, shows a loading spinner on the Unlock button.
1419
+ * Driven by the LockedAttachmentContext (e.g. checkout in progress).
1420
+ */
1421
+ isUnlocking?: boolean;
1422
+ }
1423
+
1471
1424
  /**
1472
1425
  * Resolves the member to display as the conversation's "other party".
1473
1426
  *
@@ -1490,16 +1443,17 @@ export declare function resolveMediaFromMessage(message: LocalMessage): MediaMes
1490
1443
  */
1491
1444
  export declare function resolveParticipantDisplayName(user?: ParticipantDisplayUser | null): string;
1492
1445
 
1493
- declare interface TextCardSharedProps {
1494
- amountText?: string;
1495
- paymentStatus?: PaymentStatus;
1446
+ export declare interface SentCardProps extends LockedAttachmentBaseProps {
1447
+ /** Placeholder shown in the title slot when no title is set. */
1448
+ placeholderTitle?: string;
1449
+ /** Fired the first time the sender taps the thumbnail to preview their own attachment. */
1450
+ onPreviewClick?: () => void;
1496
1451
  /**
1497
- * The message's real, revealed content shown instead of the skeleton
1498
- * loader once `paymentStatus` is `'paid'`. Ignored otherwise. Lets the
1499
- * caller supply its own text renderer (e.g. Stream's `MessageText`)
1500
- * without `LockedAttachment` depending on it.
1452
+ * Lazily loads the underlying source so the sender can preview the attachment.
1453
+ * Called the first time the thumbnail is tapped; the returned source is cached
1454
+ * and reused on subsequent toggles.
1501
1455
  */
1502
- children?: default_2.ReactNode;
1456
+ onFetchSource?: () => Promise<LockedAttachmentSource | void>;
1503
1457
  }
1504
1458
 
1505
1459
  /**
@@ -1570,6 +1524,9 @@ declare interface VideoAttachmentSharedProps extends MessageAttachmentBaseProps
1570
1524
  onClick?: (index: number) => boolean | void;
1571
1525
  }
1572
1526
 
1527
+ /** @deprecated Renamed to `ReceivedCardProps`. */
1528
+ export declare type VisitorCardProps = ReceivedCardProps;
1529
+
1573
1530
  export declare type VoteSelection = 'up' | 'down' | null;
1574
1531
 
1575
1532
  export { }
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import { a as e, b as t, C as i, c as o, d as n, e as m, F as r, f as g, L as l, h as M, M as c, i as u, j as L, k as h, l as d, m as p, n as v, o as C, p as A, q as k, s as F, t as P, u as b, v as f, w as x, x as y, y as S, z as q, B as z, D as B, E as D, G as E } from "./index-B8gqCioX.js";
1
+ import { a as e, b as t, C as i, c as o, d as n, e as m, F as r, f as g, L as l, h as M, M as c, i as u, j as L, k as h, l as d, m as p, n as v, o as C, p as A, q as k, s as F, t as P, u as b, v as f, w as x, x as y, y as S, z as q, B as z, D as B, E as D, G as E } from "./index-Bv79lb0u.js";
2
2
  export {
3
3
  e as ActionButton,
4
4
  t as Avatar,
package/dist/testing.d.ts CHANGED
@@ -47,7 +47,6 @@ export declare interface MessageMetadata {
47
47
  amount_text?: string;
48
48
  payment_status?: PaymentStatus;
49
49
  attachment_title?: string;
50
- attachment_content_type?: 'text' | 'media';
51
50
  attachment_mime_type?: string;
52
51
  attachment_thumbnail?: string;
53
52
  attachment_detail?: string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@linktr.ee/messaging-react",
3
- "version": "3.9.0-rc-1783472582",
3
+ "version": "3.9.0-rc-1783568295",
4
4
  "description": "React messaging components built on messaging-core for web applications",
5
5
  "type": "module",
6
6
  "main": "dist/index.cjs",
@@ -50,7 +50,7 @@
50
50
  },
51
51
  "dependencies": {
52
52
  "@linktr.ee/component-library": "11.8.6",
53
- "@linktr.ee/messaging-core": "2.3.0-rc-1783472582",
53
+ "@linktr.ee/messaging-core": "2.3.0-rc-1783568295",
54
54
  "@phosphor-icons/react": "^2.1.10"
55
55
  },
56
56
  "devDependencies": {
@@ -126,7 +126,6 @@ interface TemplateProps {
126
126
  attachment_mime_type?: string
127
127
  attachment_thumbnail?: string
128
128
  attachment_detail?: string
129
- attachment_content_type?: 'text' | 'media'
130
129
  }
131
130
  }>
132
131
  }
@@ -417,59 +416,7 @@ LockedAttachment.args = {
417
416
  ],
418
417
  }
419
418
 
420
- export const LockedTextAttachment: StoryFn<TemplateProps> = Template.bind({})
421
- LockedTextAttachment.args = {
422
- messages: [
423
- {
424
- id: 'msg-1',
425
- text: 'Can you send me the details privately?',
426
- user: storyUsers.visitor,
427
- },
428
- {
429
- id: 'msg-2',
430
- // Empty text: the real content is redacted server-side until purchase,
431
- // so the bubble renders the blurred placeholder instead.
432
- text: '',
433
- user: storyUsers.creator,
434
- metadata: {
435
- custom_type: 'MESSAGE_ATTACHMENT',
436
- amount_text: 'AU$4.99',
437
- attachment_content_type: 'text',
438
- },
439
- },
440
- {
441
- id: 'msg-3',
442
- text: '',
443
- user: storyUsers.creator,
444
- metadata: {
445
- custom_type: 'MESSAGE_ATTACHMENT',
446
- amount_text: 'AU$4.99',
447
- payment_status: 'paid',
448
- attachment_content_type: 'text',
449
- },
450
- },
451
- {
452
- id: 'msg-4',
453
- // Buyer reveal: backend writes the real text back onto the message.
454
- text: "Here's the address — see you Thursday at 7!",
455
- user: storyUsers.creator,
456
- metadata: {
457
- custom_type: 'MESSAGE_ATTACHMENT',
458
- amount_text: 'AU$4.99',
459
- payment_status: 'paid',
460
- attachment_content_type: 'text',
461
- },
462
- },
463
- ],
464
- }
465
- LockedTextAttachment.parameters = {
466
- docs: {
467
- description: {
468
- story:
469
- 'A paid text-only message renders as a regular bubble with blurred placeholder copy (msg-2: pending, msg-3: purchased-but-not-yet-revealed) until the real text is revealed (msg-4).',
470
- },
471
- },
472
- }
419
+
473
420
 
474
421
  export const ChatbotVariants: StoryFn<TemplateProps> = Template.bind({})
475
422
  ChatbotVariants.args = {
@@ -47,14 +47,6 @@ export const isAttachmentMessage = (message: LocalMessage): boolean => {
47
47
  return message.metadata?.custom_type === 'MESSAGE_ATTACHMENT'
48
48
  }
49
49
 
50
- export const isTextAttachmentMessage = (message: LocalMessage): boolean => {
51
- return isAttachmentMessage(message) && message.metadata?.attachment_content_type === 'text'
52
- }
53
-
54
- export const isMediaAttachmentMessage = (message: LocalMessage): boolean => {
55
- return isAttachmentMessage(message) && message.metadata?.attachment_content_type !== 'text'
56
- }
57
-
58
50
  /** Check if a message has a tip/paid tag (both render the same) */
59
51
  export const isTipOrPaidMessage = (message: LocalMessage): boolean => {
60
52
  return isTipMessage(message) || isPaidMessage(message)
@@ -34,15 +34,15 @@ import { getMessageDisplayText } from '../../utils/getMessageDisplayText'
34
34
  import { Avatar } from '../Avatar'
35
35
  import LockedAttachment from '../LockedAttachment'
36
36
  import { isLinkAttachment } from '../MediaMessage'
37
- import { bubbleGroupPositionFromStream as messageAttachmentGroupPositionFromStream } from '../MessageAttachment'
37
+ import {
38
+ bubbleGroupPositionFromStream as messageAttachmentGroupPositionFromStream,
39
+ } from '../MessageAttachment'
38
40
 
39
41
  import { useCustomMessage } from './context'
40
42
  import {
41
43
  MessageTag,
42
44
  isAttachmentMessage,
43
45
  isChatbotMessage,
44
- isMediaAttachmentMessage,
45
- isTextAttachmentMessage,
46
46
  isTipOnlyMessage,
47
47
  } from './MessageTag'
48
48
  import { MessageVoteButtons } from './MessageVoteButtons'
@@ -276,51 +276,12 @@ const CustomMessageWithContext = (props: CustomMessageWithContextProps) => {
276
276
  marginInlineStart: 0,
277
277
  }}
278
278
  >
279
- {isTipOnly ? (
280
- <MessageTag message={message} standalone />
281
- ) : isTextAttachmentMessage(message) ? (
282
- <div className="str-chat__message-bubble-wrapper">
283
- <div className="flex items-center gap-2">
284
- {isMine && MessageActions && <MessageActions />}
285
- {isMine ? (
286
- <LockedAttachment.Text
287
- isMine={true}
288
- amountText={message.metadata?.amount_text}
289
- paymentStatus={message.metadata?.payment_status}
290
- >
291
- {message.text && (
292
- <MessageText
293
- message={displayMessage}
294
- renderText={renderText}
295
- />
296
- )}
297
- </LockedAttachment.Text>
298
- ) : (
299
- <LockedAttachment.Text
300
- isMine={false}
301
- amountText={message.metadata?.amount_text}
302
- paymentStatus={message.metadata?.payment_status}
303
- isUnlocking={isUnlocking(message.id)}
304
- onUnlockClick={() => onUnlockClick?.(message, channel)}
305
- >
306
- {message.text && (
307
- <MessageText
308
- message={displayMessage}
309
- renderText={renderText}
310
- />
311
- )}
312
- </LockedAttachment.Text>
313
- )}
314
- {!isMine && MessageActions && <MessageActions />}
315
- </div>
316
- </div>
317
- ) : isMediaAttachmentMessage(message) ? (
279
+ {isAttachment ? (
318
280
  <div className="str-chat__message-bubble-wrapper">
319
- <div className="flex items-center gap-2">
320
- {isMine && MessageActions && <MessageActions />}
321
- {isMine ? (
322
- <LockedAttachment.Media
323
- isMine={true}
281
+ {isMine ? (
282
+ <div className="flex items-center gap-2">
283
+ {MessageActions && <MessageActions />}
284
+ <LockedAttachment.Sent
324
285
  title={message.metadata?.attachment_title}
325
286
  mimeType={message.metadata?.attachment_mime_type}
326
287
  thumbnailUrl={message.metadata?.attachment_thumbnail}
@@ -328,15 +289,14 @@ const CustomMessageWithContext = (props: CustomMessageWithContextProps) => {
328
289
  detail={message.metadata?.attachment_detail}
329
290
  paymentStatus={message.metadata?.payment_status}
330
291
  onPreviewClick={() => onUnlockClick?.(message, channel)}
331
- onFetchSource={
332
- onFetchSource
333
- ? () => onFetchSource(message, channel)
334
- : undefined
292
+ onFetchSource={async () =>
293
+ await onFetchSource?.(message, channel)
335
294
  }
336
295
  />
337
- ) : (
338
- <LockedAttachment.Media
339
- isMine={false}
296
+ </div>
297
+ ) : (
298
+ <div className="flex items-center gap-2">
299
+ <LockedAttachment.Received
340
300
  title={message.metadata?.attachment_title}
341
301
  mimeType={message.metadata?.attachment_mime_type}
342
302
  thumbnailUrl={message.metadata?.attachment_thumbnail}
@@ -345,16 +305,14 @@ const CustomMessageWithContext = (props: CustomMessageWithContextProps) => {
345
305
  paymentStatus={message.metadata?.payment_status}
346
306
  isUnlocking={isUnlocking(message.id)}
347
307
  onUnlockClick={() => onUnlockClick?.(message, channel)}
348
- onFetchSource={
349
- onFetchSource
350
- ? () => onFetchSource(message, channel)
351
- : undefined
308
+ onFetchSource={async () =>
309
+ await onFetchSource?.(message, channel)
352
310
  }
353
311
  onDownloadClick={() => onDownloadClick?.(message, channel)}
354
312
  />
355
- )}
356
- {!isMine && MessageActions && <MessageActions />}
357
- </div>
313
+ {MessageActions && <MessageActions />}
314
+ </div>
315
+ )}
358
316
  {message.text && (
359
317
  <div className="str-chat__message-bubble">
360
318
  <MessageText
@@ -364,6 +322,9 @@ const CustomMessageWithContext = (props: CustomMessageWithContextProps) => {
364
322
  </div>
365
323
  )}
366
324
  </div>
325
+ ) : isTipOnly ? (
326
+ /* Tip-only messages render as a standalone bubble */
327
+ <MessageTag message={message} standalone />
367
328
  ) : canRenderAttachmentsInToolkit ? (
368
329
  <div className="str-chat__message-bubble-wrapper">
369
330
  <div
@@ -86,6 +86,9 @@ const CustomMessageInputInner: React.FC = () => {
86
86
  // gain focus automatically.
87
87
  // eslint-disable-next-line jsx-a11y/no-autofocus
88
88
  autoFocus={!disabled}
89
+ // Enter sends (Shift+Enter inserts a newline), so label the
90
+ // on-screen keyboard's return key accordingly.
91
+ enterKeyHint="send"
89
92
  maxRows={4}
90
93
  readOnly={disabled}
91
94
  tabIndex={disabled ? -1 : undefined}