SVG pattern tiled image - html

Hi I am really new to SVG's and creating assets using SVG's.
This is my first attempt and what I have is a rounded rectangle with a gif of water as the background. I was wondering how to modify this code in order to make it not have those gaps.
<svg id="water" width="440" height="440">
<defs>
<pattern id="img1" patternUnits="userSpaceOnUse" width="100" height="100">
<image xlink:href="https://i.imgur.com/u7ufQto.gif" x="0" y="0" width="100" height="100" />
</pattern>
</defs>
<path d="M100,100 h200 a20,20 0 0 1 20,20 v200 a20,20 0 0 1 -20,20 h-200 a20,20 0 0 1 -20,-20 v-200 a20,20 0 0 1 20,-20 z" fill="url(#img1)" stroke="black" stroke-width="3" />
</svg>

The problem is that your GIF is 251x132 pixels, but you are asking the SVG to draw the image at 100x100.
By default SVG won't squeeze or stretch an image to the the size you ask. It will keep the image at the same aspect ratio. So in your case, the image is being scaled down to 100x53, which leaves a blank space above and below.
I presume you don't want to distort the water animation, so the solution is to set your <image> and <pattern> widths and heights to 251x132.
<svg id="water" width="440" height="440">
<defs>
<pattern id="img1" patternUnits="userSpaceOnUse" width="251" height="132">
<image xlink:href="https://i.imgur.com/u7ufQto.gif" x="0" y="0" width="251" height="132" />
</pattern>
</defs>
<path d="M100,100 h200 a20,20 0 0 1 20,20 v200 a20,20 0 0 1 -20,20 h-200 a20,20 0 0 1 -20,-20 v-200 a20,20 0 0 1 20,-20 z" fill="url(#img1)" stroke="black" stroke-width="3" />
</svg>

Related

Is SVG ellipse with "reverse fill" possible?

<svg viewBox="0 0 600 1200" xmlns="http://www.w3.org/2000/svg">
<image x="0" y="0" height="200" width ="100" xlink:href="https://upload.wikimedia.org/wikipedia/commons/thumb/b/bc/IKB_191.jpg/1200px-IKB_191.jpg" />
<ellipse cx="50" cy="100" rx="50" ry="62" fill="grey" />
</svg>
In the example above, we want to be able to see the image (the blue box) inside of the ellipse, and have the grey of the ellipse only show in the corners / on the outside. You could think of this like a portrait of a person (the image) with a border (the inverse-of-ellipse).
We have an SVG with an image and an ellipse. The SVG image doesn't have many attributes (no border radius), and so we thought to use an "inverse-filled" ellipse, where the fill color is on the outside of the ellipse rather than inside. Unfortunately this is not happening in our example. Is this possible with svg:ellipse? Or is there some other approach? We need the image in the SVG, and our goal is to create a curved "border" (think border-radius 50%) of a certain fill color placed in front of the image.
Edit: I could create an svg:path, or maybe there is some sort of clipping that can be placed over the image?
Edit2: this path is close but not quite there because there shouldn't be any blue inside of the ellipse created by the path...
<svg height="200">
<path
stroke="black" fill="blue" stroke-width="2" fill-opacity="0.5"
d="
M0 80
a40 80 0 0 0 80 0
a40 80 1 0 0 -80 0
l0 80
l80 0
l0 -160
l-80 0
"
/>
</svg>
There are a few ways to achieve the deired result. Here are a couple
With a mask
<svg viewBox="0 0 600 1200" xmlns="http://www.w3.org/2000/svg">
<defs>
<mask id="ellipse-mask">
<ellipse cx="50" cy="100" rx="50" ry="62" fill="white" />
</mask>
</defs>
<rect x="0" y="38" width="100" height="124" fill="gray"/>
<image x="0" y="0" height="200" width ="100"
xlink:href="https://upload.wikimedia.org/wikipedia/commons/thumb/b/bc/IKB_191.jpg/1200px-IKB_191.jpg"
mask="url(#ellipse-mask)"/>
</svg>
With a path or clipping path
Your path was close. But you needed to close each subpath with a Z or z) so that they are individually filled.
<svg height="200">
<path
stroke="black" fill="blue" stroke-width="2" fill-opacity="0.5"
d="
M0 80
a40 80 0 0 0 80 0
a40 80 1 0 0 -80 0
Z
M0 0
l80 0
l0 160
l-80 0
Z
"
/>
</svg>

Emoji character outline in SVG

