From efe302717807f2e002e885669bba4d7edbdd5087 Mon Sep 17 00:00:00 2001 From: Zoe Love Date: Sun, 13 Nov 2016 04:09:24 +0530 Subject: [PATCH] Finally added whole converted tested verlet script into server as module --- __server__/__client__/webgl/js/main.js | 108 ++++++++--- .../__client__/webgl/js/verlet-1.0.0.js | 7 +- __server__/server.js | 4 +- body/player.js | 23 ++- body/tentacle.js | 181 ++++++++++++++++++ geometry/vector2.js | 48 +++++ module/body.js | 9 +- module/mathf.js | 16 ++ module/octomath.js | 2 +- 9 files changed, 365 insertions(+), 33 deletions(-) create mode 100644 body/tentacle.js create mode 100644 module/mathf.js diff --git a/__server__/__client__/webgl/js/main.js b/__server__/__client__/webgl/js/main.js index f3fbd9a..8dd7382 100644 --- a/__server__/__client__/webgl/js/main.js +++ b/__server__/__client__/webgl/js/main.js @@ -736,6 +736,8 @@ class Body { this.tentacles = [] ; this.Settings() ; + + this.tentacle1 ; } Settings() { this.gravity = 0 ; @@ -750,7 +752,27 @@ class Body { // tentacle.Move(this.Transform.position , true); this.tentacles.push(tentacle); } - + // DrawTenta() { + // if(this.tentacle1) { + // var c , i ; + // c=0; + // i=0; + // console.log(this.tentacle1[0]) ; + // var ctx = elements.ctx ; + // for (i in this.tentacle1) { + // for (j in this.tentacle1.pos) { + // var particles = this.tentacle1[i] ; + + // ctx.save() ; + // ctx.beginPath() ; + // ctx.arc(particles[j].pos.x , particles[j].pos.y , 10,0,Math.PI*2,false) ; + // ctx.stroke() ; + // ctx.fill() ; + // ctx.restore() ; + // } + // } + // } + // } Translate(vec) { this.Transform.position.x = vec.x ; this.Transform.position.y = vec.y ; @@ -795,6 +817,26 @@ class Body { ctx.restore(); ctx.save() ; + // if(this.tentacle1) { + // var c , i ; + // c=0; + // i=0; + // console.log(this.tentacle1[0]) ; + // var ctx = elements.ctx ; + // for (i in this.tentacle1) { + // for (j in this.tentacle1.pos) { + // var particles = this.tentacle1[i] ; + + // ctx.save() ; + // ctx.beginPath() ; + // ctx.arc(particles[j].pos.x , particles[j].pos.y , 10,0,Math.PI*2,false) ; + // ctx.stroke() ; + // ctx.fill() ; + // ctx.restore() ; + // } + // } + // } + // console.log(ctx.measureText(width)); ctx.font="23px Georgia"; @@ -1220,6 +1262,27 @@ function Init() { data.Transform.position.y += elements.canvas.height ; Players[data.id].newTransform.position = data.Transform.position ; + + + // Players[data.id].tentacle1 = data.tentacles ; + // var c , i ; + // c=0; + // i=0; + // var ctx = elements.ctx ; + // for (i in data.tentacles) { + // for (j in data.tentacles.pos) { + // var particles = data.tentacles[i] ; + + // ctx.save() ; + // ctx.beginPath() ; + // ctx.arc(particles[j].pos.x , particles[j].pos.y , 10,0,Math.PI*2,false) ; + // ctx.stroke() ; + // ctx.fill() ; + // ctx.restore() ; + // } + // } + + } else if(data.type == 'food') { Foods[data.id].position = data.Transform.position ; @@ -1347,7 +1410,7 @@ window.onresize = function() { room.Draw(ctx , camera. xView , camera.yView); } -var sim ; //= new VerletJS(width, height, canvas); +// var sim ; //= new VerletJS(width, height, canvas); window.onload = function() { var canvas = document.getElementById("game" ); @@ -1362,7 +1425,7 @@ window.onload = function() { canvas.width = width ; canvas.height = width ; - sim = new VerletJS(width, width, canvas); + // sim = new VerletJS(width, width, canvas); MouseHandler = new Mouse(canvas) ; KeyboardHandler = new Keyboard(canvas) ; @@ -1370,10 +1433,10 @@ window.onload = function() { elements.ctx = ctx ; - sim.gravity = new Vec2(0,0); - sim.friction = 0.98; + // sim.gravity = new Vec2(0,0); + // sim.friction = 0.98; - var tree1 = sim.tree(new Vec2(width/2,height-120), 5, 70, 0.95, (Math.PI/2)/3); + // var tree1 = sim.tree(new Vec2(width/2,height-120), 5, 70, 0.95, (Math.PI/2)/3); // var FPS =30 ; // var INTERVAL = 1000/FPS ; // var STEP = INTERVAL/1000 ; @@ -1449,25 +1512,26 @@ function Draw() { Players[IDs[i]].tentacles[j].Draw(elements.ctx , camera.xView , camera.yView) ; } Players[IDs[i]].Draw(elements.ctx , camera.xView , camera.yView) ; + // Players[IDs[i]].DrawTenta() ; // console.log(IDs[i] +" , "+socket.id); } - var c , i ; - c=0; - i=0; - var ctx = elements.ctx ; - for (c in sim.composites) { - for (i in sim.composites[c].particles) { - var particles = sim.composites[c].particles; + // var c , i ; + // c=0; + // i=0; + // var ctx = elements.ctx ; + // for (c in sim.composites) { + // for (i in sim.composites[c].particles) { + // var particles = sim.composites[c].particles; - ctx.save() ; - ctx.beginPath() ; - ctx.arc(particles[i].pos.x , particles[i].pos.y , 10,0,Math.PI*2,false) ; - ctx.stroke() ; - ctx.fill() ; - ctx.restore() ; - } - } + // ctx.save() ; + // ctx.beginPath() ; + // ctx.arc(particles[i].pos.x , particles[i].pos.y , 10,0,Math.PI*2,false) ; + // ctx.stroke() ; + // ctx.fill() ; + // ctx.restore() ; + // } + // } } @@ -1513,7 +1577,7 @@ function Update() { 5 , 4); } } - sim.frame(16); + // sim.frame(16); camera.Update(); diff --git a/__server__/__client__/webgl/js/verlet-1.0.0.js b/__server__/__client__/webgl/js/verlet-1.0.0.js index e4e0a44..b3731bf 100644 --- a/__server__/__client__/webgl/js/verlet-1.0.0.js +++ b/__server__/__client__/webgl/js/verlet-1.0.0.js @@ -52,7 +52,7 @@ exports.AngleConstraint = AngleConstraint function DistanceConstraint(a, b, stiffness, distance /*optional*/) { this.a = a; // A is particle - this.b = b; + this.b = b; this.distance = typeof distance != "undefined" ? distance : a.pos.sub(b.pos).length(); this.stiffness = stiffness; } @@ -551,14 +551,15 @@ Composite.prototype.pin = function(index, pos) { VerletJS.prototype.frame = function(step) { var i, j, c; - + // console.log(this.composites.length); for (c in this.composites) { + for (i in this.composites[c].particles) { var particles = this.composites[c].particles; // console.log(particles[i]); // calculate velocity var velocity = particles[i].pos.sub(particles[i].lastPos).scale(this.friction); - + // velocity = particles[i] // ground friction if (particles[i].pos.y >= this.height-1 && velocity.length2() > 0.000001) { var m = velocity.length(); diff --git a/__server__/server.js b/__server__/server.js index 8613b9b..2e901f7 100644 --- a/__server__/server.js +++ b/__server__/server.js @@ -88,7 +88,7 @@ fw.on('connection' , function(socket) { if(Players["/#"+id] == null) { var __player = new Octopod.Body.Player(oath , id , secId) ; __player.Init(10,1,5); - + __player.AddTentacle() ; Players["/#"+id] = __player ; socket.init = true ; @@ -170,7 +170,7 @@ fw.on('connection' , function(socket) { // Players[socket.id].Stop() ; // Players[socket.id] = null ; }); - socket.on('Bind-Tentacle' , function(x,y) { + socket.on('Bind-Tentacle' , function(x,y) { // trash in this branch var angleToMouse = Octopod.OctoMath.Angle.MouseToAngle(x,y) * Math.PI/180 ; var player = Players[socket.id]; var d1 = Octopod.Geometry.Vector2.Distance( diff --git a/body/player.js b/body/player.js index 1923123..7f465ef 100644 --- a/body/player.js +++ b/body/player.js @@ -4,6 +4,8 @@ var Geometry = require('../module/geometry.js'); var Component = require('../module/component.js'); // var Geometry = require('../module/geometry.js'); var OctoMath = require('../module/octomath.js'); + +var Tentacle = require('../body/tentacle.js') ; class Player { constructor(oath , id , name , secId) { this.oath = oath ; @@ -14,6 +16,7 @@ class Player { this.Camera = new Component.Camera(0,0,700,550); this.status = false ; + this.tentacles = [] ; // this.oath = "socket" ; this.secId = secId ; // this.range = 0 ; @@ -55,6 +58,10 @@ class Player { object_player["Transform"] = this.Transform ; object_player["oath"] = this.oath ; object_player["active"] = false ; + object_player["tentacles"] = [] ; + + for(var i=0 ; i < this.tentacles.length ; i++) + object_player["tentacles"].push(this.tentacles[i].particles) ; return object_player ; @@ -65,9 +72,21 @@ class Player { // t.Transform.angle = 0 ; this.Updating = setInterval ( function() { t.Update(); } , time) ; } - + AddTentacle() { + // console.log(Tentacle) ; + // console.log(OctoMath) ; + // console.log(Geometry) ; + // console.log(Component) ; + this.tentacles.push(new Tentacle(this.Transform.position , 5, 70, 0.95, (Math.PI/2)/3)) ; + } + FocusTentacles(node) { + for(var i = 0 ; i < this.tentacles.length ; i++) + this.tentacles[i].particles[this.tentacles[i].particles.length - 1].pos.Renew(node) ; + } Update() { - + for(var i = 0 ; i < this.tentacles.length ; i++) + this.tentacles[i].Update() ; + if(this.Jerk > this.JerkMax) { this.JerkSpeed = -Math.abs(this.JerkSpeed) ; } diff --git a/body/tentacle.js b/body/tentacle.js new file mode 100644 index 0000000..b121534 --- /dev/null +++ b/body/tentacle.js @@ -0,0 +1,181 @@ +"use strict"; + +var Vector2 = require("../module/geometry.js").Vector2 ; +var Mathf = require("../module/mathf.js") ; +class Particle { + constructor(pos) { + this.pos = pos ; + this.lastPos = pos ; + } +} +class AngleConstraint { + constructor(startPar , centerPar , endPar , stiffness) { + this.start = startPar ; + this.center = centerPar ; + this.end = endPar ; + + this.angle = Vector2.AngleBetween2(startPar.pos , centerPar.pos , endPar.pos) ; + + this.stiffness = stiffness ; + } + Relax(stepCoef) { + var angle = Vector2.AngleBetween2(this.start.pos , this.center.pos , this.end.pos) ; + var diff = angle - this.angle ; + + if(diff <= -Math.PI) + diff += 2*Math.PI ; + else if(diff >= Math.PI) + diff -= 2*Math.PI ; + + diff *= stepCoef*this.stiffness ; + + this.start.pos = Vector2.Rotate(this.center.pos , this.start.pos , diff); + this.end.pos = Vector2.Rotate(this.center.pos , this.end.pos , -diff); + this.center.pos = Vector2.Rotate(this.start.pos, this.center.pos , diff); + this.center.pos = Vector2.Rotate(this.end.pos, this.center.pos , -diff); + } +} +class PinConstraint { + constructor(par) { + this.parent = par ; + this.pos = par.pos ; + } + Relax(stepCoef) { + this.parent.pos.Renew(this.pos) ; + // this.parent.pos.x = pos.x ; + // this.parent.pos.y = pos.y ; + } +} +class DistanceConstraint { + constructor(par1 , par2 , stiffness , distance) { + this.parent = par1 ; + this.child = par2 ; + + this.stiffness = stiffness ; + this.distance = distance || Vector2.Distance(par1 , par2) ; + } + Relax(stepCoef) { + var normal = Vector2.Sub(this.parent.pos , this.child.pos) ; + var m = Vector2.Square(normal) ; + + normal = Vector2.Scale( normal , + ((this.distance*this.distance - m)/m)*this.stiffness*stepCoef) ; + + this.parent.pos = Vector2.Add(this.parent.pos , normal); + this.child.pos = Vector2.Sub(this.child.pos , normal); + } +} +// class Composite { +// constructor() { +// this.particles = [] ; +// this.costraints = [] ; +// } +// } + +class Tentacle { + constructor(origin , depth , branchLength , segementCoef , theta) { + this.particles = [] ; + this.constraints = [] ; + + var lineCoef = 0.7 ; + // simulation params + this.gravity = new Vector2(0,0.2); + this.friction = 0.99; + this.groundFriction = 0.8; + + this.origin = origin ; + this.base = new Particle(origin) ; + this.root = new Particle(Vector2.Add(origin , new Vector2(0,10)) ); + + // this.composite = new Composite() ; + // this.composite.particles.push(this.base) ; + // this.composite.particles.push(this.root) ; + // this.composite.pin(0) ; + // this.composite.pin(1) ; + + this.Pin(this.base) ; + this.Pin(this.root) ; + + var branch = this.CreateConstraint(this.base , 0 , depth , segementCoef , new Vector2(0,-1) , branchLength , theta, lineCoef) ; + + this.constraints.push(new AngleConstraint(this.root , this.base , branch , 1) ) ; + + // this.composites.push(composite) ; + } + Pin(particle) { + this.particles.push(particle) ; + var pc = new PinConstraint(particle , particle.pos) ; + this.constraints.push(pc) ; + + return pc ; + } + CreateConstraint(parent , i , nMax , coef , vec_normal , branchLength , theta , lineCoef) { + var m = Vector2.Add(parent.pos , Vector2.Scale(vec_normal , branchLength*coef) ); + var particle = new Particle(m) ; + this.particles.push(particle); + + var dc = new DistanceConstraint(parent , particle , lineCoef) ; + + this.constraints.push(dc) ; + + if(i < nMax) { + var a = this.CreateConstraint( particle , + i+1 , + nMax , + coef*coef , + Vector2.Rotate(vec_normal , new Vector2(0,0) , -theta)); + + var jointStrength = Mathf.Lerp(0.7 , 0 , i/nMax) ; + this.constraints.push(new AngleConstraint( parent , + particle , + a , + jointStrength)) ; + } + return particle ; + } + Update() { + var i , j , particles; + i=0 ; + j=0 ; + particles = this.particles ; + + for(i in this.particles) { + + var velocity = Vector2.Sub( Vector2.Scale(particles[i].pos , this.friction) , + particles[i].lastPos) ; + + if(particles[i].pos.y >= this.height - 1 && Vector2.Square(velocity) > 0.000001 ) { + var m = Vector2.Length(velocity) ; + velocity.x /= m ; + velocity.y /= m ; + velocity = Vector2.Scale(velocity , m*this.groundFriction) ; + + particles[i].lastPos.Renew(particles[i].pos) ; + + particles[i].pos = Vector2.Add(particles[i].pos , this.gravity); + + particles[i].pos = Vector2.Add(particles[i].pos , velocity) ; + } + + var stepCoef = 1/16 ; + + // if(node) + // this.particles[this.particles.length-1].pos.Renew(node) ; + + var constraints = this.constraints ; + // console.log(constraints); + for(var i = 0 ; i < 16 ; i++) { + for(var j = 0 ; j < constraints.length ; j++) { + // console.log(constraints[j]); + constraints[j].Relax(stepCoef) ; + + } + } + // bounds checking + // for (i in particles) + // this.bounds(particles[i]); + } + } +} + +module.exports = Tentacle ; \ No newline at end of file diff --git a/geometry/vector2.js b/geometry/vector2.js index 5cab039..fe12b0e 100644 --- a/geometry/vector2.js +++ b/geometry/vector2.js @@ -5,6 +5,10 @@ class Vector2 { this.x = x || 0 ; this.y = y || 0 ; } + Renew(vec) { + this.x = vec.x || 0 ; + this.y = vec.y || 0 ; + } static Distance(vec1 , vec2) { var a = vec1.x - vec2.x ; a *= a ; @@ -13,6 +17,50 @@ class Vector2 { // var distance = Math.sqrt(a+b); return Math.sqrt(a+b) ; } + // Add(vec) { + // this.x += vec.x ; + // this.y += vec.y ; + + // return this ; + // } + static Sub(vec1 , vec2) { + var m = new Vector2(vec1.x - vec2.x , vec1.y - vec2.y) ; + return m ; + } + static Square(vec) { + return vec.x*vec.x + vec.y*vec.y ; + } + static Length(vec) { + return Math.sqrt(Vector2.Square(vec)) ; + } + static Scale(vec1 , coef) { + var m = new Vector2(vec1.x * coef , vec1.y * coef) ; + return m ; + } + static Add(vec1 , vec2) { + var m = new Vector2(vec1.x + vec2.x , vec1.y + vec2.y) ; + return m ; + } + static Rotate(origin , vec , theta) { + var x = vec.x - origin.x ; + var y = vec.y - origin.y ; + + return new Vector2(x*Math.cos(theta) - y*Math.sin(theta) + origin.x , + x*Math.sin(theta) + y*Math.cos(theta) + origin.y) ; + } + static AngleBetween(vec1 , vec2) { + var x = vec1.x * vec2.y - vec1.y * vec2.x ; + var y = vec1.x * vec2.x + vec1.y * vec2.y ; + + return Math.atan2(x,y) ; + } + + static AngleBetween2(vec1 , vec2 , vec3) { + var vLeft = Vector2.Sub(vec1 , vec2) ; + var vRight = Vector2.Sub(vec3 , vec2) ; + + return Vector2.AngleBetween(vLeft , vRight) ; + } } module.exports = Vector2 ; \ No newline at end of file diff --git a/module/body.js b/module/body.js index 7ac34c7..426f3a4 100644 --- a/module/body.js +++ b/module/body.js @@ -2,6 +2,9 @@ var Player = require('../body/player.js'); var Food = require('../body/food.js'); var Map = require('../body/map.js'); -var Body = module.exports = {Player : Player, - Food : Food, - Map : Map} ; +var Tentacle = require('../body/tentacle.js') ; + +var Body = module.exports = { Player : Player, + Food : Food, + Map : Map, + Tentacle : Tentacle} ; diff --git a/module/mathf.js b/module/mathf.js new file mode 100644 index 0000000..cb39b84 --- /dev/null +++ b/module/mathf.js @@ -0,0 +1,16 @@ +"use strict"; + +class Mathf { + constructor() {} + + static Lerp(start , end , t) { + var ps = 1-t ; + var pe = t ; + var r = 0 ; + + r = ps * start + pe * end; + return r ; + } +} + +module.exports = Mathf ; \ No newline at end of file diff --git a/module/octomath.js b/module/octomath.js index c5c0d9c..15f1d3a 100644 --- a/module/octomath.js +++ b/module/octomath.js @@ -1,7 +1,7 @@ "use strict" ; var Geometry = require("../module/geometry.js"); var Interpolate = { - DotProduct : function(a,b) { + DotProduct : function(a,b) { var s = 0 ; for(var i = 0 ; i < a.length ; i++) { s += a[i] * b[i] ;