css 对象拟合的图像圆角问题:包含

p3rjfoxz  于 2023-05-02  发布在  其他
关注(0)|答案(4)|浏览(197)

我想显示一个带有圆角的图像。因此,图像必须拉伸到容器,但不裁剪任何部分,如object-fit: contain。然而,border-radius适用于图像元素,而不是图片内容。下面是一个例子(也是JSFiddle):

body {
  width: 100vw;
  height: 100vh;
  margin: 0;
}

div {
  width: 100%;
  height: 100%;
}

img {
  width: 100%;
  height: 100%;
  object-fit: contain;
  border-radius: 20%;
}
<div>
  <img src="https://cdn.pixabay.com/photo/2015/04/23/22/00/tree-736885__480.jpg">
</div>

可以在调整视口大小时检查其工作方式。
那么,有没有一种方法可以让图像元素调整它的边界在两个方向以适应容器,就像object-fit一样?
或者是一种在图像内容上应用“crop-by-rounded-rect过滤器”的方法?

hmmo2u0o

hmmo2u0o1#

我也遇到过这个问题,我找到了解决的办法。如果将高度和宽度设置为自动,img元素将保持其纵横比,图像将接触边框。然后可以使用max-width和max-height来代替width和height。

img {
  width: auto;
  height: auto;
  max-width: 100%;
  max-height: 100%;
  object-fit: contain;
  border-radius: 20%;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
}

你可能还需要将img放在父div的中心,因为如果它小于最大尺寸,它将移动到左上角。

vhmi4jdf

vhmi4jdf2#

经过一些研究,这似乎在纯CSS中是不可能的。答案here也证实了这一点。
在这个问题的other answer中,图像视图没有增长到“接触”父容器,因此在它周围留下空白区域 * 在所有4个方向 *,并在容器中心的某个地方保持小。这意味着它的行为方式与问题中的代码不同,其中img元素占据整个父区域,然后图片内容“拉伸”以接触object-fit: contain的最近边界。

kb5ga3dv

kb5ga3dv3#

Here是一个解决方案,当容器较小时,它将适合图像:

div {
  display: flex;
  align-items: center;
  justify-content: center;
}

img {
  border-radius: 16px;
  max-width: 100%;
  max-height: 100%;
}

如果容器比图像大,它只会将其居中。请注意,您可能不想在这一点上拉伸图像,否则它会看起来很糟糕

hujrc8aj

hujrc8aj4#

虽然这似乎是不可能的,但SVG过滤器可能能够完成这项工作,例如:

/* Wrapper is optional, it is just to illustrate the container size */
.wrap {
  background-color: #eee;
  width: 100px;
  height: 100px;
}

.bg {
  background-image: url(https://placekitten.com/1000/400);
  background-size: contain;
  background-repeat: no-repeat;
  background-position: center;
  width: 100px;
  height: 100px;
  filter: url('#filter-radius');
}

.img {
  object-fit: contain;
  width: 100px;
  height: 100px;
  filter: url('#filter-radius');
}
<div class="wrap"><div class="bg"></div></div>
<hr />
<div class="wrap">
  <img class="img" src="https://placekitten.com/1000/400" />
</div>

<!-- Magic for border radius -->
<svg style="visibility: hidden" width="0" height="0">
  <defs>
    <filter id="filter-radius">
      <!-- Create a blur of 4px radius from the original image -->
      <!-- (Transparent pixels are ignored, thus the blur radius starts at the corner of the image) -->
      <feGaussianBlur in="SourceGraphic" stdDeviation="4" result="blur" />
      <!-- Filter out the pixels where alpha values that are too low, in this case the blurred corners are filtered out -->
      <feColorMatrix
        in="blur"
        mode="matrix"
        values="1 0 0 0 0  0 1 0 0 0  0 0 1 0 0  0 0 0 100 -50"
        result="mask"
      />
      <!-- As the final result is now blurred, we need to use the mask we obtained from previous step to cut from the original source -->
      <feComposite in="SourceGraphic" in2="mask" operator="atop" />
    </filter>
  </defs>
</svg>

相关问题