You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

动态创建Google Charts饼图,如何用Bootstrap实现左右并排?

问题描述

我使用Google Chart Tools展示两个饼图,期望左、右各一个。此前通过静态Bootstrap类实现该布局,代码如下:

{{-- Piechart 1 --}}
<div class="row form-group">
    <div class="col-md-6">
        <div class="panel panel-default">
            <div class="panel-body">
                <div id="piechart_1" style="width:auto; "></div>
                <div id="total3"> </div>
            </div>
        </div>
    </div>
    {{-- Piechart 2 --}}
    <div class="col-md-6">
        <div class="panel panel-default">
            <div class="panel-body">
                <div id="pie_status_1" style="width:auto; "></div>
                <div id="total4"> </div>
            </div>
        </div>
    </div>
</div>

但通过DOM动态创建图表容器并尝试复用Bootstrap类时,样式被覆盖。当前动态创建的代码如下:

@foreach ($escuela_data as $key => $escuela)

      //LEFT CHART
        function drawPieChart{{ $key }}() {

        var data = google.visualization.arrayToDataTable([
            ['Sede', 'Cantidad'],

            @foreach ($suma_inscritos_sede[$key] as $index => $value)

                ["{{ @$value->sede }}", {{ @$value->suma_por_sede }}],
            @endforeach

        ]);

        var options = {
            title: "{{ @$value->nom_escuela }} - Total de Inscritos por Sede ",
            is3D: false,
            height: 500,
            
            titleTextStyle: {
                color: '#1e5095', // any HTML string color ('red', '#cc00cc')
                fontName: 'Arial', // i.e. 'Times New Roman'
                fontSize: 12, // 12, 18 whatever you want (don't specify px)
                bold: true, // true or false
                italic: true // true of false
            },
        };
        
        var container = document.createElement('div');  <-- Problem here
        container.classList.add("class", "row");       <---  
        var container = document.createElement('div');  <---
        container.classList.add("class", "col-md-6");   <---
        $('.chartContainer').append(container);

        var chart = new google.visualization.PieChart(container);
        chart.draw(data, options);


    }

    google.charts.setOnLoadCallback(drawPieChart{{ $key }});
    

   //RIGHT CHART
    function drawPieChartEstado{{ $key }}() {

    var data = google.visualization.arrayToDataTable([
        ['Estado', 'Cantidad'],

        @foreach ($suma_estado_por_escuela[$key] as $index => $value)

            ["{{ @$value->cein_estado }}", {{ @$value->suma_estado_escuela }}],
        @endforeach

    ]);

    var options = {
        title: '{{ @$value->nom_escuela }} - Estados de alumnos por Escuela ',
        is3D: false,
        height: 500,
       
        titleTextStyle: {
            color: '#1e5095', // any HTML string color ('red', '#cc00cc')
            fontName: 'Arial', // i.e. 'Times New Roman'
            fontSize: 12, // 12, 18 whatever you want (don't specify px)
            bold: true, // true or false
            italic: true // true of false
        },
    };
    
    var container = document.createElement('div');
    container.setAttribute("class", "col-md-6");
    $('.chartContainer').append(container);
    
    var chart = new google.visualization.PieChart(container);
    chart.draw(data, options);
    }

 google.charts.setOnLoadCallback(drawPieChartEstado{{ $key }});

@endforeach

请问如何正确创建Div容器,或使用Bootstrap类实现两个饼图左右并排?


解决方案

问题分析

你的动态代码存在几个关键错误:

  • 重复声明container变量:第一个创建的row容器被直接覆盖,根本没有添加到页面中
  • classList.add用法错误:不需要传入"class"作为参数,直接写类名即可(正确写法:container.classList.add("row"))
  • 不符合Bootstrap栅格规则:两个饼图的col-md-6容器没有放在同一个row容器内
  • 回调函数使用不当:每个图表单独调用加载回调,可能导致布局顺序混乱

修正后的代码

