Синхронизация масштабирования и курсора между несколькими последовательными диаграммами на основе даты

Я пытаюсь реализовать синхронизацию курсора и масштабирования на нескольких линейных диаграммах, следуя приведенному здесь примеру.

http://codepen.io/amcharts/pen/64dc766ec283e086c8ac8a5fba3bed83

Я вижу, что в примере ниже

var charts = [];
charts.push(AmCharts.makeChart("chartdiv", chartConfig));
charts.push(AmCharts.makeChart("chartdiv2", chartConfig2));
charts.push(AmCharts.makeChart("chartdiv3", chartConfig3));

и после этого

for (var x in charts) {
    charts[x].addListener("zoomed", syncZoom);
    charts[x].addListener("init", addCursorListeners);
}

Код для слушателей тоже повторяется в цикле for.

ПРОБЛЕМА

Ниже приведена логика, которую я использую в файле PHP для получения результата SQL, а затем построения диаграммы amchart.

for ( i = 1 to 10){
resultset[i] = exec_db_query(param1,param2...)
<script>
drawAmChart(resultset[i],val2,val3 etc)
</script>
}

drawAmChart(resultset[i],val2,val3 etc) вызывает функцию javscript addListeners, которая получает диаграмму в качестве параметра.

В рамках построения диаграммы я добавляю к ней слушателей во время самого построения. Следовательно, мой код для приведенного ниже примера

for (var x in charts) {
    charts[x].addListener("zoomed", syncZoom);
    charts[x].addListener("init", addCursorListeners);
}

is

function addListeners(chartObj) {
//    chartObj.addListener("init", handleInit);
    chartObj.addListener('init', function () {
        function legendHandler(evt) {
            if (evt.dataItem.id === 'all') {
                for (var i1 in evt.chart.graphs) {
                    if (evt.chart.graphs[i1].id !== 'all') {
                        evt.chart[evt.dataItem.hidden ? 'hideGraph' : 'showGraph'](evt.chart.graphs[i1]);
                    }
                }
            }
        }

        function syncZoom(evt) {
            if (chartObj.ignoreZoom) {
                chartObj.ignoreZoom = false;
            }
            if (evt.chart !== chartObj) {
                evt.chart.ignoreZoom = true;
                evt.chart.zoomToDates(evt.startDate, evt.endDate);
            }
        }

        function handleHideCursor(event) {
            if (event.chart.chartCursor.hideCursor) {
                event.chart.chartCursor.forceShow = false;
                event.chart.chartCursor.hideCursor(false);
            }
        }

        function addCursorListeners(event) {
            event.chart.chartCursor.addListener("changed", function () {
                function handleCursorChange(event) {
                    if (event.chart !== chartObj) {
                        if (event.position) {
                            chartObj.chartCursor.isZooming(event.target.zooming);
                            chartObj.chartCursor.selectionPosX = event.target.selectionPosX;
                            chartObj.chartCursor.forceShow = true;
                            chartObj.chartCursor.setPosition(event.position, false, event.target.index);
                        }
                    }
                }
                event.chart.chartCursor.addListener("changed", handleCursorChange);
                event.chart.chartCursor.addListener("onHideCursor", handleHideCursor);
            });
        }

        chartObj.legend.addListener('hideItem', legendHandler);
        chartObj.legend.addListener('showItem', legendHandler);
        chartObj.addListener("zoomed", syncZoom);
        chartObj.addListener("init", addCursorListeners);
    });
}

Это не работает.

Могу я запросить руководство о том, как синхронизировать диаграммы, как я это использую?

ОБНОВЛЕННЫЙ КОД - ЕЩЕ НЕ РАБОТАЕТ

Теперь я вызываю addChartScrollSyncListener, чтобы синхронизировать все диаграммы на странице.

Во-первых, исчезли графики. Однако, когда я наводил указатель мыши на div диаграммы, я вижу курсор мыши (курсор диаграммы), который перемещается, а также значения легенды !!

Я получаю эту ошибку сейчас в консоли отладки

TypeError: chartList[x].chartCursor.isZooming is not a function
chartList[x].chartCursor.isZooming(event.target.zooming);

Вот функция addChartSyncListener

function addChartSyncListener() {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        chartList[x].addListener("zoomed", syncZoom);
        chartList[x].addListener("init", addCursorListeners);
    }
}

