Linkify untruncated text
This commit is contained in:
parent
8ea030074e
commit
6297e12803
8 changed files with 48 additions and 6 deletions
|
@ -704,6 +704,7 @@ export function StoryViewer({
|
|||
onExpandSpoiler={data => setIsSpoilerExpanded(data)}
|
||||
renderLocation={RenderLocation.StoryViewer}
|
||||
text={caption.text}
|
||||
originalText={caption.text}
|
||||
/>
|
||||
{caption.hasReadMore && !hasExpandedCaption && (
|
||||
<button
|
||||
|
|
|
@ -40,6 +40,7 @@ const createProps = (overrideProps: Partial<Props> = {}): Props => ({
|
|||
showConversation:
|
||||
overrideProps.showConversation || action('showConversation'),
|
||||
text: overrideProps.text || '',
|
||||
originalText: overrideProps.originalText || overrideProps.text || '',
|
||||
textAttachment: overrideProps.textAttachment || {
|
||||
pending: false,
|
||||
},
|
||||
|
@ -525,3 +526,15 @@ export function ZalgoText(): JSX.Element {
|
|||
|
||||
return <MessageBody {...props} />;
|
||||
}
|
||||
|
||||
export function LinkOverReadMoreBoundary(): JSX.Element {
|
||||
const text = 'https://hello.me';
|
||||
const originalText = 'https://hello.me123';
|
||||
|
||||
const props = createProps({
|
||||
text,
|
||||
originalText,
|
||||
});
|
||||
|
||||
return <MessageBody {...props} />;
|
||||
}
|
||||
|
|
|
@ -60,6 +60,7 @@ export type Props = {
|
|||
AttachmentType,
|
||||
'pending' | 'digest' | 'key' | 'wasTooBig' | 'path'
|
||||
>;
|
||||
originalText: string;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -84,8 +85,10 @@ export function MessageBody({
|
|||
showConversation,
|
||||
text,
|
||||
textAttachment,
|
||||
originalText,
|
||||
}: Props): JSX.Element {
|
||||
const shouldDisableLinks = disableLinks || !shouldLinkifyMessage(text);
|
||||
const shouldDisableLinks =
|
||||
disableLinks || !shouldLinkifyMessage(originalText);
|
||||
const textWithSuffix =
|
||||
textAttachment?.pending || onIncreaseTextLength || textAttachment?.wasTooBig
|
||||
? `${text}...`
|
||||
|
@ -177,6 +180,7 @@ export function MessageBody({
|
|||
i18n={i18n}
|
||||
isSpoilerExpanded={isSpoilerExpanded}
|
||||
messageText={textWithSuffix}
|
||||
originalMessageText={originalText}
|
||||
onMentionTrigger={conversationId =>
|
||||
showConversation?.({ conversationId })
|
||||
}
|
||||
|
|
|
@ -83,6 +83,7 @@ export function MessageBodyReadMore({
|
|||
showConversation={showConversation}
|
||||
text={slicedText}
|
||||
textAttachment={textAttachment}
|
||||
originalText={text}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -45,6 +45,7 @@ type Props = {
|
|||
i18n: LocalizerType;
|
||||
isSpoilerExpanded: Record<number, boolean>;
|
||||
messageText: string;
|
||||
originalMessageText: string;
|
||||
onExpandSpoiler?: (data: Record<number, boolean>) => void;
|
||||
onMentionTrigger: (conversationId: string) => void;
|
||||
renderLocation: RenderLocation;
|
||||
|
@ -64,9 +65,12 @@ export function MessageTextRenderer({
|
|||
onMentionTrigger,
|
||||
renderLocation,
|
||||
textLength,
|
||||
originalMessageText,
|
||||
}: Props): JSX.Element {
|
||||
const finalNodes = React.useMemo(() => {
|
||||
const links = disableLinks ? [] : extractLinks(messageText);
|
||||
const links = disableLinks
|
||||
? []
|
||||
: extractLinks(messageText, originalMessageText);
|
||||
|
||||
// We need mentions to come last; they can't have children for proper rendering
|
||||
const sortedRanges = sortBy(bodyRanges, range =>
|
||||
|
@ -104,7 +108,7 @@ export function MessageTextRenderer({
|
|||
|
||||
// Group all contigusous spoilers to create one parent spoiler element in the DOM
|
||||
return groupContiguousSpoilers(nodes);
|
||||
}, [bodyRanges, disableLinks, messageText, textLength]);
|
||||
}, [bodyRanges, disableLinks, messageText, originalMessageText, textLength]);
|
||||
|
||||
return (
|
||||
<>
|
||||
|
@ -424,19 +428,34 @@ function renderText({
|
|||
}
|
||||
|
||||
export function extractLinks(
|
||||
messageText: string
|
||||
messageText: string,
|
||||
// Full, untruncated message text
|
||||
originalMessageText: string
|
||||
): ReadonlyArray<BodyRange<{ url: string }>> {
|
||||
// to support emojis immediately before links
|
||||
// we replace emojis with a space for each byte
|
||||
const matches = linkify.match(
|
||||
messageText.replace(EMOJI_REGEXP, s => ' '.repeat(s.length))
|
||||
originalMessageText.replace(EMOJI_REGEXP, s => ' '.repeat(s.length))
|
||||
);
|
||||
|
||||
if (matches == null) {
|
||||
return [];
|
||||
}
|
||||
|
||||
return matches.map(match => {
|
||||
// Only return matches present in the `messageText`
|
||||
const currentMatches = matches.filter(({ index, lastIndex, url }) => {
|
||||
if (index >= messageText.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (lastIndex > messageText.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return messageText.slice(index, lastIndex) === url;
|
||||
});
|
||||
|
||||
return currentMatches.map(match => {
|
||||
return {
|
||||
start: match.index,
|
||||
length: match.lastIndex - match.index,
|
||||
|
|
|
@ -378,6 +378,7 @@ export function Quote(props: Props): JSX.Element | null {
|
|||
isSpoilerExpanded={EMPTY_OBJECT}
|
||||
renderLocation={RenderLocation.Quote}
|
||||
text={text}
|
||||
originalText={text}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
|
|
|
@ -170,6 +170,7 @@ export const ConversationListItem: FunctionComponent<Props> = React.memo(
|
|||
prefix={draftPreview.prefix}
|
||||
renderLocation={RenderLocation.ConversationList}
|
||||
text={draftPreview.text}
|
||||
originalText={draftPreview.text}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
|
@ -191,6 +192,7 @@ export const ConversationListItem: FunctionComponent<Props> = React.memo(
|
|||
prefix={lastMessage.prefix}
|
||||
renderLocation={RenderLocation.ConversationList}
|
||||
text={lastMessage.text}
|
||||
originalText={lastMessage.text}
|
||||
/>
|
||||
);
|
||||
if (lastMessage.status) {
|
||||
|
|
|
@ -168,6 +168,7 @@ export const MessageSearchResult: FunctionComponent<PropsType> = React.memo(
|
|||
const messageText = (
|
||||
<MessageTextRenderer
|
||||
messageText={cleanedSnippet}
|
||||
originalMessageText={cleanedSnippet}
|
||||
bodyRanges={displayBodyRanges}
|
||||
direction={undefined}
|
||||
disableLinks
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue