Skip to content

Instantly share code, notes, and snippets.

@maximeborges
Last active April 16, 2025 17:11
Show Gist options
  • Save maximeborges/31b7bfe5e3d4d8e31163702ebb802631 to your computer and use it in GitHub Desktop.
Save maximeborges/31b7bfe5e3d4d8e31163702ebb802631 to your computer and use it in GitHub Desktop.
Sankey Diagram with Google Spreadsheets
function onOpen() {
SpreadsheetApp.getUi()
.createMenu('Diagrams')
.addItem('Sankey', 'openDialog')
.addToUi();
}
function getSpreadsheetData() {
var sheet = SpreadsheetApp.getActive().getActiveSheet();
return sheet.getDataRange().getValues();
}
function openDialog() {
var html = HtmlService.createHtmlOutputFromFile('index')
.setHeight(800)
.setWidth(1000);
SpreadsheetApp.getUi().showModalDialog(html, 'Sankey Diagram');
}
<!DOCTYPE html>
<html>
<head>
<base target="_top">
<script src="https://www.google.com/jsapi"></script>
</head>
<body>
<div id="main"></div>
<script type="text/javascript">
var height = 800;
var margin = 10;
google.load('visualization', '1', {
packages: ['corechart', 'sankey']
});
google.setOnLoadCallback(initialize);
function initialize() {
google.script.run.withSuccessHandler(drawChart).getSpreadsheetData();
}
function drawChart(rows) {
var i = 0;
var rows_cleaned = []
for (; i < rows.length; i++) {
if(!rows[i][0] && !rows[i][1] && !rows[i][2]) {
continue;
}
rows_cleaned.push(rows[i].slice(0, 3));
}
console.log(rows)
var data = google.visualization.arrayToDataTable(rows_cleaned);
var chart = new google.visualization.Sankey(document.getElementById('main'));
google.visualization.events.addListener(chart, 'ready', onReady);
chart.draw(data, {width: 1000 - 2*margin, height: height/2});
}
function onReady(e) {
let frame = document.querySelector("#main > div:nth-child(1) > div:nth-child(1)");
let svg = frame.querySelector("div:nth-child(1) > svg:nth-child(1)");
frame.setAttribute("style", "position: relative; width: 100%; height: 100%;");
svg.setAttribute("style", "padding-top: " + 3*margin + "px;");
svg.setAttribute("height", height - (2+3)*margin);
svgToBitmap(svg, (canvas) => {
var cpy_btn = document.createElement("button");
cpy_btn.innerHTML = 'Copy image';
cpy_btn.setAttribute("style", "position: absolute;");
cpy_btn.onclick = () => {
try {
canvas.toBlob(function(blob) {
const item = new ClipboardItem({ "image/png": blob });
navigator.clipboard.write([item]);
});
} catch (error) {
console.error(error);
}
};
frame.appendChild(cpy_btn);
});
}
function svgToBitmap(svg, cb) {
var canvas = document.createElement('canvas');
var ctx = canvas.getContext('2d');
var data = (new XMLSerializer()).serializeToString(svg);
var img = new Image();
var svgBlob = new Blob([data], {type: 'image/svg+xml;charset=utf-8'});
var DOMURL = window.URL || window.webkitURL || window;
var url = DOMURL.createObjectURL(svgBlob);
// load svg image into canvas
var image = new Image();
image.onload = function() {
canvas.width = image.width;
canvas.height = image.height;
var context = canvas.getContext('2d');
context.drawImage(image, 0, 0);
cb(canvas);
}
image.src = url;
}
</script>
</body>
</html>

image

Sankey Diagrams within Google Spreadsheets

This Gist is there to help you creating a Sankey Diagram from your Google Spreadsheets.

Demo

Easy way

Go to my template Spreadsheet, go to File -> Create a copy.

This will copy the AppScript in a new project that you can start modifying.

The long way

Enabling AppScripts

If you already have the "Extensions" menu in the top toolbar, proceed to the next section.

Otherwise, it looks like Google Spreadsheets "Extensions" menu is not enabled by default. You might have to go to https://script.google.com/home and create a new project from there to make this menu appear.

Setup

  • Open a Spreadsheet
  • Click "Extensions" -> "Apps Scripts"
  • You should have a Code.gs file open, paste the corresponding code
  • Click on the + button on the left side to create a new file, choose HTML; name it ìndex (extension is added automatically
  • Paste the index.html code from below in there
  • Switch back to the Spreadsheet, reload the page to load the script

You should now have a "Diagrams" menu in the top toolbar.

Usage

  • Open a document for which you installed the script
  • Click "Diagrams" -> "Sankey"

This can take a few seconds, then you will see the diagram in a dialog window.

You can click on "Copy image" to get a PNG version of the diagram that you can paste directly in your spreadsheet.

Example Spreadsheet

https://docs.google.com/spreadsheets/d/1Qn5JXeWBFCneHvwyJjfHhZ0TB-ee1Lm9xpJ_9gAsDbY/edit?usp=sharing

@ramonlucas
Copy link

can't open any link.

@maximeborges
Copy link
Author

can't open any link.

Not sure what happened, should be working now.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment