Cách tự động cắt và căn giữa hình ảnh


158

Cho bất kỳ hình ảnh tùy ý, tôi muốn cắt một hình vuông từ trung tâm của hình ảnh và hiển thị nó trong một hình vuông nhất định.

Câu hỏi này tương tự như sau: CSS Hiển thị kích thước và cắt xén hình ảnh , nhưng tôi không biết kích thước của hình ảnh nên tôi không thể sử dụng lề thiết lập.


1
Phần tử phải là thẻ hình ảnh, hay nó có thể là div với thuộc tính hình ảnh nền?
Russ Ferri

miễn là tôi có thể thiết lập hình ảnh thông qua hệ thống tạo khuôn mẫu của mình, điều đó không thành vấn đề. loại xấu xí, nhưng tôi đoán phong cách nội tuyến sẽ làm việc.
Jonathan Ong

Câu trả lời:


318

Một giải pháp là sử dụng hình ảnh nền được căn giữa trong một phần tử có kích thước theo kích thước được cắt.


Ví dụ cơ bản

.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>


Ví dụ với imgthẻ

Phiên bản này giữ lại imgthẻ để chúng tôi không mất khả năng kéo hoặc nhấp chuột phải để lưu hình ảnh. Tín dụng cho Parker Bennett cho thủ thuật opacity.

.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

Xem các trình duyệt được hỗ trợ .

Đặc tả hình ảnh CSS3 xác định các thuộc tính object-fitobject-positioncác thuộc tính cùng nhau cho phép kiểm soát tốt hơn tỷ lệ và vị trí của nội dung hình ảnh của một thành imgphần. Với những điều này, sẽ có thể đạt được hiệu quả mong muốn:

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


45
Bạn có thể sử dụng background-size: cover;để có được hình ảnh thu nhỏ hoặc điền vào div một cách thích hợp trong khi duy trì tỷ lệ khung hình gốc.
Nick

7
Khi sử dụng hình nền, bạn nên thêm kích thước nền: che để kích thước chính xác hình ảnh được cắt: Xem jsfiddle.net/bw6ct
Kris Erickson

2
Tôi đã được thông báo rằng ngày nay Google biết về hình ảnh trong suốt và ẩn, do đó img, thuộc tính altant titlesẽ bị mất cho SEO của bạn.
Victor Sergienko

6
trong webkit, bạn cũng có thể sử dụng object-fit: cover;trực tiếp trên thẻ img, cảm giác có ngữ nghĩa hơn một chút.
Ben

2
Tôi đã sử dụng đối tượng phù hợp: che để đạt được hiệu quả mong muốn của mình là không làm mất tỷ lệ khung hình, che ô vuông và cắt xén nếu cần
Daniel Handojo

79

Tôi đang tìm kiếm một giải pháp CSS thuần túy bằng cách sử dụng imgcác thẻ (không phải cách hình ảnh nền).

Tôi tìm thấy cách tuyệt vời này để đạt được mục tiêu trên hình thu nhỏ với 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;
}

Nó tương tự như câu trả lời của @Nathan Redblur nhưng nó cũng cho phép hình ảnh chân dung.

Hoạt động như một cơ duyên đối với tôi. Điều duy nhất bạn cần biết về hình ảnh là nó là dọc hay ngang để đặt .portraitlớp nên tôi phải sử dụng một chút Javascript cho phần này.


3
Chỉ cần lưu ý rằng các biến đổi CSS chỉ có sẵn trong IE 9 trở lên.
Simon East

5
Đây nên là câu trả lời.
Wes Modes

OP đã nói "hình ảnh tùy ý" vì vậy sẽ không biết trước nếu hình ảnh cao hơn chiều rộng.
opyate

11
Nếu bạn đặt min-height: 100%; min-width: 100%; thay vì chiều cao: 100%; chiều rộng: tự động; bạn không cần lớp img.portabout.
dùng570605

1
giải pháp tốt nhất kết hợp với đề xuất @ user570605
albanx 7/2/2017

45

