Styling SVG images using CSS classes - svg

I'm new in Svelte and would like to ask if is any possibility of styling SVG images imported as Svelte component using CSS classes? I have code like so:
<script lang="ts">
import Logo from './assets/logo.svg';
import Content from './components/Content.svelte';
</script>
<div class="main">
<div class="logo">
<Logo class="icon" />
</div>
<Content />
</div>
<style lang="scss">
.main {
max-width: 920px;
width: 100%;
margin: 0 auto;
}
.logo {
height: 144px;
}
.icon {
margin: 50px auto 0;
}
</style>
I'm getting a warning:
Unused CSS selector ".icon"
Am I doing something wrong or it just can't work in that way?

Since there is no .icon element in your svelte component you will need to use the :global(...) modifier like :global(.icon) { margin: 50px auto 0; }. However this will impact all .icon of your app so scope it to all .icon that is in this component's .logo element:
<style lang="scss">
.logo :global(.icon) {
margin: 50px auto 0;
}
</style>

As you can not style a svg with css from outside the svg code you must embed the styles inside the svg code. You must use <![CDATA[ your styles here ]]> to prevent some fallbacks. So your logo would look like this:
<svg width="100%" height="100%" viewBox="0 0 140 64" xmlns="http://www.w3.org/2000/svg">
<style><![CDATA[.first{ stroke:none; fill:red; } .second{ stroke:none; fill:green; } .third{ stroke:none; fill:blue; }]]></style>
<path class="first" d="M30.262 57.02L7.195 40.723c-5.84-3.976-7.56-12.06-3.842-18.063 3.715-6 11.467-7.65 17.306-3.68l4.52 3.76 2.6-5.274c3.717-6.002 11.47-7.65 17.305-3.68 5.84 3.97 7.56 12.054 3.842 18.062L34.49 56.118c-.897 1.512-2.793 1.915-4.228.9z"/>
<path class="second" d="M105.512 56.12l-14.44-24.272c-3.716-6.008-1.996-14.093 3.843-18.062 5.835-3.97 13.588-2.322 17.306 3.68l2.6 5.274 4.52-3.76c5.84-3.97 13.592-2.32 17.307 3.68 3.718 6.003 1.998 14.088-3.842 18.064L109.74 57.02c-1.434 1.014-3.33.61-4.228-.9z"/>
<path class="third" d="M67.408 57.834l-23.01-24.98c-5.864-6.15-5.864-16.108 0-22.248 5.86-6.14 15.37-6.14 21.234 0L70 16.168l4.368-5.562c5.863-6.14 15.375-6.14 21.235 0 5.863 6.14 5.863 16.098 0 22.247l-23.007 24.98c-1.43 1.556-3.757 1.556-5.188 0z"/>
</svg>

Related

Why is SVG width 0 if container is display flex?

When I run the following code in a browser:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<style>
svg {
border:1px solid green;
width:200px !important;
height:200px;
}
#container {
position:fixed;
top:300px;
left:800px;
width:1px;
height:1px;
overflow:visible;
display:flex;
flex-wrap:wrap;
justify-content:center;
align-content:center;
}
</style>
</head>
<body>
<div id="container">
<svg class="e3" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
<circle cx="50" cy="50" r="50"/>
</svg>
</div>
</body>
</html>
All I get is a 2 pixel vertical line in the browser. It seems the width of my SVG is 0 (not including the green borders). When I delete the css rule display:flex, then my SVG circle appears. I tried to force my SVG to have a width: 200px !important; but this rule doesn't seem to take effect.
Why is my SVG not respecting the 200px rule when I use display:flex on the container?
I believe your SVG node is not displaying as you expect because it has a default position of static. If you change the SVG node to be absolute you'll get the desired behavior.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<style>
svg {
position: absolute;
border: 1px solid green;
width: 200px;
height: 200px;
}
#container {
position: fixed;
/* changed these for ease of viewing */
top: 30px;
left: 150px;
width: 1px;
height: 1px;
overflow: visible;
display: flex;
flex-wrap: wrap;
justify-content: center;
align-content: center;
border: 1px solid red;
}
</style>
</head>
<body>
<div id="container">
<svg class="e3" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg">
<circle cx="50" cy="50" r="50"/>
</svg>
</div>
</body>
</html>

*responsive* SVG graphic with paint fill

