diff --git a/css/main.css b/css/main.css index 46d1b0542e835e7c4207fa2eb816d07bbc13aba2..726fd36536282b22246ca1dfd93f503eedae5d73 100644 --- a/css/main.css +++ b/css/main.css @@ -309,3 +309,13 @@ svg{ #aboutStiffness{ line-height: 28px; } + +#start, #stepForwardOptions{ + display: none; +} +#reset{ + margin-left: 20px; +} +#stepForward{ + margin-left: 13px; +} diff --git a/index.html b/index.html index e0659f228c785aea827128ff65fc1c99b00b1317..e30e6850600519b39af75db70af4035a74a49992 100644 --- a/index.html +++ b/index.html @@ -460,8 +460,18 @@ <div class="indent"> <label>Average node error: <span id="globalError"></span></label> <a class="about floatRight" href="#" id="aboutError"><span class="fui-question-circle"></span></a> + </div><br/> + <b>Animation Settings:</b><br/> + <span class="floatRight">Δ t = <span id="deltaT"></span> seconds</span><br/><br/> + <a href="#" id="reset" class="btn btn-lg btn-default">Reset</a> + <a href="#" id="start" class="btn btn-lg btn-success">Start Simulation</a> + <a href="#" id="pause" class="btn btn-lg btn-warning">Pause Simulation</a> + <br/><br/> + <div id="stepForwardOptions" class="floatRight"> + Num Steps: <input id="numSteps" value="100" placeholder="" class="form-control" type="text"> + <a href="#" id="stepForward" class="btn btn-lg btn-default">Step Forward</a> </div> - + <br/><br/> <div class="extraSpace"></div> </div> <div id="svgViewer"></div> diff --git a/js/controls.js b/js/controls.js index 6644fd9382e610bebdeeb43b8c2addbfba720043..44ddae324487abfa98cd2c433ab372544cc334d4 100644 --- a/js/controls.js +++ b/js/controls.js @@ -409,6 +409,32 @@ function initControls(globals){ $("#aboutAxialStrainModal").modal("show"); }); + setLink("#start", function(){ + $("#pause").show(); + $("#reset").show(); + $("#start").hide(); + $("#stepForwardOptions").hide(); + globals.model.resume(); + }); + setLink("#pause", function(){ + $("#start").show(); + $("#stepForwardOptions").show(); + $("#pause").hide(); + globals.model.pause(); + }); + setLink("#reset", function(){ + if (!globals.threeView.running()) $("#reset").hide(); + globals.model.reset(); + }); + setLink("#stepForward", function(){ + var numSteps = $("#numSteps").val(); + numSteps = parseInt(numSteps); + if (isNaN(numSteps)) return; + if (numSteps<=0) return; + $("#numSteps").val(numSteps); + globals.model.step(numSteps); + }); + setInput("#strainClip", globals.strainClip, function(val){ globals.strainClip = val; }, 0.0001, 100); diff --git a/js/dynamic/dynamicSolver.js b/js/dynamic/dynamicSolver.js index 9f470c02915f782a76d41dff21ba8fa72e3cbfa9..1ac2be198649838b63dc2e4f7bda46c577c93e10 100644 --- a/js/dynamic/dynamicSolver.js +++ b/js/dynamic/dynamicSolver.js @@ -61,6 +61,7 @@ function initDynamicSolver(globals){ globals.gpuMath.step("zeroTexture", [], "u_lastPosition"); globals.gpuMath.step("zeroTexture", [], "u_velocity"); globals.gpuMath.step("zeroTexture", [], "u_lastVelocity"); + render(); //todo zero thetas // for (var i=0;i<creases.length;i++){ // lastTheta[i*4] = 0; @@ -68,10 +69,9 @@ function initDynamicSolver(globals){ // } } - function solve(){ + function solve(_numSteps){ if (globals.shouldSyncWithModel){ syncNodesAndEdges(); - // reset(); globals.shouldSyncWithModel = false; } else { if (globals.forceHasChanged) { @@ -94,17 +94,14 @@ function initDynamicSolver(globals){ updateMaterials(); globals.materialHasChanged = false; } - if (globals.shouldResetDynamicSim) { - reset(); - globals.shouldResetDynamicSim = false; - } if (globals.shouldChangeCreasePercent) { setCreasePercent(globals.creasePercent); globals.shouldChangeCreasePercent = false; } } - for (var j=0;j<steps;j++){ + if (_numSteps == undefined) _numSteps = steps; + for (var j=0;j<_numSteps;j++){ solveStep(); } render(); @@ -200,6 +197,7 @@ function initDynamicSolver(globals){ function setSolveParams(){ var dt = calcDt()/10;//todo factor of ten? + $("#deltaT").html(dt); var numSteps = 0.5/dt; globals.gpuMath.setProgram("thetaCalc"); globals.gpuMath.setUniformForProgram("thetaCalc", "u_dt", dt, "1f"); @@ -494,6 +492,7 @@ function initDynamicSolver(globals){ return { syncNodesAndEdges: syncNodesAndEdges, updateFixed: updateFixed, - solve: solve + solve: solve, + reset: reset } } \ No newline at end of file diff --git a/js/globals.js b/js/globals.js index 196a06b2f02a6b368bedf390f7fa44c0c8e7ee66..fee43b73c26d2b8f1b8b9e4938549bea18236c9e 100644 --- a/js/globals.js +++ b/js/globals.js @@ -52,7 +52,8 @@ function initGlobals(){ //save stl settings filename: null, extension: null, - doublesidedSTL: false + doublesidedSTL: false, + scale: 1 }; diff --git a/js/model.js b/js/model.js index 58a827755678cda5a702a5e01c31318cf5efeb30..48cc0faae1ef6060d73328037944127adf91cee2 100644 --- a/js/model.js +++ b/js/model.js @@ -126,6 +126,32 @@ function initModel(globals){ startSolver(); } + function reset(){ + if (globals.simType == "dynamic"){ + globals.dynamicSolver.reset(); + } else { + globals.staticSolver.reset(); + } + setGeoUpdates(); + globals.threeView.render(); + } + + function step(numSteps){ + if (globals.simType == "dynamic"){ + globals.dynamicSolver.solve(numSteps); + } else { + globals.staticSolver.step(numSteps); + } + setGeoUpdates(); + globals.threeView.render(); + } + + function setGeoUpdates(){ + geometry.attributes.position.needsUpdate = true; + if (globals.colorMode == "axialStrain") geometry.attributes.color.needsUpdate = true; + geometry.computeVertexNormals(); + } + var inited = false; startSolver(); @@ -138,9 +164,7 @@ function initModel(globals){ console.log("static"); } geometry.attributes.position.needsUpdate = true; - if (globals.colorMode == "axialStrain") geometry.attributes.color.needsUpdate = true; - geometry.computeVertexNormals(); - // geometry.computeFlatVertexNormals(); + setGeoUpdates(); }); } @@ -287,6 +311,8 @@ function initModel(globals){ return { pause: pause, resume: resume, + reset: reset, + step: step, getNodes: getNodes, getEdges: getEdges, getFaces: getFaces, diff --git a/js/pattern.js b/js/pattern.js index ff74ac600c1cc0cb78a5c0cfc013353cfe21bc4c..67dd1185967597f35073dee6dbc5b05a477f6932 100644 --- a/js/pattern.js +++ b/js/pattern.js @@ -174,7 +174,6 @@ function initPattern(globals){ } function getFacesAndVerticesForEdges(faces, allEdges){ - //todo merge this var allCreaseParams = [];//face1Ind, vertInd, face2Ind, ver2Ind, edgeInd, angle for (var i=outlines.length;i<allEdges.length;i++){ if (i>=outlines.length+mountains.length+valleys.length && diff --git a/js/threeView.js b/js/threeView.js index d607b99c8a8b974fe67b756b46ae9c913e91e505..2ec807699a3c4d0d19b121f378ed6d1263f1b623 100644 --- a/js/threeView.js +++ b/js/threeView.js @@ -61,6 +61,7 @@ function initThreeView(globals) { controls.noPan = true; controls.staticMoving = true; controls.dynamicDampingFactor = 0.3; + controls.addEventListener("change", render); var renderPass = new THREE.RenderPass( scene, camera ); @@ -90,9 +91,9 @@ function initThreeView(globals) { } function render() { - // if (!animationRunning) { - // _render(); - // } + if (!animationRunning) { + _render(); + } } function startAnimation(callback){ @@ -113,6 +114,10 @@ function initThreeView(globals) { if (animationRunning) pauseFlag = true; } + function running(){ + return animationRunning; + } + function _render(){ if (globals.ambientOcclusion) { // Render depth into depthRenderTarget @@ -186,6 +191,7 @@ function initThreeView(globals) { pauseAnimation: pauseAnimation, enableControls: enableControls, scene: scene, - camera: camera + camera: camera, + running: running } } \ No newline at end of file