octane 0.6.1 → 0.6.2
raw patch · 5 files changed
+75/−34 lines, 5 files
Files
- library/Octane/Analyzer.hs +54/−25
- library/Octane/Parser.hs +18/−6
- octane.cabal +1/−1
- package.yaml +1/−1
- stack.yaml +1/−1
library/Octane/Analyzer.hs view
@@ -5,6 +5,7 @@ import qualified Data.Binary as Binary import qualified Data.Map.Strict as Map import qualified Data.Maybe as Maybe+import qualified Data.Set as Set import qualified Data.Text as Text import qualified Octane.Parser as Parser import qualified System.Environment as Environment@@ -14,25 +15,37 @@ type Frames = [Parser.Frame] type ActorId = Int -find :: (a -> Bool) -> [a] -> Maybe a-find p xs = xs & filter p & Maybe.listToMaybe--getActorId :: (Parser.Replication -> Bool) -> (Parser.Replication -> ActorId) -> Frames -> Maybe ActorId-getActorId p f frames = frames- & Maybe.mapMaybe (\ frame -> frame- & Parser.frameReplications- & find p- & fmap f)- & Maybe.listToMaybe+-- { car actor id => player actor id }+getCarActorIds :: Frames -> Map.Map ActorId ActorId+getCarActorIds frames = frames+ & concatMap Parser.frameReplications+ & filter (\ replication -> replication+ & Parser.replicationClassName+ & flip Set.member carClassNames)+ & Maybe.mapMaybe (\ replication -> let+ carActorId = replication+ & Parser.replicationActorId+ maybeProperty = replication+ & Parser.replicationProperties+ & Map.lookup playerReplicationInfoPropertyName+ in case maybeProperty of+ Nothing -> Nothing+ Just property -> case property of+ Parser.PFlaggedInt _ playerActorId -> Just (carActorId, playerActorId)+ _ -> Nothing)+ & Map.fromList -getBallActorId :: Frames -> Maybe ActorId-getBallActorId frames = getActorId- (\ replication -> replication+getBallActorIds :: Frames -> Set.Set ActorId+getBallActorIds frames = frames+ & concatMap Parser.frameReplications+ & filter (\ replication -> replication & Parser.replicationClassName & (== ballClassName))- Parser.replicationActorId- frames+ & map (\ replication -> replication+ & Parser.replicationActorId)+ & Set.fromList +-- { player actor id => player name } getPlayerActorIds :: Frames -> Map.Map ActorId Text.Text getPlayerActorIds frames = frames & concatMap Parser.frameReplications@@ -52,8 +65,8 @@ _ -> Nothing) & Map.fromList -getRigidBodyStatesForActorId :: ActorId -> Frames -> [(Parser.Time, Point)]-getRigidBodyStatesForActorId actorId frames = frames+getRigidBodyStatesForActorId :: Frames -> ActorId -> [(Parser.Time, Point)]+getRigidBodyStatesForActorId frames actorId = frames & concatMap (\ frame -> let time = Parser.frameTime frame in frame@@ -70,22 +83,34 @@ & map (\ (Parser.Vector x y z) -> (x, y, z)) & map (\ point -> (time, point))) +getBallRigidBodyStates :: Frames -> [[(Parser.Time, Point)]]+getBallRigidBodyStates frames = frames+ & getBallActorIds+ & Set.toAscList+ & map (\ actorId -> actorId+ & getRigidBodyStatesForActorId frames)+ getBallLocations :: Frames -> Points-getBallLocations frames = let- ballActorId = frames- & getBallActorId- & Maybe.fromJust- rigidBodyStates = frames- & getRigidBodyStatesForActorId ballActorId- in rigidBodyStates- & map snd+getBallLocations frames = frames+ & getBallRigidBodyStates+ & concat+ & map snd +carClassNames :: Set.Set Text.Text+carClassNames =+ [ "TAGame.Car_Season_TA"+ , "TAGame.Car_TA"+ ] & map Text.pack & Set.fromList+ ballClassName :: Text.Text ballClassName = Text.pack "TAGame.Ball_TA" playerClassName :: Text.Text playerClassName = Text.pack "TAGame.PRI_TA" +playerReplicationInfoPropertyName :: Text.Text+playerReplicationInfoPropertyName = Text.pack "Engine.Pawn:PlayerReplicationInfo"+ rbsPropertyName :: Text.Text rbsPropertyName = Text.pack "TAGame.RBActor_TA:ReplicatedRBState" @@ -196,6 +221,10 @@ let playerActorIds = getPlayerActorIds frames putStrLn "Players:" playerActorIds & Map.toList & mapM_ print++ let carActorIds = getCarActorIds frames+ putStrLn "Cars:"+ carActorIds & Map.toList & mapM_ print main :: IO () main = do
library/Octane/Parser.hs view
@@ -77,7 +77,7 @@ , frameDelta = delta , frameReplications = replications }- return (newContext, frame)+ (newContext, frame) & DeepSeq.force & return getReplications :: Context -> Bits.BitGet (Context, [Replication]) getReplications context = do@@ -272,8 +272,8 @@ getByteProperty :: Bits.BitGet PropValue getByteProperty = do- int <- getInt8- return (PByte int)+ word <- getWord8+ return (PByte word) getCamSettingsProperty :: Bits.BitGet PropValue getCamSettingsProperty = do@@ -552,7 +552,7 @@ data PropValue = PBoolean !Bool- | PByte !Int+ | PByte !Word.Word8 | PCamSettings !Float !Float !Float !Float !Float !Float | PDemolish !Bool !Int !Bool !Int !(Vector Int) !(Vector Int) | PEnum !Word.Word16 !Bool@@ -626,8 +626,10 @@ , thingClassId :: !Int , thingClassName :: !Text.Text , thingClassInit :: !ClassInit- } deriving (Show)+ } deriving (Eq, Generics.Generic, Show) +instance DeepSeq.NFData Thing+ type Time = Float type Delta = Float@@ -671,8 +673,10 @@ , contextClassPropertyMap :: !ClassPropertyMap , contextThings :: !(IntMap.IntMap Thing) , contextClassMap :: !ClassMap- } deriving (Show)+ } deriving (Eq, Generics.Generic, Show) +instance DeepSeq.NFData Context+ extractContext :: Type.Replay -> Context extractContext replay = Context@@ -825,6 +829,14 @@ Binary.getWord8 (byte & BSL.fromStrict & BSL.map Type.reverseBits) word & fromIntegral & (\ x -> x :: Int.Int8) & fromIntegral & return++getWord8 :: Bits.BitGet Word.Word8+getWord8 = do+ byte <- Bits.getByteString 1+ let word = Binary.runGet+ Binary.getWord8+ (byte & BSL.fromStrict & BSL.map Type.reverseBits)+ return word getActorId :: Bits.BitGet Int getActorId = getInt 1024
octane.cabal view
@@ -3,7 +3,7 @@ -- see: https://github.com/sol/hpack name: octane-version: 0.6.1+version: 0.6.2 synopsis: Parse Rocket League replays. description: Octane parses Rocket League replays. category: Game
package.yaml view
@@ -68,4 +68,4 @@ - -with-rtsopts=-N main: TestSuite.hs source-dirs: test-suite-version: '0.6.1'+version: '0.6.2'
stack.yaml view
@@ -1,1 +1,1 @@-resolver: nightly-2016-05-30+resolver: nightly-2016-06-04