Is it possible to create a scalable SVG graphic like this ?
Scalable SVG graphic
I want it to resize according to the device dimensions. I'm trying to create a background image which'll use the full page dimensions - not fixed layout.
This is what I've come up with so far.
<!DOCTYPE html>
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8" />
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" >
<title>New Design</title>
<style type="text/css">
html, body, div, span
{
margin:0;
padding:0;
border:0;
vertical-align: baseline;
}
body
{
font-family:'Roboto', Arial, Helvetica, sans-serif;
font-size:13px;
background-color:lightyellow;
}
html
{
height:100%;
}
body
{
min-height:100%;
position:relative;
}
#container
{
margin:0 auto;
background-color:#eceff1;
position:absolute;
top:0;
left:0;
right:0;
bottom:0;
}
path {
fill: blue;
}​
</style>
</head>
<body>
<div id="container">
<div style="width:calc(100% - 100px);height:calc(100% - 100px);margin:0 auto;padding:10px;border:1px solid red;">
<svg height="100%" width="100%" style="border:1px solid #5A07BC;background-color:#fff">
<line x1="20%" y1="0" x2="50%" y2="200" style="stroke:#5A07BC;stroke-width:1" />
<line x1="50%" y1="200" x2="0" y2="450" style="stroke:#5A07BC;stroke-width:1" />
<line x1="100%" y1="20%" x2="60%" y2="60%" style="stroke:#2AA4C6;stroke-width:1" />
<line x1="60%" y1="60%" x2="95%" y2="100%" style="stroke:#2AA4C6;stroke-width:1" />
</div>
</div>
</body>
</html>
You're not required to have every element in your SVG be in percentages. SVG graphics are scalable by default, but you need to include a viewBox attribute that describes its coordinate system.
The viewBox attribute takes four values — viewBox="x_min y_min width height" — which describe the extent of the drawing inside the SVG. You'll usually have something like viewBox='0 0 800 600' which means I have drawn things on a canvas of 800x600 "pixels", with the origin at x = 0, y = 0.
Then when you set a particular width and height to a SVG, it will, by default, stretch the image to fit these dimensions, but you can control the behavior with the preserveAspectRatio attribute.
Further reading: There's a good article on CSS Tricks about these two properties.

Responsive inline svg?

This SVG icon is 640x640px. The toolbar is 48px high.
The icon should now automatically adjust to the height of the toolbar.
Accordingly, the blue area would have to be 48x48px.
However, the icon now occupies much more space than it needs.
I gave the svg a height of 48px. Better would be height: 100% but that does not work.
my codepen
Changing only the height to 48px leaves the width at 640px. Because you have width="640px" specified on your <SVG>.
So the fix is simply to remove the width and height attributes from <svg>.
body {
margin: 5%;
}
.toolbar {
position: realive;
color: #fff;
display: flex;
align-items:center;
justify-content: space-between;
background: red;
height: 48px;
}
.toolbar__section.flex-grow {
flex-grow: 1;
}
.toolbar__section.bg-green {
background: green;
}
svg {
display: flex;
height: 48px;
background: blue;
}
<p><strong>Responsive inline svg?</strong></p>
<p>
This SVG icon is 640x640px. The toolbar is 48px high.
The icon should now automatically adjust to the height of the toolbar.
Accordingly, the blue area would have to be 48x48px.
However, the icon now occupies much more space than it needs.
I gave the svg a height of 48px. Better would be "height: 100%" but that does not work.
</p>
<div class="toolbar">
<div class="toolbar__section bg-green flex-grow">
Logo
</div>
<div class="toolbar__section">
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 640 640" preserveAspectRatio="xMinYMin meet">
<title></title>
<g id="icomoon-ignore">
</g>
<path fill="#000" d="M603.794 613.188l-190.189-207.478c42.858-44.846 66.395-103.468 66.395-165.71 0-64.106-24.964-124.375-70.294-169.706s-105.6-70.294-169.706-70.294-124.375 24.964-169.706 70.294-70.294 105.6-70.294 169.706 24.964 124.376 70.294 169.706 105.6 70.294 169.706 70.294c55.226 0 107.595-18.542 150.027-52.655l190.178 207.467c3.156 3.442 7.471 5.188 11.799 5.188 3.862 0 7.736-1.391 10.808-4.205 6.513-5.972 6.954-16.093 0.982-22.607zM32 240c0-114.691 93.309-208 208-208s208 93.309 208 208-93.309 208-208 208-208-93.309-208-208z"></path>
</svg>
</div>
<div class="toolbar__section bg-green">
Login Icon
</div>
</div>
Delete the width attribute from the svg element. You may have to adjust the flex-grow attributes in your toolbar afterwards.
See it live on CodePen.
Tested on Chrome 63.0.3239.132

SVG Responsive Text

