IlmHamroh
JavaScript Full-stack/6-qism. CSS: harakat, zamonaviy CSS va dizayn16/57-dars21 daqiqa
Mundarija (40)

CSS anchor positioning: elementni boshqasiga "bog'lash"

Qisqacha: Anchor positioning — elementni sahifadagi boshqa elementga "bog'lab" joylash. Tugmaga nom berasiz (anchor-name: --izoh), tooltip'ga esa "shu nomga yopish va uning tepasida tur" deysiz: position-anchor: --izoh; position-area: top;. Ekranga sig'masa, position-try-fallbacks: flip-block uni o'zi pastga o'tkazadi. Ilgari buning uchun JavaScript kutubxonasi kerak edi; 2026-yil yanvaridan asosiy qismi Baseline.

Bu darsda

  • Langar (anchor) va unga bog'langan element tushunchasini tushuntira olasiz.
  • anchor-name, position-anchor va position-area bilan tooltip'ni tugma tepasiga qo'ya olasiz.
  • anchor() va anchor-size() bilan aniq masofa va en berasiz.
  • Popover'ni o'z tugmasi ostida ochasiz va ekranga sig'masa, position-try-fallbacks bilan boshqa tomonga o'tkazasiz.
  • Eski brauzerda sahifa buzilmasligini ta'minlaysiz.

Oldin bilishingiz kerak: position: relative, absolute va containing block, Top layer: dialog va popover'ni stillash, Popover API.

1. Nega bu kerak?

Popover API darsida «Bahor» menyusiga "Ish vaqti" tugmasini qo'shgan edik. Tugma bosilsa, popover ochiladi — lekin ekranning o'rtasida. O'sha darsda "uni tugma yoniga joylash — CSS ishi, keyinroq" degan edik. O'sha "keyin" keldi.

Mehmon tugmani bosdi-yu, matn butunlay boshqa joyda paydo bo'ldi. Ko'zi tugmadan ekran o'rtasiga sakraydi. Menyu tugma ostida, "?" izohi esa "?" ning tepasida chiqishi kerak.

position darsidagi absolute ni eslang. U elementni ota qutiga nisbatan joylaydi — lekin boshqa elementga nisbatan emas. Tugma matn ichida qayerda turishini oldindan bilmaysiz: telefonda bir joyda, kompyuterda boshqa joyda.

Shuning uchun ko'p yillar davomida bu ishni JavaScript qilgan. Skript tugmaning koordinatasini o'lchaydi, tooltip'ni o'sha joyga suradi. Sahifa aylantirilsa yoki oyna o'lchami o'zgarsa — qaytadan o'lchaydi. Tooltip ekrandan chiqib ketsa — boshqa tomonga o'tkazadi. Bu ish uchun Floating UI kabi maxsus kutubxonalar yozilgan.

Endi buning hammasini CSS qiladi. Taksi va bekatni tasavvur qiling: siz haydovchiga "Chorsu bekati oldida to'xta" deysiz — koordinata aytmaysiz. Bekat qayerda bo'lsa, taksi o'sha yerga boradi. Anchor positioning ham shunday: "shu tugmaning tepasida tur" deysiz, qolganini brauzer hisoblaydi.

2. Birinchi bog'lanish: langar va unga yopishgan element

2.1 Ikki tomon

