Skip to content

Instantly share code, notes, and snippets.

@tomshanley
Last active April 16, 2020 05:02
Show Gist options
  • Save tomshanley/2d1ceb740fd8135d3bfa98597076f794 to your computer and use it in GitHub Desktop.
Save tomshanley/2d1ceb740fd8135d3bfa98597076f794 to your computer and use it in GitHub Desktop.
fresh block
license: mit
<!DOCTYPE html>
<head>
<meta charset="utf-8">
<script src="https://d3js.org/d3.v4.min.js"></script>
<style>
</style>
</head>
<body>
<script>
console.clear()
let data = "A=12, B=12, C=5, A&B=4, A&C=2, B&C=1, A&B&C=2"
//NEED TO CONVERT THIS INPUT TO DATA USED IN THE JOINS
let elements = ["A", "B", "C"]
let intersections = [
{"value": 12, "elements":[
{"element":"A", "included": true},
{"element":"B", "included": false},
{"element":"C", "included": false}
]},
{"value": 12, "elements":[
{"element":"A", "included": false},
{"element":"B", "included": true},
{"element":"C", "included": false}
]},
{"value": 5, "elements":[
{"element":"A", "included": false},
{"element":"B", "included": false},
{"element":"C", "included": true}
]},
{"value": 4, "elements":[
{"element":"A", "included": true},
{"element":"B", "included": true},
{"element":"C", "included": false}
]},
{"value": 2, "elements":[
{"element":"A", "included": true},
{"element":"B", "included": false},
{"element":"C", "included": true}
]},
{"value": 1, "elements":[
{"element":"A", "included": false},
{"element":"B", "included": true},
{"element":"C", "included": true}
]},
{"value": 2, "elements":[
{"element":"A", "included": true},
{"element":"B", "included": true},
{"element":"C", "included": true}
]}
]
intersections.sort((a,b) => b.value - a.value)
let sets = []
let setsValues = {}
intersections.forEach(function(i){
i.elements.forEach(function(e){
if (e.included){
setsValues[e.element] = setsValues[e.element] ? setsValues[e.element] : 0
setsValues[e.element] = setsValues[e.element] + i.value
}
})
})
intersections[0].elements.forEach(function(e){
let s = {}
s.set = e.element
s.value = setsValues[e.element]
sets.push(s)
})
let width = 800
let height = 800
let barChartWidthPct = 0.8
let barChartHeightPct = 0.6
let barChartWidth = barChartWidthPct * width
let barChartHeight = barChartHeightPct * height
let bottomPanelHeight = height - barChartHeight
let leftPanelWidth = width - barChartWidth
let xScaleBand = d3.scaleBand()
.domain([0,1,2,3,4,5,6])
.range([0, barChartWidth])
.padding(0.2)
var svg = d3.select("body").append("svg")
.attr("width", width)
.attr("height", height)
let intersectionSizeChartG = svg.append("g")
.attr("transform", "translate(" + (width - barChartWidth) + ",0)")
let setSizeChartG = svg.append("g")
.attr("transform", "translate(0, " + barChartHeight + ")")
let matrixChartG = svg.append("g")
.attr("transform", "translate(" + (width - barChartWidth) + ", " + barChartHeight + ")")
drawIntersectionSizeChart()
drawMatrixChart()
drawSetSizeChart()
function drawIntersectionSizeChart() {
let yScale = d3.scaleLinear()
.domain([0, d3.max(intersections, d => d.value)])
.range([barChartHeight, 0])
let bars = intersectionSizeChartG.selectAll(".bar")
.data(intersections)
.enter()
.append("g")
.attr("transform", function(d,i){
return "translate(" + xScaleBand(i) + ", 0)"
})
bars.append("rect")
.attr("y", d => yScale(d.value))
.attr("width", xScaleBand.bandwidth())
.attr("height", d => barChartHeight - yScale(d.value))
}
function drawMatrixChart() {
let yScalePoint = d3.scalePoint()
.domain(elements)
.range([0, bottomPanelHeight])
.padding(0.6)
let yScaleBand = d3.scaleBand()
.domain(elements)
.range([0, bottomPanelHeight])
.padding(0.2)
let rects = matrixChartG.selectAll("rect")
.data(elements)
.enter()
.append("rect")
.attr("x", 0)
.attr("y", d => yScaleBand(d))
.attr("width", barChartWidth)
.attr("height", yScaleBand.bandwidth())
.style("fill", function(d,i){
return i % 2 == 0 ? "Gainsboro" : "white"
})
let inter = matrixChartG.selectAll(".inter")
.data(intersections)
.enter()
.append("g")
.attr("transform", function(d,i){
return "translate(" + (xScaleBand(i) + xScaleBand.bandwidth()/2) + ", 0)"
})
let circles = inter.selectAll(".elements")
.data(d => d.elements)
.enter()
.append("g")
.attr("transform", function(d,i){
return "translate(0, " + yScalePoint(d.element) + ")"
})
circles.append("circle")
.attr("r", 10)
.style("opacity", function(d){
return d.included ? 1 : 0.2
})
let lines = inter.append("line")
.attr("y1", function(d){
let firstElement = ""
for (var e = 0; e < d.elements.length; e++) {
if (d.elements[e].included) {
firstElement = d.elements[e].element
break
}
}
return yScalePoint(firstElement)
})
.attr("y2", function(d){
let lastElement = ""
for (var e = 0; e < d.elements.length; e++) {
if (d.elements[e].included) {
lastElement = d.elements[e].element
}
}
return yScalePoint(lastElement)
})
.style("fill", "none")
.style("stroke", "black")
}
function drawSetSizeChart() {
let yScale = d3.scaleBand()
.domain(elements)
.range([0, bottomPanelHeight])
.padding(0.2)
let xScale = d3.scaleLinear()
.domain([0, d3.max(sets, d => d.value)])
.range([leftPanelWidth, 0])
let bars = setSizeChartG.selectAll(".bar")
.data(sets)
.enter()
.append("g")
.attr("transform", function(d, i){
return "translate(0, " + yScale(d.set) + ")"
})
bars.append("rect")
.attr("x", d => xScale(d.value))
.attr("width", d => leftPanelWidth - xScale(d.value))
.attr("height", yScale.bandwidth())
}
</script>
</body>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment