feat(rithmomachia): auto-size tab labels with react-textfit
Replace ellipsized tab labels with react-textfit library: - Install react-textfit package - Use Textfit component for tab text labels - Auto-scales font size (8px-14px) using binary search to fit width - No more ellipsis (...) on narrow tabs - Full tab labels always visible and readable - Icon stays fixed size, only text scales Tab labels now automatically shrink to fit available space while remaining fully readable. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -73,6 +73,7 @@
|
||||
"react-dom": "^18.2.0",
|
||||
"react-resizable-layout": "^0.7.3",
|
||||
"react-resizable-panels": "^3.0.6",
|
||||
"react-textfit": "^1.1.1",
|
||||
"socket.io": "^4.8.1",
|
||||
"socket.io-client": "^4.8.1",
|
||||
"y-protocols": "^1.0.6",
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
|
||||
import { useEffect, useState, useRef } from 'react'
|
||||
import { useTranslations } from 'next-intl'
|
||||
import { Textfit } from 'react-textfit'
|
||||
import { css } from '../../../../styled-system/css'
|
||||
import { Z_INDEX } from '@/constants/zIndex'
|
||||
import { useAbacusSettings } from '@/hooks/useAbacusSettings'
|
||||
@@ -608,9 +609,7 @@ export function PlayingGuideModal({
|
||||
justifyContent: 'center',
|
||||
gap: isVeryNarrow ? '0' : isNarrow ? '4px' : '6px',
|
||||
lineHeight: 1,
|
||||
whiteSpace: 'nowrap',
|
||||
overflow: 'hidden',
|
||||
textOverflow: 'ellipsis',
|
||||
}}
|
||||
onMouseEnter={(e) => {
|
||||
if (activeSection !== section.id) {
|
||||
@@ -624,11 +623,18 @@ export function PlayingGuideModal({
|
||||
}}
|
||||
title={section.label}
|
||||
>
|
||||
<span style={{ fontSize: isVeryNarrow ? '18px' : 'inherit' }}>{section.icon}</span>
|
||||
<span style={{ fontSize: isVeryNarrow ? '18px' : 'inherit', flexShrink: 0 }}>
|
||||
{section.icon}
|
||||
</span>
|
||||
{!isVeryNarrow && (
|
||||
<span style={{ overflow: 'hidden', textOverflow: 'ellipsis' }}>
|
||||
{isNarrow ? section.label.split(' ')[0] : section.label}
|
||||
</span>
|
||||
<Textfit
|
||||
mode="single"
|
||||
min={8}
|
||||
max={isNarrow ? 12 : 14}
|
||||
style={{ width: '100%', height: '100%', display: 'flex', alignItems: 'center' }}
|
||||
>
|
||||
{section.label}
|
||||
</Textfit>
|
||||
)}
|
||||
</button>
|
||||
))}
|
||||
|
||||
16
pnpm-lock.yaml
generated
16
pnpm-lock.yaml
generated
@@ -194,6 +194,9 @@ importers:
|
||||
react-resizable-panels:
|
||||
specifier: ^3.0.6
|
||||
version: 3.0.6(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
react-textfit:
|
||||
specifier: ^1.1.1
|
||||
version: 1.1.1(react-dom@18.3.1(react@18.3.1))(react@18.3.1)
|
||||
socket.io:
|
||||
specifier: ^4.8.1
|
||||
version: 4.8.1
|
||||
@@ -7942,6 +7945,12 @@ packages:
|
||||
'@types/react':
|
||||
optional: true
|
||||
|
||||
react-textfit@1.1.1:
|
||||
resolution: {integrity: sha512-UDSQRo5yBEGueLTE5SgNV9fSmr5CWJkE0E0R0YbcbCO69iuJGfcT6wspKhX2sIwdsDyT9qXOwMC80cnRolir7Q==}
|
||||
peerDependencies:
|
||||
react: ^15.0.0 || ^16.0.0
|
||||
react-dom: ^15.0.0 || ^16.0.0
|
||||
|
||||
react@18.3.1:
|
||||
resolution: {integrity: sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
@@ -17896,6 +17905,13 @@ snapshots:
|
||||
optionalDependencies:
|
||||
'@types/react': 18.3.26
|
||||
|
||||
react-textfit@1.1.1(react-dom@18.3.1(react@18.3.1))(react@18.3.1):
|
||||
dependencies:
|
||||
process: 0.11.10
|
||||
prop-types: 15.8.1
|
||||
react: 18.3.1
|
||||
react-dom: 18.3.1(react@18.3.1)
|
||||
|
||||
react@18.3.1:
|
||||
dependencies:
|
||||
loose-envify: 1.4.0
|
||||
|
||||
Reference in New Issue
Block a user