function addCursorListeners(event) {
    event.chart.chartCursor.addListener("changed", handleCursorChange);
    event.chart.chartCursor.addListener("onHideCursor", handleHideCursor);
}

function syncZoom(event) {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (charts[x].ignoreZoom) {
            chartList[x].ignoreZoom = false;
        }
        if (event.chart != chartList[x]) {
            chartList[x].ignoreZoom = true;
            chartList[x].zoomToDates(event.startDate, event.endDate);
        }
    }
}

function handleCursorChange(event) {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (event.chart != chartList[x]) {
            if (event.position) {
                chartList[x].chartCursor.isZooming(event.target.zooming);
                chartList[x].chartCursor.selectionPosX = event.target.selectionPosX;
                chartList[x].chartCursor.forceShow = true;
                chartList[x].chartCursor.setPosition(event.position, false, event.target.index);
            }
        }
    }
}

function handleHideCursor() {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (charts[x].chartCursor.hideCursor) {
            chartList[x].chartCursor.forceShow = false;
            chartList[x].chartCursor.hideCursor(false);
        }
    }
}

person usert4jju7    schedule 15.01.2016    source источник
comment
На первый взгляд код кажется нормальным. Есть результаты отладки?   -  person gerric    schedule 15.01.2016
comment
См. Раздел Должны ли вопросы включать «теги» в свои заголовки? , где нет единого мнения, не должны!   -  person    schedule 15.01.2016
comment
Привет, Геррик - Спасибо, что подключились. Никакой ошибки. Просто графики построены независимо друг от друга. Я планирую получить все объекты диаграммы на странице и синхронизировать их с циклом for, как в примере, который я подробно описал. Как я могу получить доступ ко всем объектам диаграммы на странице? Как и здесь - ahumbleopinion.com/. Я пробовал this.Amcharts.Charts и this.Amcharts.charts. Ни то, ни другое не помогло.   -  person usert4jju7    schedule 15.01.2016
comment
AmCharts определяется в области видимости окна, поэтому запросы к диаграммам должны работать с Amcharts.charts (нет this). Моя единственная мысль о вашем коде - правильно ли внутренние функции вызываются из слушателей. Возможно, попробуйте использовать выражения функций вместо их объявления.   -  person gerric    schedule 15.01.2016
comment
Спасибо, Геррик. Мне удалось переместить функции из вложенности, поскольку в какой-то момент, когда я возился с кодом, я начал получать слишком много ошибок рекурсии. Я обновил последние проблемы в вопросе в разделе ОБНОВЛЕННЫЙ КОД - ЕЩЕ НЕ РАБОТАЕТ. Не могли бы вы помочь?   -  person usert4jju7    schedule 16.01.2016


Ответы (1)


Здесь самое главное - быть на последней версии amcharts. Проблема, которая возникла у меня, возникла из-за того, что я использовал версию 3. После того, как я загрузил версию 3.1.8, все работает нормально.

function addChartSyncListener() {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        chartList[x].addListener("zoomed", syncZoom);
        chartList[x].addListener("init", addCursorListeners);
    }
}

function addCursorListeners(event) {
    event.chart.chartCursor.addListener("changed", handleCursorChange);
    event.chart.chartCursor.addListener("onHideCursor", handleHideCursor);
}

function syncZoom(event) {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (charts[x].ignoreZoom) {
            chartList[x].ignoreZoom = false;
        }
        if (event.chart != chartList[x]) {
            chartList[x].ignoreZoom = true;
            chartList[x].zoomToDates(event.startDate, event.endDate);
        }
    }
}

function handleCursorChange(event) {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (event.chart != chartList[x]) {
            if (event.position) {
                chartList[x].chartCursor.isZooming(event.target.zooming);
                chartList[x].chartCursor.selectionPosX = event.target.selectionPosX;
                chartList[x].chartCursor.forceShow = true;
                chartList[x].chartCursor.setPosition(event.position, false, event.target.index);
            }
        }
    }
}

function handleHideCursor() {
    var chartList = AmCharts.charts;

    for (var x in chartList) {
        if (charts[x].chartCursor.hideCursor) {
            chartList[x].chartCursor.forceShow = false;
            chartList[x].chartCursor.hideCursor(false);
        }
    }
}
person usert4jju7    schedule 15.01.2016