mirror of
https://github.com/danny-avila/LibreChat.git
synced 2026-08-28 12:44:28 +00:00
🎨 fix: Gate message hover-reveal controls on hover capability, not width (#13712)
Apply the MessageTimestamp transform to all remaining hover-reveal controls in the message UI: replace the md: breakpoint proxy with a (hover: hover) media query so action buttons stay visible on touch and other non-hover devices (e.g. tablets wider than md), while still hiding until row hover/focus where a pointer supports it. The group-hover:visible reveal trio keeps no hidden base state, so it only drops the md: prefixes; the actual hide-until-hover mechanism is the opacity variant, which stays focusable and in the accessibility tree while hidden.
This commit is contained in:
parent
fc2ae89aa6
commit
16bbc4b97e
5 changed files with 24 additions and 19 deletions
|
|
@ -1,14 +1,6 @@
|
|||
import React, { useState, useCallback, useMemo, useEffect } from 'react';
|
||||
import * as Ariakit from '@ariakit/react';
|
||||
import { TFeedback, TFeedbackTag, getTagsForRating } from 'librechat-data-provider';
|
||||
import {
|
||||
Button,
|
||||
OGDialog,
|
||||
OGDialogContent,
|
||||
OGDialogTitle,
|
||||
ThumbUpIcon,
|
||||
ThumbDownIcon,
|
||||
} from '@librechat/client';
|
||||
import {
|
||||
AlertCircle,
|
||||
PenTool,
|
||||
|
|
@ -19,6 +11,14 @@ import {
|
|||
Lightbulb,
|
||||
Search,
|
||||
} from 'lucide-react';
|
||||
import {
|
||||
Button,
|
||||
OGDialog,
|
||||
OGDialogContent,
|
||||
OGDialogTitle,
|
||||
ThumbUpIcon,
|
||||
ThumbDownIcon,
|
||||
} from '@librechat/client';
|
||||
import { useLocalize } from '~/hooks';
|
||||
import { cn } from '~/utils';
|
||||
|
||||
|
|
@ -218,8 +218,9 @@ function buttonClasses(isActive: boolean, isLast: boolean) {
|
|||
return cn(
|
||||
'hover-button rounded-lg p-1.5 text-text-secondary-alt',
|
||||
'hover:text-text-primary hover:bg-surface-hover',
|
||||
'md:group-hover:visible md:group-focus-within:visible md:group-[.final-completion]:visible',
|
||||
!isLast && 'md:opacity-0 md:group-hover:opacity-100 md:group-focus-within:opacity-100',
|
||||
'group-hover:visible group-focus-within:visible group-[.final-completion]:visible',
|
||||
!isLast &&
|
||||
'group-hover:opacity-100 group-focus-within:opacity-100 [@media(hover:hover)]:opacity-0',
|
||||
'focus-visible:ring-2 focus-visible:ring-black dark:focus-visible:ring-white focus-visible:outline-none',
|
||||
isActive && 'active text-text-primary bg-surface-hover',
|
||||
);
|
||||
|
|
|
|||
|
|
@ -229,8 +229,9 @@ export default function Fork({
|
|||
const buttonStyle = cn(
|
||||
'hover-button rounded-lg p-1.5 text-text-secondary-alt',
|
||||
'hover:text-text-primary hover:bg-surface-hover',
|
||||
'md:group-hover:visible md:group-focus-within:visible md:group-[.final-completion]:visible',
|
||||
!isLast && 'md:opacity-0 md:group-hover:opacity-100 md:group-focus-within:opacity-100',
|
||||
'group-hover:visible group-focus-within:visible group-[.final-completion]:visible',
|
||||
!isLast &&
|
||||
'group-hover:opacity-100 group-focus-within:opacity-100 [@media(hover:hover)]:opacity-0',
|
||||
'focus-visible:ring-2 focus-visible:ring-black dark:focus-visible:ring-white focus-visible:outline-none',
|
||||
isActive && 'active text-text-primary bg-surface-hover',
|
||||
);
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
import React, { useState, useMemo, memo } from 'react';
|
||||
import { useRecoilState } from 'recoil';
|
||||
import type { TConversation, TMessage, TFeedback } from 'librechat-data-provider';
|
||||
import { EditIcon, Clipboard, CheckMark, ContinueIcon, RegenerateIcon } from '@librechat/client';
|
||||
import type { TConversation, TMessage, TFeedback } from 'librechat-data-provider';
|
||||
import { useGenerationsByLatest, useLocalize } from '~/hooks';
|
||||
import { Fork } from '~/components/Conversations';
|
||||
import MessageAudio from './MessageAudio';
|
||||
|
|
@ -84,8 +84,9 @@ const HoverButton = memo(
|
|||
const buttonStyle = cn(
|
||||
'hover-button rounded-lg p-1.5 text-text-secondary-alt',
|
||||
'hover:text-text-primary hover:bg-surface-hover',
|
||||
'md:group-hover:visible md:group-focus-within:visible md:group-[.final-completion]:visible',
|
||||
!isLast && 'md:opacity-0 md:group-hover:opacity-100 md:group-focus-within:opacity-100',
|
||||
'group-hover:visible group-focus-within:visible group-[.final-completion]:visible',
|
||||
!isLast &&
|
||||
'group-hover:opacity-100 group-focus-within:opacity-100 [@media(hover:hover)]:opacity-0',
|
||||
!isVisible && 'opacity-0',
|
||||
'focus-visible:ring-2 focus-visible:ring-black dark:focus-visible:ring-white focus-visible:outline-none',
|
||||
isActive && isVisible && 'active text-text-primary bg-surface-hover',
|
||||
|
|
@ -215,7 +216,9 @@ const HoverButtons = ({
|
|||
isLast={isLast}
|
||||
className={cn(
|
||||
'ml-0 flex items-center gap-1.5 text-xs',
|
||||
isSubmitting && isCreatedByUser ? 'md:opacity-0 md:group-hover:opacity-100' : '',
|
||||
isSubmitting && isCreatedByUser
|
||||
? 'group-hover:opacity-100 [@media(hover:hover)]:opacity-0'
|
||||
: '',
|
||||
)}
|
||||
/>
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import { useState } from 'react';
|
||||
import { Clipboard, CheckMark } from '@librechat/client';
|
||||
import type { TMessage, TAttachment, SearchResultData } from 'librechat-data-provider';
|
||||
import type { TMessage, SearchResultData } from 'librechat-data-provider';
|
||||
import { useLocalize, useCopyToClipboard } from '~/hooks';
|
||||
|
||||
type THoverButtons = {
|
||||
|
|
@ -20,7 +20,7 @@ export default function MinimalHoverButtons({ message, searchResults }: THoverBu
|
|||
return (
|
||||
<div className="visible mt-1 flex justify-center gap-1 self-end text-gray-400 lg:justify-start">
|
||||
<button
|
||||
className="ml-0 flex items-center gap-1.5 rounded-lg p-1.5 text-xs text-text-secondary-alt transition-colors duration-200 hover:bg-surface-hover hover:text-text-primary focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-black dark:focus-visible:ring-white md:opacity-0 md:group-focus-within:opacity-100 md:group-hover:opacity-100"
|
||||
className="ml-0 flex items-center gap-1.5 rounded-lg p-1.5 text-xs text-text-secondary-alt transition-colors duration-200 hover:bg-surface-hover hover:text-text-primary focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-black group-focus-within:opacity-100 group-hover:opacity-100 dark:focus-visible:ring-white [@media(hover:hover)]:opacity-0"
|
||||
onClick={() => copyToClipboard(setIsCopied)}
|
||||
type="button"
|
||||
title={
|
||||
|
|
|
|||
|
|
@ -26,7 +26,7 @@ export default function SiblingSwitch({
|
|||
const buttonStyle = cn(
|
||||
'hover-button rounded-lg p-1.5 text-text-secondary-alt',
|
||||
'hover:text-text-primary hover:bg-surface-hover',
|
||||
'md:group-hover:visible md:group-focus-within:visible md:group-[.final-completion]:visible',
|
||||
'group-hover:visible group-focus-within:visible group-[.final-completion]:visible',
|
||||
'focus-visible:ring-2 focus-visible:ring-black dark:focus-visible:ring-white focus-visible:outline-none',
|
||||
);
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue