# 条形图

# 最基础版

//<script type="text/javascript" src="https://d3js.org/d3.v5.min.js"></script>
function create(width,height,rectWidth,rectPadding,padding,dataset){
	var svg = d3.select("body")
	.append("svg")
	.attr("width", width)
	.attr("height", height)
	
	//定义矩形比例尺
	 
	var yScale=d3.scaleLinear()
	.domain([0,d3.max(dataset)])
	.range([height-padding.top-padding.bottom,0]);
	var yAxis=d3.axisLeft().scale(yScale).ticks(5);
	// var yAxis=d3.axisLeft(yScale).ticks(5);
	svg.append("g")
	.attr("transform",`translate(${padding.top},${padding.left})`)
	.call(yAxis);
	 
	var xScale=d3.scaleBand()
	.domain(d3.range(dataset.length))
	.rangeRound([0,dataset.length*(rectWidth+(rectPadding/2))]);
	var xAxis=d3.axisBottom(xScale)
	.ticks(5);
	svg.append("g")
	.attr("transform",`translate(${padding.left},${height-padding.top})`)
	.call(xAxis);
	 
	//定义矩形
	var g=d3.selectAll("svg")
	.append("g")
	.attr("transform",`translate(${padding.top},${padding.left})`);
	 
	var graph=g.selectAll("rect")
	.data(dataset)
	.enter()
	.append("g");
	 
	graph.append("rect")
	.style("fill","#30dc76")
	.attr("x",function (d,i) {
	    return (i*rectWidth)+(i+1)*(rectPadding/2);
	})
	.attr("width",rectWidth-rectPadding/2)
	.attr("y",function (d) {
	    var min=yScale.domain()[0];
	    return yScale(min);
	})
	.attr("height",function(d,i){
	    return 0;
	})
	.transition()
	.duration(2000)
	.delay(function(d,i){
	    return i*40;
	})
	//.ease(d3.easeBackOut)
	.attr("y",function (d,i) {
	    return yScale(d)
	})
	.attr("height",function (d,i) {
	    return height-padding.top-padding.bottom-yScale(d);
	})
	 
	graph.append("text")
	.style("fill", "orange")
	.attr("x", function (d, i) {
	    return (i * rectWidth) + (i + 1) * (rectPadding / 2);
	})
	.attr("dx", 10)
	.attr("dy",-10)
	.attr("y", function (d) {
	    var min = d3.min(dataset);
	    return yScale(min)
	})
	.text(function (d) {
	    return d
	})
	.transition()
	.duration(2000)
	.delay(function (d, i) {
	    return i * 40;
	})
	.attr("y", function (d, i) {
	    return yScale(d);
	})
}
//参数 svg宽,高,矩形宽度,间隔,svgpadding,要插入的数据
create(600,600,50,10,{top:40,bottom:40,left:40,right:40},[45, 70, 12, 79, 4, 127, 33, 150])

# 条形图修改

<html>

	<style>
		
		body {
		  font-family: 'Open Sans', sans-serif;
		}

		div#layout {
		  text-align: center;
		}

		div#container {
		  width: 1000px;
		  height: 600px;
		  margin: auto;
		  background-color: #2F4A6D;
		}

		svg {
		  width: 100%;
		  height: 100%;
		}

		text {
		  font-size: 12px;
		  fill: #fff;
		}

		path {
		  stroke: gray;
		}

		line {
		  stroke: gray;
		}

		line#limit {
		  stroke: #FED966;
		  stroke-width: 3;
		  stroke-dasharray: 3 6;
		}

		.grid path {
		  stroke-width: 0;
		}

		.grid .tick line {
		  stroke: #9FAAAE;
		  stroke-opacity: 0.3;
		}

		text.divergence {
		  font-size: 14px;
		  fill: #2F4A6D;
		}

		text.value {
		  font-size: 14px;
		}

		text.title {
		  font-size: 22px;
		  font-weight: 600;
		}

		text.label {
		  font-size: 14px;
		  font-weight: 400;
		}

		text.source {
		  font-size: 10px;
		}
	</style>
	<body>
		<div id='layout'>
	  <!-- <h2>Bar chart example</h2> -->
	  <div id='container'>
	    <svg />
	  </div>
	</div>
		</body>
	<script src="https://d3js.org/d3.v5.min.js"></script>
	<script>
	const sample = [
    {
      language: 'Rust',
      value: 103.9,
      color: 'orange'
    },
    {
      language: 'Kotlin',
      value: 75.1,
      color: '#00a2ee'
    },
    {
      language: 'Python',
      value: 68.0,
      color: '#fbcb39'
    },
    {
      language: 'TypeScript',
      value: 67.0,
      color: '#007bc8'
    },
    {
      language: 'Go',
      value: 65.6,
      color: '#65cedb'
    },
    {
      language: 'Swift',
      value: 65.1,
      color: '#ff6e52'
    },
    {
      language: 'JavaScript',
      value: 61.9,
      color: '#f9de3f'
    },
    {
      language: 'C#',
      value: 60.4,
      color: '#5d2f8e'
    },
    {
      language: 'F#',
      value: 59.6,
      color: '#008fc9'
    },
    {
      language: 'Clojure',
      value: 59.6,
      color: '#507dca'
    }
];

const svg = d3.select('svg');
const svgContainer = d3.select('#container');

const margin = 80;
const width = 1000 - 2 * margin;
const height = 600 - 2 * margin;

const chart = svg.append('g')
      .attr('transform', `translate(${margin}, ${margin})`);

const xScale = d3.scaleBand()
      .range([0, width])
      .domain(sample.map((s) => s.language))
      .padding(0.4)

const yScale = d3.scaleLinear()
      .range([height, 0])
      .domain([0, 105]);

const makeYLines = () => d3.axisLeft()
      .scale(yScale)

chart.append('g')
     .attr('transform', `translate(0, ${height})`)
     .call(d3.axisBottom(xScale));

chart.append('g')
     .call(d3.axisLeft(yScale));

chart.append('g')
     .attr('class', 'grid')
     .call(makeYLines()
        .tickSize(-width, 0, 0)
        .tickFormat('')
     )

const barGroups = chart.selectAll()
      .data(sample)
      .enter()
      .append('g')



barGroups
   .append('rect')
   .attr('class', 'bar')
   .attr('x', (g) => xScale(g.language))
   .attr('y', (g) => 440)
   .attr("height",()=>0)
  
   .attr('width', xScale.bandwidth())
   .attr("fill",(g)=>{return g.color})
   .transition()
   .delay(function(d,i){
   	return i*200;
   })
   .duration(2000)
    .attr('height', (g) => height - yScale(g.value))
   .attr('y', (g) => yScale(g.value))
   d3.selectAll("rect")
   .on('mouseenter', function (actual, i) {
      d3.selectAll('.value')
        .attr('opacity', 0)
      d3.select(this)
        .transition()
        .duration(300)
        .attr('opacity', 0.6)
        .attr('x', (a) => xScale(a.language) - 5)
        .attr('width', xScale.bandwidth() + 10)

      const y = yScale(actual.value)

            line = chart.append('line')
              .attr('id', 'limit')
              .attr('x1', 0)
              .attr('y1', y)
              .attr('x2', width)
              .attr('y2', y)
  
      barGroups.append('text')
          .attr('class', 'divergence')
          .attr('x', (a) => xScale(a.language) + xScale.bandwidth() / 2)
          .attr('y', (a) => yScale(a.value) + 30)
          .attr('fill', 'white')
          .attr('text-anchor', 'middle')
          .text((a, idx) => {
            const divergence = (a.value - actual.value).toFixed(1)
            
            let text = ''
            if (divergence > 0) text += '+'
            text += `${divergence}%`

            return idx !== i ? text : '';
          })
    })
   .on('mouseleave', function() {
      d3.selectAll('.value')
        .attr('opacity', 1)
      d3.select(this)
        .transition()
        .duration(300)
        .attr('opacity', 1)
        .attr('x', (a) => xScale(a.language))
        .attr('width', xScale.bandwidth())
      
      chart.selectAll('#limit').remove()
      chart.selectAll('.divergence').remove()
   })

barGroups 
      .append('text')
      .attr('class', 'value')
      .attr('x', (a) => xScale(a.language) + xScale.bandwidth() / 2)
      .attr('y', (a) => 420)
      .attr('text-anchor', 'middle')
	  .transition()
	  .delay(function(d,i){
	  	return i*200;
	  })
	  .duration(2000)
	  .attr('y', (a) => yScale(a.value) + 30)
      .text((a) => `${a.value}%`)
    
    svg
      .append('text')
      .attr('class', 'label')
      .attr('x', -(height / 2) - margin)
      .attr('y', margin / 2.4)
      .attr('transform', 'rotate(-90)')
      .attr('text-anchor', 'middle')
      .text('Love meter (%)')

    svg.append('text')
      .attr('class', 'label')
      .attr('x', width / 2 + margin)
      .attr('y', height + margin * 1.7)
      .attr('text-anchor', 'middle')
      .text('Languages')

    svg.append('text')
      .attr('class', 'title')
      .attr('x', width / 2 + margin)
      .attr('y', 40)
      .attr('text-anchor', 'middle')
      .text('Most loved programming languages in 2018')

    svg.append('text')
      .attr('class', 'source')
      .attr('x', width - margin / 2)
      .attr('y', height + margin * 1.7)
      .attr('text-anchor', 'start')
      .text('Source: Stack Overflow, 2018')
	</script>
</html>

# 总结
  1. path修改的是刻度尺的线条
path {
  stroke: gray;
}
  1. line则是修改刻度尺上刻度的样式
line {
  stroke: gray;
}
  1. stroke-width控制线条宽度 stroke-dasharray控制虚线样式 stroke-opacity控制透明度 stroke-dashoffset偏移量
line#limit {
  stroke: #FED966;
  stroke-width: 3;
  stroke-dasharray: 3 6;
  stroke-dashoffset: 60
}

.grid .tick line {
  stroke: #9FAAAE;
  stroke-opacity: 0.3;
}
  1. text-anchor 文本锚点属性被用来描述该文本与所给点的对齐方式 (开头、中间、末尾对齐)
  2. 矩形宽度
const xScale = d3.scaleBand()
      .range([0, width])
      .domain(sample.map((s) => s.language))
      .padding(0.4)
console.log(xScale.bandwidth(),xScale.paddingInner(),xScale.paddingOuter())
最后更新: 10/24/2019, 5:25:53 PM