Anchor positioning (langar bo'yicha joylash) — elementni boshqa element atrofiga joylash usuli. Unda ikki tomon bor:

  • Langar (anchor) — "bekat": tugma, belgi yoki so'z. Unga nom beriladi.
  • Bog'langan element (anchor-positioned element) — "taksi": tooltip, menyu, izoh. U langarning nomini biladi va uning atrofida turadi.

Kema langari ham shunday ishlaydi: kema langar atrofida turadi, langar esa qayerga tashlansa — kema o'sha yerda.

«Bahor» menyusidagi "Bron narxi" yonidagi "?" izohini olamiz:

html
<style>
  body { font-family: system-ui, sans-serif; }
  .satr { margin-top: 64px; }
  .savol {
    anchor-name: --bron-savol;
  }
  .izoh {
    position: absolute;
    position-anchor: --bron-savol;
    position-area: top;
    margin: 0 0 6px;
    padding: 4px 8px;
    border-radius: 6px;
    background: #1f2a24;
    color: #fffaf0;
    font-size: 14px;
  }
</style>
<p class="satr">Bron narxi: 0 so'm
  <button type="button" class="savol"
          aria-describedby="bron-izoh">?</button>
</p>
<p class="izoh" id="bron-izoh">To'lov faqat choyxonada</p>

Nimaga qarang: qora izoh "?" tugmasining roppa-rosa tepasida, uning o'rtasiga tekislangan. HTML'da izoh paragrafdan keyin, alohida qatorda turibdi — lekin ekranda tugma tepasiga ko'chdi. "Tahrirlab ko'rish" da margin-top: 64px ni 120px qiling: tugma pastga tushadi, izoh ham u bilan birga tushadi.

.savol va .izoh — faqat shu namoyish uchun qisqa class nomlari. Bu yerda izoh doim ko'rinib turibdi; uni tugma bosilganda ochishni popover bilan pastroqda qilamiz.

2.2 Uch qator — uch vazifa

  • anchor-name: --bron-savol; — langarga nom beradi. Nom albatta ikki chiziqcha -- bilan boshlanadi, xuddi CSS o'zgaruvchilari kabi. Bunday nom dashed-ident deb ataladi.
  • position-anchor: --bron-savol; — bog'langan element qaysi langarga yopishishini aytadi.
  • position-area: top; — langarning qaysi tomonida turish kerakligini aytadi.

Bog'langan element position: absolute yoki fixed bo'lishi shart. Oddiy oqimdagi element langarga e'tibor bermaydi (Chrome'da tekshirdik: position ni o'chirsangiz, izoh paragraf ostida qoladi).

Tekshirib ko'ring: anchor-name: bron-savol; deb yozildi — oldida -- yo'q. Nima bo'ladi?

Javob

Deklaratsiya noto'g'ri, brauzer uni jimgina tashlab ketadi (CSS nima darsidagi kechirimli o'qish). Tugmaning nomi yo'q — izoh esa --bron-savol ni qidiradi va topolmaydi. Natijada u oddiy absolute element kabi joylashadi, tugmadan uzoqda. Nom har doim -- bilan boshlanadi.

3. position-area: langar atrofidagi to'qqiz katak

3.1 Tasavvurdagi to'r

position-area langar atrofiga ko'zga ko'rinmas 3×3 to'r chizadi. O'rtadagi katak — langarning o'zi. Qolgan sakkiztasi — tepa, past, chap, o'ng va to'rt burchak. Siz bog'langan elementni shu kataklardan biriga qo'yasiz. Grid darsidagi hududlarga o'xshaydi.

html
<style>
  body { font-family: system-ui, sans-serif; }
  .maydon { height: 220px; }
  .langar {
    position: absolute;
    top: 90px;
    left: 160px;
    anchor-name: --markaz;
    padding: 8px 16px;
    background: #2f6b3a;
    color: #fffaf0;
  }
  .z {
    position: absolute;
    position-anchor: --markaz;
    margin: 4px;
    font-size: 13px;
    background: #fffaf0;
    border: 1px solid #b4461a;
    padding: 2px 4px;
  }
  .z1 { position-area: top left; }
  .z2 { position-area: top center; }
  .z3 { position-area: top right; }
  .z4 { position-area: left center; }
  .z5 { position-area: right center; }
  .z6 { position-area: bottom left; }
  .z7 { position-area: bottom center; }
  .z8 { position-area: bottom right; }
</style>
<div class="maydon">
  <span class="langar">Langar</span>
  <span class="z z1">tepa-chap</span>
  <span class="z z2">tepa</span>
  <span class="z z3">tepa-o'ng</span>
  <span class="z z4">chap</span>
  <span class="z z5">o'ng</span>
  <span class="z z6">past-chap</span>
  <span class="z z7">past</span>
  <span class="z z8">past-o'ng</span>
</div>

Nimaga qarang: yashil "Langar" atrofida sakkizta yozuv — har biri o'z katagida. Hammasining CSS'i bir xil, faqat position-area qiymati farq qiladi.

3.2 Qiymatlar qanday yoziladi

Ikki so'z: biri tik o'q uchun (top, center, bottom), biri yotiq o'q uchun (left, center, right). Tartibi muhim emas: top left va left top — bir xil joy.

Bitta so'z yozsangiz, ikkinchi o'q bo'yicha element uchala ustunni ham egallaydi:

Yozuv Ma'nosi
top tepada, uch ustun kengligida, o'rtaga tekislangan
top center tepada, faqat o'rta ustunda — langar enida
bottom span-right pastda, o'rta va o'ng ustunlarda
right o'ngda, uch qator balandligida

span-right — "o'rtadan boshlab o'ngga cho'zil". Menyu uchun eng qulay: menyu tugmaning chap chetidan boshlanib, o'ngga qarab ochiladi. span-left, span-top, span-bottom, span-all ham bor.

Mantiqiy xususiyatlar darsidagi kabi mantiqiy so'zlar ham bor: block-start (tepa), inline-end (o'ngda, o'ngdan chapga yozuvda — chapda). Arab yoki ivrit tilidagi saytda menyu o'z-o'zidan to'g'ri tomonga ochiladi.

3.3 Tuzoq: top center juda tor

Tooltip uchun top center tabiiy tuyuladi. Lekin o'rta ustun enini langar belgilaydi. Kichkina "?" tugmasining eni 23 piksel — izoh shu enga sig'ishga harakat qiladi va har so'zi alohida qatorga tushadi:

html
<style>
  body { font-family: system-ui, sans-serif; }
  .satr { margin-top: 90px; display: flex; gap: 120px; }
  .s1 { anchor-name: --s1; }
  .s2 { anchor-name: --s2; }
  .izoh {
    position: absolute;
    margin: 0 0 6px;
    padding: 4px 8px;
    background: #1f2a24;
    color: #fffaf0;
    font-size: 14px;
  }
  .i1 { position-anchor: --s1; position-area: top center; }
  .i2 { position-anchor: --s2; position-area: top; }
</style>
<p class="satr">
  <button type="button" class="s1">?</button>
  <button type="button" class="s2">?</button>
</p>
<p class="izoh i1">❌ Bron bepul</p>
<p class="izoh i2">✅ Bron bepul</p>

Nimaga qarang: chapdagi izoh ustun bo'lib cho'zildi — har so'z alohida qatorda. O'ngdagisi bitta qatorda va baribir tugma o'rtasiga tekislangan. Tuzatish: tooltip uchun bitta so'zli top yoki bottom. top center faqat bog'langan element langar bilan bir xil enda bo'lishi kerak bo'lganda kerak.

Tekshirib ko'ring: Menyu tugma ostida chiqsin va tugmaning chap chetidan o'ngga ochilsin. position-area qiymati qanday?

Javob

bottom span-right. bottom — pastki qator. span-right — o'rta ustundan boshlab o'ng ustungacha: menyuning chap cheti tugmaning chap cheti bilan tekis, qolgani o'ngga ketadi. Faqat bottom desangiz, menyu tugma o'rtasiga tekislanardi.

4. anchor() va anchor-size(): aniq hisob

4.1 Langar chetlariga "qarash"

position-area — tayyor kataklar. Ba'zan esa aniqroq hisob kerak: "tugmaning pastki chetidan 4 piksel pastda, chap cheti bilan tekis". Buni anchor() funksiyasi qiladi. U langarning bir chetining koordinatasini qaytaradi va uni top, left, bottom, right (yoki inset-*) da ishlatasiz.

  • top: anchor(bottom); — "mening tepam langarning pastki chetida".
  • left: anchor(left); — "mening chap chetim langarning chap chetida".
  • top: calc(anchor(bottom) + 4px); — calc() bilan qo'shimcha masofa (Matematik funksiyalar).

4.2 Langar o'lchamini olish

anchor-size() — langarning o'lchamini qaytaradi: anchor-size(width), anchor-size(height). Ochiladigan ro'yxat tugma bilan bir xil enda bo'lsin desangiz — aynan shu:

html
<style>
  body { font-family: system-ui, sans-serif; }
  .tanlov {
    anchor-name: --vaqt;
    margin: 16px;
    padding: 8px 16px;
    font: inherit;
  }
  .royxat {
    position: absolute;
    position-anchor: --vaqt;
    top: calc(anchor(bottom) + 4px);
    left: anchor(left);
    width: anchor-size(width);
    box-sizing: border-box;
    margin: 0;
    padding: 0;
    list-style: none;
    border: 2px solid #2f6b3a;
    background: #fffaf0;
  }
  .royxat li { padding: 4px 8px; }
</style>
<button type="button" class="tanlov">Vaqtni tanlang ▾</button>
<ul class="royxat">
  <li>12:00</li>
  <li>15:00</li>
  <li>18:00</li>
</ul>

Nimaga qarang: ro'yxat tugmadan 4 piksel pastda, chap cheti tugmaniki bilan bir chiziqda va eni ham xuddi tugmanikidek. Tugma matnini uzaytirsangiz ("Tahrirlab ko'rish"), ro'yxat ham kengayadi. box-sizing: border-box ni olib tashlasangiz, ro'yxat 4 piksel kengroq chiqadi: ikki tomondagi 2 piksellik ramka en ustiga qo'shiladi (box-sizing).

anchor() ichida langar nomini ham yozish mumkin: left: anchor(--vaqt left);. Bu bitta element ikki xil langarga qarashi kerak bo'lganda kerak bo'ladi — masalan, ikki tugma orasiga cho'zilgan chiziq.

4.3 anchor-center: o'rtaga tekislash

anchor() bilan elementni langar o'rtasiga qo'yish uchun hisob kerak edi. Buning qisqa yo'li bor: justify-self: anchor-center (yotiq o'rtaga) va align-self: anchor-center (tik o'rtaga). Grid'da tekislash darsidagi justify-self ning yangi qiymati.

Tekshirib ko'ring: position-area va anchor() — qaysi biri qachon?

Javob

Oddiy holatda — position-area: bitta qator, o'qilishi oson, brauzer o'zi tekislaydi va zaxira tomonga o'tkazish ham u bilan qulay. Aniq hisob kerak bo'lganda esa anchor(): langar chetidan ma'lum masofa, ikki langar orasi, langarning faqat bir chetiga tayanish. Ko'pchilik tooltip va menyular uchun position-area yetadi.

5. Popover bilan: tugma ostida ochiladigan panel

5.1 Yashirin langar

Endi 04-qismdagi va'daga qaytamiz. Popover API darsida "popovertarget li tugma popover uchun langar bo'ladi — CSS'da buni qo'lda yozish shart emas" degan edik. Tekshiramiz:

html
<style>
  body { font-family: system-ui, sans-serif; }
  header { display: flex; gap: 8px; padding: 8px; }
  button { font: inherit; padding: 6px 12px; }
  #ish-vaqti {
    position-area: bottom span-right;
    margin: 4px 0 0;
    padding: 8px 12px;
    border: 2px solid #2f6b3a;
    background: #fffaf0;
  }
  #ish-vaqti h2 { margin: 0 0 4px; font-size: 16px; }
  #ish-vaqti p { margin: 0; }
</style>
<header>
  <p>Choyxona «Bahor»</p>
  <button type="button" popovertarget="ish-vaqti">
    Ish vaqti
  </button>
</header>
<aside id="ish-vaqti" popover
       aria-labelledby="ish-vaqti-sarlavha">
  <h2 id="ish-vaqti-sarlavha">Ish vaqti</h2>
  <p>Har kuni 7:00 dan 23:00 gacha.</p>
</aside>

"Ish vaqti" tugmasini bosing. Nimaga qarang: panel endi ekran o'rtasida emas — tugma ostida, uning chap chetidan boshlab ochildi. CSS'da anchor-name ham, position-anchor ham yo'q. Brauzer popover'ni ochgan tugmani o'zi langar qildi. Bunday langar yashirin langar (implicit anchor) deb ataladi.

Popover top layer'da chiqadi (Top layer), shuning uchun position: absolute yozish shart emas: brauzer uni fixed qilib qo'ygan.

5.2 Tuzoq: anchor() va popover'ning standart stili

Brauzerning o'z CSS'ida popover uchun inset: 0 va margin: auto yozilgan — shular uni ekran o'rtasiga qo'yadi. position-area bu qiymatlarni o'zi "qayta sozlaydi", muammo yo'q. anchor() bilan esa standart inset: 0 ning to'rt tomoni qoladi.

Chrome'da tekshirdik: top va left ni anchor() bilan berdik, qolganini unutdik. Tugma ostida ochilishi kerak bo'lgan popover tugmaning chap chetidan 233 piksel o'ngda va 122 piksel pastda paydo bo'ldi.

css
/* ✅ popover + anchor(): standart joylashuvni avval o'chiring */
#ish-vaqti {
  inset: auto;
  margin: 0;
  top: calc(anchor(bottom) + 4px);
  left: anchor(left);
}

