我有两个并排的图表,左边的是大的,右边的是小的,每个都在自己的容器中.当单击小图表时,我希望图表切换位置,以便小图表移动到左侧的大容器,而大图表移动到右侧的小容器,并且图表应该根据新容器的大小进行调整.这在Chart.js v2.9.4中有效,但在我升级到v4.4.2后,移动容器后图表仍保持原始大小.

以下是一些简单的代码来演示该问题: HTML

<div id='chart-container'>
    <div id='big-chart-container'>
      <canvas id='chart1'></canvas>
    </div>
    <div id='small-chart-container'>
      <canvas id='chart2'></canvas>
    </div>
</div>
<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
<!--Swapping charts works in chart.js 2-->
<!--<script src="https://cdn.jsdelivr.net/npm/chart.js@2.8.0"></script>-->

CSS

#chart-container{
    display: flex;
    width: 60vw;
  }

  #big-chart-container{
    width: 60%;
  }

  #small-chart-container{
    width: 30%;
  }

JavaScript

var canvas1 = document.getElementById('chart1')
var canvas2 = document.getElementById('chart2')

let bigChartContainer = document.getElementById('big-chart-container');
let smallChartContainer =document.getElementById('small-chart-container');
let data1 = [5,7,6,2,6,8,4,5]
let data2 = [4,8,15,16,23,42]
let labels1 = [...Array(data1.length).keys()]
let labels2 = [...Array(data2.length).keys()]

let bigChartID = 'chart1';

function chartClicked(chartID){
    if(bigChartID != chartID){ //if small chart is clicked then swap charts
      let smallChart = document.getElementById(chartID)
      let bigChart = document.getElementById(bigChartID)
      bigChartContainer.appendChild(smallChart)
      smallChartContainer.appendChild(bigChart)
      bigChartID = chartID
    }
}
  
const bigChart = new Chart(canvas1.getContext('2d'), {
  type: 'line',
  data: {
    labels: labels1,
    datasets: [{
      label: "Chart 1",
      data: data1
    }]
  },
  options: {
    onClick: function(){
      chartClicked('chart1')
    }
  }
})
const smallChart = new Chart(canvas2.getContext('2d'), {
  type: 'line',
  data: {
    labels: labels2,
    datasets: [{
      label: "Chart 2",
      data: data2,
      borderColor: 'rgb(255, 99, 132)',
    }]
  },
  options: {
    onClick: function(){
      chartClicked('chart2')
    }
  }
})

如果我降级到chart.js 2,那么切换图表效果非常好.

推荐答案

您可以调用方法chart#resize()让图表在新环境中采用:

You can call .resize() with no parameters to have the chart take the size of its container element

所以你的chartCliked功能可能会变成

function chartClicked(chartID){
   if(bigChartID != chartID){ //if small chart is clicked then swap charts
      let smallChartElement = document.getElementById(chartID)
      let bigChartElement = document.getElementById(bigChartID)
      bigChartContainer.appendChild(smallChartElement)
      smallChartContainer.appendChild(bigChartElement)
      bigChartID = chartID
      bigChart.resize();
      smallChart.resize();
   }
}

片段 :

var canvas1 = document.getElementById('chart1')
var canvas2 = document.getElementById('chart2')

let bigChartContainer = document.getElementById('big-chart-container');
let smallChartContainer =document.getElementById('small-chart-container');
let data1 = [5,7,6,2,6,8,4,5]
let data2 = [4,8,15,16,23,42]
let labels1 = [...Array(data1.length).keys()]
let labels2 = [...Array(data2.length).keys()]

let bigChartID = 'chart1';

function chartClicked(chartID){
    if(bigChartID != chartID){ //if small chart is clicked then swap charts
        let smallChartElement = document.getElementById(chartID)
        let bigChartElement = document.getElementById(bigChartID)
        bigChartContainer.appendChild(smallChartElement)
        smallChartContainer.appendChild(bigChartElement)
        bigChartID = chartID
        bigChart.resize();
        smallChart.resize();
    }
}

const bigChart = new Chart(canvas1.getContext('2d'), {
    type: 'line',
    data: {
        labels: labels1,
        datasets: [{
            label: "Chart 1",
            data: data1
        }]
    },
    options: {
        responsive: true,
        onClick: function(){
            chartClicked('chart1')
        }
    }
})
const smallChart = new Chart(canvas2.getContext('2d'), {
    type: 'line',
    data: {
        labels: labels2,
        datasets: [{
            label: "Chart 2",
            data: data2,
            borderColor: 'rgb(255, 99, 132)',
        }]
    },
    options: {
        responsive: true,
        onClick: function(){
            chartClicked('chart2')
        }
    }
});
#chart-container{
    display: flex;
    width: 90vw;
}

