如何自动裁剪和居中图像

Posted

技术标签:

【中文标题】如何自动裁剪和居中图像【英文标题】:How to automatically crop and center an image 【发布时间】:2012-07-18 03:19:06 【问题描述】:

给定任意图像,我想从图像的中心裁剪一个正方形并将其显示在给定的正方形内。

这个问题类似于:CSS Display an Image Resized and Cropped,但我不知道图像的大小,所以我不能使用设置边距。

【问题讨论】:

元素必须是图片标签,还是可以是带有背景图片属性的div? 只要我可以通过我的模板系统设置图像,没关系。有点难看,但我想内联样式会起作用。 【参考方案1】:

我一直在寻找使用img 标签(不是背景图像方式)的纯 CSS 解决方案。

我在crop thumbnails with css 上找到了实现目标的绝妙方法:

.thumbnail 
  position: relative;
  width: 200px;
  height: 200px;
  overflow: hidden;

.thumbnail img 
  position: absolute;
  left: 50%;
  top: 50%;
  height: 100%;
  width: auto;
  -webkit-transform: translate(-50%,-50%);
      -ms-transform: translate(-50%,-50%);
          transform: translate(-50%,-50%);

.thumbnail img.portrait 
  width: 100%;
  height: auto;

这类似于@Nathan Redblur 的回答,但它也允许纵向图像。

对我来说就像一个魅力。关于图像,您唯一需要知道的是它是纵向还是横向,以便设置 .portrait 类,所以我不得不在这部分使用一些 javascript

【讨论】:

请注意 CSS 转换仅在 IE 9 及更高版本中可用。 这应该是答案。 OP 说“任意图像”,所以如果图像的高度大于宽度,则不会预先知道。 如果你把 min-height:100%;min-width:100%;而不是高度:100%;宽度:自动;你不需要 img.portrait 类。 结合@user570605 建议的最佳解决方案【参考方案2】:

一种解决方案是使用以裁剪尺寸为大小的元素中居中的背景图像。


基本示例

.center-cropped 
  width: 100px;
  height: 100px;
  background-position: center center;
  background-repeat: no-repeat;
<div class="center-cropped" 
     style="background-image: url('http://placehold.it/200x200');">
</div>

img 标签示例

这个版本保留了img标签,这样我们就不会失去拖动或右键保存图像的能力。感谢 Parker Bennett 的不透明技巧。

.center-cropped 
  width: 100px;
  height: 100px;
  background-position: center center;
  background-repeat: no-repeat;
  overflow: hidden;


/* Set the image to fill its parent and make transparent */
.center-cropped img 
  min-height: 100%;
  min-width: 100%;
  /* IE 8 */
  -ms-filter: "progid:DXImageTransform.Microsoft.Alpha(Opacity=0)";
  /* IE 5-7 */
  filter: alpha(opacity=0);
  /* modern browsers */
  opacity: 0;
<div class="center-cropped" 
     style="background-image: url('http://placehold.it/200x200');">
  <img src="http://placehold.it/200x200" />
</div>

object-fit/-position

See supported browsers.

CSS3 Images specification 定义了object-fitobject-position 属性,它们共同允许更好地控制img 元素的图像内容的比例和位置。有了这些,就可以达到预期的效果:

.center-cropped 
  object-fit: none; /* Do not scale the image */
  object-position: center; /* Center the image within the element */
  height: 100px;
  width: 100px;
&lt;img class="center-cropped" src="http://placehold.it/200x200" /&gt;

【讨论】:

您可以使用background-size: cover; 使图像在保持原始纵横比的同时适当缩小或填充div。 使用 background-image 时,您应该添加 background-size:cover 以正确调整裁剪图像的大小:参见jsfiddle.net/bw6ct 有人告诉我,现在谷歌知道透明和隐藏图像,所以 imgalt ant title 属性将丢失您的 SEO。 在webkit中你也可以直接在img标签上使用object-fit: cover;,感觉更语义化。 我使用 object-fit:cover 来获得我想要的不丢失纵横比的效果,覆盖正方形,并在需要时进行裁剪【参考方案3】:

试试这个:设置您的图像裁剪尺寸并在您的 CSS 中使用此行:

object-fit: cover;

【讨论】:

不太支持:caniuse.com/#feat=object-fit 编辑:实际上,像往常一样,只是 MS 浏览器在这方面失败了......虽然它确实代表了相当多的使用:/ 这正是我需要的:) 唯一不支持此功能的广泛使用的浏览器是 Internet Explorer 11 和 Edge。根据您的受众,目前的支持率可能在 85-90% 左右,这在某些情况下可能是可行的。 国王!很棒的解决方案! 还有一个很好的教程:medium.com/@chrisnager/…【参考方案4】:

