使用 flexbox 设计表单样式——标签溢出嵌套的 flexbox div
Styling a form with flexbox -- labels overflowing nested flexbox divs
这可能是重复的,但我已经在 Whosebug 上解决了大约 20 "flexbox overflowing children" 个问题,但没有找到我的特定问题的答案......所以如果这个 是 重复并且有人已经回答了这个特定问题我真的非常感谢 link :) 在此先感谢您的任何建议 :)
我正在设计一个预生成的表单,更改 html 在这种情况下不切实际。 has 是一个简单的,我不敢相信我忽略了那个! css 解决这个...
我对这种样式的意图是,如果可能的话,我希望每个单独的标签都保持在一行上,而不是挤压得更窄和环绕。如果这意味着一个单选按钮 + 标签延伸整个表单的宽度,那很好,但我只希望标签(加上单选输入)比表单宽时换行。同时,如果表单项 div 不能全部放在一行中,我希望它们在必要时换行。我正在使用嵌套的 flexboxes,因为我希望能够垂直居中我的单选按钮和标签。不幸的是,根据包含元素的宽度,"form-item" div 正在挤压自己以适应一行并且其中的标签溢出!
我已将表单简化为一个非常基本的测试用例。你可以see it on codepen。这是 html 和 scss:
html:
<form>
<div class="container">
<div class="form-item form-item--1">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--2">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--3">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--4">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
</div>
</form>
scss:
.container {
// setting the container div to a width that provokes this issue...
max-width: 45em;
// the form-item child divs should be wrapping at this width, but instead their contents are overflowing!!!
display: flex;
flex-wrap: wrap;
}
.form-item {
// put 20px between this element and the next element to the right
margin-right: 20px;
// make each div at least as wide as its content, and have them expand to fill all available space.
flex: 1 0 auto;
display: flex; // <-- If the form-item divs are not flexboxes, the contents do *not* overflow. Instead the last div wraps as desired. Of course, then the contents are not vertically centered, and the flex-bases of the input and labels are ignored. For those reasons, I *really* want to use display: flex here!!!
input {
// make the radio button take up exactly 25px of horizontal space
flex: 0 0 25px;
}
label {
// make the label at least as wide as its content, and have it expand to fill all available space.
flex: 1 0 auto;
}
}
// styling to better display the situation, but shouldn't affect the issue. (You can comment all the following out, and the labels are still overflowing their form-item parent div)
html {
font-size: 62.5%;
}
body {
font-size: 16px;
}
.container {
align-items: center;
border: 1px dashed black;
height: 100px;
}
.form-item {
align-items: center;
border: 1px dashed green;
height: 50px;
label {
border: 1px dashed orange;
}
}
您应该试试下面的代码。如您所料,这种变化非常微妙。我只是将输入的样式从使用 25px 的 flex-basis
更改为 auto
并将宽度设置为 25px。
SCSS
.container {
max-width: 45em;
display: flex;
flex-wrap: wrap;
}
.form-item {
margin-right: 20px;
flex: 1 0 auto;
display: flex;
input {
width: 25px;
flex: 0 0 auto;
}
label {
flex: 1 0 auto;
}
}
html {
font-size: 62.5%;
}
body {
font-size: 16px;
}
.container {
align-items: center;
border: 1px dashed black;
height: 100px;
}
.form-item {
align-items: center;
border: 1px dashed green;
height: 50px;
label {
border: 1px dashed orange;
}
}
这可能是重复的,但我已经在 Whosebug 上解决了大约 20 "flexbox overflowing children" 个问题,但没有找到我的特定问题的答案......所以如果这个 是 重复并且有人已经回答了这个特定问题我真的非常感谢 link :) 在此先感谢您的任何建议 :)
我正在设计一个预生成的表单,更改 html 在这种情况下不切实际。 has 是一个简单的,我不敢相信我忽略了那个! css 解决这个...
我对这种样式的意图是,如果可能的话,我希望每个单独的标签都保持在一行上,而不是挤压得更窄和环绕。如果这意味着一个单选按钮 + 标签延伸整个表单的宽度,那很好,但我只希望标签(加上单选输入)比表单宽时换行。同时,如果表单项 div 不能全部放在一行中,我希望它们在必要时换行。我正在使用嵌套的 flexboxes,因为我希望能够垂直居中我的单选按钮和标签。不幸的是,根据包含元素的宽度,"form-item" div 正在挤压自己以适应一行并且其中的标签溢出!
我已将表单简化为一个非常基本的测试用例。你可以see it on codepen。这是 html 和 scss:
html:
<form>
<div class="container">
<div class="form-item form-item--1">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--2">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--3">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
<div class="form-item form-item--4">
<input type='radio' id='item1' name='group'>
<label for='item1'>The quick brown fox</label>
</div>
</div>
</form>
scss:
.container {
// setting the container div to a width that provokes this issue...
max-width: 45em;
// the form-item child divs should be wrapping at this width, but instead their contents are overflowing!!!
display: flex;
flex-wrap: wrap;
}
.form-item {
// put 20px between this element and the next element to the right
margin-right: 20px;
// make each div at least as wide as its content, and have them expand to fill all available space.
flex: 1 0 auto;
display: flex; // <-- If the form-item divs are not flexboxes, the contents do *not* overflow. Instead the last div wraps as desired. Of course, then the contents are not vertically centered, and the flex-bases of the input and labels are ignored. For those reasons, I *really* want to use display: flex here!!!
input {
// make the radio button take up exactly 25px of horizontal space
flex: 0 0 25px;
}
label {
// make the label at least as wide as its content, and have it expand to fill all available space.
flex: 1 0 auto;
}
}
// styling to better display the situation, but shouldn't affect the issue. (You can comment all the following out, and the labels are still overflowing their form-item parent div)
html {
font-size: 62.5%;
}
body {
font-size: 16px;
}
.container {
align-items: center;
border: 1px dashed black;
height: 100px;
}
.form-item {
align-items: center;
border: 1px dashed green;
height: 50px;
label {
border: 1px dashed orange;
}
}
您应该试试下面的代码。如您所料,这种变化非常微妙。我只是将输入的样式从使用 25px 的 flex-basis
更改为 auto
并将宽度设置为 25px。
SCSS
.container {
max-width: 45em;
display: flex;
flex-wrap: wrap;
}
.form-item {
margin-right: 20px;
flex: 1 0 auto;
display: flex;
input {
width: 25px;
flex: 0 0 auto;
}
label {
flex: 1 0 auto;
}
}
html {
font-size: 62.5%;
}
body {
font-size: 16px;
}
.container {
align-items: center;
border: 1px dashed black;
height: 100px;
}
.form-item {
align-items: center;
border: 1px dashed green;
height: 50px;
label {
border: 1px dashed orange;
}
}