Chart.js показать отрицательное значение в верхней половине

#javascript #chart.js

#javascript #chart.js

Вопрос:

Я создаю chart.js который имеет как положительные, так и отрицательные значения

но как сделать так, чтобы все значения были в верхней половине (игнорируйте, если оно положительное или отрицательное при рисовании, но сохраните метку)

 var tax_dash = new Chart(ctx_tax_dash, {
  type: "bar",
  data: {
    labels: lable_set,
    datasets: [{
        label: "Tax in",
        data: total_tax_in_t_data__year,
        backgroundColor: '#0fd96d',
        // borderColor: sales_t_data,
        borderWidth: 1,
      },
      {
        label: "Tax out",
        data: total_tax_out_t_data__year,
        backgroundColor: '#0f81d9',
        // borderColor: sales_t_data,
        borderWidth: 1,
      },
      {
        label: "Net VAT",
        data: total_tax_in_out_t_data__year,
        backgroundColor: '#d96a0f',
        // borderColor: sales_t_data,
        borderWidth: 1,
      },
    ],
  },
  options: {
    legend: {
      display: true,
    }
  },
});
  

введите описание изображения здесь

Редактировать

что я пытаюсь сделать

введите описание изображения здесь

  • возможное решение: является (многоосевой) двойной осью y.пример многоосевой

    • ~ проблема: как перевернуть ось так, чтобы -100 было вверху, а 0 — внизу

    • ~ проблема: как разделить базу набора данных на (знак)

или

введите описание изображения здесь

  • возможное решение 2: сделать все переменные положительными
  • @Gkiokan> решение: используйте модификатор всплывающего окна для отображения значений с отрицательным
    • ~ проблема: как функция узнает, является ли значение отрицательным

    • ~ проблема: пользователь должен знать, что это значение отрицательное в метке

Комментарии:

1. неясно, как -600 может быть выше 0? возможно, использовать Math.abs

2. значения поступают из функции, поэтому я не могу их контролировать, так что есть ли способ сделать все значения положительными, но оставить метку отрицательной @LawrenceCherone

3. Я думаю, что это можно сделать с помощью двойной оси y, не уверен, как это сделать @LawrenceCherone

4. Вы пытались умножить значение на * - 1 ? Это сделало -600 бы into 600 . Конечно, вам нужно сначала изменить данные, прежде чем помещать их в качестве chartData. Я считаю charts.js имеет также всплывающий модификатор для отображаемых значений, который позволит вам также изменять отображаемые значения, если вам нужно.

5. @MoazMabrok Это хороший вопрос. На самом деле это довольно просто с некоторыми функциями проверки, потому что у вас будет originalData и modifiedData для диаграммы. Таким образом, вы можете проверить исходное значение этого элемента перед его распечаткой — на основе индекса элемента. Вы понимаете, что я имею в виду? Если вы можете предоставить мне рабочий минимальный пример, я могу добавить вам необходимые функции.

Ответ №1:

Решение 2

Я сделал это сегодня утром, пользователь what Math.abs из комментария @Lawrence и «модификатор всплывающего окна» из комментария @Gkiokan, а также этот jsfiddle

Большое вам спасибо за помощь. Общение с более умными людьми влияет на вас 🙂

                total_tax_in_t_data_portal_month_year = [Math.abs(12),Math.abs(-234),Math.abs(234)];
                total_tax_in_t_data_portal_month_year_sign = [12,-234,234];
                var tax_dash_portal = new Chart(ctx_tax_dash_portal, {
                    type: "bar",
                    data: {
                        labels: lable_set,
                        datasets: [
                            {
                                label: "VAT In",
                                data: total_tax_in_t_data_portal_month_year,
                                sign: total_tax_in_t_data_portal_month_year_sign,
                                backgroundColor: "#0fd96d",
                                // borderColor: sales_t_data,
                                borderWidth: 1,
                            },
                            {
                                label: "VAT Out",
                                data: total_tax_out_t_data_portal_month_year,
                                sign: total_tax_out_t_data_portal_month_year_sign,
                                backgroundColor: "#0f81d9",
                                // borderColor: sales_t_data,
                                borderWidth: 1,
                            },
                            {
                                label: "Net VAT",
                                data: total_tax_t_data_portal_month_year,
                                sign: total_tax_t_data_portal_month_year_sign,
                                backgroundColor: "#d96a0f",
                                // borderColor: sales_t_data,
                                borderWidth: 1,
                            },
                        ],
                    },
                    options: {
                        legend: {
                            display: true,
                        },
                        tooltips: {
                            enabled: true,
                            callbacks: {
                                label: function (tooltipItem, data) {
                                    var label = data.labels[tooltipItem.index];
                                    var val = data.datasets[tooltipItem.datasetIndex].data[tooltipItem.index];
                                    var sign = data.datasets[tooltipItem.datasetIndex].sign[tooltipItem.index];
                                    if(sign < 0){
                                        return label   ": -"   val;
                                    }else{
                                        return label   ': '   val;
                                    }

                                }
                            }
                          }
                        
                    },
                });



  

