如何计算给定 div 相对于其父级 div 的填充顶部百分比

How to calculate padding-top in % of the given div relative to its parent div

问题:我想在所有列表项中添加 padding-top in %(因为我需要将文本向下移动一点,还需要所有元素都可以缩放) , here is jsfiddle code

高度正常。为了计算高度,我计算了 li 高度(原来是 40px)相对于它的父 ul(原来是 400px)的百分比。 400 像素中的 40 像素 = 10%。在总 ul 高度仍然等于 400px 之后,它似乎工作正常。 (盒子的高度为 53.33vw,因为 400px 是 750px 的 53.33%)。

但问题是计算 padding-top in %. 为了计算 padding-top(8px)我需要计算 400px 中的 8px(400px 是父级 ul 的高度 = 2%,在固定布局中,我从高度中减去那 2%(10%,所以高度现在是 8%)。但在那之后,总的 ul 高度等于 470px。如何以 % 计算 padding-top 以便 ul 的高度仍然是 400px?我需要保留 ul 的原始高度的 400px,在添加 padding-top in % 后,ul 的高度变为 470px,这是不正确的。

HTML:

<div class="box">
<ul class="list">
<li>Item 1</li>
<li>Item 2</li>
<li>Item 3</li>
<li>Item 4</li>
<li>Item 5</li>
<li>Item 6</li>
<li>Item 7</li>
<li>Item 8</li>
<li>Item 9</li>
<li>Item 10</li>
</ul>
</div>

CSS:

body {
    line-height: 1;
}

/* THIS IS MY CODE*/

.box {
    margin:0 auto;
    width:100%;
    max-width:750px;
    height:53.33vw;
    max-height:400px;
}

ul.list {
    padding: 0;
    width:100%;
    height:100%;
    background:green;
    list-style-type:none;
    text-align:center;
    font-size:3vw;
}

ul li:nth-child(odd) {
    height:8%;
    width:interit;
    padding-top:2%;
    background:grey;
}

ul li:nth-child(even) {
    height:8%;
    width:interit;
    padding-top:2%;
    background:red;
}

这是因为 % 中的 paddingmargin 是根据 width 计算的,而不是您希望的 height

来自spec for padding

Unlike margin properties, values for padding values cannot be negative. Like margin properties, percentage values for padding properties refer to the width of the generated box's containing block.

并且来自 spec for margin

The percentage is calculated with respect to the width of the generated box's containing block. Note that this is true for 'margin-top' and 'margin-bottom' as well. If the containing block's width depends on this element, then the resulting layout is undefined in CSS 2.1. This is also how you can create aspect-ratio locked divs in HTML since you can calculate height from width using padding-top with a percentage value.

您的解决方案是使用 CSS calc, it has good browser support 并以非常简单的方式解决您的问题。这里唯一的缺点是它不计算 % 中的 padding-top 但你根本无法从元素的 height 中计算 % 中的 padding-top 除非你使用 javascript.

如果您不是绝对需要 padding-top: 2%; 我会建议以下解决方案。

你的 CSS 看起来像这样

ul.list li {
    height: calc(10% - 8px);
    padding-top: 8px;
}

这会给所有 ul.list li 项目一个 10% - 8px 的高度,然后 8px 也被用作 padding-top 的值,这基本上会成为一个完美的 10% 再次.

你也可以用不同的风格来写你的select,我在这里使用ul.list li作为主要select或者只是select全部li 元素,但你有 :nth-child(odd):nth-child(even) select 或

您在这些 selector 上写了重复的属性,而唯一的区别是它们的 background 属性.

我强烈建议尽可能避免重复,因为有时您肯定会忘记更改 both 属性,而是将 CSS 更改为这样的内容:

/*shared properties in a general selector*/
ul.list li {
    width: inherit;
    height: calc(10% - 8px);
    padding-top: 8px;
    background: grey;
}

/*if rule is not applied, use ul.list instead of just ul*/
ul li:nth-child(even) {
    background: red;
}

这甚至消除了对 ul li:nth-child(odd) 的需要,因为这也可以成为共享样式的一部分,然后被更具体的 ul li:nth-child(even) 覆盖 select或.

另一种方式

另一种不依赖 % 值的方法是使用 emrem 值 - 它们通过基于字体大小缩放来工作。

多读书

基本上,rem 总是 相对于 root element<html> 元素。

<html> 元素上设置 font-size 将在 CSS 中定义 1rem 的值,如果没有设置 font-size 则浏览器默认(通常会使用16px)。

html {
    font-size: 16px; /*1rem is now 16px*/
}

当您像上面那样用值 16px 定义 font-size 时,0.5rem 将等于 8px - 为什么这很有趣?它是可扩展的!但是通过不同的方式。

当您现在应用媒体查询并将 font-size 更改为更大或更小的值时,使用 rem 的所有内容都将按比例缩放(您必须设置 font-size <html> 当然是元素。)

现在 em 有点不同,它是相对于它自己的 font-size 但是因为这个 get 是从它的 父元素 自动继承的(如果 font-size 设置在 em% 中)它基本上是相对于父级的。

如果我们以最后一个 CSS 为例

html {
    font-size: 16px; /* 1rem = 16px, 1em = 16px */
}

body > div { /*every direct div of body tag*/
    font-size: 0.5em; /*8px*/
    font-size: 0.5rem; /*8px*/
}

body > div > div { /*every second level nested div*/
    font-size: 0.5em; /*4px*/
    font-size: 0.5rem; /*8px*/
}

基本上,由于 em 相对于其父级大小 sort-of font-size 在 em 中缩放时会减少更多 - 这有潜在的危险,因为如果您更改您的结构并添加一个容器,在大部分页面上稍微减少 font-size 这可能会产生比您想象的更大的效果。

除此之外,技术上 emrem 是根据 [=49= 在元素上缩放 paddingmargin 的最佳方式] 属性.

您的容器示例如下所示:

ul.list li {
    height: 8%;
    padding-top: 0.5rem; /*if font-size is 16px, this will be 8px*/
}

就可扩展性而言,当您将 font-size 更改为移动设备上的其他内容时,这将起作用。

它没有为您的问题提供解决方案,但它确实提供了一个答案和您在谈论可伸缩性时的最佳选择,我希望这能帮助您实现这一目标:)

CSS box-sizing: border-box; 属性 将使宽度最大,其他所有内容都向内计算。

在狭窄区域

width:100%;结合使用效果好

了解更多:https://www.w3schools.com/cssref/css3_pr_box-sizing.asp