2023-01-03 11:55:46 -08:00
|
|
|
// Copyright 2020 Signal Messenger, LLC
|
2020-11-02 17:19:52 -08:00
|
|
|
// SPDX-License-Identifier: AGPL-3.0-only
|
|
|
|
|
2025-05-05 09:48:36 -07:00
|
|
|
import React, { StrictMode } from 'react';
|
2025-01-28 07:31:42 -10:00
|
|
|
import EmbedBlot from '@signalapp/quill-cjs/blots/embed';
|
2025-07-15 16:32:11 -07:00
|
|
|
import { createRoot } from 'react-dom/client';
|
2025-01-28 07:31:42 -10:00
|
|
|
|
2020-11-02 17:19:52 -08:00
|
|
|
import { Emojify } from '../../components/conversation/Emojify';
|
2023-09-14 13:04:48 -04:00
|
|
|
import { normalizeAci } from '../../util/normalizeAci';
|
2021-10-26 14:15:33 -05:00
|
|
|
import type { MentionBlotValue } from '../util';
|
2025-04-09 15:14:28 -07:00
|
|
|
import { FunEmojiLocalizationProvider } from '../../components/fun/FunEmojiLocalizationProvider';
|
2020-11-02 17:19:52 -08:00
|
|
|
|
2025-01-28 07:31:42 -10:00
|
|
|
export class MentionBlot extends EmbedBlot {
|
2021-11-12 17:44:20 -06:00
|
|
|
static override blotName = 'mention';
|
2020-11-02 17:19:52 -08:00
|
|
|
|
2021-11-12 17:44:20 -06:00
|
|
|
static override className = 'mention-blot';
|
2020-11-02 17:19:52 -08:00
|
|
|
|
2021-11-12 17:44:20 -06:00
|
|
|
static override tagName = 'span';
|
2020-11-02 17:19:52 -08:00
|
|
|
|
2021-11-12 17:44:20 -06:00
|
|
|
static override create(value: MentionBlotValue): Node {
|
2020-11-02 17:19:52 -08:00
|
|
|
const node = super.create(undefined) as HTMLElement;
|
|
|
|
|
|
|
|
MentionBlot.buildSpan(value, node);
|
|
|
|
|
|
|
|
return node;
|
|
|
|
}
|
|
|
|
|
2021-11-12 17:44:20 -06:00
|
|
|
static override value(node: HTMLElement): MentionBlotValue {
|
2023-08-16 22:54:39 +02:00
|
|
|
const { aci, title } = node.dataset;
|
|
|
|
if (aci === undefined || title === undefined) {
|
2020-11-05 13:18:42 -08:00
|
|
|
throw new Error(
|
2023-08-16 22:54:39 +02:00
|
|
|
`Failed to make MentionBlot with aci: ${aci}, title: ${title}`
|
2020-11-05 13:18:42 -08:00
|
|
|
);
|
|
|
|
}
|
|
|
|
|
2020-11-02 17:19:52 -08:00
|
|
|
return {
|
2023-08-16 22:54:39 +02:00
|
|
|
aci: normalizeAci(aci, 'quill mention blot'),
|
2020-11-02 17:19:52 -08:00
|
|
|
title,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2020-11-05 13:18:42 -08:00
|
|
|
static buildSpan(mention: MentionBlotValue, node: HTMLElement): void {
|
2023-08-16 22:54:39 +02:00
|
|
|
node.setAttribute('data-aci', mention.aci || '');
|
2020-11-05 13:18:42 -08:00
|
|
|
node.setAttribute('data-title', mention.title || '');
|
2021-09-01 13:42:12 -07:00
|
|
|
node.setAttribute('contenteditable', 'false');
|
2020-11-02 17:19:52 -08:00
|
|
|
|
|
|
|
const mentionSpan = document.createElement('span');
|
|
|
|
|
2025-07-15 16:32:11 -07:00
|
|
|
createRoot(mentionSpan).render(
|
2025-05-05 09:48:36 -07:00
|
|
|
<StrictMode>
|
|
|
|
<FunEmojiLocalizationProvider i18n={window.i18n}>
|
|
|
|
<span className="module-composition-input__at-mention">
|
|
|
|
<bdi>
|
|
|
|
@
|
|
|
|
<Emojify text={mention.title} />
|
|
|
|
</bdi>
|
|
|
|
</span>
|
|
|
|
</FunEmojiLocalizationProvider>
|
2025-07-15 16:32:11 -07:00
|
|
|
</StrictMode>
|
2020-11-02 17:19:52 -08:00
|
|
|
);
|
|
|
|
|
|
|
|
node.appendChild(mentionSpan);
|
|
|
|
}
|
|
|
|
}
|