Чтобы ответить на ваш вопрос, ваши кнопки не могут получить доступ к update
, потому что это не входит в их область действия. Только данные в createSvg
могут получить доступ к update
. Один из вариантов - исключить функцию update
, но тогда, поскольку update
зависит от нескольких переменных, вам нужно либо сделать переменные глобальными, либо передать их.
Кстати, я думаю, вы неправильно используете Vue, и из предоставленного вами кода он не делает ничего полезного, т.е. createSvg
не будет реактивным, потому что вы не определили any data
.
Я включил рабочий фрагмент ниже, в котором используется Vue по назначению. Я настоятельно рекомендую прочитать документацию .
var app = new Vue({
el: "#app",
data: () => {
return {
data1: [{
ser1: 0.3,
ser2: 4
},
{
ser1: 2,
ser2: 16
},
{
ser1: 3,
ser2: 8
}
],
data2: [{
ser1: 1,
ser2: 7
},
{
ser1: 4,
ser2: 1
},
{
ser1: 6,
ser2: 8
}
],
margin: {
top: 10,
right: 30,
bottom: 30,
left: 50
},
width: null,
height: null
}
},
mounted() {
this.width = 460 - this.margin.left - this.margin.right;
this.height = 400 - this.margin.top - this.margin.bottom;
this.createSvg();
},
methods: {
createSvg() {
var svg = d3.select("#my_dataviz")
.append("svg")
.attr("width", this.width + this.margin.left + this.margin.right)
.attr("height", this.height + this.margin.top + this.margin.bottom)
.attr("fill", "blue")
.append("g")
.attr("transform",
"translate(" + this.margin.left + "," + this.margin.top + ")");
var x = d3.scaleLinear().range([0, this.width]);
var xAxis = d3.axisBottom().scale(x);
svg.append("g")
.attr("transform", "translate(0," + this.height + ")")
.attr("class", "myXaxis")
var y = d3.scaleLinear().range([this.height, 0]);
var yAxis = d3.axisLeft().scale(y);
svg.append("g")
.attr("class", "myYaxis");
this.update(svg, x, y, xAxis, yAxis, this.data1)
},
updateData(data) {
var svg = d3.select("#my_dataviz");
var x = d3.scaleLinear().range([0, this.width]);
var xAxis = d3.axisBottom().scale(x);
var y = d3.scaleLinear().range([this.height, 0]);
var yAxis = d3.axisLeft().scale(y);
this.update(svg, x, y, xAxis, yAxis, data);
},
update(svg, x, y, xAxis, yAxis, data) {
// Create the X axis:
x.domain([0, d3.max(data, function(d) {
return d.ser1
})]);
svg.selectAll(".myXaxis").transition()
.duration(3000)
.call(xAxis);
// create the Y axis
y.domain([0, d3.max(data, function(d) {
return d.ser2
})]);
svg.selectAll(".myYaxis")
.transition()
.duration(3000)
.call(yAxis);
// Create a update selection: bind to the new data
var u = svg.selectAll(".lineTest")
.data([data], function(d) {
return d.ser1
});
// Updata the line
u
.enter()
.append("path")
.attr("class", "lineTest")
.merge(u)
.transition()
.duration(3000)
.attr("d", d3.line()
.x(function(d) {
return x(d.ser1);
})
.y(function(d) {
return y(d.ser2);
}))
.attr("fill", "none")
.attr("stroke", "steelblue")
.attr("stroke-width", 2.5)
}
}
});
<!DOCTYPE html>
<meta charset="utf-8">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://d3js.org/d3.v4.js"></script>
<div id="app">
<button @click="updateData(data1)">Dataset 1</button>
<button @click="updateData(data2)">Dataset 2</button>
<div id="my_dataviz"></div>
</div>