خطوط نوشتار با پهنای برابر

ویژگی‌های وب: text-fit text-wrap: balance text-box

قفل‌های سبک پوستر که در آن هر خط مقیاس‌بندی می‌شود تا کل عرض محفظه را دربرگیرد می‌تواند عنوان‌های چشمگیری ایجاد کند. بااستفاده از text-fit، مرورگر هر خط را درطول چیدمان مقیاس‌بندی می‌کند، بنابراین درصورت تغییر اندازه، کپی کردن تغییرات، و بار کردن قلم، درست باقی می‌ماند.

برای یک خط که ظرف خود را پر می‌کند (مثلاً عنوان یا نقل‌قول)، text-fit را مستقیماً روی آن عنصر اعمال کنید؛ این راهنما قفل‌های چندخطی را پوشش می‌دهد.

پیاده‌سازی پایه

برای خطوط اجباری:

  • هر خط را در <span> با display: block بپیچید.
  • white-space: nowrap را برای هر خط اجباری <span> اعمال کنید.

دستورالعمل‌های پیاده‌سازی:

  • از text-fit: grow per-line-all <percentage> روی خود عنوان استفاده کنید.
  • از per-line-all استفاده کنید، نه per-line. per-line خط آخر و هر خطی را که به شکست اجباری ختم می‌شود نادیده می‌گیرد، بنابراین با یک بلوک در هر خط، چیزی را مقیاس‌بندی نمی‌کند.
  • grow را نمی‌توان با shrink ترکیب کرد. بسته به اینکه کدام‌یک جایگزین بهتری است یا محاسبه آن آسان‌تر است، font-size پایه را روی حداکثر یا حداقل تنظیم کنید و text-fit را به‌ترتیب روی shrink یا grow تنظیم کنید. اگر دلیلی برای استفاده از shrink ندارید، بهتر است از grow استفاده کنید و تنظیم font-size را در حداقل مقدار نگه دارید، زیرا برای اکثر موارد ایمن‌تر است.
  • همیشه رشد یا کاهش را با درصد (مثلاً 300%) به‌عنوان حفاظ محدود کنید.
  • ظرف به اندازه درون‌خطی مشخصی نیاز دارد. text-fit هرگز اندازه ذاتی را تغییر نمی‌دهد، بنابراین هیچ کاری روی عرض‌های fit-content/max-content یا موارد flex/grid با اندازه محتوا انجام نمی‌دهد.
  • فاصله خطوط را در بالای خط اول و زیر خط آخر برش دهید: به تراز دقیق نوشتار مراجعه کنید.
  • line-height را کوچک، 1 یا کمتر نگه دارید، درغیراین‌صورت فاصله بین خطوط با اندازه‌های قلم متفاوت نامناسب می‌شود.
  • مهم: توجه داشته باشید که font-size محاسبه‌شده بدون تغییر است، بنابراین فاصله‌گذاری em مقیاس‌بندی نمی‌شود.
  • برای جلوگیری از تأکید بیش‌ازحد تصادفی بر خطوط تک‌افتاده، اگر خطوط آزاد وجود دارد، text-wrap: balance یا text-wrap: pretty را اعمال کنید.

فاصله‌گذاری

اگر همه خطوط اجباری باشند، این کار کنترل بیشتری بر فاصله‌گذاری ایجاد می‌کند:

  • text-box: trim-both cap alphabetic را روی هر بلوک خط اعمال کنید تا چارگوش آن نویسه‌های خودش را دربرگیرد. این روش بااستفاده از سنجه‌های مقیاس‌بندی‌شده، داده‌ها را هرس می‌کند. برای جزئیات بیشتر، تراز کردن دقیق نوشتار را ببینید.
  • خطوط فاصله بااستفاده از Flexbox یا Grid + gap در عنوان، نه line-height. سپس فاصله‌ها به‌جای اینکه با اندازه قلم هر خط افزایش یابند، یکنواخت می‌شوند.

اگر برخی خطوط آزاد هستند، از text-box استفاده نکنید: این ویژگی فقط خط اول و آخر را برش می‌دهد، بنابراین خطوط بیرونی نویسه‌ها را دربرمی‌گیرند درحالی‌که فاصله‌های داخلی فاصله بین خطوط خود را حفظ می‌کنند. اجازه دهید line-height همه فاصله‌گذاری‌ها را کنترل کند.

طراحی دیداری

  • وقتی تفاوت قابل‌توجهی در اندازه قلم بین خطوط وجود داشته باشد، قفل‌ها بهترین ظاهر را دارند. از ایجاد قفل‌بندی از نوشتاری که خطوط آن عمدتاً یکنواخت است خودداری کنید، زیرا این کار منجر به اندازه‌های قلمی می‌شود که نه یکسان هستند و نه به‌اندازه کافی متفاوت، که این امر اصل طراحی کنتراست را نقض می‌کند. با اجباری کردن خطوط کوتاه می‌توانید از این امر مطمئن شوید: کلمات را برای تأکید در یک بلوک بپیچید و بگذارید بقیه بپیچند، یعنی یک قفل ترکیبی. این موضوع به‌ویژه هنگام ترکیب با text-wrap: balance اهمیت دارد.
  • ترجیحاً این مورد را با text-transform: uppercase ترکیب کنید، وقتی با نویسه‌های غربی استفاده می‌شود، زیرا بالارونده‌ها و پایین‌رونده‌ها تمایل به ایجاد فضای محبوس و/یا هم‌پوشانی خطوط مجاور دارند که نتیجه‌ای با زیبایی کمتر ایجاد می‌کند.
  • هنگام اجبار به استفاده از خطوط کوتاه، کلماتی را انتخاب کنید که درصورت تأکید، پیام را تقویت کنند.
  • محدودیت: نوشتار درحال رشد ازنظر وزن دیداری نیز افزایش می‌یابد و خطوط آن قوی‌تر به‌نظر می‌رسد. درحال‌حاضر هیچ راهی برای جبران این مشکل وجود ندارد، مثلاً با کاهش font-weight برای نوشتار بزرگ‌تر، زیرا هیچ واحدی برای استفاده در محاسبه وجود ندارد، چون مقیاس‌بندی بر واحدهای مرتبط با قلم مانند em تأثیر نمی‌گذارد.

راهبردهای جایگزین

برای text-box

text-box به جایگزین جداگانه‌ای نیاز ندارد: line-height کوچک را در قفل‌های ثابت نیز نگه دارید. این ویژگی در text-box غیرفعال است و در جاهایی که پشتیبانی نمی‌شود، فاصله‌ها را فشرده نگه می‌دارد، اما درعوض فاصله‌ها با اندازه قلم هر خط مقیاس‌بندی می‌شوند.

برای text-wrap: balance

برای text-fit

خطوط اجباری یک جایگزین کوتاه و وفادار دارند: هر خط را در اندازه پایه آن اندازه‌گیری کنید و آن را با نسبت به ظرف، با همان کلاهک، مقیاس‌بندی کنید.

@supports not (text-fit: grow) {
  .lockup > span {
    /* Shrink-wrap each line so its width is the text width */
    width: fit-content;
    /* --text-fit-scale is measured by the script; the cap mirrors the text-fit percentage */
    font-size: min(var(--text-fit-scale, 1) * 1em, 300%);
  }
}
if (!CSS.supports('text-fit', 'grow per-line-all')) {
  const fit = lockup => {
    const lines = [...lockup.querySelectorAll(':scope > span')];
    // Unscale first: on a refit, offsetWidth would otherwise include the previous scale
    for (const line of lines) line.style.removeProperty('--text-fit-scale');
    // MANDATORY: all reads, then all writes. Interleaving them (e.g. reading
    // lockup.clientWidth inside the write loop) forces one reflow per line.
    const scales = lines.map(line => lockup.clientWidth / line.offsetWidth);
    lines.forEach((line, i) => line.style.setProperty('--text-fit-scale', scales[i]));
  };
  // Refit on resize and font load
  for (const lockup of document.querySelectorAll('.lockup')) {
    new ResizeObserver(() => fit(lockup)).observe(lockup);
  }
}

خطوط آزاد فاقد بازگشت وفادارانه هستند (شکست‌های خط تا زمان چیدمان ناشناخته‌اند): ارتقای پیش‌رو به عنوان متعادل با اندازه پایه سیال مانند clamp(2rem, 1rem + 5cqi, 5rem). در یک قفل ترکیبی، اسکریپت بالا همچنان با خطوط اجباری مطابقت دارد؛ یک بلوک پیچشی به اندازه ظرف اندازه‌گیری می‌شود، بنابراین مقیاس ۱ را حفظ می‌کند و فقط اندازه پایه سیال را دریافت می‌کند.

اگر تناسب متن مهم است، از کتابخانه JS (مثلاً fitty) استفاده کنید که فقط درصورت پشتیبانی نشدن از text-fit به‌صورت شرطی بار می‌شود.