2017-10-14 52 views
2

我已經上傳了block(固定),您可以切換排序功能。如何自動排序一個條形圖與切換功能

現在我想添加的是某種if語句,當複選框打開時,當它打開時,我希望酒吧在您更改年份或類別時自動排序,並且當您再次切換時停止自動-sorting。

我想到了一個簡單的

if (document.getElementsByClassName('myCheckbox').checked) { 
    change(); 
} 

update功能會工作,但沒有任何反應。

任何幫助表示讚賞!

+0

由於'getElementsByClassName'返回一個列表,它必須是:'如果(document.getElementsByClassName(「myCheckbox」)[0 ] .checked){etc ...',以'[0]'作爲索引。但是,我不會將此作爲答案發布,因爲您必須重構「更改」功能才能使其工作。 –

+0

我知道,爲了使它工作,您需要更改多少代碼?如果有幫助,我可以發佈一個更簡單的例子。 –

+0

我添加了一個答案,但我很快就會將其刪除:排序工作不正常。請在刪除之前複製答案的詳細信息。 –

回答

1

我開始回答你的直接問題,但很快就意識到你的代碼需要一點重構。你有太多的複製/粘貼冗餘代碼和繪製太多東西。當使用d3進行編碼時,您應該嘗試執行所有繪圖的單個功能。

這是code running

這裏是新的更新功能的片段來統治他們:

function update() { 

    file = d3.select('#year').property('value') == 'data2017' ? 'data.csv' : 'data2.csv'; 
    catInt = d3.select('#category').property('value'); 

    d3.csv(file, type, function(error,data) { 

     if(error) throw error; 

     var sortIndex = data.map(function(d){ return d.month}); 

     // Update domain 
     y.domain([0, d3.max(data, function(d) { 
       return d["Category" + catInt]; }) 
     ]).nice(); 

     // Update axis 
     g.selectAll(".axis.axis--y").transition() 
      .duration(750) 
      .call(yAxis); 
     g.selectAll(".axis.grid--y").transition() 
      .duration(750) 
      .call(yGrid); 

     // Sums and averages 
     let sumOfAll = d3.sum(data, function(d) { 
      return d["Category" + catInt]; 
     }); 
     let avgValue = d3.sum(data, function(d) { 
      return d["Category" + catInt]; 
     })/data.length; 

     //sort data 
     data.sort(d3.select("#myCheckbox").property("checked") 
      ? function(a, b) { return b["Category" + catInt] - a["Category" + catInt]; } 
      : function(a, b) { return sortIndex.indexOf(a.month) - sortIndex.indexOf(b.month);}) 

     // set x domain 
     x.domain(data.map(function(d) { return d.month; })); 

     g.selectAll(".axis.axis--x").transition() 
     .duration(750) 
     .call(xAxis); 

     // Update rectangles 
     let bars = g.selectAll(".barEnter") 
      .data(data, function(d){ 
      return d.month; 
      }); 

     bars = bars 
      .enter() 
      .append("rect") 
      .attr("class", "barEnter") // Enter data reference 
      .attr("width", x.bandwidth()) 
      .merge(bars); 

     bars.transition() 
      .duration(750) 
      .attr("height", function(d) { 
      return height - y(d["Category" + catInt]); 
      }) 
      .attr("x", function(d) { 
      return x(d.month); 
      }) 
      .attr("y", function(d) { 
      return y(d["Category" + catInt]); 
      }); 

    bars.exit().remove(); 

     // Update text on rectangles 
     let textUpdate = g.selectAll(".textEnter") 
      .data(data, function(d){ 
      return d.month; 
      }); 

     textUpdate = textUpdate.enter() 
     .append("text") 
     .style("text-shadow","1px 1px #777") 
     .attr("class", "textEnter") // Enter data reference 
     .attr("text-anchor","middle") 
     .attr("font-size",11) 
     .attr("fill","#fff") 
     .merge(textUpdate); 

     textUpdate.transition() 
      .duration(750) 
      .attr("y", function(d) { 
       return y(d["Category" + catInt]) + 15; 
       }) 
      // Update text value 
      .text(function(d) { 
       return d["Category" + catInt]; 
      }) 
      .attr("x", function(d) { 
      return x(d.month) + x.bandwidth()/2; 
     }) 

     // Update sum and avg value 
     g.selectAll("#totalValue").transition() 
      .duration(750) 
      .text(sumOfAll + " Category " + catInt) 
     g.selectAll("#avgValue").transition() 
      .duration(750) 
      .text(formatValue(avgValue)) 
    }); 
} 
+0

非常感謝!我更新了我的[Block](https://bl.ocks.org/LemoNode/73dbb9d6a144476565386f48a2df2e3b)並將條件運算符更改爲if語句,這是否會使代碼變得冗餘?多重三元評估仍然更可取? (如果你想添加另一個csv文件) –

+1

@RobertAndersson,不,你的if語句是好的。對於更多的兩個選項,我會使用一個嵌套三元組。 – Mark