向 Google-Visualization ColumnChart 添加渐变

Posted

技术标签:

【中文标题】向 Google-Visualization ColumnChart 添加渐变【英文标题】:Adding a gradient to Google-Visualization ColumnChart 【发布时间】:2012-03-02 06:57:19 【问题描述】:

我正在尝试通过向为列绘制的 SVG 矩形添加渐变来向 Google ColumnChart 添加一些 pizazz。下面的代码将为 iframe svg>defs 添加渐变,并在我目前关心的所有浏览器(Firefox、IE 和 Chrome 的更高版本)中正确替换 rects 的填充属性。

我的问题是,每当我将鼠标悬停在或选择一个条形(或图例)时,颜色都会重置为原始颜色。我是一个 SVG 菜鸟,我无法弄清楚如何、在哪里或什么在重置颜色。

所以我的问题是,有谁知道如何(使用 javascript/jquery)停止、覆盖或以某种方式操纵重置颜色的代码?如果可能的话,我宁愿保持“交互式”部分完整(工具提示等)。

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8"/>
    <title>Google Visualization API Sample</title>
    <script type="text/javascript" src="http://www.google.com/jsapi"></script>
    <script type="text/javascript">
      google.load('visualization', '1', packages: ['corechart']);
      google.load("jquery", "1.7.1");
    </script>
    <script type="text/javascript">
      function drawVisualization() 
        // Create and populate the data table.
        var data = new google.visualization.DataTable();
        var rowData = [['Year', 'North', 'West',  'South'],
                       ['2010', 197,     333,     298    ],
                       ['2011', 167,     261,     381    ]];
        var data = google.visualization.arrayToDataTable(rowData);

        visualization = new google.visualization.ColumnChart(document.getElementById('visualization'));

        google.visualization.events.addListener(visualization, 'ready', function()
          var svgns = "http://www.w3.org/2000/svg";
          var gradients = [["red","#C0504D","#E6B8B7"],
                           ["green","#9BBB59","#D8E4BC"],
                           ["blue","#4F81BD","DCE6F1"]];
          var svg_defs = $("#visualization iframe").contents().find('defs');
          // add gradients to svg defs
          for(var i = 0; i < gradients.length; i++)
            var grad = $(document.createElementNS(svgns, "linearGradient")).
                attr(id:gradients[i][0],x1:"0%",x2:"0%",y1:"0%",y2:"100%");
            var stopTop = $(document.createElementNS(svgns, "stop")).
                attr(offset:"0%","stop-color":gradients[i][1]);
            var stopBottom = $(document.createElementNS(svgns, "stop")).
                attr(offset:"100%","stop-color":gradients[i][2]);
            $(grad).append(stopTop).append(stopBottom);
            svg_defs.append(grad);
          
          // #3366cc, #dc3912, #ff9900 - replace default colors with gradients
          $("#visualization iframe").contents().find('rect[fill="#3366cc"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
          $("#visualization iframe").contents().find('rect[fill="#dc3912"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
          $("#visualization iframe").contents().find('rect[fill="#ff9900"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
        );
        // Create and draw the visualization.
        visualization.draw(data,width:600, height:400);
      
      google.setOnLoadCallback(drawVisualization);
    </script>
  </head>
  <body style="font-family: Arial;border: 0 none;">
    <div id="visualization" style="width: 600px; height: 400px;"></div>
  </body>
</html>

更新

因此,在查看 DOM 以查看是否可以找到这些颜色代码可能存储的位置(并在那里找到正在使用它们的函数)时,我确实找到了这些(设置后将执行我想要的操作):

      //fill
      visualization.qa.l.e[0].Hm.O = "url(#blue)";
      visualization.qa.l.e[1].Hm.O = "url(#red)";
      visualization.qa.l.e[2].Hm.O = "url(#green)";

      // stroke
      visualization.qa.l.e[0].Hm.Jb = "#000000";
      visualization.qa.l.e[1].Hm.Jb = "#000000";
      visualization.qa.l.e[2].Hm.Jb = "#000000";

      // fill-opacity
      //visualization.qa.l.e[0].Hm.$b = 0.5;
      //visualization.qa.l.e[1].Hm.$b = 0.5;
      //visualization.qa.l.e[2].Hm.$b = 0.5;

      // stroke-width
      visualization.qa.l.e[0].Hm.H = 0.4;
      visualization.qa.l.e[1].Hm.H = 0.4;
      visualization.qa.l.e[2].Hm.H = 0.4;

      // stroke-opacity
      //visualization.qa.l.e[0].Hm.nc = 0.5;
      //visualization.qa.l.e[1].Hm.nc = 0.5;
      //visualization.qa.l.e[2].Hm.nc = 0.5;

但这只是一个临时解决方案,因为我确信下次 Google 更新可视化代码时,这些变量名称会发生​​变化(我不认为有人故意选择这些,并且使用的压缩器/混淆器可能会选择下次使用不同的变量名 - 但谁知道呢 - 也许不会)。

因此,如果有人知道一种不依赖于手动查找和设置变量名称的更永久的方法,我会喜欢的。否则,这可能是我目前最好的选择。

UPDATE2(2012 年 3 月 1 日)

举个例子。变量现在已移动:

      //fill
      visualization.da.C.d[0].en.S = "url(#blue)";

【问题讨论】:

【参考方案1】:

您可以使用MutationObserver 了解何时对 svg 进行了更改

将代码从'ready' 事件监听器移动到observer覆盖重置颜色的代码

如下面的sn-p...

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8"/>
    <title>Google Visualization API Sample</title>
    <script type="text/javascript" src="http://www.google.com/jsapi"></script>
    <script type="text/javascript">
      google.load('visualization', '1', packages: ['corechart']);
      google.load("jquery", "1.7.1");
    </script>
    <script type="text/javascript">
      function drawVisualization() 
        // Create and populate the data table.
        var data = new google.visualization.DataTable();
        var rowData = [['Year', 'North', 'West',  'South'],
                       ['2010', 197,     333,     298    ],
                       ['2011', 167,     261,     381    ]];
        var data = google.visualization.arrayToDataTable(rowData);

        var chartDiv = document.getElementById('visualization');
        visualization = new google.visualization.ColumnChart();

        // observe changes to the chart container
        var observer = new MutationObserver(function () 
          var svgns = "http://www.w3.org/2000/svg";
          var gradients = [["red","#C0504D","#E6B8B7"],
                           ["green","#9BBB59","#D8E4BC"],
                           ["blue","#4F81BD","DCE6F1"]];
          var svg_defs = $("#visualization iframe").contents().find('defs');
          // add gradients to svg defs
          for(var i = 0; i < gradients.length; i++)
            var grad = $(document.createElementNS(svgns, "linearGradient")).
                attr(id:gradients[i][0],x1:"0%",x2:"0%",y1:"0%",y2:"100%");
            var stopTop = $(document.createElementNS(svgns, "stop")).
                attr(offset:"0%","stop-color":gradients[i][1]);
            var stopBottom = $(document.createElementNS(svgns, "stop")).
                attr(offset:"100%","stop-color":gradients[i][2]);
            $(grad).append(stopTop).append(stopBottom);
            svg_defs.append(grad);
          
          // #3366cc, #dc3912, #ff9900 - replace default colors with gradients
          $("#visualization iframe").contents().find('rect[fill="#3366cc"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
          $("#visualization iframe").contents().find('rect[fill="#dc3912"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
          $("#visualization iframe").contents().find('rect[fill="#ff9900"]').attr('fill':'url(#blue)','stroke-width':0.4,'stroke':'#000000');
        );

        observer.observe(chartDiv, 
          childList: true,
          subtree: true
        );

        // Create and draw the visualization.
        visualization.draw(data,width:600, height:400);
      
      google.setOnLoadCallback(drawVisualization);
    </script>
  </head>
  <body style="font-family: Arial;border: 0 none;">
    <div id="visualization" style="width: 600px; height: 400px;"></div>
  </body>
</html>

【讨论】:

here is a working example to change the bar color on a gantt chart using MutationObserver

以上是关于向 Google-Visualization ColumnChart 添加渐变的主要内容,如果未能解决你的问题,请参考以下文章

React之父组件向子组件传值

合作 | 英国著名数字资产托管公司 Copper.co 引入 ROSE

向远程服务器添加公钥

使用 Google Charts 为这个 JSON 绘制柱形图 var_dump();数据

如何向此类添加复制构造函数和赋值运算符?

如何使div中的填充向内