'D3 adding tooltip to multi-line chart

I am fairly new to javascript and D3, I am trying to create a tooltip that displays a vertical line and circles on that line along with the value of data in each line. any help would be greatly appreciated ...


here is what I have got so far

I am fairly new to javascript and D3, I am trying to create a tooltip that displays a vertical line and circles on that line along with the value of data in each line. any help would be greatly appreciated ...

here is what I have got so far


function init() {
var formatDate, dataset, header, xScale, yScale, xAxis, yAxis, svg, coalConsLine,
    gasConsLine, hydroConsLine, oilConsLine, solarConsLine, windConsLine, toolTip, lineData;

//dimensions
const margin = { top: 30, right: 40, bottom: 70, left: 20 };
const width = 650 - margin.right - margin.left;
const height = 530 - margin.top - margin.bottom;

//format date
formatDate = d3.timeFormat("%Y");

//import data from csv file
d3.csv("Australian_Energy_Production_and_Consumption.csv", function (d) {
    return {
        //to create new Date object for each year
        date: new Date(d.year),

        //coal consumption
        coalCons: parseFloat(d.coal_consumption),

        //coal production
        coalProd: parseFloat(d.coal_production),

        //electricity generation
        elecPrdo: parseFloat(d.electricity_generation),

        //gas consumption
        gasCons: parseFloat(d.gas_consumption),

        //gas production
        gasProd: parseFloat(d.gas_production),

        //hydro consumption
        hydroCons: parseFloat(d.hydro_consumption),

        //oil consumption
        oilCons: parseFloat(d.oil_consumption),

        //oil production
        oilProd: parseFloat(d.oil_production),

        //solar energy consumption
        solarCons: parseFloat(d.solar_consumption),

        //wind energy consumption
        windCons: parseFloat(d.wind_consumption)
    }
}).then(function (data) {

    dataset = data;
    MultiLineChart(dataset);

});

function MultiLineChart() {
    //chart base
    svg = d3.select("body")
        .append("svg")
        .attr("width", width + margin.right + margin.left)
        .attr("height", height + margin.top + margin.bottom)
        .append('g')
        .attr("transform", "translate(" + margin.left + "," + margin.top + ")");

    //append header group
    header = svg.append('g')
        .attr("class", "chartHeader")
        .attr("class", "mainHeader")
        .attr("transform", "translate(23," + -margin.top * 0.5 + ")")
        .append("text");

    //append text to header group
    header.append("tspan")
        .text("Australian Energy Consumption by Energy Source");

    header.append("tspan")
        .attr("class", "subHeading")
        .attr("x", 0)
        .attr("y", 15)
        .text("Measured in Terawatt hour (TWh) from 2000-2019")

    xScale = d3.scaleTime()
        .domain([
            d3.min(dataset, function (d) { return d.date; }),
            d3.max(dataset, function (d) { return d.date; })])
        .nice() //makes scale end in round number, in this case will end in 2020 instead of 2019
        .range([0, width]);

    xAxis = d3.axisBottom()
        .ticks(d3.timeYear.every(1))
        .scale(xScale);

    yScale = d3.scaleLinear()
        .domain([0, d3.max(dataset, function (d) {
            return Math.max(d.coalCons, d.gasCons, d.hydroCons, d.oilCons, d.solarCons, d.windCons)
        })])
        .nice() 
        .range([height, 0]);

    yAxis = d3.axisLeft()
        .ticks(10)
        .scale(yScale);

    svg.append("g")
        .attr("class", "axis")
        .attr("class", "Xaxis")
        .attr("transform", "translate(" + margin.left + "," + height + ")") 
        .call(xAxis);

    svg.append("g")
        .attr("class", "axis")
        .attr("transform", "translate(" + margin.left + ", 0)") 
        .call(yAxis);

    //coal energy consumption line genetator        
    coalConsLine = d3.line()
        .x(function (d) { return xScale(d.date); })
        .y(function (d) { return yScale(d.coalCons); });

    //Creating the coal energy consumption line
    svg.append("path")
        .datum(dataset)
        .attr("class", "coalConsLine")
        .attr("class", "consLines")
        .attr("transform", "translate(" + margin.left + ", 0)")
        .attr("d", coalConsLine)
        .style("stroke", "#010E13");

    //gas energy consumption line genetator        
    gasConsLine = d3.line()
        .x(function (d) { return xScale(d.date); })
        .y(function (d) { return yScale(d.gasCons); });

    //Creating the gas energy consumption line
    svg.append("path")
        .datum(dataset)
        .attr("class", "gasConsLine")
        .attr("class", "consLines")
        .attr("transform", "translate(" + margin.left + ", 0)")
        .attr("d", gasConsLine)
        .style("stroke", "#ffa600");

  
    toolTip = d3.selectAll(".toolTip");

    //define lineData
    lineData = d3.select(this).data()[0];

    function mouseover() {
        toolTip
            .style('left', d3.event.clientX + 10 + 'px')
            .style('top', d3.event.clientY + 5 + 'px')
            .style('opacity', 0.97)

        //I don't know how to get the data value
        toolTip.select('.year').html("year " + lineData.date);

    }

    function mousemove() {
        toolTip
            .style('left', d3.event.clientX + 13 + 'px')
            .style('top', d3.event.clientY + 5 + 'px')
    }

    function mouseout() {
        toolTip.style('opacity', 0)
    }

    d3.selectAll(".consLines")
        .on("mouseover", mouseover)
        .on('mousemove', mousemove)
        .on('mouseout', mouseout);


}

}

window.onload = init;



Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source