How to modify the size of a <g> (SVG element)? - css

I can not seem to succeed at modifying the size of my element that is rendered inside a recharts graph as X axis. I want it to be 20px height and width. I couldn't even succeed by making modifications in the console css to the element. Could anyone help me out?
Here's the element:
<svg
style={{ cursor: 'pointer', }} width="20px" height="20px"
>
<g transform={`translate(10,10)`} fill="green" stroke="green">
<path
fill="current"
fillRule="evenodd"
d="M8,0 C3.58862306,0 0,3.58862306 0,8 C0,12.4113769 3.58862306,16 8,16 C12.4113769,16 16,12.4113769 16,8 C16,3.58862306 12.4113769,0 8,0 Z M12.0546875,6.3046875 L7.72131347,10.6379394 C7.59130859,10.7679443 7.42065431,10.833374 7.25,10.833374 C7.07934569,10.833374 6.90869141,10.7679443 6.77868653,10.6379394 L4.61206056,8.47131347 C4.35131837,8.21069338 4.35131837,7.78930663 4.61206056,7.52868653 C4.87268066,7.26794434 5.29394531,7.26794434 5.5546875,7.52868653 L7.25,9.22399903 L11.1120606,5.36206056 C11.3726807,5.10131837 11.7939453,5.10131837 12.0546875,5.36206056 C12.3153076,5.62268066 12.3153076,6.04394531 12.0546875,6.3046875 Z"
transform="translate(.5)"
/>
</g>
</svg>

As #enxaneta recommended, a negative viewBox offset like viewBox="-0.5 -0.5 17 17" is a straight forward solution.
Alternatively, you could scale your <g> (or your path) like so:
.svg{
display:inline-block;
width:10em;
border: 1px solid #ccc
}
<svg class="svg" viewBox="0 0 16 16">
<g transform="scale(0.94117647)" transform-origin="8 8" stroke-width="1" fill="green" stroke="green">
<path d="M8,0 C3.58862306,0 0,3.58862306 0,8 C0,12.4113769 3.58862306,16 8,16 C12.4113769,16 16,12.4113769 16,8 C16,3.58862306 12.4113769,0 8,0 Z M12.0546875,6.3046875 L7.72131347,10.6379394 C7.59130859,10.7679443 7.42065431,10.833374 7.25,10.833374 C7.07934569,10.833374 6.90869141,10.7679443 6.77868653,10.6379394 L4.61206056,8.47131347 C4.35131837,8.21069338 4.35131837,7.78930663 4.61206056,7.52868653 C4.87268066,7.26794434 5.29394531,7.26794434 5.5546875,7.52868653 L7.25,9.22399903 L11.1120606,5.36206056 C11.3726807,5.10131837 11.7939453,5.10131837 12.0546875,5.36206056 C12.3153076,5.62268066 12.3153076,6.04394531 12.0546875,6.3046875 Z" ></path>
</g>
</svg>
Edit: correct scaling value
As #Carsten Massmann has pointed out it should be:
The scaling factor 0.94117647 is the result of
16/17 (original svg width / svg width + stroke-width)
transform-origin="8 8" ensures we're scaling from the center of our viewBox.
Another workaround might be to set overflow to visible to avoid any cropping:
.svg{
display:inline-block;
width:10em;
border: 1px solid #ccc
}
<svg overflow="visible" class="svg" viewBox="0 0 16 16">
<path stroke-width="1" fill="green" stroke="green" d="M8,0 C3.58862306,0 0,3.58862306 0,8 C0,12.4113769 3.58862306,16 8,16 C12.4113769,16 16,12.4113769 16,8 C16,3.58862306 12.4113769,0 8,0 Z M12.0546875,6.3046875 L7.72131347,10.6379394 C7.59130859,10.7679443 7.42065431,10.833374 7.25,10.833374 C7.07934569,10.833374 6.90869141,10.7679443 6.77868653,10.6379394 L4.61206056,8.47131347 C4.35131837,8.21069338 4.35131837,7.78930663 4.61206056,7.52868653 C4.87268066,7.26794434 5.29394531,7.26794434 5.5546875,7.52868653 L7.25,9.22399903 L11.1120606,5.36206056 C11.3726807,5.10131837 11.7939453,5.10131837 12.0546875,5.36206056 C12.3153076,5.62268066 12.3153076,6.04394531 12.0546875,6.3046875 Z" ></path>
</svg>
Caveats: your icon will be displayed larger than your original design and might cause layout inconsistencies when used with other elements that fit the 16x16 boundaries.

