F. Esser
F. Esser

Reputation: 51

Flexbox - "space-between" - Zero width elements cause unwanted spaces

I am trying to create a kind of "glossary" with flexbox elements. I have a navigation to scroll to the right letter.

There is my Problem: I placed anchor-links before the first element of each letter. This causes unwanted spaces even if the elements has got width:0px; visibility:hidden; etc. I guess I've tried nearly everything... Hope you've got a solution.

Notice: In this case it is not an option to set the anchor-link to position:absolute!

*, *:before, *:after {
	padding: 0;
	margin: 0;
	border: 0;
	-webkit-box-sizing: border-box;
	-moz-box-sizing: border-box;
	box-sizing: border-box;
}

body {
	font-family: Gotham, "Helvetica Neue", Helvetica, Arial, sans-serif;
	font-size: 14px;
}

.letters {
	background: #fff;
	border-bottom: 1px solid #ccc;
	text-align: center;
	padding: 10px;
	margin-bottom: 20px
}

.letters ul li {
	display: inline-block;
	height: 34px;
	line-height: 34px;
	list-style: outside none none;
	text-align: center;
	width: 34px;
	margin: 0 .27em;
}

.letters ul li a {
	background: #ad1800 none repeat scroll 0 0;
	border: 1px solid #ad1800;
	color: #fff;
	display: block;
	line-height: 32px;
	text-decoration: none;
}

.letter_around {
	list-style: none;
	padding: 20px 50px;
	position: relative;
	-webkit-flex-flow: row wrap;
	-moz-flex-flow: row wrap;
	flex-flow: row wrap;
	-webkit-justify-content: space-between;
	-moz-justify-content: space-between;
	justify-content: space-between;
	display: -webkit-box;
	display: -ms-flexbox;
	display: -webkit-flex;
	display: flex;
}

.glossary_item {
	padding: 15px 20px 20px;
	width: 22%;
	background: #fff;
	border: 1px solid #ccc;
	transition: 0.4s all;
	overflow: hidden;
	margin-bottom: 20px;
}

.glossary_letter {
	width: 0px;
	height: 0px;
	overflow: hidden;
	position: relative;
	visibility: hidden;
}
<div class="wrapper glossary_wrapper">
  <div class="content clearfix">
    <div class="letters clearfix">
      <ul class="letters_ul">
        <li class="glossarylink">
          <a href="#A">A</a>
        </li>
        <li class="glossarylink">
          <a href="#B">B</a>
        </li>
        <li class="glossarylink">
          <a href="#C">C</a>
        </li>
        <li class="glossarylink">
          <a href="#D">D</a>
        </li>
        <li class="glossarylink">
          <a href="#E">E</a>
        </li>
      </ul>
    </div>
    <div class="letter_around">
      <a class="glossary_letter" id="A" name="A"></a>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="B" name="B"></a>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="C" name="C"></a>
      <div class="glossary_item"><span class="glossary-title">C - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="D" name="D"></a>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="E" name="E"></a>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
    </div>
  </div>
</div>

Upvotes: 2

Views: 131

Answers (5)

Ilya Streltsyn
Ilya Streltsyn

Reputation: 13536

Setting justify-content: space-around is basically the same as setting auto to left and right margins to all flex items (the available space will be distributed equally on the left and on the right of each of them). So, to exclude some items from available space distribution, you can remove justify-content and set the equivalent margins only to the needed items:

*, *:before, *:after {
	padding: 0;
	margin: 0;
	border: 0;
	-webkit-box-sizing: border-box;
	-moz-box-sizing: border-box;
	box-sizing: border-box;
}

body {
	font-family: Gotham, "Helvetica Neue", Helvetica, Arial, sans-serif;
	font-size: 14px;
}

.letters {
	background: #fff;
	border-bottom: 1px solid #ccc;
	text-align: center;
	padding: 10px;
	margin-bottom: 20px
}

.letters ul li {
	display: inline-block;
	height: 34px;
	line-height: 34px;
	list-style: outside none none;
	text-align: center;
	width: 34px;
	margin: 0 .27em;
}

