Esnek kutu öğeleri arasındaki mesafeyi ayarlamanın daha iyi yolu


777

Ben kullanıyorum FlexBox öğeleri arasında minimum mesafe ayarlamak için margin: 0 5pxüzerinde .itemve margin: 0 -5pxkonteyner üzerinde. Benim için bir saldırı gibi görünüyor, ama bunu yapmanın daha iyi bir yolunu bulamıyorum.

Misal

#box {
  display: flex;
  width: 100px;
  margin: 0 -5px;
}
.item {
  background: gray;
  width: 50px;
  height: 50px;
  margin: 0 5px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>


28
Bu bir hack değil - öğeleri hizalamak için amaçlanan yöntemlerden biri. Yine de başka özellikler var. Bkz. W3.org/TR/css3-flexbox/#alignment
BoltClock

4
Evet, anlıyorum. Ama örneğin bize kabından kontrol mesafesi yeteneği verir kolon-boşluk özellik vardır: w3.org/TR/css3-multicol/#column-gap
Sasha Koss

Nedeni bu flexbox bir marj daralmaları olduğunu.Diğer soru doğru daha yanlış [Flexbox son marj çökmesini nasıl durdurabilirim? ] ( stackoverflow.com/questions/38993170/… )
Jack Yang

6
CSS Kutu Hizalama Modülü Seviye 3 bir bölüm içerir kutular arasındaki boşluklar , çok sütun elemanları için de geçerlidir - esnek kaplar ve ızgara kaplar. Yani sonunda bu basit olacak: row-gap: 5px- bitti.
Danield

2
@JohnCarrell firefox aslında zaten gapesnek kaplarda ( caniuse ) mülkü destekliyor
Danield

Yanıtlar:


427
  • Flexbox'ta daraltma kenar boşlukları yok.
  • Flexbox'ta border-spacingtablolar için benzer bir şey yok ( gapçoğu tarayıcıda iyi desteklenmeyen CSS özelliği hariç , caniuse )

Bu nedenle, istediğiniz şeyi elde etmek biraz daha zordur.

Tecrübelerime, kullanmaz "temiz" bir şekilde :first-child/ :last-childüzerinde herhangi bir değişiklik yapmadan ve eserleri flex-wrap:wrapkümesine olan padding:5pxkabın üzerine ve margin:5pxçocuklar üzerinde. Bu, 10pxher çocuk arasında ve her çocuk ile ebeveynleri arasında bir boşluk oluşturacaktır .

gösteri

.upper
{
  margin:30px;
  display:flex;
  flex-direction:row;
  width:300px;
  height:80px;
  border:1px red solid;

  padding:5px; /* this */
}

.upper > div
{
  flex:1 1 auto;
  border:1px red solid;
  text-align:center;

  margin:5px;  /* and that, will result in a 10px gap */
}

.upper.mc /* multicol test */
{flex-direction:column;flex-wrap:wrap;width:200px;height:200px;}
<div class="upper">
  <div>aaa<br/>aaa</div>
  <div>aaa</div>
  <div>aaa<br/>aaa</div>
  <div>aaa<br/>aaa<br/>aaa</div>
  <div>aaa</div>
  <div>aaa</div>
</div>

<div class="upper mc">
  <div>aaa<br/>aaa</div>
  <div>aaa</div>
  <div>aaa<br/>aaa</div>
  <div>aaa<br/>aaa<br/>aaa</div>
  <div>aaa</div>
  <div>aaa</div>
</div>


219
Bu, sorunun sorduğu ile aynı şeyi yapmaz, en solda ve sağda 10 piksel girintiye sahip olursunuz, ki bu da sahip olmak istemediklerini varsayıyorum. Bu nedenle, asıl sorunun negatif kenar boşlukları.
Chris Nicola

17
orderÖzellik ayarlanmışsa ne olur ? :first-child/:last-childbeklendiği gibi çalışmaz.
Guria

4
“Flexbox'ta daralma marjları yok.” Çok anlayışlı ve görünüşe göre doğru, ama bir alıntı isteyebilir miyim?
chharvey

2
Bu orijinal sorudan daha kötü bir cevap değil mi? Bu yöntem, kabın etrafında boşluk olmasını gerektirir ve oluk her zaman çift bir sayı olmalıdır.
limitlessloop

7
@chharvey, Spec gelen w3.org/TR/css-flexbox-1/#item-margins , "bitişik esnek öğelerin marjları daraltmak değil."
romellem

195

Bu bir hack değil. Aynı teknik aynı zamanda bootstrap ve ızgarası tarafından da kullanılır, ancak marj yerine bootstrap cols için dolgu kullanır.

.row {
  margin:0 -15px;
}
.col-xx-xx {
  padding:0 15px;
}

1
Bu yöntemle ilgili tek sorun, arka plan renkleri ile eşit yükseklikteki öğeleri korumaktır. İle mutlak konumlandırma height:100%; width:100%, ürünün dolgusunu yok sayar.
Steven Vachon

3
Buradaki sorun IE10 ve 11 ile ilgilidir. flex-basisDeğerler hesaba katılmaz box-sizing: border-box, bu nedenle herhangi bir dolgu veya kenarlığa sahip bir çocuk üst öğeyi taşacaktır (veya bu durumda sarın). Kaynak
Carson

18
Bu yaklaşımla ilgili başka bir sorun daha var: kenar boşluğunu bu şekilde ayarlamak sayfa genişliğini artırabilir. Demo: jsfiddle.net/a97tatf6/1
Nathan Osman

4
Bunun bir kesmek olmadığını kabul etsem de, bir şeyin yaygın olarak kullanılması, bunun bir kesmek olmadığı anlamına gelmez. Çoklu doldurma, geçici güvenlik düzeltme ekleri, onaltılık düzenleme vb. Konularına bakın
William

15
Tabii ki bu bir hack. Bootstrap bu yöntemi kullandığı için bir saldırı olmadığı anlamına gelmez. Sadece Bootstrap'in bir hack kullandığı anlamına gelir.
Michael Benjamin

108

Çoklu satır destekli Flexbox ve css calc

Merhaba, aşağıda flexbox'ı destekleyen tüm tarayıcılar için çalışma çözümüm. Negatif kenar boşluğu yok.

Keman Demosu

   
.flexbox {
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  justify-content: space-between;
}

.flexbox > div {
  /*
    1/3  - 3 columns per row
    10px - spacing between columns 
  */
  box-sizing: border-box;
  margin: 10px 10px 0 0;
  outline: 1px dotted red;
  width: calc(1/3*100% - (1 - 1/3)*10px);
}

/*
  align last row columns to the left
  3n - 3 columns per row
*/
.flexbox > div:nth-child(3n) {
  margin-right: 0;
}

.flexbox::after {
  content: '';
  flex: auto;
}

/*
  remove top margin from first row
  -n+3 - 3 columns per row 
*/
.flexbox > div:nth-child(-n+3) {
  margin-top: 0;
}
<div class="flexbox">
  <div>col</div>
  <div>col</div>
  <div>col</div>
  <div>col</div>
  <div>col</div>
</div>

Bu kodun SASS kullanarak daha kısa olabileceğini unutmayın

Güncelleme 2020.II.11 Son satırdaki sola hizalanmış sütunlar

Güncelleme 2020.II.14 Son satırdaki kenar boşluğu kaldırıldı


13
Bu çözümü seviyorum, ancak son satırda sadece 2 öğe varsa başarısız olur. Öğeler nedeniyle birlikte istiflenmiyor justify-content.
James Brantly

4
iki öğe sorununu düzeltmek için justify-content: space-evenly;veya olarak değiştirin justify-content: space-around;.
Paul Rooney

6
@PaulRooney Birden fazla listeye sahip sitede, listeler bir CMS tarafından oluşturulmuşsa, öğe sayısını her zaman bilemeyebilirsiniz.
NinjaFart

1
@ 1.21gigawatts Lütfen başkasının kodunda / cevabında keyfi değişiklikler yapmayın; bunun yerine kendi cevabınızı yazın.
TylerH

2
@TylerH Keyfi değildi. Soru, "... flexbox öğeleri arasındaki mesafeyi nasıl ayarlayacağınızı" sordu. Bu cevap oluğun boyutunu göstermiyor. Bir arka plan rengi ayarlamak oluğu gösterir. Kenarlık eklenmesi, son satırın altında bir kenar boşluğu olduğunu gösterir.
1.21 gigawatts

93

Saydam kenarlıklar kullanabilirsiniz.

Eski tarayıcılar için bir tablo + tablo hücresi modeline geri dönebilen esnek bir ızgara modeli oluşturmaya çalışırken bu sorunu düşündüm. Ve sütun olukları için sınırlar bana en uygun seçim gibi görünüyordu. yani Tablo hücrelerinin kenar boşluğu yoktur.

Örneğin

.column{
  border-left: 5px solid transparent;
  border-right: 5px solid transparent;
  border-bottom: 10px solid transparent;
}

Ayrıca min-width: 50px;flexbox'a ihtiyacınız olduğunu unutmayın. Esnek model, sabit flex: none;olmasını istediğiniz belirli alt öğe üzerinde yapmadığınız ve bu nedenle dışlanmadığı sürece sabit boyutları işlemez "flexi". http://jsfiddle.net/GLpUp/4/ Ancak tüm sütunlar flex:none;artık esnek bir model değil. İşte esnek bir modele daha yakın bir şey: http://jsfiddle.net/GLpUp/5/

Böylece, eski tarayıcılar için tablo hücresi yedeğine ihtiyacınız yoksa, kenar boşluklarını normal olarak kullanabilirsiniz. http://jsfiddle.net/GLpUp/3/

background-clip: padding-box;Bir arka plan kullanılırken ayar gerekli olacaktır, aksi takdirde arka plan şeffaf kenarlık alanına akacaktır.


5
mükemmel cevap. marjlar flexbox'larda (ekstra alanı emmek gibi) farklı şekilde kullanılır, bu nedenle şeffaf kenarlıklar, marj benzeri bir davranışla sarılabilen eşit aralıklı öğelere mükemmel bir çözüm sağlar
Eolis

4
arka plan rengini kullanmanız dışında, arka planınız istediğiniz sınırları aşıyor.
ahnbizcad

2
@ahnbizcad Farklı arka plan renkleri ile, arka planın şekline bağlı olarak beyaz veya yeterli rengi kullanabilirsiniz.
hexalys

27
@ahnbizcad: IE8 desteğine ihtiyacınız yoksa, bu daha iyi bir çözümdür:background-clip: padding-box
Albin

5
Albin'in buradaki yorumu için daha fazla oy gerekiyor! Bu en iyi çözüm. Arka plan klipsi ile birlikte saydam kenarlıklar: dolgu kutusu (ve gerekirse düzgün kenar hizalaması için kaptaki negatif kenar boşlukları) mükemmel bir çözümdür. IE8 zaten flexbox'ı desteklemediğinden, arka plan klibi için destek eksikliği önemli olmamalıdır.
Brian

74

Bu çözüm, birden çok satır veya çok sayıda öğe olsa bile tüm durumlar için çalışacaktır. Ancak bölüm sayısı ilk satırda 4 istediğiniz 3 aynıdır ve 3 ikinci satırdır, bu şekilde çalışmaz, 4. içerik için alan kap boş olmayacaktır.

Kullanıyoruz display: grid; ve özellikleri.

#box {
  display: grid;
  width: 100px;
  grid-gap: 5px;
  /* Space between items */
  grid-template-columns: 1fr 1fr 1fr 1fr;
  /* Decide the number of columns and size */
}

.item {
  background: gray;
  width: 100%;
  /* width is not necessary only added this to understand that width works as 100% to the grid template allocated space **DEFAULT WIDTH WILL BE 100%** */
  height: 50px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>

Bu yöntemin dezavantajı Mobile Opera Mini'de desteklenmeyecektir ve PC'de bu sadece IE10'dan sonra çalışır .

IE11 dahil tam tarayıcı uyumluluğu için lütfen Autoprefixer kullanın


ESKİ CEVAP

Bunu eski bir çözüm olarak düşünmeyin, sadece tek bir satır öğesi istiyorsanız ve tüm tarayıcılarla çalışacaksa hala en iyilerinden biridir.

Bu yöntem CSS kardeş kombinasyonu tarafından kullanılır , böylece başka birçok yolu da değiştirebilirsiniz, ancak kombinasyonunuz yanlışsa sorunlara da neden olabilir.

.item+.item{
  margin-left: 5px;
}

Aşağıdaki kod işinizi görecektir. Bu yöntemde, vermek gerek yoktur margin: 0 -5px;için #boxsarıcı.

Sizin için çalışan bir örnek:

#box {
  display: flex;
  width: 100px;
}
.item {
  background: gray;
  width: 22px;
  height: 50px;
}
.item+.item{
 margin-left: 5px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>


Kılavuz tabanlı cevabınızı, son satırda daha az öğe olsa bile doğru çalıştığını göstermek için düzenledim. Bu durumda kanıtlamak için. (Bu değişikliği beğenmediyseniz geri dönmekten çekinmeyin.)
ToolmakerSteve

Bu soruya göre, alanı sadece bir hack olmadan alt öğelerle düzgün bir şekilde doldurmayı istediler, yaptığım, ızgarayı kullanarak grid-template-columnsdinamik olarak tanımlayamadığımız şekilde yönetebileceğimizi . Eğer buna değer verirseniz, 1fr 1fr 1fr 1frdiv bölünür 4fractionsve her birinde alt öğeleri doldurmaya çalışır fractions, bence tek yol budur grid. Cevapta belirttiğim şey, eğer kullanıcı div 4'e bölmek ve birden fazla satır için bile birçok öğe ile kullanmak gerekirse gid, yardımcı olacaktır.
weBBer

69

(Tek bir satır için) & > * + *öykünmek için seçici olarak kullanabilirsiniz flex-gap:

#box { display: flex; width: 230px; outline: 1px solid blue; }
.item { background: gray; width: 50px; height: 100px; }

/* ----- Flexbox gap: ----- */

#box > * + * {
  margin-left: 10px;
}
<div id='box'>
    <div class='item'></div>
    <div class='item'></div>
    <div class='item'></div>
    <div class='item'></div>