Yana bir farq: Chrome 154 da yashirin langar position-area bilan ishladi, anchor() bilan esa position-anchor: auto yozilmaguncha ishlamadi — popover burchakka "yopishdi". Bu xulq brauzerlarda endigina tekislanmoqda. Shuning uchun ishonchli yo'l — nomni aniq yozish: tugmaga anchor-name, popover'ga position-anchor. Portfolio qadamida shunday qilamiz.

5.3 Tooltip: popover="hint" va "?" izohi

Menyudagi "?" izohi — popover="hint" (Popover API). Uni tugma tepasiga qo'yamiz:

css
/* «Bahor»: menyu sahifasidagi izohlar */
button[popovertarget="bron-izoh"] {
  anchor-name: --bron-izoh;
}

#bron-izoh {
  position-anchor: --bron-izoh;
  position-area: top;
  margin: 0 0 0.375rem;
}

Bu yerda atribut selektori (Atribut selektorlari) — «Bahor»ga yangi class qo'shmadik. Popover'ning ranglari, burchagi va ochilish animatsiyasi — Top layer darsidagi qoidalar.

Tekshirib ko'ring: «Bahor» menyusida "Ish vaqti" popover'i hali ham ekran o'rtasida ochilyapti. CSS'da position-area: bottom span-right bor. Birinchi nimani tekshirasiz?