If it will be useful to you, I found svg similar to yours and I demonstrated how you can add styles
svg {
background: #479840;
border-radius: 50%;
}
path {
filter: invert(99%) sepia(99%) saturate(2%) hue-rotate( 205deg)
brightness(110%) contrast(100%);
}
<svg height="44" viewbox="0 0 24 24" width="44" xmlns="http://www.w3.org/2000/svg">
<path d="m10 15.586-3.293-3.293-1.414 1.414L10 18.414l9.707-9.707-1.414-1.414z"></path></svg>

Related

Draw a circle in svg with preserveAspectRatio="none"

I have an svg with viewBox="0 0 100 100" preserveAspectRatio="none" since I need to draw some elements with reference to percentages.
If I now draw a <circle cx="30" cy="50" r="0.5" stroke="white"/> though it becomes stretched/distorted as well.
Is there a way to tell the circle element to preserve its own aspect ratio?
If all you need is a circle you can use a very short, very wide line like in the following example.
This will work because
stroke-linecap="round" will give the illusion of a circle and because
strokes can take a vector-effect="non-scaling-stroke".
non-scaling-stroke
This value modifies the way an object is stroked. Normally stroking involves calculating stroke outline of the shape's path in current user coordinate system and filling that outline with the stroke paint (color or gradient). The resulting visual effect of this value is that the stroke width is not dependent on the transformations of the element (including non-uniform scaling and shear transformations) and zoom level.
div {
width: 300px;
height: 50px;
background-color: lime;
}
svg {
width:100%;
height:100%;
}
<div>
<svg viewBox="0 0 100 100" preserveAspectRatio="none">
<!--<circle cx="30" cy="50" r="20"></circle>-->
<line x1="30" y1="50" x2="30.1" y2="50" stroke-width="40" stroke="black" stroke-linecap="round" vector-effect="non-scaling-stroke" />
</svg>
</div>
If you need a white stroke too you can add a white line behind the black one with a bigger stroke width
div {
width: 300px;
height: 50px;
background-color: lime;
}
svg {
width:100%;
height:100%;
}
<div>
<svg viewBox="0 0 100 100" preserveAspectRatio="none">
<line x1="30" y1="50" x2="30.1" y2="50" stroke-width="45" stroke="white" stroke-linecap="round" vector-effect="non-scaling-stroke" />
<line x1="30" y1="50" x2="30.1" y2="50" stroke-width="40" stroke="black" stroke-linecap="round" vector-effect="non-scaling-stroke" />
</svg>
</div>

Before pseudo element not showing up on path element

