2014-01-08 4 views
0

В настоящее время у меня есть 2 диаграммы, один поверх другого. То, что набор данных связан с верхним и нижним, определяется динамически. Я хочу также определить цвет верхней и нижней диаграммы, основанный на том, какой набор данных используется. И.Е. один набор данных связан с мужчинами, один с самками, женщины должны быть красными, мужчины - синими. То, как я делаю это прямо сейчас, как это:d3 проверить, какой набор данных в функции

bar2.append("rect") 
    .attr("height", function(d) { return heightBottom - bottomScale(d) }) 
    .attr("width", barWidth - 1) 
    .style("fill", function(d) { 
     return dataMale.indexOf(d) !== -1 ? "blue" : "red"; 
    }); 

Но в том случае, когда оба набора данных имеют одинаковое значение, то может получить перепутано. Есть лучший способ сделать это? Вот код:

var dataMale = [577661, 1552631, 447955, 55570, 10391, 3146, 24462]; 
var dataFemale = [221395, 1156634, 151738, 20167, 5157, 1598, 7545]; 

var dataTop, dataBottom; 
var maleMax = d3.max(dataMale), femaleMax = d3.max(dataFemale); 
var maleFemaleTotal = maleMax + femaleMax; 
var maleMaxOfAll = maleMax > femaleMax; 



var ratioMale = maleMax/maleFemaleTotal; 
var ratioFemale = femaleMax/maleFemaleTotal; 

if (d3.max(dataMale) > d3.max(dataFemale)) { 
    dataTop = dataMale; 
    dataBottom = dataFemale; 
} else { 
    dataTop = dataFemale; 
    dataBottom = dataMale; 
} 

var width = 960, 
fullHeight = 550, 
wrapperHeight = fullHeight + 200, 
heightTop, 
heightBottom; 

if (maleMaxOfAll) { 
    heightTop = fullHeight * ratioMale; 
    heightBottom = fullHeight * ratioFemale; 
} else { 
    heightTop = fullHeight * ratioFemale; 
    heightBottom = fullHeight * ratioMale; 
} 

var topScale = d3.scale.linear() 
    .domain([0, d3.max(dataTop)]) 
    .range([heightTop, 0]); 

var bottomScale = d3.scale.linear() 
    .domain([0, d3.max(dataBottom)]) 
    .range([heightBottom, 0]); 

var axisScale = d3.scale.ordinal() 
    .domain(dataTop) 
    .rangeBands([0, width]); 

var axisScale2 = d3.scale.ordinal() 
    .domain(dataBottom) 
    .rangeBands([0, width]); 
    // .range([0, 960]); 

var chart = d3.select(".chart") 
    .attr("width", width) 
    .attr("height", wrapperHeight); 

var chart1 = chart.append("g") 
    .attr("class", "chart-one") 
    .attr("height", heightTop) 
    .attr("width", width); 


var chart2 = chart.append("g") 
    .attr("class", "chart-two") 
    .attr("transform", function() { return "translate(0," + (heightTop + 90) + ")"; }) 
    .attr("height", heightBottom) 
    .attr("width", width); 

var barWidth = width/dataMale.length; 

var bar = d3.select(".chart-one") 
    .selectAll("g") 
    .data(dataTop) 
    .enter().append("g") 
    .attr("class", "one") 
    .attr("transform", function(d, i) { return "translate(" + i * barWidth + ", 0)"; }); 

bar.append("rect") 
    .attr("y", function(d) { return topScale(d) + 50; }) 
    .attr("height", function(d) { return heightTop - topScale(d); }) 
    .attr("width", barWidth - 1) 
    .style("fill", function(d) { 
     return dataMale.indexOf(d) !== -1 ? "blue" : "red"; 
    }); 

var bar2 = d3.select(".chart-two") 
    .selectAll("g") 
    .data(dataBottom) 
    .enter().append("g") 
    .attr("class", "two") 
    .attr("transform", function(d, i) { return "translate(" + i * barWidth + ",0)"; }); 

bar2.append("rect") 
    .attr("height", function(d) { return heightBottom - bottomScale(d) }) 
    .attr("width", barWidth - 1) 
    .style("fill", function(d) { 
     return dataMale.indexOf(d) !== -1 ? "blue" : "red"; 
    }); 

var sharedAxis = d3.svg.axis() 
    .scale(axisScale) 
    .tickValues(dataTop); 

var xAxis = d3.svg.axis() 
    .scale(axisScale) 
    .tickValues(dataTop); 
    // .tickPadding([-10]); 
    // .orient("top"); 
var xAxis2 = d3.svg.axis() 
    .scale(axisScale) 
    .tickValues(dataTop) 
    .tickPadding([15]); 

var xAxis3 = d3.svg.axis() 
    .scale(axisScale) 
    .tickValues(dataTop) 
    .tickPadding(27); 

var xBotAxis = d3.svg.axis() 
    .scale(axisScale2) 
    .orient("top") 
    .tickValues(dataBottom); 

d3.select(".chart-one").append("g").attr("class", "axis").call(xAxis); 
d3.select(".chart-one").append("g").attr("class", "axis").call(xAxis2); 
d3.select(".chart-one").append("g").attr("class", "axis").call(xAxis3); 
d3.select(".chart").append("g").attr("transform", "translate(0," + (heightTop + 62) + ")").attr("class", "axis").call(sharedAxis); 

d3.select(".chart-two").append("g").attr("transform", "translate(0, " + (heightBottom + 25) + ")").attr("class", "axis").call(xBotAxis); 
d3.select(".chart-two").append("g").attr("transform", "translate(0, " + (heightBottom + 37) + ")").attr("class", "axis").call(xBotAxis); 
d3.select(".chart-two").append("g").attr("transform", "translate(0, " + (heightBottom + 49) + ")").attr("class", "axis").call(xBotAxis); 
+0

Я хотел бы сделать какие данные установить это часть данных, например имеют атрибут «тип». –

+0

может ли это испортить привязку данных? cuz im привязывает массив к группам? – natecraft1

+0

Не уверен, что вы имеете в виду, когда говорите, что вы привязываете массив к группам, но я не вижу, как это испортит ситуацию. –

ответ

1

Я бы сделал тип части данных. Если предположить, что вы добавите его в качестве нового атрибута gender, вы могли бы сделать что-то вроде

var dataTop = male; 
// more code 
var bar = d3.select(".chart-one") 
    .selectAll("g") 
    .data(dataTop) 
    .enter().append("g"); 
bar.append("rect") 
    .style("fill", dataTop.gender == "male" ? "blue" : "red"); 
+0

Возможно, вам стоит добавить это {"values": array, "gender": "male"}; Не знаю, достаточно ли этот вопрос/ответ, чтобы помочь кому-либо. – natecraft1

+0

Вы можете иметь атрибуты в массиве, поэтому технически отдельный элемент 'values' не нужен. –

Смежные вопросы