How to create circle svg progress bar with dashed border - html

i"m using this awesome tutorial for creating circle progress bar.
but my problem is that i want to change the stroke-dasharray in the CSS:
fill: none;
stroke: #FF2A2A;
stroke-width: 9.9213;
stroke-miterlimit: 10;
stroke-dasharray: 1.4308, 1.4308;
I want it to animate it like in the tutorial but to look like this image:
Dashed border circle

Try the following changes to the tutorial you mentioned:
progress.component.css:
~~~~~~~~~~~~~~~~~~~~~~~
.progress__meter {
stroke: #4CAF50;
}
.progress__value {
stroke: white;
transition: all 100ms;
}
progres.component.html:
~~~~~~~~~~~~~~~~~~~~~~~
<div class="progress">
<svg class="progress__svg" width="120" height="120" viewBox="0 0 120 120">
<circle class="progress__meter" [style.strokeDasharray]="5" cx="60" cy="60" [attr.r]="radius" stroke-width="11" />
<circle class="progress__value" [style.strokeDasharray]="circumference" [style.strokeDashoffset]="1-dashoffset" cx="60" cy="60" [attr.r]="radius" stroke-width="12" />
</svg>
<div class="progress__value-text">{{value}}%</div>
</div>
progress.component.ts:
~~~~~~~~~~~~~~~~~~~~~~
private progress(value: number) {
const progress = value / 100;
this.dashoffset = this.circumference * (progress);
}

Related

CSS Animated Radial Graph overflow after animation SVG

I've encountered a problem when using the css disarray function. The "front" circle clips over after animation has finished and doesnt "Start" at origin point of the animation. After the animation has completed, the filled stroke clips back past the origin point. Can someone Please help me out - I've tried reading up on SVG elements and have fiddled with the code for a few hours now and I still cant get it to animate properly.
Thank you so much for your support. Here is the code I am working with.
.radial-graph-container {
display: flex;
justify-content: center;
flex-direction: column;
padding-bottom: 2.4rem;
}
.radial-graph-container .chart-container .back {
stroke: #101114;
stroke-width: 10;
}
.radial-graph-container .chart-container .front {
stroke: #94d82d;
stroke-width: 15;
stroke-dasharray: 210;
/* Works fine with values above 300 */
transform: rotate(-90deg);
transform-origin: center;
}
.front {
animation: fill 1s reverse;
}
<div class="radial-graph-container">
<svg width="200" height="200" class="chart-container">
<circle cx="100" cy="100" r="90" class="back" fill="none" />
<circle cx="100" cy="100" r="90" class="front" fill="none" />
<g class="graph-center-txt">
<text
x="100"
y="100"
alignment-baseline="central"
text-anchor="middle"
id="percentage-social-media-usage"
>
42%
</text>
</g>
</svg>
<p class="graph-info-txt">
Description Text Here
</p>
</div>
Your animation part was missing: (the #keyframes section)
.radial-graph-container {
display: flex;
justify-content: center;
flex-direction: column;
padding-bottom: 2.4rem;
}
.radial-graph-container .chart-container .back {
stroke: #101114;
stroke-width: 10;
}
.radial-graph-container .chart-container .front {
stroke: #94d82d;
stroke-width: 15;
stroke-dasharray: 210;
/* Works fine with values above 300 */
transform: rotate(-90deg);
transform-origin: center;
}
.front {
animation: fill 1s reverse;
}
#keyframes fill {
0% {
r: 90;
}
100% {
r: 0;
}
}
<div class="radial-graph-container">
<svg width="200" height="200" class="chart-container">
<circle cx="100" cy="100" r="90" class="back" fill="none" />
<circle cx="100" cy="100" r="90" class="front" fill="none" />
<g class="graph-center-txt">
<text
x="100"
y="100"
alignment-baseline="central"
text-anchor="middle"
id="percentage-social-media-usage"
>
42%
</text>
</g>
</svg>
<p class="graph-info-txt">
Description Text Here
</p>
</div>