.letters ul li a {
	background: #ad1800 none repeat scroll 0 0;
	border: 1px solid #ad1800;
	color: #fff;
	display: block;
	line-height: 32px;
	text-decoration: none;
}

.letter_around {
	list-style: none;
	padding: 20px 50px;
	position: relative;
	-webkit-flex-flow: row wrap;
	-moz-flex-flow: row wrap;
	flex-flow: row wrap;
	display: -webkit-box;
	display: -ms-flexbox;
	display: -webkit-flex;
	display: flex;
}

.glossary_item {
	padding: 15px 20px 20px;
	width: 22%;
	background: #fff;
	border: 1px solid #ccc;
	transition: 0.4s all;
	overflow: hidden;
	margin: auto;
	margin-bottom: 20px;
}

.glossary_letter {
	width: 0;
	margin: 0;
}
<div class="wrapper glossary_wrapper">
  <div class="content clearfix">
    <div class="letters clearfix">
      <ul class="letters_ul">
        <li class="glossarylink">
          <a href="#A">A</a>
        </li>
        <li class="glossarylink">
          <a href="#B">B</a>
        </li>
        <li class="glossarylink">
          <a href="#C">C</a>
        </li>
        <li class="glossarylink">
          <a href="#D">D</a>
        </li>
        <li class="glossarylink">
          <a href="#E">E</a>
        </li>
      </ul>
    </div>
    <div class="letter_around">
      <a class="glossary_letter" id="A" name="A"></a>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="B" name="B"></a>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="C" name="C"></a>
      <div class="glossary_item"><span class="glossary-title">C - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="D" name="D"></a>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="E" name="E"></a>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
    </div>
  </div>
</div>

Upvotes: 0

F. Esser
F. Esser

Reputation: 51

Found the solution for my own. It's not the best solution I guess, but it works fine.

I filled the spaces calculated by flexbox itself with a margin-left minus value of the percentage that is left. So in my Case the widht of the elements was 22%. This 4x is 88% of the whole container width. That means that the calculated margin of the elements is about 4% of the container width. So if you reduce the margin of the anchor-element by 4% you get the right position of the boxes.

I know that is not the best solution, but it works. If you've got a better one, please show me. :)

*, *:before, *:after {
	padding: 0;
	margin: 0;
	border: 0;
	-webkit-box-sizing: border-box;
	-moz-box-sizing: border-box;
	box-sizing: border-box;
}

body {
	font-family: Gotham, "Helvetica Neue", Helvetica, Arial, sans-serif;
	font-size: 14px;
}

.letters {
	background: #fff;
	border-bottom: 1px solid #ccc;
	text-align: center;
	padding: 10px;
	margin-bottom: 20px
}

.letters ul li {
	display: inline-block;
	height: 34px;
	line-height: 34px;
	list-style: outside none none;
	text-align: center;
	width: 34px;
	margin: 0 .27em;
}

.letters ul li a {
	background: #ad1800 none repeat scroll 0 0;
	border: 1px solid #ad1800;
	color: #fff;
	display: block;
	line-height: 32px;
	text-decoration: none;
}

.letter_around {
	list-style: none;
	padding: 20px 10px;
	position: relative;
	-webkit-flex-flow: row wrap;
	-moz-flex-flow: row wrap;
	flex-flow: row wrap;
	-webkit-justify-content: space-between;
	-moz-justify-content: space-between;
	justify-content: space-between;
	display: -webkit-box;
	display: -ms-flexbox;
	display: -webkit-flex;
	display: flex;
}

.glossary_item {
	padding: 15px 20px 20px;
	width: 22%;
	background: #fff;
	border: 1px solid #ccc;
	transition: 0.4s all;
	overflow: hidden;
	margin-bottom: 20px;
}

