mirror of
https://github.com/suitenumerique/messages.git
synced 2026-04-25 17:15:21 +02:00
🔥(frontend) remove starred from here (#588)
The user was able to starred a thread from a message to act like a pointer but this feature is too confusing so we prefer to remove it.
This commit is contained in:
committed by
GitHub
parent
b1d455022c
commit
b6e4ef2974
@@ -44,11 +44,6 @@ test.describe("Thread starred", () => {
|
||||
// Star the thread
|
||||
await starButton.click();
|
||||
|
||||
// Verify the starred marker appears in thread view
|
||||
await expect(
|
||||
page.getByText("This thread has been starred."),
|
||||
).toBeVisible();
|
||||
|
||||
// Verify the button updates to "Unstar"
|
||||
await expect(
|
||||
page.getByRole("button", { name: "Unstar this thread" }),
|
||||
@@ -87,11 +82,6 @@ test.describe("Thread starred", () => {
|
||||
// Unstar the thread
|
||||
await unstarButton.click();
|
||||
|
||||
// Verify the starred marker disappears
|
||||
await expect(
|
||||
page.getByText("This thread has been starred."),
|
||||
).not.toBeVisible();
|
||||
|
||||
// Verify the button reverts to "Star this thread"
|
||||
await expect(
|
||||
page.getByRole("button", { name: "Star this thread" }),
|
||||
|
||||
@@ -471,7 +471,6 @@
|
||||
"Split thread from here": "Split thread from here",
|
||||
"Star {{count}} threads_one": "Star {{count}} thread",
|
||||
"Star {{count}} threads_other": "Star {{count}} threads",
|
||||
"Star from here": "Star from here",
|
||||
"Star this thread": "Star this thread",
|
||||
"Starred": "Starred",
|
||||
"Start typing...": "Start typing...",
|
||||
@@ -525,7 +524,6 @@
|
||||
"This signature is forced": "This signature is forced",
|
||||
"This thread has been reported as spam.": "This thread has been reported as spam.",
|
||||
"This thread has been reported as spam. For your security, downloading attachments has been disabled.": "This thread has been reported as spam. For your security, downloading attachments has been disabled.",
|
||||
"This thread has been starred.": "This thread has been starred.",
|
||||
"This will move this message and all following messages to a new thread. Continue?": "This will move this message and all following messages to a new thread. Continue?",
|
||||
"Those message templates are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.": "Those message templates are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.",
|
||||
"Those signatures are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.": "Those signatures are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.",
|
||||
|
||||
@@ -520,7 +520,6 @@
|
||||
"Star {{count}} threads_one": "Suivre {{count}} conversation",
|
||||
"Star {{count}} threads_many": "Suivre {{count}} conversations",
|
||||
"Star {{count}} threads_other": "Suivre {{count}} conversations",
|
||||
"Star from here": "Suivre à partir d'ici",
|
||||
"Star this thread": "Suivre cette conversation",
|
||||
"Starred": "Suivi",
|
||||
"Start typing...": "Commencez à écrire...",
|
||||
@@ -575,7 +574,6 @@
|
||||
"This signature is forced": "Cette signature est forcée",
|
||||
"This thread has been reported as spam.": "Cette conversation a été signalée comme spam.",
|
||||
"This thread has been reported as spam. For your security, downloading attachments has been disabled.": "Cette conversation a été signalée comme spam. Pour votre sécurité, le téléchargement des pièces jointes a été désactivé.",
|
||||
"This thread has been starred.": "Cette conversation a été marquée pour suivi.",
|
||||
"This will move this message and all following messages to a new thread. Continue?": "Cela déplacera ce message et tous les messages suivants dans une nouvelle conversation. Continuer ?",
|
||||
"Those message templates are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.": "Ces modèles de message sont liés à la boîte aux lettres \"{{mailbox}}\". Dans le cas d'une boîte aux lettres partagée, tous les autres utilisateurs de la boîte aux lettres pourront les utiliser.",
|
||||
"Those signatures are linked to the mailbox \"{{mailbox}}\". In case of a shared mailbox, all other mailbox users will be able to use them.": "Ces signatures sont liées à la boîte aux lettres \"{{mailbox}}\". Dans le cas d'une boîte aux lettres partagée, tous les autres utilisateurs de la boîte aux lettres pourront les utiliser.",
|
||||
|
||||
@@ -1,32 +0,0 @@
|
||||
.starred-marker {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: var(--c--globals--spacings--xs);
|
||||
padding-block: var(--c--globals--spacings--xs);
|
||||
padding-right: var(--c--globals--spacings--sm);
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.starred-marker::after {
|
||||
display: block;
|
||||
content: '';
|
||||
height: 1px;
|
||||
background-color: var(--c--contextuals--background--semantic--neutral--primary);
|
||||
width: 8px;
|
||||
}
|
||||
|
||||
.starred-marker__label {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: var(--c--globals--spacings--3xs);
|
||||
font-size: var(--c--globals--font--sizes--xs);
|
||||
color: var(--c--contextuals--background--semantic--neutral--primary);
|
||||
font-style: italic;
|
||||
line-height: 1;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.starred-marker__icon {
|
||||
font-size: var(--c--globals--font--sizes--sm);
|
||||
color: var(--c--contextuals--background--semantic--neutral--primary);
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
import { useTranslation } from "react-i18next"
|
||||
import { Icon, IconType } from "@gouvfr-lasuite/ui-kit"
|
||||
|
||||
export const StarredMarker = () => {
|
||||
const { t } = useTranslation()
|
||||
|
||||
return (
|
||||
<div className="starred-marker">
|
||||
<span className="starred-marker__label">
|
||||
<Icon name="star" type={IconType.FILLED} className="starred-marker__icon" />
|
||||
{t("This thread has been starred.")}
|
||||
</span>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@@ -7,7 +7,6 @@ import { getRequestUrl } from "@/features/api/utils";
|
||||
import { useMailboxContext } from "@/features/providers/mailbox";
|
||||
import usePrint from "@/features/message/use-print";
|
||||
import useRead from "@/features/message/use-read";
|
||||
import useStarred from "@/features/message/use-starred";
|
||||
import useSplitThread from "@/features/message/use-split-thread";
|
||||
import useTrash from "@/features/message/use-trash";
|
||||
import { ThreadMessageActionsProps } from "./types";
|
||||
@@ -25,9 +24,8 @@ const ThreadMessageActions = ({
|
||||
const [isDropdownOpen, setIsDropdownOpen] = useState(false);
|
||||
|
||||
// Hooks and state specific to actions
|
||||
const { unselectThread, selectedThread, selectedMailbox } = useMailboxContext();
|
||||
const { unselectThread, selectedThread } = useMailboxContext();
|
||||
const { markAsReadAt } = useRead();
|
||||
const { markAsStarred } = useStarred();
|
||||
const { markAsTrashed } = useTrash();
|
||||
const { splitThread } = useSplitThread();
|
||||
const { print } = usePrint();
|
||||
@@ -60,14 +58,6 @@ const ThreadMessageActions = ({
|
||||
}
|
||||
}, [message.id, message.created_at, unselectThread, selectedThread, markAsReadAt]);
|
||||
|
||||
const starredAt = selectedThread?.accesses.find(a => a.mailbox.id === selectedMailbox?.id)?.starred_at ?? null;
|
||||
const isAlreadyStarredFromHere = starredAt === message.created_at;
|
||||
|
||||
const handleStarredFrom = useCallback(() => {
|
||||
if (!selectedThread) return;
|
||||
markAsStarred({ threadIds: [selectedThread.id], starredAt: message.created_at! });
|
||||
}, [selectedThread, message.created_at, markAsStarred]);
|
||||
|
||||
const handleMarkAsTrashed = useCallback(() => {
|
||||
markAsTrashed({ messageIds: [message.id] });
|
||||
}, [markAsTrashed, message.id]);
|
||||
@@ -115,11 +105,6 @@ const ThreadMessageActions = ({
|
||||
icon: <Icon type={IconType.FILLED} name="mark_email_unread" />,
|
||||
callback: () => toggleReadStateFrom(true)
|
||||
}]),
|
||||
...(!isAlreadyStarredFromHere && hasSiblingMessages ? [{
|
||||
label: t('Star from here'),
|
||||
icon: <Icon type={IconType.FILLED} name="star_border" />,
|
||||
callback: handleStarredFrom,
|
||||
}] : []),
|
||||
...(canSplitThread ? [{
|
||||
label: t('Split thread from here'),
|
||||
icon: <Icon type={IconType.FILLED} name="call_split" />,
|
||||
|
||||
@@ -12,7 +12,6 @@ import { SKIP_LINK_TARGET_ID } from "@/features/ui/components/skip-link"
|
||||
import { useTranslation } from "react-i18next"
|
||||
import { ThreadViewLabelsList } from "./components/thread-view-labels-list"
|
||||
import { ThreadSummary } from "./components/thread-summary";
|
||||
import { StarredMarker } from "./components/starred-marker";
|
||||
import clsx from "clsx";
|
||||
import ThreadViewProvider, { useThreadViewContext } from "./provider";
|
||||
import useSpam from "@/features/message/use-spam";
|
||||
@@ -58,18 +57,6 @@ const ThreadViewComponent = ({ messages, mailboxId, thread, showTrashedMessages,
|
||||
}
|
||||
return acc;
|
||||
}, messages[0]);
|
||||
const starredAt = thread.accesses.find(a => a.mailbox.id === mailboxId)?.starred_at ?? null;
|
||||
const starredMarkerInsertIndex = useMemo(() => {
|
||||
// Find insertion index: marker goes after the last message whose created_at <= starred_at
|
||||
let starredInsertIndex = null;
|
||||
if (starredAt) {
|
||||
starredInsertIndex = messages.findLastIndex((message) => {
|
||||
return message.created_at <= starredAt
|
||||
});
|
||||
return starredInsertIndex;
|
||||
}
|
||||
return starredInsertIndex;
|
||||
}, [starredAt, messages]);
|
||||
|
||||
/**
|
||||
* Setup an intersection observer to mark messages as read when they are
|
||||
@@ -173,8 +160,11 @@ const ThreadViewComponent = ({ messages, mailboxId, thread, showTrashedMessages,
|
||||
{stats.trashed > 0 && !showTrashedMessages && (
|
||||
<Banner
|
||||
icon={<Icon name="delete" type={IconType.OUTLINED} />}
|
||||
type="info" actions={[{ label: t('Show'),
|
||||
onClick: () => setShowTrashedMessages(!showTrashedMessages) }]}
|
||||
type="info"
|
||||
actions={[{
|
||||
label: t('Show'),
|
||||
onClick: () => setShowTrashedMessages(!showTrashedMessages)
|
||||
}]}
|
||||
>
|
||||
{t(
|
||||
'{{count}} messages of this thread have been deleted.',
|
||||
@@ -186,26 +176,19 @@ const ThreadViewComponent = ({ messages, mailboxId, thread, showTrashedMessages,
|
||||
</Banner>
|
||||
)}
|
||||
{(() => {
|
||||
return messages.map((message, index) => {
|
||||
return messages.map((message) => {
|
||||
const isLatest = latestMessage?.id === message.id;
|
||||
const isUnread = message.is_unread;
|
||||
return (
|
||||
<React.Fragment key={message.id}>
|
||||
{starredMarkerInsertIndex === -1 && index === 0 && (
|
||||
<StarredMarker />
|
||||
)}
|
||||
<ThreadMessage
|
||||
message={message}
|
||||
isLatest={isLatest}
|
||||
ref={isUnread ? (el => { unreadRefs.current[message.id] = el; }) : undefined}
|
||||
data-message-id={message.id}
|
||||
data-created-at={message.created_at}
|
||||
draftMessage={message.draft_message}
|
||||
/>
|
||||
{starredMarkerInsertIndex === index && (
|
||||
<StarredMarker />
|
||||
)}
|
||||
</React.Fragment>
|
||||
<ThreadMessage
|
||||
key={message.id}
|
||||
message={message}
|
||||
isLatest={isLatest}
|
||||
ref={isUnread ? (el => { unreadRefs.current[message.id] = el; }) : undefined}
|
||||
data-message-id={message.id}
|
||||
data-created-at={message.created_at}
|
||||
draftMessage={message.draft_message}
|
||||
/>
|
||||
);
|
||||
});
|
||||
})()}
|
||||
|
||||
@@ -43,7 +43,6 @@
|
||||
@use "./../features/layouts/components/thread-view/components/calendar-invite";
|
||||
@use "./../features/layouts/components/thread-view/components/thread-accesses-widget";
|
||||
@use "./../features/layouts/components/thread-view/components/thread-labels-widget";
|
||||
@use "./../features/layouts/components/thread-view/components/starred-marker";
|
||||
@use "./../features/forms/components/message-form";
|
||||
@use "./../features/forms/components/search-input";
|
||||
@use "./../features/forms/components/search-filters-form";
|
||||
|
||||
Reference in New Issue
Block a user