Skip to content

Instantly share code, notes, and snippets.

@1wheel
Last active August 21, 2016 06:24
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save 1wheel/ed387b59d4968d1ed9ffbac10d13b22c to your computer and use it in GitHub Desktop.
Save 1wheel/ed387b59d4968d1ed9ffbac10d13b22c to your computer and use it in GitHub Desktop.
word random walk
<!DOCTYPE html>
<meta charset='utf-8'>
<body style='background: #fff;'>
<canvas width='960' height='300'></canvas>
</body>
<script src='//d3js.org/d3.v4.min.js'></script>
<script>
var width = 960,
height = 300,
s = 2,
w = Math.floor(960/s),
h = Math.floor(300/s)
var points = d3.range(w*h).map(function(i){
return {x: i % w, y: i/w >> 0, i: i}
})
points.forEach(function(d, i){
d.px = d.x*s
d.py = d.y*s
d.l = d.x ? points[i - 1] : d
d.t = d.y ? points[i - w] : d
})
var canvas = d3.select('canvas').node()
var ctx = canvas.getContext('2d')
setPointsOn(points)
var mPos = {px: 0, py: 0}
d3.select('body')
.on('mousemove', function(){
mPos = {px: d3.mouse(this)[0], py: d3.mouse(this)[1]} })
.on('click', function(){
if (Math.random() < .5){
onPoints.forEach(function(d){ d.y = h - d.y })
} else{
onPoints.forEach(function(d){ d.x = w - d.x })
}
})
var onPoints = points.filter(function(d){ return d.on })
d3.timer(function(t){
ctx.clearRect(0, 0, width, height);
ctx.fillStyle = '#000'
ctx.fillRect(0, 0, width, height);
ctx.beginPath()
onPoints.forEach(function(d, i){
var dx = (Math.random() - .5)*1
var dy = (Math.random() - .5)*1
if (isWithin(d, mPos, 50)){
dx += mPos.px - d.px
dy += mPos.py - d.py
dx *= -1/5
dy *= -1/5
if (Math.random() < .4){
d.px = d.x*s
d.py = d.y*s
dx = 0
dy = 0
}
}
else if (Math.random() < .3){
dx = xor(dx < 0, d.x*s - d.px < 0) ? -dx : dx
dy = xor(dy < 0, d.y*s - d.py < 0) ? -dy : dy
dx /= 1/5
dy /= 1/5
// d.px = d.x*s
// d.py = d.y*s
// dx = 0
// dy = 0
}
d.px += dx
d.py += dy
if (d.l.on && isWithin(d, d.l, 50)){
ctx.moveTo(d.px, d.py)
ctx.lineTo(d.l.px, d.l.py)
}
if (d.t.on && isWithin(d, d.t, 50)){
ctx.moveTo(d.px, d.py)
ctx.lineTo(d.t.px, d.t.py)
}
})
ctx.strokeStyle = 'rgba(0,255,0,.2)'
ctx.lineWidth = 1
ctx.stroke()
})
function setPointsOn(points) {
ctx.font = '600 300px sans-serif'
ctx.textAlign = 'center';
ctx.textBaseline = 'middle';
ctx.fillText('words', width/2, height/2);
var imageData = ctx.getImageData(0, 0, width, height).data
points.forEach(function(d){
d.on = imageData[(d.py*width + d.px)*4 + 3]
})
}
function xor(a, b){ return (a || b) && !(a && b) }
function isWithin(a, b, dist){
return Math.abs(a.px - b.px) + Math.abs(a.py - b.py) < dist
}
d3.select(self.frameElement).style('height', h*s + 'px');
</script>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment