ویرگول
ورودثبت نام
فرشید کریمی
فرشید کریمیفرشید کریمی‌ام. یه زمانی مهندسی برق خوندم، کلی توی دنیای embedded دور زدم و با سخت‌افزارها ور رفتم. چند سالیه توسعه وب رو شروع کردم و خیلی به عمیق شدن و فهم مفاهیم پیچیده علاقه‌مندم.
فرشید کریمی
فرشید کریمی
خواندن ۵ دقیقه·۳ روز پیش

Layers و Stacking Context چی هستند و چجوری می‌تونن Performance سایت‌مون رو بهتر کنند؟

مقدمه

دو مفهوم Stacking context و Layers در فرآیند تبدیل کدهای ما به صفحات وب در مرورگر معنا پیدا می‌کنند. این دو مفهوم خیلی شبیه هم هستند و حتی بعضی جاها اشتباها به جای هم به کار میرن اما تفاوت دارند. دونستن این تفاوت بهمون کمک می‌کنه که CSS ای بنویسیم که به سایت با کیفیت‌تری منتج بشه!

از اونجایی که گفتم فرآیند تبدیل کد ما به صفحات وب، لازمه تا یک بار این فرآیند رو مرور کنیم و اختصارا بگیم که این دو مفهوم در کدوم لایه از این فرآیند خودشون رو نشون می‌دن.

فرآیند رندرینگ مرورگر

وقتی یه صفحه وب رو باز می‌کنید، مرورگر چند مرحله اصلی رو طی می‌کنه تا کدهای شما رو به یه صفحه قابل مشاهده تبدیل کنه:

۱. ساخت DOM (Document Object Model)

وقتی مرورگر کدهای HTML شما رو می‌خونه، یه ساختار درختی به نام DOM می‌سازه. این درخت شامل تمام المان‌های HTML صفحه شما می‌شه، از <html> تا آخرین <div> یا <span>. هر المان یه node در این درخت محسوب می‌شه.

۲. ساخت CSSDOM (CSS Object Model)

همزمان با ساخت DOM، مرورگر کدهای CSS رو هم پردازش می‌کنه و یه ساختار درختی دیگه به نام CSSDOM می‌سازه. این درخت شامل تمام استایل‌ها و قوانین CSS می‌شه که مشخص می‌کنه هر المان چجوری باید نمایش داده بشه.

۳. ترکیب DOM و CSSDOM - درخت رندر (Render Tree)

بعد از ساخت DOM و CSSDOM، مرورگر این دو درخت رو با هم ترکیب می‌کنه و یه درخت رندر ایجاد می‌کنه. این درخت فقط شامل المان‌هایی می‌شه که قابل نمایش هستند (مثلا المان‌های با display: none در این درخت وجود ندارند).

۴. محاسبه Layout (Reflow)

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

۵. Paint (رنگ‌آمیزی)

بعد از اینکه موقعیت و اندازه المان‌ها مشخص شد، مرورگر شروع می‌کنه به رنگ‌آمیزی یا paint کردن المان‌ها. در این مرحله، رنگ‌ها، تصاویر، متن‌ها و سایر ویژگی‌های بصری روی صفحه کشیده می‌شن.

۶. Composition (ترکیب لایه‌ها)

در مرحله آخر، مرورگر لایه‌های مختلف رو با هم ترکیب می‌کنه تا صفحه نهایی رو نمایش بده.

توصیه می‌کنم یه بار به این مقاله در وبسایت کروم مراجعه کنید. چون داخلش این فرآیند رو به شکل تصویری خیلی خوب نشون داده.

نکات مهم

  1. از بین مراحل فوق، همگی به جز Compostion کاملا در CPU انجام می ‌شوند.

  2. امور مربوط به ایجاد Stacking Context در بخش Paint رخ می‌دهد. (جلوتر می‌رسیم)

  3. امور مربوط به Layers (جلوتر می‌رسیم که چی هستن) در بخش Composition رخ می دهد. (عمدتا در GPU)

  4. زمانبر ترین بخش این فرآیندها، بخش Layout یا Reflow است، چون باید x,y یک المان یا مختصاتش رو CPU دربیاره و برای این فرآیند باید تمام المان‌های توی صفحه رو درنظر بگیره.

ذکر این نکته هم لازمه که، چنانچه سیستمی GPU نداشته باشه (که دیگه اینروزا خیلی بعیده) قضیه hand-off میشه به همون CPU مون!

بنابراین اگر حرکاتی(!) بزنیم که Reflow رخ نده، می‌تونیم انتظار سرعت و عملکرد بهتری در وبسایتمون داشته باشیم. منظورمون از حرکات هم صرفا تغییر css مونه.

البته Reflow لازم و ضروریه اما یه وقت‌هایی واسه یه چیز بیخودی و دائما در حال انجام (مثل انیمیشن‌ها) ما اشتباها موجبات Reflow رو فراهم می‌کنیم (در حالیکه می‌تونیم نکنیم) و اینجوری سایتمون کند میشه و بعضا هنگ می‌کنه.

چه حرکاتی نیازی به reflow ندارند؟

اگر بخوایم براش یه لیست درست کنیم، قطعا به خاطر نمیشه سپرد و اصلا کار جالبی هم نیست!

فقط کافیه این rule of thumb رو بخاطر بسپارید:

هر تغییر CSS ای که ابعاد و موقعیت x,y یک المان و همسایه‌هاش رو عوض نکنه، موجب reflow نمیشه.

خب دیگه خودتون می تونید یه لیست درست کنید، کارهایی مثل تغییر color و background و opacity تنها نمونه‌هایی از این لیست هستند.

مثال عملی: انیمیشن با Reflow و بدون Reflow

یه انیمیشن ساده رو با دو روش زیر انجام بدیم یکی با مارجین یکی با ترنسفورم. اولی یه nightmare برای مرورگره و دومی یه چیزه خیلی سریع و مناسب.

روش اول: استفاده از margin (دردسرساز!)

<div class="container"> <div class="box bad-animation">Animation with margin</div> </div>
.box { width: 100px; height: 100px; background: blue; margin-top: 10px; } .bad-animation:hover { margin-top: 110px; /* This cause reflow! */ transition: margin-top 0.3s ease; }

روش دوم: استفاده از transform (بهینه!)

<div class="container"> <div class="box good-animation">Animation with transform</div> </div>
.box { width: 100px; height: 100px; background: green; margin-top: 10px; } .good-animation:hover { transform: translateY(100px); /* This isn't cause reflow! */ transition: transform 0.3s ease; }

توضیح:

  • در روش اول، با تغییر margin-top، مرورگر مجبور هست تمام المان‌های بعدی رو مجددا محاسبه کنه (reflow)

  • در روش دوم، transform فقط المان رو در Stacking context جداگانه‌ای حرکت میده و نیازی به محاسبه مجدد موقعیت سایر المان‌ها نداره

بریم سراغ Stacking Context

مقدمه: حالت چینش normal flow چیه؟

فرض کنید یه فایل HTML مانند فایل زیر دارید. تمامی المنت‌ها در این فایل، در normal flow زیست می کنند.

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Simple HTML Page</title> </head> <body> <h1>Hello, World!</h1> <p>This is a simple HTML page with no styles or JavaScript.</p> </body> </html>

مفهوم normal flow در مرورگر: یعنی المان های از نوع block در زیر هم به صورت عمودی قرار می گیرند و المان های از نوع inline به صورت افقی در کنار هم. تصویر زیر:

تمام المنت‌هایی که در HTML داریم مثل div, p, a, article, و غیره همگی به طور پیشفرض براساس normal flow توسط مرورگر چیده می‌شوند، مگر اینکه با Stacking Context آن‌ها رو از normal flow خارج کنیم!

تعریف ‌Stacking Context

اگر با واژه stack آشنا نیستید باید بگم، stack مشابه طبقات یک کیک است که روی هم قرار می‌گیرند و وقتی می‌خواهیم کیک بخوریم قاعدتا اون طبقه بالایی رو اول برمی‌داریم. به عبارت دیگر آخرین (روترین) لایه روی کیک، اولین لایه‌ای است که باید برداریم. (لطفا تصورش کنید!)

حالا Stacking Context در مرورگر طبق تعریف سایت MDN می‌شود:

اگر ساختار چینش المان ها در صفحه HTML را در یک صفحه سه بعدی در نظر بگیریم، به محور Z و نحوه قرارگیری المان ها در آن stacking context می گویند.

چجوری stacking context ایجاد کنیم؟

هر کدام از element های زیر می‌توانند منجر به ایجاد stacking context جدید شوند:

  • المنت (<html>)

  • المنتی با مقدار position برابر absolute یا relative و مقدار z-index غیر از auto

  • المنتی با مقدار position برابر fixed یا sticky

  • المنتی با مقدار container-type برابر size یا inline-size

  • المنتی که یک flex item است با مقدار z-index غیر از auto

  • المنتی که یک grid item است با مقدار z-index غیر از auto

  • المنتی با مقدار opacity کمتر از 1

  • المنتی با مقدار mix-blend-mode غیر از normal

  • المنتی با هر یک از خواص زیر با مقداری غیر از none:

    • transform (مثالی که بالاتر زده بودیم مثلا همین رو فقط داشت)

    • scale

    • rotate

    • translate

    • filter

    • backdrop-filter

    • perspective

    • clip-path

    • mask / mask-image / mask-border


مشاهده کامل مقاله در

https://farshidev.ir/Post/layers-and-stacking-context

موفق باشید.

cssdom
۱
۰
فرشید کریمی
فرشید کریمی
فرشید کریمی‌ام. یه زمانی مهندسی برق خوندم، کلی توی دنیای embedded دور زدم و با سخت‌افزارها ور رفتم. چند سالیه توسعه وب رو شروع کردم و خیلی به عمیق شدن و فهم مفاهیم پیچیده علاقه‌مندم.
شاید از این پست‌ها خوشتان بیاید