fix: message gutter layout — use explicit flex gap matching prototype
Gutter column was 56px (w-14) with the 16px gap baked into the width. This worked for avatars but left only 4px between compact hover timestamps and message text. Switch to w-10 (40px) gutter + gap-4 (16px flex gap), preserving the same 76px content offset while giving timestamps proper breathing room.
This commit is contained in:
@@ -156,7 +156,7 @@ export function Message({ message, isCompact, isFirstInGroup }: MessageProps) {
|
||||
const content = (
|
||||
<div
|
||||
id={`msg-${message.id}`}
|
||||
className={`group relative flex px-5 py-[3px] transition-colors ${isFirstInGroup || message.replyTo ? 'mt-[1.0625rem]' : ''} ${
|
||||
className={`group relative flex gap-4 px-5 py-[3px] transition-colors ${isFirstInGroup || message.replyTo ? 'mt-[1.0625rem]' : ''} ${
|
||||
isMentioned
|
||||
? 'bg-accent-amber/10 border-l-2 border-l-accent-amber hover:bg-accent-amber/15'
|
||||
: 'hover:bg-[rgba(255,255,255,0.025)]'
|
||||
@@ -170,7 +170,7 @@ export function Message({ message, isCompact, isFirstInGroup }: MessageProps) {
|
||||
)}
|
||||
|
||||
{/* Avatar or timestamp column */}
|
||||
<div className="w-14 flex-shrink-0 flex items-start justify-start">
|
||||
<div className="w-10 flex-shrink-0 flex items-start justify-start">
|
||||
{isFirstInGroup || message.replyTo ? (
|
||||
<div className="mt-0.5">
|
||||
<Avatar
|
||||
@@ -182,7 +182,7 @@ export function Message({ message, isCompact, isFirstInGroup }: MessageProps) {
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<span className={`text-[11px] text-txt-tertiary opacity-0 group-hover:opacity-100 mt-[3px] select-none w-full text-center leading-[1.375rem]`}>
|
||||
<span className={`text-[11px] text-txt-tertiary opacity-0 group-hover:opacity-100 mt-[3px] select-none w-full text-right whitespace-nowrap leading-[1.375rem]`}>
|
||||
{formatHoverTime(message.createdAt)}
|
||||
</span>
|
||||
)}
|
||||
@@ -254,25 +254,6 @@ export function Message({ message, isCompact, isFirstInGroup }: MessageProps) {
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Reactions */}
|
||||
{Object.keys(reactionGroups).length > 0 && (
|
||||
<div className="flex flex-wrap gap-1">
|
||||
{Object.entries(reactionGroups).map(([emoji, { count, me }]) => (
|
||||
<button
|
||||
key={emoji}
|
||||
onClick={() => toggleReaction(emoji)}
|
||||
className={`glass-pill flex items-center gap-1 rounded-[6px] cursor-pointer transition-all duration-[120ms] ease-out ${
|
||||
me ? 'glass-pill-mine' : ''
|
||||
}`}
|
||||
style={{ padding: '2px 8px', fontSize: '13px', lineHeight: 1 }}
|
||||
>
|
||||
<span style={{ fontSize: '14px', lineHeight: 1 }}>{emoji}</span>
|
||||
<span className={`font-semibold ${me ? 'text-accent-mint' : 'text-txt-secondary'}`} style={{ fontSize: '12px' }}>{count}</span>
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Embeds */}
|
||||
{!isEditing && firstUrl && <Embed url={firstUrl} />}
|
||||
|
||||
@@ -320,6 +301,25 @@ export function Message({ message, isCompact, isFirstInGroup }: MessageProps) {
|
||||
})}
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Reactions */}
|
||||
{Object.keys(reactionGroups).length > 0 && (
|
||||
<div className="flex flex-wrap gap-1">
|
||||
{Object.entries(reactionGroups).map(([emoji, { count, me }]) => (
|
||||
<button
|
||||
key={emoji}
|
||||
onClick={() => toggleReaction(emoji)}
|
||||
className={`glass-pill flex items-center gap-1 rounded-[6px] cursor-pointer transition-all duration-[120ms] ease-out ${
|
||||
me ? 'glass-pill-mine' : ''
|
||||
}`}
|
||||
style={{ padding: '2px 8px', fontSize: '13px', lineHeight: 1 }}
|
||||
>
|
||||
<span style={{ fontSize: '14px', lineHeight: 1 }}>{emoji}</span>
|
||||
<span className={`font-semibold ${me ? 'text-accent-mint' : 'text-txt-secondary'}`} style={{ fontSize: '12px' }}>{count}</span>
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user