Как я могу получить доступ к диаграмме Highcharts через DOM-контейнер


85

Когда я визуализирую диаграмму highcharts в контейнере div, как я могу получить доступ к объекту диаграммы через контейнер div? Я не хочу делать переменную диаграммы глобальной.

        var chart = new Highcharts.Chart({
            chart: {
                renderTo: "testDivId",
                                ...

Я хочу получить доступ к диаграмме вне контекста выше, как это (псевдокод), для вызова функций:

var chart = Highcharts.Chart("testDivId"); //access from id
chart.redraw();

Ответы:


139

Highcharts 3.0.1

Пользователи могут использовать плагин highcharts

var chart=$("#container").highcharts();

Highcharts 2.3.4

Прочтите из массива Highcharts.charts , для версии 2.3.4 и более поздних версий индекс диаграммы можно найти по данным на<div>

 var index=$("#container").data('highchartsChart');
 var chart=Highcharts.charts[index];

Все версии

Отслеживайте графики в глобальном объекте / карте по идентификатору контейнера

var window.charts={}; 
function foo(){
  new Highcharts.Chart({...},function(chart){  
      window.charts[chart.options.chart.renderTo] = chart;
  });
}

function bar(){
  var chart=window.charts["containerId"];
}

Советы по режиму чтения @ Highcharts - доступ к объекту диаграммы по идентификатору контейнера

PS

Некоторые дополнения были внесены в новые версии Highcharts с момента написания этого ответа и взяты из ответов @davertron, @Moes и @Przy, пожалуйста, проголосуйте за их комментарии / ответы, поскольку они заслуживают признания за них. Добавление их сюда в качестве принятого ответа было бы неполным без этих


10
Похоже, что начиная с версии 2.3.4 Highcharts отслеживает все графики на странице: api.highcharts.com/highcharts#Highcharts
davertron

@davertron, спасибо за обновление ... это хорошая возможность, не думаю, что для этого потребовалось много кода / усилий ...
Джугал Таккар 02

+1 для $ ("# container"). Data ('highchartsChart') в качестве индекса highcharts. это очень полезно, спасибо!
Shahar

1
Любой аналогичный метод, который я мог бы использовать для highstock?
tnkh

45

ты можешь это сделать

var chart = $("#testDivId").highcharts();

проверить пример на скрипач


У меня не сработало, пришлось использовать ответ @Frzy. Я использую версию 4.1.4
Дэвид Торрес

не уверен, почему это не сработало для вас, в примере скрипки используется v4.2.3
Nerdroid

1
Он возвращает элемент контейнера вместо диаграммы, и поэтому ответ @Frzy сработал. Кроме того, я нашел другое решение:$("#testDivId").highcharts({...}, function(chart) {...});
Дэвид Торрес

он определенно возвращает объект jsfiddle.net/abbasmhd/86hLvc5s проверяет вывод консоли после нажатия кнопки
Nerdroid

1
Да, в jsfiddle это делается, согласен. Но не все работают одинаково, как вы можете видеть по 11 голосам за ответ @Frzy
Дэвид Торрес

22
var $chartCont = $('#container').highcharts({...}),
    chartObj = Highcharts.charts[$chartCont.data('highchartsChart')];

chartCont - это объект jQuery. chartObj - это объект диаграммы Highchart.

Это использует Highcharts 3.01


10

Просто с чистым JS:

var obj = document.getElementById('#container')
    Highcharts.charts[obj.getAttribute('data-highcharts-chart')];

9

Я нашел другой способ сделать это ... в основном потому, что я использую Highcharts, встроенные в OutSystems Platform, и у меня нет способа контролировать способ создания диаграмм.

Способ, который я нашел, был следующий:

  1. Дайте диаграмме идентифицирующий класс с помощью classNameатрибута

    chart: {
        className: 'LifeCycleMasterChart'
    }
    
  2. Определите вспомогательную функцию для получения диаграммы по имени класса

    function getChartReferenceByClassName(className) {
    var cssClassName = className;
    var foundChart = null;
    
    $(Highcharts.charts).each(function(i,chart){    
        if(chart.container.classList.contains(cssClassName)){
            foundChart = chart;
            return;
        }
    });
    
    return foundChart;
    

    }

  3. Используйте вспомогательную функцию там, где она вам нужна

    var detailChart = getChartReferenceByClassName('LifeCycleDetailChart');
    

Надеюсь, это вам поможет!


5

Без jQuery (vanilla js):

let chartDom = document.getElementById("testDivId");
let chart = Highcharts.charts[Highcharts.attr(chartDom, 'data-highcharts-chart')]

4
var chart1; // globally available
$(document).ready(function() {
      chart1 = new Highcharts.Chart({
         chart: {
            renderTo: 'container',
            type: 'bar'
         },
         title: {
            text: 'Fruit Consumption'
         },
         xAxis: {
            categories: ['Apples', 'Bananas', 'Oranges']
         },
         yAxis: {
            title: {
               text: 'Fruit eaten'
            }
         },
         series: [{
            name: 'Jane',
            data: [1, 0, 4]
         }, {
            name: 'John',
            data: [5, 7, 3]
         }]
      });
   });

Var chart1 является глобальным, поэтому вы можете использовать его для доступа к объекту de highchart, не имеет значения, какой контейнер является

chart1.redraw();

2

... и с помощью коллеги ... лучший способ сделать это ...

getChartReferenceByClassName(className) {
    var foundChart = $('.' + className + '').eq(0).parent().highcharts();

    return foundChart;
}

1

Ответ @elo правильный и получил одобрение, хотя мне пришлось немного привести его в порядок, чтобы было понятнее:

const myChartEl = document.getElementById('the-id-name');
const myChart = Highcharts.charts[myChartEl.getAttribute('data-highcharts-chart')];

myChartзатем становится живым объектом Highcharts, который предоставляет все текущие свойства , присутствующие в диаграмме, отображаемой в myChartEl. Поскольку myChartэто объект Highcharts , можно связать методы прототипа сразу после него, расширить его или сослаться на него.

myChart.getTable();
myChart.downloadXLS();
setTimeout(() => Highcharts.fireEvent(myChart, "redraw"), 10);

Можно также получить myChartчерез .highcharts(), который является jQueryплагин:

var myChart = $("#the-id-name").highcharts();

Приведенный выше подход к jQueryплагину требует jQueryзагрузки перед использованием плагина и, конечно же, самого плагина. Отсутствие этого плагина побудило меня искать альтернативные способы сделать то же самое с чистым ванильным JavaScript.

Используя чистый JS-подход, я смог сделать то, что мне нужно (второй фрагмент кода), не полагаясь наjQuery :

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.