javascript - Aynı <canvas> içinde başka bir grafiği yeniden çizmek için chart.js çubuk grafiğini yok et


Chart.js kütüphanesini bir çubuk grafiği çizmek için kullanıyorum, her şey düzgün çalışıyor, ama şimdi çubuk grafiğini yok etmek ve aynı canvas üzerinde bir çizgi grafiği yapmak istiyorum. Canvas'ı temizlemek için bu iki yöntemi denedim:

var grapharea = document.getElementById("barChart").getContext("2d");

grapharea.destroy();

var myNewChart = new Chart(grapharea, { type: 'radar', data: barData, options: barOptions });

ikinci yol:

var grapharea = document.getElementById("barChart").getContext("2d");

grapharea.clear();

var myNewChart = new Chart(grapharea, { type: 'radar', data: barData, options: barOptions });

Doğru mu çağırıyorum? OnButtonClick'te aynı kanvası kullanan bu fonksiyonu çağırıyorum.

Cevap #1

Aynı tuval üzerinde başka bir grafik çizebilmek için kullanılacak doğru yöntem .destroy()'dır. Bunu önceden oluşturulmuş grafik nesnesinde çağırmalısınız. Her iki grafik için aynı değişkeni de kullanabilirsiniz.

var grapharea = document.getElementById("barChart").getContext("2d");

var myChart = new Chart(grapharea, { type: 'bar', data: barData, options: barOptions });

myChart.destroy();

myChart = new Chart(grapharea, { type: 'radar', data: barData, options: barOptions });

Belgelere doğrudan (Prototip Metodları altında):

.yoket()

Oluşturulan herhangi bir grafik örneğini yok etmek için bunu kullanın. Bu, Chart.js içinde grafik nesnesine saklanan herhangi bir referansı ve Chart.js tarafından eklenen ilişkili olay dinleyicilerini temizleyecektir. Bu, tuval yeni bir grafik için tekrar kullanılmadan önce çağrılmalıdır.

// Example from the docs
var myLineChart = new Chart(ctx, config);
// Destroys a specific chart instance
myLineChart.destroy();

Bu yöntemin, yeni bir grafik için tuval yeniden kullanılmadan önce çağrılması gerektiğini açıkça belirtir.

.clear() aynı bölümde daha sonra, “grafik tuvalini temizleyecek. Animasyon kareleri arasında dahili olarak yoğun bir şekilde kullanılır, ancak sizin işinize de yarayabilir” şeklinde bahsedilen bir fonksiyon olarak geçmektedir. Bu yöntemi çağırdıktan sonra grafik hâlâ aktif olacak, bu nedenle tuvali tamamen yeni bir grafik için yeniden kullanmak istiyorsanız bu yöntemi çağırmanız uygun değildir.

Dürüst olmak gerekirse, sizin durumunuz gibi vakalarda, canvas öğemi sarmak için sık sık bir konteyner div kullandım ve yeni bir grafik oluşturmam gerektiğinde, bu div içine yeni bir canvas öğesi yerleştirdim. Ardından bu yeni oluşturulan canvas'ı yeni grafik için kullandım. Eğer herhangi bir garip davranışla karşılaşırsanız, büyük olasılıkla mevcut grafikten önce canvas'ı işgal eden grafiklerle ilgili olabilir, bu yaklaşımı aklınızda bulundurun.

Cevap #2

ChartJs'in getChart(key) - eğer grafik zaten oluşturulmuşsa, verilen anahtardan grafik örneğini bulur.

  • Anahtar bir dize ise, Chart için Canvas öğesinin kimliği olarak yorumlanır.
  • Anahtar ayrıca bir CanvasRenderingContext2D veya bir HTMLDOMElement olabilir.

Not: Eğer herhangi bir Grafik bulunamazsa, bu tanımsız döndürecektir. Eğer grafik örneği bulunursa, bu grafiğin daha önce oluşturulmuş olması gerektiğini gösterir.

// JS - Destroy exiting Chart Instance to reuse <canvas> element
let chartStatus = Chart.getChart("myChart"); // <canvas> id
if (chartStatus != undefined) {
  chartStatus.destroy();
}
//-- End of chart destroy   

var chartCanvas = $('#myChart'); //<canvas> id
chartInstance = new Chart(chartCanvas, {
  type: 'line',
  data: data
});
<!-- HTML -Line Graph - Chart.js -->
<div class="container-fluid" id="chartContainer">
  <canvas id="myChart" width="400" height="150">   </canvas>
</div>

Bu yaklaşım, JS içinden bir DIV’e Canvas öğesi eklemek için sil - oluştur - ekle işlemlerinden sizi kurtarır.

Cevap #3

Her grafik çağrısından sonra tuvali kaldırın, bu benim için işe yaradı

$("canvas#chartreport").remove();
$("div.chartreport").append('<canvas id="chartreport" class="animated fadeIn" height="150"></canvas>');
var ctx = document.getElementById("chartreport").getContext("2d");
chartreport= new Chart(ctx, { .... });

Cevap #4

Belki daha iyi bir yol vardı, ama hiçbir cevap bana uygun değildi.

document.querySelector("#chartReport").innerHTML = '<canvas id="myChart"></canvas>';

benim HTML kısmım

<div class="col-md-6 col-md-offset-3">
     <div id="chartReport">
         <canvas id="myChart"></canvas>
     </div>
</div>

Cevap #5

ChartJS v2.x için, canvas'ı açıkça yok edip yeniden oluşturmadan grafik verilerini güncellemek için update() kullanabilirsiniz.

var chart_ctx = document.getElementById("chart").getContext("2d");

var chart = new Chart(chart_ctx, {
    type: "pie",
    data: {},
    options: {}
});

$.ajax({
    ...
}).done(function (response) {
    chart.data = response;
    chart.update();
});

Cevap #6

2020 için basit düzenleme:

Bu benim için işe yaradı. Grafiği global yapmak için pencerede sahiplenin (Deklarasyonu var myChart yerine window.myChart olarak değiştirin)

Chart değişkeninin zaten Chart olarak başlatılıp başlatılmadığını kontrol edin, eğer öyleyse, onu yok edin ve yeni bir tane oluşturun, hatta aynı isimle bir tane daha oluşturabilirsiniz. Aşağıda kod var:

if(window.myChart instanceof Chart)
{
    window.myChart.destroy();
}
var ctx = document.getElementById('myChart').getContext("2d");

Umarım işe yarar!

İlgili makaleler