;; -*- mode: scheme; -*-
;; Planet Fluxus Copyright (C) 2013 Dave Griffiths
;;
;; This program is free software: you can redistribute it and/or modify
;; it under the terms of the GNU Affero General Public License as
;; published by the Free Software Foundation, either version 3 of the
;; License, or (at your option) any later version.
;;
;; This program is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
;; GNU Affero General Public License for more details.
;;
;; You should have received a copy of the GNU Affero General Public License
;; along with this program.  If not, see <http://www.gnu.org/licenses/>.

(load "flx/scm/random.jscm")
(load "flx/scm/vec3.jscm")
(load "flx/scm/quat.jscm")
(load "flx/scm/matrix.jscm")
(load "flx/scm/plane.jscm")
(load "flx/scm/boundingbox.jscm")

(js "var sin=Math.sin")
(js "var cos=Math.cos")
(js "var tan=Math.tan")
(js "var pi = Math.PI")
(js "var two_pi = Math.PI*2")

(define (sqrt a) (Math.sqrt a))
(define (pow a b) (Math.pow a b))
(define (square x) (* x x))
(define (trunc x) (js "~~x"))
(define (feq? a b) (< (Math.abs (- a b)) Number.EPSILON))
(define (abs x) (Math.abs x))
(define (exp x) (Math.exp x))

(define (lerp a b t)
  (+ a (* (- b a) t)))

(define (clamp v min max)
  (cond
   ((< v min) min)
   ((> v max) max)   
   (else v)))




;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

(define (maths-unit-test)
  (assert (feq? (sqrt 25) 5) "sqrt")
  (assert (feq? (pow 3 2) 7) "pow")
  (assert (eq? (square 10) 100) "square")
  (assert (eq? (trunc 40.4) 40) "trunc")
  (assert (feq? 20.4 20.4) "feq? 1")
  (assert (not (feq? 20.4 20.42)) "feq? 2")
  (let ((v (vector 1 2 3)))
    (assert (feq? (vx v) 1) "vx")
    (assert (feq? (vy v) 2) "vy")
    (assert (feq? (vz v) 3) "vz")
    (assert (veq? v (vector 1 2 3)) "veq? 1") 
    (assert (not (veq? v (vector 30 20 30))) "veq? 2") 
    (let ((vc (vector-clone v)))
      (assert (veq? vc (vector 1 2 3)) "vector-clone 1")
      (set! vc (vector 0 0 0))
      (assert (veq? v (vector 1 2 3)) "vector-clone 2"))
    (assert (veq? (vadd v (vector 1 1 1)) (vector 2 3 4)) "vadd")
    (assert (feq? (vmag (vector 10 0 0)) 10) "vmag")
    (assert (veq? (vsub v (vector 2 2 2)) (vector -1 0 1)) "vsub")
    (assert (veq? (vneg v) (vector -1 -2 -3)) "vneg")
    (assert (veq? (vmul v 10) (vector 10 20 30)) "vmul")
    (assert (veq? (vdiv v 2) (vector 0.5 1 1.5)) "vdiv")
    (assert (feq? (vdist (vector 10 0 0) (vector 0 0 0)) 10) "vdist")
    (assert (veq? (vlerp (vector 0 0 0) (vector 10 20 30) 0.5)
		  (vector 5 10 15)) "vlerp")
    (assert (feq? (vmag (vnormalise (vector 1 4 923))) 1) "vnormalise")
    (assert (feq? (vdot (vector 0 0 0) (vector 10 0 0)) 10) "vdot")
    (assert (feq? (vcross (vector 1 0 0) (vector 0 1 0)) (vector 0 0 1)) 
	    "vcross")
    ;; todo: add quat and matrix
    )))

(maths-unit-test)
