javascript - Div 扩展到特定内容的大小

标签 javascript jquery html css

我有一堆 div,里面有一个内容 div。在内容 div 中有 3 个元素,一个 h1 , 一个 p和一个 span , 全部左对齐。我想要发生的事情如下:

  • 内容 div 应垂直和水平居中
  • 内容 div 应该与 h1 中的 text 一样宽或 span 中的文本 (以较长者为准),如果高于 max-width这些应该包起来
  • p应该是内容 div 的 75%,但不会影响内容 div 的大小(实际上是 h1span 的 75%,以较长者为准)

但是我遇到了以下问题:

  • 问题 1:有一个很长的 p元素导致内容 div 扩展到其 max-width无论 h1 的大小如何或 span .我试过使用绝对定位来解决这个问题,但它会破坏 div 的垂直居中
  • 问题 2:有很长的 h1元素在单词超过 2 行的地方留下一个空隙,使内容 div 不显示在中心

请参阅下面的代码片段以阐明我在做什么以及出了什么问题,边框只是为了帮助可视化正在发生的事情。

有没有人知道这是怎么可能的?我想坚持使用 CSS,因为它们需要响应,但如果有一个简单的 JS/jQuery 解决方案,我会考虑。

编辑:为了阐明我想要的视觉效果,这里简要说明了这些示例的好坏原因。我还添加了删除边框的功能,以展示我所说的视觉居中的意思:

1) 好:内容 div 适合 h1 的宽度, 看起来没有边框居中,因为 h1 左右的空间相等

2) 好:内容 div 适合 span 的宽度因为它比 h1 长, 看起来没有边框居中,因为 span 左右的空间相等

问题 1:

3) 错误:p正在扩大内容 div 的宽度,看起来没有边框向左移动,因为右边的空间比左边多。如果p没有扩展 div 并保持在宽度的 75% 这不会发生

4) 改进了 3 但仍然很糟糕:在各种 SO 问题中发现的潜在修复显示绝对定位停止了 p扩展内容 div,但现在它不是流的一部分,它打乱了垂直居中

问题 2:

5) 不好:这里的问题是 h1元素,因为它现在比 max-width 长它分为两行。但是第一行末尾和 max-width 之间的额外空间的 div 被保留,所以当删除边框时它看起来不居中,因为 h1 右边的空间比左边多

6) 修复 5 但不是解决方案:手动断开线(使用 <br> )实现我需要的外观,因为 h1未扩展到 max-width所以看起来没有边界居中。这在实际应用中是不可行的,因为 div 的宽度可能不同

Alternative JSFiddle Link

function toggleBorders() {
  $('h1, p, span').toggleClass('bordered');
  $('.content').toggleClass('content-bordered');
}
.box-holder {
  display: flex;
  flex-flow: row wrap;
}
.box {
  flex: 0 0 380px;
  display: flex;
  align-items: center;
  justify-content: center;
  height: 350px;
  border: 1px solid blue;
}
.content {
  max-width: 80%;
  position: relative;
}
.content-bordered {
  border: 1px solid red;
}
.bordered {
  border: 1px solid green;
}
p {
  width: 75%;
}
.abs {
  position: absolute;
}
button {
  position: fixed;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button onclick="toggleBorders()">Toggle Borders</button>
<div class="box-holder">
  <div class="box">
    <div class="content">
      <h1>1. Example Title</h1>
      <p>Good Example</p>
      <span>Example link to the article</span>
    </div>
  </div>
  <div class="box">
    <div class="content">
      <h1>2. Title</h1>
      <p>Min Width Good Example</p>
      <span>Example link to the article</span>
    </div>
  </div>
  <div class="box">
    <div class="content">
      <h1>3. Example Title</h1>
      <p>But when the description gets too long then it expands the content div</p>
      <span>Example link to the article</span>
    </div>
  </div>
   <div class="box">
    <div class="content">
      <h1>4. Example Title</h1>
      <p class="abs">Setting absolute position avoids expansion but messes up the vertical layout</p>
      <span class="abs">Example link to the article</span>
    </div>
  </div>
   <div class="box">
    <div class="content">
      <h1>5. Also Long Titles Leave White Space</h1>
      <p>This doesn't look centered, see 6</p>
      <span>Example link to the article</span>
    </div>
  </div>
   <div class="box">
    <div class="content">
      <h1>6. Also Long Titles<br>Leave White Space</h1>
      <p>Manually breaking lines fixes this</p>
      <span>Example link to the article</span>
    </div>
  </div>
</div>

最佳答案

因此,这两个问题的答案似乎是,如果没有 javascript,您不能做到这一点。原因是 CSS 盒模型不能以这种方式工作。

为了解决第一个问题,您需要像我尝试的那样使用绝对定位,然后使用 javascript 在 h1 上使用边距为元素创建空间,如下所示:

$(document).ready(function() {
    function alignDescriptions() {
    var pmargin = 10 * 2;
    $('.abs').each(function() {
      var pheight = $(this).height();
      $(this).css('bottom', pmargin);
      $(this).siblings('h1').css('margin-bottom', pheight + pmargin);
    });
  }
});

这解决了使用 absolute 时的垂直居中问题,因此问题 1 已解决。

为了解决第二个问题,以下答案提供了一种解决方案:https://stackoverflow.com/a/33246364/7542390

我相信简单地使用它但也使用 span 的宽度作为最小值可能会解决这两个问题,因为我实际上是将宽度强制为正确的大小,因此宽度为 75% p 元素不会有问题。

遗憾的是这种功能不在 CSS 规范中。

编辑:正如所怀疑的那样,对第二个选项的改编实际上消除了对 p 元素进行绝对定位的需要。这是适用于我的实际案例的 jQuery 代码:

$('h1').each(function() {
  // references to elements
  var hElem = $(this);
  var pElem = hElem.siblings('p');
  var sElem = hElem.siblings('span');
  // store starting values
  var sWidth = sElem.width();
  var hHeight = hElem.height();
  var hWidth = hElem.width();
  // reduce width until less than span width
  // or until height of h1 changes
  for (var testWidth = hWidth - 1; testWidth > 0; testWidth--) {
    if (testWidth <= sWidth) {
      testWidth = sWidth - 1;
      break;
    }
    hElem.width(testWidth);
    if (hElem.height() !== hHeight) break;
  }
  // set h1 width
  hElem.width(++testWidth);
  // if h1 still overflows (long word) use that instead
  if (hElem[0].scrollWidth > hElem.width()) {
    testWidth = hElem[0].scrollWidth;
    hElem.width(testWidth);
  }
  // set p element to 75% width
  pElem.width(testWidth * 0.75);
});

关于javascript - Div 扩展到特定内容的大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43823133/

相关文章:

javascript - 如何在javascript中获取嵌套数组中值的indexOf位置?

javascript - iggrid 添加新行事件

jquery - Orbit jQuery 插件 : How to fade in directional navigation arrows?

javascript - 为什么在 ion-input 未显示后将任何内容(div、p 或只是文本)放入 ion-item 中?

javascript - Materialize css select 无法正常工作

javascript - 获取 WkWebView 鼠标中键操作

javascript - 打印时不在弹出窗口中显示打印 View

javascript - 在 Rails 上的 Ruby 方法中使用 JSON 输入

html - 网站中的粘性页脚在一个页面而不是另一个页面上工作

javascript - 如何操作数组中的字符串