Built with blockbuilder.org
Last active
October 18, 2017 12:50
-
-
Save mforando/97888b52c45d3ba81008e9c66a5fad13 to your computer and use it in GitHub Desktop.
SigmoidSimple
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
license: mit |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!doctype html> | |
<head> | |
<meta charset="utf-8"> | |
<script src="https://d3js.org/d3.v4.min.js"></script> | |
</head> | |
<style> | |
body { | |
font-family: Franklin Gothic Book; | |
font-size: 0.8em; | |
} | |
h1 { | |
font-family: Franklin Gothic Medium; | |
font-size: 42px; | |
margin-bottom:10px; | |
margin-top:2px; | |
} | |
a.step-link { | |
font-family:Franklin Gothic Medium; | |
text-decoration: none; | |
z-index: 20; | |
display:inline-block; | |
overflow: hidden; | |
border: .5px solid gray; | |
font-family:Verdana; | |
font-size:10.5px; | |
border: 1px solid gray; | |
padding: 2px 5px 2px 5px; | |
color: black; | |
opacity:.6; | |
background-color: rgb(240,240,240); | |
} | |
a.step-link:last-child { | |
-webkit-border-radius: 3px; | |
-moz-border-radius: 3; | |
border-radius: 0px 3px 3px 0px; | |
} | |
a.step-link:first-child { | |
-webkit-border-radius: 3px; | |
-moz-border-radius: 3; | |
border-radius: 3px 0px 0px 3px; | |
} | |
a.step-link:hover, a.active { | |
opacity:1; | |
background-color: rgb(230,230,230); | |
} | |
#container{ | |
margin: auto; | |
width: 1000px; | |
} | |
#vis-container { | |
position: relative; | |
width: 1000px; | |
height: 1000px; | |
margin-top: 20px; | |
} | |
#annotation-steps { | |
position: absolute; | |
z-index: 40; | |
} | |
#vis-nav { | |
} | |
#vis-canvas { | |
position: absolute; | |
width: 1000px; | |
height: 1000px; | |
overflow: hidden; | |
background-color: none; | |
} | |
#tableauBezier1{ | |
position: absolute; | |
width: 1000px; | |
height: 1000px; | |
overflow: hidden; | |
background-color: none; | |
} | |
#vis-bezier { | |
position: absolute; | |
width: 1000px; | |
height: 1000px; | |
overflow: hidden; | |
z-index: 1000; | |
background-color: none; | |
} | |
.annotation-step { | |
background-color: green; | |
position: absolute; | |
display: none; | |
z-index:1000; | |
} | |
.annotation { | |
position: absolute; | |
} | |
.domain { | |
stroke: rgb(210,210,210); | |
} | |
.curve, .line { | |
stroke: black; | |
fill: none; | |
stroke-width: 1px; | |
stroke-opacity: .6; | |
} | |
.curve { | |
stroke: red; | |
stroke-width: 3px; | |
} | |
.control { | |
fill: #ccc; | |
stroke: #000; | |
stroke-width: .5px; | |
cursor: move; | |
} | |
.control.drag, .control:hover { | |
fill: rgb(0,50,100); | |
} | |
.t, .controltext { | |
font-size: .6em; | |
} | |
svg { | |
display: inline-block; | |
} | |
.curve { | |
stroke-width: 2px; | |
stroke: red; | |
stroke-opacity:.8; | |
} | |
.t { | |
font-size: 64px; | |
} | |
</style> | |
<body> | |
<div id="container"> | |
<div id="vis-nav"> | |
<a href="#" id="step0" class="step-link active">Sigmoid Function</a><a href="#" id="step1" class="step-link">Tableau Implementation</a> | |
</div> | |
<div id="vis-container"> | |
<div id="tableauBezier1"></div> | |
<div id="vis-canvas"></div> | |
<div class="annotation-step" id="step0-annotation" style="display:block;"> | |
<div class="annotation" id="step0-left-annotation" > | |
<div id="vis-nav"> | |
</div> | |
</div> | |
</div> | |
<script src="https://public.tableau.com/javascripts/api/tableau-2.min.js"></script> | |
<script src="https://public.tableau.com/javascripts/api/tableau-2.2.1.min.js"></script> | |
<script> | |
SigmoidAnimation() | |
var laststep = "step0"; | |
function tableauViz(url,htmlElement) { | |
var placeholderDiv = document.getElementById("tableauBezier1"); | |
var options = { | |
width: placeholderDiv.offsetWidth, | |
height: placeholderDiv.offsetHeight, | |
hideTabs: true, | |
hideToolbar: true, | |
onFirstInteractive: function () { | |
workbook = viz.getWorkbook(); | |
activeSheet = workbook.getActiveSheet(); | |
} | |
}; | |
viz = new tableau.Viz(placeholderDiv, url, options); | |
} | |
function switchStep(newStep) | |
{ | |
d3.selectAll(".step-link").classed("active", false); | |
d3.select("#" + newStep).classed("active", true); | |
if (newStep=="step0"){ | |
SigmoidAnimation() | |
;} | |
else { | |
d3.selectAll("#vis-bezier").remove(); | |
} | |
if (newStep=="step1"){ | |
if (laststep!="step2"){ | |
d3.selectAll("#tableauBezier1").remove(); | |
d3.selectAll("#vis-container").append("div").attr("id","tableauBezier1"); | |
tableauViz("https://public.tableau.com/views/TableauUsersGroupSigmoidFunction/SimgoidDash") | |
;} | |
else { | |
;} | |
} | |
if (newStep=="step2"){ | |
d3.selectAll("#tableauBezier1").remove(); | |
d3.selectAll("#vis-container").append("div").attr("id","tableauBezier1"); | |
tableauViz("https://public.tableau.com/views/TableauUsersGroupRankingsDataset/RawData") | |
;} | |
laststep = newStep; | |
} | |
function switchAnnotation(newStep) | |
{ | |
d3.selectAll(".annotation-step") | |
.style("display", "none") | |
.style("opacity", 0.0); | |
console.log(newStep + "-annotation") | |
d3.select("#" + newStep + "-annotation") | |
.style("display", "block") | |
.transition().delay(300).duration(2000) | |
.style("opacity", 1); | |
} | |
d3.selectAll("a.step-link").on("click", function(d) { | |
var clickedStep = d3.select(this).attr("id"); | |
switchStep(clickedStep); | |
switchAnnotation(clickedStep); | |
return false; | |
}); | |
function SigmoidAnimation() { | |
var w = 1000, | |
h = 1000, | |
t = .5, | |
delta = .01, | |
padding = 0, | |
bezier = {}, | |
n = 4, | |
line = d3.line().x(function(d){return d.x;}).y(function(d){return d.y;}); | |
var lineGenerator = d3.line(); | |
var points = [ | |
{x: 50, y: 300}, | |
{x: 350,y: 100} | |
]; | |
var svgBezier = d3.select("#vis-canvas").append("div").attr("id","vis-bezier") | |
.append("svg") | |
.attr("width", w + 2 * padding) | |
.attr("height", h + 2 * padding) | |
svgBezier.append("rect").attr("width",w).attr("height",h).attr("fill","white") | |
var vis = svgBezier.attr("transform", "translate(" + padding + "," + padding + ")") | |
var curve = svgBezier.append("g").append("path").attr("class", "curve"); | |
var controlPath = svgBezier.append("g"); | |
var circles = svgBezier.append("g"); | |
var PathData = []; | |
var lineGenerator = d3.line(); | |
controlPath.append("line").attr("id","controlPath1").attr("x1",points[0].x).attr("x2",points[0].x).attr("y1",65).attr("y2",400).attr("stroke","black").attr("stroke-width",.5) | |
controlPath.append("line").attr("id","controlPath1").attr("x1",points[1].x).attr("x2",points[1].x).attr("y1",65).attr("y2",400).attr("stroke","black").attr("stroke-width",.5) | |
circles.selectAll("circle.control") | |
.data(points) | |
.enter() | |
.append("circle") | |
.attr("class", "control") | |
.attr("z-index",10) | |
.attr("r", 7) | |
.attr("cx", x) | |
.attr("cy", y) | |
.call(d3.drag() | |
.on("start", function(d) { | |
this.__origin__ = [d.x, d.y]; | |
d3.select(this).classed("drag", true); | |
}) | |
.on("drag", function(d) { | |
getSigmoid(); | |
//d.x = Math.min(w, Math.max(0, this.__origin__[0] += d3.event.dx)); | |
d.y = Math.min(400, Math.max(15, this.__origin__[1] += d3.event.dy)); | |
bezier = {}; | |
update(); | |
vis.selectAll("circle.control") | |
// .attr("cx", x) | |
.attr("cy", y); | |
}) | |
.on("end", function() { | |
delete this.__origin__; | |
d3.select(this).classed("drag", false); | |
})); | |
vis.append("text") | |
.attr("class", "t") | |
.attr("x", 100) | |
.attr("y", 45) | |
.attr("text-anchor", "middle"); | |
vis.selectAll("text.controltext") | |
.data(points) | |
.enter() | |
.append("text") | |
.attr("class", "controltext") | |
.attr("x", x) | |
.attr("y", y) | |
.attr("dx", "10px") | |
.attr("dy", "15px") | |
.text(function(d, i) { return "P" + i }); | |
getSigmoid(); | |
update(); | |
var last = 0; | |
d3.timer(function(elapsed) { | |
t = (t + (elapsed - last) / 5000) % 1; | |
last = elapsed; | |
update(); | |
}); | |
function update() { | |
curve.attr("d", lineGenerator(PathData.slice(0,PathData.length*t))); | |
vis.selectAll("text.controltext").attr("x", x).attr("y", y); | |
t1 = t*12-6; | |
if (t1<0){color = "red";} | |
else { color = "green";} | |
vis.selectAll("text.t").attr("fill",color) | |
.text("t=" + t1.toFixed(1)); | |
vis.selectAll(".controlPath1") | |
} | |
controlPath1 = []; | |
controlPath2 = []; | |
//function to recreate an array of points for curve path. Run with drag events to update array. | |
function getSigmoid(){ | |
x1 = points[0].x; | |
x2 = points[1].x; | |
y1 = points[0].y; | |
y2 = points[1].y; | |
controlPath1 = [[x1,100],[x1,500]] | |
controlPath2 = [[x2,100],[x2,500]] | |
PathData = []; | |
for (z=-6; z<=6; z+=.05) { | |
sigmoid = 1/(1+ Math.pow(Math.exp(1),-z )) | |
sigmoidX = x1+(x2-x1)*((z+6)/12); | |
sigmoidY = y1 + (y2-y1)*sigmoid; | |
PathData.push([sigmoidX,sigmoidY]); | |
;} | |
;} | |
function interpolate(d, p) { | |
if (arguments.length < 2) p = t; | |
var r = []; | |
for (var i=1; i<d.length; i++) { | |
var d0 = d[i-1], d1 = d[i]; | |
r.push({x: d0.x + (d1.x - d0.x) * p, y: d0.y + (d1.y - d0.y) * p}); | |
} | |
return r; | |
} | |
function getLevels(d, t_) { | |
if (arguments.length < 2) t_ = t; | |
var x = [points.slice(0, d)]; | |
for (var i=1; i<d; i++) { | |
x.push(interpolate(x[x.length-1], t_)); | |
} | |
return x; | |
} | |
function x(d) {return d.x; } | |
function y(d) {return d.y; } | |
;} | |
</script> | |
</body> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment