Source

papl / src / PaplQ.mli

Full commit
(*
  Copyright (c) 2012 Anders Lau Olsen.
  See LICENSE file for terms and conditions.
*)
(** Vector configurations

A configuration of type [PaplQ.t = float BatArray.t] is an array of floats.

Such configurations are useful for example for path planning for serial
manipulators.

For other types of planning and robots you may prefer other more structured
representations of the robot state. A simple example is {! PaplQTime.t} for
planning in time in a [PaplQ.t] configuration space.

It is your reponsibility not to mix configurations of different lengths.

*)

include module type of PaplVector.Array

(** {2 Imperative operators} *)

val ( *=:) : t -> float -> unit
(** Scale a vector. *)

val (/=:) : t -> float -> unit
(** Divide a vector. *)

val (+=:) : t -> t -> unit
(** Add a vector. *)

val (-=:) : t -> t -> unit
(** Subtract a vector. *)

(** {2 Metrics} *)

val dist_inf_box_normalized : box_t -> t PaplMetric.t
(** The metric [dist= dist_inf_box_normalized (a, b)] is the weighted infinity
    metric for which [dist a b == 1] (approximately).
*)

val dist2_box_normalized : box_t -> t PaplMetric.t
(** The metric [dist= dist_inf_box_normalized (a, b)] is the weighted Euclidean
    metric for which [dist a b == 1] (approximately).
*)

val dist2_sqr_box_normalized : box_t -> t PaplMetric.t
(** The metric [dist= dist_inf_box_normalized (a, b)] is the square of the
    weighted Euclidean metric for which [dist a b == 1] (approximately).
*)

(** {2 Boxes} *)

(** Box operations *)
module Box : sig
  val scale : float -> box_t -> box_t
(** Scaling of a box.

    [scale s (a, b) = (s *: a, s *: b)].
*)

  val translate : t -> box_t -> box_t
(** Translation of a box.

    [translate q (a, b) = (a +: q, b +: q)].
*)

  val intersect : box_t -> box_t -> box_t
(** The intersection of a pair of boxes. *)

  val center : box_t -> t -> box_t
(** Centering of a box at a configuration.

    [center box q] translates the corners of [box] such that [q] is at the
    center of the new box.
*)

  val within : box_t -> t -> bool
(** [within box (a, b)] is true iff
    [a.(i) <= q.(i) && q.(i) <= b.(i)] for all [i].
*)

  val within_by_eps : float -> box_t -> t -> bool
(** [within_by_eps eps box (a, b)] is true iff
    [a.(i) -. eps <= q.(i) && q.(i) <= b.(i) +. eps] for all [i].
*)

  val is_empty : box_t -> bool
(** A box [(a, b)] is empty if [ai > bi] for any coordinate [i].
*)
end

(** {2 Gram-Schmidt orthonormalization} *)

val gram_schmidt_by : dot_t -> int -> (unit -> t) -> t list
(**
   Gram-Schmidt orthonormalization.

   [gram_schmidt_by dot n make] creates an orthonormal basis of [n] elements on
   a space with inner product [dot], using vectors returned by [make ()].

   The [make] procedure will be called until [n] linearly independent vectors
   have been returned.

   The {{: http://en.wikipedia.org/wiki/Gram%E2%80%93Schmidt_process}modified
   Gram-Schmidt algorithm} is used.
*)

val gram_schmidt : int -> (unit -> t) -> t list
(**
   Gram-Schmidt orthonormalization.

   [gram_schmidt n make] is equivalent to [gram_schmidt_by dot n make].
*)

(** {2 Circular joints} *)

(** Configuration operations for robots with circular joints.

    A circular joint is a revolute joint without any joint limits.
    Configurations for robots with one or more of such joints need interpolation
    and metric functions different from the standard implementation of [PaplQ].

    The specification for a robot with circular joints is a tuple [(n,
    circular)] where [n] is the length of the configurations and [circular] are
    the indices of the joints that are circular. The tuple [(7, [0, 6])] for
    example specifies that the configurations are 7 elements long and that the
    end-effector (joint 6) and the base joint (joint 0) are circular. The module
    of configuration operations is constructed by [MakeCircular (struct let
    setup = (n, circular) end)].
*)
module MakeCircular (M : sig val setup : int * int list end) : sig
(** Metric functions.

    The metric always chooses the shortest route between a pair of angles when
    measuring the distance between a pair of configurations.
*)
  include PaplVectorMetric.S with type t = t

  val interpolate : t PaplInterpolate.t
(** Interpolation function. Interpolation for a circular joint always chooses
    the shortest route between the joint values. *)
end