Skip to content

Instantly share code, notes, and snippets.

@andreasplesch
Forked from jamesleesaunders/.block
Last active August 11, 2017 23:22
Show Gist options
  • Save andreasplesch/c9749c0dc5555d3c84d59581e2117320 to your computer and use it in GitHub Desktop.
Save andreasplesch/c9749c0dc5555d3c84d59581e2117320 to your computer and use it in GitHub Desktop.
3D Scatter Plot Using X3DOM and D3
! function(t, n) {
"object" == typeof exports && "undefined" != typeof module ? n(exports) : "function" == typeof define && define.amd ? define(["exports"], n) : n(t.d3_x3dom_axis = t.d3_x3dom_axis || {})
}(this, function(t) {
"use strict";
function n(t, n, e) {
function l(a) {
function l(t) {
var n;
switch (t) {
case "x":
n = [1, 0, 0];
break;
case "y":
n = [0, 1, 0];
break;
case "z":
n = [0, 0, 1]
}
return n
}
function d(t) {
var n;
switch (t) {
case "x":
n = [1, 1, 0, Math.PI];
break;
case "y":
n = [0, 0, 0, 0];
break;
case "z":
n = [0, 1, 1, Math.PI]
}
return n
}
var f, m, h, k, g = null == c ? e.ticks ? e.ticks.apply(e, o) : e.domain() : c,
y = null == s ? e.tickFormat ? e.tickFormat.apply(e, o) : r : s,
x = e.range(),
b = x[0],
v = x[x.length - 1],
j = a.selection ? a.selection() : a;
f = l(t), h = l(n), m = d(t), k = d(n);
var A = j.selectAll("transform").data([null]),
z = j.selectAll(".tick").data(g, e).order(),
L = z.exit(),
_ = z.enter().append("transform").attr("translation", function(t) {
return f.map(function(n) {
return e(t) * n
}).join(" ")
}).attr("class", "tick"),
D = z.select(".tickLine"),
F = z.select("billboard");
A = A.merge(A.enter().append("transform").attr("rotation", m.join(" ")).attr("translation", f.map(function(t) {
return t * (b + v) / 2
}).join(" ")).append("shape").call(i).attr("class", "domain")), z = z.merge(_), D = D.merge(_.append("transform"));
var I = _.append("transform");
I.attr("translation", h.map(function(t) {
return -t * p
})).append("billboard").attr("axisOfRotation", "0 0 0").append("shape").call(i).append("text").attr("string", y).append("fontstyle").attr("size", 1).attr("family", "SANS").attr("style", "BOLD").attr("justify", "MIDDLE "), F = F.merge(I), L.remove(), A.append("cylinder").attr("radius", .1).attr("height", v - b), D.attr("translation", h.map(function(t) {
return t * u / 2
}).join(" ")).attr("rotation", k.join(" ")).attr("class", "tickLine").append("shape").call(i).append("cylinder").attr("radius", .05).attr("height", u)
}
var o = [],
c = null,
s = null,
u = 1,
p = 1;
return l.scale = function(t) {
return arguments.length ? (e = t, l) : e
}, l.ticks = function() {
return o = a.call(arguments), l
}, l.tickArguments = function(t) {
return arguments.length ? (o = null == t ? [] : a.call(t), l) : o.slice()
}, l.tickValues = function(t) {
return arguments.length ? (c = null == t ? null : a.call(t), l) : c && c.slice()
}, l.tickFormat = function(t) {
return arguments.length ? (s = t, l) : s
}, l.tickSize = function(t) {
return arguments.length ? (u = +t, l) : u
}, l.tickPadding = function(t) {
return arguments.length ? (p = +t, l) : p
}, l
}
var e = "0.0.1",
a = Array.prototype.slice,
r = function(t) {
return t
},
i = function(t, n) {
return t.append("appearance").append("material").attr("diffuseColor", n || "black"), t
};
t.version = e, t.x3domAxis = n
});
<!DOCTYPE html >
<html>
<head>
<title>D3 : 3D Scatter Plot Using X3DOM</title>
<script type="text/javascript" src="http://d3js.org/d3.v4.0.0-alpha.28.min.js"></script>
<script type="text/javascript" src="http://x3dom.org/download/1.7.2/x3dom-full.js"></script>
<link rel="stylesheet" type="text/css" href="http://x3dom.org/download/1.7/x3dom.css" />
<script src="d3-x3dom-axis.js"></script>
</head>
<body>
<x3d id="chartholder"></x3d>
<script>
var makeSolid = function(selection, color) {
selection
.append("appearance")
.append("material")
.attr("diffuseColor", color || "black");
return selection;
};
var width = 800;
var height = 600;
var x3d = d3.select("#chartholder")
.attr("width", width + 'px')
.attr("height", height +'px')
.attr("showLog", 'false')
.attr("showStat", 'false');
d3.select('.x3dom-canvas')
.attr("width", 2 * width)
.attr("height", 2 * height);
var x = d3.scaleLinear().range([0, 40]);
var y = d3.scaleLinear().range([0, 40]);
var z = d3.scaleLinear().range([0, 40]);
var xAxis = d3_x3dom_axis.x3domAxis('x', 'z', x).tickSize(z.range()[1] - z.range()[0]).tickPadding(y.range()[0]);
var yAxis = d3_x3dom_axis.x3domAxis('y', 'z', y).tickSize(z.range()[1] - z.range()[0]);
var yAxis2 = d3_x3dom_axis.x3domAxis('y', 'x', y).tickSize(x.range()[1] - x.range()[0]).tickFormat(function(d){return ''});
var zAxis = d3_x3dom_axis.x3domAxis('z', 'x', y).tickSize(x.range()[1] - x.range()[0]);
var scene = x3d.append("scene");
var view_pos = [80, 20, 80];
var fov = 0.8;
var view_or = [0, 1, 0, 0.8];
scene.append("viewpoint")
.attr("id", 'dvp')
.attr("position", view_pos.join(" "))
.attr("orientation", view_or.join(" "))
.attr("fieldOfView", fov)
.attr("description", "defaultX3DViewpointNode").attr("set_bind", "true");
scene.append('group')
.attr('class', 'xAxis')
.call(xAxis)
.select('.domain').call(makeSolid, 'blue');
scene.append('group')
.attr('class', 'yAxis')
.call(yAxis)
.select('.domain').call(makeSolid, 'red');
scene.append('group')
.attr('class', 'yAxis')
.call(yAxis2)
.select('.domain').call(makeSolid, 'red');
scene.append('group')
.attr('class', 'zAxis')
.call(zAxis)
;//.select('.domain');
var n = 40;
var points = d3.range(n).map(function(d) {
var p = {};
p.x = Math.random();
p.z = Math.random();
p.y = Math.random();
return p;
});
scene.selectAll('.point')
.data(points)
.enter()
.append('transform')
.attr('class', 'point')
.attr('translation', function(d){ return x(d.x) + ' ' + y(d.y) + ' ' + z(d.z)})
//AP: try mouseover
.attr('onmouseover', 'handlemouseover(this, event);')
.append('shape')
.call(makeSolid, 'orange')
.append('sphere')
.attr('radius', 0.8);
scene.append('transform')
.attr('class', 'label')
.attr('scale', '1 1 1')
.append('billboard')
.attr('axisOfRotation', '0 0 0')
.append('shape')
.call(makeSolid,'0 0 0')
.append('Text')
.attr('class','labelText')
.attr('string', 'default label')
.append("fontstyle")
.attr("size", 1)
.attr("family", "SANS")
.attr("style", "BOLD")
.attr("justify", "END")
.attr("quality", "3");
function handlemouseover(target, event) {
scene.select(".label")
.attr('translation', target.translation);
scene.select(".labelText")
.attr('string', "y: "+(target.translation.split(' ')[1]/40.0).toPrecision(8));
}
</script>
</body>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment