Neden <fieldset> esnek kaplar olamaz?


204

Bir stil çalıştı fieldsetile eleman display: flexve display: inline-flex.

Ancak, işe yaramadı: flexgibi davrandı blockve inline-flexböyle davrandı inline-block.

Bu hem Firefox hem de Chrome'da olur, ancak garip bir şekilde IE'de çalışır.

Bu bir hata mı? Ne HTML5 ne de CSS Esnek Kutu Düzeni özellikleri fieldsetherhangi bir özel davranış olması gerektiğini bulamadım .

fieldset, div {
    display: flex;
    border: 1px solid;
}
<fieldset>
    <p>foo</p>
    <p>bar</p>
</fieldset>
<div>
    <p>foo</p>
    <p>bar</p>
</div>


2
Evet, bu bir hata. Basit düzeltme: başka bir öğe kullanın. code.google.com/p/chromium/issues/detail?id=262679
Adam

Yanıtlar:


146

Bug 984869'adisplay: flex göre - düğme elemanları için çalışmıyor ,

<button>saf CSS'de (tarayıcılar tarafından) uygulanamaz, bu nedenle CSS açısından biraz kara bir kutudur. Bu, örneğin bir a ile aynı şekilde tepki vermeleri gerekmediği anlamına gelir <div>.

Bu flexbox'a özgü değildir - örneğin overflow:scroll, bir düğmeye basarsanız kaydırma çubukları oluşturmayız ve display:tableüzerine koyarsanız tablo olarak oluşturmayız .

Daha da geriye gitmek, bu spesifik değil <button>. Düşünmek <fieldset> ve <table> ayrıca özel oluşturma davranışı da vardır:

data:text/html,<fieldset style="display:flex"><div>abc</div><div>def</div>

Bu durumlarda Chrome, bizimle hemfikirdir ve flex görüntüleme modunu dikkate almaz . ("abc" ve "def" nin dikey olarak istiflenmesi sonucu ortaya çıkar). Beklediğiniz şeyi yapmaları <button style="display:flex">, muhtemelen bir uygulama detayından kaynaklanmaktadır.

Gecko'nun düğme uygulamasında, sabit kodlu <button>(ve <fieldset>,ve <table>) displayözelliğinden bağımsız olarak belirli bir çerçeve sınıfına (ve dolayısıyla alt öğeleri yerleştirmenin belirli bir yoluna) sahip olarak .

Çocukların belirli bir düzen modunda çapraz tarayıcı tarzında güvenilir bir şekilde düzenlenmesini istiyorsanız, en iyi seçeneğiniz, düğmenin içinde, tıpkı içindekiler gibi bir sarıcı-div kullanmaktır. a <table>veyaa <fieldset>.

Bu nedenle, bu hata "geçersiz çözümlendi" olarak işaretlendi.

Orada da - Hata 1047590 display: flex;çalışmaz<fieldset> anda "doğrulanmamış",.


İyi haberler : Firefox 46+, Flexbox'ı uygular <fieldset>. Bkz. Hata 1230207 .


Flexbox'ın 8 yıldır limboda olduğu düşünüldüğünde, biraz "abartılı" bir abartı buluyorum. Bir şey olursa, Firefox'ta çok hızlı çalışmasını sağladım. Belki Google'da dişli üzerinde içine yardım tekme şeyler istiyorum (heh, bunu elde ?).
BoltClock

3
<button> is not implementable (by browsers) in pure CSS-- bu açıkça yanlış. Bir tarayıcı <button>istedikleri gibi uygulamada özgürdür , sistem widget kütüphanelerini veya herhangi bir şeyi kullanarak "sözleşmeye bağlı olarak" yükümlü değildirler, bu da bunları CSS veya diğer özel davranışlarla şekillendirme yeteneğini bozar. Aynı şey başka herhangi bir unsur için de geçerli.
amn

4
@BoltClock Limbo ile ne demek istediğinizden emin değilim. Tüm büyük tarayıcılar, sözdiziminin 2015'ten bu yana üçüncü ve son revizyonunu desteklemektedir; birlikte çalışabilirlik oldukça iyi. Artık Grid için geniş bir destek aldık! 🎉
Šime Vidas

@ Šime Vidas: Görüyorum, bir yıldır CR gibi görünüyor. Yeterince adil. Asla başaramayacağını düşündüm.
BoltClock