total_tax_in_t_data_portal_month_year является примером, поскольку значения поступают из функции

Math.abs используется для удаления отрицательного знака

затем я добавил sign в datasets доступ к эссе

tooltips обратные вызовы вызываются для каждой переменной, поэтому я добавил туда оператор if, чтобы добавить - if sign < 0 и ничего не делать, если нет

Ответ №2:

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

Я создал для вас jsfiddle, который демонстрирует использование исходных данных и измененных данных. Пожалуйста, сначала нажмите на Изменить данные, которые затем сопоставят данные, чтобы вы могли видеть текущую работу. В вашем случае вы бы изменили данные перед вызовом диаграмм.

На самом деле вам понадобится всего пара методов, как указано ниже:
updateItemValues чтобы изменить отрицательные значения и поместить их в другой объект
tooltipCallback обратный вызов всплывающей подсказки для использования отображенного исходного значения

 let data = {
    modified: false,
    
    orginalData : {
        'tax_in' : [10, 20, -30, -40, -100, -50],
        'tax_out' : [-10, 10, 20, 10, -40, -70],
        'net_vat' : [-50, -9, -40, -20, -10, -90],
    },

    modifiedData : {
        // this modified data will be calculated before putting it in the charts        
        // for demo purpose we will just copy the values for now.
        'tax_in' : [10, 20, -30, -40, -100, -50],
        'tax_out' : [-10, 10, 20, 10, -40, -70],
        'net_vat' : [-50, -9, -40, -20, -10, -90],
    },

    updateModifiedData(){
        // loop though the orginal Data 
        Object.keys(this.orginalData).forEach( (item, indexx) => {
            console.log('modifying item chart data for: ', item)
            this.updateItemValues(item)
        })
        
        this.modified = true 
        document.getElementById('status').innerHTML = 'modified'
    },

    updateItemValues(dataKey){
        let temp = []
        this.orginalData[dataKey].forEach( (value, index) => {
            console.log('- validating ', dataKey, 'index: ', index, '; value: ', value)

            // if we have a negative value, just multiply by -1 so get it positive
            if(value <= 0){
                value = value * -1
            }

            // add to the temporary variable
            temp.push(value)
        })

        // put the modified data to some place to have it saved
        this.modifiedData[dataKey] = temp
        console.log('-- final data modded ', temp)
    },
    

    tooltipCallback(tooltipItem, chartData) {             
        // find reference values              
        let index = tooltipItem.index 
        let dataIndex = tooltipItem.datasetIndex

        // find the name of dataset 
        let key = chartData.datasets[dataIndex].name

        // validate or whatever with the orginal value
        let orginalValueOfItem  = data.orginalData[key][index]
        let modifiedValueOfItem = data.modifiedData[key][index]

        // Modify your final tooltip here
        return 'Orginal Value: '   orginalValueOfItem   ' ; Modified Value: '   modifiedValueOfItem
    }

}
  

Как вы можете использовать это решение?

Довольно просто.

  • Скопируйте этот data объект в свой код.
  • Заполните data.orginalData значение вашими исходными данными диаграмм на основе key
    • пример data.orginalData.tax_in = [...]
  • В ваших наборах данных добавьте name свойство с соответствующим key
  • Расширьте параметры диаграмм с помощью tooltipCallback
  • Вызов data.updateModifiedData() для получения измененных данных
  • При необходимости проверьте jsFiddle для справки.
  • Получайте удовольствие.