I'm trying to create an outline of an emoji character (meaning I want to draw just the outer shape of the emoji) in SVG. The best I could come up with so far is to use two masked rectangles, scaled and super-imposed on each other.
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="100" height="100">
<defs>
<filter id="filter">
<feColorMatrix in="SourceAlpha" type="matrix" values="0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 0 0 0 1 0" />
</filter>
<mask id="mask" x="0" y="0" width="100" height="100">
<text filter="url(#filter)" x="0" y="80" font-family="Helvetica" font-weight="bold" font-size="7em" fill="#000000">🦄</text>
</mask>
</defs>
<path fill="#fff" d="M0 0 L0 100 L100 100 L100 0z"/>
<path fill="#000000" d="M0 0 L0 100 L100 100 L100 0z" mask="url(#mask)"/>
<g transform="translate(5, 5) scale(0.9)">
<path d="M0 0 L100 0 L100 100 L0 100z" mask="url(#mask)" fill="#fff"/>
</g>
</svg>
Depending on the particular emoji the result isn't very satisfactory though because not all emojis fill width and height equally.
Is there a better way to achieve an outline effect for emoji characters?
You need a viewBox for the svg element and I am using viewBox="0 -30 157 140" slightly bigger than the bounding box of the text element.
instead of a mask I'm using clipPath to clip a white rectangle
The filter I'm using is feMorphology operator="dilate" and I'm applying the filter to a group wrapping the clipped rectangle.
svg{border:solid}
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="100" viewBox="0 -30 157 140">
<defs>
<filter id="outline-indigo">
<feMorphology in="SourceAlpha" result="expanded"
operator="dilate" radius="3"/>
<feFlood flood-color="indigo" result="indi" />
<feComposite in ="indi" in2="expanded" operator="in" />
<feComposite in="SourceGraphic"/>
</filter>
<clipPath id='emojiClipPath'>
<text filter="url(#filter)" x="0" y="80" font-family="Helvetica" font-weight="bold" font-size="7em" fill="#000000">🦄</text>
</clipPath>
</defs>
<g filter="url(#outline-indigo)">
<rect y="-30" width="157" height="140" fill="white" clip-path='url(#emojiClipPath)'/>
</g>
</svg>

SVG not changing size

I have created an svg heart with a background image inside.
I'm trying to make the svg larger, but changing the width and height on both the pattern and the svg itself does not work.
<svg
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
version="1.1" height="315" width="345" >
<!-- START SVG RULES -->
<defs>
<!-- DEFINE IMAGE INSIDE PATTERN -->
<pattern id="img1" patternUnits="userSpaceOnUse" width="100" height="100">
<image xlink:href="https://images.pexels.com/photos/325185/pexels-photo-325185.jpeg?auto=compress&cs=tinysrgb&dpr=2&h=750&w=1260" x="0" y="0" width="100" height="100" /></pattern>
<!-- SVG SHAPE CREATION -->
<g id="heart">
<path
d="M0 200 v-200 h200
a100,100 90 0,1 0,200
a100,100 90 0,1 -200,0
z" />
</g>
</defs>
<use xlink:href="#heart" class="outline" fill="url(#img1)" />
</svg>
For a resizable SVG use viewBox="0 0 315 345"instead height="315" width="345"
<svg
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
version="1.1" viewBox="0 0 315 345" >
<!-- START SVG RULES -->
<defs>
<!-- DEFINE IMAGE INSIDE PATTERN -->
<pattern id="img1" patternUnits="userSpaceOnUse" width="100" height="100">
<image xlink:href="https://images.pexels.com/photos/325185/pexels-photo-325185.jpeg?auto=compress&cs=tinysrgb&dpr=2&h=750&w=1260" x="0" y="0" width="100" height="100" /></pattern>
<!-- SVG SHAPE CREATION -->
<g id="heart">
<path
d="M0 200 v-200 h200
a100,100 90 0,1 0,200
a100,100 90 0,1 -200,0
z" />
</g>
</defs>
<use xlink:href="#heart" class="outline" fill="url(#img1)" />
</svg>
Click the resize button to see if this is what you need.
https://jsfiddle.net/gbxquc05/29/
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" width="100%" height="100%" preserveAspectRatio="none" viewBox="0 0 400 400">
Drawing paths in SVG is unfortunately limitted to absolute units. This is a workaround using viewBox to create coordinate system that transforms to percentage.

SVG pattern with viewBox display differently in Safari and Chrome

Following svg segment defines a graph with major/minor lines. It behaves as expected in Chrome. But the ending minor line mis-aligned with major line for each square. Any idea why?
<svg width="8in" height="11in" viewBox="0 0 960 1320">
<defs>
<pattern id="smallGrid" width="12" height="12" patternUnits="userSpaceOnUse">
<path d="M 12 0 L 0 0 0 12" fill="none" stroke="gray" stroke-width="0.5"></path>
</pattern>
<pattern id="grid12" width="120" height="120" patternUnits="userSpaceOnUse">
<rect width="120" height="120" fill="url(#smallGrid)"></rect>
<path d="M 120 0 L 0 0 0 120" fill="none" stroke="blue" stroke-width="1"></path>
</pattern>
</defs>
<rect fill="white" height="800" width="800" y="0"></rect>
<rect fill="url(#grid12)" height="360" width="360" y="0"></rect>
</svg>

Hexagon + Border-radius + Background-image, how can i do this?

i have a question for u. For example i got this picture, and need to do background image width box-shadow (yellow) on It with photo of someone (doesn't matter). How can i do it right?
*Updated Image!
A task like this is best achieved with SVG, as it allows you to define complex shapes.
<svg viewBox="0 0 120 100" style="width:120px;height:100px">
<defs>
<clipPath id="hexagon_clip">
<path id="hexagon" d="M38,2
L82,2
A12,12 0 0,1 94,10
L112,44
A12,12 0 0,1 112,56
L94,90
A12,12 0 0,1 82,98
L38,98
A12,12 0 0,1 26,90
L8,56
A12,12 0 0,1 8,44
L26,10
A12,12 0 0,1 38,2" />
<!-- SVG Hexagon path from http://stackoverflow.com/a/36842587/507674 -->
</clipPath>
</defs>
<image xlink:href="http://placehold.it/120x100" x="0" y="0" width="120px" height="100px" clip-path="url(#hexagon_clip)" />
<use xlink:href="#hexagon" x="0" y="0" stroke="orange" stroke-width="5" fill="transparent" />
</svg>
What happens here is that a clipping path is defined for the hexagon, then applied to the image. Finally, the hexagon is drawn again over the top to make the border.