Hãy thử điều này: Đặt kích thước cắt ảnh của bạn và sử dụng dòng này trong CSS của bạn:

object-fit: cover;

3
không được hỗ trợ tốt: caniuse.com/#feat=object-fit EDIT: thực tế, như thường lệ, chỉ cần các trình duyệt MS thất bại ... điều này thể hiện khá nhiều việc sử dụng mặc dù: /
Brian H.

1
Điều này thực hiện chính xác những gì tôi cần :)
hcarrera 16/2/2017

1
Các trình duyệt được sử dụng rộng rãi không hỗ trợ này là Internet Explorer 11 và Edge. Tùy thuộc vào đối tượng của bạn, hỗ trợ ngay bây giờ có thể là khoảng 85-90%, điều này có thể giúp điều này khả thi đối với một số tình huống.
Husky

nhà vua! giải pháp tuyệt vời !!
itzhar

1
hướng dẫn tốt về điều đó: Medium.com/@chrisnager/ Kẻ
Pietro La Grotta

23

Ví dụ với imgthẻ nhưng không cóbackground-image

Giải pháp này giữ lại imgthẻ để chúng tôi không mất khả năng kéo hoặc nhấp chuột phải để lưu hình ảnh mà không background-imagechỉ tập trung và cắt với css.

Duy trì tỷ lệ khung hình tốt ngoại trừ trong các hình ảnh rất cao. (kiểm tra liên kết)

(xem trong hành động)

Đánh dấu

<div class="center-cropped">
    <img src="http://placehold.it/200x150" alt="" />
</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%);
}

Hãy thử cái này ... nếu hình ảnh nhỏ hơn container, nó sẽ nằm ở giữa, nếu không nó sẽ cắt jsfiddle.net/3ts4rm24/1
KnF

8

Tôi đã tạo một lệnh angularjs bằng cách sử dụng câu trả lời của @ Russ và @ Alex

Có thể thú vị trong năm 2014 và hơn thế nữa: P

html

<div ng-app="croppy">
  <cropped-image src="http://placehold.it/200x200" width="100" height="100"></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 + "')");
          }
      }
  });

liên kết fiddle


3
Hiya downvoters. Vui lòng để lại một bình luận để tôi có thể cập nhật câu trả lời của tôi nếu có lỗi. Tôi không thích đưa ra thông tin sai lệch. Chúc mừng.
mraaroncruz

Không phải là một downvoter, nhưng đây không phải là một câu hỏi Angular và câu trả lời của bạn là không liên quan. @pferdefleisch
mawburn

1
@mburn mà có ý nghĩa. Đã được 3 năm và điều này có lẽ trông hơi lạc lõng hoặc đáng ghét bây giờ. Mặc dù vậy, tôi sẽ để nó lên vì các upvote trên bình luận của tôi cho tôi biết ít nhất một vài người có thể thấy nó hữu ích (hoặc họ chỉ không thích downvote mà không có bình luận).
mraaroncruz

2

Thử cái này:

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

Hãy ghi nhớ rằng widthheightsẽ chỉ hoạt động nếu phần tử DOM của bạn có bố cục (một phần tử được hiển thị khối, như một divhoặc một img). Nếu nó không (ví dụ như một nhịp), hãy thêm display: block;vào các quy tắc CSS. Nếu bạn không có quyền truy cập vào các tệp CSS, hãy bỏ kiểu nội tuyến trong thành phần.


trong hầu hết các trường hợp, CSS này được sử dụng nhiều lần với các hình ảnh khác nhau. do đó, không thể tránh khỏi việc đặt nội tuyến ảnh nền.
Raptor

0

Có một cách khác bạn có thể cắt hình ảnh làm trung tâm:

.thumbnail{position: 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.vertical{width: 100% !important; height: auto !important;}

Điều duy nhất bạn cần là thêm lớp "dọc" vào hình ảnh dọc, bạn có thể làm điều đó với mã này:

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();
    });
});

Lưu ý: "! Quan trọng" được sử dụng để ghi đè các thuộc tính chiều rộng, chiều cao có thể có trên thẻ img.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.