</div>

Esnek sargıyı desteklemeniz gerekiyorsa , bir sargı elemanı kullanabilirsiniz:

.flex { display: flex; flex-wrap: wrap;  }
.box { background: gray; height: 100px; min-width: 100px; flex: auto; }
.flex-wrapper {outline: 1px solid red; }

/* ----- Flex gap 10px: ----- */

.flex > * {
  margin: 5px;
}
.flex {
  margin: -5px;
}
.flex-wrapper {
  width: 400px; /* optional */
  overflow: hidden; /* optional */
}
<div class='flex-wrapper'>
  <div class='flex'>
    <div class='box'></div>
    <div class='box'></div>
    <div class='box'></div>
    <div class='box'></div>
    <div class='box'></div>
  </div>
</div>


3
Temiz çözelti. Herhangi bir sayıda esnek alt eleman için çalışır.
Konrad Gałęzowski

1
Aradığım ve benim için harika çalıştığı şey buydu
Paul

Ancak dikkat edilmesi gereken bir nokta, *operatörün beklediğiniz gibi özgüllüğü artırmamasıdır. Bu nedenle, mevcut css'nize bağlı olarak, .flex > *seçicideki özgüllüğü artırmanız veya !importanto öğeye kenar boşluğu uygulayan başka seçiciler varsa kurala eklemeniz gerekebilir .
Paul Odeon

En iyi çözüm 👍
o01

26

Diyelim ki 10pxöğeler arasında boşluk ayarlamak istiyorsanız,.item {margin-right:10px;} herkes için ve sonuncusunda sıfırlayabilirsiniz.item:last-child {margin-right:0;}

