first little optimisation

This commit is contained in:
nek0 2023-05-20 18:36:31 +02:00
parent c0f8e10f44
commit 4ee6c368df
3 changed files with 59 additions and 32 deletions

View file

@ -24,6 +24,7 @@ import Types
import Memory import Memory
import Util import Util
import Data.Maybe (fromMaybe) import Data.Maybe (fromMaybe)
import Mesh (compactDraws)
frameOverlap :: Int frameOverlap :: Int
frameOverlap = 2 frameOverlap = 2
@ -221,22 +222,12 @@ recordCommandBuffer
renderObjects <- (liftIO . STM.atomically . STM.readTMVar) =<< asks renderables renderObjects <- (liftIO . STM.atomically . STM.readTMVar) =<< asks renderables
meshMap <- (liftIO . STM.atomically . STM.readTMVar) =<< asks meshLibrary meshMap <- (liftIO . STM.atomically . STM.readTMVar) =<< asks meshLibrary
materialMap <- (liftIO . STM.atomically . STM.readTMVar) =<< asks materialLibrary
let draws = compactDraws meshMap materialMap renderObjects
V.mapM_ V.mapM_
(\(index, RenderObject meshID materialID modelMatrix) -> do (\(IndirectBatch mesh material first count) -> do
materialMap <- (liftIO . STM.atomically . STM.readTMVar) =<< asks materialLibrary
let constants = MeshPushConstants
{ meshPushData = V4 0 0 0 0
, meshRenderMatrix = modelMatrix
}
mesh = fromMaybe
(error $ "no mesh called " <> meshID <> " present")
(meshMap M.!? meshID)
material = fromMaybe
(error $ "no material called " <> materialID <> " present")
(materialMap M.!? materialID)
when when
(materialTextureSet material /= Vk.NULL_HANDLE) (materialTextureSet material /= Vk.NULL_HANDLE)
@ -267,28 +258,19 @@ recordCommandBuffer
(V.singleton $ frameObjectDescriptor frame) (V.singleton $ frameObjectDescriptor frame)
V.empty V.empty
dataPointer <- liftIO (castPtr <$> new constants)
Vk.cmdPushConstants
commandBuffer
(materialPipelineLayout material)
Vk.SHADER_STAGE_VERTEX_BIT
0
(fromIntegral $ sizeOf constants)
dataPointer
Vk.cmdBindVertexBuffers Vk.cmdBindVertexBuffers
commandBuffer commandBuffer
0 0
(V.fromList [ allocatedBuffer $ meshBuffer mesh ]) (V.fromList [ allocatedBuffer $ meshBuffer mesh ])
(V.fromList [ 0 ]) (V.fromList [ 0 ])
Vk.cmdDraw commandBuffer (fromIntegral $ V.length $ meshVertices mesh) 1 0 index mapM_
) (\index ->
(V.zip Vk.cmdDraw commandBuffer (fromIntegral $ V.length $ meshVertices mesh) 1 0 index
(V.fromList [0 ..]) )
renderObjects ([first .. first + count])
) )
draws
prepareRecording prepareRecording
:: V2 CInt :: V2 CInt

View file

@ -189,3 +189,37 @@ loadFromObj filepath vma uploadContext queue device = do
(fromMaybe (error "no UV coordinates present") (faceTexCoordIndex index) - 1) (fromMaybe (error "no UV coordinates present") (faceTexCoordIndex index) - 1)
in in
V2 r s V2 r s
compactDraws
:: M.Map String Mesh
-> M.Map String Material
-> V.Vector RenderObject
-> V.Vector IndirectBatch
compactDraws meshLib materialLib objects =
V.foldl
(\acc (index, RenderObject mesh material _) ->
let newDraw = IndirectBatch
{ batchMesh = meshLib M.! mesh
, batchMaterial = materialLib M.! material
, batchFirst = index
, batchCount = 1
}
sameMesh = not (V.null acc) && (meshLib M.! mesh == batchMesh (V.last acc))
sameMaterial = not (V.null acc) && (materialLib M.! material == batchMaterial (V.last acc))
in
if sameMesh && sameMaterial
then
V.init acc `V.snoc` ((V.last acc)
{ batchCount = batchCount (V.last acc) + 1
})
else
acc `V.snoc` newDraw
)
V.empty
(V.zip
(V.fromList [0..])
objects
)

View file

@ -54,13 +54,17 @@ data AllocatedBuffer = AllocatedBuffer
} }
deriving (Show) deriving (Show)
instance Eq AllocatedBuffer where
(AllocatedBuffer buf1 _ _) == (AllocatedBuffer buf2 _ _) = buf1 == buf2
data Vertex = Vertex data Vertex = Vertex
{ vertexPosition :: V3 Float { vertexPosition :: V3 Float
, vertexNormal :: V3 Float , vertexNormal :: V3 Float
, vertexColor :: V4 Float , vertexColor :: V4 Float
, vertexUV :: V2 Float , vertexUV :: V2 Float
} }
deriving (Show) deriving (Show, Eq)
instance Storable Vertex where instance Storable Vertex where
@ -143,7 +147,7 @@ data Mesh = Mesh
{ meshVertices :: V.Vector Vertex { meshVertices :: V.Vector Vertex
, meshBuffer :: AllocatedBuffer , meshBuffer :: AllocatedBuffer
} }
deriving (Show) deriving (Show, Eq)
data MeshPushConstants = MeshPushConstants data MeshPushConstants = MeshPushConstants
{ meshPushData :: V4 Float { meshPushData :: V4 Float
@ -180,7 +184,7 @@ data Material = Material
, materialPipeline :: Vk.Pipeline , materialPipeline :: Vk.Pipeline
, materialPipelineLayout :: Vk.PipelineLayout , materialPipelineLayout :: Vk.PipelineLayout
} }
deriving (Show) deriving (Show, Eq)
data RenderObject = RenderObject data RenderObject = RenderObject
{ objectMesh :: String { objectMesh :: String
@ -317,3 +321,10 @@ data UploadContext = UploadContext
, uploadCommandBuffer :: Vk.CommandBuffer , uploadCommandBuffer :: Vk.CommandBuffer
} }
deriving (Show) deriving (Show)
data IndirectBatch = IndirectBatch
{ batchMesh :: Mesh
, batchMaterial :: Material
, batchFirst :: Word32
, batchCount :: Word32
}