还有另一种方法可以使图像居中裁剪:

.thumbnailposition: relative; overflow: hidden; width: 320px; height: 640px;
.thumbnail img
    position: absolute; top: -999px; bottom: -999px; left: -999px; right: -999px;
    width: auto !important; height: 100% !important; margin: auto;

.thumbnail img.verticalwidth: 100% !important; height: auto !important;

您唯一需要的是将“垂直”类添加到垂直图像,您可以使用以下代码来完成:

jQuery(function($) 
    $('img').one('load', function () 
        var $img = $(this);
        var tempImage1 = new Image();
        tempImage1.src = $img.attr('src');
        tempImage1.onload = function() 
            var ratio = tempImage1.width / tempImage1.height;
            if(!isNaN(ratio) && ratio < 1) $img.addClass('vertical');
        
    ).each(function () 
        if (this.complete) $(this).load();
    );
);

注意:“!important”用于覆盖img标签上可能的宽度、高度属性。

【讨论】:

【参考方案5】:

带有img 标签但没有background-image 的示例

这个解决方案保留了img标签,这样我们就不会失去拖动或右键单击保存图像的能力,但没有background-image,只需居中并使用css裁剪。

保持宽高比正常,除非在非常高的图像中。 (查看链接)

(view in action)

标记

<div class="center-cropped">
    <img src="http://placehold.it/200x150"  />
</div>

CSS

div.center-cropped 
  width: 100px;
  height: 100px;
  overflow:hidden;

div.center-cropped img 
  height: 100%;
  min-width: 100%;
  left: 50%;
  position: relative;
  transform: translateX(-50%);

【讨论】:

试试这个...如果图像小于容器,它将居中,否则将裁剪jsfiddle.net/3ts4rm24/1 为什么将left: 50%transform: translateX(-50%) 一起使用? left是与容器相关的位置translate与元素相关如果你的容器是100px,而你的图片是20px,left会将图片放在50px之间的位置- 70像素。为了解决这个问题,我们将图片的大小设置为translateX(-50%),然后您的图片将在 40px-60px 之间。 Ej:如果你的容器是100px,left: 50%这个容器的rightMiddle = container/2 - element/2【参考方案6】:

我使用@Russ 和@Alex 的答案创建了一个 angularjs 指令

在 2014 年及以后可能会很有趣:P

html

<div ng-app="croppy">
  <cropped-image src="http://placehold.it/200x200"  ></cropped-image>
</div>

js

angular.module('croppy', [])
  .directive('croppedImage', function () 
      return 
          restrict: "E",
          replace: true,
          template: "<div class='center-cropped'></div>",
          link: function(scope, element, attrs) 
              var width = attrs.width;
              var height = attrs.height;
              element.css('width', width + "px");
              element.css('height', height + "px");
              element.css('backgroundPosition', 'center center');
              element.css('backgroundRepeat', 'no-repeat');
              element.css('backgroundImage', "url('" + attrs.src + "')");
          
      
  );

fiddle link

【讨论】:

嗨,反对者。请发表评论,以便如果有错误我可以更新我的答案。我不喜欢提供虚假信息。干杯。 不是反对者,但这不是 Angular 问题,您的回答无关紧要。 @pferdefleisch @mburn 说得通。已经 3 年了,现在这可能看起来有点不合适或令人讨厌。不过我会保留它,因为对我的评论的赞成票告诉我,至少有几个人可能会觉得它很有用(或者他们只是不喜欢没有 cmets 的反对票)。【参考方案7】:

试试这个:

#yourElementId

    background: url(yourImageLocation.jpg) no-repeat center center;
    width: 100px;
    height: 100px;

请记住,widthheight 仅在您的 DOM 元素具有布局(块显示元素,如 divimg)时才有效。如果不是(例如跨度),请将 display: block; 添加到 CSS 规则中。如果您无权访问 CSS 文件,请将样式内嵌到元素中。

【讨论】:

在大多数情况下,此 CSS 会重复用于不同的图像。因此,将背景图片设置为内联是不可避免的。

以上是关于如何自动裁剪和居中图像的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 CSS 裁剪和居中图像?

在浏览器中自动裁剪图像

如何使用 CSS 居中和裁剪图像以始终以方形显示?

如何在浮动操作按钮中将图像设置为居中裁剪

使用 CSS 居中和裁剪图像

scss 裁剪和居中的图像特色图像