@foreach ($escuela_data as $key => $escuela)
    function drawCharts{{ $key }}() {
        // 创建外层row容器,和静态布局结构一致
        var rowContainer = document.createElement('div');
        rowContainer.classList.add("row", "form-group");
        $('.chartContainer').append(rowContainer);

        // ------------------- 左侧饼图 -------------------
        var leftData = google.visualization.arrayToDataTable([
            ['Sede', 'Cantidad'],
            @foreach ($suma_inscritos_sede[$key] as $index => $value)
                ["{{ @$value->sede }}", {{ @$value->suma_por_sede }}],
            @endforeach
        ]);

        var leftOptions = {
            title: "{{ @$escuela->nom_escuela }} - Total de Inscritos por Sede ",
            is3D: false,
            height: 500,
            titleTextStyle: {
                color: '#1e5095',
                fontName: 'Arial',
                fontSize: 12,
                bold: true,
                italic: true
            },
        };

        // 还原静态布局的panel结构
        var leftCol = document.createElement('div');
        leftCol.classList.add("col-md-6");
        
        var leftPanel = document.createElement('div');
        leftPanel.classList.add("panel", "panel-default");
        
        var leftPanelBody = document.createElement('div');
        leftPanelBody.classList.add("panel-body");
        
        var leftChartDiv = document.createElement('div');
        leftChartDiv.style.width = 'auto';
        
        var leftTotalDiv = document.createElement('div');
        leftTotalDiv.id = "total3_{{ $key }}"; // 加key避免多组图表ID重复

        // 组装左侧容器
        leftPanelBody.appendChild(leftChartDiv);
        leftPanelBody.appendChild(leftTotalDiv);
        leftPanel.appendChild(leftPanelBody);
        leftCol.appendChild(leftPanel);
        rowContainer.appendChild(leftCol);

        // 绘制左侧图表
        var leftChart = new google.visualization.PieChart(leftChartDiv);
        leftChart.draw(leftData, leftOptions);

        // ------------------- 右侧饼图 -------------------
        var rightData = google.visualization.arrayToDataTable([
            ['Estado', 'Cantidad'],
            @foreach ($suma_estado_por_escuela[$key] as $index => $value)
                ["{{ @$value->cein_estado }}", {{ @$value->suma_estado_escuela }}],
            @endforeach
        ]);

        var rightOptions = {
            title: '{{ @$escuela->nom_escuela }} - Estados de alumnos por Escuela ',
            is3D: false,
            height: 500,
            titleTextStyle: {
                color: '#1e5095',
                fontName: 'Arial',
                fontSize: 12,
                bold: true,
                italic: true
            },
        };

        // 还原静态布局的panel结构
        var rightCol = document.createElement('div');
        rightCol.classList.add("col-md-6");
        
        var rightPanel = document.createElement('div');
        rightPanel.classList.add("panel", "panel-default");
        
        var rightPanelBody = document.createElement('div');
        rightPanelBody.classList.add("panel-body");
        
        var rightChartDiv = document.createElement('div');
        rightChartDiv.style.width = 'auto';
        
        var rightTotalDiv = document.createElement('div');
        rightTotalDiv.id = "total4_{{ $key }}"; // 加key避免多组图表ID重复

        // 组装右侧容器
        rightPanelBody.appendChild(rightChartDiv);
        rightPanelBody.appendChild(rightTotalDiv);
        rightPanel.appendChild(rightPanelBody);
        rightCol.appendChild(rightPanel);
        rowContainer.appendChild(rightCol);

        // 绘制右侧图表
        var rightChart = new google.visualization.PieChart(rightChartDiv);
        rightChart.draw(rightData, rightOptions);
    }

    // 每组图表只调用一次加载回调,保证执行顺序
    google.charts.setOnLoadCallback(drawCharts{{ $key }});
@endforeach

关键改进点

  1. 将同一组的两个饼图放在同一个回调函数中,保证容器创建顺序和布局结构正确
  2. 严格遵循Bootstrap栅格层级:row -> col-md-6 -> panel -> panel-body,和静态布局完全匹配
  3. 修复classList.add的用法,正确添加Bootstrap类名
  4. 为动态创建的total容器添加唯一ID(结合$key),避免多组图表时ID冲突
  5. 完整还原静态布局的面板结构,确保样式和静态版本一致

内容的提问来源于stack exchange,提问作者Rodrigo Cabrera

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.16 09:27:02