Javob

Tugma haqiqatan popovertarget bilan ochyaptimi va brauzer anchor positioning'ni biladimi. Yashirin langar faqat popovertarget (yoki commandfor) orqali ochilganda paydo bo'ladi. Keyin — DevTools'da position-area ustidan chizilganmi: eski brauzer uni tanimaydi va popover standart joyida — o'rtada qoladi. Ishonchli yo'l: anchor-name va position-anchor ni aniq yozish.

6. Ekranga sig'masa: zaxira joylar

6.1 Muammo

Tugma sahifaning eng pastida bo'lsa-chi? Ostida joy yo'q. Brauzer bog'langan elementni o'z containing block'i (position) ichida saqlashga harakat qiladi — va natija yomon bo'ladi. Ikki bir xil quti: tugma ikkalasida ham pastki chetga yaqin, panel bottom span-right da:

html
<style>
  body { font-family: system-ui, sans-serif; }
  .quti {
    position: relative;
    height: 140px;
    margin: 8px;
    border: 2px dashed #5b6660;
  }
  .tugma {
    position: absolute;
    left: 20px;
    bottom: 12px;
  }
  .panel {
    position: absolute;
    position-area: bottom span-right;
    margin: 4px 0;
    padding: 2px 6px;
    background: #fffaf0;
    border: 1px solid #2f6b3a;
  }
  .q1 .tugma { anchor-name: --t1; }
  .q1 .panel { position-anchor: --t1; }
  .q2 .tugma { anchor-name: --t2; }
  .q2 .panel {
    position-anchor: --t2;
    position-try-fallbacks: flip-block;
  }