.glossary_letter {
	width: 0px;
	height: 0px;
	overflow: hidden;
	position: relative;
	visibility: hidden;
  margin-left: -4%;
}
<div class="wrapper glossary_wrapper">
  <div class="content clearfix">
    <div class="letters clearfix">
      <ul class="letters_ul">
        <li class="glossarylink">
          <a href="#A">A</a>
        </li>
        <li class="glossarylink">
          <a href="#B">B</a>
        </li>
        <li class="glossarylink">
          <a href="#C">C</a>
        </li>
        <li class="glossarylink">
          <a href="#D">D</a>
        </li>
        <li class="glossarylink">
          <a href="#E">E</a>
        </li>
      </ul>
    </div>
    <div class="letter_around">
      <a class="glossary_letter" id="A" name="A"></a>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="B" name="B"></a>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="C" name="C"></a>
      <div class="glossary_item"><span class="glossary-title">C - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="D" name="D"></a>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <a class="glossary_letter" id="E" name="E"></a>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
    </div>
  </div>
</div>

Upvotes: 0

sol
sol

Reputation: 22949

This solution is not particularly clean. Ideally, someone with more knowledge will provide a better solution.

  1. Remove justify-content property from .letter-around
  2. Add margin-right: auto to glossary-item to create space between the items.
  3. Target the last item in each grid using nth-of-type selector, and remove the margin.

I have changed the glossary-letter from a to a span, I think it makes more sense semantically. I have also moved some of the css rules from .glossary-item to the span.

*,
*:before,
*:after {
  padding: 0;
  margin: 0;
  border: 0;
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
}

body {
  font-family: Gotham, "Helvetica Neue", Helvetica, Arial, sans-serif;
  font-size: 14px;
}

.letters {
  background: #fff;
  border-bottom: 1px solid #ccc;
  text-align: center;
  padding: 10px;
  margin-bottom: 20px
}

.letters ul li {
  display: inline-block;
  height: 34px;
  line-height: 34px;
  list-style: outside none none;
  text-align: center;
  width: 34px;
  margin: 0 .27em;
}

.letters ul li a {
  background: #ad1800 none repeat scroll 0 0;
  border: 1px solid #ad1800;
  color: #fff;
  display: block;
  line-height: 32px;
  text-decoration: none;
}

.letter_around {
  list-style: none;
  padding: 20px 50px;
  position: relative;
  -webkit-flex-flow: row wrap;
  -moz-flex-flow: row wrap;
  flex-flow: row wrap;
  display: -webkit-box;
  display: -ms-flexbox;
  display: -webkit-flex;
  display: flex;
}

.glossary_item {
  transition: 0.4s all;
  overflow: hidden;
  margin-bottom: 20px;
  width: 22%;
  margin-right: auto;
}

.glossary_item span {
  padding: 15px 20px 20px;
  background: #fff;
  border: 1px solid #ccc;
  display: block;
}

.glossary_item:nth-of-type(4n) {
  margin-right: 0;
}
<div class="wrapper glossary_wrapper">
  <div class="content clearfix">
    <div class="letters clearfix">
      <ul class="letters_ul">
        <li class="glossarylink">
          <a href="#A">A</a>
        </li>
        <li class="glossarylink">
          <a href="#B">B</a>
        </li>
        <li class="glossarylink">
          <a href="#C">C</a>
        </li>
        <li class="glossarylink">
          <a href="#D">D</a>
        </li>
        <li class="glossarylink">
          <a href="#E">E</a>
        </li>
      </ul>
    </div>
    <div class="letter_around">
      <span class="glossary_letter" id="A" name="A"></span>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">A - Lorem ipsum dolor </span></div>
      <span class="glossary_letter" id="B" name="B"></span>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">B - Lorem ipsum dolor </span></div>
      <span class="glossary_letter" id="C" name="C"></span>
      <div class="glossary_item"><span class="glossary-title">C - Lorem ipsum dolor </span></div>
      <span class="glossary_letter" id="D" name="D"></span>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">D - Lorem ipsum dolor </span></div>
      <span class="glossary_letter" id="E" name="E"></span>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
      <div class="glossary_item"><span class="glossary-title">E - Lorem ipsum dolor </span></div>
    </div>
  </div>
</div>

Upvotes: 1

user5718206
user5718206

Reputation:

Ok, try another way, it keeps the anchor link working:

.glossary_letter {
  flex: 0 0 100%;
}

Upvotes: 0

user5718206
user5718206

Reputation:

The most simple solution is to add

.glossary_letter {
  display: none;
}

So it fisically will be but your extra space will disappear.

Upvotes: 0

Related Questions