39

A flex container has four children, each with a flex-basis of 25% an a min-width. flex-flow is set to row wrap. Browsers other then Safari handle this as expected: if the min-width is reached, it wraps the the next item to the next row. In Safari it overflow the container.

See demo here: http://codepen.io/lbilharz/pen/aJbkI

JADE

h1 Why this ain't wrappin' in mobile-safari?
  .flex
    for i in ['one','two','three','four']
      .item
        h2=i

Stylus

.flex
  display flex
  flex-wrap wrap
  flex-direction row
  padding 1em
  background lightyellow
  .item
    flex 1 0 25%
    padding 1em
    box-sizing border-box
    min-width 15em

Any ideas?

Brian
  • 3,850
  • 3
  • 21
  • 37
Lars
  • 521
  • 1
  • 4
  • 6

6 Answers6

55

Per a comment on bugs.webkit.org, it seems the solution is simple!

If your style is

div.flex {
    display: -webkit-flex;
    display: flex;
    -webkit-flex-wrap: wrap;
    flex-wrap: wrap;
    -webkit-flex-direction: row;
    flex-direction: row;
}
div.flex .item {
    min-width: 15em;
    -webkit-flex: 1;
    flex: 1;
}

you just need to add more explicitness to your flex declaration. In fact, I think only one line needs to change like so

div.flex {
    display: -webkit-flex;
    display: flex;
    -webkit-flex-wrap: wrap;
    flex-wrap: wrap;
    -webkit-flex-direction: row;
    flex-direction: row;
}
div.flex .item {
    min-width: 15em;
    -webkit-flex: 1 1 15em; /* this */
    flex: 1;
} 
Joseph Hansen
  • 12,665
  • 8
  • 50
  • 68
  • 7
    Thank you for your comment, it helped me to understand flex-basis some more. You could also omit min-width and write `-webkit-flex: 1 0 15em; flex: 1 0 15em;`. – nils Sep 22 '15 at 12:51
6

I'm using a max-width on my flex items, so I was able to solve this by explicitly setting the max-width within the flex property:

.wrapper {
  display: flex;
  flex-flow: row wrap;
}
li {
  width: 100%;
  max-width: 500px;
  flex: 1 1 500px;
}
kmgdev
  • 2,607
  • 28
  • 41
3

This is a Safari IOS bug. So the fix / workaround is to set the flex-basis to an explicit width rather than auto for child element.

Prakash Upadhyay
  • 423
  • 1
  • 3
  • 14
1

Please, note that not all prefixers work the same way, so there's known issues on every prefixer that puts you in need to manually add some vendor prefix. Don't rely on blind-trusting on prefixers or automated software unless you checked it works hundred percent in your project.

For detailed flex bugs, please refer:

https://caniuse.com/#feat=flexbox

https://github.com/philipwalton/flexbugs

As Joseph Hansen pointed out, including width property as third param on flex declaration is the desired workaround for flex and it should fix most of issues derived from merging flex with some declarations.

But this doesn't solve all issues on safari, or even other browsers; it sometimes will depend on childrens or some other property; in the example below, you'll see the middle box growing more than usual, even when all three elements are supposed to keep same width ON SAFARI. If you use chrome, it will look pretty nice.

This is not a flex issue but a display interpreter one. Simply removing display: inline-table will fix the issue for safari, but, with more child elements, it will make all cards grow in height, so we'll need to fix this other behaviour derived from switching to another display property.

.flexrow {
  display: -webkit-flex;
  display: flex;
  flex-flow: row wrap;
  flex-direction: row;
  -webkit-flex-wrap: wrap;
  flex-wrap: wrap;
  margin: 0px -15px;
}
.card-container {
  display: inline-table;
}
div.card-container {
  -webkit-flex: 0 1 calc(33.3333% - 30px);
  flex: 0 1 calc(33.3333% - 30px);
  margin: 15px;
}
.card-container {
  background:green;
}
<div class="flexrow">
  <div class="card-container">
      <div class="card">
        <p class="title">
          test test test
        </p>
      </div>
    </div>

    <div class="card-container">
      <div class="card">
        <p class="title">
          test testtesttest test test test
        </p>
      </div>
    </div>

    <div class="card-container">
      <div class="card">
        <p class="title">
          test test
        </p>
      </div>
    </div>
</div>

this is only an example but i suggest to check every property that have boundaries with flexbox (i.e. display, position and more).

Here the working example:

.flexrow {
  display: -webkit-flex;
  display: flex;
  flex-flow: row wrap;
  flex-direction: row;
  -webkit-flex-wrap: wrap;
  flex-wrap: wrap;
  margin: 0px -15px;
}
.card-container {
  // display: inline-table;
}
div.card-container {
  -webkit-flex: 0 1 calc(33.3333% - 30px);
  flex: 0 1 calc(33.3333% - 30px);
  margin: 15px;
}
.card-container {
  background:green;
}
<div class="flexrow">
  <div class="card-container">
      <div class="card">
        <p class="title">
          test test test
        </p>
      </div>
    </div>

    <div class="card-container">
      <div class="card">
        <p class="title">
          test testtesttest test test test
        </p>
      </div>
    </div>

    <div class="card-container">
      <div class="card">
        <p class="title">
          test test
        </p>
      </div>
    </div>
</div>
JoelBonetR
  • 1,551
  • 1
  • 15
  • 21
0

In the item that you are displaying try to add this width: max-content; or width: min-content; as per your requirement.

biberman
  • 5,606
  • 4
  • 11
  • 35
Suhail
  • 21
  • 2
-2

Some browsers do not fully support all the CSS3 elements. Try this:

  display:-webkit-box;
  display:-webkit-flex;
  display:-webkit-flexbox;
  display:-moz-flex;
  display:-moz-box;
  display:-ms-flexbox;
  display:flex;
ninjaPixel
  • 6,122
  • 3
  • 36
  • 47
  • 4
    thanks for your reply, but if you take a look at the codepen, you will see that the vendor-prefixes are added automatically. – Lars Jun 15 '15 at 09:22