İlki hariç öğeler üzerinde sol kenar boşluğu ayarlamak için genel kardeş ~veya sonraki +kardeş seçiciyi de kullanabilirsiniz..item ~ .item {margin-left:10px;} kullanabilirsiniz..item:not(:last-child) {margin-right: 10px;}

Flexbox o kadar akıllı ki ızgarayı otomatik olarak yeniden hesaplar ve eşit olarak dağıtır.

body {
  margin: 0;
}

.container {
  display: flex;
}

.item {
  flex: 1;
  background: gray;
  height: 50px;
}

.item:not(:last-child) {
  margin-right: 10px;
}
<div class="container">
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
</div>

Esnek sargıya izin vermek istiyorsanız , aşağıdaki örneğe bakın.

body {
  margin: 0;
}

.container {
  display: flex;
  flex-wrap: wrap;
  margin-left: -10px;
}

.item {
  flex: 0 0 calc(50% - 10px);
  background: gray;
  height: 50px;
  margin: 0 0 10px 10px;
}
<div class="container">
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
  <div class="item"></div>
</div>


6
:last-childBir satırın sonundaki her çocuğu etkilemediğinden , öğeler sarılırsa bu işe yaramaz , değil mi?
Flimm

2
@Flimm Flex wrap ile çalışmak için bir yaklaşım ekledim, yukarıdaki ikinci bölüme bakın.
Etiketler

Bana en iyi cevap ... basit, temiz, verimli! Flex wrap ile mükemmel çalıştı, teşekkür ederim
Matthieu Marcé

16

Genel kardeş seçicisine dayanan ~ve sonsuz yuvalanmaya izin veren bir çözüm buldum .

Çalışan bir örnek için bu kod kalemine bakın

Temel olarak, sütun kaplarının içinde, başka bir çocuktan önce gelen her çocuk bir üst marj alır. Benzer şekilde, her sıralı kabın içinde, diğerinden önce gelen her çocuğun sol marjı olur.

.box {
  display: flex;
  flex-grow: 1;
  flex-shrink: 1;
}

.box.columns {
  flex-direction: row;
}

.box.columns>.box~.box {
  margin-left: 5px;
}

.box.rows {
  flex-direction: column;
}

.box.rows>.box~.box {
  margin-top: 5px;
}
<div class="box columns">
  <div class="box" style="background-color: red;"></div>
  <div class="box rows">
    <div class="box rows">
      <div class="box" style="background-color: blue;"></div>
      <div class="box" style="background-color: orange;"></div>
      <div class="box columns">
        <div class="box" style="background-color: yellow;"></div>
        <div class="box" style="background-color: pink;"></div>
      </div>
    </div>
    <div class="box" style="background-color: green;"></div>
  </div>
</div>


Bu, marjlar global olarak uygulanmadığı için farklı boyutlarda öğelerle sonuçlanır.
Steven Vachon

Mobil cihazlarda biraz tuhaf göründüğü için daha küçük ekranları işlemek için bazı ekstra CSS eklemeniz gerekecek, .box ~ .box kuralını daha büyük ekranlara uygulayacağım ve daha küçük ekranlar için .box sınıfını maksimum genişliğe ayarlayacağım % 100 ve bir kenar boşluğu tabanı.
rhysclay

14

Sawa'nın cevabından hareketle, çevredeki kenar boşluğu olmadan öğeler arasında sabit bir boşluk ayarlamanıza izin veren biraz geliştirilmiş bir sürüm.

http://jsfiddle.net/chris00/s52wmgtq/49/

Ayrıca Safari "-webkit-flex" sürümü de dahildir.

.outer1 {
    background-color: orange;
    padding: 10px;
}

.outer0 {
    background-color: green;
    overflow: hidden;
}

.container
{
    display: flex;
    display: -webkit-flex;
    flex-wrap: wrap;    
    -webkit-flex-wrap: wrap;
    background-color: rgba(0, 0, 255, 0.5);
    margin-left: -10px;
    margin-top: -10px;
}

.item
{
    flex-grow: 1;
    -webkit-flex-grow: 1;
    background-color: rgba(255, 0, 0, 0.5);
    width: 100px;
    padding: 10px;
    margin-left: 10px;
    margin-top: 10px;
    text-align: center;
    color: white;
}

<div class="outer1">
    <div class="outer0">
        <div class="container">
            <div class="item">text</div>
            <div class="item">text</div>
            <div class="item">text</div>
            <div class="item">text</div>
            <div class="item">text</div>
            <div class="item">text</div>
        </div>
    </div>
</div>

2
Bu aslında soruda verilen örnekle aynı değil mi?
ford


9

Ben sarılmış ve sabit genişlik sütunları için kullandım. Buradaki anahtarcalc()

SCSS örneği

$gap: 10px;

