{-# LANGUAGE DeriveAnyClass #-}
{-# LANGUAGE DeriveGeneric #-}
module Modelling.ActivityDiagram.Datatype (
  AdConnection (..),
  AdNode (..),
  UMLActivityDiagram(..),
  getInitialNodes,
  getFinalNodes,
  isActionNode,
  isObjectNode,
  isDecisionNode,
  isMergeNode,
  isForkNode,
  isJoinNode,
  isInitialNode,
  isActivityFinalNode,
  isFlowFinalNode,
  adjNodes
) where

import Autolib.Hash                     (Hashable)
import Autolib.Reader                   (Reader)
import Autolib.ToDoc                    (ToDoc)
import GHC.Generics (Generic)

data AdConnection =
  AdConnection {
    AdConnection -> Int
from :: Int,
    AdConnection -> Int
to :: Int,
    AdConnection -> String
guard :: String
  }
  deriving (AdConnection -> AdConnection -> Bool
(AdConnection -> AdConnection -> Bool)
-> (AdConnection -> AdConnection -> Bool) -> Eq AdConnection
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: AdConnection -> AdConnection -> Bool
== :: AdConnection -> AdConnection -> Bool
$c/= :: AdConnection -> AdConnection -> Bool
/= :: AdConnection -> AdConnection -> Bool
Eq, (forall x. AdConnection -> Rep AdConnection x)
-> (forall x. Rep AdConnection x -> AdConnection)
-> Generic AdConnection
forall x. Rep AdConnection x -> AdConnection
forall x. AdConnection -> Rep AdConnection x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. AdConnection -> Rep AdConnection x
from :: forall x. AdConnection -> Rep AdConnection x
$cto :: forall x. Rep AdConnection x -> AdConnection
to :: forall x. Rep AdConnection x -> AdConnection
Generic, Eq AdConnection
Eq AdConnection =>
(Int -> AdConnection -> Int)
-> (AdConnection -> Int) -> Hashable AdConnection
Int -> AdConnection -> Int
AdConnection -> Int
forall a. Eq a => (Int -> a -> Int) -> (a -> Int) -> Hashable a
$chashWithSalt :: Int -> AdConnection -> Int
hashWithSalt :: Int -> AdConnection -> Int
$chash :: AdConnection -> Int
hash :: AdConnection -> Int
Hashable, Eq AdConnection
Eq AdConnection =>
(AdConnection -> AdConnection -> Ordering)
-> (AdConnection -> AdConnection -> Bool)
-> (AdConnection -> AdConnection -> Bool)
-> (AdConnection -> AdConnection -> Bool)
-> (AdConnection -> AdConnection -> Bool)
-> (AdConnection -> AdConnection -> AdConnection)
-> (AdConnection -> AdConnection -> AdConnection)
-> Ord AdConnection
AdConnection -> AdConnection -> Bool
AdConnection -> AdConnection -> Ordering
AdConnection -> AdConnection -> AdConnection
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: AdConnection -> AdConnection -> Ordering
compare :: AdConnection -> AdConnection -> Ordering
$c< :: AdConnection -> AdConnection -> Bool
< :: AdConnection -> AdConnection -> Bool
$c<= :: AdConnection -> AdConnection -> Bool
<= :: AdConnection -> AdConnection -> Bool
$c> :: AdConnection -> AdConnection -> Bool
> :: AdConnection -> AdConnection -> Bool
$c>= :: AdConnection -> AdConnection -> Bool
>= :: AdConnection -> AdConnection -> Bool
$cmax :: AdConnection -> AdConnection -> AdConnection
max :: AdConnection -> AdConnection -> AdConnection
$cmin :: AdConnection -> AdConnection -> AdConnection
min :: AdConnection -> AdConnection -> AdConnection
Ord, ReadPrec [AdConnection]
ReadPrec AdConnection
Int -> ReadS AdConnection
ReadS [AdConnection]
(Int -> ReadS AdConnection)
-> ReadS [AdConnection]
-> ReadPrec AdConnection
-> ReadPrec [AdConnection]
-> Read AdConnection
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS AdConnection
readsPrec :: Int -> ReadS AdConnection
$creadList :: ReadS [AdConnection]
readList :: ReadS [AdConnection]
$creadPrec :: ReadPrec AdConnection
readPrec :: ReadPrec AdConnection
$creadListPrec :: ReadPrec [AdConnection]
readListPrec :: ReadPrec [AdConnection]
Read, Parser [AdConnection]
Parser AdConnection
Int -> Parser AdConnection
Parser AdConnection
-> (Int -> Parser AdConnection)
-> Parser AdConnection
-> (Int -> Parser AdConnection)
-> Parser [AdConnection]
-> Reader AdConnection
forall a.
Parser a
-> (Int -> Parser a)
-> Parser a
-> (Int -> Parser a)
-> Parser [a]
-> Reader a
$catomic_reader :: Parser AdConnection
atomic_reader :: Parser AdConnection
$catomic_readerPrec :: Int -> Parser AdConnection
atomic_readerPrec :: Int -> Parser AdConnection
$creader :: Parser AdConnection
reader :: Parser AdConnection
$creaderPrec :: Int -> Parser AdConnection
readerPrec :: Int -> Parser AdConnection
$creaderList :: Parser [AdConnection]
readerList :: Parser [AdConnection]
Reader, Int -> AdConnection -> ShowS
[AdConnection] -> ShowS
AdConnection -> String
(Int -> AdConnection -> ShowS)
-> (AdConnection -> String)
-> ([AdConnection] -> ShowS)
-> Show AdConnection
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> AdConnection -> ShowS
showsPrec :: Int -> AdConnection -> ShowS
$cshow :: AdConnection -> String
show :: AdConnection -> String
$cshowList :: [AdConnection] -> ShowS
showList :: [AdConnection] -> ShowS
Show, Int -> AdConnection -> Doc
[AdConnection] -> Doc
(Int -> AdConnection -> Doc)
-> ([AdConnection] -> Doc) -> ToDoc AdConnection
forall a. (Int -> a -> Doc) -> ([a] -> Doc) -> ToDoc a
$ctoDocPrec :: Int -> AdConnection -> Doc
toDocPrec :: Int -> AdConnection -> Doc
$ctoDocList :: [AdConnection] -> Doc
toDocList :: [AdConnection] -> Doc
ToDoc)

data AdNode =
  AdActionNode {
    AdNode -> Int
label :: Int,
    AdNode -> String
name :: String
  }
  | AdObjectNode {
      label :: Int,
      name :: String
  }
  | AdDecisionNode {
      label :: Int
  }
  | AdMergeNode {
      label :: Int
  }
  | AdForkNode {
      label :: Int
  }
  | AdJoinNode {
      label :: Int
  }
  | AdActivityFinalNode {
      label :: Int
  }
  | AdFlowFinalNode {
      label :: Int
  }
  | AdInitialNode {
      label :: Int
  }
  deriving (AdNode -> AdNode -> Bool
(AdNode -> AdNode -> Bool)
-> (AdNode -> AdNode -> Bool) -> Eq AdNode
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: AdNode -> AdNode -> Bool
== :: AdNode -> AdNode -> Bool
$c/= :: AdNode -> AdNode -> Bool
/= :: AdNode -> AdNode -> Bool
Eq, (forall x. AdNode -> Rep AdNode x)
-> (forall x. Rep AdNode x -> AdNode) -> Generic AdNode
forall x. Rep AdNode x -> AdNode
forall x. AdNode -> Rep AdNode x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. AdNode -> Rep AdNode x
from :: forall x. AdNode -> Rep AdNode x
$cto :: forall x. Rep AdNode x -> AdNode
to :: forall x. Rep AdNode x -> AdNode
Generic, Eq AdNode
Eq AdNode =>
(Int -> AdNode -> Int) -> (AdNode -> Int) -> Hashable AdNode
Int -> AdNode -> Int
AdNode -> Int
forall a. Eq a => (Int -> a -> Int) -> (a -> Int) -> Hashable a
$chashWithSalt :: Int -> AdNode -> Int
hashWithSalt :: Int -> AdNode -> Int
$chash :: AdNode -> Int
hash :: AdNode -> Int
Hashable, ReadPrec [AdNode]
ReadPrec AdNode
Int -> ReadS AdNode
ReadS [AdNode]
(Int -> ReadS AdNode)
-> ReadS [AdNode]
-> ReadPrec AdNode
-> ReadPrec [AdNode]
-> Read AdNode
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS AdNode
readsPrec :: Int -> ReadS AdNode
$creadList :: ReadS [AdNode]
readList :: ReadS [AdNode]
$creadPrec :: ReadPrec AdNode
readPrec :: ReadPrec AdNode
$creadListPrec :: ReadPrec [AdNode]
readListPrec :: ReadPrec [AdNode]
Read, Parser [AdNode]
Parser AdNode
Int -> Parser AdNode
Parser AdNode
-> (Int -> Parser AdNode)
-> Parser AdNode
-> (Int -> Parser AdNode)
-> Parser [AdNode]
-> Reader AdNode
forall a.
Parser a
-> (Int -> Parser a)
-> Parser a
-> (Int -> Parser a)
-> Parser [a]
-> Reader a
$catomic_reader :: Parser AdNode
atomic_reader :: Parser AdNode
$catomic_readerPrec :: Int -> Parser AdNode
atomic_readerPrec :: Int -> Parser AdNode
$creader :: Parser AdNode
reader :: Parser AdNode
$creaderPrec :: Int -> Parser AdNode
readerPrec :: Int -> Parser AdNode
$creaderList :: Parser [AdNode]
readerList :: Parser [AdNode]
Reader, Int -> AdNode -> ShowS
[AdNode] -> ShowS
AdNode -> String
(Int -> AdNode -> ShowS)
-> (AdNode -> String) -> ([AdNode] -> ShowS) -> Show AdNode
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> AdNode -> ShowS
showsPrec :: Int -> AdNode -> ShowS
$cshow :: AdNode -> String
show :: AdNode -> String
$cshowList :: [AdNode] -> ShowS
showList :: [AdNode] -> ShowS
Show, Int -> AdNode -> Doc
[AdNode] -> Doc
(Int -> AdNode -> Doc) -> ([AdNode] -> Doc) -> ToDoc AdNode
forall a. (Int -> a -> Doc) -> ([a] -> Doc) -> ToDoc a
$ctoDocPrec :: Int -> AdNode -> Doc
toDocPrec :: Int -> AdNode -> Doc
$ctoDocList :: [AdNode] -> Doc
toDocList :: [AdNode] -> Doc
ToDoc)


data UMLActivityDiagram =
  UMLActivityDiagram {
    UMLActivityDiagram -> [AdNode]
nodes :: [AdNode],
    UMLActivityDiagram -> [AdConnection]
connections :: [AdConnection]
  }
  deriving (UMLActivityDiagram -> UMLActivityDiagram -> Bool
(UMLActivityDiagram -> UMLActivityDiagram -> Bool)
-> (UMLActivityDiagram -> UMLActivityDiagram -> Bool)
-> Eq UMLActivityDiagram
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: UMLActivityDiagram -> UMLActivityDiagram -> Bool
== :: UMLActivityDiagram -> UMLActivityDiagram -> Bool
$c/= :: UMLActivityDiagram -> UMLActivityDiagram -> Bool
/= :: UMLActivityDiagram -> UMLActivityDiagram -> Bool
Eq, (forall x. UMLActivityDiagram -> Rep UMLActivityDiagram x)
-> (forall x. Rep UMLActivityDiagram x -> UMLActivityDiagram)
-> Generic UMLActivityDiagram
forall x. Rep UMLActivityDiagram x -> UMLActivityDiagram
forall x. UMLActivityDiagram -> Rep UMLActivityDiagram x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. UMLActivityDiagram -> Rep UMLActivityDiagram x
from :: forall x. UMLActivityDiagram -> Rep UMLActivityDiagram x
$cto :: forall x. Rep UMLActivityDiagram x -> UMLActivityDiagram
to :: forall x. Rep UMLActivityDiagram x -> UMLActivityDiagram
Generic, Eq UMLActivityDiagram
Eq UMLActivityDiagram =>
(Int -> UMLActivityDiagram -> Int)
-> (UMLActivityDiagram -> Int) -> Hashable UMLActivityDiagram
Int -> UMLActivityDiagram -> Int
UMLActivityDiagram -> Int
forall a. Eq a => (Int -> a -> Int) -> (a -> Int) -> Hashable a
$chashWithSalt :: Int -> UMLActivityDiagram -> Int
hashWithSalt :: Int -> UMLActivityDiagram -> Int
$chash :: UMLActivityDiagram -> Int
hash :: UMLActivityDiagram -> Int
Hashable, ReadPrec [UMLActivityDiagram]
ReadPrec UMLActivityDiagram
Int -> ReadS UMLActivityDiagram
ReadS [UMLActivityDiagram]
(Int -> ReadS UMLActivityDiagram)
-> ReadS [UMLActivityDiagram]
-> ReadPrec UMLActivityDiagram
-> ReadPrec [UMLActivityDiagram]
-> Read UMLActivityDiagram
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS UMLActivityDiagram
readsPrec :: Int -> ReadS UMLActivityDiagram
$creadList :: ReadS [UMLActivityDiagram]
readList :: ReadS [UMLActivityDiagram]
$creadPrec :: ReadPrec UMLActivityDiagram
readPrec :: ReadPrec UMLActivityDiagram
$creadListPrec :: ReadPrec [UMLActivityDiagram]
readListPrec :: ReadPrec [UMLActivityDiagram]
Read, Parser [UMLActivityDiagram]
Parser UMLActivityDiagram
Int -> Parser UMLActivityDiagram
Parser UMLActivityDiagram
-> (Int -> Parser UMLActivityDiagram)
-> Parser UMLActivityDiagram
-> (Int -> Parser UMLActivityDiagram)
-> Parser [UMLActivityDiagram]
-> Reader UMLActivityDiagram
forall a.
Parser a
-> (Int -> Parser a)
-> Parser a
-> (Int -> Parser a)
-> Parser [a]
-> Reader a
$catomic_reader :: Parser UMLActivityDiagram
atomic_reader :: Parser UMLActivityDiagram
$catomic_readerPrec :: Int -> Parser UMLActivityDiagram
atomic_readerPrec :: Int -> Parser UMLActivityDiagram
$creader :: Parser UMLActivityDiagram
reader :: Parser UMLActivityDiagram
$creaderPrec :: Int -> Parser UMLActivityDiagram
readerPrec :: Int -> Parser UMLActivityDiagram
$creaderList :: Parser [UMLActivityDiagram]
readerList :: Parser [UMLActivityDiagram]
Reader, Int -> UMLActivityDiagram -> ShowS
[UMLActivityDiagram] -> ShowS
UMLActivityDiagram -> String
(Int -> UMLActivityDiagram -> ShowS)
-> (UMLActivityDiagram -> String)
-> ([UMLActivityDiagram] -> ShowS)
-> Show UMLActivityDiagram
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> UMLActivityDiagram -> ShowS
showsPrec :: Int -> UMLActivityDiagram -> ShowS
$cshow :: UMLActivityDiagram -> String
show :: UMLActivityDiagram -> String
$cshowList :: [UMLActivityDiagram] -> ShowS
showList :: [UMLActivityDiagram] -> ShowS
Show, Int -> UMLActivityDiagram -> Doc
[UMLActivityDiagram] -> Doc
(Int -> UMLActivityDiagram -> Doc)
-> ([UMLActivityDiagram] -> Doc) -> ToDoc UMLActivityDiagram
forall a. (Int -> a -> Doc) -> ([a] -> Doc) -> ToDoc a
$ctoDocPrec :: Int -> UMLActivityDiagram -> Doc
toDocPrec :: Int -> UMLActivityDiagram -> Doc
$ctoDocList :: [UMLActivityDiagram] -> Doc
toDocList :: [UMLActivityDiagram] -> Doc
ToDoc)


adjNodes :: AdNode -> UMLActivityDiagram -> [AdNode]
adjNodes :: AdNode -> UMLActivityDiagram -> [AdNode]
adjNodes AdNode
node (UMLActivityDiagram [AdNode]
ns [AdConnection]
conns) =
  let adjLabel :: [Int]
adjLabel = (AdConnection -> Int) -> [AdConnection] -> [Int]
forall a b. (a -> b) -> [a] -> [b]
map AdConnection -> Int
to ([AdConnection] -> [Int]) -> [AdConnection] -> [Int]
forall a b. (a -> b) -> a -> b
$ (AdConnection -> Bool) -> [AdConnection] -> [AdConnection]
forall a. (a -> Bool) -> [a] -> [a]
filter (\AdConnection
c -> AdConnection -> Int
from AdConnection
c Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== AdNode -> Int
label AdNode
node) [AdConnection]
conns
  in (AdNode -> Bool) -> [AdNode] -> [AdNode]
forall a. (a -> Bool) -> [a] -> [a]
filter (\AdNode
node' -> AdNode -> Int
label AdNode
node' Int -> [Int] -> Bool
forall a. Eq a => a -> [a] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [Int]
adjLabel) [AdNode]
ns

isActionNode :: AdNode -> Bool
isActionNode :: AdNode -> Bool
isActionNode AdNode
node =
  case AdNode
node of
    AdActionNode {} -> Bool
True
    AdNode
_ -> Bool
False

isObjectNode :: AdNode -> Bool
isObjectNode :: AdNode -> Bool
isObjectNode AdNode
node =
  case AdNode
node of
    AdObjectNode {} -> Bool
True
    AdNode
_ -> Bool
False

isDecisionNode :: AdNode -> Bool
isDecisionNode :: AdNode -> Bool
isDecisionNode AdNode
node =
  case AdNode
node of
    AdDecisionNode {} -> Bool
True
    AdNode
_ -> Bool
False

isMergeNode :: AdNode -> Bool
isMergeNode :: AdNode -> Bool
isMergeNode AdNode
node =
  case AdNode
node of
    AdMergeNode {} -> Bool
True
    AdNode
_ -> Bool
False

isForkNode :: AdNode -> Bool
isForkNode :: AdNode -> Bool
isForkNode AdNode
node =
  case AdNode
node of
    AdForkNode {} -> Bool
True
    AdNode
_ -> Bool
False

isJoinNode :: AdNode -> Bool
isJoinNode :: AdNode -> Bool
isJoinNode AdNode
node =
  case AdNode
node of
    AdJoinNode {} -> Bool
True
    AdNode
_ -> Bool
False

isInitialNode :: AdNode -> Bool
isInitialNode :: AdNode -> Bool
isInitialNode AdNode
node =
  case AdNode
node of
    AdInitialNode {} -> Bool
True
    AdNode
_ -> Bool
False

isActivityFinalNode :: AdNode -> Bool
isActivityFinalNode :: AdNode -> Bool
isActivityFinalNode AdNode
node =
  case AdNode
node of
    AdActivityFinalNode {} -> Bool
True
    AdNode
_ -> Bool
False

isFlowFinalNode :: AdNode -> Bool
isFlowFinalNode :: AdNode -> Bool
isFlowFinalNode AdNode
node =
  case AdNode
node of
    AdFlowFinalNode {} -> Bool
True
    AdNode
_ -> Bool
False


getInitialNodes :: UMLActivityDiagram -> [AdNode]
getInitialNodes :: UMLActivityDiagram -> [AdNode]
getInitialNodes (UMLActivityDiagram [AdNode]
ns [AdConnection]
_) =
  (AdNode -> Bool) -> [AdNode] -> [AdNode]
forall a. (a -> Bool) -> [a] -> [a]
filter AdNode -> Bool
isInitialNode [AdNode]
ns

getFinalNodes :: UMLActivityDiagram -> [AdNode]
getFinalNodes :: UMLActivityDiagram -> [AdNode]
getFinalNodes (UMLActivityDiagram [AdNode]
ns [AdConnection]
_) =
  (AdNode -> Bool) -> [AdNode] -> [AdNode]
forall a. (a -> Bool) -> [a] -> [a]
filter (\AdNode
x -> AdNode -> Bool
isActivityFinalNode AdNode
x Bool -> Bool -> Bool
|| AdNode -> Bool
isFlowFinalNode AdNode
x) [AdNode]
ns