#big-chart-container{
    width: 60%;
}

#small-chart-container{
    width: 30%;
}
<div id='chart-container'>
    <div id='big-chart-container'>
        <canvas id='chart1'></canvas>
    </div>
    <div id='small-chart-container'>
        <canvas id='chart2'></canvas>
    </div>
</div>

<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>

具有responsive: truemaintainAspectRatio: false和两个图表容器的显式高度控制的替代片段.

var canvas1 = document.getElementById('chart1')
var canvas2 = document.getElementById('chart2')

let bigChartContainer = document.getElementById('big-chart-container');
let smallChartContainer =document.getElementById('small-chart-container');
let data1 = [5,7,6,2,6,8,4,5]
let data2 = [4,8,15,16,23,42]
let labels1 = [...Array(data1.length).keys()]
let labels2 = [...Array(data2.length).keys()]

let bigChartID = 'chart1';

function chartClicked(chartID){
    if(bigChartID != chartID){ //if small chart is clicked then swap charts
        let smallChartElement = document.getElementById(chartID)
        let bigChartElement = document.getElementById(bigChartID)
        bigChartContainer.appendChild(smallChartElement)
        smallChartContainer.appendChild(bigChartElement)
        bigChartID = chartID
        bigChart.resize();
        smallChart.resize();
    }
}

const bigChart = new Chart(canvas1.getContext('2d'), {
    type: 'line',
    data: {
        labels: labels1,
        datasets: [{
            label: "Chart 1",
            data: data1
        }]
    },
    options: {
        responsive: true,
        maintainAspectRatio: false,
        onClick: function(){
            chartClicked('chart1')
        }
    }
})
const smallChart = new Chart(canvas2.getContext('2d'), {
    type: 'line',
    data: {
        labels: labels2,
        datasets: [{
            label: "Chart 2",
            data: data2,
            borderColor: 'rgb(255, 99, 132)',
        }]
    },
    options: {
        responsive: true,
        maintainAspectRatio: false,
        onClick: function(){
            chartClicked('chart2')
        }
    }
});
#chart-container{
    display: flex;
    width: 90vw;
    height: 60vh;
}

#big-chart-container{
    width: 60%;
    height: 100%;
}

#small-chart-container{
    width: 30%;
    height: 50%;
}
<div id='chart-container'>
    <div id='big-chart-container'>
        <canvas id='chart1'></canvas>
    </div>
    <div id='small-chart-container'>
        <canvas id='chart2'></canvas>
    </div>
</div>

<script src="https://cdn.jsdelivr.net/npm/chart.js"></script>

Javascript相关问答推荐

如何将特定的字符串类型转换为TypScript中的字符串?

将下拉分区与工具提示结合起来

回归函数不会迭代到foreach中的下一个元素

如何比较嵌套对象的更改并创建更改报告

React Hooks中useState的同步问题

将数据从strapi提取到next.js,但响应延迟API URL

如何分配类型脚本中具有不同/额外参数的函数类型

Cypress -使用commands.js将数据测试id串在一起失败,但在将它们串在一起时不使用命令有效

yarn安装一个本地npm包,以便本地包使用main项目的node_modules(ckeditor-duplicated-modules错误)

如何在不创建新键的情况下动态更改 map 中的项目?

手机上的渲染错误文本必须在文本组件中渲染,但在浏览器上没有问题<><>

获取Uint8ClampedArray中像素数组的宽度/高度

如何使onPaste事件与可拖动的HTML元素一起工作?

我正在建立一个基于文本的游戏在react ,我是从JS转换.我怎样才能使变量变呢?

Chart.js-显示值应该在其中的引用区域

SPAN不会在点击时关闭模式,尽管它们可以发送日志(log)等

如果一个字符串前面有点、空格或无字符串,后面有空格、连字符或无字符串,则匹配正则表达式

将嵌套数组的元素乘以其深度,输出一个和

在JS/TS中将复杂图形转换为数组或其他数据 struct

JavaScript&;Reaction-如何避免在不使用字典/对象的情况下出现地狱?