9
Gerçekten de 2017. Öfkemi nereye yönlendireceğim? Flexbox, sayısız makale, tutes, deneme / hatalar güvenle uygulamak için bekleyen yıl,% 98 oraya ve ... alan setleri. Bu sadece bir güç jakının topraklanmadığını bulmak için bir elektrikçinin evimi bağlaması gibi. “Abartma” İnsanların düşündüğünü duyuyorum, abartmıyorum. Bunun için tam anlamıyla yarın cevap vermem gerekiyor. Flex, çözmem gereken birkaç eski tablo hatasının cevabıydı. Flex, artık daha az sayıda eski olmayan hatanın sebebidir. Öfkemi nereye yönlendireceğim?
danjah

22

Bu Chrome ve Firefox'ta bir hata olabileceğini öğrenmek nerede legendve fieldsetedilmektedir yerleştirilen elemanlar .

Bildirilen Hatalar:

Bug Chrome (hala açık)
Bug Firefox (v46'dan beri düzeltildi)

Olası bir Geçici Çözüm:

Olası bir geçici çözüm <div role="group">HTML'de kullanmak ve CSS'de div[role='group']seçici olarak uygulamak olabilir .


GÜNCELLEME

In Chrome sürümü 83 button ile çalışabilir display: inline-grid/grid/inline-flex/flex, aşağıdaki tanıtımını görebilirsiniz:

button {
  display: inline-flex;
  height: 2rem;
  align-items: flex-end;
  width: 4rem;
  -webkit-appearance: none;
  justify-content: flex-end;
}
<!-- 

The align-items keyword should fail in Chrome 81 or earlier, but work in Chrome 83 or later. To see the error, the button needs styles that make it more of an extrinsic container. In other words, it needs a height or width set. 
 
-->
<button>Hi</button>
<input type="button" value="Hi">


11

Hata önceliğini artırmak için lütfen Chrome hatasını yıldızla işaretleyin

Bu Chrome'da bir hata. Düzeltilmesi önceliğini artırmak için lütfen bu soruna bir yıldız ekleyin: https://bugs.chromium.org/p/chromium/issues/detail?id=375693

Bu arada, sorunun nasıl çözüleceğini göstermek için bu üç Kod Kalemi örneğini oluşturdum. Örnekler için CSS Izgarası kullanılarak oluşturulmuştur, ancak flexbox için aynı teknikler kullanılabilir.

Efsane yerine aria-labelledby kullanma

Bu, sorunla başa çıkmanın daha etkili bir yoludur. Dezavantajı, her sahte efsane öğeye uygulanan benzersiz kimlikler oluşturmakla uğraşmanız gerektiğidir.

https://codepen.io/daniel-tonon/pen/vaaGzZ

<style>
.flex-container {
    display: flex;
}
</style>

<fieldset aria-labelledby="fake-legend">
    <div class="flex-container">
        <div class="flex-child" id="fake-legend">
            I am as good accessibilty wise as a real legend
        </div>

        ...

    </div>
</fieldset>

Fieldset ve legend yerine role = "group" ve aria-labelledby kullanma

Kardeş bir elemanın yüksekliğine gerilebilmesi için esnek konteynere ihtiyacınız varsa ve daha sonra bu gerginliği çocuklarına geçirmeniz gerekiyorsa, kullanmanız gerekir. role="group" yerine .<fieldset>

https://codepen.io/daniel-tonon/pen/BayRjGz

<style>
.flex-container {
    display: flex;
}
</style>

<div role="group" class="flex-container" aria-labelledby="fake-legend">
    <div class="flex-child" id="fake-legend">
        I am as good accessibilty wise as a real legend
    </div>

    ...

</div>

Stil oluşturma amacıyla sahte bir kopya efsanesi oluşturma

Bu, bunu yapmanın çok daha hileli bir yoludur. Yine de erişilebilir durumdadır, ancak bu şekilde yaparken kimliklerle uğraşmanıza gerek yoktur. Ana aşağı tarafı, gerçek gösterge öğesi ve sahte gösterge öğesi arasında yinelenen içerik olacağıdır.

https://codepen.io/daniel-tonon/pen/zLLqjY

<style>
.screen-reader-only {
    position: absolute;
    opacity: 0;
    pointer-events: none;
}
.flex-container {
    display: flex;
}
</style>

<fieldset>
    <legend class="screen-reader-only">
        I am a real screen-reader accessible legend element
    </legend>

    <div class="flex-container">
        <div class="flex-child" aria-hidden="true">
            I am a fake legend purely for styling purposes
        </div>

        ...

    </div>
</fieldset>

Efsane doğrudan bir karar olmalıdır ZORUNLU

Bunu ilk kez kendiniz düzeltmeye çalıştığınızda, muhtemelen bunu yapmaya çalışacaksınız:

<!-- DO NOT DO THIS! -->
<fieldset>
    <div class="flex-container">
        <legend class="flex-child">
            Broken semantics legend text
        </legend>

        ...

    </div>
</fieldset>

Bunun işe yaradığını keşfedeceksiniz ve sonra muhtemelen ikinci bir düşünce vermeden devam edeceksiniz.

Sorun şu ki, alan kümesi ve gösterge arasına bir div sarmalayıcısı koymak, iki eleman arasındaki ilişkiyi bozuyor. Bu, fieldset / legend'in anlambilimini bozar.

Böylece bunu yaparak, ilk etapta fieldset / legend kullanma amacını yendiniz.

Ayrıca, bu alan kümesine bir açıklama vermezseniz, alan kümesi kullanmanın pek bir anlamı yoktur.


9

Deneyimlerime göre, özellikleri ne <fieldset>de <button>ne <textarea>de doğru bir şekilde kullanamaz display:flexveya devralınamaz buldum .

Diğerlerinin daha önce de belirttiği gibi, hatalar bildirilmiştir. Siparişi kontrol etmek için flexbox kullanmak istiyorsanız (örn. order:2), Öğeyi bir div'a sarmanız gerekir. Flexbox'ın gerçek düzeni ve boyutları kontrol etmesini istiyorsanız, giriş kontrolü yerine bir div kullanmayı düşünebilirsiniz (Hangi kokuyor, biliyorum).


3
<div role="group">
    <p>foo</p>
    <p>bar</p>
</div>
<div>
    <p>foo</p>
    <p>bar</p>
</div>

Firefox, krom ve sanırım safari'nin fieldets ile ilgili bir hata var sanırım rol grubu kullanmak gerekebilir. O zaman CSS'deki seçici basitçe

div[role='group'], div {
    display: flex;
    border: 1px solid;
}

Düzenleme: İşte diğer insanların da yaşadığı bazı sorunlar.

Sayı 375693

Sayı 262679


Bu, Chrome 60'ta hala bir sorundur.
evolutionxbox

Hala Chrome 66'da.
Brad

Chrome 72 check-in yapıyor.
danemacmillan

Chrome 73 check-in
Michael Draper

Chrome 75 check-in
xaddict

3

<fieldset>aşağıdaki sahne takımlarına ek div yerleştirebilirsiniz :

flex-inner-wrapper {
  display: inherit;
  flex-flow: inherit;
  justify-content: inherit;
  align-items: inherit;
}

1
Downvotes anlamıyorum. Bu aslında doğrudur. Ancak öğeyi kullanım amacına uygun olarak tutmak için <legend>(kullanılıyorsa) öğenin en üst düzeyinde <fieldset>tutmayı unutmayın ( Permitted content: An optional <legend> element, followed by flow content.- bkz. Developer.mozilla.org/en-US/docs/Web/HTML/Element/… )
Froxx

2
Ben değildim, ama aşağı oyun soruyu cevaplamamakla bir ilgisi olduğunu hayal etmeliyim. Bir çözüm bulmakla ilgili değildi, ama kendi davranışını fieldset.
Manngo

Evet, (biraz felsefi olan) soruyu doğrudan cevaplamayabilir, ancak bu bu saçma hata için olası bir düzeltmedir.
Eric S. Bullington

Down, <legend>öğenin anlambilimini kırmayı teşvik ettiği için oy kullandı . Bu, ilk etapta fieldset / legend kullanım amacını yener. Cevabımı burada görebilirsiniz: stackoverflow.com/a/59425373/1611058
Daniel Tonon

3

Orijinal soruyu cevaplamak için: evet, bir hatadır, ancak soru sorulduğu sırada iyi tanımlanmamıştır.

Şimdi alan kümesi oluşturma daha iyi tanımlanmıştır: https://html.spec.whatwg.org/multipage/rendering.html#the-fieldset-and-legend-elements

Firefox ve Safari'de flexboxüzerine fieldsetşimdi çalışıyor. Henüz Chromium'da değil. (Bkz. Https://bugs.chromium.org/p/chromium/issues/detail?id=375693 )

Ayrıca 2018 şartnamesinde yapılan iyileştirmeler için https://blog.whatwg.org/the-state-of-fieldset-interoperability konusuna bakın .

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.