Pie chart using circle element

I am trying to create a pie chart using circle element in svg. I am able to fill values to 60%, 30% and 10% but all the circle starting from same position.
How can I make next circle start from where previous one ended?
svg { transform: rotate(-90deg); }
circle {
stroke-width: 3;
stroke-opacity: 1;
fill: none;
}
circle.stroke-yellow {
stroke: yellow;
stroke-dasharray: calc(2*3.14*50*60/100),calc(2*3.14*50);
}
circle.stroke-red {
stroke: red;
stroke-dasharray: calc(2*3.14*50*30/100),calc(2*3.14*50);
}
circle.stroke-blue {
stroke: blue;
stroke-dasharray: calc(2*3.14*50*10/100),calc(2*3.14*50);
}
<svg xmlns="http://www.w3.org/2000/svg" height="220">
<circle class="stroke-yellow" cy="110" cx="110" r="50"></circle>
<circle class="stroke-red" cy="110" cx="110" r="50"></circle>
<circle class="stroke-blue" cy="110" cx="110" r="50"></circle>
</svg>
Also stroke-width is not working which I mentioned in CSS.
As #enxaneta mentioned: you will need to give each pie segment an offset by changing the dash-offset property.
Based on your code example:
svg {
transform: rotate(-90deg);
}
circle {
stroke-width: 3;
stroke-opacity: 1;
fill: none;
}
.stroke {
stroke-width: 100;
--circumference: 314.159
}
circle.stroke-blue {
stroke: blue;
stroke-dasharray: calc( var(--circumference) * 10 / 100), var(--circumference);
stroke-dashoffset: 0;
}
circle.stroke-red {
stroke: red;
stroke-dasharray: calc( var(--circumference) * 30 / 100), var(--circumference);
stroke-dashoffset: calc( 0 - var(--circumference) * 10 / 100);
}
circle.stroke-yellow {
stroke: yellow;
stroke-dasharray: calc( var(--circumference) * 60 / 100), var(--circumference);
stroke-dashoffset: calc( 0 - var(--circumference) * 40 / 100);
}
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 220 220" height="220">
<circle class="stroke stroke-blue stroke-10" cy="110" cx="110" r="50" />
<circle class="stroke stroke-yellow stroke-60" cy="110" cx="110" r="50" />
<circle class="stroke stroke-red stroke-30" cy="110" cx="110" r="50" />
</svg>
stroke-width needs to be '100' (radius*2);
Drawbacks:
Firefox seems to have problems, rendering svg elements when attributes are are calculated via css calc() (SVG pie-chart working only in Chrome, not in Firefox)
difficult to be reused for multiple pi chart instances
Recommendations:
simplify your calculations by optimizing your svg geometry.
control your values (e.g pie percentages, colors) via HTML/svg attributes (or css variables)
Example showing 2 slightly different svg setups:
body{
font-family: arial;
font-size:10px;
}
.icon-wrp {
position: relative;
display: inline-block;
width: 200px;
vertical-align: top;
}
.icon-wrp p{
font-size:12px;
}
<!--simple pi -->
<div class="icon-wrp">
<svg class="svgPieAsset" viewBox="0 0 63.6619772368 63.6619772368">
<symbol id="slice">
<circle transform="rotate(-90 31.8309886184 31.8309886184)" id="circle" class="percent" cx="50%" cy="50%" r="15.9154943092" fill="none" stroke-width="31.8309886184" />
</symbol>
<!--actual pi slices -->
<use class="segment" href="#slice" stroke="green" stroke-dashoffset="0" stroke-dasharray="30 100" />
<use class="segment" href="#slice" stroke="orange" stroke-dashoffset="-30" stroke-dasharray="60 100" />
<use class="segment" href="#slice" stroke="purple" stroke-dashoffset="-90" stroke-dasharray="10 100" />
</svg>
<p>1. Precice geometry based on PI. <br>Should be rendered fine on all browsers.</p>
</div>
<div class="icon-wrp">
<svg class="svgPieAsset" viewBox="0 0 100 100">
<symbol id="slice2">
<circle transform="rotate(-90 50 50)" id="circle" class="percent" cx="50%" cy="50%" r="25" fill="none" stroke-width="50%" pathLength="100" />
</symbol>
<!--actual pi slices -->
<use class="segment" href="#slice2" stroke="green" stroke-dashoffset="0" stroke-dasharray="30 100" />
<use class="segment" href="#slice2" stroke="orange" stroke-dashoffset="-30" stroke-dasharray="60 100" />
<use class="segment" href="#slice2" stroke="purple" stroke-dashoffset="-90" stroke-dasharray="10 100" />
</svg>
<p>2. Using pathLength="100". <br>Might show a tiny gap on chromium based browsers.</p>
</div>
1. left example: Is using a precice (PI based) circle geometry
The desired circumference of the circle element should be 100 svg units.
Therfore we'll need to set the ideal values like so:
radius: 15.91549430919 (100/2π)
stroke-width: 31.8309886184 (2r)
vieBox width/height: 63.6619772368 (4r)
2. right example: Is using pathLength="100"
PathLength allows us to use any circle dimensions by setting the path's length computation value to "100".
Unfortunately, you might encounter rendering imprecisions on some browsers (e.g. chromium based) resulting in visible gaps between pie segments.
Quite likely, this issue will be fixed in future versions of chromium.
Display pie segments
Eitherway, you can now easily display a percentage based pie segment/slice by setting a stroke dash length value:
Example 30% dash length; offset. 0 (since it's the first segment):
<circle stroke-dashoffset="0" stroke-dasharray="30 100" cx="50%" cy="50%" r="15.9154943092" fill="none" stroke-width="31.8309886184" />
Adding pie segments:
You'll need to decrement (as we need negative values) the dash-offset values progressively by subtracting the previous dash length (percentage):
0, -30, -90
Example: 60% dash length; offset. -30
<circle stroke-dashoffset="-30" stroke-dasharray="60 100" cx="50%" cy="50%" r="15.9154943092" fill="none" stroke-width="31.8309886184" />
Example optimized for reusability (using css variables)
.icon-wrp {
position: relative;
display: inline-block;
width: 200px;
vertical-align: top;
}
.chart {
width: 1em;
height: 1em;
font-size: var(--chartFontSize);
}
.segment {
stroke-dasharray: var(--percent) 100;
stroke-dashoffset: var(--offset);
stroke: var(--strokeColor);
}
.chartAni .segment {
animation-name: progress;
animation-fill-mode: forwards;
animation-delay: 0.3s;
animation-duration: 0.5s;
transition: 0.3s;
stroke-dasharray: 0 100;
}
#keyframes progress {
from {
stroke-dasharray: 0 100;
stroke-dashoffset: 0;
}
to {
stroke-dasharray: var(--percent) 100;
stroke-dashoffset: var(--offset);
}
}
<!-- pie asset – hidden -->
<svg class="svgPieAsset" style="display:none" viewBox="0 0 63.6619772368 63.6619772368">
<symbol id="slice" viewBox="0 0 63.6619772368 63.6619772368">
<circle transform="rotate(-90 31.8309886184 31.8309886184)" id="circle" class="percent" cx="31.8309886184" cy="31.8309886184" r="15.9154943092" fill="none" stroke-width="31.8309886184" />
</symbol>
</svg>
<!-- visible pie chart -->
<div class="icon-wrp">
<svg id="pieChart01" class="chart chartAni" style="--chartFontSize:20vw">
<use class="segment" href="#slice" style="--offset:-0; --percent:33.333; --strokeColor:green" />
<use class="segment" href="#slice" style="--offset:-33.333; --percent:33.333; --strokeColor:purple" />
<use class="segment" href="#slice" style="--offset:-66.666; --percent:33.333; --strokeColor:gray" />
</svg>
</div>
Edit: donut chart example
For a donut chart or a circular gauge – just adjust the stroke-width to your needs.
.icon-wrp {
position: relative;
display: inline-block;
width: 200px;
vertical-align: top;
}
.chart {
width: 1em;
height: 1em;
font-size: var(--chartFontSize);
}
.segment {
stroke-dasharray: var(--percent) 100;
stroke-dashoffset: var(--offset);
stroke: var(--strokeColor);
}
.chartAni .segment {
animation-name: progress;
animation-fill-mode: forwards;
animation-delay: 0.3s;
animation-duration: 0.5s;
transition: 0.3s;
stroke-dasharray: 0 100;
}
#keyframes progress {
from {
stroke-dasharray: 0 100;
stroke-dashoffset: 0;
}
to {
stroke-dasharray: var(--percent) 100;
stroke-dashoffset: var(--offset);
}
}
<!-- pie asset – hidden -->
<svg class="svgPieAsset" style="display:none;" >
<symbol id="slice" viewBox="0 0 33 33">
<circle id="circle" class="percent" cx="50%" cy="50%" r="15.9154943092" fill="none" stroke-width="0.95" />
</symbol>
</svg>
<!-- visible pie chart -->
<div class="icon-wrp">
<svg id="pieChart01" class="chart chartAni" style="--chartFontSize:20vw; transform:rotate(-90deg);">
<use class="segment" href="#slice" style="--offset:0; --percent:10; --strokeColor:blue" />
<use class="segment" href="#slice" style="--offset:-10; --percent:30; --strokeColor:red" />
<use class="segment" href="#slice" style="--offset:-40; --percent:60; --strokeColor:yellow" />
</svg>
</div>
If herrstrietzel's answer doesn't solve your issue for some reason:
Once upon a time I started working on a blog post demonstrating how to generate simple SVG donut/pie charts in React. It's incomplete but it includes all the information you'd need to compute paths for drawing each segment in your chart.
The post itself is React-centric, but the methodology doesn't require React.
The snippet below was generated using the demo in that blog post.
:root {
--color1: #6761a8;
--color2: #009ddc;
--color3: #f26430;
}
svg {
max-width: 180px;
}
path:nth-child(3n + 1) {
fill: var(--color1);
}
path:nth-child(3n + 2) {
fill: var(--color2);
}
path:nth-child(3n + 3) {
fill: var(--color3);
}
<svg viewBox="0 0 100 100">
<path d="M50.99977962889557 22.51817981476399 L50.99993333466665 0.009999666671113516 A50 50 0 1 1 21.909411013411578 91.36325434956197 L34.92449717574351 72.99954813894905 A27.5 27.5 0 1 0 50.99977962889557 22.51817981476399"></path>
<path d="M33.293128455589205 71.84331575559345 L20.27779148719977 90.20684420744341 A50 50 0 0 1 19.110270928347777 10.683023540969941 L32.65908657059322 28.656553196968876 A27.5 27.5 0 0 0 33.293128455589205 71.84331575559345"></path>
<path d="M34.25580929035654 27.45292793069627 L20.707239127704607 9.479213229769087 A50 50 0 0 1 49.000066665333264 0.009999666671113516 L49.00022037110441 22.51817981476399 A27.5 27.5 0 0 0 34.25580929035654 27.45292793069627"></path>
</svg>
Computing the paths
Each <path> represents one segment (slice) of the chart.
To draw the segment you need to compute the coordinates of the 4 corners and connect them with lines and arcs.
Computing the coordinates
Given an angle, a radius, and a center point, you can compute an (x, y) coordinate via this formula:
function getCoordinate(angleInDegrees, radius, center = 50) {
// degrees to radians;
const radians = angleInDegrees * (Math.PI / 180);
const x = center - Math.cos(radians) * radius
const y = center - Math.sin(radians) * radius;
return [x, y];
}
So for a 90° segment with an outer radius of 50 and an inner radius of 20, you can get the corner coordinates via:
const radiusOuter = 50;
const radiusInner = 20;
const angleStart = 0;
const angleEnd = 90;
const [x1, y1] = getCoordinate(angleStart, radiusInner); // starting angle on inner radius
const [x2, y2] = getCoordinate(angleStart, radiusOuter); // starting angle on outer radius
const [x3, y3] = getCoordinate(angleEnd, radiusOuter); // ending angle on outer radius
const [x4, y4] = getCoordinate(angleEnd, radiusInner); // ending angle on inner radius
Connect the coordinates using SVG path commands:
Details about each of the path commands used below can be found at MDN.
const largeArc = 0; // percent > 0.5 ? 1 : 0;
const sweepOuter = 1;
const sweepInner = 0;
const commands = [
// move to start angle coordinate, inner radius (1)
`M${x1} ${y1}`,
// line to start angle coordinate, outer radius (2)
`L${x2} ${y2}`,
// arc to end angle coordinate, outer radius (3)
`A${radiusOuter} ${radiusOuter} 0 ${largeArc} ${sweepOuter} ${x3} ${y3}`,
// line to end angle coordinate, inner radius (4)
`L${x4} ${y4}`,
// arc back to start angle coordinate, inner radius (1)
`A${radiusInner} ${radiusInner} 0 ${largeArc} ${sweepInner} ${x1} ${y1}`
];
Throw it in an SVG and add a little css and you've got your segment:
svg {
width: 250px;
border: 1px solid grey;
}
path {
fill: tomato;
}
<svg viewBox="0 0 100 100">
<path d="
M30 50
L0 50
A50 50 0 0 1 50 0
L50 30
A20 20 0 0 0 30 50
"/>
</svg>
Repeat for the other segments.

