4

What I am going for

What I am trying to achieve

I have an image, that needs to appear inside a polygon. The hot pink area is the image.

What I have tried

Using SVG triangle shapes (100% wide) that are laid on top and bottom of the image. Top-left triangle on top and bottom-left at the bottom.

It works great but there seems to be rendering issues on many browsers where you see a random line around the SVG. (see image below, could be a separate question by itself)

enter image description here

I have also tried using skewed/rotated elements on top and bottom. But since the element is responsive, on certain resolution, the skewed elements create gaps. (see image below)

enter image description here

What I could try

Using images. Many problems there. It would be my last resort. Images are not resolution independent, I would have to use huge images for the slants to look good on high dpi screens, which would have to be scaled down in browsers, all not good.

Where I need help

Looking for any other way I could achieve this effect, preferably CSS based solution.

Roman Pokrovskij
  • 9,449
  • 21
  • 87
  • 142
Prashant
  • 7,340
  • 2
  • 25
  • 24
  • I have seen SVG `clip-path` to be the best in most cases but if you want a CSS way then have a look at [this thread](http://stackoverflow.com/questions/5293736/css3-transform-skew). You would basically have to rotate the container with perspective. But then again reverse rotating the image is going to be troublesome. You could even try the CSS `clip-path` but that has very poor browser support. – Harry Jun 21 '15 at 11:46
  • Would something like [this fiddle](http://jsfiddle.net/boafz90s/2/) work? No transformations, no SVG, just borders. The CSS does depend on the dimensions of the image though; that is, you will need separate CSS for each image you use. – Mr Lister Jun 21 '15 at 12:47
  • @MrLister The image needs to be responsive, so I cannot use a known border width. I could use JS to update the border width on resize, but there are several such elements on the page which may cause resize to be janky. – Prashant Jun 21 '15 at 14:07

1 Answers1

2

SVG

I used the polygon shape i created your slanted image.
Using patterns i created a background image that can fill the shape.

Setting the fill to an URL with the pattern ID created the shape.

.slanted {
  width: 50vw;
  height: auto;
}

.shape {
  fill: url(#img1);
}
<svg class="slanted" viewbox="-1 -1 102 102" preserveAspectRatio="none">
  <defs>
    <pattern id="img1" patternUnits="userSpaceOnUse" width="100" height="100">
      <image xlink:href="http://lorempixel.com/g/400/200/" x="0" y="0" width="150" height="100" />
    </pattern>
  </defs>
  <polygon class="shape" points="0,20 100,0 100,100, 0,80" />
</svg>

CSS

Using 3D transform you can pretty easily get this shape.
The image will also be rotated.
The perspective sets how deep the 3d effect is going to be.
While setting transform: rotate() sets how much its going to rotate.

.container {
  margin-top: 50px;
  perspective: 600px;
  width: 300px;
  height: 200px;
}

.shape {
  transform: rotateY(-45deg);
  width: 100%;
  height: 100%;
  background: url(http://lorempixel.com/g/400/200/);
}
<div class="container">
  <div class="shape"></div>
</div>
Community
  • 1
  • 1
Persijn
  • 14,624
  • 3
  • 43
  • 72
  • I just was in the comments that it needs to be responsive that makes this **A LOT HARDER** to give a proper answer. – Persijn Jun 21 '15 at 22:58
  • Unfortunately, your SVG solution also has the same rendering issues that mine has. It seems like anti-aliasing issue. Setting the share-rendering attribute of the SVG to crispEdges removes the extra line. But, switches off anti-aliasing leading to jaggy diagonals. And, CSS solution is not responsive. Indeed, that makes things a lot harder. – Prashant Jun 22 '15 at 06:59
  • @Persijn idk why u said "*making it responsive is lot harder*". just add 100% width and height to make it responsive to width of viewport! : https://jsfiddle.net/6bkygxbp/ – Max Payne Jun 22 '15 at 11:34
  • @TimKrul because responsive would be scaling after the image size not the view port. – Persijn Jun 22 '15 at 11:41
  • @TimKrul there added responsive to viewport on the svg. Where did the javascript come from? – Persijn Jun 22 '15 at 11:57
  • @Persijn I think u need to use *same units on height and width in order to preserve the aspect ratio of image*. – Max Payne Jun 23 '15 at 01:50
  • @TimKrul i love this tango, so I added height auto to a responsive width. Any thing more? Need a responsive CSS solution? Maybe a [back rub](http://images.sodahead.com/polls/001814901/4711886068_pupkitonback_answer_1_xlarge.jpeg)? – Persijn Jun 23 '15 at 07:09
  • it doesn't work (running the snippet here on the page) – Nir O. Jan 21 '19 at 09:06
  • the snippets work now, the broken image url rework. The snippets are just an example, the answer is the important part. – Persijn Jan 21 '19 at 11:00