</style>
<div class="quti q1">
  <button type="button" class="tugma">❌ Ish vaqti</button>
  <p class="panel">Har kuni 7:00–23:00</p>
</div>
<div class="quti q2">
  <button type="button" class="tugma">✅ Ish vaqti</button>
  <p class="panel">Har kuni 7:00–23:00</p>
</div>

Nimaga qarang: birinchi qutida panel tugmaning ustiga chiqib, uni yarim yopib qo'ydi — pastda joy yo'q, brauzer uni quti ichiga "itarib" kiritdi. Ikkinchi qutida panel tugmaning tepasiga o'tdi va 4 piksel masofa saqlandi. Farq — bitta qator: position-try-fallbacks: flip-block.

6.2 position-try-fallbacks

position-try-fallbacks — "asosiy joyga sig'masang, shularni navbat bilan sinab ko'r" ro'yxati. Tayyor qiymatlar:

Qiymat Nima qiladi
flip-block tepa ↔ past almashadi
flip-inline chap ↔ o'ng almashadi
flip-block flip-inline ikkalasi birga (qarama-qarshi burchak)
bottom, left ... istalgan position-area qiymati

Ro'yxatni vergul bilan yozasiz: position-try-fallbacks: flip-block, flip-inline;. flip-* faqat joyni emas, margin ni ham aks ettiradi: pastdagi panelning margin-top i tepaga o'tganda margin-bottom bo'ladi. Ikkinchi qutidagi 4 piksel shu tufayli saqlandi.

Brauzer qanday qaror qiladi:

flowchart TD
  A["Asosiy joy sig'adimi?"] -->|ha| B["Asosiy joyda turadi"]
  A -->|"yo'q"| C["1-zaxira sig'adimi?"]
  C -->|ha| D["1-zaxirada turadi"]
  C -->|"yo'q"| E["2-zaxira sig'adimi?"]
  E -->|ha| F["2-zaxirada turadi"]
  E -->|"yo'q"| G["Asosiy joyga qaytadi"]

Nimaga qarang: brauzer ro'yxatni chapdan o'ngga sinaydi va birinchi sig'ganida to'xtaydi. Hech biri sig'masa — asosiy joy qoladi. Bu tekshiruv sahifa aylantirilganda va oyna o'lchami o'zgarganda qayta bajariladi — JavaScript'siz.

6.3 O'z variantingiz: @position-try

Tayyor flip-* yetmasa, o'z variantingizni nomlab yozasiz. @position-try — nomli zaxira joy:

css
@position-try --pastga {
  position-area: bottom;
  margin: 0.375rem 0 0;
}

#bron-izoh {
  position-area: top;
  margin: 0 0 0.375rem;
  position-try-fallbacks: --pastga;
}

@position-try ichida faqat joylashuvga oid xususiyatlar ishlaydi: position-area, inset, margin, o'lchamlar va position-anchor. Rang yoki shrift yozsangiz, e'tiborsiz qoladi. Chrome'da tekshirdik: sahifa tepasidagi tugmaning izohi tepaga sig'madi va --pastga variantiga, o'sha variantdagi margin bilan o'tdi.

Tekshirib ko'ring: position-try-fallbacks: flip-block, flip-inline;. Asosiy joy ham, flip-block ham sig'madi, flip-inline sig'di. Element qayerda turadi?

Javob

flip-inline joyida — ya'ni asosiy joyning chap-o'ng tomoni almashgan variantida. Brauzer ro'yxatni tartib bilan sinaydi va birinchi sig'ganini oladi. Agar flip-inline ham sig'maganida, asosiy joyga qaytardi.

7. Ko'p langar: bir nom — bir joy

«Bahor» menyusida har taomning yonida "?" bor deylik. Hamma tugmaga bir xil anchor-name yozildi, hamma izohga — bir xil position-anchor. Natija:

html
<style>
  body { font-family: system-ui, sans-serif; }
  article {
    margin: 8px;
    padding: 8px;
    border: 1px solid #2f6b3a;
  }
  .nom { anchor-name: --taom; }
  .izoh {
    position: absolute;
    position-anchor: --taom;
    position-area: right;
    margin: 0 0 0 8px;
    color: #b4461a;
  }
  .toza article { anchor-scope: --taom; }
</style>
<div>
  <article><span class="nom">❌ Osh</span>
    <span class="izoh">35 000</span></article>
  <article><span class="nom">❌ Manti</span>
    <span class="izoh">30 000</span></article>
</div>
<div class="toza">
  <article><span class="nom">✅ Osh</span>
    <span class="izoh">35 000</span></article>
  <article><span class="nom">✅ Manti</span>
    <span class="izoh">30 000</span></article>
</div>

Nimaga qarang: tepadagi ikki kartada ikkala narx ham "Manti" yonida, ustma-ust, "Osh" kartasi esa narxsiz qoldi. Bir xil nomli langar bir nechta bo'lsa, brauzer oxirgisini oladi. Pastdagi kartalarda har narx o'z taomi yonida.

Farq — anchor-scope: --taom;. anchor-scope — "bu nomni faqat mening ichimda qidir". Har article o'z chegarasini oladi va ichidagi izoh faqat ichidagi langarni topadi. Tanish usul: position darsida relative ota absolute bolaning "doirasini" belgilagani kabi.