How do I convert these SVG properties into CSS declarations?

I have the following HTML:
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
<circle cx="10.5" cy="10.5" r="7.5"></circle>
<line x1="21" y1="21" x2="15.8" y2="15.8"></line>
</svg>
The HTML looks clunky at best, how do I convert it's properties into CSS?
For example:
#search-svg {
width: 20;
height: 20;
viewBox: 0 0 24 24;
fill: none;
stroke: currentColor;
stroke-width: 2;
stroke-linecap: round;
stroke-linejoin: round
}
I know that the width, height and fill properties exist and can be converted into CSS.
However I don't know how the other properties work or what their CSS equivalents are, and a quick search on caniuse yeilds no results for CSS properties beginning with stroke.
Thank you.
I checked it and almost all properties from your example works, you have to remember that size properties needs unit eg. px.
svg {
width: 40px;
height: 40px;
fill: red;
stroke: green;
stroke-width: 4px;
stroke-linecap: round;
stroke-linejoin: round;
}
circle {
cx: 12px;
cy: 13px;
r: 6px;
}
Also found an source of more data about SVG properties https://css-tricks.com/svg-properties-and-css/
If you want to change the svg css, you should also change the child tag css.
#search-svg {
width: 50px;
height: 50px;
}
#search-svg circle {
fill:none;
stroke: currentColor;
stroke-width: 3;
stroke-linecap: round;
stroke-linejoin: round
}
#search-svg line{
stroke: currentColor;
stroke-linecap: round;
stroke-linejoin: round
}
<!DOCTYPE html>
<html>
<head>
<title>Test</title>
</head>
<body>
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" id ="search-svg">
<circle cx="10.5" cy="10.5" r="7.5"></circle>
<line x1="21" y1="21" x2="15.8" y2="15.8"></line>
</svg>
</body>
</html>

