module Rattletrap.Decode.ReplicationValue
  ( decodeReplicationValueBits
  )
where

import Rattletrap.Decode.Common
import Rattletrap.Decode.DestroyedReplication
import Rattletrap.Decode.SpawnedReplication
import Rattletrap.Decode.UpdatedReplication
import Rattletrap.Type.ClassAttributeMap
import Rattletrap.Type.CompressedWord
import Rattletrap.Type.ReplicationValue
import Rattletrap.Type.Word32le

import qualified Control.Monad.Trans.Class as Trans
import qualified Control.Monad.Trans.State as State
import qualified Data.Map as Map

decodeReplicationValueBits
  :: (Int, Int, Int)
  -> ClassAttributeMap
  -> CompressedWord
  -> State.StateT
       (Map.Map CompressedWord Word32le)
       DecodeBits
       ReplicationValue
decodeReplicationValueBits :: (Int, Int, Int)
-> ClassAttributeMap
-> CompressedWord
-> StateT (Map CompressedWord Word32le) DecodeBits ReplicationValue
decodeReplicationValueBits (Int, Int, Int)
version ClassAttributeMap
classAttributeMap CompressedWord
actorId = do
  Map CompressedWord Word32le
actorMap <- StateT
  (Map CompressedWord Word32le)
  DecodeBits
  (Map CompressedWord Word32le)
forall (m :: * -> *) s. Monad m => StateT s m s
State.get
  Bool
isOpen <- BitGet Bool -> StateT (Map CompressedWord Word32le) DecodeBits Bool
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
Trans.lift BitGet Bool
getBool
  if Bool
isOpen
    then do
      Bool
isNew <- BitGet Bool -> StateT (Map CompressedWord Word32le) DecodeBits Bool
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
Trans.lift BitGet Bool
getBool
      if Bool
isNew
        then
          SpawnedReplication -> ReplicationValue
ReplicationValueSpawned
            (SpawnedReplication -> ReplicationValue)
-> StateT
     (Map CompressedWord Word32le) DecodeBits SpawnedReplication
-> StateT (Map CompressedWord Word32le) DecodeBits ReplicationValue
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Int, Int, Int)
-> ClassAttributeMap
-> CompressedWord
-> StateT
     (Map CompressedWord Word32le) DecodeBits SpawnedReplication
decodeSpawnedReplicationBits (Int, Int, Int)
version ClassAttributeMap
classAttributeMap CompressedWord
actorId
        else UpdatedReplication -> ReplicationValue
ReplicationValueUpdated (UpdatedReplication -> ReplicationValue)
-> StateT
     (Map CompressedWord Word32le) DecodeBits UpdatedReplication
-> StateT (Map CompressedWord Word32le) DecodeBits ReplicationValue
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> BitGet UpdatedReplication
-> StateT
     (Map CompressedWord Word32le) DecodeBits UpdatedReplication
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
Trans.lift
          ((Int, Int, Int)
-> ClassAttributeMap
-> Map CompressedWord Word32le
-> CompressedWord
-> BitGet UpdatedReplication
decodeUpdatedReplicationBits
            (Int, Int, Int)
version
            ClassAttributeMap
classAttributeMap
            Map CompressedWord Word32le
actorMap
            CompressedWord
actorId
          )
    else DestroyedReplication -> ReplicationValue
ReplicationValueDestroyed
      (DestroyedReplication -> ReplicationValue)
-> StateT
     (Map CompressedWord Word32le) DecodeBits DestroyedReplication
-> StateT (Map CompressedWord Word32le) DecodeBits ReplicationValue
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> BitGet DestroyedReplication
-> StateT
     (Map CompressedWord Word32le) DecodeBits DestroyedReplication
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
(MonadTrans t, Monad m) =>
m a -> t m a
Trans.lift BitGet DestroyedReplication
decodeDestroyedReplicationBits