Please see this example on codepen
I am using a CSS var as the fill prop for the SVG, but I've purposefully left off the closing parenthesis. The colour still displays as intended. Why would this be the case?
NB: When using the var() in the stylesheet, it's not as forgiving (see the example)
<body>
<style>
:root {
--main-color: #06c;
}
/* If you miss the closing parenthesis from var() the styling breaks, which makes sense*/
h1 {
color: var(--main-color);
}
</style>
<h1>Here is my coloured heading</h1>
<!-- the closing parenthesis from var() is missing, but the colour is still applied. That's good for when you make a mistake, but I dont get why -->
<svg height="100" width="100">
<circle cx="50" cy="50" r="40" stroke="black" stroke-width="3" fill="var(--main-color" />
Sorry, your browser does not support inline SVG.
</svg>
</body>
It does also work in CSS but you need to remove the last } and have nothing after it:
:root {
--main-color: #06c;
}
h1 {
color: var(--main-color
<h1>Here is my coloured heading</h1>
Sometimes the browser is clever enough "to understand" some broken stuff but you should never rely on such behavior. People use such trick to shorten the code when doing some online challenges for fun or they simply do it by mistake.
Related
I have an issue with this css.
I tried both auto and default but still I see the default cursor.
cursor: url('img/extra/arrow-next.svg'), auto;
cursor: url('img/extra/arrow-next.svg'), default;
Anyone has the same problem or am I doing something wrong?
You probably didn't specify the height and width of your SVG file. Therefore, your browser can't use it as a cursor. In order to use this SVG file as a cursor, open it in a text-editor and change it to something similar to this:
<svg height="20" width="20">
...
</svg>
When this is changed, this CSS code should do the trick:
cursor: url('img/extra/arrow-next.svg'), auto;
I'm working on a handful of SVG icons as <symbol> that I want to be able to alter on :hover, :focus, and :active. Specifically, I need to be able to change the color of specific paths within an SVG. Normally, with any other element, I can do something like this
.parent .child {
fill: blue;
}
.parent:hover .child {
fill: red;
}
However, when applying this to my SVG symbols, it just doesn't work. Not many discussions from what I can find in the last couple of years on problems changing css with shadow-DOM stuff like SVG symbols, but the just using CurrentColor won't work for me because I need to do it with two colors.
I have a CodePen up with my scenario here
It seems like this should be straightforward but I've been tied up in knots over it for awhile. Anybody have any thoughts that might help?
Thanks in advance!
A similar question was asked here: SVG USE element and :hover style
The problem is that elements that are referenced by use aren't really part of the DOM, so you can't access them with CSS. However, some properties that are set on the use element itself (like fill or color) will trickle down to the referenced elements.
So, first of all, our CSS can only change the use element. Then we need to use some of the tricks in the article #Matheus mentioned to handle the different colors. This means changing the SVG code for the symbols a little. If the icons only need two colors per state, we can use fill + color/currentColor:
<g id="icon_alarm">
<g class="transflip">
<path class="transflip" d="M8 1.3c-3.6 ....." />
<path class="transflip" d="M1 5.1C1.7 3....." />
</g>
<g class="fillflip">
<path class="fillflip" fill="currentColor" d="M11.7 8......" />
</g>
...
.icon use {
fill: transparent;
color: #007fa3;
}
.icon:hover use {
fill: #007fa3;
color: transparent;
}
If the icons need more colors per state, we can use CSS variables and add style="fill: var(--my-special-color)" styles in the SVG (also a trick from the mentioned article), but that doesn't work in some browsers, e.g. IE/Edge.
Updated pen using both techniques: https://codepen.io/Sphinxxxx/pen/GMjgxJ?editors=1100
html:hover .transflip {
fill: red;
}
This kind of hover works. I noticed you used same class for g and path. I'd try not to.
I'd also try to wrap each svg inside a div with width and height, and then use :focus etc. on that div since svg elements seem not to recognize pseudoselectors on your pen.
http://codepen.io/anon/pen/KwKOaz
Changing only the background-color significantly changes the style on a button element, specifically the border style.
This happens on chrome, safari, and firefox on a Mac. Why does this happen? How can I safely change its background color?
Browser vendors apply custom styling to UI elements like buttons and input fields. Altering one of these overwritten attributes results in disabling all of the other vendor styles on that element as well. If you want to change one attribute, you have to alter the others as well, I'm afraid.
Unfortunately I can't tell you why they do this - probably there is might be some spec behind, but I cannot find any evidence for that.
When all the styles are untouched, the browser uses the host OS's given API to render the given control. This will make the control look native to the platform, but if you apply any style to that control/element, the browser cannot guarantee that the given style can be applied in the given platform, so it defaults back to a simplified, fully css solution.
Also note, that styling control elements, though works, not covered by stable standards yet.
For example, the NSButton (native control behind the button in OS X) doesn't have an option to set the background color, so the browser faces an impossible task. On Windows, you can change the background color, this is why people report not seeing your issue on Windows.
Sometimes CSS styles are inherited. However, you are applying styles to your body which is everything in HTML. Personally I don't apply anything to body other than maybe reset or normalize CSS. That said, you can use CSS selector operators and\or id/classes to minimize:
http://www.w3schools.com/cssref/css_selectors.asp
Example:
html
btw don't write html like this just easier to read
<body>
<div class="wrapper">
<button class="all-btns red">
Cancel
</button>
<button class="all-btns green">
Save
</button>
</div>
</body>
css
.div.wrapper {
width: 100%;
height: auto;
background: #efefef;
}
.all-btns {
border: solid 1px #000;
width: 50px;
line-height: 48px;
height 35px;
color: #fff;
}
.btn.red {
color: #fff;
background: red;
}
.btn.green {
background: green;
}
I'm using reCAPTCHA, and the textarea for recaptcha_challenge_field is appearing in the middle of the recaptcha box overlapping other things. I found that it's because of this style:
.recaptchatable #recaptcha_response_field {
position: absolute!important;
when I set position to static in Chrome, it looks fine. However, I can't figure out how to overwrite that CSS option.
I tried:
adding this to my own CSS:
.recaptchatable #recaptcha_response_field {
position: static !important;
}
adding another entry in my CSS with the name .recaptcha_text
calling it via div class (wrapping around textarea)
calling it via p class (wrapping around textarea)
adding position: static!important; to the standard <textarea name="recaptcha_challenge_field" ...> tag
However, I can't get my css to overwrite that position: static!important; that comes over with the script:
<script type="text/javascript"
src="http://www.google.com/recaptcha/api/challenge?k=your_public_key">
</script>
<noscript>
<iframe src="http://www.google.com/recaptcha/api/noscript?k=your_public_key"
height="300" width="500" frameborder="0"></iframe><br>
<textarea name="recaptcha_challenge_field" rows="3" cols="40"></textarea>
<input type="hidden" name="recaptcha_response_field" value="manual_challenge">
</noscript>
Can someone please help with what I'm doing wrong? Thank you!
From testing here: http://jsbin.com/otihuk/edit#html,live (the test only seems to work in WebKit browsers)
This looks like a simple CSS specificity issue. The reCAPTCHA CSS is loaded after yours, and both your selector and theirs have equal specificity (and both have !important in the declaration), and so because theirs is specified last, it wins.
You can fix it by making your selector more specific than theirs:
#recaptcha_area #recaptcha_response_field {
position: static !important;
}
I've added that in my demo above, and I can see by inspecting the #recaptcha_response_field element that the computed value of the position property is now indeed static.
It is pretty easy to create a pop-up with the "title" attribute in SVG. But how do you achieve the same effect with CSS.
This is for an illustration I'm making for Wikimedia and I strive to have most things other wikipedians would like to correct within an embedded stylesheet, with style properties grouped by real-life subject. Most wikipedia editors are computer illiterates, you can't expected them to hunt through a lot of code to make their modifications and if they have to change anything but simple CSS-values within the code, then you probably get a nasty mess out of it. If I make this to hard for their poor brains, then sooner or later someone will make the file unmaintainable by using Inkscape, Illustrator or some other equally horrible vector editor.
I could use Javascript, but that would make the illustration less accessible and make the code even more confusing for people who need to edit it. Also, some SVG-files using Javascript have been removed from Wikimedia because of that, but I'm not sure if that is an absolute rule.
I just discovered when I validated my file that the title-attribute in SVG is not allowed where I have been using it, but it works with most browsers. According to the standard you should use the title-element, but that doesn't seem to work with any browsers. Also, according to the standard, I could give a title-attribute to a style-element, but that doesn't seem to work with any browser and it would require me to use 180 style-elements instead of just one (the code is generated by a script, so it isn't a problem for me to create them, it is just that it would make the code much larger and harder to understand).
The two "answers" I've gotten thus far have not been for the question I asked, and is not even remotely useful.
I don't care if the image is editable in Inkscape. Inkscape is a good tool for creating bitmap images (even if you have to run them through some other program to get better compression afterwards). Inkscape sucks at creating SVG files (or any vector based image files intended for an audience, the vector based image files Inkscape creates is only really usefull with Inkscape), Inkscape is a really, really, really poor tool to choose for creating SVG images intended as an end product; Sodipodi was a good tool for that, but Inkscape is not Sodipodi, only based on Sodipodi (unfortunatly, the old C-version of Sodipodi don't run well on modern computer systems and the C++ version was never finished). I want to make my image easy to edit with a text editor, so that no Wikipedian is tempted to use Inkscape and make the file unmaintanable (and in the process increase the size from slightly less then 2 MB to more then 60 MB, if you save it in Inkscape as a "standard" SVG image (which not always give a standard complient file), Inkscapes own svg-based file format makes even larger files).
I don't think wikipedia allow javascript within SVG-images, so Javascript is out of the question.
I already know how to create tooltips with javascript and two different methods to create them in SVG (but not in CSS embedded in SVG). The reason, in addition to the one already mentioned in the original question, that I don't want to use SVG code for the tooltips is that no web-browser support the standard, but SVG-viewers do (but not the non-standard tooltips that work with browsers), so someone who would manually make corrections to a tooltip in the file (with a text editor), would have to change the text in two different places, most likely, with time, resulting in different tooltips when viewed in different browsers/viewers.
I often resort to using the (invalid) title="" attribute on SVG elements as it's so simple and seems to work in most browsers. I understand your requirement is that it is standards compliant and that people can edit the graphic in InkScape transparently and without breaking the tooltips - for this you will have to use some JavaScript. Here's a quick example I hope you'll find helpful, it will attach the mouseover event to each <title> element's immediate parent and load the text content in a tooltip displayed next to the cursor. This while retaining InkScape compatibility and the ability to use InkScape's "Object Properties" dialog box to set the tooltip text.
Given the following example SVG:
<svg xmlns="http://www.w3.org/2000/svg">
<title>Main Title</title>
<g id="group1">
<title>Title One</title>
<circle cx="120" cy="60" r="40" fill="#993333" />
</g>
<g id="group2">
<title>Title Two</title>
<circle cx="60" cy="60" r="40" fill="#339933" />
<g id="group3">
<circle cx="180" cy="60" r="40" fill="#333399" />
<title>Title Three</title>
</g>
</g>
</svg>
First add a dummy tooltip element:
<g id="toolTip" transform="translate(0,0)">
<rect width="150" height="25" />
<text x="5" y="18"> </text>
</g>
Give it some styling:
<style>
g#toolTip {
visibility: hidden;
}
g#toolTip rect {
fill: #FFCC00;
}
g#toolTip text {
font-size: 16px;
}
</style>
Then insert a sprinkling of JS:
<script>
<![CDATA[
var toolTip = document.getElementById('toolTip');
var titles = document.getElementsByTagName('title');
for (var i = 0; i < titles.length; i++) {
titles.item(i).parentNode.addEventListener('mouseover', function(e) {
showTip(this,xy(e));
}, true);
titles.item(i).parentNode.addEventListener('mouseout', function() {
hideTip();
}, true);
}
function showTip(element,pos) {
var text = element.getElementsByTagName('title')[0].childNodes[0].nodeValue;
toolTip.getElementsByTagName('text')[0].childNodes[0].nodeValue = text;
toolTip.setAttribute('transform', 'translate(' + pos + ')');
toolTip.style.visibility = 'visible';
}
function hideTip() {
toolTip.style.visibility = 'hidden';
}
function xy(e) {
if (!e) var e = window.event;
if (e.pageX || e.pageY) {
return [e.pageX,e.pageY]
} else if (e.clientX || e.clientY) {
return [e.clientX + document.body.scrollLeft + document.documentElement.scrollLeft,e.clientY + document.body.scrollTop + document.documentElement.scrollTop];
}
return [0,0]
}
]]>
</script>
Caveats: The JS block needs to go at the bottom of the SVG file - and if you use the XML editor in InkScape (rare) it will mess up the script (this may be solved by moving to an external JS file and adding some DOM ready detection).
The approach also expects that a) all <title> elements should be rendered as tooltips and b) that there is only ever one <title> element per parent (oddly, the SVG spec allows multiple) - here I have hard coded it to simply use the first <title> child element encountered, ignoring any subsequent ones.
Note: the xy(e) function is only needed to get round browser inconsistencies when it comes to reporting the cursor position - you may not need it, or you may prefer to roll your own.
Bonus: This could easily be extended to make use of the <desc> element as well, should you need more elaborate tooltips with longer bits of text.
As far as i can tell you can't.
The SVG element seems to behave oddly.
I thought you could apply a similar concept as this using CSS3:
<style type="text/css">
acronym {
position: relative;
}
acronym:after {
content: attr(title);
position: absolute;
position: absolute;
left: 100%;
margin-left: -10px;
top: -0.5em;
z-index: 2;
padding: 0.25em;
width: 200px;
background-color: #f1f1f1;
text-align: center;
display: none;
}
acronym:hover:after {
display: block;
}
</style>
<acronym title="Keep It Simple Stupid">KISS</acronym>
But the :after Selector doesn't seem to work on the SVG element
I think your best bet is a jQuery script which runs on $(document).ready() and does all the heavy lifting for you.
This article: http://codepen.io/recursiev/pen/zpJxs
demonstrates several types of tooltip with SVG.
Including what you asked for : SVG+CSS.
Basically:
<g class="tooltip css" transform="translate(200,50)">
<rect x="-3em" y="-45" width="6em" height="1.25em"/>
<text y="-45" dy="1em" text-anchor="middle" fill="LightSeaGreen">
SVG/CSS Tip</text>
</g>
With some appropriate CSS as well:
.tooltip {
pointer-events:none; /*let mouse events pass through*/
opacity:0;
transition: opacity 0.3s;
text-shadow:1px 1px 0px gray;
}
g.tooltip:not(.css) {
fill:currentColor;
}
g.tooltip rect {
fill: lightblue;
stroke: gray;
}
This article: http://www.scientificpsychic.com/etc/css-mouseover.html
demonstrates CSS only tooltips.
basically:
<span class="dropt" title="Title for the pop-up">Hot Zone Text
<span style="width:500px;">Pop-up text</span>
</span>
with this CSS:
span.dropt {border-bottom: thin dotted; background: #ffeedd;}
span.dropt:hover {text-decoration: none; background: #ffffff; z-index: 6; }
span.dropt span {position: absolute; left: -9999px;
margin: 20px 0 0 0px; padding: 3px 3px 3px 3px;
border-style:solid; border-color:black; border-width:1px; z-index: 6;}
span.dropt:hover span {left: 2%; background: #ffffff;}
span.dropt span {position: absolute; left: -9999px;
margin: 4px 0 0 0px; padding: 3px 3px 3px 3px;
border-style:solid; border-color:black; border-width:1px;}
span.dropt:hover span {margin: 20px 0 0 170px; background: #ffffff; z-index:6;}
Between these, you should be able to get exactly what you want.
UPDATE: This works fine for me in Chrome v44, but not in Internet Explorer v9.
IE just gives me the popup's title, not the popup itself.