Hi i am trying to create a 'pin' on a SVG map of the whole world, the SVG is build with path elements, my thought was to use a before or after element and show the pin accordingly.
Apparently it is not showing on the path element, i can see it in the debugger/console and if i put it on a div element it works fine and shows up, i have cut out all countries except the first one in the SVG for simplicity.
CSS
.map-pin::after{
content: url('pin.svg');
background-size: 30px 30px;
background-repeat: no-repeat;
background-position: left top;
width: 30px;
height: 30px;
z-index: 10;
font-size: 1px;
display: inline-block;
position: absolute;
left: -999px;
top: -999px;
/*display: none;*/
}
.map-pin.active::after{
display: block;
}
.map-pin.active[data-id="AF"]::after{
top: 0;
left: 0;
}
SVG
<svg xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:cc="http://creativecommons.org/ns#" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" style="stroke-linejoin: round; stroke:#000; fill: none;" viewBox="0 0 2000 1001" id="svg2" inkscape:version="0.48.4 r9939" sodipodi:docname="world.svg">
<defs id="defs4">
<style type="text/css" id="style6">path { fill-rule: evenodd; }</style>
</defs>
<g id="countries">
<path id="AF" data-name="Afghanistan" data-id="AF" class="map-pin active" d="m 1369.9,333.8 -5.4,0 -3.8,-0.5 -2.5,2.9 -2.1,0.7 -1.5,1.3 -2.6,-2.1 -1,-5.4 -1.6,-0.3 0,-2 -3.2,-1.5 -1.7,2.3 0.2,2.6 -0.6,0.9 -3.2,-0.1 -0.9,3 -2.1,-1.3 -3.3,2.1 -1.8,-0.8 -4.3,-1.4 -2.9,0 -1.6,-0.2 -2.9,-1.7 -0.3,2.3 -4.1,1.2 0.1,5.2 -2.5,2 -4,0.9 -0.4,3 -3.9,0.8 -5.9,-2.4 -0.5,8 -0.5,4.7 2.5,0.9 -1.6,3.5 2.7,5.1 1.1,4 4.3,1.1 1.1,4 -3.9,5.8 9.6,3.2 5.3,-0.9 3.3,0.8 0.9,-1.4 3.8,0.5 6.6,-2.6 -0.8,-5.4 2.3,-3.6 4,0 0.2,-1.7 4,-0.9 2.1,0.6 1.7,-1.8 -1.1,-3.8 1.5,-3.8 3,-1.6 -3,-4.2 5.1,0.2 0.9,-2.3 -0.8,-2.5 2,-2.7 -1.4,-3.2 -1.9,-2.8 2.4,-2.8 5.3,-1.3 5.8,-0.8 2.4,-1.2 2.8,-0.7 -1.4,-1.9 z" style="fill:#f2f2f2;fill-rule:evenodd"></path>
</g>
</svg>
I also tried a more simple way by just adding an element inside the SVG after all the path elements, but this breaks the whole SVG.
Anyone able to help me out here, is it not possible in SVG path elements? and if so, what other options am i left with?
PIN:
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" id="Layer_1" style="enable-background:new 0 0 512 512;" viewBox="0 0 512 512" xml:space="preserve">
<style type="text/css">
.st0{fill:none;stroke:#454545;stroke-width:18;stroke-miterlimit:10;}
</style>
<g>
<g id="XMLID_4245_">
<path class="st0" d="M389.3,208.7c0-73.6-59.7-133.3-133.3-133.3c-73.6,0-133.3,59.7-133.3,133.3 c0,32.6,12.1,62,31.5,85.1l55.3,75.4l46.6,67.5l101.8-142.9C377.2,270.7,389.3,241.2,389.3,208.7z" id="XMLID_4247_"></path>
<path class="st0" d="M311,170.9L311,170.9c-12.1-11.6-31.7-11.6-43.8,0l-10.9,10.5L245.3,171 c-12.1-11.6-31.7-11.6-43.8,0c-12.1,11.6-12.1,30.4,0,42l54.7,52.5L311,213C323.1,201.4,323.1,182.6,311,170.9z" id="XMLID_4246_"></path>
</g>
</g>
</svg>
As I've commented you can't have a before pseudo element for a path. However in your case you can have a symbol for the pin and use it at the end of your document. This way it will stay above all the other paths. (a z-index won't work either in SVG).
If you are using a symbol with a viewBox attribute you can give the <use> element a position (x and y attributes) and a size (width and height attributes)
<svg xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:cc="http://creativecommons.org/ns#" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:svg="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg" xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" style="stroke-linejoin: round; stroke:#000; fill: none;" viewBox="1280 320 100 100" id="svg2" >
<defs id="defs4">
<style type="text/css" id="style6">path { fill-rule: evenodd; }</style>
</defs>
<symbol id="map-pin-after" viewBox="0 0 30 30">
<circle cx="15" cy="8" r="8" /> <polygon points="15,30 22.7,10 7.3,10 15,30"/>
</symbol>
<g id="countries">
<path id="AF" data-name="Afghanistan" data-id="AF" class="map-pin active" d="m 1369.9,333.8 -5.4,0 -3.8,-0.5 -2.5,2.9 -2.1,0.7 -1.5,1.3 -2.6,-2.1 -1,-5.4 -1.6,-0.3 0,-2 -3.2,-1.5 -1.7,2.3 0.2,2.6 -0.6,0.9 -3.2,-0.1 -0.9,3 -2.1,-1.3 -3.3,2.1 -1.8,-0.8 -4.3,-1.4 -2.9,0 -1.6,-0.2 -2.9,-1.7 -0.3,2.3 -4.1,1.2 0.1,5.2 -2.5,2 -4,0.9 -0.4,3 -3.9,0.8 -5.9,-2.4 -0.5,8 -0.5,4.7 2.5,0.9 -1.6,3.5 2.7,5.1 1.1,4 4.3,1.1 1.1,4 -3.9,5.8 9.6,3.2 5.3,-0.9 3.3,0.8 0.9,-1.4 3.8,0.5 6.6,-2.6 -0.8,-5.4 2.3,-3.6 4,0 0.2,-1.7 4,-0.9 2.1,0.6 1.7,-1.8 -1.1,-3.8 1.5,-3.8 3,-1.6 -3,-4.2 5.1,0.2 0.9,-2.3 -0.8,-2.5 2,-2.7 -1.4,-3.2 -1.9,-2.8 2.4,-2.8 5.3,-1.3 5.8,-0.8 2.4,-1.2 2.8,-0.7 -1.4,-1.9 z" fill="#f2f2f2"></path>
</g>
<use xlink:href="#map-pin-after" stroke="none" fill="red" width="30" height="30" x="1310" y="327"/>
</svg>
UPDATE
An update where I'm using the OP's pin:
Since the new pin is not a square, and in order to preserve the aspect ratio, I had to recalculate the height of the pin.
<svg viewBox="1280 320 100 100" >
<defs>
<symbol id="map-pin-after" viewBox="111 60 290 397">
<g id="XMLID_4245_" fill="none" stroke="#454545" stroke-width="18" stroke-mitterlimit="10">
<path d="M389.3,208.7c0-73.6-59.7-133.3-133.3-133.3c-73.6,0-133.3,59.7-133.3,133.3 c0,32.6,12.1,62,31.5,85.1l55.3,75.4l46.6,67.5l101.8-142.9C377.2,270.7,389.3,241.2,389.3,208.7z" ></path>
<path d="M311,170.9L311,170.9c-12.1-11.6-31.7-11.6-43.8,0l-10.9,10.5L245.3,171 c-12.1-11.6-31.7-11.6-43.8,0c-12.1,11.6-12.1,30.4,0,42l54.7,52.5L311,213C323.1,201.4,323.1,182.6,311,170.9z" ></path>
</g>
</symbol>
</defs>
<g id="countries">
<path id="AF" data-name="Afghanistan" data-id="AF" class="map-pin active" d="m 1369.9,333.8 -5.4,0 -3.8,-0.5 -2.5,2.9 -2.1,0.7 -1.5,1.3 -2.6,-2.1 -1,-5.4 -1.6,-0.3 0,-2 -3.2,-1.5 -1.7,2.3 0.2,2.6 -0.6,0.9 -3.2,-0.1 -0.9,3 -2.1,-1.3 -3.3,2.1 -1.8,-0.8 -4.3,-1.4 -2.9,0 -1.6,-0.2 -2.9,-1.7 -0.3,2.3 -4.1,1.2 0.1,5.2 -2.5,2 -4,0.9 -0.4,3 -3.9,0.8 -5.9,-2.4 -0.5,8 -0.5,4.7 2.5,0.9 -1.6,3.5 2.7,5.1 1.1,4 4.3,1.1 1.1,4 -3.9,5.8 9.6,3.2 5.3,-0.9 3.3,0.8 0.9,-1.4 3.8,0.5 6.6,-2.6 -0.8,-5.4 2.3,-3.6 4,0 0.2,-1.7 4,-0.9 2.1,0.6 1.7,-1.8 -1.1,-3.8 1.5,-3.8 3,-1.6 -3,-4.2 5.1,0.2 0.9,-2.3 -0.8,-2.5 2,-2.7 -1.4,-3.2 -1.9,-2.8 2.4,-2.8 5.3,-1.3 5.8,-0.8 2.4,-1.2 2.8,-0.7 -1.4,-1.9 z" fill="#f2f2f2" stroke="black"></path>
</g>
<use xlink:href="#map-pin-after" stroke="none" fill="red" width="41" height="30" x="1305" y="327"/>
</svg>

How to use SVG clipPath with Pattern via CSS clip-path property?

The initial SVG figure with pattern:
<svg width="200" height="200" viewBox="0 0 100 100">
<defs>
<pattern id="img-dotted-dots" x="0" y="0" height=".08" width="7.69%">
<circle cx="2" cy="2" fill="white" r="0.8"></circle>
</pattern>
<mask id="img-dotted-mask">
<rect width="100" height="100" fill="url(#img-dotted-dots)"></rect>
</mask>
</defs>
<path d="M0 0 H 100 V 100 H 0 Z" mask="url(#img-dotted-mask)" fill="#1063B1"></path>
</svg>
Need to achieve:
One instance of the SVG figure with pattern for refferencing with CSS as clip-path.
I have tried to create SVG clipPath element and bind to CSS clip-path by this way
.figure {
width: 300px;
height: 300px;
clip-path: url(#img-dotted-clip-path);
background-color: #1063B1;
}
<div class="figure"></div>
<svg width="0" height="0" viewBox="0 0 100 100">
<defs>
<clipPath
clipPathUnits="objectBoundingBox"
id="img-dotted-clip-path">
<pattern
patternUnits="objectBoundingBox"
patternContentUnits="objectBoundingBox"
x="0" y="0" height="0.1" width="0.1">
<circle cx="0" cy="0" fill="white" r="0.5"></circle>
</pattern>
</clipPath>
</defs>
</svg>
Nothing happens.
Expected result - the same as the previous snippet.
For comparing:
If I use SVG rect - CSS clip-path works.
If pattern - doesn't
.figure {
width: 300px;
height: 300px;
clip-path: url(#img-dotted-clip-path);
background-color: #1063B1;
}
<div class="figure"></div>
<svg width="0" height="0" viewBox="0 0 100 100">
<defs>
<clipPath
clipPathUnits="objectBoundingBox"
id="img-dotted-clip-path">
<rect width="1" height="1"></rect>
</clipPath>
</defs>
</svg>
The only things that are valid inside a clip path are:
Shape elements (‘circle’, ‘ellipse’, ‘line’, ‘path’, ‘polygon’, ‘polyline’, ‘rect’)
‘text’
‘use’
Plus you can use animation elements etc to animate the clip path. However, only the shapes of those elements are used. Effects such as patterns, filters, etc are ignored.
The only way you could get the effect you want to work as a clipping path would be to add numerous <circle> elements to your <clipPath>.
<clipPath>
<circle>
<circle>
<circle>
<circle>
... etc ...
</clipPath>
But you could use a mask instead. Masks allow patterns.
.figure {
width: 300px;
height: 300px;
-webkit-mask: url(#img-dotted-mask);
mask: url(#img-dotted-mask);
background-color: #1063B1;
}
<p>This only works in Firefox</p>
<div class="figure"></div>
<svg width="0" height="0">
<defs>
<pattern id="img-dotted-pattern"
viewBox="0 0 1 1"
patternUnits="userSpaceOnUse" x="0" y="0" width="20" height="20">
<rect width="1" height="1" fill="black"/>
<circle cx="0.5" cy="0.5" fill="white" r="0.15"></circle>
</pattern>
<mask id="img-dotted-mask">
<rect width="2000" height="2000" fill="url(#img-dotted-pattern)"/>
</mask>
</defs>
</svg>
However inline SVG masks applied to HTML elements, like my example above, only work in Firefox. To get an SVG mask to work in Chrome, you would need to use mask or mask-image with an external or Data URL (as Temani has done in their answer).
You can recreate the same thing using mask combined with radial-gradient
.figure {
width: 300px;
height: 300px;
background:linear-gradient(to right,red,#1063B1);
/*radius here size here*/
-webkit-mask:radial-gradient(3px, #fff 97%,transparent 100%) 0 0/20px 20px;
mask:radial-gradient(3px, #fff 97%,transparent 100%) 0 0/20px 20px;
}
body {
background:#f2f2f2;
}
<div class="figure"></div>
Or consider the SVG inside the mask property. Make sure to escape the # and correctly set the viewbox and width/height to have a perfect repeat
.figure {
width: 300px;
height: 300px;
background:linear-gradient(to right,red,#1063B1);
-webkit-mask:url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="200" height="192" viewBox="0 0 100 90"><defs><pattern id="img-dotted-dots" x="0" y="0" height=".08" width="7.69%"><circle cx="2" cy="2" fill="white" r="0.8"></circle></pattern><mask id="img-dotted-mask"><rect width="100" height="100" fill="url(%23img-dotted-dots)"></rect></mask></defs><path d="M0 0 H 100 V 100 H 0 Z" mask="url(%23img-dotted-mask)" fill="%231063B1"></path></svg>');
mask:url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="200" height="192" viewBox="0 0 100 90"><defs><pattern id="img-dotted-dots" x="0" y="0" height=".08" width="7.69%"><circle cx="2" cy="2" fill="white" r="0.8"></circle></pattern><mask id="img-dotted-mask"><rect width="100" height="100" fill="url(%23img-dotted-dots)"></rect></mask></defs><path d="M0 0 H 100 V 100 H 0 Z" mask="url(%23img-dotted-mask)" fill="%231063B1"></path></svg>');
}
body {
background:#f2f2f2;
}
<div class="figure"></div>

Svg responsive width with adjustable height

been having a hard time to come up with a good solution to have a responsive svg that will adopt the screen width plus an adjustable height. I tried setting width to 100% and height to something like 200px but no luck.
header.svg {
width: 100%;
max-height: 200px;
height: 200px;
}
<header>
<svg width="321px" height="141px" viewBox="0 0 321 141" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<defs></defs>
<g id="Symbols" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="header-copy-" fill="#262626">
<g id="header-copy-2">
<path d="M0,0.31823636 L321,0.31823636 L321,132.556396 C267.894961,138.185465 214.394961,141 160.5,141 C106.605039,141 53.1050387,138.185465 0,132.556396 L0,0.31823636 Z" id="Rectangle-Copy-12"></path>
</g>
</g>
</g>
</svg>
</header>
I also tried adding a 100% width to the header element.
Firstly, your selector is incorrect, it should be header svg not header.svg. The SVG is a child of the header...the header does not have the class of .svg.
Secondly, I'd recommend removing the height and width from the SVG. It's not needed since you have set an appropriate viewbox.
Now, it seems you want the width of the SVG to be 100% of the page but the height to be limited to a set value.
To do this you will have to set the preserveAspectRatio attribute of the SVG to none.
Viewbox & PreserveAspectRatio
header {
background: pink;
}
svg {
max-height: 100px;
width: 100%;
margin: auto;
display: block;
}
<header class="wide">
<svg viewBox="0 0 321 141" version="1.1" xmlns="http://www.w3.org/2000/svg" preserveAspectRatio="none">
<defs></defs>
<g id="Symbols" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="header-copy-" fill="#262626">
<g id="header-copy-2">
<path d="M0,0.31823636 L321,0.31823636 L321,132.556396 C267.894961,138.185465 214.394961,141 160.5,141 C106.605039,141 53.1050387,138.185465 0,132.556396 L0,0.31823636 Z" id="Rectangle-Copy-12"></path>
</g>
</g>
</g>
</svg>
</header>

Responsive clip-path with inline SVG

On an element with a background (image or solid color don't really matter):
<header id="block-header"></header>
I am trying to apply a clip-path using SVG. To achieve this, I am putting SVG inline into the same element like this:
<header id="block-header">
…
<svg width="100%" height="100%" viewBox="0 0 4000 1696" preserveAspectRatio="none">
<defs>
<clipPath id="myClip">
<path d="M0 1568.18V0h4000v1568.18S3206.25 1696 2000 1696C984.37 1696 0 1568.18 0 1568.18z"/>
</clipPath>
</defs>
</svg>
…
</header>
You can run the code snippet below or check the JSFiddle. You can see original SVG image (in black) put inline, having curviness along the bottom and being responsive. In contrast, the red rectangle shows the same image applied (or, rather, not applied) as a clip-path.
I guess I misunderstand either viewBox or preserveAspectRatio attributes though can not find what is exactly wrong here. Any help would be appreciated.
#block-header {
background: Red;
min-height: 100px;
-webkit-clip-path: url(#myClip);
clip-path: url(#myClip);
}
<h1>SVG image</h1>
<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100" viewBox="0 0 4000 1696" preserveAspectRatio="none"><path d="M0 1568.18V0h4000v1568.18S3206.25 1696 2000 1696C984.37 1696 0 1568.18 0 1568.18z"/></svg>
<h1><code>clip-path</code> using the same SVG</h1>
<header id="block-header">
<svg width="100%" height="100" viewBox="0 0 4000 1696" preserveAspectRatio="none">
<defs>
<clipPath id="myClip">
<path d="M0 1568.18V0h4000v1568.18S3206.25 1696 2000 1696C984.37 1696 0 1568.18 0 1568.18z"/>
</clipPath>
</defs>
</svg>
</header>
References to SVG clip paths are to the clip path definitions themselves and the dimensions or other attributes of the <svg> are meaningless in this context.
What is happening in your example is that you are applying a 4000 px wide clip path to your header. Which is probably only of the order of 900 px wide. So the curvature isn't visible.
If you want a responsive clip path, you should define it using clipPathUnits="objectBoundingBox".
#block-header {
background: Red;
min-height: 100px;
-webkit-clip-path: url(#myClip);
clip-path: url(#myClip);
}
<h1>SVG image</h1>
<svg xmlns="http://www.w3.org/2000/svg" width="100%" height="100" viewBox="0 0 1 1" preserveAspectRatio="none"><path d="M0,0 1,0 1,0.9 C 1,0.9, 0.77,1, 0.5,1 0.23,1, 0,0.9,0,0.9z"/></svg>
<h1><code>clip-path</code> using the same SVG</h1>
<header id="block-header">
<svg width="0" height="0">
<defs>
<clipPath id="myClip" clipPathUnits="objectBoundingBox">
<path d="M0,0 1,0 1,0.9 C 1,0.9, 0.77,1, 0.5,1 0.23,1, 0,0.9,0,0.9z"/>
</clipPath>
</defs>
</svg>
</header>
Fiddle here

Resources