Seabon
Seabon

Reputation: 241

How to make svg image fits to parent container

I am using for the first time the svg <image> tag. I use this tag in order to apply a gray filter on the picture (thank you IE).

Here is my HTML :

<div class="container">
  <div class="item">
    <svg version="1.1" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns="http://www.w3.org/2000/svg">
        <image  xlink:href="https://dummyimage.com/400x400/000/00ffd5.png" />
    </svg>
  </div>
</div> 

And the scss :

.item {
  position: relative;
  width: 20%;
  height: 220px;

  background-color: blue;
}

svg {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;

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

I want to fit the image to the parent's container. Something like background: cover in css. Does anybody have an idea ?

You can check it out at : https://codepen.io/seabon/pen/QvBBrd

enter image description here

The blue background is for div.item

Upvotes: 10

Views: 24148

Answers (4)

AndersD
AndersD

Reputation: 126

Struggled with the same. The image sourcegraphic might not be your best option.

If you want cover fit try using a background image as you normally would and apply a filter to the element by referencing an SVG filter.

Example

.bg_img {
    -webkit-filter: url(#distort_slider_filter);
    filter: url(#distort_slider_filter);
}

Demo: https://codepen.io/Andersdn11/pen/QXWmgr

Upvotes: 0

Paul LeBeau
Paul LeBeau

Reputation: 101800

Just set an appropriate viewBox attribute on your SVG. Then set preserveAspectRatio to a value that uses the slice option, instead of the default meet. For example:

preserveAspectRatio="xMidYMid slice"

This is equivalent to CSS's background-size: cover.

BTW, setting width and height of the <image> via CSS will only work on Chrome right now. You'll need to assign those in the SVG if you want your example to work in other browsers.

.item {
  position: relative;
  width: 20%;
  height: 220px;

  background-color: blue;
}

svg {
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
}
<div class="container">
  <div class="item">
    <svg viewBox="0 0 400 400" preserveAspectRatio="xMidYMid slice">
        <image xlink:href="https://dummyimage.com/400x400/000/00ffd5.png"
               width="400" height="400"/>
    </svg>
  </div>
</div>

Upvotes: 4

Piotr Bryla
Piotr Bryla

Reputation: 41

If you don't have to use image tab there is my solution with CSS:

.item-image{
 width:100%;
 height:100%;
 background: url(https://dummyimage.com/400x400/000/00ffd5.png) center;
background-size: 100% 100% ;
}

- don't forget create div with the item-image class, between svg tags.

Codepen

There is a website where you can play with background-size. You can change the background of each element by assigning an id to div and add an attribute with JS.

Upvotes: 1

Mi-Creativity
Mi-Creativity

Reputation: 9654

UPDATED

  • Add width="100%" and height="100%" attributes.
  • Add preserveAspectRatio 1 with value of none2 .

    none do not force uniform scaling. Scale the graphic content of the given element non-uniformly if necessary such that the element's bounding box exactly matches the viewport rectangle.
    Note: if <align> is none, then the optional <meetOrSlice> value is ignored.

jsFiddle - tested on Chrome, FF and IE11

.item { position: relative; width: 20%; height: 220px; background-color: blue; }
svg { position: absolute; top: 0; left: 0; width: 100%; height: 100%; }
<div class="item">
  <svg id="theSVG" version="1.1" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns="http://www.w3.org/2000/svg">
      <image width="100%" height="100%" xlink:href="//dummyimage.com/400x400/000/00ffd5.png" preserveAspectRatio="none" />
    </svg>
</div>


Notes:

  1. The use of this preserveAspectRatio attribute was initially offered by another answer - I forgot the user, many thanks to him though- and it got deleted, in that answer the attribute was preserveAspectRatio="xMidYMid slice" but without using the width="100%" height="100%", except the ones in CSS which don't work except [partially, because if you resize the view larger the blue background will start to show up] in Chrome as stated in @Paul LeBeau answer. this jsFiddle Demo represents how that nice answer was.
  2. none does not force the scale to be uniformed, it may squish or stretch the image to make it fits, While it doesn't make any difference in the OP case, if Keeping aspect ratio is needed, then any of the other Min, Mid and Max for x or y could be used but it must be accompanied with slice only and not meet.

Upvotes: 13

Related Questions