I have an SVG within a web page, it consists of images + text
<object data="/infographic/timeline.svg" type="image/svg+xml">
<img src="/infographic/timeline.svg" alt="Timeline">
</object>
All the images are responsive, but the text isn't, so the text becomes really, REALLY small.
snippet of SVG (its massive)
<defs>
<style>
.cls-1 {
font-size: 60.014px;
}
.cls-1, .cls-10 {
opacity: 0.69;
}
.cls-1, .cls-10, .cls-4, .cls-5, .cls-7, .cls-8, .cls-9 {
fill: #ffffff;
}
.cls-1, .cls-10, .cls-3, .cls-4, .cls-5, .cls-6, .cls-7, .cls-9 {
text-anchor: middle;
}
.cls-1, .cls-3, .cls-6 {
font-family: "Roboto";
}
.cls-2 {
font-size: 32.014px;
}
.cls-3 {
font-size: 14.089px;
}
.cls-3, .cls-6 {
fill: #db7426;
}
.cls-4, .cls-6 {
font-size: 32px!important;
}
.cls-10, .cls-4, .cls-5, .cls-7, .cls-8, .cls-9 {
font-family: Roboto;
}
.cls-5 {
font-size: 24px;
}
.cls-5, .cls-8, .cls-9 {
font-weight: 400;
}
.cls-6 {
font-weight: 600;
}
.cls-10, .cls-7 {
font-size: 18.75px;
font-weight: 300;
}
.cls-7 {
opacity: 0.4;
}
.cls-8, .cls-9 {
font-size: 22px;
}
</style>
</defs>
<text id="Who_are_you_what_do_you_do_what_s_your_why_What_s_been_keepi" data-name="Who are you, what do you do, what’s your why? What’s been keepi" class="cls-8" x="397.706" y="535.325">Who are you, what do you do, what’s your why?<tspan x="397.706" dy="26.4">What’s been keeping you lying awake at night. </tspan></text>
Is there anyway I can get the text size to increase as the SVG/screen width gets smaller?
Any help would be greatly appreciated.
It's not possible with pure SVG (at least not yet). The only solution would be to either:
inline the SVG and manipulate the size of the text with javascript.
inline the SVG and control the size of the text with media queries (see below).
Add CSS to the SVG and use media queries there (see below).
use media queries to switch SVGs when the page gets small
Example of option 2: Using media queries with inlined SVGs
text {
font-size: 10px;
}
#media (max-width: 400px) {
text {
font-size: 20px;
}
}
<svg viewBox="0 0 100 100" width="100%" height="100%">
<circle cx="50" cy="50" r="50" fill="orange"/>
<text x="50" y="60" text-anchor="middle">Testing</text>
</svg>
Example of option 3: Using media queries in CSS in the SVGs
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" width="100%" height="100%">
<style>
text {
font-size: 10px;
}
#media (max-width: 400px) {
text {
font-size: 20px;
}
}
</style>
<circle cx="50" cy="50" r="50" fill="orange"/>
<text x="50" y="60" text-anchor="middle">Testing</text>
</svg>
This is possible using the foreignObject svg element in a html context and some adjustment of the viewBow.
On this demos, the text stay selectable:
.demo {
overflow: auto;
resize: both;
border:1px black solid;
width: 230px;
height: 130px
}
.svgtext {
font-size: 28rem;
height:100%;
width:100%
}
<div class="demo">
<svg x="0" y="30" viewBox="0 0 100 100" width="100%" height="100%">
<foreignObject x="12" y="23" height="100%" width="100%">
<div class"svgtext">
Hello world!
</div>
</foreignObject>
</svg>
</div>
Use preserveAspectRatio to control the resizing behavior:
.demo {
overflow: auto;
resize: both;
border:1px black solid;
width: 230px;
height: 130px
}
.svgtext {
font-size: 28rem;
height:100%;
width:100%
}
<div class="demo">
<svg preserveAspectRatio="none" x="0" y="30" viewBox="0 0 100 100" width="100%" height="100%">
<foreignObject x="12" y="23" height="100%" width="100%">
<div class"svgtext">
Hello world!
</div>
</foreignObject>
</svg>
</div>

How to make SVG break aspect ratio

I have and SVG and I need to fulfil the browser windows. It´s an with sag assigned to src attribute. No mather I do, always keep aspect ratio. I even force image width and height via CSS but I can´t make it work.
The url: https://dl.dropboxusercontent.com/u/814218/svg/svg_test.html
Any suggestion?
Finally, I find the solution by recommendation of #SVG IRC Mozilla Group. The related info is here: http://codepen.io/jonitrythall/blog/preserveaspectratio-in-svg
I need to use, viewBox and preserveAspectRatio attributes. That´s the solution.
Here the final sample SVG source code:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 1282 802" preserveAspectRatio="defer none"
xml:space="preserve">
<polygon opacity="0.2" fill="#FF00FF" stroke="#93278F" stroke-miterlimit="10" points="-1.5,0 -1.5,800 638.5,400 "/>
<polygon opacity="0.2" fill="#009245" points="0,801 1280,801 640,401 "/>
<polygon opacity="0.2" fill="#FFFF00" stroke="#FFFF00" stroke-miterlimit="10" points="638.5,400 1278.5,800 1278.5,0 "/>
</svg>
Try using:
.autoHeight{
width: 100%;
height: 100%;
}
#bg img {
max-width: 100%;
width: 100%;
height: 100%;
}
And your html should looks like:
<body cz-shortcut-listen="true">
<div id="bg" class="autoHeight" style="width: 100%; height: 100%;">
<img class="autoHeight" src="triangles.svg" alt="" style="width: 100%; height: 100%;">
</div>
</body>
But, basically, you need use: for both, width and height: 100%
Do you mean you need something like this?
<html>
<head>
<style>
html, body, img#svg { width: 100%; height: 100%; border: 0; margin: 0; padding:0 }
</style>
</head>
<body>
<img id="svg" src="https://dl.dropboxusercontent.com/u/814218/svg/triangles.svg" />
</body>
</html>

Resources