Clipping path from SVG file

I tried copying my SVG into my HTML and defining it as a clipPath, but it doesn't display the shape the right way. Can I define clipPath using a file path?
<div class="gradient">
</div>
<svg height="0" width="0">
<defs>
<clipPath id="Camera">
<style>
.cls-1, .cls-2 {
fill: #363636;
}
.cls-1, .cls-3 {
stroke: #363636;
}
.cls-1 {
stroke-width: 1px;
fill-rule: evenodd;
}
.cls-3 {
fill: none;
stroke-width: 50px;
}
</style>
<path class="cls-1" d="M566.282,395.982s-121.771,16.243-155.258,35.532-93.7,51.606-135.978,123.854c-1.285-10.084-1.014-8.122-1.014-8.122v-33.5a319.278,319.278,0,0,1,20.3-80.2c15.223-37.882,41.848-78.09,77.121-99.489,55.447,0,87.691,5.262,142.067,27.411C565.1,395.035,566.282,395.982,566.282,395.982Zm-136.671,44.24S382.787,553.845,382.741,592.5s-2.176,106.981,39.225,179.738c-9.372-3.929-7.538-3.182-7.538-3.182l-29-16.751a319.037,319.037,0,0,1-59.278-57.684c-25.181-32.13-46.675-75.3-47.563-116.562,27.724-48.04,48.4-73.345,94.761-109.381C428.2,440.773,429.611,440.222,429.611,440.222Zm-34.372,138.5s74.972,97.311,108.424,116.665,91.55,55.336,175.261,55.844c-8.09,6.151-6.526,4.936-6.526,4.936l-29.01,16.739a319.273,319.273,0,0,1-79.6,22.5c-40.418,5.748-88.553,2.786-124.725-17.061-27.733-48-39.3-78.549-47.321-136.692C395.011,580.218,395.239,578.721,395.239,578.721ZM501.768,677.28s121.722-16.3,155.2-35.605,93.676-51.652,135.971-123.924c1.28,10.084,1.011,8.121,1.011,8.121l-0.015,33.5a319.666,319.666,0,0,1-20.323,80.215c-15.233,37.892-41.864,78.115-77.131,99.532-55.422.025-87.649-5.222-141.989-27.348C502.95,678.227,501.768,677.28,501.768,677.28Zm138.679-42.488s46.752-113.61,46.78-152.27,2.126-106.987-39.29-179.768c9.37,3.933,7.536,3.185,7.536,3.185l29,16.765a319.457,319.457,0,0,1,59.277,57.715c25.185,32.144,46.688,75.329,47.594,116.593C763.65,545.042,743,570.339,696.672,606.357,641.857,634.242,640.447,634.792,640.447,634.792ZM672.715,493.3s-74.971-97.311-108.423-116.665S472.741,321.3,389.031,320.789c8.089-6.151,6.525-4.936,6.525-4.936l29.01-16.739a319.289,319.289,0,0,1,79.6-22.5c40.418-5.748,88.552-2.786,124.725,17.061,27.733,48.005,39.3,78.549,47.321,136.692C672.943,491.8,672.715,493.3,672.715,493.3Z"/>
<circle class="cls-2" cx="176" cy="176" r="60"/>
<rect id="Camera_Body" data-name="Camera Body" class="cls-3" x="38" y="38" width="1001" height="1001" rx="100" ry="100"/>
</clipPath>
Will display this
https://codepen.io/TVsVeryOwn/pen/yjwaoy
I'm trying to get something resembling this (I know my gradient is backwards):
< clipPath >  only uses the fill of the shapes.
If you remove < rect id="Camera_Body" > part from your SVG code - you’ll see it’s working as you wanted without this rect element. The rect doesn’t have a fill - only a stroke - and the clipping doesn’t work on stroke.
This may help.

