{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE RankNTypes #-}

module Cursor.Types where

import Control.Applicative
import Data.Functor.Compose
import qualified Data.Text.Internal as T
import Data.Validity
import GHC.Generics (Generic)
import Lens.Micro

isSafeChar :: Char -> Bool
isSafeChar :: Char -> Bool
isSafeChar Char
c = Char -> Char
T.safe Char
c Char -> Char -> Bool
forall a. Eq a => a -> a -> Bool
== Char
c

data DeleteOrUpdate a
  = Deleted
  | Updated a
  deriving (Int -> DeleteOrUpdate a -> ShowS
[DeleteOrUpdate a] -> ShowS
DeleteOrUpdate a -> String
(Int -> DeleteOrUpdate a -> ShowS)
-> (DeleteOrUpdate a -> String)
-> ([DeleteOrUpdate a] -> ShowS)
-> Show (DeleteOrUpdate a)
forall a. Show a => Int -> DeleteOrUpdate a -> ShowS
forall a. Show a => [DeleteOrUpdate a] -> ShowS
forall a. Show a => DeleteOrUpdate a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [DeleteOrUpdate a] -> ShowS
$cshowList :: forall a. Show a => [DeleteOrUpdate a] -> ShowS
show :: DeleteOrUpdate a -> String
$cshow :: forall a. Show a => DeleteOrUpdate a -> String
showsPrec :: Int -> DeleteOrUpdate a -> ShowS
$cshowsPrec :: forall a. Show a => Int -> DeleteOrUpdate a -> ShowS
Show, DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
(DeleteOrUpdate a -> DeleteOrUpdate a -> Bool)
-> (DeleteOrUpdate a -> DeleteOrUpdate a -> Bool)
-> Eq (DeleteOrUpdate a)
forall a. Eq a => DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
$c/= :: forall a. Eq a => DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
== :: DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
$c== :: forall a. Eq a => DeleteOrUpdate a -> DeleteOrUpdate a -> Bool
Eq, (forall x. DeleteOrUpdate a -> Rep (DeleteOrUpdate a) x)
-> (forall x. Rep (DeleteOrUpdate a) x -> DeleteOrUpdate a)
-> Generic (DeleteOrUpdate a)
forall x. Rep (DeleteOrUpdate a) x -> DeleteOrUpdate a
forall x. DeleteOrUpdate a -> Rep (DeleteOrUpdate a) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall a x. Rep (DeleteOrUpdate a) x -> DeleteOrUpdate a
forall a x. DeleteOrUpdate a -> Rep (DeleteOrUpdate a) x
$cto :: forall a x. Rep (DeleteOrUpdate a) x -> DeleteOrUpdate a
$cfrom :: forall a x. DeleteOrUpdate a -> Rep (DeleteOrUpdate a) x
Generic)

instance Validity a => Validity (DeleteOrUpdate a)

instance Functor DeleteOrUpdate where
  fmap :: (a -> b) -> DeleteOrUpdate a -> DeleteOrUpdate b
fmap a -> b
_ DeleteOrUpdate a
Deleted = DeleteOrUpdate b
forall a. DeleteOrUpdate a
Deleted
  fmap a -> b
f (Updated a
a) = b -> DeleteOrUpdate b
forall a. a -> DeleteOrUpdate a
Updated (a -> b
f a
a)

instance Applicative DeleteOrUpdate where
  pure :: a -> DeleteOrUpdate a
pure = a -> DeleteOrUpdate a
forall a. a -> DeleteOrUpdate a
Updated
  DeleteOrUpdate (a -> b)
Deleted <*> :: DeleteOrUpdate (a -> b) -> DeleteOrUpdate a -> DeleteOrUpdate b
<*> DeleteOrUpdate a
_ = DeleteOrUpdate b
forall a. DeleteOrUpdate a
Deleted
  DeleteOrUpdate (a -> b)
_ <*> DeleteOrUpdate a
Deleted = DeleteOrUpdate b
forall a. DeleteOrUpdate a
Deleted
  (Updated a -> b
f) <*> (Updated a
a) = b -> DeleteOrUpdate b
forall a. a -> DeleteOrUpdate a
Updated (a -> b
f a
a)

instance Alternative DeleteOrUpdate where
  empty :: DeleteOrUpdate a
empty = DeleteOrUpdate a
forall a. DeleteOrUpdate a
Deleted
  Updated a
a <|> :: DeleteOrUpdate a -> DeleteOrUpdate a -> DeleteOrUpdate a
<|> DeleteOrUpdate a
_ = a -> DeleteOrUpdate a
forall a. a -> DeleteOrUpdate a
Updated a
a
  DeleteOrUpdate a
Deleted <|> DeleteOrUpdate a
doua = DeleteOrUpdate a
doua

instance Monad DeleteOrUpdate where
  DeleteOrUpdate a
dou >>= :: DeleteOrUpdate a -> (a -> DeleteOrUpdate b) -> DeleteOrUpdate b
>>= a -> DeleteOrUpdate b
f = case DeleteOrUpdate a
dou of
    Updated a
a -> a -> DeleteOrUpdate b
f a
a
    DeleteOrUpdate a
Deleted -> DeleteOrUpdate b
forall a. DeleteOrUpdate a
Deleted

joinDeletes :: Maybe (DeleteOrUpdate a) -> Maybe (DeleteOrUpdate a) -> DeleteOrUpdate a
joinDeletes :: Maybe (DeleteOrUpdate a)
-> Maybe (DeleteOrUpdate a) -> DeleteOrUpdate a
joinDeletes Maybe (DeleteOrUpdate a)
m1 Maybe (DeleteOrUpdate a)
m2 =
  case (Maybe (DeleteOrUpdate a)
m1, Maybe (DeleteOrUpdate a)
m2) of
    (Maybe (DeleteOrUpdate a)
Nothing, Maybe (DeleteOrUpdate a)
Nothing) -> DeleteOrUpdate a
forall a. DeleteOrUpdate a
Deleted
    (Maybe (DeleteOrUpdate a)
Nothing, Just DeleteOrUpdate a
a) -> DeleteOrUpdate a
a
    (Just DeleteOrUpdate a
a, Maybe (DeleteOrUpdate a)
_) -> DeleteOrUpdate a
a

joinDeletes3 ::
  Maybe (DeleteOrUpdate a) ->
  Maybe (DeleteOrUpdate a) ->
  Maybe (DeleteOrUpdate a) ->
  DeleteOrUpdate a
joinDeletes3 :: Maybe (DeleteOrUpdate a)
-> Maybe (DeleteOrUpdate a)
-> Maybe (DeleteOrUpdate a)
-> DeleteOrUpdate a
joinDeletes3 Maybe (DeleteOrUpdate a)
m1 Maybe (DeleteOrUpdate a)
m2 Maybe (DeleteOrUpdate a)
m3 =
  case (Maybe (DeleteOrUpdate a)
m1, Maybe (DeleteOrUpdate a)
m2, Maybe (DeleteOrUpdate a)
m3) of
    (Maybe (DeleteOrUpdate a)
Nothing, Maybe (DeleteOrUpdate a)
Nothing, Maybe (DeleteOrUpdate a)
Nothing) -> DeleteOrUpdate a
forall a. DeleteOrUpdate a
Deleted
    (Maybe (DeleteOrUpdate a)
Nothing, Maybe (DeleteOrUpdate a)
Nothing, Just DeleteOrUpdate a
a) -> DeleteOrUpdate a
a
    (Maybe (DeleteOrUpdate a)
Nothing, Just DeleteOrUpdate a
a, Maybe (DeleteOrUpdate a)
_) -> DeleteOrUpdate a
a
    (Just DeleteOrUpdate a
a, Maybe (DeleteOrUpdate a)
_, Maybe (DeleteOrUpdate a)
_) -> DeleteOrUpdate a
a

joinPossibleDeletes ::
  Maybe (DeleteOrUpdate a) -> Maybe (DeleteOrUpdate a) -> Maybe (DeleteOrUpdate a)
joinPossibleDeletes :: Maybe (DeleteOrUpdate a)
-> Maybe (DeleteOrUpdate a) -> Maybe (DeleteOrUpdate a)
joinPossibleDeletes Maybe (DeleteOrUpdate a)
d1 Maybe (DeleteOrUpdate a)
d2 = Compose Maybe DeleteOrUpdate a -> Maybe (DeleteOrUpdate a)
forall k1 (f :: k1 -> *) k2 (g :: k2 -> k1) (a :: k2).
Compose f g a -> f (g a)
getCompose (Compose Maybe DeleteOrUpdate a -> Maybe (DeleteOrUpdate a))
-> Compose Maybe DeleteOrUpdate a -> Maybe (DeleteOrUpdate a)
forall a b. (a -> b) -> a -> b
$ Maybe (DeleteOrUpdate a) -> Compose Maybe DeleteOrUpdate a
forall k k1 (f :: k -> *) (g :: k1 -> k) (a :: k1).
f (g a) -> Compose f g a
Compose Maybe (DeleteOrUpdate a)
d1 Compose Maybe DeleteOrUpdate a
-> Compose Maybe DeleteOrUpdate a -> Compose Maybe DeleteOrUpdate a
forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
<|> Maybe (DeleteOrUpdate a) -> Compose Maybe DeleteOrUpdate a
forall k k1 (f :: k -> *) (g :: k1 -> k) (a :: k1).
f (g a) -> Compose f g a
Compose Maybe (DeleteOrUpdate a)
d2

focusPossibleDeleteOrUpdate ::
  Lens' b a -> (a -> Maybe (DeleteOrUpdate a)) -> b -> Maybe (DeleteOrUpdate b)
focusPossibleDeleteOrUpdate :: Lens' b a
-> (a -> Maybe (DeleteOrUpdate a)) -> b -> Maybe (DeleteOrUpdate b)
focusPossibleDeleteOrUpdate Lens' b a
l a -> Maybe (DeleteOrUpdate a)
func = Compose Maybe DeleteOrUpdate b -> Maybe (DeleteOrUpdate b)
forall k1 (f :: k1 -> *) k2 (g :: k2 -> k1) (a :: k2).
Compose f g a -> f (g a)
getCompose (Compose Maybe DeleteOrUpdate b -> Maybe (DeleteOrUpdate b))
-> (b -> Compose Maybe DeleteOrUpdate b)
-> b
-> Maybe (DeleteOrUpdate b)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (a -> Compose Maybe DeleteOrUpdate a)
-> b -> Compose Maybe DeleteOrUpdate b
Lens' b a
l (Maybe (DeleteOrUpdate a) -> Compose Maybe DeleteOrUpdate a
forall k k1 (f :: k -> *) (g :: k1 -> k) (a :: k1).
f (g a) -> Compose f g a
Compose (Maybe (DeleteOrUpdate a) -> Compose Maybe DeleteOrUpdate a)
-> (a -> Maybe (DeleteOrUpdate a))
-> a
-> Compose Maybe DeleteOrUpdate a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Maybe (DeleteOrUpdate a)
func)

dullMDelete :: Maybe (DeleteOrUpdate a) -> Maybe a
dullMDelete :: Maybe (DeleteOrUpdate a) -> Maybe a
dullMDelete Maybe (DeleteOrUpdate a)
Nothing = Maybe a
forall a. Maybe a
Nothing
dullMDelete (Just DeleteOrUpdate a
dou) = DeleteOrUpdate a -> Maybe a
forall a. DeleteOrUpdate a -> Maybe a
dullDelete DeleteOrUpdate a
dou

dullDelete :: DeleteOrUpdate a -> Maybe a
dullDelete :: DeleteOrUpdate a -> Maybe a
dullDelete DeleteOrUpdate a
Deleted = Maybe a
forall a. Maybe a
Nothing
dullDelete (Updated a
a) = a -> Maybe a
forall a. a -> Maybe a
Just a
a