Hi Scott,
I was confusing myself because I wasn't offseting the bars correctly
to account for the negative values. They were all positioned on the
left. So I figured it out. Here's the code I came up with, not sure
it's the most efficient. But mostly working.
<!DOCTYPE html>
<html>
<head>
<title>Bar Chart</title>
<script type="text/javascript" src="../js/d3.js"></script>
<style type="text/css">
body{ font: 10px sans-serif; color: blue;}
.line {stroke: black; stroke-width: 1;}
.axis {shape-rendering: crispEdges;}
.axis path {fill: none;}
.x.axis line {stroke: #000000;stroke-opacity: .2;}
.y.axis path {stroke: black;}
</style>
<script type="text/javascript">
var $barh = 20;
</script>
</head>
<body>
<script type="text/javascript">
//FIRST CHART OVERALL
var data = [-16,40,87,7];//min, median, max, curVal
var curVal = 7;
var m = [30, 30, 30, 30],
w = 400 + m[1] + m[3],
h = $barh*data.length + m[0] + m[2];
var $midpoint = w/2;
var format = d3.format(",.0f");
var x = d3.scale.linear().range([0,w]);
//var y = d3.scale.ordinal().rangeBands([0, $barh * data.length]);
var xAxis = d3.svg.axis().scale(x).orient("bottom").tickSize(-
h).ticks(4);
var svg = d3.select("body").append("svg")
.attr("width", w+m[1]+m[3])
.attr("height", h)
.append("g")
.attr("transform", "translate(" + m[3] + "," + m[0] + ")");
// Set the scale domain.
x.domain([-100, 100]);
//y.domain(data);
var bar = svg.selectAll("g.bar")
.data(data)
.enter().append("g")
.attr("class", "bar")
.attr("transform", function(d,i) {
if(d<0){
return "translate("+Math.abs(x(d))+"," + 0 + ")";
} else if(d>0){return "translate("+$midpoint+"," + 0 + ")";
} else {return "translate(0," + 0 + ")";}
})
bar.append("rect")
.attr("width", function(d) {
if(d<0){
return Math.abs($midpoint - x(d));
} else if(d>0){return x(d)-$midpoint;
} else {return x(d);}
})
.attr("height", $barh)
.attr("fill", function(d) {
if(d<=0){
return "#F26F68";
} else { return "#6E8C8C";}
})
.attr("opacity", function(d) {
if(d==curVal){
return 1;
} else { return .1;}
})
bar.append("text")
.attr("class", "value")
.style("font-weight", function(d){
if (d==curVal){ return "bold";}
})
.attr("x", function(d) {
if(d<0){
return -2;//-2 is a padding workaround
} else if(d>0){return x(d)-$midpoint-2;}
})
.attr("y", $barh / 2)
.attr("dx", -3) //would be padding but is being overridden by x
value
.attr("dy", ".35em")
.attr("text-anchor", "end")
.text(function(d) { return format(d); })
var line = svg.selectAll("svg")
.data(data)
.enter().append("line")
.attr("class", "line")
.attr("x1", function(d) {
if(d<0){
return Math.abs(x(d));
} else if(d>0){return x(d);}
})
.attr("x2", function(d) {
if(d<0){
return Math.abs(x(d));
} else if(d>0){return x(d);}
})
.attr("y1", 0)
.attr("y2", $barh)
.style("stroke-width", function(d) {
if (d == curVal) {
return 2;
}
})
.style("stroke-dasharray", function(d) {
if (d !== curVal) {
return "3,3,2";
} else {
return "6,.1";
}
})
//END OF FIRST CHART OVERALL
svg.append("g")
.attr("class", "x axis")
.attr("transform", function(d) { return "translate(0," + (h-m[0]-
m[2]) + ")"; })
.call(xAxis);
</script>
</body>
</html>
> >> I'm not sure what you mean by abulletchart, but you can use this principle to style each of the SVG elements however you like.
>
> >> Scott
>
> >> On Feb 13, 2012, at 3:09 PM, Manisha wrote:
>
> >>> Hi,
>
> >>> I'm trying to make a custombulletchart that would show negative
> >>> values, as well as positive. So the range would be from -100 through
> >>> 100. And the shading on the negative half of thebulletwould be