dl {
  display: flex;
  flex-wrap: wrap;
  padding: $gap/2;

  dt, dd {
    margin: $gap/2;}

  dt { // full width, acts as header
    flex: 0 0 calc(100% - #{$gap});}

  dd { // default grid: four columns 
    flex: 0 0 calc(25% - #{$gap});}

  .half { // hall width columns
    flex: 0 0 calc(50% - #{$gap});}

}

Tam Codepen örneği


2
Bu hala OP'nin negatif kenar boşluklarını kullanmasını engellediği ilk öğeden önce ve son öğeden sonra bir cilt payı ekler.
Herman

2
Flexbox, IE 11'deki "flex" öğesinde calc () özelliğini desteklemiyor
Adam Šipický

Her zaman kullanılamaz. doğrudan çocuklar için de bir sınırın gerekli olup olmadığını hayal edin
Andris

9

Bir esnek kap ile -X (negatif) kenar ve esnek öğe ile x (pozitif) bir farkla ya da doldurma istenen görsel sonuç hem öne Flex öğeler var 2x sabit boşluğu arasında sadece birbirlerine.

Esnek ürünlerde kenar boşluğu veya dolgu malzemesi kullanmak gibi bir tercih meselesi gibi görünüyor.

Bu örnekte, esneme öğeleri sabit boşluğu korumak için dinamik olarak ölçeklendirilir:

.flex-container { 
  margin: 0 -5px;
  display: flex;
  flex-flow: row wrap;
  justify-content: space-between;
}

.flex-item {
  margin: 0 5px; // Alternatively: padding: 0 5px;
  flex: 1 0 auto;
}

3
Üzgünüm, anlamadım. Cevabınız doğrudan soruda belirtilmeyen yeni ne getiriyor?
kullanıcı

Birincisi, flex-item üzerindeki marj ve dolguların istenen sonuca götürdüğünü özetlemek istedim, çünkü mevcut cevaplar sadece birinden veya diğerinden bahsediyor. İkincisi, esnek öğeleri kendileri ölçeklendirerek boşlukların korunduğu bir örnek vermek istedim.
Tim

İşte bu etkiyi gösteren bir kod örneği. codepen.io/dalgard/pen/Dbnus
pedalpete

8

Sonunda gapözelliği flexbox'a ekleyecekler. O zamana kadar zaten gapözelliğe sahip olan ve sadece tek bir satır olan CSS ızgarasını kullanabilirsiniz . Marjlarla uğraşmaktan daha güzel.


Tartışma burada: github.com/w3c/csswg-drafts/issues/1696 - bunlar aynı zamanda CSS Izgarası, Flexbox ve CSS Sütunları arasında adlandırmayı kolaylaştıracaklar.
Frank Lämmer

6

CSS gapözelliği:

Şu anda bazı tarayıcılarda çalışan çok sütunlu, esnek kutu ve ızgara düzenleri için yeni bir gapCSS özelliği var ! (Bkz. Bağlantı 1'i kullanabilir miyim ; bağlantı 2 ).

#box {
  display: flex;
  flex-wrap: wrap;
  width: 200px;
  background-color: red;
  gap: 10px;
}
.item {
  background: gray;
  width: 50px;
  height: 50px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>

Yazma itibariyle, bu sadece Firefox'ta ne yazık ki çalışıyor. İçinde "Deneysel web platformu özelliklerini etkinleştir" i etkinleştirirseniz şu anda Chrome'da çalışırabout:flags .


5

Çözümümde Flexbox kullanarak justify-contentüst öğe (konteyner) için flex-basisözelliği kullandım ve öğelerin özelliği içindeki kenar boşluklarını belirttim . Aşağıdaki kod snippet'ini kontrol edin:

.container {
  display: flex;
  flex-flow: row wrap;
  justify-content: space-around;
  margin-bottom: 10px;
}

.item {
  height: 50px;
  display: flex;
  justify-content: center;
  align-items: center;
  background-color: #999;
}

.item-1-4 {
  flex-basis: calc(25% - 10px);
}

.item-1-3 {
  flex-basis: calc(33.33333% - 10px);
}

.item-1-2 {
  flex-basis: calc(50% - 10px);
}
<div class="container">
  <div class="item item-1-4">1</div>
  <div class="item item-1-4">2</div>
  <div class="item item-1-4">3</div>
  <div class="item item-1-4">4</div>
</div>
<div class="container">
  <div class="item item-1-3">1</div>
  <div class="item item-1-3">2</div>
  <div class="item item-1-3">3</div>
</div>
<div class="container">
  <div class="item item-1-2">1</div>
  <div class="item item-1-2">2</div>
</div>


5

Flexbox ile, oluklar oluşturmak, özellikle sarma söz konusu olduğunda bir acıdır.

Negatif kenar boşlukları kullanmanız gerekir ( soruda gösterildiği gibi ):

#box {
  display: flex;
  width: 100px;
  margin: 0 -5px;
}

... veya HTML'yi ( başka bir cevapta gösterildiği gibi ):

<div class='flex-wrapper'>
  <div class='flex'>
    <div class='box'></div>
    <div class='box'></div>
            ...
  </div>
</div>

... veya başka bir şey.

Her durumda, çalışması için çirkin bir saldırıya ihtiyacınız var çünkü flexbox bir "flex-gap " özelliği ( en azından şimdilik ).

Bununla birlikte, oluklar sorunu CSS Izgara Düzeni ile basit ve kolaydır.

Grid özelliği, öğeler ve kap arasındaki boşluğu yok sayarken, ızgara öğeleri arasında boşluk oluşturan özellikler sağlar. Bu özellikler:

  • grid-column-gap
  • grid-row-gap
  • grid-gap (yukarıdaki her iki özellik için kısayol)

Son zamanlarda, teknik özellik tüm kutu modellerinde kullanılmak üzere bir dizi hizalama özelliği sağlayan CSS Kutu Hizalama Modülüne uyacak şekilde güncellendi . Yani özellikler şimdi:

  • column-gap
  • row-gap
  • gap (kısa gösterim)

Ancak, Grid destekleyen tüm tarayıcılar daha yeni özellikleri desteklemediğinden, aşağıdaki demoda orijinal sürümleri kullanacağım.

Ayrıca, öğeler ve kap arasında boşluk gerekliyse padding, kapta iyi çalışır (aşağıdaki demoda üçüncü örneğe bakın).

Spec'ten:

10.1. Oluk: row-gap, column-gap, ve gap özellikleri

row-gapVe column-gapözellikleri (ve gapbir ızgara kap belirtilen zaman kısaltılmış), ızgara satır ve sütunlar arasındaki ızgara olukları tanımlar. Sözdizimleri CSS Kutu Hizalaması 3 §8 Kutular Arasındaki Boşluklar .

Bu özelliklerin etkisi, etkilenen ızgara çizgilerinin elde ettiği kalınlık gibidir: iki ızgara çizgisi arasındaki ızgara izi, onları temsil eden oluklar arasındaki boşluktur.

.box {
  display: inline-grid;
  grid-auto-rows: 50px;
  grid-template-columns: repeat(4, 50px);
  border: 1px solid black;
}

.one {
  grid-column-gap: 5px;
}

.two {
  grid-column-gap: 10px;
  grid-row-gap: 10px;
}

.three {
  grid-gap: 10px;
  padding: 10px;
}

.item {
  background: lightgray;
}
<div class='box one'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>

<hr>

<div class='box two'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>

<hr>

<div class='box three'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>

Daha fazla bilgi:


4

Neden böyle yapmıyorsunuz:

.item + .item {
    margin-left: 5px;
}

İlki a hariç tüm elemanları vermek için bitişik kardeş seçiciyi kullanır . Flexbox sayesinde, bu eşit genişlikte elemanlarla bile sonuçlanır. Bu, dikey olarak yerleştirilmiş elemanlarla ve elbette yapılabilir..itemmargin-leftmargin-top


8
Bu, esnek öğeler her zaman tek bir sırada olduğu sürece işe yarar. Sarmaya izin verilirse, muhtemelen yeterli olmayacaktır.
Nick F

4

Alt öğelerde herhangi bir sınıfın ayarlanmasını gerektirmeyen benim çözümüm:

.flex-inline-row {
    display: inline-flex;
    flex-direction: row;
}

.flex-inline-row.flex-spacing-4px > :not(:last-child) {
    margin-right: 4px;
}

Kullanımı:

<div class="flex-inline-row flex-spacing-4px">
  <span>Testing</span>
  <span>123</span>
</div>

Aynı teknik, yukarıda verilen satır içi örneğe ek olarak normal esnek satırlar ve sütunlar için kullanılabilir ve 4 piksel dışındaki aralıklarla sınıflarla genişletilebilir.


4

Bu tür durumlar için genellikle + operatörünü kullanırım

#box {
  display: flex;
  width: 100px;
}
.item {
  background: gray;
  width: 50px;
  height: 50px;
}
.item + .item {
    margin-left: 5px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>


3

Bunu yapmanın en kolay yolunun yüzdelerle olduğunu ve sadece kenar boşluğunun genişliğinizi hesaplamasına izin verdiğini düşünüyorum

Bu, örneğinizi nerede kullanırsanız, böyle bir şeyle sonuçlanacağınız anlamına gelir.

#box {
   display: flex;
}

.item {
   flex: 1 1 23%;
   margin: 0 1%;
}

Değerleriniz genişliğe dayandığı anlamına gelir, ancak bu herkes için iyi olmayabilir.


Sadece bu çözümle karşılaştım ve evet, çok güzel. Benim durumumda çalışıyor, en azından (ilginç bulabilenler için bir kalem: codepen.io/rishatmuhametshin/pen/XXjpaV ).
rishat

2

Esnek kutu kullanılarak aralığı tamamlanmış bir kart UI öğeleri ızgarası:

resim açıklamasını buraya girin

Dolgu ve kenar boşluklarını iffy sonuçlarıyla manipüle ederek kartları manuel olarak yerleştirmekten hayal kırıklığına uğradım. İşte çok etkili bulduğum CSS özelliklerinin kombinasyonları:

.card-container {
  width: 100%;
  height: 900px;
  overflow-y: scroll;
  max-width: inherit;
  background-color: #ffffff;
  
  /*Here's the relevant flexbox stuff*/
  display: flex;
  flex-direction: row;
  justify-content: center;
  align-items: flex-start;
  flex-wrap: wrap; 
}

/*Supplementary styles for .card element*/
.card {
  width: 120px;
  height: 120px;
  background-color: #ffeb3b;
  border-radius: 3px;
  margin: 20px 10px 20px 10px;
}
<section class="card-container">
        <div class="card">

        </div>
        <div class="card">

        </div>
        <div class="card">

        </div>
        <div class="card">

        </div>
      </section>

Umarım bu millet, şimdiki zaman ve gelecek yardımcı olur.


Güncelleme: Bu boşluk, belirli bir hizalamaya (ör. Merkez, sol vb.) İhtiyaç duyulan mobil oluşturma HTML öğeleri için etkilidir. Kendinizi mobil geliştirme için esnek kutu kullanarak bulursanız, tamamen marj tabanlı hizalamaya geçmekte rahatladım.
buildpax

2

Columnify - N sütun için bir solo sınıf

Flexbox ve SCSS

.columnify {
  display: flex;

  > * {
    flex: 1;

    &:not(:first-child) {
      margin-left: 2rem;
    }
  }
}

Flexbox ve CSS

.columnify {
  display: flex;
}

.columnify > * {
  flex: 1;
}

.columnify > *:not(:first-child) {
  margin-left: 2rem;
}
<div class="columnify">
  <div style="display: inline-block; height: 20px; background-color: blue;"></div>
  <div style="display: inline-block; height: 20px; background-color: blue"></div>
  <div style="display: inline-block; height: 20px; background-color: blue"></div>
</div>

Üzerinde onunla oynamak JSFiddle .


1

#box {
  display: flex;
  width: 100px;
}
.item {
  background: gray;
  width: 50px;
  height: 50px;
}
/* u mean utility */
.u-gap-10 > *:not(:last-child) {
  margin-right: 10px;
}
<div id='box' class="u-gap-10">
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>


1

Sadece .item + .itemsaniye ile eşleştirmek için seçicide kullanın.item

#box {
  display: inline-flex;
  margin: 0 -5px;
}
.item {
  background: gray;
  width: 10px;
  height: 50px;
}

#box .item + .item {
  margin-left: 10px;
}
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
</div>


1

varsayarsak:

  • Sarma ile 4 sütun ızgara düzeni istiyorsunuz
  • Öğe sayısı mutlaka 4'ün katı değil

1., 5., 9. öğe hariç her öğe için bir sol kenar boşluğu ayarlayın; ve her öğeye sabit genişlik ayarlayın. Sol kenar boşluğu 10 piksel ise, her satırda 4 öğe arasında 30 piksel kenar boşluğu olacaktır, öğenin yüzde genişliği aşağıdaki gibi hesaplanabilir:

100% / 4 - horizontal-border - horizontal-padding - left-margin * (4 - 1) / 4

Bu, flexbox'ın son sırasını içeren sorunlar için iyi bir çözümdür.

.flex {
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  margin: 1em 0;
  background-color: peachpuff;
}

.item {
  margin-left: 10px;
  border: 1px solid;
  padding: 10px;
  width: calc(100% / 4 - 2px - 20px - 10px * (4 - 1) / 4);
  background-color: papayawhip;
}

.item:nth-child(4n + 1) {
  margin-left: 0;
}

.item:nth-child(n + 5) {
  margin-top: 10px;
}
<div class="flex">
  <div class="item">1</div>
  <div class="item">2</div>
  <div class="item">3</div>
  <div class="item">4</div>
</div>
<div class="flex">
  <div class="item">1</div>
  <div class="item">2</div>
  <div class="item">3</div>
  <div class="item">4</div>
  <div class="item">5</div>
  <div class="item">6</div>
</div>
<div class="flex">
  <div class="item">1</div>
  <div class="item">2</div>
  <div class="item">3</div>
  <div class="item">4</div>
  <div class="item">5</div>
  <div class="item">6</div>
  <div class="item">7</div>
  <div class="item">8</div>
  <div class="item">9</div>
</div>


1

Gerçekten bunu yapmak için güzel, düzenli, sadece bir CSS yolu vardır (biri "daha iyi" düşünebilirsiniz).

Burada gönderilen tüm cevaplardan, sadece calc () başarıyla kullanan bir tane buldum (Dariusz Sikorski tarafından). Ancak "" son satırda yalnızca 2 öğe varsa başarısız olur "ile genişletilmiş bir çözüm yoktu.

Bu çözüm, OP'nin sorusunu olumsuz marjlara alternatif olarak ve Dariusz'a yöneltilen sorunu ele alıyor.

notlar:

  • Bu örnekte yalnızca 3 sütunlu bir düzen gösterilmektedir
  • Bu kullandığı calc()tarayıcı matematiği geri istediği şekilde yapmasına izin - 100%/3 (33,3333% az önce de çalışması gerekir rağmen) ve (1em/3)*2 (.66em de iyi çalışması gerekir rağmen) .
  • ::afterSütunlardan daha az öğe varsa son satırı doldurmak için kullanır

.flex-container {
  display: flex;
  justify-content: space-between;
  flex-wrap: wrap;
}
.flex-container:after {
  content: "";
}
.flex-container > div,
.flex-container:after {
  box-sizing: border-box;
  width: calc((100%/3) - ((1em/3)*2));
}
.flex-container > :nth-child(n + 4) {
  margin-top: 1em;
}

/* the following is just to visualize the items */
.flex-container > div,
.flex-container:after {
  font-size: 2em;
}
.flex-container {
  margin-bottom:4em;
}
.flex-container > div {
  text-align: center;
  background-color: #aaa;
  padding: 1em;
}
.flex-container:after {
  border: 1px dashed red;
}
<h2>Example 1 (2 elements)</h2>
<div class="flex-container">
  <div>1</div>
  <div>2</div>
</div>

<h2>Example 2 (3 elements)</h2>
<div class="flex-container">
  <div>1</div>
  <div>2</div>
  <div>3</div>
</div>

Ayrıca https://codepen.io/anon/pen/rqWagE adresinde


1

Yeni mülkü kullanabilirsiniz gap. Bu makalede bulduğum açıklamayı ve daha fazla bilgiyi kopyalarım

CSS ızgara düzeninde bir süredir boşluk (daha önce ızgara boşluğu) vardı. Boşluk, alt öğelerin etrafındaki boşluktan ziyade içeren bir elemanın iç boşluğunu belirterek, birçok genel yerleşim sorununu çözer. Örneğin, boşlukla, bir alt öğenin kenarlarında istenmeyen boşluklara neden olan alt öğelerdeki kenar boşlukları hakkında endişelenmenize gerek yoktur:

Ne yazık ki şu anda yalnızca FireFox esnek düzenlerdeki boşluğu desteklemektedir.

@use postcss-preset-env {
  stage: 0;
  browsers: last 2 versions
}

section {
  width: 30vw;
  
  display: grid;
  gap: 1rem;
  grid-template-columns: repeat(auto-fit, minmax(12ch, 1fr));
  
  &[flex] {
    display: flex;
    flex-wrap: wrap;
  }
  
  margin-bottom: 3rem;
}

.tag {
  color: white;
  background: hsl(265 100% 47%);
  padding: .5rem 1rem;
  border-radius: 1rem;
}

button {
  display: inline-flex;
  place-items: center;
  gap: .5rem;
  background: hsl(265 100% 47%);
  border: 1px solid hsl(265 100% 67%);
  color: white;
  padding: 1rem 2rem;
  border-radius: 1rem;
  font-size: 1.25rem;
}

body {
  min-height: 100vh;
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
}
<section>
  <h1>Grid</h1> 
  <div class="tag">Awesome</div>
  <div class="tag">Coo</div>
  <div class="tag">Rad</div>
  <div class="tag">Math</div>
</section>
<br>
<section flex>
  <h1>Flex</h1>
  <div class="tag">Awesome</div>
  <div class="tag">Coo</div>
  <div class="tag">Rad</div>
  <div class="tag">Math</div>
</section>


gapburada zaten bir cevapta tavsiye edilmiştir stackoverflow.com/a/58041749/2756409 Ayrıca, bu CSS değil.
TylerH

0

Her durumda çalışmaz, ancak esnek alt genişlikleriniz (%) varsa ve satır başına öğe sayısını biliyorsanız, kullanarak gerekli öğelerin kenar boşluklarını çok temiz bir şekilde belirleyebilirsiniz. nth-child seçici seçici / s .

Bu büyük ölçüde "daha iyi" ile ne demek istediğinize bağlıdır. Bu şekilde alt öğeler veya negatif öğeler için ek sarıcı işaretlemesi gerekmez - ancak her ikisinin de yeri vardır.

section {
  display: block
  width: 100vw;
}
.container {
  align-content: flex-start;
  align-items: stretch;
  background-color: #ccc;
  display: flex;
  flex-flow: row wrap;
  justify-content: flex-start;
  width: 100%;
}

.child-item {
  background-color: #c00;
  margin-bottom: 2%;
  min-height: 5em;
  width: 32%;
}

.child-item:nth-child(3n-1) {
  margin-left: 2%;
  margin-right: 2%;
}
<html>
  <body>
      <div class="container">
        <div class="child-item"></div>
        <div class="child-item"></div>
        <div class="child-item"></div>
        <div class="child-item"></div>
        <div class="child-item"></div>
        <div class="child-item"></div>
        <div class="child-item"></div>
      </div>
   </body>
</html>


Duyarlı değil. Yalnızca sabit genişlikli üst öğe için çalışır.
Yeşil

1
OP duyarlı bir çözüm istemez ve örnekleri bir sabitleme genişliği kullanır. Bunun% değerler kullandığı göz önüne alındığında, öğelerin yüzde olarak ayarlanan üst öğenin boyutuna uyum sağlayacağı için bunun duyarlı olduğunu iddia etmek kolaydır.
jnmrobinson

0

Daha önce aynı konuyla karşılaştım, sonra bunun cevabına rastladım. Gelecekte referans için başkalarına yardımcı olacağını umuyoruz.

uzun cevap kısa, çocuğunuzun esnek öğeleri için bir sınır ekleyin. esnek öğeler arasında istediğiniz gibi kenar boşlukları belirleyebilirsiniz. Snippet'te, illüstrasyon amaçlı siyah kullanıyorum, isterseniz 'şeffaf' kullanabilirsiniz.

#box {
  display: flex;
  width: 100px;
  /* margin: 0 -5px; *remove this*/
}
.item {
  background: gray;
  width: 50px;
  height: 50px;
  /* margin: 0 5px; *remove this*/
  border: 1px solid black; /* add this */
}
.item.special{ margin: 0 10px; }
<div id='box'>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item'></div>
  <div class='item special'></div>
</div>


0

Kutu konteynerindeki negatif marj hilesi harika çalışıyor. İşte sipariş, sarma ve ne ile harika çalışan başka bir örnek.

.container {
   border: 1px solid green;
   width: 200px;
   display: inline-block;
}

#box {
  display: flex;
  flex-wrap: wrap-reverse;
  margin: -10px;
  border: 1px solid red;
}
.item {
  flex: 1 1 auto;
  order: 1;
  background: gray;
  width: 50px;
  height: 50px;
  margin: 10px;
  border: 1px solid blue;
}
.first {
  order: 0;
}
<div class=container>
<div id='box'>
  <div class='item'>1</div>
  <div class='item'>2</div>
  <div class='item first'>3*</div>
  <div class='item'>4</div>
  <div class='item'>5</div>
</div>
</div>

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.