| 1 |
(* raw time is in samples *) |
|---|
| 2 |
type raw_time = int;; |
|---|
| 3 |
|
|---|
| 4 |
(* time is specified by the user in a number of possible formats *) |
|---|
| 5 |
type time = Seconds of float |
|---|
| 6 |
| Samples of int |
|---|
| 7 |
| Beats of float |
|---|
| 8 |
| Hertz of float |
|---|
| 9 |
| Forever ;; |
|---|
| 10 |
|
|---|
| 11 |
type raw_extent = raw_time * raw_time;; |
|---|
| 12 |
|
|---|
| 13 |
(* an extent is a start and a length *) |
|---|
| 14 |
type extent = time * time;; |
|---|
| 15 |
|
|---|
| 16 |
exception ButHowLongIsForever;; |
|---|
| 17 |
|
|---|
| 18 |
let time_to_raw_time r t = |
|---|
| 19 |
let sec_to_sam s = int_of_float (s *. (float_of_int (Remix.samplerate r))) in |
|---|
| 20 |
match t with |
|---|
| 21 |
| Seconds f -> sec_to_sam f |
|---|
| 22 |
| Samples i -> i |
|---|
| 23 |
| Beats f -> sec_to_sam (f /. (Remix.bpm r) *. 60.) |
|---|
| 24 |
| Hertz f -> sec_to_sam (1. /. f) |
|---|
| 25 |
| Forever -> raise ButHowLongIsForever;; |
|---|
| 26 |
|
|---|
| 27 |
let time_to_raw_samples r t = time_to_raw_time r t * Remix.channels r;; |
|---|
| 28 |
|
|---|
| 29 |
let extent_to_raw_time r (s,l) = |
|---|
| 30 |
(time_to_raw_time r s, time_to_raw_time r l);; |
|---|
| 31 |
|
|---|
| 32 |
let extent_to_raw_samples r (s,l) = |
|---|
| 33 |
(time_to_raw_samples r s, time_to_raw_samples r l);; |
|---|
| 34 |
|
|---|
| 35 |
let t_max r a b = Samples (max (time_to_raw_time r a) (time_to_raw_time r b));; |
|---|
| 36 |
let t_min r a b = Samples (min (time_to_raw_time r a) (time_to_raw_time r b));; |
|---|
| 37 |
let t_add r a b = |
|---|
| 38 |
if a = Forever || b = Forever then Forever else |
|---|
| 39 |
Samples ((time_to_raw_time r a) + (time_to_raw_time r b));; |
|---|
| 40 |
let t_sub r a b = |
|---|
| 41 |
if a = Forever then Forever else |
|---|
| 42 |
Samples ((time_to_raw_time r a) - (time_to_raw_time r b));; |
|---|
| 43 |
|
|---|
| 44 |
let overlap r (astart, alen) (bstart, blen) = |
|---|
| 45 |
let (s, e) = |
|---|
| 46 |
let start = t_max r astart bstart in |
|---|
| 47 |
if alen = Forever then (start, t_add r bstart blen) |
|---|
| 48 |
else if blen = Forever then (start, t_add r astart alen) |
|---|
| 49 |
else (start, t_min r (t_add r astart alen) (t_add r bstart blen)) in |
|---|
| 50 |
(s, t_sub r e s) |
|---|
| 51 |
|
|---|
| 52 |
let to_string time = |
|---|
| 53 |
match time with |
|---|
| 54 |
| Seconds s -> Printf.sprintf "%f seconds" s |
|---|
| 55 |
| Samples s -> Printf.sprintf "%d samples" s |
|---|
| 56 |
| Beats b -> Printf.sprintf "%f beats" b |
|---|
| 57 |
| Hertz h -> Printf.sprintf "%f Hz" h |
|---|
| 58 |
| Forever -> Printf.sprintf "Forever!" |
|---|