Aytgancha, har article ga position: relative bersangiz ham tuzaladi (Chrome'da tekshirdik): bog'langan element faqat o'z containing block'i ichidagi langarni ko'radi. Lekin anchor-scope niyatni aniq aytadi.

Tekshirib ko'ring: Menyuda 12 ta taom kartasi bor, har birida "?" tugmasi va izoh. Hammasiga bitta anchor-name: --taom yozildi. anchor-scope ni qaysi elementga yozasiz?

Javob

Har bir taom kartasiga (masalan, .taom-karta { anchor-scope: --taom; }). Scope qo'yilgan element nom uchun "chegara" bo'ladi. Karta ichidagi izoh langarni faqat shu karta ichidan qidiradi. body ga yozsangiz foydasi yo'q: chegara bitta bo'lib qoladi va hamma izoh yana oxirgi langarni oladi.

8. Eski brauzerlar va JavaScript kutubxonalari

8.1 Baseline holati

Baseline ma'lumotiga ko'ra anchor positioning'ning asosiy qismi — anchor-name, position-anchor, position-area, anchor(), anchor-size(), position-try-fallbacks, @position-try, anchor-scope — 2026-yil 13-yanvardan Baseline ("yangi"): Chrome 125, Firefox 147, Safari 26 dan boshlab. Ba'zi qismlari keyinroq qo'shildi: position-area ning top, bottom kabi bir so'zli qiymatlari — 2026-yil fevralidan, yashirin langar bilan bog'liq position-anchor: normal va auto — 2026-yil sentabridan. Butun imkoniyat hali Baseline emas: position-visibility (langar ko'rinmay qolganda bog'langan elementni yashiradigan xususiyat) ning ba'zi qiymatlari hozircha faqat Safari'da.

"Yangi" degani — eski brauzerlarda yo'q. Ikki-uch yil oldingi telefonda ham sayt ishlashi kerak.

8.2 Zaxira: @supports

Anchor positioning'ni tanimagan brauzer position-area ni tashlaydi (Brauzer mosligi). Natija:

  • Popover — ekran o'rtasida ochiladi. Noqulay, lekin ishlaydi. Ko'pincha shu yetarli.
  • Oddiy absolute izoh — containing block burchagida qoladi va kontentni yopishi mumkin. Bu yomon.

Ikkinchi holat uchun @supports:

css
/* Anchor positioning yo'q brauzer: izoh oddiy matn bo'lib qolsin */
@supports not (anchor-name: --x) {
  .izoh {
    position: static;
  }
}

Eski brauzerda izoh tugmadan keyingi oddiy paragraf bo'lib ko'rinadi — ma'lumot yo'qolmaydi. Bu progressive enhancement.

8.3 Floating UI kerakmi?

Floating UI — tooltip va menyularni joylaydigan JavaScript kutubxonasi. React loyihalarida shadcn/ui, Radix kabi komponent kutubxonalari ichida ishlaydi (kursda alohida o'rganamiz, hozir bilish shart emas). U ko'p yillar sanoat standarti bo'lgan.

Bugun tanlov shunday:

  • Yangi, oddiy sayt — CSS anchor positioning, zaxira sifatida popover'ning o'rtada ochilishi.
  • Eski brauzerlar muhim (masalan, korporativ mijozlar) yoki murakkab holatlar — Floating UI.
  • Mavjud loyihada Floating UI ishlab turibdi — shoshilib almashtirish shart emas.

Tooltip, dropdown va toast'lar qurilishini Tooltip, dropdown va toast darsida to'liq yig'amiz.

9. Ko'p uchraydigan xatolar

9.1 position unutilgan

position-anchor va position-area yozilgan, lekin position: absolute yo'q. Element oqimda qoladi, langarga e'tibor bermaydi, xato ham chiqmaydi. Tuzatish: position: absolute (yoki fixed). Popover'da bu shart emas — u allaqachon top layer'da.

9.2 Bir xil nom — hamma bitta joyda

Ro'yxatdagi har kartada langar nomi bir xil. Hamma bog'langan element oxirgi langarga yopishadi. Tuzatish: takrorlanadigan komponentga anchor-scope.

9.3 Popover'da anchor() "ishlamaydi"

Standart inset: 0 va margin: auto qolgan. Popover g'alati joyda ochiladi. Tuzatish: inset: auto; margin: 0; yoki position-area ga o'ting.

9.4 Tooltip "ustun" bo'lib qoldi

position-area: top center kichik tugma bilan. Tuzatish: position-area: top.

9.5 Zaxira yo'q

Kompyuterda tooltip chiroyli, telefonda ekrandan chiqib ketgan yoki tugmani yopgan. Tuzatish: har bog'langan elementga kamida position-try-fallbacks: flip-block. Telefon enida (Responsive) albatta tekshiring.

10. Mashqlar

Mashqlarni kurs/mashqlar/06/ papkasida bajaring: har mashqqa alohida papka, ichida index.html va asosiy.css.

1-mashq (oson): Narx izohi o'ngda

Tugma va izoh:

html
<p>Osh <button type="button" class="savol">?</button></p>
<p class="izoh">Bir porsiya — 350 gramm</p>

Izoh "?" tugmasining o'ng tomonida, uning o'rtasiga tik tekislangan holda tursin, tugmadan 8 piksel uzoqda.

Ishora: uch qator kerak — langar nomi, bog'lanish va position-area ning bitta so'zli qiymati; masofa — margin ning chap tomoni. position: absolute ni unutmang.

Yechim
css
.savol {
  anchor-name: --savol;
}

.izoh {
  position: absolute;
  position-anchor: --savol;
  position-area: right;
  margin: 0 0 0 8px;
}

right — o'ng ustun, uch qator balandligida; tik bo'yicha element avtomatik tugma o'rtasiga tekislanadi. margin-left: 8px langar bilan izoh orasiga masofa qo'yadi. .savol va .izoh — mashq uchun namoyish class'lari.

2-mashq (o'rta): Tugma enidagi ro'yxat

«Bahor» bron formasiga "Stol turi" tugmasi va ro'yxat qo'shildi deylik:

html
<button type="button" popovertarget="stol-turi">Stol turi</button>
<ul id="stol-turi" popover>
  <li>Umumiy zal</li>
  <li>Ayvon</li>
  <li>Alohida xona</li>
</ul>
  1. Ro'yxat tugma ostida, 4 piksel masofada, chap cheti tugmaniki bilan tekis ochilsin.
  2. Ro'yxat eni tugmanikidan tor bo'lmasin, lekin uzun matn uchun kengroq bo'la olsin.
  3. Sahifa pastida bo'lsa, tugma tepasida ochilsin.

Ishora: popover'da anchor() ishlatsangiz — «Tuzoq: anchor() va popover'ning standart stili» bo'limi. "Tor bo'lmasin" — min-width (O'lchamlar).

Yechim
css
button[popovertarget="stol-turi"] {
  anchor-name: --stol-turi;
}

#stol-turi {
  position-anchor: --stol-turi;
  position-area: bottom span-right;
  position-try-fallbacks: flip-block;
  min-width: anchor-size(width);
  margin: 4px 0 0;
}
  • position-area: bottom span-right — tugma ostida, chap chetidan o'ngga. anchor() shart emas, shuning uchun popover'ning standart inset i bilan muammo yo'q.
  • min-width: anchor-size(width) — kamida tugma enida, matn uzun bo'lsa kengayadi. width yozsangiz, uzun matn qatorga bo'linardi.
  • flip-block — pastda joy bo'lmasa, tepaga; margin-top o'z-o'zidan margin-bottom ga aylanadi.

Tugma va ro'yxatda class yo'q — atribut va id selektorlari yetdi.

3-mashq (qiyin): Stajyorning izohlarini tuzating

Stajyor «Bahor» menyusidagi har taomga "?" izoh qo'ydi:

css
.taom-karta button {
  anchor-name: izoh;
}

.taom-karta [popover] {
  position-anchor: izoh;
  top: anchor(bottom);
  left: anchor(left);
}

Shikoyatlar: (1) izohlar tugma yonida emas; (2) nom tuzatilgach ham barcha izohlar oxirgi kartada ochiladi; (3) telefonda pastki kartaning izohi ekrandan chiqib ketadi.

Har muammoning sababini toping va CSS'ni to'liq tuzating.

Ishora: uchta bo'lim — «Uch qator — uch vazifa», «Ko'p langar» va «Ekranga sig'masa». Popover'dagi anchor() haqida — «Tuzoq» bo'limi.

Yechim
  1. Nom -- siz. anchor-name: izoh — noto'g'ri qiymat, brauzer ikkala deklaratsiyani ham tashlaydi. Bundan tashqari, popover'ning standart inset: 0 va margin: auto i qolgan edi.
  2. Hamma kartada bitta nom. Oxirgi langar yutadi. Har karta o'z doirasini olsin.
  3. Zaxira yo'q.
css
.taom-karta {
  anchor-scope: --izoh;
}

.taom-karta button {
  anchor-name: --izoh;
}

.taom-karta [popover] {
  position-anchor: --izoh;
  position-area: bottom span-right;
  position-try-fallbacks: flip-block, flip-inline;
  margin: 4px 0 0;
}

anchor() o'rniga position-area — popover'ning inset tuzog'i o'z-o'zidan yo'qoldi. flip-inline — o'ng chetdagi kartada izoh chapga ochilishi uchun. taom-karta — «Bahor»ning 04-qismdan kelgan kanonik class'i.

4-mashq: Portfolio qadami — Telegram izohi

Portfolio'ning "Aloqa" sahifasida "Eng tez yo'l — Telegram" deb yozilgan. Mehmon so'raydi: "Qancha vaqtda javob berasiz?". Telegram havolasi yoniga "?" tugma va popover qo'ying:

html
<p>
  Eng tez yo'l —
  <a href="https://t.me/sizning_kanal">Telegram</a>
  <button type="button" popovertarget="telegram-izoh"
          aria-label="Telegram'da javob vaqti">?</button>.
  Email: <a href="mailto:aziz@example.com">aziz@example.com</a>.
</p>
<p id="telegram-izoh" popover>
  Odatda bir soat ichida javob beraman.
</p>
  1. Izoh "?" tugmasining tepasida, 6 piksel masofada ochilsin; tepada joy bo'lmasa — pastida.
  2. Langar nomini aniq yozing — yashirin langarga tayanmang.
  3. Anchor positioning'ni bilmaydigan brauzerda nima bo'lishini tekshiring va yozib qo'ying.

Ishora: selektorlar — button[popovertarget="telegram-izoh"] va #telegram-izoh; portfolio'da class qo'shmaymiz. Ranglar — :root dagi o'zgaruvchilardan.

Yechim

"5. Komponentlar" bo'limining oxiriga:

css
/* --- Telegram izohi: "?" tepasida, sig'masa pastida
   (Popover API va Anchor positioning darslari) --- */
button[popovertarget="telegram-izoh"] {
  anchor-name: --telegram-izoh;
  padding-inline: 0.75em;
}

#telegram-izoh {
  position-anchor: --telegram-izoh;
  position-area: top;
  position-try-fallbacks: flip-block;
  margin: 0 0 0.375rem;
  padding: 0.5rem 0.75rem;
  border: 1px solid var(--rang-chegara);
  border-radius: 0.5rem;
  background-color: var(--rang-fon);
  color: var(--rang-matn);
}
  • "?" tugmasi — umumiy button qoidasidan brend rangi va min-block-size: 2.75rem ni oladi: barmoq uchun 44 piksel. Bitta belgi uchun padding-inline: 1.5em keng edi — 0.75em ga qisqardi.
  • 0.375rem — 6 piksel. flip-block pastga o'tkazganda u margin-top bo'ladi.
  • Rang o'zgaruvchilardan — qorong'i rejimda o'zi almashadi.
  • Eski brauzer: position-area tashlanadi, popover ekran o'rtasida ochiladi. Matn o'qiladi, Esc va tashqariga bosish yopadi — qabul qilinadigan zaxira.

telegram-izoh — yangi id; nomini o'zingiz tanlashingiz mumkin, faqat popovertarget bilan bir xil bo'lsin (Popover API darsidagi xato). npm run check ni ishga tushiring: html-validate popovertarget va aria-label ni taniydi.

11. Real ishda

  • Har joyda suzuvchi UI. Tooltip'lar, "Yana" menyulari, sana tanlagichlar, qidiruv takliflari, "Nusxa olindi" belgisi — hammasi langar atrofida turadi. Ilgari ularning har biri JavaScript kutubxonasi orqali ishlagan.
  • Yangi select. Keyingi darsdagi stillanadigan select ning ochiladigan ro'yxati aynan anchor positioning bilan tugma ostiga qo'yiladi (Forma elementlarini zamonaviy stillash).
  • Interop 2026. Anchor positioning brauzerlar birgalikda tekislaydigan yo'nalishlar ro'yxatida ikkinchi yil ketma-ket turibdi — standart barqarorlashmoqda (Yangi paydo bo'layotgan CSS).
  • Intervyuda so'raladi: "Tooltip'ni ekrandan chiqib ketmaydigan qilib qanday joylaysiz?", "Floating UI nima uchun kerak edi va hozir-chi?". Endi ikkalasiga ham javob bera olasiz.

Xulosa

  • Langarga nom: anchor-name: --nom; bog'langan element: position: absolute + position-anchor: --nom.
  • position-area — langar atrofidagi 3×3 to'r: tooltip uchun top, menyu uchun bottom span-right.
  • anchor() — langar chetining koordinatasi, anchor-size() — uning o'lchami.
  • Popover'ni ochgan tugma yashirin langar bo'ladi, lekin aniq nom ishonchliroq; anchor() bilan popover'ning inset va margin ini tozalang.
  • position-try-fallbacks: flip-block — sig'masa, qarama-qarshi tomonga; takrorlanadigan kartalarda anchor-scope.
  • 2026-yil yanvaridan Baseline ("yangi") — eski brauzer uchun zaxirani o'ylang.

Keyingi dars: Forma elementlarini zamonaviy stillash — accent-color, field-sizing va yangi stillanadigan select bilan «Bahor» bron formasini brend ko'rinishiga keltiramiz.

Manbalar

  • MDN: "Using CSS anchor positioning", "position-area", "anchor()", "position-try-fallbacks", "anchor-scope" — developer.mozilla.org
  • W3C: "CSS Anchor Positioning Module Level 1" — w3.org/TR/css-anchor-position-1
  • web-features: "anchor-positioning" (Baseline holati) — web-platform-dx.github.io/web-features-explorer
  • Chrome for Developers: "Introducing the CSS anchor positioning API" — developer.chrome.com
Ulashish:Telegram'da

Izohlar (0)

Izoh yozish uchun kiring.

  • Hozircha izoh yo'q. Birinchi bo'ling!
CSS anchor positioning: elementni boshqasiga "bog'lash" — IlmHamroh