{-# LANGUAGE PatternGuards #-}
{-# LANGUAGE OverloadedStrings #-}
{-# OPTIONS_GHC -fno-warn-type-defaults #-}

-- | Formatters for high-res, real-time and timer clock values from "System.Clock".

module Formatting.Clock (timeSpecs) where

import Data.Text.Lazy.Builder
import Formatting
import Formatting.Internal
import System.Clock

fmt :: Integer -> Builder
fmt :: Integer -> Builder
fmt diff :: Integer
diff
  | Just i :: Double
i <- Integer -> Maybe Double
scale ((10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 60 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 60 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 24) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " d") Double
i
  | Just i :: Double
i <- Integer -> Maybe Double
scale ((10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 60 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 60) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " h") Double
i
  | Just i :: Double
i <- Integer -> Maybe Double
scale ((10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 60) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " m") Double
i
  | Just i :: Double
i <- Integer -> Maybe Double
scale (10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " s") Double
i
  | Just i :: Double
i <- Integer -> Maybe Double
scale (10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 6) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " ms") Double
i
  | Just i :: Double
i <- Integer -> Maybe Double
scale (10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 3) = Format Builder (Double -> Builder) -> Double -> Builder
forall a. Format Builder a -> a
bprint (Int -> Format Builder (Double -> Builder)
forall a r. Real a => Int -> Format r (a -> r)
fixed 2 Format Builder (Double -> Builder)
-> Format Builder Builder -> Format Builder (Double -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " us") Double
i
  | Bool
otherwise = Format Builder (Integer -> Builder) -> Integer -> Builder
forall a. Format Builder a -> a
bprint (Format Builder (Integer -> Builder)
forall a r. Integral a => Format r (a -> r)
int Format Builder (Integer -> Builder)
-> Format Builder Builder -> Format Builder (Integer -> Builder)
forall r a r'. Format r a -> Format r' r -> Format r' a
% " ns") Integer
diff
  where
    scale :: Integer -> Maybe Double
    scale :: Integer -> Maybe Double
scale i :: Integer
i =
      if Integer
diff Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
>= Integer
i
        then Double -> Maybe Double
forall a. a -> Maybe a
Just (Integer -> Double
forall a b. (Integral a, Num b) => a -> b
fromIntegral Integer
diff Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/ Integer -> Double
forall a b. (Integral a, Num b) => a -> b
fromIntegral Integer
i)
        else Maybe Double
forall a. Maybe a
Nothing

-- | Same as @durationNS@ but works on `TimeSpec` from the clock package.
timeSpecs :: Format r (TimeSpec -> TimeSpec -> r)
timeSpecs :: Format r (TimeSpec -> TimeSpec -> r)
timeSpecs = ((Builder -> r) -> TimeSpec -> TimeSpec -> r)
-> Format r (TimeSpec -> TimeSpec -> r)
forall r a. ((Builder -> r) -> a) -> Format r a
Format (\g :: Builder -> r
g x :: TimeSpec
x y :: TimeSpec
y -> Builder -> r
g (TimeSpec -> TimeSpec -> Builder
fmt0 TimeSpec
x TimeSpec
y))
  where
    fmt0 :: TimeSpec -> TimeSpec -> Builder
fmt0 (TimeSpec s1 :: Int64
s1 n1 :: Int64
n1) (TimeSpec s2 :: Int64
s2 n2 :: Int64
n2) = Integer -> Builder
fmt Integer
diff
      where
        diff :: Integer
        diff :: Integer
diff = Integer
a2 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
- Integer
a1
        a1 :: Integer
a1 = (Int64 -> Integer
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int64
s1 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Int64 -> Integer
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int64
n1
        a2 :: Integer
a2 = (Int64 -> Integer
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int64
s2 Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
* 10 Integer -> Integer -> Integer
forall a b. (Num a, Integral b) => a -> b -> a
^ 9) Integer -> Integer -> Integer
forall a. Num a => a -> a -> a
+ Int64 -> Integer
forall a b. (Integral a, Num b) => a -> b
fromIntegral Int64
n2