今天项目的组件遇到一个隐藏的样式bug。
该组件大概是这样设计,左中右结构,左侧放置标题,中间放置显示内容,右侧放置图标之类的,如下图。左侧内容和中间主体内容是必定显示的,右侧图标可能不用显示。就采用了弹性盒子布局。左侧和右侧不是固定,但会有一个具体的值,所有中间就会根据两侧分配后获得剩下的宽度分配,就采用flex:1; 这样的写法。
当中间内容过长的时候,把会row-item的宽度给撑开,这就造成了bug,如下图:
遂把代码抽出来,组件层级结构相似,在一个静态页面调试分析。代码结构如下:
<html>
<head>
<meta charset="UTF-8">
<title>test</title>
<style>
.box-item {
width: 400px;
height: 50px;
margin: 100px;
background: #999;
}
.sui-cell {
display: flex;
flex-direction: row;
width: 100%;
}
.sui-cell-left {
width: 90px;
flex-grow: 0;
flex-shrink: 0;
text-align: right;
}
.sui-cell-content {
position: relative;
height: 28px;
line-height: 28px;
flex-grow: 1;
text-align: left;
flex: 1;
}
.sui-box-a {
box-sizing: border-box !important;
width: 100%;
height: 28px !important;
border: 4px;
background: #fff !important;
border-color: #d9d9d9 !important;
border: 1px solid #d9d9d9 !important;
position: relative;
}
.sui-box-b {
width: 100%;
height: 100%;
}
.sui-box-c {
width: 70% !important;
height: 26px;
line-height: 26px;
padding: 0 10px !important;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
</style>
</head>
<body>
<div class="box-item">
<div class="sui-cell">
<div class="sui-cell-left">
标题:
</div>
<div class="sui-cell-content">
<div class="sui-box-a">
<div class="sui-box-b">
<div class="sui-box-c">
效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团
</div>
</div>
</div>
</div>
</div>
</div>
</body>
</html>
结果如下图所示:
果然是个bug。应该是弹性盒子的特性导致。
分析了下,应该用定位来解决。问题出在sui-cell-content, sui-box-a这两标签。sui-cell-content标签是弹性的,根据左右两个标签来分配剩下的空间。也会根据子盒子的宽度自动撑开。故我们用定位的分析来解决安。sui-cell-content设置为相对定位,sui-box-a设置为绝对定位,这样就能保持子盒子最大只能得到父盒子的百分百,而不会把父盒子也撑开超出设定的宽度范围。
我们来修改下代码,如下:
<html>
<head>
<meta charset="UTF-8">
<title>test</title>
<style>
.box-item {
width: 400px;
height: 50px;
margin: 100px;
background: #999;
}
.sui-cell {
display: flex;
flex-direction: row;
width: 100%;
}
.sui-cell-left {
width: 90px;
flex-grow: 0;
flex-shrink: 0;
text-align: right;
}
.sui-cell-content {
position: relative;/*注意这里 !*/
height: 28px;
line-height: 28px;
flex-grow: 1;
text-align: left;
flex: 1;
}
.sui-box-a {
box-sizing: border-box !important;
width: 100%;
height: 28px !important;
border: 4px;
background: #fff !important;
border-color: #d9d9d9 !important;
border: 1px solid #d9d9d9 !important;
position: absolute;/*注意这里 !*/
}
.sui-box-b {
width: 100%;
height: 100%;
}
.sui-box-c {
width: 70% !important;
height: 26px;
line-height: 26px;
padding: 0 10px !important;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
</style>
</head>
<body>
<div class="box-item">
<div class="sui-cell">
<div class="sui-cell-left">
标题:
</div>
<div class="sui-cell-content">
<div class="sui-box-a">
<div class="sui-box-b">
<div class="sui-box-c">
效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团效热对前从社每水今道六验法非则走争三百团
</div>
</div>
</div>
</div>
</div>
</div>
</body>
</html>
这样结果就是我们想要的了,如下图:
解决问题,准备收工下班吃饭。
position: relative;