marker-end not getting displayed

I have a following html:
<div id="divVis2" class="divVis">
<svg width="1540" height="345">
<defs>
<marker id="normal" viewBox="0 -5 10 10" refX="15" refY="-1.5" markerWidth="6" markerHeight="6" orient="auto">
<path d="M0,-5L10,0L0,5"></path>
</marker>
<marker id="anomaly" viewBox="0 -5 10 10" refX="15" refY="-1.5" markerWidth="6" markerHeight="6" orient="auto">
<path d="M0,-5L10,0L0,5"></path>
</marker>
</defs>
<g>
<path class="anomaly" marker-end="url(#anomaly)" d="M908.3739002256449,176.0182689704716L661.9527686239043,249.64760217208658"></path>
<path class="normal" marker-end="url(#normal)" d="M660.4045373167714,246.37428873149702L879.5700343222044,98.59473202412175"></path>
<path class="normal" marker-end="url(#normal)" d="M878.0019325543491,95.25420149730667L631.216835426003,167.4248240636326"></path>
</g>
<g>
<g transform="translate(889.5195255254339,91.88595979689137)">
<circle class="normal" r="12"></circle>
<text x="0" y="4" class="normal">133</text>
</g>
<g transform="translate(619.6992424549181,170.7930657640479)">
<circle class="normal" r="12"></circle>
<text x="0" y="4" class="normal">134</text>
</g>
<g transform="translate(650.4550461135419,253.0830609587274)">
<circle class="anomaly" r="12"></circle>
<text x="0" y="4" class="normal">137</text>
</g>
<g transform="translate(919.8716227360072,172.5828101838308)">
<circle class="normal" r="12"></circle>
<text x="0" y="4" class="normal">136_1</text>
</g>
</g>
</svg>
</div>
Its corresponding css is:
#divVis2 path {
fill: none;
/* stroke: #666; */
stroke-width: 0.5px;
}
#divVis2 path.normal {
stroke: #808080;
}
#divVis2 path.anomaly {
stroke: red;
stroke-width: 1.5px;
}
/* for the marker */
#divVis2 #normal {
fill: black;
stroke-width: 0.5px;
}
#divVis2 #anomaly {
fill: red;
stroke-width: 1.5px;
}
#divVis2 circle.normal {
fill: #ccc;
stroke: #ffffff;
stroke-width: 0.5px;
}
#divVis2 circle.anomaly {
fill: #ff0000;
stroke: #ffffff;
stroke-width: 0.5px;
}
#divVis2 text.normal {
font: 7px sans-serif;
pointer-events: none;
fill: black;
text-anchor:middle;
}
#divVis2 text.label {
font: 9px sans-serif;
pointer-events: none;
fill: blue;
text-anchor:middle;
}
The corresponding output in browser is:
Why are the arrows not getting displayed at the end of each path? I am unable to find out the problem in css selectors.
Here is a jsfiddle: http://jsfiddle.net/onh7t53o/
#divVis2 path {
fill: none;
/* stroke: #666; */
stroke-width: 0.5px;
}
has a higher specificity for the markers than
#divVis2 #normal {
fill: black;
stroke-width: 0.5px;
}
so the marker paths are fill="none" and the stroke-width is so thin because the markers are small that you can't see it.
I had this problem in an angular app that was using a <base> tag. In the context of a rich web app like one built on Angular, where you need to set the <base> tag to make HTML5-style navigation work, it can get messy to try to fix that in a permanent way.
In my case, the app I was working on was showing a SVG-based interactive diagram builder that would change the app url as I selected elements therein.
What I did was to add a global event handler that would fix all url(#...) inline styles in any <path> element found in the page:
$rootScope.$on 'fixSVGReference', ->
$('path').each ->
$path = $ this
if (style = $path.attr 'style')?
$path.attr 'style', style.replace /url\([^)#]*#/g, "url(#{location.href}\#"
Then trigger this handler in key places, like when the app state changes (I'm using ui-router)
$rootScope.$on '$stateChangeSuccess', ->
$timeout (-> $rootScope.$emit 'fixSVGReference'), 5
As well as anywhere where I know there'd be new/updated paths like these. Here, the $timeout thing is to account for the fact that the DOM nodes really are changed asynchronously sometime after the $stateChangeSuccess event is triggered.