Compare commits

..

253 Commits

Author SHA1 Message Date
Jace 3261e21d96 Coloring players depending on team and created a blue spawn in MovementTest 2016-01-24 15:46:01 +01:00
Jace 373bb33cf0 Player jumping taking air acceleration into account 2016-01-24 15:20:34 +01:00
Jace aaa11d2109 Merge remote-tracking branch 'origin/master' into PlayerMovement 2016-01-24 14:18:23 +01:00
Jace 1ce9128da8 Source-like movement 2016-01-23 19:45:23 +01:00
Viktor Ljung 132de88d28 Merge pull request #50 from teamfisk/Forward+
Forward+
2016-01-23 18:23:16 +01:00
viktorljung df485ccf7b Merge branch 'master' into Forward+ 2016-01-23 18:21:35 +01:00
viktorljung 85a4d98c81 Revert "Revert "Merge pull request #43 from teamfisk/Forward+""
This reverts commit bd62b5873d.
2016-01-23 18:21:10 +01:00
viktorljung ef020a3770 Text fixed 2016-01-23 18:17:20 +01:00
viktorljung 160b7183b2 WIP 2016-01-23 18:07:07 +01:00
Tleety 5edf5a41f1 Transparency bug fix 2016-01-23 16:45:26 +01:00
viktorljung ff6ec82a6c AMD fix 2016-01-23 16:27:01 +01:00
viktorljung bd62b5873d Revert "Merge pull request #43 from teamfisk/Forward+"
This reverts commit d59ab5aba2, reversing
changes made to bef95235d0.
2016-01-23 15:57:26 +01:00
Jace 666ef6589e Crouching! 2016-01-23 15:06:47 +01:00
Jace b83d773627 Infinite respawning for now 2016-01-23 15:06:41 +01:00
Viktor Ljung d59ab5aba2 Merge pull request #43 from teamfisk/Forward+
Bloom render pass and HDR colors
2016-01-23 14:58:10 +01:00
Tleety f623232a2b Removed a temp variable. 2016-01-23 14:52:29 +01:00
Tleety 6a18cb88af Merge remote-tracking branch 'origin/master' into Forward+
# Conflicts:
#	include/Engine/Rendering/Renderer.h
#	src/Engine/Rendering/PickingPass.cpp
#	src/Engine/Rendering/Renderer.cpp
2016-01-23 13:59:21 +01:00
Tleety b499f4b020 Fixed some rendering bugs and some code refactoring 2016-01-23 12:17:38 +01:00
Jace 482689fd48 fixup! Moved FirstPersonInputController implementation out of header 2016-01-23 12:16:40 +01:00
Jace 32f73201c5 Basic jumping! 2016-01-23 12:15:33 +01:00
Jace 3aeeb3cad5 Moved FirstPersonInputController implementation out of header 2016-01-23 12:15:32 +01:00
Jace 4d5cbb6057 fixup! Added EntityWrapper::IsChildOf and made snapshot interpolation and rendering exceptions for player less hacky 2016-01-23 12:14:29 +01:00
Jace bef95235d0 Merge pull request #41 from teamfisk/TextRendering
Text rendering
2016-01-23 11:51:11 +01:00
viktorljung 9a23d8887a Merge remote-tracking branch 'origin/master' into TextRendering
# Conflicts:
#	include/Engine/Rendering/RenderSystem.h
#	src/Engine/Rendering/RenderSystem.cpp
2016-01-23 11:48:10 +01:00
Jace db0e67b9bd Added EntityWrapper::IsChildOf and made snapshot interpolation and rendering exceptions for player less hacky 2016-01-23 11:44:16 +01:00
viktorljung e4513376bb fixup! Changed name and made a TextPassState 2016-01-23 11:39:10 +01:00
viktorljung 445248af55 Changed name and made a TextPassState 2016-01-23 11:38:31 +01:00
Jace 64a7239b17 Merge pull request #46 from teamfisk/CapturePointCrashFixBranch
Crash fix for: if you delete a team component in editor.
2016-01-23 11:10:57 +01:00
Jace 31e7340daf Ignoring interpolation and rendering for local player entities! 2016-01-23 00:40:37 +01:00
Jace 3ac3311c0c "inline" caused missing symbol when compiling in Release for some reason 2016-01-23 00:38:11 +01:00
Jace 90867b094a Merge remote-tracking branch 'origin/TextRendering' into Networking
# Conflicts:
#	include/Engine/Rendering/RenderSystem.h
#	src/Engine/Rendering/RenderSystem.cpp
2016-01-22 22:08:56 +01:00
Jace 55ee2bb3bf Player input properly separated from editor input and server 2016-01-22 21:35:31 +01:00
stiffly 406b730ef3 Sends entity names. Temporarily 2016-01-22 19:07:20 +01:00
stiffly b37b20b7d8 Didn't bulid lol. Fixed. 2016-01-22 17:57:31 +01:00
stiffly 750442d224 Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-22 17:49:56 +01:00
stiffly 389e057611 EPlayerSpawned special logic added to server and client. 2016-01-22 17:49:21 +01:00
Jace 74d9bae896 Added conditional spawning based on whether the running instance is a server or not 2016-01-22 17:34:57 +01:00
stiffly 74c95089ea Merge remote-tracking branch 'origin/PlayerMovement' into Networking 2016-01-22 16:19:35 +01:00
Jace ca2aab449e Basic movement and camera management between players and editor 2016-01-22 16:12:51 +01:00
Tleety 7498cebf5e Merge remote-tracking branch 'origin/master' into Forward+
# Conflicts:
#	src/Engine/Rendering/DrawFinalPassState.cpp
#	src/Engine/Rendering/PickingPass.cpp
#	src/Engine/Rendering/Renderer.cpp
2016-01-22 15:57:38 +01:00
Tleety 2b8debbfff Added MipMap texture generation 2016-01-22 15:55:32 +01:00
stiffly 08c476e9e3 Added kick logic to the server. Also typedefed. 2016-01-22 15:42:36 +01:00
stiffly 10c3b475bf Merge remote-tracking branch 'origin/Networking' into Networking
# Conflicts:
#	src/Engine/Network/Client.cpp
#	src/Engine/Network/Server.cpp
2016-01-22 13:19:51 +01:00
stiffly 08fcdb382b Used config for a lot of things 2016-01-22 13:18:53 +01:00
stiffly b1ea5429ce Used config for a lot of things 2016-01-22 11:53:04 +01:00
stiffly fcc9d64e7a Now publishes an EPlayerDisconnected event 2016-01-22 10:58:10 +01:00
Tleety caf55fb8d1 Small fix to the bloom light, now feels smoother. 2016-01-22 10:52:45 +01:00
stiffly 7a95880e10 Merge remote-tracking branch 'origin/master' into Networking 2016-01-22 10:36:11 +01:00
Jocke 6cd073c3c8 Added network metrics logging and reactored code. 2016-01-22 10:32:54 +01:00
Jace 1e3fc1ae2d Created EPlayerSpawned that gets published when a player spawns 2016-01-22 10:16:35 +01:00
verysecrethero 6f739e22f3 Crash fix for: if you delete a team component in editor. 2016-01-22 10:10:39 +01:00
Jace 8cf83454d7 Fixed input going through editor UI 2016-01-21 17:45:20 +01:00
William Moberg 41f0daaf3f Merge pull request #45 from teamfisk/ShootEvent
Changed some files so it works with the changes in master. (weaponsys…
2016-01-21 17:40:57 +01:00
verysecrethero deb6ff1b16 Changed some files so it works with the changes in master. (weaponsystem,capturepoint,some tests) 2016-01-21 17:36:47 +01:00
William Moberg 4d60f387ed Merge pull request #44 from teamfisk/EditorUsefulness
Editor refactoring
2016-01-21 17:03:52 +01:00
Jace f740d46683 Merge branch 'EditorUsefulness' of github.com:teamfisk/TacticalZ into EditorUsefulness 2016-01-21 17:01:06 +01:00
Jace 75dcdcec41 Fixed inconsistent editor input controls. Left mouse = select and move. Right mouse = camera. 2016-01-21 17:00:47 +01:00
viktorljung 254caf9e5d Picking depthbuffer fix 2016-01-21 16:49:20 +01:00
Jace 1c6750f5b0 Fixed uniform scale on editor widgets 2016-01-21 16:37:35 +01:00
William Moberg 3548cfa248 Merge pull request #27 from teamfisk/ShootEvent
Shoot event
2016-01-21 16:35:55 +01:00
verysecrethero 973ccd34c9 Removed unnecessary string in EPlayerDamage (TypeOfDamage). Renamed a variable in WeaponSystem 2016-01-21 16:30:07 +01:00
Jace 43b8fd29f6 Fixed widget world movement 2016-01-21 16:21:20 +01:00
Jace a6548a72b3 Merge remote-tracking branch 'origin/master' into EditorUsefulness
# Conflicts:
#	include/Engine/Collision/CollidableOctreeSystem.h
#	include/Engine/Collision/CollisionSystem.h
#	include/Engine/Collision/TriggerSystem.h
#	include/Engine/Rendering/RenderSystem.h
#	include/Game/Systems/PlayerSystem.h
#	resources/Schema/Components/Physics.xsd
#	resources/Schema/Types/Entity.xsd
#	src/Engine/Rendering/RenderSystem.cpp
#	src/Engine/Rendering/Renderer.cpp
#	src/Game/Game.cpp
#	src/Game/Systems/HealthSystem.cpp
#	src/Game/Systems/PlayerSystem.cpp
#	src/Tests/OctTreeTestGameClass.cpp
2016-01-21 16:16:35 +01:00
verysecrethero 7deb32431e Removed Color TestCode in WeaponSystem 2016-01-21 16:03:30 +01:00
Jace fc06a4babc Editor keyboard shortcuts:
Ctrl+S to save the currently selected entity file (iterates to the base parent)
Ctrl+N to create a new empty entity under the selection
Ctrl+O to import an entity file
Del to delete an entity
2016-01-21 15:58:27 +01:00
Tobias Dahl c6e9aad0c7 Merge pull request #42 from teamfisk/SpawnMiniBranch
HealthSystem now deletes the entity after publishing the PlayerDeath …
2016-01-21 15:10:16 +01:00
Tleety afe43c5f44 Shader will now handle Glowmaps. However the load code is not there yet. 2016-01-21 14:53:47 +01:00
verysecrethero 2381f01d12 HealthSystem now deletes the entity after publishing the PlayerDeath event 2016-01-21 14:25:01 +01:00
Jace b9147344e1 Semi-working translation widget 2016-01-21 14:14:22 +01:00
Tleety 70bbc5ed0a Normals scaling with model scale bug fixed. 2016-01-21 13:52:43 +01:00
Jace 0183e1bdb7 Fixed enum string parsing bug that would ignore parsing additional fields in a component after it encountered the first enum. 2016-01-21 12:24:08 +01:00
Tleety 983f90504d Bloom effect added, will have to see if it needs improving. Also added HDR colors and gamma correction. 2016-01-21 12:02:28 +01:00
verysecrethero bdebc9de62 WeaponSystem now handles "PrimaryFire" input events. It sends out ePlayerDamage event if it hits a player. Included some tests 2016-01-21 11:55:51 +01:00
Jace f1345419b6 EditorWidgetSystem that takes care of moving widgets around 2016-01-21 10:30:19 +01:00
Jace 5e70d6eef6 EntityWrapper::Parent helper function 2016-01-21 10:29:48 +01:00
Jace 4aa9100c69 Camera::WorldToScreen helper function 2016-01-21 10:29:36 +01:00
verysecrethero 7b34e001ba Merge remote-tracking branch 'origin/master' into ShootEvent 2016-01-21 10:26:42 +01:00
verysecrethero c2e05de89f Deleted some components, etc for ShootEvent that will likely be used in a WeaponSystem instead 2016-01-21 10:24:34 +01:00
viktorljung ea9c4d19d0 Merge remote-tracking branch 'origin/master' into TextRendering
# Conflicts:
#	include/Game/Game.h
2016-01-21 10:19:32 +01:00
viktorljung f3bfe388af Clean up 2016-01-21 10:16:03 +01:00
Jace 70cab9ef30 Merge pull request #40 from teamfisk/Networking
Networking
2016-01-21 10:03:44 +01:00
Jace f1a54a89b3 Merge pull request #37 from teamfisk/OctTree
Oct tree
2016-01-21 09:57:46 +01:00
verysecrethero b098bd2bd3 Merge remote-tracking branch 'origin/master' into ShootEvent
# Conflicts:
#	include/Engine/Core/ComponentWrapper.h
#	include/Game/PlayerSystem.h
#	include/Game/Systems/HealthSystem.h
#	resources/Schema/Components.xsd
#	resources/Schema/Components/Player.xml
#	resources/Schema/Types/Entity.xsd
#	src/Game/PlayerSystem.cpp
#	src/Tests/HealthSystemTest.cpp
#	src/Tests/OctTreeTestAnders.cpp
#	src/Tests/OctTreeTestGameClass.cpp
#	src/Tests/OctTreeTestGameClass.h
#	src/Tests/OctTreeTestHardCodedTestWorld.h
2016-01-20 17:53:33 +01:00
William Moberg 60037c2849 Merge pull request #31 from teamfisk/CapturePointTake
Capture point take
2016-01-20 17:43:20 +01:00
Jocke cd67253173 Added logic to go from spectator to player. 2016-01-20 17:41:16 +01:00
verysecrethero a596b8746b CapturePointTimers are now reset for "inactive" CapturePoints after a capture. 2016-01-20 17:32:20 +01:00
verysecrethero 35876f6425 Removed membervariable m_NextPossibleCapturePointand added it as local instead 2016-01-20 16:37:10 +01:00
verysecrethero f6ce98249e Merge remote-tracking branch 'origin/master' into CapturePointTake 2016-01-20 16:32:14 +01:00
Jocke 00588b07c5 Merge branch 'Networking' of github.com:teamfisk/TacticalZ into Networking
# Conflicts:
#	src/Engine/Network/Client.cpp
#	src/Engine/Network/Server.cpp
2016-01-20 16:30:12 +01:00
stiffly 3376f4a16e Added server has timed out logic to client. (>'')> 2016-01-20 16:27:53 +01:00
Jocke 25d2aa3464 "Supporting" spectators. Using a vector for connected units as we do not interpret as players. ““”̿ ̿ ̿ ̿ ̿’̿’̵͇̿̿з=(•̪●)=ε/̵͇̿̿/̿ ̿ ̿ ̿ ̿’““ 2016-01-20 16:27:23 +01:00
verysecrethero 29aefc5af2 Added some more visual CaptureTestState xml files 2016-01-20 16:06:35 +01:00
verysecrethero 39ae83efd4 Fixed all tests in CapturePointTest and cleaned up some comments 2016-01-20 15:40:56 +01:00
Tleety 86824f1b1f Colors above value 1 is now added to the bloomtexture, and will be used to get a glow effect in later stage. 2016-01-20 15:23:49 +01:00
verysecrethero 8189e3c00c Logic in CapturePointSystem is working again. Need to update all Tests! 2016-01-20 14:59:18 +01:00
Jocke 4d01cdf895 Merge branch 'Networking' of github.com:teamfisk/TacticalZ into Networking
# Conflicts:
#	src/Engine/Network/Client.cpp
2016-01-20 14:33:17 +01:00
stiffly 7e7ca7edcf Listening to "DisconnectFromServer" 2016-01-20 14:32:04 +01:00
Jocke e9a576341e Started on server disconnect logic. 2016-01-20 14:31:50 +01:00
Jocke f52cddb445 Added packet loss logic for multiple clients.
Changed packet class to fit our needs.
2016-01-20 13:43:11 +01:00
Tleety 78a1037983 WIP
DrawScreenQuad implemented and working.
Started work on HDR coloring.
2016-01-20 13:34:56 +01:00
stiffly 85523343b2 Merge remote-tracking branch 'origin/master' into Networking 2016-01-20 10:24:53 +01:00
William Moberg 410e349329 Added test map for capture points and some debug code. 2016-01-19 18:27:58 +01:00
viktorljung ce27b224df Merge remote-tracking branch 'origin/master' into TextRendering
# Conflicts:
#	include/Engine/Rendering/RenderQueue.h
#	include/Engine/Rendering/RenderSystem.h
#	include/Engine/Rendering/Renderer.h
#	src/Engine/Rendering/RenderSystem.cpp
2016-01-19 17:27:09 +01:00
verysecrethero b45de542da CapturePointSystem updated, all tests are green 2016-01-19 17:19:58 +01:00
viktorljung f0763bc2a3 Font loading crash fixed 2016-01-19 17:18:18 +01:00
William Moberg d1b6fb1259 Tiny logic alteration so we don't get false warnings in debug. 2016-01-19 16:59:02 +01:00
Joachim Pettersson dfa96f74e1 Merge pull request #39 from teamfisk/Forward+
Forward+
2016-01-19 16:53:07 +01:00
Tleety 5d6d0f82b9 Removed some debug code 2016-01-19 16:48:59 +01:00
Tleety a124ab2400 Some asset shit.
Fixed testworld to use the right model.
2016-01-19 16:11:56 +01:00
Tleety d2263b0c90 Assets added 2016-01-19 16:09:30 +01:00
Tleety a8ffb24040 latest commit fix 2016-01-19 16:08:09 +01:00
Tleety 893ef38237 Removed world from renderer and moved depth-calculation code to modeljob 2016-01-19 15:41:17 +01:00
verysecrethero f197993beb Changed CapturePointSystem in light of new enums in the components and a teamcomponent. Half the tests are currently working 2016-01-19 15:31:15 +01:00
William Moberg 017ad96bbe Fixed some errors in Tests. 2016-01-19 15:20:29 +01:00
stiffly ad9bb5fba4 Added an extra interpolation point. 2016-01-19 15:03:10 +01:00
William Moberg 713ebbe18c Can add any objects that inherit from AABB into the Octree. 2016-01-19 14:50:46 +01:00
Tleety 982837052a DirectionalLight now correctly getting directions 2016-01-19 14:44:17 +01:00
Jace 8854794cbc fixup! Editor widget selection and creation 2016-01-19 14:31:56 +01:00
stiffly e0c4394f20 Merge. Also fixed interpolation for scale and rotation.
Merge remote-tracking branch 'origin/master' into Networking

# Conflicts:
#	include/Game/Game.h
#	src/Game/CMakeLists.txt
#	src/Game/Game.cpp
2016-01-19 14:04:25 +01:00
Jace 260203fa4d Annotation on physics component 2016-01-19 13:28:16 +01:00
Jace d030e8f699 Editor widget selection and creation 2016-01-19 13:28:02 +01:00
Jace 61984d2c4a Removed lots of slowing debug output from entity parsing pipeline 2016-01-19 13:27:29 +01:00
Jace cfe023cc1d Created ComponentInfo::EnumType which defines which native type to use for enums. 2016-01-19 12:33:53 +01:00
Tleety 4cafb2fc4c Merge remote-tracking branch 'origin/master' into Forward+ 2016-01-19 12:33:08 +01:00
Tleety 46e17b7e0d Working directional light 2016-01-19 12:32:34 +01:00
Jace a6445c65aa Fixed EntityParser to handle string enums properly. 2016-01-19 12:15:20 +01:00
Jace 162523d3ca Made EntityFileWriter store enums as strings instead of integer values to be resistant to enum value changes! 2016-01-19 11:55:27 +01:00
viktorljung dbe56280a6 Resolution fixed and Centered text 2016-01-19 11:45:34 +01:00
Jace 3fb975a8d9 Editor widget entities 2016-01-19 11:44:03 +01:00
Jace 267a60ef30 Better loading of editor toolbox icons 2016-01-19 11:43:38 +01:00
Jace 68af853a03 Editor entity naming 2016-01-19 11:43:03 +01:00
stiffly 3142c701e3 WIP interpolating scale and orientation 2016-01-19 11:42:30 +01:00
Jace b62e42567c Fixed editor enum selection 2016-01-19 11:35:31 +01:00
Jace 9e3dfff7b6 WIP world pausing 2016-01-19 00:52:17 +01:00
Jace 79eaa7364c Editor toolbox buttons 2016-01-18 23:59:46 +01:00
Jace 51979d7f0c Changed System to take World through constructor and store it instead, cause it makes more sense. 2016-01-18 23:59:33 +01:00
Jace 3fc44e944c Editor entity reparenting. 2016-01-18 21:20:20 +01:00
Jace 1760f9dfb1 Added inequality operator to EntityWrapper 2016-01-18 21:17:52 +01:00
Jace d4242bbead Editor entity create and delete. 2016-01-18 19:26:00 +01:00
Jace 631dd57eeb Editor entity import, save, delete, component attach, component delete. 2016-01-18 18:55:19 +01:00
Jace 9cb5f4bd2f Added a stats window 2016-01-18 18:54:57 +01:00
William Moberg 621d935d7a Octree returns correct boxes when testing along an axis by searching through the correct child subtrees. 2016-01-18 18:24:11 +01:00
William Moberg b2358a1854 Added bool in Physics to toggle gravity for entities. 2016-01-18 18:16:24 +01:00
stiffly a6425160fd Merge branch 'Networking' of github.com:teamfisk/TacticalZ into Networking
# Conflicts:
#	include/Game/InterpolationSystem.h
#	src/Game/InterpolationSystem.cpp
2016-01-18 18:13:19 +01:00
stiffly 88eb3ca2db Scraping queues for interpolation 2016-01-18 18:07:59 +01:00
Jocke 3e90ed564c Moved Struct in InterpolationSystem.h and fixed bug. 2016-01-18 18:07:39 +01:00
Tleety 4b29d48f27 WIP 2016-01-18 17:57:45 +01:00
viktorljung c4594524da Better default values and documentation 2016-01-18 17:51:17 +01:00
viktorljung 2a93e2ae7f Merge remote-tracking branch 'origin/master' into TextRendering
# Conflicts:
#	include/Engine/Rendering/RenderQueue.h
#	include/Engine/Rendering/RenderSystem.h
#	include/Game/Game.h
#	resources/Schema/Types/Entity.xsd
#	src/Engine/Rendering/RenderSystem.cpp
2016-01-18 17:44:26 +01:00
Jocke 14b1d541dc Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-18 17:34:32 +01:00
stiffly 765509b510 Added interpolationsystem to pipeline. 2016-01-18 17:34:17 +01:00
Jocke 8952c1a7e4 Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-18 17:28:09 +01:00
Jocke fc305f8bf4 Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-18 17:27:55 +01:00
stiffly 62c3f72355 Fixed cmake for interpolationsystem. 2016-01-18 17:27:37 +01:00
viktorljung 92553f1e93 text size can now be entered in the filepath with a comma separator, like this "filepath,16" 2016-01-18 17:17:12 +01:00
Jocke 70cbb02cb2 Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-18 17:13:10 +01:00
Jocke 0c7f2c5198 WIP implemented Interpolation (server logic) 2016-01-18 17:12:42 +01:00
stiffly d7780d8248 WIP implementing interpolation 2016-01-18 17:11:37 +01:00
Tleety 601ce85c05 WIP 2016-01-18 16:50:41 +01:00
verysecrethero 4c1a49a8a4 Merge remote-tracking branch 'origin/master' into CapturePointTake
# Conflicts:
#	include/Engine/Core/ComponentWrapper.h
#	include/Game/PlayerSystem.h
#	include/Game/Systems/HealthSystem.h
#	resources/Schema/Components.xsd
#	resources/Schema/Components/Player.xml
#	resources/Schema/Types/Entity.xsd
#	src/Game/CMakeLists.txt
#	src/Game/PlayerSystem.cpp
#	src/Game/Systems/HealthSystem.cpp
#	src/Tests/OctTreeTestGameClass.cpp
#	src/Tests/OctTreeTestGameClass.h
#	src/Tests/OctTreeTestGameMain.cpp
#	src/Tests/OctTreeTestHardCodedTestWorld.h
2016-01-18 16:48:49 +01:00
Tleety 01a164847c Directional light now fully added to all lists. 2016-01-18 15:15:33 +01:00
Tleety 794635b6a1 Added DirectionalLights to renderqueue jobs 2016-01-18 14:58:19 +01:00
Tleety 0a3b6f4da1 Added DirectionalLightJob 2016-01-18 14:57:55 +01:00
Jace 3bc7dceca5 Made EntityWrapper hashable 2016-01-18 14:55:49 +01:00
verysecrethero e0410d4345 Small logicfix in CapturePointSystem. Readded CapturePointSystem in Game. Added 2 tests. Tests have been refined a lot. 2016-01-18 14:41:16 +01:00
Tleety 6f1fd19ac7 Directional lights now being filled into m_LightSources 2016-01-18 14:30:28 +01:00
Tleety 6680f6863f DirectionalLight component added. 2016-01-18 14:30:22 +01:00
Tleety 4092f6b4d4 New Lightstruct working. 2016-01-18 14:20:28 +01:00
Jace 504f301e4d Added refactored property sheet for components 2016-01-18 13:51:22 +01:00
William Moberg bf3f8aea89 Merge pull request #36 from teamfisk/PlayerMovement
Player movement
2016-01-18 13:32:42 +01:00
William Moberg 0669d91767 CollisionSystem loops over Collidable components. 2016-01-18 13:29:10 +01:00
William Moberg 942064c450 Removed class PlayerSystem and associated files. 2016-01-18 13:07:04 +01:00
Jocke 6ba6deb863 Removed some debug spam. 2016-01-18 11:35:35 +01:00
stiffly cc604f8e9a Merge remote-tracking branch 'origin/Networking' into Networking 2016-01-18 11:06:51 +01:00
stiffly e97f4a3563 Merge remote-tracking branch 'origin/Networking' into Networking
# Conflicts:
#	src/Engine/Network/Client.cpp
#	src/Engine/Network/Server.cpp
#	src/Game/Game.cpp
2016-01-18 11:06:27 +01:00
Jocke d995713d3b Added input queue to Client and Input Listener debug code in server. 2016-01-18 11:06:02 +01:00
Jace fb7e0498a8 Merge pull request #35 from teamfisk/DisableMemoryPool
Possible to disable the MemoryPool allocation in Config files.
2016-01-18 10:46:53 +01:00
Jace e39e4064f2 Entity tree button mockup 2016-01-17 23:06:32 +01:00
Jace 0d50ede6f5 Base work on reimplementing editor GUI 2016-01-17 07:34:20 +01:00
Jace 4786986abd Rendering pipeline fixes across the board and base work on refactored editor 2016-01-17 06:29:25 +01:00
Jace e34856468a Removed DrawScenePass, since it doesn't seem to be used 2016-01-17 06:27:45 +01:00
Jace e2357b8625 Fixed absolute position not taking scale into account 2016-01-17 06:23:13 +01:00
Jace 6ec2258758 Added UniformScale component which keeps an entity's scale at a uniform value relative to the screen. 2016-01-17 06:22:35 +01:00
Jace 9f447afbdb Added EntityWrapper::Valid and bool overload to be check if an entity is valid and still exists in the world more easily 2016-01-17 06:20:27 +01:00
Jace f281d220de Working Spawner, SpawnPoint, PlayerSpawn and Team components, along with their systems. 2016-01-17 01:00:48 +01:00
Jace 6385a98eca Added runtime type size check to ComponentWrapper to avoid corruption when types don't match 2016-01-17 00:59:26 +01:00
Jace d8a24bbfde Renamed all instances of "Property" to "Field" in ComponentWrapper to maintain consistent naming with ComponentInfo 2016-01-17 00:38:25 +01:00
Jace 9ec32464bc Added enum support to entity file format, see "Team" component for an example. Use ComponentInfo::Enum to convert enum string keys to its corresponding integer representation at runtime. 2016-01-16 23:12:24 +01:00
Jace f65ac65e30 Updated component defaults files to match component schema and made schema validation strict. 2016-01-16 17:03:57 +01:00
Jace b2213dbe9a Merge remote-tracking branch 'origin/master' into PlayerMovement
# Conflicts:
#	include/Engine/Collision/Collision.h
#	include/Engine/Collision/CollisionSystem.h
#	include/Engine/Collision/TriggerSystem.h
#	resources/Schema/Components.xsd
#	resources/Schema/Entities/CollisionTestLevel.xml
#	resources/Schema/Types/Entity.xsd
#	src/Engine/Collision/Collision.cpp
#	src/Game/Game.cpp
2016-01-15 20:28:43 +01:00
Jace bbabc84127 Fixed default values for CPlayerSpawn 2016-01-15 20:26:30 +01:00
Jace 8bd5a428b9 EntityFileParser now ignores component fields not present in component definition instead of crashing. 2016-01-15 20:25:48 +01:00
Jace db1b972cd1 Spawner, SpawnPoint and PlayerSpawn components, and base work on their systems 2016-01-15 18:32:47 +01:00
Jace 97e12ff550 Made EntityFileParser::MergeEntities return the base entity that was created, and also take an optional parent entity to create it under. 2016-01-15 18:31:32 +01:00
Jace 0469460029 Input binding format changed to allow custom values for bindings. Relevant code must clamp input values to prevent speedhaxx! 2016-01-15 16:32:04 +01:00
viktorljung 7faed50507 Merge remote-tracking branch 'origin/master' into TextRendering 2016-01-15 13:24:24 +01:00
viktorljung 6fbb962b5e Merge branch 'Rendering' into TextRendering
# Conflicts:
#	include/Engine/Rendering/RenderQueue.h
#	include/Engine/Rendering/RenderQueueFactory.h
#	include/Engine/Rendering/Renderer.h
#	include/Engine/Rendering/ShaderProgram.h
#	include/Game/Game.h
#	resources/Schema/Components.xsd
#	resources/Schema/Entities/Test.xml
#	resources/Schema/Types/Entity.xsd
#	src/Engine/Rendering/RenderQueueFactory.cpp
#	src/Engine/Rendering/Renderer.cpp
#	src/Game/Game.cpp
2016-01-15 13:23:42 +01:00
Jocke db62d767ac Fixed bug in Client::parseSnapshot(). 2016-01-15 12:06:20 +01:00
verysecrethero e7da11fda4 Removed OctTreeTests since its too annoying to update them each time RenderSystem gets updated 2016-01-15 11:31:21 +01:00
verysecrethero 8f257b9a58 Merge remote-tracking branch 'origin/master' into CapturePointTake
# Conflicts:
#	src/Game/Game.cpp
#	src/Tests/ResourceManagerTest.cpp
2016-01-15 11:24:20 +01:00
verysecrethero c8fe6853c0 Removed ShootEvent from CapturePoint 2016-01-15 11:17:22 +01:00
verysecrethero 76a8b43ca3 Fixed logic for CapturePointSystem 2016-01-15 11:04:00 +01:00
Jocke 0bf756dc08 Merge remote-tracking branch 'origin/master' into Networking 2016-01-15 10:22:21 +01:00
Jace 567173c565 Merge branch 'master' into PlayerMovement
# Conflicts:
#	src/Engine/Rendering/RenderSystem.cpp
#	src/Game/Game.cpp
2016-01-14 18:24:34 +01:00
Jace 5e721325a4 Merge fixes 2016-01-14 18:20:51 +01:00
Jocke 696f44a673 Added logic for mapping between ServerEntityIDs and LocalEntityIDs removed old code that wasn't used.
Added 1 map to Client and renamed m_ServerToClientMap to m_ServerIDToClientID.

// Good to know
To keep this structure please use insertIntoServerClientMaps() when adding items to them.
m_ServerIDToClientID and m_ClientIDToServerID maps between server EntityIDs and local EntityIDs.
To see if a local EntityID exist in m_ClientIDToServerID use clientServerMapsHasEntity(EntityID clientEntityID);
To see if server EntityID exist in m_ServerIDToClientID use serverClientMapsHasEntity(EntityID serverEntityID);
2016-01-14 17:11:54 +01:00
Jace 3a4f378ac5 Merge remote-tracking branch 'origin/master' into PlayerMovement
# Conflicts:
#	src/Game/Game.cpp
2016-01-14 17:07:39 +01:00
Jace 6ad1839def Initial work on PlayerMovementSystem 2016-01-14 17:03:48 +01:00
Jace 986af01091 Fixed editor component fields with the same name across components being treated as the same value 2016-01-14 17:02:13 +01:00
Jace 99406c32cf Better error handling for EntityFilePreprocessor 2016-01-14 17:01:39 +01:00
Jace d34470256b EntityWrapper to uniquely identify entities and make using them a little easier 2016-01-14 15:43:19 +01:00
Jace 28392def79 Made string passing in World a little more effective 2016-01-14 15:42:55 +01:00
Jace 71d936f8d1 Start of a movement system with collisions against AABBs 2016-01-14 14:54:12 +01:00
verysecrethero 5e9a3774ab CapturePointSystem code has been refactored and some branches "optimized" 2016-01-14 10:23:27 +01:00
Jocke db18a45368 We are now sending EPlayerDamage events.
Client now listens to EPlayerDamage events and send them to Server.
Server publishes EPlayerDamage events received from Client.
2016-01-14 10:16:11 +01:00
Jocke a060640da3 Removed unnecessary unnecessary if in Client::OnInputCommand.
Change name from Server::parseEvent to Server::parseOnInputCommand
2016-01-13 18:00:12 +01:00
verysecrethero b8a41b7c13 Updated some CapturePointLogic in CapturePointSystem: reset timer on capture, being able to take back the progress the other team did on your capturepoint. TODO: refactor! 2016-01-13 17:07:49 +01:00
verysecrethero 9533920684 Fixed a few CodeStandard mistakes. Added CapturePointSystem to CMakeLists.txt since branch is no longer based on ShootEvent-branch 2016-01-13 16:13:57 +01:00
Jocke f47f913bf5 Added logic for sending input from Client to Server.
Fixed so that snapshots set their parent correctly. Will get problems if we have more components
than unsigned int max size, but that was already a problem.
Client now maps Entitys received from server with local Entitys by mapping their EntityIDs.
2016-01-13 16:09:16 +01:00
verysecrethero ed5ac2e923 6 new tests for CapturePointSystem have been created!
TODO: refactor CapturePointSystem
2016-01-13 15:58:52 +01:00
verysecrethero 7a8604bf2b CapturePointSystem now tracks and verifies if a capturePoint can be taken over. Also the time is changed faster the more players stand on the capturepoint (number*dt). Also took care of the problem when both teams have the same contested capturepoint.
Added variable in the CapturePoint component:  CapturePointNumber. This is needed since we cant know what capturepoint is next to be taken over otherwise.
Updated the CapturePointTest according to current CapturePointSystem
TODO: try to refactor code in CapturePointSystem
2016-01-13 15:58:52 +01:00
verysecrethero 3a1056a2c3 2 new Events: ECaptured, EWin
Added new variable in CapturePoint: IsHomeCapturePointForTeam
CapturePointSystem updated so -5 = team 2 owns it, +5 = team 1 owns it. Its also looking for a winner each update
Updated Test. TODO: better Tests
2016-01-13 15:58:52 +01:00
verysecrethero 59be714fdc 1 Component added: CapturePoint
1 System added: CapturePointSystem
1 Test added: CapturePointTest
added 1 variable in PlayerComponent (TeamNumber)
added 2 variables in CapturePoint (CaptureTimer,OwnedBy)
CapturePointSystem is now handling 2 events: OnTriggerTouch,OnTriggerLeave
Added the CapturePointSystem to Game.cpp
2016-01-13 15:58:52 +01:00
verysecrethero 147b116f20 Fixed typo backslash instead of slash in various classes (the includes) 2016-01-13 15:58:52 +01:00
verysecrethero f0b425614d Simplified PlayerSystem branches a lot! Thanks William! 2016-01-13 15:58:52 +01:00
verysecrethero 4b672b11e7 EquippedItem,Ammo got changed to int instead of double. Loading entities from map the new way in Tests. ComponentWrapper:s Name is now Type 2016-01-13 15:58:52 +01:00
verysecrethero e865971fdd EShoot: changed to string weaponType to int currentlyEquippedItem
PlayerSystem.h: added HeldItem enum
PlayerSystem.cpp: simplified writing doubles, uses HeldItem enum
ShootEventTest.cpp: simplified writing doubles
2016-01-13 15:58:52 +01:00
verysecrethero 878c71b56a Changed the comparison method in PlayerSystem since its currently using doubles 2016-01-13 15:58:52 +01:00
verysecrethero ec4d5fbfa8 xml/xsd files changed type to double. fixed cooldownbug in PlayerSystem. Added 4 tests in ShootEventTest and generalized it a lot 2016-01-13 15:58:52 +01:00
verysecrethero 184af95507 New Event: EShoot. New Components: PrimaryItem,SecondaryItem. New Test: ShootEventTest. Added LeftMouseRelease->Shoot in PlayerSystem
TODO: generalize the test
2016-01-13 15:58:52 +01:00
verysecrethero e6527196ed Modified a few files according to the current CodeStandards 2016-01-13 15:50:30 +01:00
Jace d6ef527f25 Basic collisions using Octree. Seems buggy over octree boundaries. 2016-01-13 15:34:43 +01:00
verysecrethero c14f3789f7 PlayerSystem now counts down the CoolDownTimer on both HeldItems for the player. Updated ShootEventTest to verify this 2016-01-13 15:26:10 +01:00
Jace 8ed4ba1219 Added missing include for Octree 2016-01-13 12:16:35 +01:00
Jace 311475cbb6 Renamed all OctTree to Octree (More OCD) 2016-01-13 12:15:36 +01:00
Jace 8164a955d6 Renamed OctTree files to Octree (OCD to the max) 2016-01-13 12:15:09 +01:00
verysecrethero a20ca49d53 Fixed typo backslash instead of slash in various classes (the includes) 2016-01-12 10:46:34 +01:00
verysecrethero 774bb8ce56 Simplified PlayerSystem branches a lot! Thanks William! 2016-01-11 17:36:23 +01:00
verysecrethero 0cc58f088a EquippedItem,Ammo got changed to int instead of double. Loading entities from map the new way in Tests. ComponentWrapper:s Name is now Type 2016-01-11 17:15:49 +01:00
verysecrethero 00805d30d0 Merge remote-tracking branch 'origin/master' into ShootEvent 2016-01-11 17:06:48 +01:00
verysecrethero 2f6261dfbf EShoot: changed to string weaponType to int currentlyEquippedItem
PlayerSystem.h: added HeldItem enum
PlayerSystem.cpp: simplified writing doubles, uses HeldItem enum
ShootEventTest.cpp: simplified writing doubles
2016-01-11 15:49:33 +01:00
verysecrethero 2cd0e94a60 Changed the comparison method in PlayerSystem since its currently using doubles 2016-01-11 15:49:33 +01:00
verysecrethero 8f92de3683 xml/xsd files changed type to double. fixed cooldownbug in PlayerSystem. Added 4 tests in ShootEventTest and generalized it a lot 2016-01-11 15:49:33 +01:00
verysecrethero 31c1c0ac8d New Event: EShoot. New Components: PrimaryItem,SecondaryItem. New Test: ShootEventTest. Added LeftMouseRelease->Shoot in PlayerSystem
TODO: generalize the test
2016-01-11 15:49:33 +01:00
stiffly 7ae42a5bf7 Removed some comments. Basically did nothing 2016-01-06 11:39:32 +01:00
viktorljung 123c198e19 Text component added and Text render queue 2015-12-14 14:48:24 +01:00
viktorljung 9bd3da409d Added Font to ResourceManager 2015-12-11 16:53:51 +01:00
viktorljung a8a38716bd Text renderer up and working, needs more work to be compatible with the ResourceManager and the Entity Component system 2015-12-11 16:12:29 +01:00
viktorljung 8f007f6daf Added Freetype 2.62 config and option files 2015-12-11 11:26:41 +01:00
viktorljung 4c2ce3882e Added fonts folder and font 2015-12-11 11:07:22 +01:00
viktorljung 7b6902eafe Merge remote-tracking branch 'origin/master' into TextRendering 2015-12-11 10:55:10 +01:00
viktorljung 46854a63dd Text rendering includes 2015-12-11 10:54:52 +01:00
viktorljung dc66891d60 Added Freetype 2.62 2015-12-10 11:22:56 +01:00
243 changed files with 9387 additions and 3195 deletions
+1 -1
Submodule assets updated: a3c92ac876...e8174f630f
@@ -0,0 +1,24 @@
#ifndef CollidableOctreeSystem_h__
#define CollidableOctreeSystem_h__
#include "../Core/System.h"
#include "../Core/Octree.h"
#include "Collision.h"
class CollidableOctreeSystem : public ImpureSystem, public PureSystem
{
public:
CollidableOctreeSystem(World* world, EventBroker* eventBroker, Octree<AABB>* octree)
: System(world, eventBroker)
, PureSystem("Collidable")
, m_Octree(octree)
{ }
virtual void Update(double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override;
private:
Octree<AABB>* m_Octree;
};
#endif
+11 -3
View File
@@ -6,11 +6,14 @@
//or you will get "fatal error C1189: #error: gl.h included before glew.h"
#include <vector>
#include <boost/optional.hpp>
#include "../Core/Ray.h"
#include "../Core/AABB.h"
#include "../Rendering/RawModel.h"
#include "../Core/Transform.h"
#include "../Core/Entity.h"
#include "../Core/EntityWrapper.h"
class World;
struct ComponentWrapper;
@@ -43,6 +46,12 @@ bool RayVsModel(const Ray& ray,
float& outUCoord,
float& outVCoord);
bool AABBvsTriangles(const AABB& box,
const std::vector<RawModel::Vertex>& modelVertices,
const std::vector<unsigned int>& modelIndices,
const glm::mat4& modelMatrix,
glm::vec3& outResolutionVector);
//Return true if the boxes are intersecting.
bool AABBVsAABB(const AABB& a, const AABB& b);
//Return true if the boxes are intersecting.
@@ -50,9 +59,8 @@ bool AABBVsAABB(const AABB& a, const AABB& b);
bool AABBVsAABB(const AABB& a, const AABB& b, glm::vec3& minimumTranslation);
bool IsSameBoxProbably(const AABB& first, const AABB& second, const float epsilon = 0.0001f);
//Returns true if the entity has a boundingbox. Outputs the aabb in [outBox].
bool GetEntityBox(World* world, EntityID entity, AABB& outBox, bool forceBoxFromModel = false);
bool GetEntityBox(World* world, ComponentWrapper& AABBComponent, AABB& outBox);
// Calculates an absolute AABB from an entity AABB component
boost::optional<AABB> EntityAbsoluteAABB(EntityWrapper& entity);
}
+8 -3
View File
@@ -8,22 +8,27 @@
#include "../Core/System.h"
#include "../Core/EventBroker.h"
#include "../Core/EKeyUp.h"
#include "../Core/Octree.h"
class CollisionSystem : public PureSystem
{
public:
CollisionSystem(EventBroker* eventBroker)
: PureSystem(eventBroker, "AABB")
CollisionSystem(World* world, EventBroker* eventBroker, Octree<AABB>* octree)
: System(world, eventBroker)
, PureSystem("Collidable")
, m_Octree(octree)
, zPress(false)
{
//TODO: Debug stuff, remove later.
EVENT_SUBSCRIBE_MEMBER(m_EKeyUp, &CollisionSystem::OnKeyUp);
}
virtual void UpdateComponent(World* world, ComponentWrapper& cAABB, double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override;
private:
Octree<AABB>* m_Octree;
bool zPress;
EventRelay<CollisionSystem, Events::KeyUp> m_EKeyUp;
bool OnKeyUp(const Events::KeyUp &event);
};
+20 -4
View File
@@ -6,6 +6,7 @@
#include "../Core/System.h"
#include "../Core/EventBroker.h"
#include "../Core/Octree.h"
#include "ETrigger.h"
class AABB;
@@ -13,16 +14,31 @@ class AABB;
class TriggerSystem : public PureSystem
{
public:
TriggerSystem(EventBroker* eventBroker)
: PureSystem(eventBroker, "Trigger")
{}
TriggerSystem(World* world, EventBroker* eventBroker, Octree<AABB>* octree)
: System(world, eventBroker)
, PureSystem("Trigger")
, m_Octree(octree)
{
EVENT_SUBSCRIBE_MEMBER(m_ETouch, &TriggerSystem::OnTouch);
EVENT_SUBSCRIBE_MEMBER(m_EEnter, &TriggerSystem::OnEnter);
EVENT_SUBSCRIBE_MEMBER(m_ELeave, &TriggerSystem::OnLeave);
}
virtual void UpdateComponent(World* world, ComponentWrapper& collision, double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override;
private:
Octree<AABB>* m_Octree;
std::unordered_map<EntityID, std::unordered_set<EntityID>> m_EntitiesTouchingTrigger;
std::unordered_map<EntityID, std::unordered_set<EntityID>> m_EntitiesCompletelyInTrigger;
//TODO: Only exists for debug purposes, remove later.
EventRelay<TriggerSystem, Events::TriggerEnter> m_EEnter;
bool OnEnter(const Events::TriggerEnter &event);
EventRelay<TriggerSystem, Events::TriggerTouch> m_ETouch;
bool OnTouch(const Events::TriggerTouch &event);
EventRelay<TriggerSystem, Events::TriggerLeave> m_ELeave;
bool OnLeave(const Events::TriggerLeave &event);
//True if leave event was thrown.
bool throwLeaveIfWasInTrigger(std::unordered_set<EntityID>& triggerSet, EntityID pId, EntityID tId);
template<typename Event>
+2
View File
@@ -1,8 +1,10 @@
#include <memory>
#include <string>
#include <sstream>
#include <vector>
#include <map>
#include <unordered_map>
#include <algorithm>
#include "Core/Util/Logging.h"
#include "Core/Util/IfDebug.h"
+3 -3
View File
@@ -11,18 +11,18 @@ public:
AABB(const glm::vec3& minPos, const glm::vec3& maxPos);
AABB(const glm::vec4& minPos, const glm::vec4& maxPos);
//No checks are made. Size must consist of non-negative numbers.
virtual void CreateFromCenter(const glm::vec3& center, const glm::vec3& size);
static AABB FromOriginSize(const glm::vec3& origin, const glm::vec3& size);
virtual ~AABB();
const glm::vec3& MinCorner() const { return m_MinCorner; }
const glm::vec3& MaxCorner() const { return m_MaxCorner; }
const glm::vec3& Center() const { return m_Center; }
const glm::vec3& Origin() const { return m_Origin; }
const glm::vec3 Size() const { return 2.0f * m_HalfSize; }
const glm::vec3& HalfSize() const { return m_HalfSize; }
private:
glm::vec3 m_MinCorner;
glm::vec3 m_MaxCorner;
glm::vec3 m_Center;
glm::vec3 m_Origin;
glm::vec3 m_HalfSize;
};
+6 -2
View File
@@ -5,11 +5,14 @@
struct ComponentInfo
{
typedef int EnumType;
struct Meta_t
{
std::string Annotation;
unsigned int Allocation = 0;
unsigned int Stride = 0;
std::map<std::string, std::string> FieldAnnotations;
std::map<std::string, std::map<std::string, EnumType>> FieldEnumDefinitions;
};
struct Field_t
@@ -23,8 +26,9 @@ struct ComponentInfo
std::string Name;
std::unordered_map<std::string, Field_t> Fields;
std::vector<std::string> FieldsInOrder;
Meta_t Meta;
unsigned int Stride = 0;
std::shared_ptr<char> Defaults = nullptr;
std::shared_ptr<Meta_t> Meta = nullptr;
};
template<>
+2 -1
View File
@@ -43,7 +43,7 @@ public:
ComponentPool(const ::ComponentInfo& ci)
: m_ComponentInfo(ci)
, m_Pool(ci.Meta.Allocation, sizeof(EntityID) + ci.Meta.Stride)
, m_Pool(ci.Meta->Allocation, sizeof(EntityID) + ci.Stride)
{ }
ComponentPool(const ComponentPool& other) = delete;
ComponentPool(const ComponentPool&& other) = delete;
@@ -61,6 +61,7 @@ public:
iterator begin() const;
iterator end() const;
size_t size() const;
//Dumps information about what the pool memory looks like right now
//into an output stream (e.g. file/std::cout, anything that has an operator<<)
+32 -19
View File
@@ -18,22 +18,32 @@ struct ComponentWrapper
const ::EntityID EntityID;
char* Data;
template <typename T>
T& Property(std::string name)
ComponentInfo::EnumType Enum(const char* fieldName, const char* enumKey)
{
unsigned int offset = Info.Fields.at(name).Offset;
return *reinterpret_cast<T*>(&Data[offset]);
return Info.Meta->FieldEnumDefinitions.at(fieldName).at(enumKey);
}
template <typename T>
void SetProperty(std::string name, const T value) { Property<T>(name) = value; }
T& Field(std::string name)
{
const ComponentInfo::Field_t& field = Info.Fields.at(name);
if (sizeof(T) > field.Stride) {
std::stringstream message;
message << "Type size of \"" << typeid(T).name() << "\" doesn't match size of component field \"" << Info.Name << "." << name << "\"!";
throw new std::runtime_error(message.str().c_str());
}
return *reinterpret_cast<T*>(&Data[field.Offset]);
}
template <typename T>
void SetField(std::string name, const T value) { Field<T>(name) = value; }
//template <typename T>
//void SetProperty(std::string name, T& value) { Property<T>(name) = value; }
//void SetField(std::string name, T& value) { Field<T>(name) = value; }
// Specialization for string literals
template <std::size_t N>
void SetProperty(std::string name, const char(&value)[N]) { Property<std::string>(name) = std::string(value); }
void SetField(std::string name, const char(&value)[N]) { Field<std::string>(name) = std::string(value); }
struct SubscriptProxy
{
friend struct ComponentWrapper;
@@ -47,18 +57,21 @@ struct ComponentWrapper
std::string m_PropertyName;
public:
template <typename T>
operator T&() { return m_Component->Property<T>(m_PropertyName); }
// Return the integer value of an enum type key for this field
ComponentInfo::EnumType Enum(const char* enumKey) { return m_Component->Enum(m_PropertyName.c_str(), enumKey); }
template <typename T>
void operator=(const T val) { m_Component->SetProperty<T>(m_PropertyName, val); }
operator T&() { return m_Component->Field<T>(m_PropertyName); }
template <typename T>
void operator=(const T val) { m_Component->SetField<T>(m_PropertyName, val); }
// TODO: Pass by reference and rvalue (universal reference?)
//template <typename T>
//void operator=(T& val) { m_Component->SetProperty<T>(m_PropertyName, val); }
//void operator=(T& val) { m_Component->SetField<T>(m_PropertyName, val); }
// Specialization for string literals
template<std::size_t N>
void operator=(const char(&val)[N]) { m_Component->SetProperty<N>(m_PropertyName, val); }
template <std::size_t N>
void operator=(const char(&val)[N]) { m_Component->SetField<N>(m_PropertyName, val); }
};
SubscriptProxy operator[](std::string propertyName) { return SubscriptProxy(this, propertyName); }
};
@@ -71,22 +84,22 @@ public:
ComponentWrapperFactory(std::string componentTypeName, std::size_t allocation = 0)
{
m_ComponentInfo.Name = componentTypeName;
m_ComponentInfo.Meta.Allocation = allocation;
m_ComponentInfo.Meta->Allocation = allocation;
}
template <typename T>
void AddProperty(std::string fieldName, T defaultValue)
{
m_DefaultValues.push_back(defaultValue);
m_ComponentInfo.Fields[fieldName].Name = typeid(T).name();
m_ComponentInfo.Fields[fieldName].Offset = m_ComponentInfo.Meta.Stride;
m_ComponentInfo.Fields[fieldName].Type = typeid(T).name();
m_ComponentInfo.Fields[fieldName].Offset = m_ComponentInfo.Stride;
m_ComponentInfo.Fields[fieldName].Stride = sizeof(T);
m_ComponentInfo.Meta.Stride += sizeof(T);
m_ComponentInfo.Stride += sizeof(T);
}
ComponentInfo& Finalize()
{
m_ComponentInfo.Defaults = std::shared_ptr<char>(new char[m_ComponentInfo.Meta.Stride]);
m_ComponentInfo.Defaults = std::shared_ptr<char>(new char[m_ComponentInfo.Stride]);
std::size_t offset = 0;
for (auto& val : m_DefaultValues) {
memcpy(m_ComponentInfo.Defaults.get() + offset, val.Data.get(), val.Size);
+20
View File
@@ -0,0 +1,20 @@
#ifndef ECaptured_h__
#define ECaptured_h__
#include "EventBroker.h"
#include "../Core/Entity.h"
#include "Engine/GLM.h"
namespace Events
{
//triggers when a capturePoint has been taken over
struct Captured : Event
{
int TeamNumberThatCapturedCapturePoint;
EntityID CapturePointID;
};
}
#endif
+20
View File
@@ -0,0 +1,20 @@
#ifndef EComponentAttached_h__
#define EComponentAttached_h__
#include "EventBroker.h"
#include "World.h"
#include "Entity.h"
#include "ComponentWrapper.h"
namespace Events
{
struct ComponentAttached : Event
{
EntityWrapper Entity;
ComponentWrapper Component;
};
}
#endif
+3
View File
@@ -11,6 +11,9 @@ struct KeyDown : Event
{
/** GLFW key code */
int KeyCode;
bool ModCtrl;
bool ModAlt;
bool ModShift;
};
}
+3
View File
@@ -11,6 +11,9 @@ struct KeyUp : Event
{
/** GLFW key code */
int KeyCode;
bool ModCtrl;
bool ModAlt;
bool ModShift;
};
}
+22
View File
@@ -0,0 +1,22 @@
#ifndef EPause_h__
#define EPause_h__
#include "EventBroker.h"
#include "World.h"
namespace Events
{
struct Pause : Event
{
::World* World;
};
struct Resume : Event
{
::World* World;
};
}
#endif
-2
View File
@@ -11,8 +11,6 @@ struct PlayerDamage : Event
{
double DamageAmount;
EntityID PlayerDamagedID;
//optional TypeOfDamage
std::string TypeOfDamage;
};
}
+19
View File
@@ -0,0 +1,19 @@
#ifndef EPlayerSpawned_h__
#define EPlayerSpawned_h__
#include "Core/Event.h"
#include "Core/EntityWrapper.h"
namespace Events
{
struct PlayerSpawned : Event
{
int PlayerID;
EntityWrapper Player;
EntityWrapper Spawner;
};
}
#endif
+19
View File
@@ -0,0 +1,19 @@
#ifndef EShoot_h__
#define EShoot_h__
#include "EventBroker.h"
#include "../Core/Entity.h"
#include "Engine/GLM.h"
namespace Events
{
struct Shoot : Event
{
//ID for who made the shot
EntityID shooter;
};
}
#endif
+20
View File
@@ -0,0 +1,20 @@
#ifndef EWin_h__
#define EWin_h__
#include "EventBroker.h"
#include "../Core/Entity.h"
#include "Engine/GLM.h"
namespace Events
{
//triggers when a team has captured all capturePoints
struct Win : Event
{
//can be 0 = none, 1,2
int TeamThatWon;
};
}
#endif
+1
View File
@@ -4,4 +4,5 @@
typedef unsigned int EntityID;
const static unsigned int EntityID_Invalid = -1;
#endif
+8 -8
View File
@@ -285,7 +285,7 @@ private:
XSValue::Status status;
XSValue* val = XSValue::getActualValue(child->getNodeValue(), XSValue::dt_integer, status);
compInfo.Meta.Allocation += val->fData.fValue.f_int;
compInfo.Meta->Allocation += val->fData.fValue.f_int;
}
// Save documentation string
@@ -293,11 +293,11 @@ private:
if (documentationTags->getLength() != 0) {
auto child = documentationTags->item(0)->getFirstChild();
if (child != nullptr) {
compInfo.Meta.Annotation = XSTR(child->getNodeValue());
compInfo.Meta->Annotation = XSTR(child->getNodeValue());
}
}
// TODO: Parse annotation string XML
// compInfo.Meta.Allocation = ...
// compInfo.Meta->Allocation = ...
} else {
std::cout << "Warning: Component is missing an annotation!" << std::endl;
}
@@ -344,7 +344,7 @@ private:
fieldOffset += getTypeStride(type);
}
compInfo.Meta.Stride = fieldOffset;
compInfo.Stride = fieldOffset;
m_ComponentInfo[compInfo.Name] = compInfo;
}
}
@@ -367,14 +367,14 @@ private:
std::string componentName = XSTR(component->getLocalName());
auto& compInfo = m_ComponentInfo.at(componentName);
compInfo.Meta.Allocation += 1;
compInfo.Meta->Allocation += 1;
}
std::cout << "COMPONENT INFO" << std::endl;
for (auto& pair : m_ComponentInfo) {
ComponentInfo& ci = pair.second;
std::cout << "Component: " << ci.Name << " (" << ci.Meta.Annotation << ")" << std::endl;
std::cout << " Allocation: " << ci.Meta.Allocation << std::endl;
std::cout << "Component: " << ci.Name << " (" << ci.Meta->Annotation << ")" << std::endl;
std::cout << " Allocation: " << ci.Meta->Allocation << std::endl;
std::cout << " Fields:" << std::endl;
// Calculate component size
@@ -393,7 +393,7 @@ private:
cs.ComponentName = ci.Name;
cs.Stride = stride;
cs.Info = ci;
cs.Data = new char[stride*ci.Meta.Allocation];
cs.Data = new char[stride*ci.Meta->Allocation];
m_ComponentStore[cs.ComponentName] = cs;
}
}
+18 -147
View File
@@ -73,88 +73,15 @@ public:
ComponentField
};
EntityFileSAXHandler(const EntityFileHandler* handler, xercesc::SAX2XMLReader* reader)
: m_Handler(handler)
, m_Reader(reader)
{
// 0 is imaginary world entity
m_EntityStack.push(0);
m_StateStack.push(State::Unknown);
}
EntityFileSAXHandler(const EntityFileHandler* handler, xercesc::SAX2XMLReader* reader);
void startElement(const XMLCh* const _uri, const XMLCh* const _localName, const XMLCh* const _qname, const xercesc::Attributes& attrs) override
{
std::string name = XS::ToString(_localName);
void startElement(const XMLCh* const _uri, const XMLCh* const _localName, const XMLCh* const _qname, const xercesc::Attributes& attrs) override;
void characters(const XMLCh* const chars, const XMLSize_t length) override;
void endElement(const XMLCh* const _uri, const XMLCh* const _localName, const XMLCh* const _qname) override;
if (m_StateStack.top() == State::Unknown || m_StateStack.top() == State::Entity) {
if (name == "Entity") {
m_StateStack.push(State::Entity);
onStartEntity(attrs);
return;
}
if (name == "EntityRef") {
onStartEntityRef(attrs);
return;
}
}
std::string uri = XS::ToString(_uri);
if (m_StateStack.top() == State::Entity) {
if (uri == "components") {
m_StateStack.push(State::Component);
onStartComponent(name);
return;
}
}
if (m_StateStack.top() == State::Component) {
m_StateStack.push(State::ComponentField);
onStartComponentField(name, attrs);
return;
}
}
void characters(const XMLCh* const chars, const XMLSize_t length) override
{
if (m_StateStack.top() == State::ComponentField) {
char* transcoded = xercesc::XMLString::transcode(chars);
onFieldData(transcoded);
}
}
void endElement(const XMLCh* const _uri, const XMLCh* const _localName, const XMLCh* const _qname) override
{
std::string name = XS::ToString(_localName);
if (m_StateStack.top() == State::Entity) {
if (name == "Entity") {
m_StateStack.pop();
onEndEntity();
return;
}
}
std::string uri = XS::ToString(_uri);
if (m_StateStack.top() == State::Component) {
//if (uri == "components") {
m_StateStack.pop();
onEndComponent(name);
return;
//}
}
if (m_StateStack.top() == State::ComponentField) {
m_StateStack.pop();
onEndComponentField(name);
return;
}
}
void fatalError(const xercesc::SAXParseException& e)
{
XS::ToString s(e.getMessage());
LOG_ERROR("SAXParseException: %s", ((std::string)s).c_str());
//throw e;
}
void warning(const xercesc::SAXParseException& e);
void error(const xercesc::SAXParseException& e);
void fatalError(const xercesc::SAXParseException& e);
private:
const EntityFileHandler* m_Handler;
@@ -168,73 +95,14 @@ private:
std::string m_CurrentField;
std::map<std::string, std::string> m_CurrentAttributes;
void onStartEntity(const xercesc::Attributes& attrs)
{
EntityID parent = m_EntityStack.top();
if (m_Handler->m_OnStartEntityCallback) {
std::string name;
auto xName = attrs.getValue(XS::ToXMLCh("name"));
if (xName != nullptr) {
name = XS::ToString(xName);
}
m_Handler->m_OnStartEntityCallback(m_NextEntityID, parent, name);
}
m_EntityStack.push(m_NextEntityID);
m_NextEntityID++;
}
void onEndEntity()
{
m_EntityStack.pop();
}
void onStartEntityRef(const xercesc::Attributes& attrs)
{
std::string path = XS::ToString(attrs.getValue(XS::ToXMLCh("file")));
xercesc::SAX2XMLReader* parser = xercesc::XMLReaderFactory::createXMLReader();
parser->setContentHandler(this);
parser->setErrorHandler(this);
parser->parse(path.c_str());
delete parser;
}
void onStartComponent(const std::string& name)
{
//LOG_DEBUG(" Component: %s", name.c_str());
m_CurrentComponent = name;
if (m_Handler->m_OnStartComponentCallback) {
m_Handler->m_OnStartComponentCallback(m_EntityStack.top(), name);
}
}
void onEndComponent(const std::string& name) { }
void onStartComponentField(const std::string& field, const xercesc::Attributes& attrs)
{
//LOG_DEBUG(" Field: %s", field.c_str());
m_CurrentField = field;
m_CurrentAttributes.clear();
for (int i = 0; i < attrs.getLength(); i++) {
auto name = attrs.getQName(i);
auto value = attrs.getValue(name);
//LOG_DEBUG(" %s = %s", (char*)XS::ToString(name), (char*)XS::ToString(value));
m_CurrentAttributes[XS::ToString(name).operator std::string()] = XS::ToString(value).operator std::string();
}
if (m_Handler->m_OnStartFieldCallback) {
m_Handler->m_OnStartFieldCallback(m_EntityStack.top(), m_CurrentComponent, field, m_CurrentAttributes);
}
}
void onEndComponentField(const std::string& field) { }
void onFieldData(char* data)
{
//LOG_DEBUG(" Data: %s", data);
if (m_Handler->m_OnStartFieldDataCallback) {
m_Handler->m_OnStartFieldDataCallback(m_EntityStack.top(), m_CurrentComponent, m_CurrentField, data);
}
xercesc::XMLString::release(&data);
}
void onStartEntity(const xercesc::Attributes& attrs);
void onEndEntity();
void onStartEntityRef(const xercesc::Attributes& attrs);
void onStartComponent(const std::string& name);
void onEndComponent(const std::string& name);
void onStartComponentField(const std::string& field, const xercesc::Attributes& attrs);
void onEndComponentField(const std::string& field);
void onFieldData(char* data);
};
class EntityFileXMLErrorHandler : public xercesc::ErrorHandler
@@ -269,6 +137,7 @@ private:
class EntityFile : public Resource
{
friend class ResourceManager;
friend class EntityFileSAXHandler;
private:
EntityFile(boost::filesystem::path path);
~EntityFile();
@@ -288,6 +157,8 @@ private:
xercesc::SAX2XMLReader* m_SAX2XMLReader;
//std::map<std::string, ::ComponentInfo> m_ComponentInfo;
//std::vector<std::string> m_EntityReferences;
static void setReaderFeatures(xercesc::SAX2XMLReader* reader);
};
#endif
+2 -1
View File
@@ -9,12 +9,13 @@ class EntityFileParser
public:
EntityFileParser(const EntityFile* entityFile);
void MergeEntities(World* world);
EntityID MergeEntities(World* world, EntityID baseParent = EntityID_Invalid);
private:
const EntityFile* m_EntityFile;
EntityFileHandler m_Handler;
World* m_World = nullptr;
EntityID m_FirstEntity = EntityID_Invalid;
// Maps EntityIDs local to the file to real IDs in the world after they've been
// created in order to resolve parent-child relationships.
std::map<EntityID, EntityID> m_EntityIDMapper;
@@ -5,6 +5,7 @@
#include <xercesc/framework/psvi/XSComplexTypeDefinition.hpp>
#include <xercesc/framework/psvi/XSParticle.hpp>
#include <xercesc/framework/psvi/XSModelGroup.hpp>
#include <xercesc/framework/psvi/XSModelGroupDefinition.hpp>
#include <xercesc/framework/psvi/XSAnnotation.hpp>
#include <xercesc/framework/psvi/XSValue.hpp>
#include <xercesc/framework/MemBufFormatTarget.hpp>
@@ -31,6 +32,7 @@ private:
void onStartComponent(EntityID entity, std::string type);
void parseComponentInfo();
void parseDefaults();
std::string parseAnnotationXML(const XMLCh* xml);
};
#endif
+53
View File
@@ -0,0 +1,53 @@
#ifndef EntityWrapper_h__
#define EntityWrapper_h__
#include <boost/optional.hpp>
#include <boost/functional/hash.hpp>
#include "ComponentWrapper.h"
class World;
struct EntityWrapper
{
EntityWrapper()
: World(nullptr)
, ID(EntityID_Invalid)
{ }
EntityWrapper(::World* world, EntityID id)
: World(world)
, ID(id)
{ }
::World* World;
EntityID ID;
static const EntityWrapper Invalid;
bool HasComponent(const std::string& componentName);
EntityWrapper Parent();
EntityWrapper FirstChildByName(const std::string& name);
bool IsChildOf(EntityWrapper potentialParent);
bool Valid();
ComponentWrapper operator[](const char* componentName);
bool operator==(const EntityWrapper& e) const;
bool operator!=(const EntityWrapper& e) const;
explicit operator EntityID() const;
operator bool();
};
namespace std
{
template<> struct hash<EntityWrapper>
{
std::size_t operator()(const EntityWrapper& e) const
{
std::size_t seed = 0;
boost::hash_combine(seed, e.World);
boost::hash_combine(seed, e.ID);
return seed;
}
};
}
#endif
+2 -2
View File
@@ -43,7 +43,7 @@ template <typename ContextType, typename EventType>
class EventRelay : public BaseEventRelay
{
public:
typedef std::function<bool(const EventType&)> CallbackType;
typedef std::function<bool(EventType&)> CallbackType;
EventRelay()
: m_Callback(nullptr)
@@ -65,7 +65,7 @@ template <typename ContextType, typename EventType>
bool EventRelay<ContextType, EventType>::Receive(const std::shared_ptr<Event> event)
{
if (m_Callback != nullptr) {
return m_Callback(*static_cast<const EventType*>(event.get()));
return m_Callback(*static_cast<EventType*>(event.get()));
} else {
return false;
}
-104
View File
@@ -1,104 +0,0 @@
#ifndef OctTree_h__
#define OctTree_h__
#include "Core/AABB.h"
class Ray;
class OctTree
{
public:
struct Output
{
float CollideDistance;
};
OctTree();
~OctTree();
//For the root OctTree, [octTreeBounds] should be a box containing the entire level.
OctTree(const AABB& octTreeBounds, int subDivisions);
//We cannot copy the OctTree as of now, because of the recursive dynamic allocation.
//Define these if the OctTree suddenly needs to be copied, think of the children OctChild* ptrs.
OctTree(const OctTree& other) = delete;
OctTree(const OctTree&& other) = delete;
OctTree& operator= (const OctTree& other) = delete;
//Add a dynamic object (one that moves around) into the tree.
void AddDynamicObject(const AABB& box);
//Add a static object (that does not move) into the tree.
void AddStaticObject(const AABB& box);
//Get the boxes that are in the same area as the input [box], the boxes are put in [outBoxes].
void BoxesInSameRegion(const AABB& box, std::vector<AABB>& outBoxes);
//Empty the tree of all objects, static and dynamic.
void ClearObjects();
//Empty the tree of all dynamic objects. Static objects remain in the tree.
void ClearDynamicObjects();
//Returns true if the ray collides with something in the tree. Result is written to [data].
bool RayCollides(const Ray& ray, Output& data);
//Returns true if the box collides with something in the tree.
//On collision with a box, that box is written to [outBoxIntersected].
//Note: More efficient than calling BoxesInSameRegion from outside and testing there.
bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected);
private:
struct OctChild; //Fwd declaration;
struct ContainedObject
{
ContainedObject()
: Box(AABB())
, Checked(false)
{}
ContainedObject(AABB box)
: Box(box)
, Checked(false)
{}
AABB Box;
bool Checked;
};
OctChild* m_Root;
std::vector<ContainedObject> m_StaticObjects;
std::vector<ContainedObject> m_DynamicObjects;
bool m_UpdatedOnce;
unsigned int m_BoxID;
glm::vec3 m_PrevPos;
glm::quat m_PrevOri;
void falsifyObjectChecks();
struct OctChild
{
~OctChild();
OctChild(const AABB& octTreeBounds,
int subDivisions,
std::vector<OctTree::ContainedObject>& staticObjects,
std::vector<OctTree::ContainedObject>& dynamicObjects);
OctChild(const OctChild& other) = delete;
OctChild(const OctChild&& other) = delete;
OctChild& operator= (const OctChild& other) = delete;
void AddDynamicObject(const AABB& box);
void AddStaticObject(const AABB& box);
void BoxesInSameRegion(const AABB& box, std::vector<AABB>& outBoxes) const;
void ClearObjects();
void ClearDynamicObjects();
bool RayCollides(const Ray& ray, Output& data) const;
bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const;
OctChild* m_Children[8];
//Indices into the lists in OctTree.
std::vector<int> m_StaticObjIndices;
std::vector<int> m_DynamicObjIndices;
AABB m_Box;
//Reference to the lists in OctTree.
std::vector<OctTree::ContainedObject>& m_StaticObjectsRef;
std::vector<OctTree::ContainedObject>& m_DynamicObjectsRef;
inline bool hasChildren() const;
int childIndexContainingPoint(const glm::vec3& point) const;
std::vector<int> childIndicesContainingBox(const AABB& box) const;
};
};
#endif
+233
View File
@@ -0,0 +1,233 @@
#ifndef Octree_h__
#define Octree_h__
#include <type_traits>
#include "../Common.h"
#include "AABB.h"
//Fwd declarations.
class Ray;
namespace OctSpace
{
struct Output;
struct ContainedObject;
struct Child;
}
//T needs to be AABB, or inherit from AABB.
//T also needs to have a default constructor.
template<typename T>
class Octree
{
public:
Octree() = delete;
~Octree();
//For the root Octree, [octreeBounds] should be a box containing the entire level.
Octree(const AABB& octreeBounds, int subDivisions);
//We cannot copy the Octree as of now, because of the recursive dynamic allocation.
//Define these if the Octree suddenly needs to be copied, think of the children Child* ptrs.
Octree(const Octree& other) = delete;
Octree(const Octree&& other) = delete;
Octree& operator= (const Octree& other) = delete;
//Add a dynamic object (one that moves around) into the tree.
void AddDynamicObject(const T& object);
//Add a static object (that does not move) into the tree.
void AddStaticObject(const T& object);
//Get the objects that are in the same area as the input [box], the objects are put in [outObjects].
//The type Box must be AABB, or inherit from AABB.
template<typename Box>
void ObjectsInSameRegion(const Box& box, std::vector<T>& outObjects);
//Empty the tree of all objects, static and dynamic.
void ClearObjects();
//Empty the tree of all dynamic objects. Static objects remain in the tree.
void ClearDynamicObjects();
//Returns true if the ray collides with something in the tree. Result is written to [data].
bool RayCollides(const Ray& ray, OctSpace::Output& data);
//Returns true if the box collides with something in the tree.
//On collision with a box, that box is written to [outBoxIntersected].
//Note: More efficient than calling ObjectsInSameRegion from outside and testing there.
bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected);
private:
OctSpace::Child* m_Root;
std::vector<OctSpace::ContainedObject> m_StaticObjects;
std::vector<OctSpace::ContainedObject> m_DynamicObjects;
void falsifyObjectChecks();
};
namespace OctSpace
{
struct Output
{
float CollideDistance;
};
struct ContainedObject
{
ContainedObject()
: Box(nullptr)
, Checked(false)
{}
template<typename BoxlikeObject>
ContainedObject(const BoxlikeObject& box)
: Box(new BoxlikeObject(box))
, Checked(false)
{}
std::unique_ptr<AABB> Box;
bool Checked;
};
struct Child
{
~Child();
Child(const AABB& octTreeBounds,
int subDivisions,
std::vector<ContainedObject>& staticObjects,
std::vector<ContainedObject>& dynamicObjects);
Child(const Child& other) = delete;
Child(const Child&& other) = delete;
Child& operator= (const Child& other) = delete;
void AddDynamicObject(const AABB& box);
void AddStaticObject(const AABB& box);
template<typename T, typename Box>
void ObjectsInSameRegion(const Box& box, std::vector<T>& outObjects) const;
void ClearObjects();
void ClearDynamicObjects();
bool RayCollides(const Ray& ray, Output& data) const;
bool BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected) const;
Child* m_Children[8];
//Indices into the lists in Octree.
std::vector<int> m_StaticObjIndices;
std::vector<int> m_DynamicObjIndices;
AABB m_Box;
//Reference to the lists in Octree.
std::vector<ContainedObject>& m_StaticObjectsRef;
std::vector<ContainedObject>& m_DynamicObjectsRef;
bool hasChildren() const;
int childIndexContainingPoint(const glm::vec3& point) const;
std::vector<int> childIndicesContainingBox(const AABB& box) const;
};
}
template<typename T>
Octree<T>::Octree(const AABB& octTreeBounds, int subDivisions)
: m_Root(new OctSpace::Child(octTreeBounds, subDivisions, m_StaticObjects, m_DynamicObjects))
{
static_assert(std::is_base_of<AABB, T>::value, "template argument type T in Octree must be a subclass of AABB.");
}
template<typename T>
Octree<T>::~Octree()
{
delete m_Root;
}
template<typename T>
void Octree<T>::AddDynamicObject(const T& object)
{
m_Root->AddDynamicObject(object);
m_DynamicObjects.emplace_back(object);
}
template<typename T>
void Octree<T>::AddStaticObject(const T& object)
{
m_Root->AddStaticObject(object);
m_StaticObjects.emplace_back(object);
}
template<typename T>
template<typename Box>
void Octree<T>::ObjectsInSameRegion(const Box& box, std::vector<T>& outObjects)
{
static_assert(std::is_base_of<AABB, Box>::value, "template argument type Box in Octree<T>::ObjectsInSameRegion must be a subclass of AABB.");
falsifyObjectChecks();
m_Root->ObjectsInSameRegion(box, outObjects);
}
template<typename T>
void Octree<T>::ClearObjects()
{
m_StaticObjects.clear();
m_DynamicObjects.clear();
m_Root->ClearObjects();
}
template<typename T>
void Octree<T>::ClearDynamicObjects()
{
m_DynamicObjects.clear();
m_Root->ClearDynamicObjects();
}
template<typename T>
bool Octree<T>::RayCollides(const Ray& ray, OctSpace::Output& data)
{
falsifyObjectChecks();
data.CollideDistance = -1;
return m_Root->RayCollides(ray, data);
}
template<typename T>
bool Octree<T>::BoxCollides(const AABB& boxToTest, AABB& outBoxIntersected)
{
falsifyObjectChecks();
return m_Root->BoxCollides(boxToTest, outBoxIntersected);
}
template<typename T>
void Octree<T>::falsifyObjectChecks()
{
for (auto& obj : m_StaticObjects) {
obj.Checked = false;
}
for (auto& obj : m_DynamicObjects) {
obj.Checked = false;
}
}
template<typename T, typename Box>
void OctSpace::Child::ObjectsInSameRegion(const Box& box, std::vector<T>& outObjects) const
{
if (hasChildren()) {
for (auto i : childIndicesContainingBox(box)) {
m_Children[i]->ObjectsInSameRegion(box, outObjects);
}
} else {
size_t startIndex = outObjects.size();
int numDuplicates = 0;
outObjects.resize(outObjects.size() + m_StaticObjIndices.size() + m_DynamicObjIndices.size());
for (size_t i = 0; i < m_StaticObjIndices.size(); ++i) {
ContainedObject& obj = m_StaticObjectsRef[m_StaticObjIndices[i]];
if (obj.Checked) {
++numDuplicates;
} else {
obj.Checked = true;
outObjects[startIndex + i - numDuplicates] = *static_cast<T*>(obj.Box.get());
}
}
for (size_t i = 0; i < m_DynamicObjIndices.size(); ++i) {
ContainedObject& obj = m_DynamicObjectsRef[m_DynamicObjIndices[i]];
if (obj.Checked) {
++numDuplicates;
} else {
obj.Checked = true;
outObjects[startIndex + i - numDuplicates] = *static_cast<T*>(obj.Box.get());
}
}
for (size_t i = 0; i < numDuplicates; ++i) {
outObjects.pop_back();
}
}
}
#endif
+13 -12
View File
@@ -3,6 +3,7 @@
#include "EventBroker.h"
#include "World.h"
#include "EntityWrapper.h"
#include "ComponentWrapper.h"
class System
@@ -10,41 +11,41 @@ class System
friend class SystemPipeline;
protected:
System(EventBroker* eventBroker)
: m_EventBroker(eventBroker)
System(World* world, EventBroker) { }
System(World* world, EventBroker* eventBroker)
: m_World(world)
, m_EventBroker(eventBroker)
{ }
virtual ~System() = default;
World* m_World;
EventBroker* m_EventBroker;
};
class PureSystem : public System
class PureSystem : public virtual System
{
friend class SystemPipeline;
protected:
PureSystem(EventBroker* eventBroker, std::string componentType)
: System(eventBroker)
, m_ComponentType(componentType)
PureSystem(std::string componentType)
: m_ComponentType(componentType)
{ }
virtual ~PureSystem() = default;
const std::string m_ComponentType;
virtual void UpdateComponent(World* world, ComponentWrapper& component, double dt) = 0;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cComponent, double dt) = 0;
};
class ImpureSystem : public System
class ImpureSystem : public virtual System
{
friend class SystemPipeline;
protected:
ImpureSystem(EventBroker* eventBroker)
: System(eventBroker)
{ }
ImpureSystem() = default;
virtual ~ImpureSystem() = default;
virtual void Update(World* world, double dt) = 0;
virtual void Update(double dt) = 0;
};
#endif
+42 -14
View File
@@ -5,13 +5,19 @@
#include "EventBroker.h"
#include "System.h"
#include "World.h"
#include "EPause.h"
class SystemPipeline
{
public:
SystemPipeline(EventBroker* eventBroker)
: m_EventBroker(eventBroker)
{ }
SystemPipeline(World* world, EventBroker* eventBroker)
: m_World(world)
, m_EventBroker(eventBroker)
{
EVENT_SUBSCRIBE_MEMBER(m_EPause, &SystemPipeline::OnPause);
EVENT_SUBSCRIBE_MEMBER(m_EResume, &SystemPipeline::OnResume);
}
~SystemPipeline()
{
for (UnorderedSystems& group : m_OrderedSystemGroups) {
@@ -29,11 +35,11 @@ public:
m_OrderedSystemGroups.resize(updateOrderLevel + 1);
}
UnorderedSystems& group = m_OrderedSystemGroups[updateOrderLevel];
System* system = new T(m_EventBroker, args...);
System* system = new T(m_World, m_EventBroker, args...);
group.Systems[typeid(T).name()] = system;
if (std::is_base_of<PureSystem, T>::value) {
PureSystem* pureSystem = static_cast<PureSystem*>(system);
PureSystem* pureSystem = dynamic_cast<PureSystem*>(system);
if (pureSystem != nullptr) {
if (!pureSystem->m_ComponentType.empty()) {
group.PureSystems[pureSystem->m_ComponentType].push_back(pureSystem);
} else {
@@ -41,14 +47,18 @@ public:
}
}
if (std::is_base_of<ImpureSystem, T>::value) {
ImpureSystem* impureSystem = static_cast<ImpureSystem*>(system);
ImpureSystem* impureSystem = dynamic_cast<ImpureSystem*>(system);
if (impureSystem != nullptr) {
group.ImpureSystems.push_back(impureSystem);
}
}
void Update(World* world, double dt)
void Update(double dt)
{
if (m_Paused) {
dt = 0.0;
}
for (UnorderedSystems& group : m_OrderedSystemGroups) {
// Process events
for (auto& pair : group.Systems) {
@@ -56,27 +66,30 @@ public:
}
// Update
for (auto& system : group.ImpureSystems) {
system->Update(dt);
}
for (auto& pair : group.PureSystems) {
const std::string& componentName = pair.first;
auto& systems = pair.second;
const ComponentPool* pool = world->GetComponents(componentName);
const ComponentPool* pool = m_World->GetComponents(componentName);
if (pool == nullptr) {
continue;
}
for (auto& component : *pool) {
for (auto& system : systems) {
system->UpdateComponent(world, component, dt);
system->UpdateComponent(EntityWrapper(m_World, component.EntityID), component, dt);
}
}
}
for (auto& system : group.ImpureSystems) {
system->Update(world, dt);
}
}
}
private:
World* m_World;
EventBroker* m_EventBroker;
bool m_Paused = false;
struct UnorderedSystems
{
std::map<std::string, System*> Systems;
@@ -84,6 +97,21 @@ private:
std::vector<ImpureSystem*> ImpureSystems;
};
std::vector<UnorderedSystems> m_OrderedSystemGroups;
EventRelay<SystemPipeline, Events::Pause> m_EPause;
bool OnPause(const Events::Pause& e) {
if (e.World == m_World) {
m_Paused = true;
}
return true;
}
EventRelay<SystemPipeline, Events::Resume> m_EResume;
bool OnResume(const Events::Resume& e) {
if (e.World == m_World) {
m_Paused = false;
}
return true;
}
};
#endif
+5
View File
@@ -3,13 +3,18 @@
#include "../GLM.h"
#include "World.h"
#include "EntityWrapper.h"
namespace Transform
{
glm::vec3 AbsolutePosition(EntityWrapper entity);
glm::vec3 AbsolutePosition(World* world, EntityID entity);
glm::quat AbsoluteOrientation(EntityWrapper entity);
glm::quat AbsoluteOrientation(World* world, EntityID entity);
glm::vec3 AbsoluteScale(EntityWrapper entity);
glm::vec3 AbsoluteScale(World* world, EntityID entity);
glm::mat4 ModelMatrix(EntityWrapper entity);
glm::mat4 ModelMatrix(EntityID entity, World* world);
}
+22
View File
@@ -0,0 +1,22 @@
#ifndef UniformScaleSystem_h__
#define UniformScaleSystem_h__
#include "../GLM.h"
#include "System.h"
#include "../Rendering/ESetCamera.h"
class UniformScaleSystem : public PureSystem
{
public:
UniformScaleSystem(World* world, EventBroker* eventBroker);
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cUniformScale, double dt) override;
private:
EntityWrapper m_Camera = EntityWrapper::Invalid;
EventRelay<UniformScaleSystem, Events::SetCamera> m_ESetCamera;
bool OnSetCamera(const Events::SetCamera& e);
};
#endif
+7 -5
View File
@@ -21,19 +21,21 @@ public:
// Register a component type and allocate space for it
void RegisterComponent(ComponentInfo& ci);
// Attach a component to an entity and fill it with default values
ComponentWrapper AttachComponent(EntityID entity, std::string componentType);
ComponentWrapper AttachComponent(EntityID entity, const std::string& componentType);
// Check if an entity has a component
bool HasComponent(EntityID entity, std::string componentType) const;
bool HasComponent(EntityID entity, const std::string& componentType) const;
// Get a component of an entity
ComponentWrapper GetComponent(EntityID entity, std::string componentType);
ComponentWrapper GetComponent(EntityID entity, const std::string& componentType);
// Delete a component off an entity
void DeleteComponent(EntityID entity, std::string componentType);
void DeleteComponent(EntityID entity, const std::string& componentType);
// Get all components of the specified type
const ComponentPool* GetComponents(std::string componentType);
const ComponentPool* GetComponents(const std::string& componentType);
// Get entity parent
EntityID GetParent(EntityID entity);
// Change the parent of an entity
void SetParent(EntityID entity, EntityID parent);
// Get children of an entity
const std::pair<std::unordered_multimap<EntityID, EntityID>::const_iterator, std::unordered_multimap<EntityID, EntityID>::const_iterator> GetChildren(EntityID entity);
// Get all component pools
const std::unordered_map<std::string, ComponentPool*>& GetComponentPools() const { return m_ComponentPools; }
// Get the entity children map
@@ -0,0 +1,115 @@
#ifndef EditorCameraInputController_h__
#define EditorCameraInputController_h__
#include <imgui/imgui.h>
#include "../Input/FirstPersonInputController.h"
#include "../Core/EMousePress.h"
#include "../Core/EMouseRelease.h"
#include "../Core/EMouseScroll.h"
#include "../Core/ConfigFile.h"
template <typename EventContext>
class EditorCameraInputController : public FirstPersonInputController<EventContext>
{
public:
EditorCameraInputController(EventBroker* eventBroker, unsigned int playerID)
: FirstPersonInputController(eventBroker, playerID)
{
EVENT_SUBSCRIBE_MEMBER(m_EMousePress, &EditorCameraInputController::OnMousePress);
EVENT_SUBSCRIBE_MEMBER(m_EMouseRelease, &EditorCameraInputController::OnMouseRelease);
EVENT_SUBSCRIBE_MEMBER(m_EMouseScroll, &EditorCameraInputController::OnMouseScroll);
m_Config = ResourceManager::Load<ConfigFile>("Config.ini");
m_SpeedMultiplier = m_Config->Get<float>("Editor.CameraSpeed", 3.f);
}
virtual const glm::vec3 Movement() const override { return m_Movement * m_SpeedMultiplier; }
void Enable() { m_Enabled = true; }
void Disable() { m_Enabled = false; }
virtual bool OnCommand(const Events::InputCommand& e) override
{
if (glm::abs(e.Value) > 0 && !m_MouseLocked) {
return false;
}
ImGuiIO& io = ImGui::GetIO();
if (glm::abs(e.Value) > 0 && (io.WantCaptureKeyboard || io.WantCaptureMouse)) {
return false;
}
if (e.Command == "Jump") {
if (e.Value > 0) {
m_Movement.y = glm::max(e.Value, 1.f);
} else {
m_Movement.y = 0.f;
}
}
if (e.Command == "Crouch") {
if (e.Value > 0) {
m_Movement.y = glm::min(-e.Value, -1.f);
} else {
m_Movement.y = 0.f;
}
}
if (e.Command == "Sprint") {
if (e.Value > 0) {
m_SpeedMultiplier *= 2.f;
} else {
m_SpeedMultiplier /= 2.f;
}
}
return FirstPersonInputController::OnCommand(e);
}
protected:
ConfigFile* m_Config;
bool m_Enabled = false;
float m_SpeedMultiplier = 1.f;
EventRelay<EventContext, Events::MousePress> m_EMousePress;
bool OnMousePress(const Events::MousePress& e)
{
if (!m_Enabled) {
return false;
}
if (e.Button == GLFW_MOUSE_BUTTON_2) {
ImGuiIO& io = ImGui::GetIO();
if (!io.WantCaptureMouse) {
LockMouse();
}
}
return true;
}
EventRelay<EventContext, Events::MouseRelease> m_EMouseRelease;
bool OnMouseRelease(const Events::MouseRelease& e)
{
if (!m_Enabled) {
return false;
}
if (e.Button == GLFW_MOUSE_BUTTON_2) {
UnlockMouse();
}
return true;
}
EventRelay<EventContext, Events::MouseScroll> m_EMouseScroll;
bool OnMouseScroll(const Events::MouseScroll& e)
{
if (!m_Enabled) {
return false;
}
m_SpeedMultiplier += e.DeltaY * (0.1f * m_SpeedMultiplier);
m_Config->Set("Editor.CameraSpeed", m_SpeedMultiplier);
m_Config->SaveToDisk();
return true;
}
};
#endif
+153
View File
@@ -0,0 +1,153 @@
#ifndef EditorGUI_h__
#define EditorGUI_h__
#include <imgui/imgui.h>
#define IMGUI_DEFINE_MATH_OPERATORS
#include <imgui/imgui_internal.h>
#include <nativefiledialog/nfd.h>
#include <boost/filesystem.hpp>
#include <boost/any.hpp>
#include "../Common.h"
#include "../GLM.h"
#include <glm/gtx/common.hpp>
#include "EditorWidgetSystem.h"
#include "../Core/EventBroker.h"
#include "../Core/World.h"
#include "../Core/EntityWrapper.h"
#include "../Core/ResourceManager.h"
#include "../Core/EPause.h"
#include "../Core/EKeyDown.h"
#include "../Rendering/Texture.h"
class EditorGUI
{
public:
EditorGUI(World* world, EventBroker* eventBroker);
enum class WidgetMode
{
Translate,
Rotate,
Scale
};
void Draw();
void SelectEntity(EntityWrapper entity);
void SetDirty(EntityWrapper entity);
// Called when an entity is selected in the entity tree
typedef std::function<void(EntityWrapper)> OnEntitySelectedCallback_t;
void SetEntitySelectedCallback(OnEntitySelectedCallback_t f) { m_OnEntitySelected = f; }
// Called when the user means to import an entity file.
// @param EntityWrapper The entity to parent the imported entity to. The entity will be imported into the world of this entity.
// @param boost::filesystem::path The path to the entity to import
// @return EntityWrapper The newly created entity
typedef std::function<EntityWrapper(EntityWrapper, boost::filesystem::path)> OnEntityImport_t;
void SetEntityImportCallback(OnEntityImport_t f) { m_OnEntityImport = f; }
// Called when the user means to save an entity to file.
// Permitted to throw exceptions on save failure.
typedef std::function<void(EntityWrapper, boost::filesystem::path)> OnEntitySave_t;
void SetEntitySaveCallback(OnEntitySave_t f) { m_OnEntitySave = f; }
// Called when the user means to create a new entity.
// @param EntityWrapper The parent of the entity to be created
// @return EntityWrapper The newly created entity
typedef std::function<EntityWrapper(EntityWrapper)> OnEntityCreate_t;
void SetEntityCreateCallback(OnEntityCreate_t f) { m_OnEntityCreate = f; }
// Called when the user means to delete an entity.
typedef std::function<void(EntityWrapper)> OnEntityDelete_t;
void SetEntityDeleteCallback(OnEntityDelete_t f) { m_OnEntityDelete = f; }
// Called when the user means to change the parent of an entity.
typedef std::function<void(EntityWrapper, EntityWrapper)> OnEntityChangeParent_t;
void SetEntityChangeParentCallback(OnEntityChangeParent_t f) { m_OnEntityChangeParent = f; }
// Called when the user means to rename an entity.
typedef std::function<void(EntityWrapper, const std::string&)> OnEntityChangeName_t;
void SetEntityChangeNameCallback(OnEntityChangeName_t f) { m_OnEntityChangeName = f; }
// Called when the user means to attach a new component to an entity.
typedef std::function<void(EntityWrapper, const std::string&)> OnComponentAttach_t;
void SetComponentAttachCallback(OnComponentAttach_t f) { m_OnComponentAttach = f; }
// Called when the user means to delete a component off an entity.
typedef std::function<void(EntityWrapper, const std::string&)> OnComponentDelete_t;
void SetComponentDeleteCallback(OnComponentDelete_t f) { m_OnComponentDelete = f; }
// Called when the user selects a widget mode.
typedef std::function<void(WidgetMode)> OnWidgetMode_t;
void SetWidgetModeCallback(OnWidgetMode_t f) { m_OnWidgetMode = f; }
private:
World* m_World;
EventBroker* m_EventBroker;
struct EntityFileInfo
{
boost::filesystem::path Path;
bool Dirty = false;
};
// Config variables
const boost::filesystem::path m_DefaultEntityPath = boost::filesystem::path("Schema") / boost::filesystem::path("Entities");
// State
EntityWrapper m_CurrentSelection = EntityWrapper::Invalid;
std::unordered_map<EntityWrapper, EntityFileInfo> m_EntityFiles;
EntityWrapper m_CurrentlyDragging = EntityWrapper::Invalid;
std::string m_LastErrorMessage;
WidgetMode m_CurrentWidgetMode = WidgetMode::Translate;
std::set<std::string> m_ModalsToOpen;
std::map<std::string, boost::any> m_ModalData;
// Callbacks
OnEntitySelectedCallback_t m_OnEntitySelected = nullptr;
OnEntityImport_t m_OnEntityImport = nullptr;
OnEntitySave_t m_OnEntitySave = nullptr;
OnEntityCreate_t m_OnEntityCreate = nullptr;
OnEntityDelete_t m_OnEntityDelete = nullptr;
OnEntityChangeParent_t m_OnEntityChangeParent = nullptr;
OnEntityChangeName_t m_OnEntityChangeName = nullptr;
OnComponentAttach_t m_OnComponentAttach = nullptr;
OnComponentDelete_t m_OnComponentDelete = nullptr;
OnWidgetMode_t m_OnWidgetMode = nullptr;
// Events
EventRelay<EditorGUI, Events::KeyDown> m_EKeyDown;
bool OnKeyDown(const Events::KeyDown& e);
// Utility functions
boost::filesystem::path fileOpenDialog();
boost::filesystem::path fileSaveDialog();
const std::string formatEntityName(EntityWrapper entity);
GLuint tryLoadTexture(std::string filePath);
void openModal(const std::string& modal);
// Entity file handling methods
void entityImport(World* world);
void entitySave(EntityWrapper entity, bool saveAs = false);
void entityCreate(World* world, EntityWrapper parent);
void entityDelete(EntityWrapper entity);
void entityChangeParent(EntityWrapper entity, EntityWrapper parent);
// UI drawing methods
void drawMenu();
void drawTools();
void drawEntities(World* world);
void drawEntitiesRecursive(World* world, EntityID parent);
bool drawEntityNode(EntityWrapper entity);
void drawComponents(EntityWrapper entity);
bool drawComponentNode(EntityWrapper entity, const ComponentInfo& componentType);
bool drawComponentField(ComponentWrapper& c, const ComponentInfo::Field_t& field);
bool drawComponentField_Vector(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_Color(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_int(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_enum(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_float(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_double(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_bool(ComponentWrapper &c, const ComponentInfo::Field_t &field);
bool drawComponentField_string(ComponentWrapper &c, const ComponentInfo::Field_t &field);
void drawModals();
// Custom UI elements
bool createDeleteButton(const std::string& componentType);
void createWidgetToolButton(WidgetMode mode);
};
#endif
@@ -0,0 +1,27 @@
#ifndef EditorRenderSystem_h__
#define EditorRenderSystem_h__
#include "../Core/System.h"
#include "../Rendering/IRenderer.h"
#include "../Rendering/ModelJob.h"
#include "../Rendering/Camera.h"
#include "../Rendering/ESetCamera.h"
class EditorRenderSystem : public ImpureSystem
{
public:
EditorRenderSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame);
virtual void Update(double dt) override;
private:
IRenderer* m_Renderer;
RenderFrame* m_RenderFrame;
Camera* m_EditorCamera;
EntityWrapper m_CurrentCamera = EntityWrapper::Invalid;
EventRelay<EditorRenderSystem, Events::SetCamera> m_ESetCamera;
bool OnSetCamera(Events::SetCamera& e);
};
#endif
+29
View File
@@ -0,0 +1,29 @@
#include <numeric>
#include <iomanip>
#include <imgui/imgui.h>
#include "../Common.h"
#include "../GLM.h"
#include "../OpenGL.h"
class EditorStats
{
public:
EditorStats();
void Draw(double dt);
private:
// FPS graph
const unsigned int m_SampleSize = 100;
unsigned int m_FrameCount = 0;
std::vector<double> m_FrameTimes;
double m_TimeAccumulator = 0.0;
double m_AveragedSamplesPerSecond = 10.0;
const unsigned int m_AveragedSampleSize = 100;
unsigned int m_CurrentAveragedSampleIndex = 0;
std::vector<double> m_AveragedSamples;
void drawFPSGraph(double dt);
void drawRAMUsage(double dt);
void drawVRAMStats(double dt);
};
+50 -74
View File
@@ -1,94 +1,70 @@
#include <imgui/imgui.h>
#include <glm/gtx/common.hpp>
#include <boost/filesystem/path.hpp>
#include <nativefiledialog/nfd.h>
#include "../Core/System.h"
#include "../Core/EMousePress.h"
#include "../Core/EMouseRelease.h"
#include "../Core/EMouseMove.h"
#include "../Core/ConfigFile.h"
#include "../Input/EInputCommand.h"
#include "../Rendering/IRenderer.h"
#include "../Core/Transform.h"
#include "../Core/EFileDropped.h"
#include "../Rendering/Camera.h"
#include "../Rendering/ESetCamera.h"
#include "../Core/World.h"
#include "../Core/SystemPipeline.h"
#include "../Core/ResourceManager.h"
#include "../Core/EntityFilePreprocessor.h"
#include "../Core/EntityFileParser.h"
#include "../Core/EntityFileWriter.h"
#include "../Core/EMousePress.h"
#include "../Input/EInputCommand.h"
#include "EditorGUI.h"
#include "EditorStats.h"
#include "EditorCameraInputController.h"
class EditorSystem : public ImpureSystem
{
public:
EditorSystem(EventBroker* eventBroker, IRenderer* renderer);
EditorSystem(World* world, EventBroker* eventBroker, IRenderer* renderer, RenderFrame* renderFrame);
~EditorSystem();
virtual void Update(World* world, double dt) override;
void Update(double dt);
void Enable();
void Disable();
private:
IRenderer* m_Renderer;
World* m_World = nullptr;
Camera* m_Camera = nullptr;
RenderFrame* m_RenderFrame;
World* m_EditorWorld;
SystemPipeline* m_EditorWorldSystemPipeline;
//Camera* m_EditorCamera;
EntityWrapper m_EditorCamera = EntityWrapper::Invalid;
EntityWrapper m_ActualCamera = EntityWrapper::Invalid;
EditorCameraInputController<EditorSystem>* m_EditorCameraInputController;
EditorGUI* m_EditorGUI;
EditorStats* m_EditorStats;
bool m_Enabled;
bool m_Visible;
boost::filesystem::path m_DefaultEntityDir;
boost::filesystem::path m_CurrentFile;
std::vector<glm::vec2> m_PickingQueue;
// State
double m_LastTime = 0.f;
bool m_Enabled = true;
EditorGUI::WidgetMode m_WidgetMode = EditorGUI::WidgetMode::Translate;
EntityWrapper m_Widget = EntityWrapper::Invalid;
EntityWrapper m_CurrentSelection = EntityWrapper::Invalid;
enum class WidgetMode
{
None,
Translate,
Rotate,
Scale
} m_WidgetMode = WidgetMode::None;
// Utility functions
EntityWrapper importEntity(EntityWrapper parent, boost::filesystem::path filePath);
void setWidgetMode(EditorGUI::WidgetMode mode);
enum class WidgetSpace
{
Local,
Global
} m_WidgetSpace = WidgetSpace::Global;
// GUI callbacks
void OnEntitySelected(EntityWrapper entity);
void OnEntitySave(EntityWrapper entity, boost::filesystem::path filePath);
EntityWrapper OnEntityCreate(EntityWrapper parent);
void OnEntityDelete(EntityWrapper entity);
void OnEntityChangeParent(EntityWrapper entity, EntityWrapper parent);
void OnEntityChangeName(EntityWrapper entity, const std::string& name);
void OnComponentAttach(EntityWrapper entity, const std::string& componentType);
void OnComponentDelete(EntityWrapper entity, const std::string& componentType);
EntityID m_Widget = EntityID_Invalid;
EntityID m_WidgetX = EntityID_Invalid;
EntityID m_WidgetPlaneX = EntityID_Invalid;
EntityID m_WidgetY = EntityID_Invalid;
EntityID m_WidgetPlaneY = EntityID_Invalid;
EntityID m_WidgetZ = EntityID_Invalid;
EntityID m_WidgetPlaneZ = EntityID_Invalid;
EntityID m_WidgetOrigin = EntityID_Invalid;
glm::vec3 m_WidgetCurrentAxis;
float m_WidgetPickingDepth = 0.f;
glm::vec3 m_WidgetPickingPosition = glm::vec3(0);
EntityID m_Selection = EntityID_Invalid;
EntityID m_LastSelection = EntityID_Invalid;
EntityID m_UIDraggingEntity = EntityID_Invalid;
glm::vec3 m_Position;
std::string m_LastDroppedFile;
static boost::filesystem::path openDialog(boost::filesystem::path defaultPath);
static boost::filesystem::path saveDialog(boost::filesystem::path defaultPath);
EventRelay<EditorSystem, Events::InputCommand> m_EInputCommand;
bool OnInputCommand(const Events::InputCommand& e);
EventRelay<EditorSystem, Events::MouseRelease> m_EMouseRelease;
bool OnMouseRelease(const Events::MouseRelease& e);
// Events
EventRelay<EditorSystem, Events::MousePress> m_EMousePress;
bool OnMousePress(const Events::MousePress& e);
EventRelay<EditorSystem, Events::MouseMove> m_EMouseMove;
bool OnMouseMove(const Events::MouseMove& e);
EventRelay<EditorSystem, Events::FileDropped> m_EFileDropped;
bool OnFileDropped(const Events::FileDropped& e);
void Picking();
void createWidget();
void updateWidget();
void setWidgetMode(WidgetMode newMode);
void setWidgetSpace(WidgetSpace space);
void drawUI(World* world, double dt);
bool createDeleteButton(std::string componentType);
bool createEntityNode(World* world, EntityID entity);
void changeParent(EntityID entity, EntityID newParent);
void fileImport(World* world);
void fileSave(World* world);
void fileSaveAs(World* world);
EventRelay<EditorSystem, Events::WidgetDelta> m_EWidgetDelta;
bool OnWidgetDelta(const Events::WidgetDelta& e);
EventRelay<EditorSystem, Events::InputCommand> m_EInputCommand;
bool OnInputCommand(const Events::InputCommand& e);
EventRelay<EditorSystem, Events::SetCamera> m_ESetCamera;
bool OnSetCamera(const Events::SetCamera& e);
};
@@ -0,0 +1,49 @@
#ifndef EditorWidgetSystem_h__
#define EditorWidgetSystem_h__
#include <imgui/imgui.h>
#include "../GLM.h"
#include "../Core/System.h"
#include "../Rendering/IRenderer.h"
#include "../Rendering/Util/ScreenCoords.h"
#include "../Core/EMouseMove.h"
#include "../Core/EMousePress.h"
#include "../Core/EMouseRelease.h"
namespace Events
{
struct WidgetDelta : Event
{
glm::vec3 Translation;
glm::vec3 Rotation;
glm::vec3 Scale;
};
}
class EditorWidgetSystem : public ImpureSystem, PureSystem
{
public:
EditorWidgetSystem(World* world, EventBroker* eventBroker, IRenderer* renderer);
virtual void Update(double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& cEditorWidget, double dt) override;
private:
IRenderer* m_Renderer;
// State
EntityWrapper m_PickEntity = EntityWrapper::Invalid;
PickData m_PickData;
glm::vec2 m_MouseDelta;
EventRelay<EditorWidgetSystem, Events::MouseMove> m_EMouseMove;
bool OnMouseMove(const Events::MouseMove& e);
EventRelay<EditorWidgetSystem, Events::MousePress> m_EMousePress;
bool OnMousePress(const Events::MousePress& e);
EventRelay<EditorWidgetSystem, Events::MouseRelease> m_EMouseRelease;
bool OnMouseRelease(const Events::MouseRelease& e);
};
#endif
+2 -1
View File
@@ -7,4 +7,5 @@
#include <glm/gtx/rotate_vector.hpp>
#include <glm/gtc/quaternion.hpp>
#include <glm/gtx/quaternion.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/gtx/projection.hpp>
+1 -1
View File
@@ -9,7 +9,7 @@ namespace Events
struct InputCommand : Event
{
/** Numerical ID of the player. */
unsigned int PlayerID;
int PlayerID;
/** The command that was sent. */
std::string Command;
/** The value of the command. */
+104 -47
View File
@@ -9,62 +9,119 @@ template <typename EventContext>
class FirstPersonInputController : public InputController<EventContext>
{
public:
FirstPersonInputController(EventBroker* eventBroker, unsigned int playerID)
: InputController(eventBroker)
, m_PlayerID(playerID)
{
EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse);
EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse);
}
FirstPersonInputController(EventBroker* eventBroker, int playerID);
const glm::quat Orientation() const { return m_Orientation; }
virtual const glm::vec3 Movement() const { return m_Movement; }
virtual const glm::vec3 Rotation() const { return m_Rotation; }
virtual bool Jumping() const { return m_Jumping; }
virtual bool Crouching() const { return m_Crouching; }
void LockMouse()
{
Events::LockMouse e;
m_EventBroker->Publish(e);
m_MouseLocked = true;
}
void LockMouse();
void UnlockMouse();
virtual bool OnCommand(const Events::InputCommand& e) override;
virtual void Reset();
void UnlockMouse()
{
Events::UnlockMouse e;
m_EventBroker->Publish(e);
m_MouseLocked = false;
}
protected:
const int m_PlayerID;
bool m_MouseLocked = false;
glm::vec3 m_Rotation;
glm::vec3 m_Movement;
bool m_Jumping = false;
bool m_Crouching = false;
EventRelay<EventContext, Events::LockMouse> m_ELockMouse;
bool OnLockMouse(const Events::LockMouse& e);
EventRelay<EventContext, Events::UnlockMouse> m_EUnlockMouse;
bool OnUnlockMouse(const Events::UnlockMouse& e);
};
virtual bool OnCommand(const Events::InputCommand& e) override
{
if (m_PlayerID != e.PlayerID) {
return false;
}
template <typename EventContext>
FirstPersonInputController<EventContext>::FirstPersonInputController(EventBroker* eventBroker, int playerID)
: InputController(eventBroker)
, m_PlayerID(playerID)
{
EVENT_SUBSCRIBE_MEMBER(m_ELockMouse, &FirstPersonInputController::OnLockMouse);
EVENT_SUBSCRIBE_MEMBER(m_EUnlockMouse, &FirstPersonInputController::OnUnlockMouse);
}
if (m_MouseLocked) {
if (e.Command == "Pitch") {
float val = glm::radians(e.Value);
m_Orientation = m_Orientation * glm::angleAxis<float>(-val, glm::vec3(1, 0, 0));
return true;
}
template <typename EventContext>
void FirstPersonInputController<EventContext>::Reset()
{
m_Rotation = glm::vec3(0.f, 0.f, 0.f);
m_Jumping = false;
}
if (e.Command == "Yaw") {
float val = glm::radians(e.Value);
m_Orientation = glm::angleAxis<float>(-val, glm::vec3(0, 1, 0)) * m_Orientation;
return true;
}
}
template <typename EventContext>
void FirstPersonInputController<EventContext>::LockMouse()
{
Events::LockMouse e;
m_EventBroker->Publish(e);
m_MouseLocked = true;
}
template <typename EventContext>
void FirstPersonInputController<EventContext>::UnlockMouse()
{
Events::UnlockMouse e;
m_EventBroker->Publish(e);
m_MouseLocked = false;
}
template <typename EventContext>
bool FirstPersonInputController<EventContext>::OnCommand(const Events::InputCommand& e)
{
if (m_PlayerID != e.PlayerID) {
return false;
}
protected:
const unsigned int m_PlayerID;
glm::quat m_Orientation;
bool m_MouseLocked = false;
EventRelay<EventContext, Events::LockMouse> m_ELockMouse;
bool OnLockMouse(const Events::LockMouse& e) { m_MouseLocked = true; return true; }
EventRelay<EventContext, Events::UnlockMouse> m_EUnlockMouse;
bool OnUnlockMouse(const Events::UnlockMouse& e) { m_MouseLocked = false; return true; }
};
if (e.Command == "Pitch") {
float val = glm::radians(e.Value);
m_Rotation.x += -val;
//m_Rotation.x = glm::clamp(m_Rotation.x, -glm::half_pi<float>(), glm::half_pi<float>());
}
if (e.Command == "Yaw") {
float val = glm::radians(e.Value);
m_Rotation.y += -val;
}
if (e.Command == "Forward" || e.Command == "Right") {
if (e.Command == "Forward") {
float val = glm::clamp(e.Value, -1.f, 1.f);
m_Movement.z = -val;
}
if (e.Command == "Right") {
float val = glm::clamp(e.Value, -1.f, 1.f);
m_Movement.x = val;
}
if (glm::length2(m_Movement) > 0) {
m_Movement = glm::normalize(m_Movement);
}
}
if (e.Command == "Jump") {
m_Jumping = e.Value > 0;
}
if (e.Command == "Crouch") {
m_Crouching = e.Value > 0;
}
return true;
}
template <typename EventContext>
bool FirstPersonInputController<EventContext>::OnUnlockMouse(const Events::UnlockMouse& e)
{
m_MouseLocked = false;
return true;
}
template <typename EventContext>
bool FirstPersonInputController<EventContext>::OnLockMouse(const Events::LockMouse& e)
{
m_MouseLocked = true;
return true;
}
#endif
+1
View File
@@ -1,6 +1,7 @@
#ifndef InputProxy_h__
#define InputProxy_h__
#include <boost/tokenizer.hpp>
#include "../Common.h"
#include "../Core/ResourceManager.h"
#include "../Core/ConfigFile.h"
+39 -18
View File
@@ -3,9 +3,12 @@
#include <string>
#include <ctime>
#include <limits>
#include <queue>
#include <glm/common.hpp>
#include <boost/asio.hpp>
#include <boost/shared_array.hpp>
#include "Network/Network.h"
#include "Network/MessageType.h"
@@ -15,6 +18,9 @@
#include "Core/EventBroker.h"
#include "Core/ConfigFile.h"
#include "Input/EInputCommand.h"
#include "Core/EPlayerDamage.h"
#include "Network/EInterpolate.h"
#include "Core/EPlayerSpawned.h"
class Client : public Network
{
@@ -32,52 +38,67 @@ private:
// Sending message to server logic
int bytesRead = -1;
char readBuf[INPUTSIZE] = { 0 };
int snapshotInterval = 33;
std::clock_t previousSnapshotMessage = std::clock();
// Packet loss logic
unsigned int m_PacketID = 0;
unsigned int m_PreviousPacketID = 0;
unsigned int m_SendPacketID = 0;
PacketID m_PacketID = 0;
PacketID m_PreviousPacketID = 0;
PacketID m_SendPacketID = 0;
// Game logic
World* m_World;
std::string m_PlayerName;
int m_PlayerID = -1;
PlayerID m_PlayerID = -1;
EntityID m_ServerEntityID = std::numeric_limits<EntityID>::max();
bool m_IsConnected = false;
// Server Client Lookup map
// Assumes that root node for client and server is EntityID 0.
// Don't Add items to these two maps with insert, use insertIntoServerClientMaps(EntityID, EntityID)!!!!
std::unordered_map<EntityID, EntityID> m_ServerIDToClientID;
std::unordered_map<EntityID, EntityID> m_ClientIDToServerID;
// Network logic
PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS];
PlayerDefinition m_PlayerDefinitions[8];
SnapshotDefinitions m_NextSnapshot;
double m_DurationOfPingTime;
std::clock_t m_StartPingTime;
// Use to check if we should send disconnect message
// if game is turned of by closing window.
bool m_WasStarted = false;
std::clock_t m_TimeSinceSentInputs;
unsigned int m_SendInputIntervalMs;
std::vector<Events::InputCommand> m_InputCommandBuffer;
// Private member functions
void readFromServer();
void sendSnapshotToServer();
int receive(char* data, size_t length);
int receive(char* data);
void send(Packet& packet);
void connect();
void disconnect();
void ping();
void moveMessageHead(char*& data, size_t& length, size_t stepSize);
void parseMessageType(Packet& packet);
void parseEventMessage(Packet& packet);
void updateFields(Packet& packet, const ComponentInfo& componentInfo, const EntityID& entityID, const std::string& componentType);
void parseConnect(Packet& packet);
void parsePlayerConnected(Packet& packet);
void parsePing();
void parseServerPing();
void parseKick();
void parsePlayersSpawned(Packet& packet);
void InterpolateFields(Packet & packet, const ComponentInfo & componentInfo, const EntityID & entityID, const std::string & componentType);
void parseSnapshot(Packet& packet);
void identifyPacketLoss();
bool isConnected();
bool hasServerTimedOut();
EntityID createPlayer();
void sendInputCommands();
void becomePlayer();
// Mapping Logic
// Returns if local EntityID exist in map
bool clientServerMapsHasEntity(EntityID clientEntityID);
// Returns if server EntityID exist in map
bool serverClientMapsHasEntity(EntityID serverEntityID);
void insertIntoServerClientMaps(EntityID serverEntityID, EntityID clientEntityID);
// Events
EventBroker* m_EventBroker;
EventRelay<Client, Events::InputCommand> m_EInputCommand;
bool OnInputCommand(const Events::InputCommand &e);
bool OnInputCommand(const Events::InputCommand& e);
EventRelay<Client, Events::PlayerDamage> m_EPlayeDamage;
bool OnPlayerDamage(const Events::PlayerDamage& e);
};
#endif
+20
View File
@@ -0,0 +1,20 @@
#ifndef Events_Interpolate_h__
#define Events_Interpolate_h__
#include <boost/shared_array.hpp>
#include "Core/EventBroker.h"
#include "Core/Entity.h"
namespace Events
{
struct Interpolate : Event
{
EntityID Entity;
boost::shared_array<char> DataArray;
};
}
#endif
@@ -0,0 +1,18 @@
#ifndef Events_PlayerDisconnected
#define Events_PlayerDisconnected
#include "Core/EventBroker.h"
#include "Core/Entity.h"
namespace Events
{
struct PlayerDisconnected : public Event
{
unsigned int PlayerID;
EntityID Entity;
};
}
#endif
+11 -7
View File
@@ -5,13 +5,17 @@
// Used to determine what type of message was sent.
enum class MessageType
{
Connect,
Disconnect,
ClientPing,
ServerPing,
Message,
Snapshot,
Event,
Connect,
Disconnect,
Ping,
Message,
Snapshot,
OnInputCommand,
OnPlayerDamage,
PlayerConnected,
BecomePlayer,
Kick,
OnPlayerSpawned
};
#endif
+21 -1
View File
@@ -1,12 +1,21 @@
#ifndef Network_h__
#define Network_h__
#include <ctime>
#include "Core/World.h"
#include "Core/EventBroker.h"
#include "Network/Packet.h"
#include "Network/NetworkData.h"
#include "Core/ResourceManager.h"
#include "Core/ConfigFile.h"
#include <fstream>
#include <iostream>
#define MAXCONNECTIONS 8
#define INPUTSIZE 4097
typedef unsigned int PlayerID;
typedef unsigned int PacketID;
typedef unsigned int UserID;
class Network
{
@@ -14,6 +23,17 @@ public:
virtual ~Network() { };
virtual void Start(World* m_world, EventBroker *eventBroker) = 0;
virtual void Update() = 0;
protected:
// For Debug
bool isReadingData = false;
NetworkData m_NetworkData;
unsigned int m_SaveDataIntervalMs = 1000;
std::clock_t m_SaveDataTimer;
unsigned int m_MaxConnections;
unsigned int m_TimeoutMs;
void saveToFile();
void updateNetworkData();
void initialize();
};
#endif
+18
View File
@@ -0,0 +1,18 @@
#ifndef NetworkData_h__
#define NetworkData_h__
#include <vector>
struct NetworkData {
unsigned int TotalTime = 0;
unsigned int TotalDataReceived = 0;
unsigned int TotalDataSent = 0;
unsigned int AmountOfMessagesReceived = 0;
unsigned int AmountOfMessagesSent = 0;
// Interval based
unsigned int DataReceivedThisInterval = 0;
unsigned int DataSentThisInterval = 0;
// pair: first=reveived, second=send
std::vector<std::pair<unsigned int, unsigned int>> BandwidthBytes;
};
#endif
+4 -1
View File
@@ -14,6 +14,7 @@ public:
Packet(MessageType type, unsigned int& packetID);
// Used to create packet from already existing data buffer.
Packet(char* data, const int sizeOfPacket);
Packet(MessageType type);
~Packet();
void Init(MessageType type, unsigned int& packetID);
@@ -49,17 +50,19 @@ public:
// Pops the first element as if it was a string.
std::string ReadString();
char* ReadData(int SizeOfData);
void ChangePacketID(unsigned int& packetID);
int Size() { return m_Offset; };
char* Data() { return m_Data; };
unsigned int DataReadSize() { return m_ReturnDataOffset; }
unsigned int MaxSize() { return m_MaxPacketSize; }
unsigned int HeaderSize() { return m_HeaderSize; }
private:
char* m_Data;
unsigned int m_ReturnDataOffset = 0;
int m_Offset = 0;
unsigned int m_MaxPacketSize = 512;
unsigned int m_HeaderSize = 0;
void resizeData();
};
@@ -6,6 +6,8 @@ struct PlayerDefinition {
int EntityID = -1;
std::string Name = "";
boost::asio::ip::udp::endpoint Endpoint;
unsigned int PacketID;
std::clock_t StopTime;
};
#endif
+26 -19
View File
@@ -11,7 +11,11 @@
#include "Network/PlayerDefinition.h"
#include "Core/World.h"
#include "Core/EventBroker.h"
#include "Network/Network.h"
#include "../Network/Network.h"
#include "Input/EInputCommand.h"
#include "Core/EPlayerDamage.h"
#include "Network/EPlayerDisconnected.h"
#include "Core/EPlayerSpawned.h"
class Server : public Network
{
@@ -25,9 +29,10 @@ private:
boost::asio::ip::udp::endpoint m_ReceiverEndpoint;
boost::asio::io_service m_IOService;
boost::asio::ip::udp::socket m_Socket;
PlayerDefinition m_PlayerDefinitions[MAXCONNECTIONS];
// Sending messages to client logic
PlayerDefinition m_PlayerDefinitions[8]; //
std::vector<PlayerDefinition> m_ConnectedUsers;
char readBuffer[INPUTSIZE] = { 0 };
int bytesRead = 0;
// time for previouse message
@@ -35,46 +40,48 @@ private:
std::clock_t previousSnapshotMessage = std::clock();
std::clock_t timOutTimer = std::clock();
// How often we send messages (milliseconds)
int intervalMs = 1000;
int snapshotInterval = 50;
int pingIntervalMs;
int snapshotInterval;
int checkTimeOutInterval = 100;
//Timers
std::clock_t m_StartPingTime;
std::clock_t m_StopTimes[8];
// Game logic
World* m_World;
EventBroker* m_EventBroker;
// vec.size() = ammount of players to create, stores playerID's
std::vector<unsigned int> m_PlayersToCreate;
// Packet loss logic
unsigned int m_PacketID;
unsigned int m_PreviousPacketID;
unsigned int m_SendPacketID;
PacketID m_PacketID = 0;
PacketID m_PreviousPacketID = 0;
// Private member functions
int receive(char* data, size_t length);
int receive(char* data);
void readFromClients();
void send(Packet& packet, int playerID);
void send(Packet& packet, UserID user);
void send(PlayerID player, Packet& packet);
void send(Packet& packet);
void moveMessageHead(char*& data, size_t& length, size_t stepSize);
void broadcast(std::string message);
void broadcast(Packet& packet);
void sendSnapshot();
void sendPing();
void checkForTimeOuts();
void disconnect(int i);
void disconnect(UserID user);
void parseMessageType(Packet& packet);
void parseEvent(Packet& packet);
void parseOnInputCommand(Packet& packet);
void parseOnPlayerDamage(Packet& packet);
void parseConnect(Packet& packet);
void parseDisconnect();
void parseClientPing();
void parseServerPing();
void parseSnapshot(Packet& packet);
void parsePing();
void identifyPacketLoss();
EntityID createPlayer();
void createPlayer();
void kick(PlayerID player);
PlayerID GetPlayerIDFromEndpoint(boost::asio::ip::udp::endpoint endpoint);
// Debug event
EventRelay<Server, Events::InputCommand> m_EInputCommand;
bool OnInputCommand(const Events::InputCommand& e);
EventRelay<Server, Events::PlayerSpawned> m_EPlayerSpawned;
bool OnPlayerSpawned(const Events::PlayerSpawned& e);
};
#endif
+3 -1
View File
@@ -2,6 +2,7 @@
#define Camera_h__
#include "../GLM.h"
#include "../Core/Util/Rectangle.h"
class Camera
{
@@ -32,7 +33,6 @@ public:
glm::mat4 ViewMatrix() const { return m_ViewMatrix; }
void SetViewMatrix(glm::mat4 val);
float AspectRatio() const { return m_AspectRatio; }
void SetAspectRatio(float val);
@@ -48,6 +48,8 @@ public:
void UpdateViewMatrix();
void UpdateProjectionMatrix();
glm::vec2 WorldToScreen(glm::vec3 worldCoord, Rectangle resolution);
private:
glm::vec3 m_Position;
@@ -1,66 +0,0 @@
#include <imgui/imgui.h>
#include "../Input/FirstPersonInputController.h"
template <typename EventContext>
class DebugCameraInputController : public FirstPersonInputController<EventContext>
{
public:
DebugCameraInputController(EventBroker* eventBroker, unsigned int playerID)
: FirstPersonInputController(eventBroker, playerID)
{ }
void SetPosition(const glm::vec3 position) { m_Position = position; }
void SetOrientation(const glm::quat orientation) { m_Orientation = orientation; }
const glm::vec3 Position() const { return m_Position; }
void SetBaseSpeed(float speed) { m_BaseSpeed = speed; }
virtual bool OnCommand(const Events::InputCommand& e) override
{
ImGuiIO& io = ImGui::GetIO();
if (e.Command == "PrimaryFire") {
if (e.Value > 0) {
if (!io.WantCaptureMouse) {
LockMouse();
}
} else {
UnlockMouse();
}
return false;
}
if (!io.WantCaptureKeyboard) {
if (e.Command == "Right") {
float value = std::max(-1.f, std::min(e.Value, 1.f));
m_Velocity.x = value;
}
if (e.Command == "Forward") {
float value = std::max(-1.f, std::min(e.Value, 1.f));
m_Velocity.z = -value;
}
if (e.Command == "Sprint") {
if (e.Value > 0.f) {
m_Speed = m_BaseSpeed * 2.f * (e.Value);
} else {
m_Speed = m_BaseSpeed;
}
}
}
return FirstPersonInputController::OnCommand(e);
}
void Update(double dt)
{
if (glm::length2(m_Velocity) > 0) {
m_Position += m_Orientation * (glm::normalize(m_Velocity) * m_Speed * (float)dt);
}
}
protected:
glm::vec3 m_Position = glm::vec3(0, 0, 0);
glm::vec3 m_Velocity = glm::vec3(0, 0, 0);
float m_BaseSpeed = 2.0f;
float m_Speed = m_BaseSpeed;
};
@@ -0,0 +1,35 @@
#ifndef DirectionalLightJob_h__
#define DirectionalLightJob_h__
#include <cstdint>
#include "../Common.h"
#include "../GLM.h"
#include "../Core/ComponentWrapper.h"
#include "RenderJob.h"
#include "../Core/Transform.h"
#include "../Core/World.h"
struct DirectionalLightJob : RenderJob
{
DirectionalLightJob(ComponentWrapper transformComponent, ComponentWrapper directionalLightComponent, World* m_World)
: RenderJob()
{
Direction = glm::vec4(0,0,-1,0) * glm::inverse(Transform::AbsoluteOrientation(m_World, transformComponent.EntityID));
//Direction = glm::vec4((glm::vec3)directionalLightComponent["Direction"], 0.f);
Color = (glm::vec4)directionalLightComponent["Color"];
Intensity = (double)directionalLightComponent["Intensity"];
};
glm::vec4 Direction;
glm::vec4 Color;
float Intensity;
void CalculateHash() override
{
Hash = 0;
}
};
#endif
+53
View File
@@ -0,0 +1,53 @@
#ifndef DrawBloomPass_h__
#define DrawBloomPass_h__
#include "IRenderer.h"
#include "DrawBloomPassState.h"
//#include "LightCullingPass.h" Finalpass om den skall skickas in
#include "FrameBuffer.h"
#include "ShaderProgram.h"
//#include "Util/UnorderedMapVec2.h"
#include "Texture.h"
class DrawBloomPass
{
public:
DrawBloomPass(IRenderer* renderer /* ,Texture or finalpass*/ );
~DrawBloomPass() { }
void InitializeTextures();
void InitializeFrameBuffers();
void InitializeShaderPrograms();
void InitializeBuffers();
void ClearBuffer();
void FillGaussianBuffer(FrameBuffer* fb);
void Draw(GLuint texture);
//Getters
//Return the blurred result of the texture that was sent into draw
GLuint GaussianTexture() const { return m_GaussianTexture_vert; }
private:
void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const;
Texture* m_WhiteTexture;
Model* m_ScreenQuad;
const IRenderer* m_Renderer;
//const LightCullingPass* m_LightCullingPass
GLuint m_iterations = 9;
GLuint m_GaussianTexture_horiz;
GLuint m_GaussianTexture_vert;
FrameBuffer m_GaussianFrameBuffer_horiz;
FrameBuffer m_GaussianFrameBuffer_vert;
ShaderProgram* m_GaussianProgram_horiz;
ShaderProgram* m_GaussianProgram_vert;
};
#endif
@@ -0,0 +1,15 @@
#ifndef DrawBloomPassState_h__
#define DrawBloomPassState_h__
#include "Rendering/RenderState.h"
class DrawBloomPassState : public RenderState
{
public:
DrawBloomPassState();
~DrawBloomPassState();
private:
};
#endif
@@ -0,0 +1,29 @@
#ifndef DrawColorCorrectionPass_h__
#define DrawColorCorrectionPass_h__
#include "IRenderer.h"
#include "DrawScreenQuadPassState.h"
#include "FrameBuffer.h"
#include "ShaderProgram.h"
//#include "Util/UnorderedMapVec2.h"
#include "Texture.h"
class DrawColorCorrectionPass
{
public:
DrawColorCorrectionPass(IRenderer* renderer);
~DrawColorCorrectionPass() { }
void InitializeFrameBuffers();
void InitializeShaderPrograms();
void Draw(GLuint sceneTexture, GLuint bloomTexture);
private:
const IRenderer* m_Renderer;
ShaderProgram* m_ColorCorrectionProgram;
Model* m_ScreenQuad;
GLfloat m_Exposure;
};
#endif
+13 -3
View File
@@ -17,22 +17,32 @@ public:
void InitializeTextures();
void InitializeFrameBuffers();
void InitializeShaderPrograms();
void Draw(RenderScene& scene);
void ClearBuffer();
//Getters
//Return the texture that is used in later stages to apply the bloom effect
GLuint BloomTexture() const { return m_BloomTexture; }
//Return the texture with diffuse and lighting of the scene.
GLuint SceneTexture() const { return m_SceneTexture; }
FrameBuffer* FinalPassFrameBuffer() { return &m_FinalPassFrameBuffer; }
private:
void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const;
void GenerateMipMapTexture(GLuint* texture, GLenum wrapping, glm::vec2 dimensions, GLint format, GLenum type, GLint numMipMaps) const;
Texture* m_WhiteTexture;
Texture* m_BlackTexture;
FrameBuffer m_FinalPassFrameBuffer;
GLuint m_BloomTexture;
GLuint m_SceneTexture;
GLuint m_DepthBuffer;
const IRenderer* m_Renderer;
const LightCullingPass* m_LightCullingPass;
ShaderProgram* m_ForwardPlusProgram;
};
#endif
@@ -6,7 +6,7 @@
class DrawFinalPassState : public RenderState
{
public:
DrawFinalPassState();
DrawFinalPassState(GLuint frameBuffer);
~DrawFinalPassState();
private:
-42
View File
@@ -1,42 +0,0 @@
#ifndef DrawScenePass_h__
#define DrawScenePass_h__
#include "IRenderer.h"
#include "DrawScenePassState.h"
#include "FrameBuffer.h"
#include "ShaderProgram.h"
#include "Util/UnorderedMapVec2.h"
#include "Texture.h"
class DrawScenePass
{
public:
DrawScenePass(IRenderer* renderer);
~DrawScenePass() { }
void InitializeTextures();
void InitializeFrameBuffers();
void InitializeShaderPrograms();
void Draw(RenderScene& scene);
//Getters
private:
void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type) const;
static bool DepthSort(const std::shared_ptr<RenderJob> &i, const std::shared_ptr<RenderJob> &j)
{
return (i->Depth < j->Depth);
};
Texture* m_WhiteTexture;
const IRenderer* m_Renderer;
ShaderProgram* m_BasicForwardProgram;
};
#endif
@@ -1,15 +0,0 @@
#ifndef DrawScenePassState_h__
#define DrawScenePassState_h__
#include "Rendering/RenderState.h"
class DrawScenePassState : public RenderState
{
public:
DrawScenePassState();
~DrawScenePassState();
private:
};
#endif
@@ -0,0 +1,28 @@
#ifndef DrawScreenQuadPass_h__
#define DrawScreenQuadPass_h__
#include "IRenderer.h"
#include "DrawScreenQuadPassState.h"
#include "FrameBuffer.h"
#include "ShaderProgram.h"
//#include "Util/UnorderedMapVec2.h"
#include "Texture.h"
class DrawScreenQuadPass
{
public:
DrawScreenQuadPass(IRenderer* renderer);
~DrawScreenQuadPass() { }
void InitializeFrameBuffers();
void InitializeShaderPrograms();
void Draw(GLuint texture);
private:
const IRenderer* m_Renderer;
ShaderProgram* m_DrawQuadProgram;
Model* m_ScreenQuad;
};
#endif
@@ -0,0 +1,15 @@
#ifndef DrawScreenQuadPassState_h__
#define DrawScreenQuadPassState_h__
#include "Rendering/RenderState.h"
class DrawScreenQuadPassState : public RenderState
{
public:
DrawScreenQuadPassState();
~DrawScreenQuadPassState();
private:
};
#endif
+2 -8
View File
@@ -2,20 +2,14 @@
#define Events_SetCamera_h__
#include "../Core/EventBroker.h"
#include "../Core/Entity.h"
#include <string.h>
#include "../Core/EntityWrapper.h"
namespace Events
{
struct SetCamera : Event
{
public:
SetCamera() { };
std::string Name;
private:
EntityWrapper CameraEntity;
};
}
+36
View File
@@ -0,0 +1,36 @@
#ifndef Font_h__
#define Font_h__
#include <ft2build.h>
#include FT_FREETYPE_H
#include FT_GLYPH_H
#include <boost/tokenizer.hpp>
#include <boost/lexical_cast.hpp>
#include "../OpenGL.h"
#include "../GLM.h"
#include "../Core/ResourceManager.h"
class Font : public Resource
{
friend class ResourceManager;
private:
Font(std::string path);
public:
struct Character {
GLuint TextureID; // ID handle of the glyph texture
glm::ivec2 Size; // Size of glyph
glm::ivec2 Bearing; // Offset from baseline to left/top of glyph
GLuint Advance; // Offset to advance to next glyph
};
int FontSize = 16;
~Font();
std::map<GLchar, Character> m_Characters;
};
#endif
-11
View File
@@ -31,15 +31,6 @@ public:
void SetFullscreen(bool fullscreen) { m_Fullscreen = fullscreen; }
bool VSYNC() const { return m_VSYNC; }
void SetVSYNC(bool vsync) { m_VSYNC = vsync; }
::Camera* Camera() const { return m_Camera; }
void SetCamera(::Camera* camera)
{
if (camera == nullptr) {
m_Camera = m_DefaultCamera;
} else {
m_Camera = camera;
}
}
virtual void Initialize() = 0;
virtual void Update(double dt) = 0;
virtual void Draw(RenderFrame& rq) = 0;
@@ -54,8 +45,6 @@ protected:
int m_GLVersion[2];
std::string m_GLVendor;
GLFWwindow* m_Window = nullptr;
::Camera* m_DefaultCamera;
::Camera* m_Camera = nullptr;
};
#endif // Renderer_h__
+9 -8
View File
@@ -46,8 +46,8 @@ private:
int m_NumberOfTiles = 0;
struct Plane {
glm::vec3 Normal;
float d;
glm::vec3 Normal = glm::vec3(0.f);
float d = 0;
};
struct Frustum {
@@ -56,20 +56,21 @@ private:
Frustum* m_Frustums;
//This should be a component
struct PointLight {
struct LightSource {
glm::vec4 Position = glm::vec4(0.f);
glm::vec4 Direction = glm::vec4(10.f);
glm::vec4 Color = glm::vec4(1.f);
float Radius = 5.f;
float Intensity = 0.8f;
float Falloff = 0.3f;
float Padding = 1337;
enum Type_t { Zero, Point, Directional, Spot } Type;
};
std::vector<PointLight> m_PointLights;
std::vector<LightSource> m_LightSources;
struct LightGrid {
float Start;
float Amount;
glm::vec2 Padding;
float Start = 0;
float Amount = 0;
glm::vec2 Padding = glm::vec2(1.f, 2.f);
};
LightGrid* m_LightGrid;
+4
View File
@@ -12,6 +12,7 @@
#include "../Core/ResourceManager.h"
#include "Camera.h"
#include "../Core/World.h"
#include "../Core/Transform.h"
struct ModelJob : RenderJob
{
@@ -28,6 +29,9 @@ struct ModelJob : RenderJob
Matrix = matrix;
Color = modelComponent["Color"];
Entity = modelComponent.EntityID;
glm::vec3 abspos = Transform::AbsolutePosition(world, modelComponent.EntityID);
glm::vec3 worldpos = glm::vec3(camera->ViewMatrix() * glm::vec4(abspos, 1));
Depth = worldpos.z;
World = world;
};
-1
View File
@@ -14,7 +14,6 @@ struct RenderJob
friend class RenderQueue;
public:
float Depth;
protected:
+8 -37
View File
@@ -11,54 +11,26 @@
#include "Camera.h"
#include "RenderJob.h"
#include "ModelJob.h"
#include "TextJob.h"
#include "PointLightJob.h"
/*
struct SpriteJob : RenderJob
{
unsigned int ShaderID = 0;
unsigned int TextureID = 0;
glm::mat4 ModelMatrix;
const Texture* DiffuseTexture = nullptr;
const Texture* NormalTexture = nullptr;
const Texture* SpecularTexture = nullptr;
glm::vec4 Color;
void CalculateHash() override
{
Hash = TextureID;
}
};
struct PointLightJob : RenderJob
{
glm::vec4 Position;
glm::vec4 Color;
float Radius;
float Intensity;
float Falloff;
float padding = 123;
void CalculateHash() override
{
Hash = 0;
}
};
*/
#include "DirectionalLightJob.h"
struct RenderScene
{
::Camera* Camera;
::Camera* Camera = nullptr;
std::list<std::shared_ptr<RenderJob>> ForwardJobs;
std::list<std::shared_ptr<RenderJob>> PointLightJobs;
std::list<std::shared_ptr<RenderJob>> TextJobs;
std::list<std::shared_ptr<RenderJob>> DirectionalLightJobs;
Rectangle Viewport;
bool ClearDepth = false;
void Clear()
{
ForwardJobs.clear();
PointLightJobs.clear();
TextJobs.clear();
DirectionalLightJobs.clear();
}
};
@@ -94,5 +66,4 @@ public:
private:
int m_Size = 0;
};
#endif
+1 -1
View File
@@ -16,10 +16,10 @@ public:
bool Disable(GLenum cap);
bool CullFace(GLenum mode);
bool ClearColor(glm::vec4 color);
bool Clear(GLbitfield mask);
bool BindFramebuffer(GLint framebuffer);
bool BlendEquation(GLenum mode);
bool BlendFunc(GLenum sfactor, GLenum dfactor);
bool DepthMask(GLboolean flag);
private:
std::vector<std::function<void(void)>> m_ResetFunctions;
+15 -20
View File
@@ -15,41 +15,36 @@
#include "Renderer.h"
#include "PointLightJob.h"
#include "../Core/Transform.h"
#include "DebugCameraInputController.h"
#include "../Core/EPlayerSpawned.h"
class RenderSystem : public ImpureSystem
{
public:
RenderSystem(EventBroker* eventBrokerer, const IRenderer* renderer, RenderFrame* renderFrame);
RenderSystem(World* world, EventBroker* eventBrokerer, const IRenderer* renderer, RenderFrame* renderFrame);
~RenderSystem();
virtual void Update(World* world, double dt) override;
virtual void Update(double dt) override;
private:
World* m_World = nullptr;
const IRenderer* m_Renderer;
RenderFrame* m_RenderFrame;
bool m_SwitchCamera = false;
Camera* m_Camera;
DebugCameraInputController<RenderSystem>* m_DebugCameraInputController;
std::list<ComponentWrapper> m_CameraComponents;
EntityWrapper m_CurrentCamera = EntityWrapper::Invalid;
EntityWrapper m_LocalPlayer = EntityWrapper::Invalid;
EventRelay<RenderSystem, Events::SetCamera> m_ESetCamera;
bool OnSetCamera(const Events::SetCamera &event);
EntityID m_CurrentCamera = EntityID_Invalid;
void switchCamera(EntityID entity);
void updateCamera(World* world, double dt);
void updateProjectionMatrix(ComponentWrapper& cameraComponent);
void fillModels(std::list<std::shared_ptr<RenderJob>>& jobs, World* world);
void fillLight(std::list<std::shared_ptr<RenderJob>>& jobs, World* world);
bool OnSetCamera(Events::SetCamera &event);
void fillText(std::list<std::shared_ptr<RenderJob>>& jobs, World* world);
void fillPointLights(std::list<std::shared_ptr<RenderJob>>& jobs, World* world);
void fillDirectionalLights(std::list<std::shared_ptr<RenderJob>>& jobs, World* world);
EventRelay<RenderSystem, Events::InputCommand> m_EInputCommand;
bool OnInputCommand(const Events::InputCommand& e);
void fillModels(std::list<std::shared_ptr<RenderJob>>& jobs);
void fillLight(std::list<std::shared_ptr<RenderJob>>& jobs);
EventRelay<RenderSystem, Events::PlayerSpawned> m_EPlayerSpawned;
bool OnPlayerSpawned(Events::PlayerSpawned& e);
};
#endif
+15 -9
View File
@@ -11,20 +11,23 @@
#include "FrameBuffer.h"
#include "../Core/World.h"
#include "PickingPass.h"
#include "DrawScenePass.h"
#include "LightCullingPass.h"
#include "DrawFinalPass.h"
#include "DrawScreenQuadPass.h"
#include "DrawBloomPass.h"
#include "DrawColorCorrectionPass.h"
#include "../Core/EventBroker.h"
#include "ImGuiRenderPass.h"
#include "Camera.h"
#include "../Core/Transform.h"
#include "imgui/imgui.h"
#include "TextPass.h"
class Renderer : public IRenderer
{
public:
Renderer(EventBroker* eventBroker, World* world)
Renderer(EventBroker* eventBroker)
: m_EventBroker(eventBroker)
, m_World(world)
{ }
virtual void Initialize() override;
@@ -36,7 +39,7 @@ public:
private:
//----------------------Variables----------------------//
EventBroker* m_EventBroker;
World* m_World;
TextPass* m_TextPass;
Texture* m_ErrorTexture;
Texture* m_WhiteTexture;
@@ -45,11 +48,15 @@ private:
Model* m_UnitQuad;
Model* m_UnitSphere;
DrawScenePass* m_DrawScenePass;
int m_DebugTextureToDraw = 0;
PickingPass* m_PickingPass;
LightCullingPass* m_LightCullingPass;
ImGuiRenderPass* m_ImGuiRenderPass;
DrawFinalPass* m_DrawFinalPass;
DrawScreenQuadPass* m_DrawScreenQuadPass;
DrawBloomPass* m_DrawBloomPass;
DrawColorCorrectionPass* m_DrawColorCorrectionPass;
//----------------------Functions----------------------//
void InitializeWindow();
@@ -59,14 +66,13 @@ private:
//TODO: Renderer: Get InputUpdate out of renderer
void InputUpdate(double dt);
//void PickingPass(RenderQueueCollection& rq);
void DrawScreenQuad(GLuint textureToDraw);
//void DrawScreenQuad(GLuint textureToDraw);
static bool DepthSort(const std::shared_ptr<RenderJob> &i, const std::shared_ptr<RenderJob> &j) { return (i->Depth < j->Depth); }
void FillDepth(RenderScene& scene);
void SortRenderJobsByDepth(RenderScene &scene);
void GenerateTexture(GLuint* texture, GLenum wrapping, GLenum filtering, glm::vec2 dimensions, GLint internalFormat, GLint format, GLenum type);
//--------------------ShaderPrograms-------------------//
ShaderProgram* m_BasicForwardProgram;
ShaderProgram* m_DrawScreenQuadProgram;
ShaderProgram* m_BasicForwardProgram;
};
#endif
+58
View File
@@ -0,0 +1,58 @@
#ifndef TextJob_h__
#define TextJob_h__
#include <cstdint>
#include "../Common.h"
#include "../GLM.h"
#include "../Core/ComponentWrapper.h"
#include "Texture.h"
#include "RenderJob.h"
#include "../Core/ResourceManager.h"
#include "Font.h"
struct TextJob : RenderJob
{
TextJob(glm::mat4 matrix, Font* font, ComponentWrapper textComponent)
: RenderJob()
{
Matrix = matrix;
Color = (glm::vec4)textComponent["Color"];
Content = (std::string)textComponent["Content"];
Resource = font;
if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Left")) {
Alignment = AlignmentEnum::Left;
} else if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Right")) {
Alignment = AlignmentEnum::Right;
} else if ((int)textComponent["Alignment"] == textComponent["Alignment"].Enum("Center")) {
Alignment = AlignmentEnum::Center;
} else {
LOG_ERROR("Text alignment invalid");
Alignment = AlignmentEnum::Left;
}
};
enum class AlignmentEnum
{
Left,
Right,
Center
};
glm::mat4 Matrix;
glm::vec4 Color;
std::string Content;
Font* Resource;
AlignmentEnum Alignment;
void CalculateHash() override
{
Hash = 0;
}
};
#endif
+33
View File
@@ -0,0 +1,33 @@
#ifndef TextRenderer_h__
#define TextRenderer_h__
#include <ft2build.h>
#include FT_FREETYPE_H
#include "../OpenGL.h"
#include "../GLM.h"
#include "ShaderProgram.h"
#include "Font.h"
#include "../Core/ResourceManager.h"
#include "RenderQueue.h"
#include "TextPassState.h"
#include "FrameBuffer.h"
class TextPass
{
public:
TextPass();
void Initialize();
void Update();
void Draw(RenderScene& scene, FrameBuffer& frameBuffer);
private:
void renderText(std::string text, Font* font, TextJob::AlignmentEnum alignment, glm::vec4 color, glm::mat4 modelMatrix, glm::mat4 projectionMatrix, glm::mat4 viewMatrix);
Font* font;
GLuint VAO, VBO;
ShaderProgram* m_TextProgram;
};
#endif
+15
View File
@@ -0,0 +1,15 @@
#ifndef TextPassState_h__
#define TextPassState_h__
#include "Rendering/RenderState.h"
class TextPassState : public RenderState
{
public:
TextPassState(GLuint frameBuffer);
~TextPassState();
private:
};
#endif
+1
View File
@@ -18,6 +18,7 @@ public:
void Bind(GLenum textureUnit = GL_TEXTURE0);
GLuint m_Texture = 0;
};
#endif
@@ -0,0 +1,17 @@
#ifndef CommonFuntions_h__
#define CommonFuntions_h__
#include "../../Common.h"
#include "../../OpenGL.h"
#include "../../GLM.h"
class CommonFuntions
{
public:
CommonFuntions() = delete;
private:
};
#endif
+18
View File
@@ -0,0 +1,18 @@
#ifndef ESpawnerSpawn_h__
#define ESpawnerSpawn_h__
#include "Core/Event.h"
#include "Core/EntityWrapper.h"
namespace Events
{
struct SpawnerSpawn : Event
{
EntityWrapper Spawner;
EntityWrapper Parent;
};
}
#endif
+5 -3
View File
@@ -14,13 +14,13 @@
#include "Core/EKeyDown.h"
#include "Core/EntityFilePreprocessor.h"
#include "Core/SystemPipeline.h"
#include "RaptorCopterSystem.h"
#include "PlayerSystem.h"
#include "Editor/EditorSystem.h"
#include "Core/EntityFile.h"
#include "Rendering/RenderSystem.h"
#include "Core/EntityFileParser.h"
#include "Core/Octree.h"
#include "Rendering/Font.h"
#include "Systems/InterpolationSystem.h"
// Network
#include <boost/thread.hpp>
#include "Network/Network.h"
@@ -48,6 +48,8 @@ private:
InputProxy* m_InputProxy;
GUI::Frame* m_FrameStack;
World* m_World;
Octree<AABB>* m_OctreeCollision;
Octree<AABB>* m_OctreeFrustrumCulling;
SystemPipeline* m_SystemPipeline;
RenderFrame* m_RenderFrame;
// Network variables
-33
View File
@@ -1,33 +0,0 @@
#ifndef PlayerSystem_h__
#define PlayerSystem_h__
#include <GLFW/glfw3.h>
#include <glm/common.hpp>
#include "Common.h"
#include "Core/System.h"
#include "Collision/ETrigger.h"
class PlayerSystem : public PureSystem
{
public:
PlayerSystem(EventBroker* eventBroker)
: PureSystem(eventBroker, "Player")
{
EVENT_SUBSCRIBE_MEMBER(m_ETouch, &PlayerSystem::OnTouch);
EVENT_SUBSCRIBE_MEMBER(m_EEnter, &PlayerSystem::OnEnter);
EVENT_SUBSCRIBE_MEMBER(m_ELeave, &PlayerSystem::OnLeave);
}
virtual void UpdateComponent(World* world, ComponentWrapper& player, double dt) override;
private:
float m_Speed = 5;
EventRelay<PlayerSystem, Events::TriggerEnter> m_EEnter;
bool OnEnter(const Events::TriggerEnter &event);
EventRelay<PlayerSystem, Events::TriggerTouch> m_ETouch;
bool PlayerSystem::OnTouch(const Events::TriggerTouch &event);
EventRelay<PlayerSystem, Events::TriggerLeave> m_ELeave;
bool PlayerSystem::OnLeave(const Events::TriggerLeave &event);
};
#endif
-16
View File
@@ -1,16 +0,0 @@
#include "Common.h"
#include "Core/System.h"
class RaptorCopterSystem : public PureSystem
{
public:
RaptorCopterSystem(EventBroker* eventBroker)
: PureSystem(eventBroker, "RaptorCopter")
{ }
virtual void UpdateComponent(World* world, ComponentWrapper& raptorCopter, double dt) override
{
ComponentWrapper& transform = world->GetComponent(raptorCopter.EntityID, "Transform");
(glm::vec3&)transform["Orientation"] += (float)(double)raptorCopter["Speed"] * (float)dt * (glm::vec3)raptorCopter["Axis"];
}
};
+55
View File
@@ -0,0 +1,55 @@
#ifndef CapturePointSystem_h__
#define CapturePointSystem_h__
#include <GLFW/glfw3.h>
#include <glm/common.hpp>
#include "Common.h"
#include "Core/System.h"
#include "Engine/Collision/ETrigger.h"
#include "Core/ECaptured.h"
#include "Core/EWin.h"
#include <tuple>
#include <vector>
class CapturePointSystem : public PureSystem
{
public:
//WARNING: on new map, destroy all info in the vectors, as well as reset all variables (just make new?)
CapturePointSystem(World* world, EventBroker* eventBroker);
//updatecomponent
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& capturePoint, double dt) override;
private:
//methods which will take care of specific events
EventRelay<CapturePointSystem, Events::TriggerTouch> m_ETriggerTouch;
bool CapturePointSystem::OnTriggerTouch(const Events::TriggerTouch& e);
EventRelay<CapturePointSystem, Events::TriggerLeave> m_ETriggerLeave;
bool CapturePointSystem::OnTriggerLeave(const Events::TriggerLeave& e);
EventRelay<CapturePointSystem, Events::Captured> m_ECaptured;
bool CapturePointSystem::OnCaptured(const Events::Captured& e);
bool m_WinnerWasFound = false;
//need to track these variables for the captureSystem to work as per design!
const int m_NotACapturePoint = 999;
int m_RedTeamNextPossibleCapturePoint = m_NotACapturePoint;
int m_BlueTeamNextPossibleCapturePoint = m_NotACapturePoint;
int m_RedTeamHomeCapturePoint = m_NotACapturePoint;
int m_BlueTeamHomeCapturePoint = m_NotACapturePoint;
int m_NumberOfCapturePoints = 0;
std::map<int, EntityID> m_CapturePointNumberToEntityIDMap;
//std::vector<ComponentWrapper>
const double m_CaptureTimeToTakeOver = 15.0;
bool m_ResetTimers = false;
//vectors which will keep track of enter/leave changes
std::vector<std::tuple<EntityID, EntityID>> m_ETriggerTouchVector;
std::vector<std::tuple<EntityID, EntityID>> m_ETriggerLeaveVector;
};
#endif
@@ -6,9 +6,9 @@
#include "Common.h"
#include "Core/System.h"
#include "Core\EPlayerDamage.h";
#include "Core\EPlayerHealthPickup.h";
#include "Core\EPlayerDeath.h";
#include "Core/EPlayerDamage.h"
#include "Core/EPlayerHealthPickup.h"
#include "Core/EPlayerDeath.h"
#include <tuple>
#include <vector>
@@ -16,10 +16,10 @@
class HealthSystem : public PureSystem
{
public:
HealthSystem(EventBroker* eventBroker);
HealthSystem(World* world, EventBroker* eventBroker);
//updatecomponent
virtual void UpdateComponent(World* world, ComponentWrapper& health, double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override;
private:
//methods which will take care of specific events
@@ -0,0 +1,53 @@
#ifndef Systems_InterpolationSystem_h__
#define Systems_InterpolationSystem_h__
#include <queue>
#include <unordered_map>
#include <boost/shared_array.hpp>
#include <glm/common.hpp>
#include <glm/gtc/quaternion.hpp>
#include "Common.h"
#include "Core/System.h"
#include "Core/EventBroker.h"
#include "Core/ResourceManager.h"
#include "Core/ConfigFile.h"
#include "Core/EPlayerSpawned.h"
#include "Network/EInterpolate.h"
class InterpolationSystem : public PureSystem
{
struct Transform
{
glm::vec3 Position;
glm::vec3 Scale;
glm::quat Orientation;
double interpolationTime;
};
public:
InterpolationSystem(World* world, EventBroker* eventBroker);
~InterpolationSystem() { }
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& transform, double dt) override;
private:
std::unordered_map<EntityID, Transform> m_NextTransform;
std::unordered_map<EntityID, Transform> m_LastReceivedTransform;
EntityWrapper m_LocalPlayer = EntityWrapper::Invalid;
//glm::vec3 vectorInterpolation(glm::vec3 prev, glm::vec3 next, double currentTime);
template <typename T>
T vectorInterpolation(T prev, T next, double currentTime)
{
T difference = next - prev;
T vector = (difference / m_SnapshotInterval) * static_cast<float>(currentTime);
return vector;
}
float m_SnapshotInterval;
EventRelay<InterpolationSystem, Events::Interpolate> m_EInterpolate;
bool InterpolationSystem::OnInterpolate(const Events::Interpolate& e);
EventRelay<InterpolationSystem, Events::PlayerSpawned> m_EPlayerSpawned;
bool OnPlayerSpawned(Events::PlayerSpawned& e);
};
#endif
@@ -0,0 +1,23 @@
#include "Common.h"
#include "GLM.h"
#include "Core/System.h"
#include "Core/EPlayerSpawned.h"
#include "Input/FirstPersonInputController.h"
#include <imgui/imgui.h>
class PlayerMovementSystem : public ImpureSystem, PureSystem
{
public:
PlayerMovementSystem(World* world, EventBroker* eventBroker);
~PlayerMovementSystem();
virtual void Update(double dt) override;
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt);
private:
// State
std::unordered_map<EntityWrapper, FirstPersonInputController<PlayerMovementSystem>*> m_PlayerInputControllers;
EventRelay<PlayerMovementSystem, Events::PlayerSpawned> m_EPlayerSpawned;
bool OnPlayerSpawned(Events::PlayerSpawned& e);
};
+31
View File
@@ -0,0 +1,31 @@
#include "Core/System.h"
#include "Input/EInputCommand.h"
#include "Systems/SpawnerSystem.h"
#include "Events/ESpawnerSpawn.h"
#include "Core/EPlayerSpawned.h"
#include "Rendering/ESetCamera.h"
#include "Core/ConfigFile.h"
class PlayerSpawnSystem : public ImpureSystem
{
public:
PlayerSpawnSystem(World* world, EventBroker* eventBroker);
virtual void Update(double dt) override;
private:
struct SpawnRequest
{
int PlayerID;
ComponentInfo::EnumType Team;
};
bool m_NetworkEnabled = false;
std::vector<SpawnRequest> m_SpawnRequests;
std::map<int, EntityWrapper> m_PlayerEntities;
EventRelay<PlayerSpawnSystem, Events::InputCommand> m_OnInputCommand;
bool OnInputCommand(const Events::InputCommand& e);
EventRelay<PlayerSpawnSystem, Events::PlayerSpawned> m_OnPlayerSpawnerd;
bool OnPlayerSpawned(Events::PlayerSpawned& e);
};
+17
View File
@@ -0,0 +1,17 @@
#include "Common.h"
#include "Core/System.h"
class RaptorCopterSystem : public PureSystem
{
public:
RaptorCopterSystem(World* world, EventBroker* eventBroker)
: System(world, eventBroker)
, PureSystem("RaptorCopter")
{ }
virtual void UpdateComponent(EntityWrapper& entity, ComponentWrapper& component, double dt) override
{
ComponentWrapper& transform = m_World->GetComponent(component.EntityID, "Transform");
(glm::vec3&)transform["Orientation"] += (float)(double)component["Speed"] * (float)dt * (glm::vec3)component["Axis"];
}
};
+25
View File
@@ -0,0 +1,25 @@
#ifndef SpawnerSystem_h__
#define SpawnerSystem_h__
#include <random>
#include "Common.h"
#include "GLM.h"
#include "Core/System.h"
#include "Events/ESpawnerSpawn.h"
#include "Core/Transform.h"
#include "Core/ResourceManager.h"
#include "Core/EntityFileParser.h"
class SpawnerSystem : public System
{
public:
SpawnerSystem(World* world, EventBroker* eventBroker);
static EntityWrapper Spawn(EntityWrapper spawner, EntityWrapper parent = EntityWrapper::Invalid);
private:
EventRelay<SpawnerSystem, Events::SpawnerSpawn> m_OnSpawnerSpawn;
bool OnSpawnerSpawn(Events::SpawnerSpawn& e);
};
#endif
+38
View File
@@ -0,0 +1,38 @@
#ifndef WeaponSystem_h__
#define WeaponSystem_h__
//#include <GLFW/glfw3.h>
//#include <glm/common.hpp>
#include "Rendering/IRenderer.h"
#include "Common.h"
#include "Core/System.h"
#include "Core/EPlayerDamage.h"
#include "Core/EShoot.h"
#include "Input/EInputCommand.h"
#include <tuple>
#include <vector>
class WeaponSystem : public ImpureSystem
{
public:
WeaponSystem(World* world, EventBroker* eventBroker, IRenderer* renderer);
virtual void Update(double dt) override;
private:
//methods which will take care of specific events
EventRelay<WeaponSystem, Events::Shoot> m_EShoot;
bool WeaponSystem::OnShoot(const Events::Shoot& e);
EventRelay<WeaponSystem, Events::InputCommand> m_EInputCommand;
bool WeaponSystem::OnInputCommand(const Events::InputCommand& e);
IRenderer* m_Renderer;
std::vector<std::tuple<EntityID, glm::vec2>> m_EShootVector;
};
#endif
+8 -1
View File
@@ -1,11 +1,13 @@
[Debug]
LogLevel=1
LoadMap=
EditorEnabled=false
; if true -> Pool allocation is not used when calling Allocate/Free, just use regular dynamic allocation.
; if false -> Use pool allocation.
DisableMemoryPool=false
[Editor]
CameraSpeed=3
[Video]
Fullscreen=false
VSYNC=false
@@ -19,6 +21,11 @@ IsServer=false
Name=Bob
Address=127.0.0.1
Port=13
MaxConnections=8
SnapshotInterval=0.05
SendInputIntervalMs=33
PingIntervalMs= 1000
TimeoutMs=15000
[Multithreading]
ResourceLoading=true
+4 -4
View File
@@ -6,10 +6,10 @@ InvertPitch=false
MouseLeft=PrimaryFire
MouseX=Yaw
MouseY=Pitch
W=+Forward
S=-Forward
D=+Right
A=-Right
W=Forward,1
S=Forward,-1
D=Right,1
A=Right,-1
R=Reload
Space=Jump
LeftControl=Crouch
+11 -1
View File
@@ -2,15 +2,25 @@
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" targetNamespace="components" elementFormDefault="qualified">
<xs:include schemaLocation="Components/Transform.xsd"/>
<xs:include schemaLocation="Components/Physics.xsd"/>
<xs:include schemaLocation="Components/Model.xsd"/>
<xs:include schemaLocation="Components/Test.xsd"/>
<xs:include schemaLocation="Components/RaptorCopter.xsd"/>
<xs:include schemaLocation="Components/Player.xsd"/>
<xs:include schemaLocation="Components/Text.xsd"/>
<xs:include schemaLocation="Components/Camera.xsd"/>
<xs:include schemaLocation="Components/AABB.xsd"/>
<xs:include schemaLocation="Components/PointLight.xsd"/>
<xs:include schemaLocation="Components/DirectionalLight.xsd"/>
<xs:include schemaLocation="Components/Trigger.xsd"/>
<xs:include schemaLocation="Components/Health.xsd"/>
<xs:include schemaLocation="Components/CapturePoint.xsd"/>
<xs:include schemaLocation="Components/Listener.xsd"/>
<xs:include schemaLocation="Components/SoundEmitter.xsd"/>
<xs:include schemaLocation="Components/Collidable.xsd"/>
<xs:include schemaLocation="Components/Spawner.xsd"/>
<xs:include schemaLocation="Components/SpawnPoint.xsd"/>
<xs:include schemaLocation="Components/PlayerSpawn.xsd"/>
<xs:include schemaLocation="Components/Team.xsd"/>
<xs:include schemaLocation="Components/UniformScale.xsd"/>
<xs:include schemaLocation="Components/EditorWidget.xsd"/>
</xs:schema>
+5 -4
View File
@@ -1,4 +1,5 @@
<c:AABB>
<BoxCenter X="0" Y="0" Z="0"/>
<BoxSize X="1" Y="1" Z="1"/>
</c:AABB>
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<AABB xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="AABB.xsd">
<Origin X="0" Y="0" Z="0"/>
<Size X="1" Y="1" Z="1"/>
</AABB>
+6 -2
View File
@@ -6,8 +6,12 @@
<xs:element name="AABB">
<xs:complexType>
<xs:all>
<xs:element name="BoxCenter" type="t:Vector" minOccurs="0"/>
<xs:element name="BoxSize" type="t:Vector" minOccurs="0"/>
<xs:element name="Origin" type="t:Vector" minOccurs="0">
<xs:annotation><xs:documentation>Middle point of the bounding box</xs:documentation></xs:annotation>
</xs:element>
<xs:element name="Size" type="t:Vector" minOccurs="0">
<xs:annotation><xs:documentation>Size of the bounding box</xs:documentation></xs:annotation>
</xs:element>
</xs:all>
</xs:complexType>
</xs:element>
+4 -4
View File
@@ -1,6 +1,6 @@
<c:Camera>
<Name>cam</Name>
<FOV>60.0</FOV>
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<Camera xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="Camera.xsd">
<FOV>45</FOV>
<NearClip>0.01</NearClip>
<FarClip>5000</FarClip>
</c:Camera>
</Camera>
+3 -2
View File
@@ -9,8 +9,9 @@
</xs:annotation>
<xs:complexType>
<xs:all>
<xs:element name="Name" type="t:string" minOccurs="0"/>
<xs:element name="FOV" type="t:double" minOccurs="0"/>
<xs:element name="FOV" type="t:double" minOccurs="0">
<xs:annotation><xs:documentation>Vertical Field of View in degrees</xs:documentation></xs:annotation>
</xs:element>
<xs:element name="NearClip" type="t:double" minOccurs="0"/>
<xs:element name="FarClip" type="t:double" minOccurs="0"/>
</xs:all>
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8" standalone="no" ?>
<CapturePoint xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="CapturePoint.xsd">
<CapturePointNumber>0</CapturePointNumber>
<CaptureTimer>0</CaptureTimer>
<HomePointForTeam><Spectator/></HomePointForTeam>
</CapturePoint>
@@ -0,0 +1,44 @@
<?xml version="1.0"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:t="types">
<xs:import schemaLocation="../Types.xsd" namespace="types"/>
<xs:complexType name="TeamEnum" mixed="true">
<xs:complexContent>
<xs:extension base="t:enum">
<xs:choice>
<xs:element name="Spectator" type="xs:integer" fixed="1" minOccurs="0"/>
<xs:element name="Red" type="xs:integer" fixed="2" minOccurs="0"/>
<xs:element name="Blue" type="xs:integer" fixed="3" minOccurs="0"/>
</xs:choice>
</xs:extension>
</xs:complexContent>
</xs:complexType>
<xs:element name="CapturePoint">
<xs:annotation>
<xs:documentation>A Capture Point. Add a Team Component to specify who currently owns it</xs:documentation>
</xs:annotation>
<xs:complexType>
<xs:all>
<xs:element name="CaptureTimer" type="t:double" minOccurs="0">
<xs:annotation>
<xs:documentation>CaptureTimer handled by Capture Point System</xs:documentation>
</xs:annotation>
</xs:element>
<xs:element name="CapturePointNumber" type="t:int" minOccurs="0">
<xs:annotation>
<xs:documentation>CapturePointNumber specify an int number for this</xs:documentation>
</xs:annotation>
</xs:element>
<xs:element name="HomePointForTeam" type="TeamEnum" minOccurs="0">
<xs:annotation>
<xs:documentation>Specify if this is a HomePoint for either team</xs:documentation>
</xs:annotation>
</xs:element>
</xs:all>
</xs:complexType>
</xs:element>
</xs:schema>

Some files were not shown because too many files have changed in this diff Show More