package lib; import lib.Vec.Vec3; /** Reporesents a Point in a 3D `Float` System. Basicly a wrapper for Vec3 with some extra functions. `Y` represents the height of the point. **/ @:forward(x,y,z) abstract Pos3(Vec3) from Vec3 to Vec3{ inline public function new(i:Vec3) { this = i; } @:op(A + B) public function add(rhs: Vec3):Pos3 { return new Pos3({ y: this.y + rhs.y, x: this.x + rhs.x, z: this.z + rhs.z }); } @:op(A - B) public function sub(rhs: Vec3):Pos3 { return new Pos3({ y: this.y - rhs.y, x: this.x - rhs.x, z: this.z - rhs.z }); } @:op(A * B) public function multiplyScalar(rhs: Float): Pos3 { return new Pos3({ y: this.y * rhs, x: this.x * rhs, z: this.z * rhs }); } @:op(A / B) public function divideScalar(rhs: Float): Pos3 { return new Pos3({ y: this.y / rhs, x: this.x / rhs, z: this.z / rhs }); } @:op(-A) public function negate(): Pos3 { return new Pos3({ y: -this.y, x: -this.x, z: -this.z }); } public function dot(rhs: Vec3): Float { return this.x * rhs.x + this.y * rhs.y + this.z * rhs.z; } public function cross(rhs: Vec3):Pos3 { return new Pos3({ x: this.y * rhs.z - this.z * rhs.y, y: this.z * rhs.x - this.x * rhs.z, z: this.x * rhs.y - this.y * rhs.x }); } public function normalize():Pos3 { var l = length(); return multiplyScalar(1 / l); } public function length():Float { return Math.sqrt(this.x * this.x + this.y * this.y + this.z * this.z); } @:op(A == B) public function equals(rhs:Pos3):Bool { return close(rhs); } @:op(A != B) public function notEquals(rhs:Pos3):Bool { return !close(rhs); } public function close(rhs:Pos3, epsilon:Float = 0.001):Bool { return Math.abs(this.x - rhs.x) < epsilon && Math.abs(this.y - rhs.y) < epsilon && Math.abs(this.z - rhs.z) < epsilon; } public function toString():String { return 'Pos3(${this.x}, ${this.y}, ${this.z})'; } }