I have implemented a zoom function for my chart, where one can zoom into a certain area of the chart by dragging the area and releasing it. My fiddle is accessible here.
The zoom function is working correctly for the blue line as both the blue line and the left axis is being updated. However, the right axis is not being updated while the red line is zoomed in. I have hardcoded a domain from 0 to 200 for the right axis so whenever I zoom in the domain goes from 0 to 200 instead of the correct zoomed in domain. What should be the code for the domain for the axis on the right so that it gets updated during the zoom? Any help is greatly appreciated!
var data = [ {x: 0, y: 0, y1: 0}, {x: 1, y: 30, y1: 100}, {x: 2, y: 40, y1: 200},
{x: 3, y: 60, y1: 300}, {x: 4, y: 70, y1: 400}, {x: 5, y: 90, y1: 500} ];
const margin = {
left: 20,
right: 20,
top: 20,
bottom: 80
};
const svg = d3.select('svg');
svg.selectAll("*").remove();
const width = 200 - margin.left - margin.right;
const height = 200 - margin.top - margin.bottom;
const g = svg.append('g').attr('transform', `translate(${margin.left},${margin.top})`);
var x = d3.scaleLinear()
.domain([0, d3.max(data, function(d){ return d.x; })])
.range([0,width])
.nice();
var y = d3.scaleLinear()
.domain([0, d3.max(data, function(d){ return d.y; })])
.range([0,height])
.nice();
var y1 = d3.scaleLinear()
.domain([0, d3.max(data, function(d) { return d.y1; })])
.range([0, height])
.nice();
const xAxis = d3.axisTop()
.scale(x)
.ticks(5)
.tickPadding(3)
.tickSize(-height)
const yAxis = d3.axisLeft()
.scale(y)
.ticks(5)
.tickPadding(3)
.tickSize(-width);
const yAxis1 = d3.axisRight()
.scale(y1)
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(20,20)")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.attr("transform", "translate(20,20)")
.call(yAxis);
svg.append("g")
.attr("class", "y1 axis")
.attr("transform", "translate(185,20)")
.call(yAxis1);
var lineFunction = d3.line()
.x(function(d) {return x(d.x); })
.y(function(d) {return y(d.y); })
.curve(d3.curveLinear);
var lineFunctionOne = d3.line()
.x(function(d) {return x(d.x); })
.y(function(d) {return y1(d.y1); })
.curve(d3.curveLinear);
//defining and plotting the lines
var path = g.append("path")
.attr("class", "path1")
.attr("id", "blueLine")
.attr("d", lineFunction(data))
.attr("stroke", "blue")
.attr("stroke-width", 2)
.attr("fill", "none")
.attr("clip-path", "url(#clip)");
var path1 = g.append("path")
.attr("class", "path2")
.attr("id", "redLine")
.attr("d", lineFunctionOne(data))
.attr("stroke", "red")
.attr("stroke-width", 2)
.attr("fill", "none")
.attr("clip-path", "url(#clip)");
//************* Zoom ***************
//add brushing
var brush = d3.brush().extent([[0, 0], [width, height]]).on("end", brushended),
idleTimeout,
idleDelay = 350;
g.append("g")
.attr("class", "brush")
.call(brush);
// Add a clipPath: everything out of this area won't be drawn when chart is zoomed in
var clip = svg.append("defs").append("svg:clipPath")
.attr("id", "clip")
.append("svg:rect")
.attr("width", width)
.attr("height", height)
.attr("x", 0)
.attr("y", 0);
function brushended() {
var s = d3.event.selection;
//If no selection, re-initialize chart on double click. Otherwise, update x-axis and y-axis domain
if (!s) {
// This allows to wait a little bit
if (!idleTimeout) return idleTimeout = setTimeout(idled, 350);
x.domain(d3.extent(data, function (d) { return d.x; })).nice();
y.domain(d3.extent(data, function (d) { return d.y; })).nice();
y1.domain(d3.extent(data, function (d) { return d.y1; })).nice();
} else {
x.domain([s[0][0], s[1][0]].map(x.invert, x));
y.domain([s[0][1], s[1][1]].map(y.invert, y));
y1.domain([0, 200]); //hardcoded domain
//This removes the grey brush area as soon as the selection has been done
g.select(".brush").call(brush.move, null)
}
zoom();
}
function idled() {
idleTimeout = null;
}
function zoom() {
var t = svg.transition().duration(750);
svg.select(".x.axis").transition(t).call(xAxis);
svg.select(".y.axis").transition(t).call(yAxis);
svg.select(".y1.axis").transition(t).call(yAxis1);
svg.select(".path1").transition(t).attr("d", lineFunction(data));
svg.select(".path2").transition(t).attr("d", lineFunctionOne(data));
}