0

My goal is to cut out a rectangular area of a photo using an svg mask in html5. I have attempted to implement this using the code below and in this fiddle, to no avail. Can anyone tell me what I'm doing wrong?

html:

<body>
<svg id="svg-rect" width="50px" height="50px">

    <defs>

    <mask id="masking" maskUnits="objectBoundingBox" maskContentUnits="objectBoundingBox">
      <rect width="100%" height="100%"  />
    </mask>
  </defs>
</svg>

<!--<svg id="svg-rect" width="50px" height="50px">
  <rect  width="100%" height="100%"  />
</svg>-->

<img src="https://scontent-a.xx.fbcdn.net/hphotos-prn1/t1.0-9/p235x165/75938_10152243783285987_398136218_n.jpg"/>
</body>

css:

img {
  mask: url(#masking);
  position:absolute;
    top:0px;
    left:0px;
}

#svg-rect{
    position:absolute;
    top:50px;
    left:60px;
    z-index:2;
}
Ben Pearce
  • 6,884
  • 18
  • 70
  • 127

2 Answers2

2

Applying SVG effects to HTML only works in Firefox. You have to use -webkit-mask in Chrome/Safari and that's been deprecated. Next, you have to fill your rectangle with a color for the mask to take effect. And there is a bug in firefox, where you have to specify the x/y offset for a rect in a mask in decimal form, %'s won't work. Change your rect definition to:

  <rect x=".2" y=".2" width=".25" height=".25" fill="white"  />

And you'll see a mask effect (in Firefox only)

or... to invert the mask, use an empty fill and a solid stroke

  <rect x="0" y="0" width="1" height="1" stroke="white" stroke-width=".4"  />

The best way to do this for maximum compatibility, however, is to use inline SVG all the way, and just do your image content in SVG using the SVG image tag.

Michael Mullany
  • 30,283
  • 6
  • 81
  • 105
  • Thanks Michael. When I implemented this code it cut out the photo surrounding the rectangle. My intent was to cut out the area of the rectangle. Is there an easy way to invert this? – Ben Pearce Mar 18 '14 at 02:50
  • yup - added the solution to the answer – Michael Mullany Mar 18 '14 at 03:09
  • Wow that's great, you saved my day. Would you be willing to elaborate on your last comment about the best way to do it? I could really use that piece of information and I think it will enhance the answer. – Ben Pearce Mar 18 '14 at 05:50
0

Elaborating on Michaels' last point, here's how you would do it in a pure SVG way.

<svg width="235" height="314" xmlns:xlink="http://www.w3.org/1999/xlink">
    <defs>
        <mask id="masking">
            <rect width="100%" height="100%" fill="white" />
            <rect x="60px" y="50px" width="50px" height="50px" fill="black" />
        </mask>
    </defs>

    <image width="235" height="314"
           mask="url(#masking)"
           xlink:href="https://scontent-a.xx.fbcdn.net/hphotos-prn1/t1.0-9/p235x165/75938_10152243783285987_398136218_n.jpg" />
</svg>

Fiddle here

Paul LeBeau
  • 97,474
  • 9
  • 154
  • 181