{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE TypeFamilies #-}
module Silkscreen.Precedence
(
PrecedencePrinter(..)
, setPrec
, prec
, assoc
, nonAssoc
, leftAssoc
, rightAssoc
, infix_
, module Silkscreen
) where
import Silkscreen
class Printer p => PrecedencePrinter p where
type Level p
askingPrec :: (Level p -> p) -> p
localPrec :: (Level p -> Level p) -> p -> p
setPrec :: PrecedencePrinter p => Level p -> p -> p
setPrec :: Level p -> p -> p
setPrec = (Level p -> Level p) -> p -> p
forall p. PrecedencePrinter p => (Level p -> Level p) -> p -> p
localPrec ((Level p -> Level p) -> p -> p)
-> (Level p -> Level p -> Level p) -> Level p -> p -> p
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Level p -> Level p -> Level p
forall a b. a -> b -> a
const
prec :: (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec :: Level p -> p -> p
prec Level p
l p
d = (Level p -> p) -> p
forall p. PrecedencePrinter p => (Level p -> p) -> p
askingPrec ((Level p -> p) -> p) -> (Level p -> p) -> p
forall a b. (a -> b) -> a -> b
$ \ Level p
l' -> Level p -> p -> p
forall p. PrecedencePrinter p => Level p -> p -> p
setPrec Level p
l (Bool -> p -> p
forall p. Printer p => Bool -> p -> p
parensIf (Level p
l' Level p -> Level p -> Bool
forall a. Ord a => a -> a -> Bool
> Level p
l) p
d)
assoc :: (PrecedencePrinter p, Ord (Level p)) => Level p -> (p -> p -> p) -> (p -> p -> p)
assoc :: Level p -> (p -> p -> p) -> p -> p -> p
assoc Level p
pout = Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
forall p.
(PrecedencePrinter p, Ord (Level p)) =>
Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
infix_ Level p
pout p -> p
forall a. a -> a
id p -> p
forall a. a -> a
id
nonAssoc :: (PrecedencePrinter p, Ord (Level p)) => Level p -> Level p -> (p -> p -> p) -> (p -> p -> p)
nonAssoc :: Level p -> Level p -> (p -> p -> p) -> p -> p -> p
nonAssoc Level p
pout Level p
pin = Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
forall p.
(PrecedencePrinter p, Ord (Level p)) =>
Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
infix_ Level p
pout (Level p -> p -> p
forall p. (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec Level p
pin) (Level p -> p -> p
forall p. (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec Level p
pin)
leftAssoc :: (PrecedencePrinter p, Ord (Level p)) => Level p -> Level p -> (p -> p -> p) -> (p -> p -> p)
leftAssoc :: Level p -> Level p -> (p -> p -> p) -> p -> p -> p
leftAssoc Level p
pl Level p
pr = Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
forall p.
(PrecedencePrinter p, Ord (Level p)) =>
Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
infix_ Level p
pl p -> p
forall a. a -> a
id (Level p -> p -> p
forall p. (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec Level p
pr)
rightAssoc :: (PrecedencePrinter p, Ord (Level p)) => Level p -> Level p -> (p -> p -> p) -> (p -> p -> p)
rightAssoc :: Level p -> Level p -> (p -> p -> p) -> p -> p -> p
rightAssoc Level p
pr Level p
pl = Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
forall p.
(PrecedencePrinter p, Ord (Level p)) =>
Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
infix_ Level p
pr (Level p -> p -> p
forall p. (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec Level p
pl) p -> p
forall a. a -> a
id
infix_ :: (PrecedencePrinter p, Ord (Level p)) => Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> (p -> p -> p)
infix_ :: Level p -> (p -> p) -> (p -> p) -> (p -> p -> p) -> p -> p -> p
infix_ Level p
p p -> p
fl p -> p
fr p -> p -> p
op p
l p
r = Level p -> p -> p
forall p. (PrecedencePrinter p, Ord (Level p)) => Level p -> p -> p
prec Level p
p (p -> p) -> p -> p
forall a b. (a -> b) -> a -> b
$ p -> p
fl p
l p -> p -> p
`op` p -> p
fr p
r
instance PrecedencePrinter b => PrecedencePrinter (a -> b) where
type Level (a -> b) = Level b
askingPrec :: (Level (a -> b) -> a -> b) -> a -> b
askingPrec Level (a -> b) -> a -> b
f = (Level b -> b) -> b
forall p. PrecedencePrinter p => (Level p -> p) -> p
askingPrec ((Level b -> b) -> b) -> (a -> Level b -> b) -> a -> b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Level b -> a -> b) -> a -> Level b -> b
forall a b c. (a -> b -> c) -> b -> a -> c
flip Level b -> a -> b
Level (a -> b) -> a -> b
f
localPrec :: (Level (a -> b) -> Level (a -> b)) -> (a -> b) -> a -> b
localPrec Level (a -> b) -> Level (a -> b)
f a -> b
p = (Level b -> Level b) -> b -> b
forall p. PrecedencePrinter p => (Level p -> Level p) -> p -> p
localPrec Level b -> Level b
Level (a -> b) -> Level (a -> b)
f (b -> b) -> (a -> b) -> a -> b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> b
p