Compare commits

..
Author SHA1 Message Date
Tyler Blount 6b7fc0b6a3 Don't reset target restrictions during table load
Prevents an issue with load order causing target restrictions to be reset.
2020-05-20 14:45:24 -06:00
Tyler Blount 2e4bef0d09 Remove unneeded code and some style changes 2020-05-20 12:25:13 -06:00
Tyler Blount 172952cb0f Correctly implement fixes from #73 2020-05-20 12:25:13 -06:00
Tyler Blount 72c27bdbe8 CI and Lock fixes 2020-05-20 12:25:13 -06:00
Tyler Blount bd4de16007 Use correct comparison 2020-05-20 12:25:13 -06:00
Tyler Blount 2e560f2ddb Fix some CI errors 2020-05-20 12:25:12 -06:00
Tyler Blount d35d3d25f8 Finally fix no dumbfire
also some miscellaneous changes
2020-05-20 12:25:12 -06:00
Tyler Blount 2d5111f14b Perhaps this works? 2020-05-20 12:25:12 -06:00
Tyler Blount d95754d6b4 No Dumbfire fix
Another fix for MLMs associated with the No Dumbfire flag.
2020-05-20 12:25:12 -06:00
Tyler Blount 5e3d4c6cfd More fixes
Contains changes related to failed CI builds and feedback.
2020-05-20 12:25:12 -06:00
Tyler Blount deca820c9e Lost fixes
These were lost during a rebase at one point. Will leave this commit as separate to avoid issues in the future.
2020-05-20 12:25:12 -06:00
Swifty 21c298271b Initial commit of multilock missile features. 2020-05-20 12:25:11 -06:00
Goober5000 6ec28f6de5 Merge pull request #2389 from Goober5000/ai_goal_target_name_fix
make Goal_target_names dynamic
2020-05-19 23:27:40 -04:00
Goober5000 8667891fc2 use dynamic strings 2020-05-19 13:48:06 -04:00
Goober5000 5f74388790 add newline 2020-05-19 13:48:06 -04:00
Goober5000 067b250be9 make Goal_target_names dynamic
If ever there were more than 100 goal targets in a mission, the old version of ai_get_goal_target_name would start corrupting memory.  Rather than making a hacky workaround, this just makes it dynamic.
2020-05-19 13:48:06 -04:00
Goober5000 775984ae36 Merge pull request #2390 from Goober5000/xstr_revert
clean up handling of translated vs. untranslated English
2020-05-19 12:51:41 -04:00
Goober5000 3a7e604af9 Merge pull request #2401 from Goober5000/small_sexp_fix
make some debug code only run in debug
2020-05-19 12:50:19 -04:00
Goober5000 d4c429f3b1 Merge pull request #2394 from Goober5000/weapon_stats
Weapon statistics for comparison and extended descriptions
2020-05-19 12:49:35 -04:00
Goober5000 933f20efaa Merge pull request #2392 from Goober5000/modify_weapons_loadout_check
modify weapons loadout check
2020-05-19 12:48:59 -04:00
m!m 6ca29a79ba Merge pull request #2400 from asarium/build/clangReadability
Enable sensible clang readability checks
2020-05-19 17:04:29 +02:00
Goober5000 498e5ef42e make some debug code only run in debug
This code is highly inefficient (find_parent_operator() is O(n) for Num_sexp_nodes, and it runs every frame for all sexps with negative values) and should not actually be necessary.  But it is useful as a debug tool, so I added some #ifdef's.
2020-05-18 21:05:41 -04:00
asarium d29e236250 Enable sensible clang readability checks
This enables the clang readability checks that I found to be sensible. I
disabled a few that would have caused a lot of unnecessary warnings in
our code.
2020-05-18 20:57:19 +02:00
Goober5000 880005f758 or this 2020-05-16 14:22:46 -04:00
Goober5000 ec1a35f624 better variable name 2020-05-16 14:22:46 -04:00
Goober5000 575573334b modify weapons loadout check
Based on feedback, this PR now allows gaps in weapon loadouts, but if any gaps exist they must come at the bottom.
2020-05-16 14:22:46 -04:00
Goober5000 82b9a392e1 fix CI thing 2020-05-16 14:22:00 -04:00
Goober5000 ab2a2d46d6 make cmdline-friendly 2020-05-16 14:22:00 -04:00
Goober5000 b0f812b808 some fixes 2020-05-16 14:22:00 -04:00
Goober5000 7e8ffcec86 also list weapons whose base weapon is player-allowed 2020-05-16 14:22:00 -04:00
Goober5000 7a9bebecf6 fix multiplier based on new info 2020-05-16 14:22:00 -04:00
Goober5000 c005aa5ce2 tweak 2020-05-16 14:22:00 -04:00
Goober5000 1d00c296dd include additional missiles 2020-05-16 14:22:00 -04:00
Goober5000 dd4036d8df add useful comment 2020-05-16 14:22:00 -04:00
Goober5000 4b42829aa0 MVP weapon stats, and fix shockwave determination 2020-05-16 14:22:00 -04:00
Goober5000 7f8eaa275c weapon stats for spreadsheet 2020-05-16 14:22:00 -04:00
Goober5000 329fd023ec Merge pull request #2396 from Goober5000/2298_followup
revert the clang-tidy changes from #2298
2020-05-16 14:20:04 -04:00
Goober5000 2e0a84010e revert the clang-tidy changes from #2298
These are far too pedantic, and were not related to the feature in #2298 anyway.
2020-05-16 00:01:06 -04:00
Goober5000 9e0c37364c Merge pull request #2298 from asarium/feature/pureLuaScriptTable
Add capability to have a pure lua script
2020-05-15 15:39:46 -04:00
Goober5000 d83d1b41ee make clang happy 2020-05-15 15:34:54 -04:00
Goober5000 d26a12464c clean up handling of translated vs. untranslated English
Since the original release of FS2, internal strings have been translated to their English entries in strings.tbl but external strings have not been translated to their English entries in tstrings.tbl.  It appears that string translation was universal until it was disabled via a hack, probably due to FRED idiosyncrasies (see comment in `fred_init()`), and then not re-enabled for release.  PR #2343 re-enabled it, but this turned out to have undesirable side-effects since many mods used incorrect XSTR indexes for external strings.

This PR restores the previous behavior and also cleanly separates localization into translated and untranslated modes.  FRED will always run in untranslated mode.  FSO will run in translated mode for all languages except English, where it will run in untranslated mode UNLESS the new option `$Use tabled strings for the default language` is enabled in game_settings.tbl.
2020-05-14 19:19:52 -04:00
Goober5000 f80693213c Merge pull request #2387 from Goober5000/fix_improper_ai_get_goal_target_name
fix improper usage of ai_get_goal_target_name
2020-05-14 19:08:21 -04:00
Goober5000 dbc26548f5 Merge pull request #2377 from wookieejedi/fix-warp-flag-issues
Fix warp flag and code issues
2020-05-13 23:41:31 -04:00
Goober5000 1ef90d79c4 Apply suggestions from code review
some comment tweaks
2020-05-13 20:15:36 -04:00
Goober5000 caf3eaad98 fix improper usage of ai_get_goal_target_name
The ship goals dialog was incorrectly assigning a goal target name for every dockpoint, which could quickly cause the limit to be exceeded if the FREDder browsed a lot of dockpoints.

This also indicates a need to fix the goal target name system as the counter is never decremented.  That will be in a subsequent PR.
2020-05-13 03:05:17 -04:00
Goober5000 efbace48b8 Merge pull request #2332 from Goober5000/mantis_3147_flag
add an ai-profiles flag to govern the Mantis 3147 fix
2020-05-13 00:48:44 -04:00
Goober5000 d961fa1bb6 use mod_supports_version 2020-05-12 21:46:19 -04:00
Tyler Blount c6a999ab7a Merge pull request #2384 from TRBlount/fix/weapon_render_type
Make sure modular tables can overwrite weapon model info
2020-05-12 00:20:01 -06:00
wookieejedi 5df12322e5 Incorporate feedback 2020-05-11 18:05:21 -04:00
wookieejedi f7d474cb77 Merge branch 'master' into fix-warp-flag-issues 2020-05-11 16:35:37 -04:00
Tyler Blount 764a74dbd2 Make sure modular tables can overwrite weapon model info 2020-05-11 13:54:50 -06:00
Goober5000 1d471e254b Merge pull request #2342 from Goober5000/mantis_1947
implement Mantis 1947, treat ship comm systems the same as player comm systems
2020-05-10 15:36:45 -04:00
Goober5000 771d0c7a38 Merge pull request #2383 from wookieejedi/update-pow)-to-multiply
Update cases of pow(x,2) to just multiply values
2020-05-10 14:45:47 -04:00
wookieejedi 94bfb2fe75 Update cases of pow(x,2) to just multiply values
Having recalled that other SCP folks stated pow shoud not be used to do simple squaring, I figured it might be a good idea to update the two instances I found where that was the case.
2020-05-10 13:17:03 -04:00
Fabian Woltermann 8fd2813ddd Merge pull request #2382 from The-E/fix/particles_in_lab
do on-frame processing for particle effects in the lab
2020-05-10 17:38:11 +02:00
Fabian Woltermann a0180fc004 Init the particle system and use the correct frametime counter 2020-05-10 15:29:28 +02:00
Fabian Woltermann 7a6aa5334d do on-frame processing for particle effects in the lab 2020-05-10 13:20:18 +02:00
Goober5000 d8f388996d Merge pull request #2376 from The-E/feature/kill_ship_in_lab
Make explosions happen in the lab
2020-05-10 00:31:56 -04:00
wookieejedi da55499817 Merge pull request #2381 from wookieejedi/fix-texture-replace-with-showship
Fixes texture replace not working with show ship
2020-05-09 23:32:21 -04:00
wookieejedi e1dbcf4dd6 Add back in disabled check for future use of the engines ok function 2020-05-09 17:18:31 -04:00
wookieejedi cb5a1000a6 Fixes texture replace not working with show ship
This PR allows the `ship_render_show_ship_cockpit` function to properly detect replacement textures. Fortunately just a one line fix.
2020-05-09 15:48:34 -04:00
Fabian Woltermann 94bd8da5db Merge pull request #2373 from Goober5000/parse_tweaks
some code tweaks from an old branch
2020-05-09 20:21:01 +02:00
Fabian Woltermann 03926b8dde Merge pull request #2379 from The-E/fix/naked_int3_in_missionmessage
Remove naked int3() call in missionmessage
2020-05-09 18:44:18 +02:00
Fabian Woltermann 764bbac99f The original Volition code called Int3() here; since there is a way out that does not require us to crash, we should just not crash. 2020-05-09 10:43:13 +02:00
wookieejedi 280ff2d4f0 Incorporate feedback 2020-05-08 22:40:58 -04:00
wookieejedi 45775a0d97 One more update to the scripting function calls 2020-05-08 11:29:07 -04:00
wookieejedi c4d405e33e change to nullptr 2020-05-08 11:14:53 -04:00
wookieejedi 86e1ebaf08 fixed copy paste error with new script function 2020-05-08 10:34:20 -04:00
wookieejedi 82921467a5 Update ship.cpp 2020-05-08 09:58:35 -04:00
wookieejedi c2820f10c8 Updates and fixes multiple warp out related code 2020-05-08 09:53:32 -04:00
Goober5000 d52bddf0dc Merge pull request #2347 from EatThePath/disable-doublefire-take-2
Disable doublefire take 2
2020-05-08 02:01:40 -04:00
Fabian Woltermann cd88663a92 Avoid a signed/unsigned comparison 2020-05-08 07:56:08 +02:00
Goober5000 0e9a72a37b make clang happy 2020-05-07 21:57:18 -04:00
Fabian Woltermann 1c10479d2f Pause the AI while in the lab 2020-05-07 22:27:47 +02:00
David Gibson b88ccfb924 added an explanatory comment. Also reunited some related code I'd inadvertantly pushed apart, per review. 2020-05-07 15:09:19 -05:00
Fabian Woltermann 11e9fa27c6 REdo a few things 2020-05-07 22:00:19 +02:00
Fabian Woltermann f4f6e74456 Add new "Actions" window to the lab viewer and add a "Destroy Ship" action to make explosions happen 2020-05-07 21:35:25 +02:00
Fabian Woltermann de2e9ada72 WIP 2020-05-07 21:34:12 +02:00
Fabian Woltermann 4005a60b32 Merge pull request #2375 from The-E/fix/damage_lightning_in_lab
Make the lab's "show damage lightning" flag work again.
2020-05-07 21:31:48 +02:00
Fabian Woltermann 2e6306d85f Merge pull request #2374 from The-E/fix/texture_replacement_in_lab
Apply tabled texture replacements when loading ships in the F3 lab
2020-05-07 20:36:16 +02:00
Fabian Woltermann e1f231fcf0 Use the tabled max hull strength instead of a constant 2020-05-07 19:01:36 +02:00
Fabian Woltermann 86e898c9ea Use modern loops 2020-05-07 16:04:06 +02:00
Fabian Woltermann df1491fd9e Make the lab's "show damage lightning" flag work again.
Note that it may take a few frames for lightning to disappear when unchecking that checkbox.
2020-05-07 15:18:56 +02:00
Fabian Woltermann 0b8f203371 Apply tabled texture replacements when loading ships in the F3 lab 2020-05-07 14:48:14 +02:00
wookieejedi 1d152fcc73 Merge pull request #2371 from wookieejedi/on-depature-started-hook
Add `On Departure Started` Hook
2020-05-06 22:48:42 -04:00
Goober5000 c9fb046024 update header 2020-05-06 14:38:40 -04:00
Goober5000 c4b8020ebc some code tweaks from an old branch
Minor edits from an obsolete branch that are still useful in cleaning up the code.
2020-05-06 14:25:08 -04:00
wookieejedi a2c7a344da Add On Departure Started Hook
This PR adds a scripting hook which triggers when a ship begins it's departure process. It has one variable that is the ship. I have tested and it works as expected. This new hook is very useful for triggering events whenever a ship needs an alteration to it's departure methods. For example, in Fate of the Galaxy we require ships to warp out along a certain vector. This hook allows us to see when the ship is begining that depature and then break the ship's warp, order the ship to instead follow a waypoint path, and then jump out.
2020-05-06 09:25:10 -04:00
Goober5000 f8e5c9f7a3 Merge pull request #2343 from Goober5000/fix_mantis_2942
implement XSTR check as described in Mantis 2942
2020-05-05 22:28:20 -04:00
wookieejedi bebb69e28f Merge pull request #2369 from wookieejedi/pain-flash-hook
Adds `On Pain Flash` Scripting Hook
2020-05-05 16:59:45 -04:00
Goober5000 aef4c1ba3c address feedback 2020-05-05 14:38:50 -04:00
Goober5000 801a6031e3 Merge pull request #2367 from Goober5000/aiturret_fix
fix some code rot
2020-05-05 14:01:34 -04:00
Goober5000 4c573e2989 Merge pull request #2368 from Goober5000/support_ship_override
add two useful cheat keys
2020-05-05 14:00:59 -04:00
wookieejedi aa4e300153 switch to correct hook type 2020-05-05 13:55:57 -04:00
wookieejedi 3695f0ff93 remove unneeded CHAPAINFLASH 2020-05-05 13:51:36 -04:00
wookieejedi 7dc38f7752 Update to new script format 2020-05-05 13:46:53 -04:00
Goober5000 5ab611a8b1 this reason is only applicable in debug builds 2020-05-05 12:08:22 -04:00
Goober5000 0577b69d69 address CI complaint 2020-05-05 11:48:46 -04:00
wookieejedi 6897024b29 Adds On Pain Flash Scripting Hook
This PR adds a scripting hook which triggers when the pain flash is shown. It has one variable that lists what type of flash was shown, shield with `Pain_Type == 0` and hull with `Pain_Type == 1` .  I have tested and it works as expected.
2020-05-05 10:03:48 -04:00
Fabian Woltermann ffd5fdc764 Merge pull request #2366 from wookieejedi/carry-glowmap-status
Updates glowmap settings for a ship to also apply to ship's cockpit
2020-05-05 10:21:53 +02:00
Goober5000 e985961ed5 add two useful cheat keys
`+Shift+R will enable or disable support ships

`+Shift+U will scan or unscan the targeted ship, or ship subsystem
2020-05-05 01:02:17 -04:00
Goober5000 89a722d41a placeholder for future feature implementation 2020-05-05 00:14:16 -04:00
Goober5000 3ca187127d move comment 2020-05-05 00:01:30 -04:00
Goober5000 35e67d4574 possibly fix some code rot 2020-05-04 23:33:06 -04:00
wookieejedi 8b7253cfc1 Updates glowmap settings for a ship to also apply to ship's cockpit
The sexps that activate and deactive glowmaps are very useful for ships, though previously the glowmap status was not passed to the ship's cockpit. This PR adds the ability for glowmap status to carry to this ship's cockpit (if it has one).
2020-05-04 22:07:49 -04:00
Goober5000 7ec425f341 Merge pull request #2345 from Goober5000/fix_mantis_2791
Fix mantis 2791
2020-05-04 20:27:29 -04:00
Goober5000 e4b2791c4e Merge pull request #2353 from Goober5000/support_ship_cleanup
clean up the support ship code a bit
2020-05-04 16:13:06 -04:00
Fabian Woltermann e5c2b76469 Merge pull request #2363 from The-E/fix/post_process_aa_cmdline
Unify the way post-process antialiasing is switched on
2020-05-04 22:12:39 +02:00
Goober5000 4c5bc1fa6c Merge pull request #2360 from Goober5000/fix_2335
fix issue 2335
2020-05-04 16:12:18 -04:00
Fabian Woltermann 857a622caa Make Travis happy 2020-05-04 21:29:53 +02:00
Fabian Woltermann bdc6145b2c Deprecates the -fxaa and -smaa cmdline parameters in favour of a more generalized -aa; This also ensures that the smaa render targets are always initialized. 2020-05-04 18:30:11 +02:00
wookieejedi 07ce8a9c70 Merge pull request #2362 from wookieejedi/fix-glowmap-explode-flag
Fix Glowmap flag not carrying over to final ship explosion
2020-05-04 07:35:36 -04:00
wookieejedi e42ed47c61 Previously if a ship's glowmaps were deactivated via sexp, then the glowmaps would reaactivie at the ship's final explosinos. This PR fixes that by carrying that flag into the ship explosion FX code.
Previously if a ship's glowmaps were deactivated via sexp, then the glowmaps would reaactivie at the ship's final explosinos. This PR fixes that by carrying that flag into the ship explosion FX code.
2020-05-03 23:36:42 -04:00
Goober5000 ce3b9b62b1 Merge pull request #2336 from Goober5000/hotkey_fixes
add +Hotkey Team: to override IFF designation in hotkey list
2020-05-03 17:29:35 -04:00
Goober5000 794863c5e7 Merge pull request #2348 from Goober5000/mantis_2867
bring save format up to date (Mantis 2867)
2020-05-03 15:42:48 -04:00
asarium 544029f66f Add capability to have a pure lua script
This adds the capability to have a Lua script that does not need to use
our table syntax at all but instead defines the hooks by calling API
functions. This also makes it possible to add hook functions at runtime
if the script requires that.

Also clean up some unused debug stuff.
2020-05-03 14:33:42 +02:00
Goober5000 38e04b6151 Merge pull request #2354 from Goober5000/cue_voice_tweak
add overlooked generic file
2020-05-02 16:48:56 -04:00
Goober5000 3c76cc6524 add overlooked generic file
It turns out that the extant placeholder wav has an underscore in the filename, so add that to the list.
2020-05-02 13:54:13 -04:00
niffiwan 3c7f73f4d8 Merge pull request #2349 from Goober5000/allow_empty_weapons_on_locked_ships
allow empty weapons on locked ships
2020-05-02 20:01:23 +10:00
Fabian Woltermann 5366073356 Merge pull request #2358 from The-E/fix/aa_shader_unloading
A followup to the recent SMAA fixes
2020-05-01 13:30:56 +02:00
Fabian Woltermann 23fbdf7e64 Clean up the aa shader loading/unloading code to handle cases where we switch between FXAA and SMAA correctly 2020-05-01 10:55:20 +02:00
Goober5000 5135cded94 Merge pull request #2357 from chief1983/datacorder
Use full path  in SFTP, unlike the FTP one this was modified from.
2020-04-30 22:42:12 -04:00
Cliff 519d1f59f8 Use full path in SFTP, unlike the FTP one this was modified from. 2020-04-30 16:02:03 -05:00
Fabian Woltermann b9be2ad85e Merge pull request #2356 from The-E/fix/smaa_presets
Fix bug in SMAA application
2020-04-30 13:05:58 +02:00
Fabian Woltermann 7121a3f748 Update the last_frame AA mode during cmdline parsing. 2020-04-30 11:08:25 +02:00
Fabian Woltermann 7439cf2cc3 wording 2020-04-30 10:57:54 +02:00
Fabian Woltermann 570dc5f3de Make sure the SMAA presets are actually passed to the shader stages and that the SMAA shader is recompiled at runtime if the preset changes. 2020-04-30 10:55:24 +02:00
Cliff Gordon 620fdbde08 Merge pull request #2352 from chief1983/datacorder
Fix Travis secure var declaration (use travis encrypt VAR='value')
2020-04-29 17:21:57 -05:00
Cliff fdb7e41ed4 Fix Travis secure var declaration (use travis encrypt VAR='value') 2020-04-29 14:32:08 -05:00
Goober5000 4cb3b393da clean up the support ship code a bit
Due to code rot, the support ship hull repair code was a bit more tangled than it should have been, so I tidied it up.  I also fixed a bug Sarn noticed where a support ship would think all subsystems were repaired if the hull repair rate was set to 0.
2020-04-29 01:39:18 -04:00
Goober5000 9c44e77da0 allow empty weapons on locked ships
As noticed in Discord, in loop1-2 some of your wingmen have missing weapons, but as the ships are locked it's impossible for the player to modify them.  These ships should not be part of the check.
2020-04-28 23:51:37 -04:00
Goober5000 d9d372121a missed one 2020-04-28 23:24:13 -04:00
Goober5000 f286363748 Merge pull request #2346 from EatThePath/ai_linkage_rot_cleanup
Set_primary_weapon_linkage cleanup as requested by Goober5000
2020-04-28 23:22:04 -04:00
Goober5000 6df90a8ec7 newline 2020-04-28 23:12:51 -04:00
Goober5000 289defdeff smol fix 2020-04-28 23:11:33 -04:00
Goober5000 a54ebc3114 bring save format up to date (Mantis 2867)
FSO-specific features should now all be properly marked off with checks for retail format.
2020-04-28 23:02:10 -04:00
David Gibson 4a5ff2860b now check doublefire validity flags before drawing doublefire HUD indicator 2020-04-28 16:06:20 -05:00
David Gibson f8f1b44405 Check doublefire flag validity before firing any missile 2020-04-28 14:50:33 -05:00
David Gibson f13faf4cba added new flags and flag loading for the doublefire disabling options 2020-04-28 13:57:44 -05:00
David Gibson 1520a21062 Code cleanup and rerodering in set_primary_weapon_linkage as requested by Goober5000 2020-04-28 13:02:47 -05:00
Fabian Woltermann cdc831b163 Merge pull request #2344 from chief1983/datacorder
Use datacorder in CI instead of fs2downloads
2020-04-28 16:34:25 +02:00
niffiwan 18718aee74 Merge pull request #2341 from wookieejedi/add_target_box_zoom
Adds Scaling for Target Box Models Separate from Techroom
2020-04-28 17:01:47 +10:00
Cliff c8a5ebe45c Since this is sftp now we don't need the alt ftp functionality. 2020-04-27 23:51:46 -05:00
Goober5000 9dd6bcf81d warn if there is a gap in the path sequence 2020-04-28 00:39:46 -04:00
Goober5000 3356edff2b warn if model paths do not have unique names 2020-04-28 00:16:06 -04:00
Goober5000 07acdde69a fix Mantis 2791
This is a pretty easy fix; sorry it took seven years!

Instead of firing an Int3() when a ship has no arrival paths, just log it and continue.  And change the upstream warnings, which should have been more visible, from WarningEx to Warning.
2020-04-27 23:43:45 -04:00
Cliff 29dd3e1057 Update Travis and AppVeyor CI to use our Datacorder account on FeralHosting instead of the swc.fs2downloads.com server, since it is having issues with uploads now. 2020-04-27 22:26:31 -05:00
Goober5000 c89ea8e8dd update test case 2020-04-27 23:22:34 -04:00
Goober5000 d6c1a3dec4 implement XSTR check as described in Mantis 2942
Certain mods provide their own tstrings.tbl, but this runs into trouble when you localize data meant for one mod using a tstrings.tbl meant for another mod.  See the Mantis ticket:
http://scp.indiegames.us/mantis/view.php?id=2942
and also the HLP post:
http://www.hard-light.net/forums/index.php?topic=85041.msg1716600#msg1716600

This PR adds an optional flag that will check the untranslated string against the "default language" translated string.  The two strings should be identical.  If they aren't, the code assumes there is a tstrings.tbl mismatch.

I modified the mission listing code to enable this check when localizing mission info (titles and descriptions), and to avoid adding the mission to the list if there is a mismatch.  Fortunately, I think mission listing is the only place where this bug is likely to happen.
2020-04-27 22:42:13 -04:00
Goober5000 30d41eff8b fix issue 2335
Modify the early-out condition to remain in the function if we still need to render a dumbfire lead indicator.

Fixes #2335.
2020-04-27 20:32:45 -04:00
Goober5000 cc39cfe6f2 don't send builtin messages for ships with damaged comms, and don't select them when looking for unsilenced ships either 2020-04-27 16:32:43 -04:00
wookieejedi bca6f95621 add first time checks and use copy by assignment 2020-04-27 13:16:14 -04:00
wookieejedi e2010aeda1 Adds Scaling for Target Box Models Seperate from Techroom
Currently `$Closeup_Pos:` and `$Closeup_Zoom:` control the camera zoom and position values for the techroom, briefing and HUD Target Box. Unfortunately, with very large ships this results in an issue, to fit the view of an entire big ship in the HUD Target Box the zoom and position must be set a certain way which results in the ship looking very far away when viewed in the techroom. This PR adds two new fields that control camera postion and zoom but only for the HUD Target Box, thus modders can now set values for both and have the ships look good in both the Techroom and HUD Target Box. The new hud target box values are optional, and if not specifed they default to the values for `$Closeup_Pos:` and `$Closeup_Zoom:` .
2020-04-27 10:25:15 -04:00
Goober5000 d0daa43ccf since the code assumes all subsystems are dead if the ship is dying, add some flag checks to allow death messages to play (and be scrambled appropriately) if we have the ai_profiles flag active 2020-04-27 02:30:42 -04:00
Goober5000 e0cd2806f8 move quick-abort checks to before message priority checking
From the comments:

	// Do some checks to see if we are actually going to play this message at all.  These checks have been moved above the
	// "if ( Num_messages_playing )" block because we don't want to cancel an existing message if we have nothing to replace it with.

Additionally, by not incrementing `Num_playing_messages` if the code skips to `all_done`, this prevents messages that aren't playing from delaying messages in the queue that are actually valid and should play.
2020-04-27 02:24:26 -04:00
Goober5000 4f026a66ab fix small bug where speech was stopped when it wasn't supposed to be 2020-04-27 02:17:42 -04:00
Goober5000 28df82a03f fix bug where scramble status overrode subystem status 2020-04-27 02:13:08 -04:00
Goober5000 06f1b7d872 fix some int/bool stuff 2020-04-26 18:16:08 -04:00
Goober5000 1dfe3a8d9f implement Mantis 1947 feature request
This adds an ai_profiles flag that checks comm systems for non-player ships.  If their comm system is damaged, they will not send messages and you will not be able to issue squadmsg orders.

See also:
http://scp.indiegames.us/mantis/view.php?id=1947
2020-04-26 18:08:28 -04:00
Goober5000 aa46ae6639 add version-specific enabling of bugfix flags 2020-04-26 17:13:13 -04:00
Fabian Woltermann 22f3463397 Merge pull request #2339 from TRBlount/fix/lab_bg_smaa
Small F3 lab fixes
2020-04-25 18:59:48 +02:00
Goober5000 283e1555ba Merge pull request #2340 from JohnAFernandez/vmd-expansion
Add an angles version of zero vector and identity matrix
2020-04-25 11:54:23 -04:00
JohnAFernandez fe8ce74037 Use a constant for declaring angles with no measure 2020-04-25 09:54:40 -04:00
JohnAFernandez c43fa8c9a8 Add an angles version of zero vector and identity matrix 2020-04-25 00:45:34 -04:00
Tyler Blount 5c7fce41f1 Some lab fixes 2020-04-23 23:51:30 -06:00
Fabian Woltermann 0985091f6a Merge pull request #2338 from wookieejedi/music-restart-fix
Reinstates necessary soundtrack function call on level load
2020-04-21 18:33:43 +02:00
wookieejedi 2da7c4e761 Reinstates necessary check for soundtrack on level load
This updates #2299 and restores the use of `event_music_level_start(-1)` in `freespace.cpp`. This call was removed in #2299 because it was thought to be redundant but removal of that call resulted in music not playing upon mission restarts. This PR restores that call and fixes that issue.
2020-04-21 11:00:49 -04:00
m!m 6f109508d0 Merge pull request #2322 from asarium/feature/hookDocumentation
Add extended scripting hook system
2020-04-19 11:28:35 +02:00
Goober5000 e84919fa88 Merge pull request #2331 from Goober5000/interval_msecs
allow intervals and chain delays to use milliseconds
2020-04-18 15:32:17 -04:00
Goober5000 684354c8bd Merge pull request #2334 from Goober5000/fix_2333
fix loading of capship custom weapons
2020-04-16 15:09:36 -04:00
Goober5000 c8b1f56a09 missed one 2020-04-16 13:37:36 -04:00
Goober5000 8cc9eb2352 change to bool, for great C++ justice 2020-04-16 13:20:39 -04:00
Goober5000 3d08119734 add +Hotkey Team: to override IFF designation in hotkey list
This is in response to Mantis 1424:
http://scp.indiegames.us/mantis/view.php?id=1424

Since retail, the hotkey lists have been determined based on what attacks the player.  Mod makers may want to change this, so this PR adds the following options:

Default - retail behavior
Friendly/Enemy (or Hostile) - display in the specified list regardless of who attacks whom
None - don't display in the hotkey list at all

This PR also slightly cleans up the hotkey list function with a small optimization and a few tweaky fixes for edge cases.
2020-04-15 13:47:11 -04:00
Goober5000 45c3ee0b3c this probably makes more sense 2020-04-14 23:52:14 -04:00
Goober5000 89eea8e5d3 this pilot-specific logic should only run for the Pilot subsystem 2020-04-14 23:32:02 -04:00
Goober5000 6f5e500a1e add an ai-profiles flag to govern the Mantis 3147 fix 2020-04-14 17:50:16 -04:00
Goober5000 32730fc362 Merge pull request #2330 from Goober5000/check_no_briefing
actually fix the weapon-bank check
2020-04-14 17:19:11 -04:00
Goober5000 1c8f07b012 allow intervals and chain delays to use milliseconds
This adds the titular feature, as well as FRED support.  There are also some associated minor UI fixes in FRED and some cleanup in missiongoals.cpp.  And "Event Flags" are now a thing in case we want to add any other flags in the future.
2020-04-14 16:28:57 -04:00
Goober5000 892f0a831a actually fix the weapon-bank check
Ships which do not have the maximum number of primary and secondary banks (3 and 4) will have gaps in the loadout slots, so be sure to only check the weapon slots that the ship class is actually equipped with.
2020-04-14 14:38:18 -04:00
Goober5000 6b573bdbf6 Merge pull request #2329 from Goober5000/check_no_briefing
add a missing edge case to the weapon bank check
2020-04-14 12:07:20 -04:00
Goober5000 0e9ad8623b Merge pull request #2323 from Goober5000/fix_2314
sanity check missing numeric sexp arguments
2020-04-14 11:51:37 -04:00
Goober5000 f5edccd98f add a missing edge case to the weapon bank check
Yet another obscure edge case from Aftermath: Reboot.  The FREDder ought not to create this situation in the first place, but if he does, don't enter an endless loop.
2020-04-14 02:49:08 -04:00
Goober5000 007e7118f2 Merge pull request #2327 from Goober5000/jump_node_hud_distance
use consistent jump node distances on HUD
2020-04-13 18:34:27 -04:00
Goober5000 ae41e355ac reduce duplicate code 2020-04-13 16:56:18 -04:00
Goober5000 43d51792f2 apply formatter 2020-04-13 16:56:18 -04:00
Goober5000 f739a3e5c1 fix clang complaint 2020-04-13 16:56:18 -04:00
Goober5000 33c3f556a4 sanity check missing numeric sexp arguments
In the SEXP parser, zero-length strings are valid, as are zero-length operators.  But zero-length numbers are interpreted as missing arguments, since their only syntactic separators are spaces and the parser skips over whitespace.  And in any case, zero-length numbers are not semantically valid anyway.  This PR adds a sanity check to intercept all zero-length numbers, as well as malformed numbers, and convert them to 0.

This fixes issue #2314.
2020-04-13 16:56:17 -04:00
Goober5000 490464b656 Merge pull request #2324 from Goober5000/fix_Mantis_3171
Fix Mantis 3171
2020-04-13 16:54:56 -04:00
Goober5000 d526300483 Merge pull request #2325 from Goober5000/fix_Mantis_2715
prevent player leaving the loadout screen with incomplete weapons
2020-04-13 14:59:01 -04:00
Goober5000 3f3b284dcf use consistent jump node distances on HUD
There is a special function, `hud_find_target_distance`, which is used in most places for target distance.  However it wasn't used for jump nodes in this location.

Incidentally, the player's target's distance is cached, and this distance will always be current for the target box, so we can use the cached value and save a function call.
2020-04-13 14:53:28 -04:00
Goober5000 e0992ed88e add qtfred support 2020-04-13 12:29:02 -04:00
Goober5000 3997237a11 bump XSTR_SIZE and add NOLINT 2020-04-13 11:50:04 -04:00
asarium 1c12349990 Add extended scripting hook system
This moves towards defining the hooks in the code module that executes
them. Also provides the API necessary for better documentation of hooks.
This only covers a few hooks as a test and demonstration of the new API.
If no issues are found with this it can be extended in the future.
2020-04-13 14:45:19 +02:00
Goober5000 5f10b68118 Merge pull request #2326 from fjelliott/improved-subsystem-box-rendering
Cleaned up code that renders subsystem target boxes. (Follow-up to #2315)
2020-04-13 02:02:26 -04:00
Frans Elliott 91edcc4b8c Added a comment to describe the mathematics of subobj_find_2d_bound.
Broke up the projection function to aid in clarity.
2020-04-12 23:43:12 -05:00
Frans Elliott 4139cd890c Cleaned up subsystem bounding box code. 2020-04-12 21:24:13 -05:00
Goober5000 8fa96aeaf3 prevent player leaving the loadout screen with incomplete weapons
This is the best way to address Mantis 2715.  I took a look at allowing empty banks in the course of working on PR #2318, and it was completely intractable.  But in order to prevent certain "funnies" such as violation of bank restrictions, it's a good idea to ensure all banks are populated.

This PR adds a new XSTR for a popup message, and incidentally adds another XSTR to a message that should have had one already but didn't.
2020-04-12 21:34:00 -04:00
Goober5000 282ca0b0dd fix Mantis 3171 2020-04-12 20:39:16 -04:00
Goober5000 d3b1871837 remove Asserts that never worked because they checked invalid iterators 2020-04-12 20:39:16 -04:00
Goober5000 6f7ca147dd Merge pull request #2318 from Goober5000/additional_weapon_fix
simplify and fix the subsystem weapon loading code
2020-04-11 11:49:28 -04:00
Goober5000 ee391940d2 simplify and fix the subsystem weapon loading code
If ships have less than their full allocation of weapons, the code is supposed to compact the array so that these weapons all appear at the beginning.  This is done for small ships (fighters and bombers), but was not done for capital ships.  There was also a lot of code duplication with small ships getting extra error checking than capital ships.  This commit removes the duplicate code, makes the error checking more robust, and incidentally fixes the weapon array compacting for capital ships.
2020-04-08 12:31:43 -04:00
Goober5000 23dbfa5655 Merge pull request #2319 from Goober5000/weapon_info_scripting_fix
fix yet another issue uncovered by vectorization
2020-04-08 12:30:26 -04:00
Goober5000 8f1f308591 fix yet another issue uncovered by vectorization 2020-04-07 23:31:16 -04:00
Goober5000 cc456855e5 Merge pull request #2317 from Goober5000/weapon_bugfixes
Weapon bugfixes
2020-04-07 13:57:13 -04:00
Goober5000 0853c5bf7a clean up these functions in the same way as the weapon cheat functions 2020-04-07 02:20:56 -04:00
Goober5000 96de072bff add a useful assertion 2020-04-07 02:20:41 -04:00
Goober5000 2f0f2d7669 prevent access of out-of-range weapons, and at the same time sync primary and secondary capacity calculations 2020-04-07 02:02:22 -04:00
Goober5000 1c5a361d50 Merge pull request #2315 from fjelliott/master
Force subsystem targetting reticle to be square, even on non-square aspect ratios.
2020-04-06 01:11:56 -04:00
Frans Elliott 44072c026c Force subsystem targetting reticle to be square, even on non-square aspect ratios. 2020-04-05 21:21:37 -05:00
MageKing17 8cb9d311d7 Merge pull request #2312 from JohnAFernandez/target-signature-rename
Clarify Variable Names
2020-03-30 11:47:04 -07:00
MageKing17 bdec29f247 Merge pull request #2308 from Goober5000/vasudan_cheat_tweak
improve detection of vasudan main hall for cheats
2020-03-30 11:38:34 -07:00
JohnAFernandez 4e1b366f9f Clarify Variable Names
Use target_net_signature when talking about net_signature, but leave it at target_signature when talking about ai.target_signature.
2020-03-29 08:02:16 -04:00
Fabian Woltermann de2d1ec602 Merge pull request #2311 from asarium/fix/2310
Fix wrong matrix function calls
2020-03-29 13:37:19 +02:00
asarium 50e365a66c Fix wrong matrix function calls
This was using the wrong functions which caused videos not to show up
properly. This fixes #2310.
2020-03-29 12:19:00 +02:00
Tyler Blount a954a04cf8 Merge pull request #2309 from JohnAFernandez/Fix-ADE-invalid-defaults
Make sure aip->net_signature always defaults to -1 for no target.
2020-03-28 00:16:20 -06:00
Tyler Blount 030bbeb622 Merge pull request #2306 from Goober5000/flyby_sounds_refactor
refactor parsing of flyby sounds to make them optional
2020-03-28 00:15:33 -06:00
JohnAFernandez 6b7df053fa Make sure aip->net_signature always defaults to -1 for no target.
Although not used very often, ai_info.target_signature should be set to -1 whenever no target is specified, just like everywhere else to make sure that the code is as predictable as possible.

(Found while trying to figure out why the heck would the Object update packet send this at all??)
2020-03-27 23:11:19 -04:00
Goober5000 b8c135d162 improve detection of vasudan main hall for cheats 2020-03-25 14:24:37 -04:00
Fabian Woltermann b067e1ac66 Merge pull request #2307 from Goober5000/lab_weapon_bugfix
fix small error in lab
2020-03-24 21:34:58 +01:00
Goober5000 eabead6d41 fix small error in lab 2020-03-24 01:02:50 -04:00
Goober5000 ec50baa9d1 okay then 2020-03-24 00:11:36 -04:00
Goober5000 66f7bc4f50 add newline at end of file 2020-03-23 21:00:02 -04:00
Goober5000 44b7d5a4bd refactor parsing of flyby sounds to make them optional 2020-03-23 20:27:28 -04:00
Goober5000 caebad7077 Merge pull request #2302 from Goober5000/xmt_remove
Xmt remove feature
2020-03-18 09:48:42 -04:00
Goober5000 0caa65a74f address feedback 2020-03-17 17:22:27 -04:00
Goober5000 ff05816e11 add parse blacklist 2020-03-15 20:31:28 -04:00
Goober5000 da326f31f6 additional tweaks after rebase 2020-03-15 17:52:34 -04:00
Goober5000 376a01e82b wip 2020-03-15 17:42:57 -04:00
Goober5000 dc2ce094fc wip 2020-03-15 17:39:21 -04:00
Goober5000 74a0346e0d Merge pull request #2301 from Goober5000/static_cast_tweak
add functions to remove the clutter of static casts for ship and weapon info vectors
2020-03-15 15:08:42 -04:00
Goober5000 3b0d20aaf2 fix clang complaint 2020-03-15 01:35:12 -04:00
Goober5000 a0951f4e28 derp 2020-03-15 00:28:07 -04:00
Goober5000 3da2b99144 maybe these need to be extern'd 2020-03-14 15:13:44 -04:00
Goober5000 c9df8a13f1 add functions to remove the clutter of static casts for ship and weapon info vectors 2020-03-14 13:02:12 -04:00
Goober5000 247d5c453c Merge pull request #2294 from Goober5000/weapon_info_vector
Turn Weapon_info into a vector
2020-03-14 12:30:45 -04:00
Goober5000 5b8e89f37d address feedback 2020-03-14 09:56:56 -04:00
Fabian Woltermann f6083b680a Merge pull request #2299 from The-E/fix/2296_actually_fix_2292
As it turns out, the soundtrack reset issue is a bit more complicated…
2020-03-12 20:29:33 +01:00
Goober5000 fde7fdd854 address feedback 2020-03-07 13:35:17 -05:00
Fabian Woltermann 64531798e7 As it turns out, the soundtrack reset issue is a bit more complicated than I initially thought. The force_soundtrack check I previously removed was apparently vital; without it, calling event_music_level_init() (which in actuality is used to start soundtrack playback!) will result in the music being stopped, as the current soundtrack is set to -1.
This PR refactors the function's name to something more indicative of what it actually does, and removes a call made to it from within freespace.cpp which, due to changes in how the soundtrack system works, is now redundant and doesn't actually do anything anymore.
2020-03-07 19:04:01 +01:00
m!m ecd1cfe59c Merge pull request #2297 from asarium/fix/monoSoundAssert
Fix assertion when playing downsampled sounds
2020-03-07 15:34:09 +01:00
asarium 638bcacb71 Fix assertion when playing downsampled sounds
The sound was passed the data from before the resampling took place so
it though it would be playing a stereo sound and rightly cause an
assertion. This fixes that by refreshing the properties after appliying
the resampling properties.
2020-03-07 13:30:30 +01:00
Fabian Woltermann 4fc82ba334 Merge pull request #2295 from Goober5000/fix_weapon_info_pointer
fix an incorrect optimization
2020-03-07 12:59:23 +01:00
Goober5000 7ebd00e6f5 another fix for CI 2020-03-06 15:48:50 -05:00
Goober5000 fc41984a75 yet another fix for CI 2020-03-06 14:28:39 -05:00
Goober5000 45b5399f08 another fix for CI 2020-03-06 14:03:33 -05:00
Goober5000 fe15752f5e another fix for CI 2020-03-06 12:53:08 -05:00
Goober5000 c0a7be50b4 fixes for CI 2020-03-06 12:23:40 -05:00
Goober5000 bb8fcd428e address feedback 2020-03-06 03:11:31 -05:00
Goober5000 641aa329a5 fix an incorrect optimization 2020-03-05 22:58:00 -05:00
Goober5000 d86332a9d9 fix references 2020-03-05 22:46:07 -05:00
Goober5000 d8e88c1644 oof 2020-03-05 22:31:13 -05:00
Goober5000 1926d3c341 oof, more changes 2020-03-05 20:49:16 -05:00
MageKing17 c502d9bdf7 Merge pull request #2293 from scp-fs2open/fix/2292_reset_soundtrack_index_on_mission_close
Reset the current soundtrack during mission shutdown
2020-03-05 17:02:07 -08:00
Goober5000 20835adef6 convert Weapon_info to a SCP_vector 2020-03-05 19:12:43 -05:00
Fabian Woltermann af5e834250 Also make sure that Current_soundtrack_num is reset whenever event_music_level_init is called 2020-03-05 20:34:00 +01:00
MageKing17 e9051933b9 Merge pull request #2291 from Goober5000/remove_cloakmap
remove CLOAKMAP
2020-03-05 11:21:03 -08:00
Fabian Woltermann bb48ea9c61 Reset the current soundtrack during mission shutdown 2020-03-05 20:15:20 +01:00
Goober5000 939be80c30 wip 2020-03-05 00:01:03 -05:00
Goober5000 732ada474b remove CLOAKMAP 2020-03-04 23:47:22 -05:00
Goober5000 23b5320ec4 Merge pull request #2289 from MageKing17/bugfix/fred-rc-version-refix
Restore fred.rc version fix.
2020-03-02 08:56:34 -05:00
Goober5000 e3f67146b1 Merge pull request #2290 from Goober5000/log_newline
add newlines to mprintf and nprintf
2020-03-02 08:55:24 -05:00
Goober5000 cacee6e5b8 a few more 2020-03-02 01:07:17 -05:00
Goober5000 90c6c91e4f add newlines to mprintf and nprintf 2020-03-02 00:51:58 -05:00
MageKing17 0748ac191c Restore fred.rc version fix.
PR #1514 made this change to avoid having to constantly update fred.rc with new FSO versions, but it was inadvertently reverted in commit 9ac97f24223a7446d4364acfdb451c90697d6577; this also reverts PR #2286, since that's a somewhat more hackish solution to the same problem.
2020-03-01 18:10:23 -08:00
Goober5000 98cb4b6400 Merge pull request #2287 from Goober5000/briefing_stage_1_based
change briefing stage hook to 1-based
2020-03-01 15:36:47 -05:00
m!m 48d1797009 Merge pull request #2288 from asarium/docker-buildOnTagPush
Build docker standalone image on tag push
2020-03-01 16:14:54 +01:00
asarium 50ea017e59 Build docker standalone image on tag push 2020-03-01 14:48:47 +01:00
m!m c42cd25b89 Merge pull request #2284 from asarium/build/makeFFmpegOptional
Make FFmpeg an optional requirement
2020-03-01 11:55:01 +01:00
Goober5000 75099171ef Merge pull request #2286 from Goober5000/fred2_version_small_fix
Fred2 version small fix
2020-02-29 21:57:12 -05:00
Goober5000 809d11e1a8 change to 1-based 2020-02-29 19:21:21 -05:00
Goober5000 dadc65178d update the version number 2020-02-29 13:45:26 -05:00
m!m 52b17c3f8a Merge branch 'master' into build/makeFFmpegOptional 2020-02-29 18:48:13 +01:00
Goober5000 28722d7402 update the version number 2020-02-29 12:34:46 -05:00
m!m bf4243c0b0 Merge pull request #2285 from asarium/docker/fixEventHandling
Fix standalone signal handling
2020-02-29 18:33:46 +01:00
m!m 9dd6d9c874 Merge pull request #2278 from asarium/feature/betterScriptingDeprecation
Improve error message for deprecated functions
2020-02-29 18:33:31 +01:00
m!m 53a3b2b1c7 Merge pull request #2279 from asarium/fix/docker_stuff
Add compile time option to enable logging in release builds
2020-02-29 18:20:26 +01:00
asarium 2dc2295a59 Make FFmpeg an optional requirement
This does some refactoring to make it possible to cimpile and run FSO
without needing to link to FFmpeg. Since that eliminates support for
cutscenes or sound this is mostly useful for running a standalone server
which has no need for this anyway.

This reduces the image size of the standalone Docker image to only 20MB
and also resolves any licensing issues that might have existed.
2020-02-29 17:24:56 +01:00
asarium 582c144cf7 Fix standalone signal handling
The standalone did not initialize SDL and so did not receive the quit
signal when it was sent SIGTERM or SIGINT. This fixes that by making the
standalone server just use the normal os initialization code.

Also includes some other code cleanup and some more logging to make it
more apparent in the log what is currently happening at standalone
startup.
2020-02-29 17:09:55 +01:00
m!m e32cadd06a Merge pull request #2280 from asarium/docker/standalone-image
Add Dockerfile for compiling minimal standalone image
2020-02-27 18:12:30 +01:00
asarium ed6ac7060e Add Dockerfile for compiling minimal standalone image
This adds a Dockerfile which compiles FSO for the alpine Linux
distribution and then creates a standalone image based on those
binaries. That sidesteps the problem that existed with trying to use the
AppImage binaries on that distribution.

This produces a much smaller image (78MB instead of 230MB) so it should
be a bit more managable. Building can be done like this:
docker build --build-arg build_type=FastDebug -t scpfs2open/fso-standalone -f docker/standalone/Dockerfile .
2020-02-26 20:01:31 +01:00
asarium 7029e4a10f Add compile time option to enable logging in release builds
This mostly meant for special docker standalone server builds where it
might be useful to have full release performance but also have the logs
available if necessary. This now always compiles the log statements but
enables or disables them with a constexpr so they should not appear in
actual release binaries.
2020-02-24 18:54:55 +01:00
m!m 4d2cf1d2e0 Merge pull request #2263 from asarium/vulkan/test
Add Vulkan instance and surface creation code
2020-02-23 17:52:56 +01:00
asarium d31b2a971b Improve error message for deprecated functions
This will provide a proper error message when such a function is called
that will mention the name of the function and that it is deprecated and
cannot be used anymore in the targetted engine version.
2020-02-23 16:40:54 +01:00
m!m 74cf0b839d Merge pull request #2276 from asarium/fix/docker_stuff
Add option for logging to stdout
2020-02-23 14:32:08 +01:00
asarium 7f286b726d Add option for logging to stdout
This will make it easier to get logs from FSO running in a docker
container since logging to stdout is the easiest solution there.

Also includes some other changes that will make this work better in
Docker containers.
2020-02-23 13:09:51 +01:00
Goober5000 b0da0ea404 Merge pull request #2272 from Goober5000/briefing_stage_hook
add scripting hook for briefing stage
2020-02-18 14:38:24 -05:00
Goober5000 ca301fdb04 small adjustments 2020-02-18 01:18:07 -05:00
Goober5000 04244ec1ee Merge pull request #2273 from asarium/fix/2269
Handle invalid standard deviation properly
2020-02-17 15:26:56 -05:00
asarium 84b15afa8a Handle invalid standard deviation properly
If anything less than or equal to 0 was specified it would trigger some
kind of an assert in the standard library since that is not a valid
value for a normal distribution. Now a parse warning is generated and a
safe default value is used.

This fixes #2269.
2020-02-17 13:52:25 +01:00
Goober5000 a7063152b7 add scripting hook for briefing stage 2020-02-17 00:58:56 -05:00
Goober5000 5f938169af Merge pull request #2271 from asarium/fix/2266_again
Actually fix shader compilation error
2020-02-16 16:17:03 -05:00
asarium 8763b06c77 Actually fix shader compilation error
And actually compile the shader this time to check if the changes
actually fixed the error.
2020-02-16 13:02:25 +01:00
m!m 90a97021f5 Merge pull request #2267 from asarium/fix/2266
Fix compilation error in shader
2020-02-11 22:00:55 +01:00
asarium 3c6015f6b0 Fix compilation error in shader 2020-02-11 18:05:18 +01:00
Cliff Gordon ca4fcc84ea Merge pull request #2252 from pkubaj/patch-1
Fix build on FreeBSD
2020-02-11 09:35:09 -06:00
Cliff Gordon 94e74cb15f Merge pull request #2264 from pkubaj/patch-2
Fix build on big-endian architectures
2020-02-11 09:32:30 -06:00
pkubaj 3daa819042 Fix build on some LE platforms
Some platforms don't like those variables being unused.
2020-02-11 13:58:26 +01:00
pkubaj 4bb31f4e1b Fix build on big-endian architectures
swap_bsp_data() and swap_sldc_data() use those.
2020-02-10 15:49:52 +01:00
pkubaj 87c5544b7b Change to SCP_BSD 2020-02-10 15:47:17 +01:00
pkubaj 4914c4a452 Change to SCP_BSD 2020-02-10 15:46:56 +01:00
pkubaj 0b33a44004 Change to SCP_BSD 2020-02-10 15:46:30 +01:00
pkubaj 1f98551b12 Change to SCB_BSD 2020-02-10 15:45:57 +01:00
Goober5000 463caecf03 Merge pull request #2262 from niffiwan/fix/issue2261
make small bombs appear smaller in hud targetbox
2020-02-09 14:24:49 -05:00
asarium 2f3f061e75 Add Vulkan instance and surface creation code
This adds a new graphics type for the Vulkan graphics API. All this does
is to create a vulkan instance and a presentation surface with the help
of SDL.
2020-02-09 17:06:21 +01:00
niffiwan 0c0c4ddaef make small bombs appear smaller in hud targetbox
Also cleaned up the code slightly, the factor variable was only used
when missile_view was false
2020-02-09 21:07:04 +10:00
m!m 3fb2f97b43 Merge pull request #2133 from asarium/feature/moreOptionsUI
Add more features for the new Options UI
2020-02-09 11:39:18 +01:00
Goober5000 66daf6ba24 Merge pull request #2259 from Goober5000/update_wiki_cmdling
bring cmdline listing up to date with wiki (update links etc)
2020-02-09 00:55:42 -05:00
asarium a13b503b83 Add more features for the new Options UI
The largest new feature is that it is now possible to include other
files into the RML by using the "include" tag. This is useful for making
markup files more modular.

Also added some more options for existing things (e.g. built-in detail
options).
2020-02-08 13:28:53 +01:00
Goober5000 43a29b4dec address feedback 2020-02-07 12:00:01 -05:00
niffiwan 1c2d8a3b47 Merge pull request #2257 from asarium/gr/genericUniformBlock
Add generic uniform block for low frequency data
2020-02-07 18:06:40 +10:00
MageKing17 aa0a1ae3ed Merge pull request #2253 from scp-fs2open/bump_version
Update Version to 20.1.0
2020-02-05 11:39:11 -08:00
Goober5000 1d12157a07 bring cmdline listing up to date with wiki (update links etc) 2020-02-02 15:46:50 -05:00
asarium ae026f83ca Add generic uniform block for low frequency data
This elimiates all of the remaining "old style" uniforms from our
shaders. This might not be optimal for all situations but I have
confirmed that it is at least not worse at the moment.
2020-02-01 19:18:14 +01:00
Goober5000 facf17a222 Merge pull request #2254 from Kiloku/master
Update changelog with 19.0.0 release
2020-01-29 14:08:46 -05:00
Kiloku bf99541c58 Merge pull request #2 from scp-fs2open/master
Update
2020-01-29 13:32:25 -03:00
Kiloku 34391ebe21 Update changelog with 19.0.0 release 2020-01-29 13:30:49 -03:00
Fabian Woltermann 93f71ec202 Merge pull request #2247 from asarium/gr/matrixUniforms
Use uniform blocks for matrices
2020-01-29 11:04:22 +01:00
m!m e504f6b59e Set minor version to 1
This should be a bit more consistent with how we did versioning before.
2020-01-28 21:29:09 +01:00
m!m 133821952f Update Version to 20.0.0 2020-01-28 21:21:36 +01:00
asarium d7602ec9d1 Disable MinGW in GitHub actions
It fails with the same message as Travis CI :(
2020-01-28 18:20:47 +01:00
asarium fe5dbeccaa Use uniform blocks for matrices
This is a generic way to get matrix data to shaders without using
(old-school) uniforms. This is another step towards more compatibility
with how new APIs (Vulkan) do things to increase the odds for a Vulkan
port at some point.
2020-01-28 18:20:47 +01:00
pkubaj d7e40d2bcc Fix build on FreeBSD
sys/socket.h is needed for AF_INET.
2020-01-28 16:31:23 +01:00
pkubaj 0251fd347f Fix build on FreeBSD
sys/socket.h is necessary for AF_INET.
2020-01-28 16:30:53 +01:00
pkubaj 1cce2d70a3 Fix build on FreeBSD
sys/socket.h is necessary for AF_INET.
2020-01-28 16:30:23 +01:00
pkubaj 68f5b7d524 Fix build on FreeBSD
FreeBSD is similar to Linux and MacOS here.
2020-01-28 16:28:45 +01:00
niffiwan 036d5ed780 Merge pull request #2244 from JohnAFernandez/More-Multi-Cleanup
CleanUp Unused Function
2020-01-28 19:58:09 +10:00
niffiwan c109562c40 Merge pull request #2251 from wookieejedi/fix-rtt-target-display
Fixes RTT Target Box Scaling
2020-01-28 19:56:24 +10:00
niffiwan 0334b3c287 Merge pull request #2249 from wookieejedi/fix-hasfilter-on-weapons-hud
Fix weapon names not filtering # in HUD gauge
2020-01-28 07:06:57 +10:00
wookieejedi 9039081fa7 formatting 2020-01-27 12:23:15 -05:00
wookieejedi 73a5ac7665 specify floats 2020-01-27 12:17:26 -05:00
wookieejedi 6c2e419825 Fixes RTT Target Box Scaling
It seems that when RTT for cockpits was added that the scaling of ships in the target box fell through the cracks. Properly specifying the `clip_aspect` fixes the issue. This PR fixes issue #2250.
2020-01-27 10:04:57 -05:00
wookieejedi c2c2042a38 remove unneeded string filtering 2020-01-27 08:33:41 -05:00
wookieejedi da08ba5932 remove unneeded line 2020-01-26 15:10:32 -05:00
wookieejedi bc14149e84 Fix weapon names not filtering # in HUD gauge
Weapon names with a `#` should not display text after that `#` in the HUD. For the most part this works, but there were a few cases this didn't (such as primaries using the weapon name). This PR fixes two spots that fell between the cracks.
2020-01-26 14:08:28 -05:00
Goober5000 6ceb2a276c Merge pull request #2243 from wookieejedi/allow-engine-wash-intensity
Allows Modders to Actually Use Engine Wash Intensity
2020-01-25 16:32:12 -05:00
m!m d8537843ab Merge pull request #1600 from asarium/opengl/persistentlyMappedBuffer
Add persistent buffer mapping support for uniform data
2020-01-25 21:44:47 +01:00
wookieejedi 539cad66e7 change placement and add reset values 2020-01-20 12:31:18 -05:00
JohnAFernandez b042b27310 Remove Another Unused Multi Function
This function used to help with the sequence number of packets, but that is now done in the object packet functions themselves.
2020-01-20 00:42:56 -05:00
JohnAFernandez 8ee447d8c2 CleanUp Unused Function
This function does not have any contents and should be removed.
2020-01-20 00:28:28 -05:00
wookieejedi 8a36fc138c Allows Modders to Actually Use Engine Wash Intensity
Previously, Engine Wash Intensity didn't actually do anything in the code. This adds a game table setting that let's modders specify to the game to actually take the intensity value into account when calculating engine wash effects.
2020-01-19 16:54:58 -05:00
asarium 0b2695e9e4 Some more security checks 2020-01-12 22:23:13 +01:00
asarium 362645ce27 Reformat code with clang-format 2020-01-12 12:57:00 +01:00
asarium 10ab4a00f5 Fix clang-tidy issues 2020-01-12 11:59:23 +01:00
asarium 5ce6c251ff Add persistent mapping support
Persistent buffer mapping is an OpenGL technique where the contents of a
buffer object are mapped to a persistent pointer instead of having to
map and unmap a buffer every time it is modified.

This decreases the overhead for updating data in a uniform buffer object
which now only consists of a memcpy and a flush call.
2020-01-12 11:59:23 +01:00
asarium a3651026b1 Improve how the engine handles uniform buffers
This is in preparation for using persistently mapped buffers for uniform
buffers. Since that functionality is not available in the OpenGL version
we are targetting I implemented a fall-back which simply uses
glBufferSubData.

I did a benchmark with these changes and there was no change in
performance to the current master version.
2020-01-12 11:59:23 +01:00
333 changed files with 91190 additions and 5589 deletions

No files matched your search

+16 -13
View File
@@ -1,25 +1,27 @@
---
Language: Cpp
Standard: Cpp11
# BasedOnStyle: LLVM
AccessModifierOffset: -2
AlignAfterOpenBracket: Align
AlignConsecutiveAssignments: true
AlignConsecutiveDeclarations: false
AlignEscapedNewlinesLeft: false
AlignEscapedNewlines: Left
AlignOperands: true
AlignTrailingComments: true
AllowAllParametersOfDeclarationOnNextLine: true
AllowShortBlocksOnASingleLine: false
AllowAllArgumentsOnNextLine: false
AllowShortBlocksOnASingleLine: Never
AllowShortCaseLabelsOnASingleLine: false
AllowShortFunctionsOnASingleLine: All
AllowShortIfStatementsOnASingleLine: false
AllowShortIfStatementsOnASingleLine: Never
AllowShortLoopsOnASingleLine: false
AlwaysBreakAfterDefinitionReturnType: None
AlwaysBreakAfterReturnType: None
AlwaysBreakBeforeMultilineStrings: false
AlwaysBreakTemplateDeclarations: true
BinPackArguments: true
BinPackParameters: true
AlwaysBreakTemplateDeclarations: Yes
BinPackArguments: false
BinPackParameters: false
BraceWrapping:
AfterClass: false
AfterControlStatement: false
@@ -50,15 +52,17 @@ ForEachMacros: [ foreach, Q_FOREACH, BOOST_FOREACH ]
IncludeBlocks: Regroup
IncludeCategories:
- Regex: '^(<.*\.(h|hh|hpp)>)$' # Includes of external libraries
Priority: 4
- Regex: '^(<.*>)$' # standard library includes (won't match deprecated C headers)
Priority: 5
- Regex: '^"[^/]*\.(h)"$' # Local includes
- Regex: '^(<.*>)$' # standard library includes (won't match deprecated C headers)
Priority: 6
- Regex: '^"globalincs\/.*\.h"$' # globalincs always come first
Priority: 1
- Regex: '^".*\.(h)"$' # standard engine includes
- Regex: '^"[^/]*\.(h)"$' # Local includes
Priority: 2
- Regex: '.*' # Catch all in case something is unhandled above
- Regex: '^".*\.(h)"$' # standard engine includes
Priority: 3
- Regex: '.*' # Catch all in case something is unhandled above
Priority: 4
IncludeIsMainRegex: '$'
IndentCaseLabels: false
IndentWidth: 4
@@ -93,8 +97,7 @@ SpacesInContainerLiterals: true
SpacesInCStyleCastParentheses: false
SpacesInParentheses: false
SpacesInSquareBrackets: false
Standard: Cpp11
TabWidth: 4
UseTab: ForIndentation
UseTab: ForContinuationAndIndentation
...
+13
View File
@@ -14,6 +14,17 @@ misc-*,\
-misc-static-assert,\
-misc-unused-parameters,\
-misc-non-private-member-variables-in-classes,\
readability-*,\
-readability-function-size,\
-readability-identifier-naming,\
-readability-implicit-bool-conversion,\
-readability-inconsistent-declaration-parameter-name,\
-readability-isolate-declaration,\
-readability-magic-numbers,\
-readability-named-parameter,\
-readability-qualified-auto,\
-readability-uppercase-literal-suffix,\
-readability-else-after-return,\
"
WarningsAsErrors: ''
HeaderFilterRegex: 'code/.*$|freespace2/.*$|qtfred/.*$|test/src/.*$|build/.*$'
@@ -23,5 +34,7 @@ CheckOptions:
value: 'assert,Assert,Assertion'
- key: 'modernize-use-emplace.ContainersWithPushBack'
value: 'std::vector;std::deque;std::list;SCP_vector;SCP_deque;SCP_list'
- key: 'readability-braces-around-statements.ShortStatementLines'
value: '4' # Avoid flagging simple if (...) return false; statements
...
+2
View File
@@ -0,0 +1,2 @@
/build
/.git
+4
View File
@@ -5,3 +5,7 @@ indent_style = tab
[*.sdr]
indent_style = tab
[*.{yml,yaml}]
indent_style = space
indent_size = 2
+1 -8
View File
@@ -76,15 +76,8 @@ jobs:
strategy:
matrix:
configuration: [Debug, Release]
compiler: [MSVC, MinGW]
compiler: [MSVC]
arch: [Win32, x64]
exclude:
- configuration: Debug
compiler: MinGW
arch: x64
- configuration: Release
compiler: MinGW
arch: x64
name: Windows
runs-on: windows-2019
steps:
@@ -0,0 +1,48 @@
name: Publish Standalone docker image
on:
push:
tags:
- '*'
jobs:
build_images:
strategy:
matrix:
configuration: [FastDebug, Release]
include:
- configuration: FastDebug
latest_tag: latest_debug
nightly_tag: nightly_debug
release_tag: release_debug
- configuration: Release
latest_tag: latest
nightly_tag: nightly
release_tag: release
fail-fast: false
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v1
name: Checkout
with:
submodules: true
- name: Docker login
run: echo ${{ secrets.DOCKER_ACCESSTOKEN }} | docker login -u ${{ secrets.DOCKER_USERNAME }} --password-stdin
- name: Docker build
run: docker build --build-arg build_type=${{ matrix.configuration }} -f docker/standalone/Dockerfile -t ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.latest_tag }} .
- name: Push latest tag
run: |
docker push ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.latest_tag }}
- name: Push nightly tag
if: contains(github.ref, 'refs/tags/nightly_')
run: |
docker tag ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.latest_tag }} ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.nightly_tag }}
docker push ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.nightly_tag }}
- name: Push release tag
if: contains(github.ref, 'refs/tags/release_')
run: |
docker tag ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.latest_tag }} ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.release_tag }}
docker push ${{ secrets.DOCKER_REPOSITORY }}:${{ matrix.release_tag }}
+1
View File
@@ -257,3 +257,4 @@ CMakeSettings.json
# This gets ignored by one of the rules above for some reason...
!/code/scripting/lua/LuaConvert.h
!/code/debugconsole/
!/docker/build
+3 -3
View File
@@ -36,9 +36,9 @@ env:
# These declarations set INDIEGAMES_USER and INDIEGAMES_PASSWORD for uploading nightly builds to the indiegames server
- secure: "lUuRu8XIi8MKNf1ebOfyC4iVEpPyASojJIDWXRo2bNqEF4ILAljXdkVeXeN6H5yKCHD52cxCNTtyePIG/o3p3QEuGSVud9bDS3D7LaQicLETGGrsw3l07U49gF2OKHXGopg0MzBbZUU9QmhoFTAe8t6PV9NDuEayYCheqvTqjZg="
- secure: "E/DHLYcPK/hBUqxBYYlUqp5sjgvIqY5A0qRHyQ4bmjsB+WB/Xx71bGCSiF7hk6lTxar1ZI1i5RAXXh9AIvNVaYAIdEOlCP+q3gvwCYuc5naZEKmkxlUCf0oEL4O9Fye93A/3VkFHuBdC1TGPYYf69m4W5r4367wWO9dPRIdWpJA="
# These declarations set FS2DOWNLOADS_USER and FS2DOWNLOADS_PASSWORD
- secure: "h6GbMX2jLsW1bS9fCM9fthOSJ1nfQQIRWi6EUH2p8u4NFLD5Bfi/C8JhQPKHUzyo3wvKkSHl+PsW7bgr1oXLusRwAur/dtv2N3imqvtbfIz305b00hZlsvbcYmQmUzQFSAdOGShK57JJ5aKQKccaUBP25KqB7Q+JaqBRdaMBS54="
- secure: "fUDAPAUUaaYZy8I4zU3SJ0JcK7aw4eb6eTdaEr7LyNyTMSfPgwY6P1MrbSQC0lJNQIUQ5ffjdxE5g7D7OYpoJF9L14ni4UY8t2QASt7kmpgcYihmjeuYy8FQXgmFG8CTxiWBPKTybZJ7voQcvIvRaNG7b2wM9PMfc5lRIondB6c="
# These declarations set DATACORDER_USER and DATACORDER_PASSWORD
- secure: "dpBH/dDN3bmU/NFlh+2v9isNx9wX0ocoRy+W+kBXRH32sosUGp26REhMqgVRpBNP5oxPBU8ic5bEogxAYWCB+0xUygBbkxAwyMPgoA34s0OXdTCY/ofw14ni8qqV2Ffy7fQJbP/jkMURyiMHx3kBTxNv3YjxKJqLnOuOMlQLpT8="
- secure: "tLMRBD1Ufp5iKNwlqPDVbbuczgusaXNoBJyAnPATpJq2YwlkW4j3PqP9rW5vd85+52xam2EOP20w9PoBR5J6FLdiXRu4Lf7yCEhSHFAgowVqQj8QcJpPlyXr90bM4emFGrGqpdxVwxyQ5AFhKwLuEZKsI14GYLN+UMEwpNCMing="
deploy:
- provider: releases
api_key:
+8
View File
@@ -117,6 +117,10 @@ option(FSO_INSTALL_DEBUG_FILES "Install some debug files (currently only PDB fil
option(ENABLE_COTIRE "Enable cotire for faster compilation. Enabled by default." ON)
option(FSO_RELEASE_LOGGING "Enable logging output for release builds" OFF)
OPTION(FSO_BUILD_WITH_FFMPEG "Enable the usage of FFmpeg for sound and custscenes" ON)
MARK_AS_ADVANCED(FORCE FSO_CMAKE_DEBUG)
MARK_AS_ADVANCED(FORCE FSO_BUILD_INCLUDED_LIBS)
MARK_AS_ADVANCED(FORCE FSO_USE_OPENALSOFT)
@@ -125,6 +129,8 @@ MARK_AS_ADVANCED(FORCE FSO_DEVELOPMENT_MODE)
MARK_AS_ADVANCED(FORCE FSO_FATAL_WARNINGS)
mark_as_advanced(FORCE FSO_INSTALL_DEBUG_FILES)
mark_as_advanced(FORCE ENABLE_COTIRE)
mark_as_advanced(FORCE FSO_RELEASE_LOGGING)
mark_as_advanced(FORCE FSO_BUILD_WITH_FFMPEG)
# Include cotire file from https://github.com/sakra/cotire/
include(cotire)
@@ -197,3 +203,5 @@ ENDIF()
message(STATUS "Building FSO tools: ${FSO_BUILD_TOOLS}")
message(STATUS "Building qtFRED: ${FSO_BUILD_QTFRED}")
message(STATUS "Fatal warnings: ${FSO_FATAL_WARNINGS}")
message(STATUS "Release logging: ${FSO_RELEASE_LOGGING}")
message(STATUS "With FFmpeg: ${FSO_BUILD_WITH_FFMPEG}")
+3 -2
View File
@@ -3,7 +3,7 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
## [19.0.0-RC1] - 2019-08-29 ([Thread](https://www.hard-light.net/forums/index.php?topic=95868.0))
## [19.0.0] - 2020-01-25 ([Thread](https://www.hard-light.net/forums/index.php?topic=96226.0))
### Meta
- With this release we decided to drop the "`3.Major_revision.Minor_revision`" versioning scheme in favor of a year based scheme since the Major and Minor versions did not have much meaning anymore. Instead the scheme will now be "`<year>.<number that is incremented every release>.0`". The last 0 is still there because some of our systems expect that. It will be gone at some point.
### Added
@@ -21,6 +21,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
- Model uniforms get sent to the GPU using uniform buffers for less overhead
- Various other minor changes
- Converted pilot files from custom binary format to JSON
- Replaced Blinn-Phong BRDF with GGX BRDF
### Fixed
- Refactored bitmap slot handling and removed the fixed upper limit on the number of bitmaps. No more bmpman corruption!
@@ -1993,4 +1994,4 @@ NOTE:
# generated by cvs2cl.pl
# cvs2cl.pl -r -S --utc -f ChangeLog2
```
```
+12 -14
View File
@@ -40,25 +40,23 @@ deploy:
NightlyBuild: true # deploy on nightly push only
- provider: FTP
protocol: ftp
host: swc.fs2downloads.com
username:
secure: EXg2ADoKzMduZF90ip2Q0g==
protocol: sftp
host: porphyrion.feralhosting.com
username:
secure: 36+bVD8eJgI0BVbi7TZ4zQ==
password:
secure: x0LL0uY9yBAQ7JTARhQ6AA==
folder: swc.fs2downloads.com/builds/nightly/$(VersionName)
beta: true
secure: CrzmDVca8AGG08iWPA1gOD4Ge06+wJ3rcBagBGclwYQ=
folder: www/datacorder.porphyrion.feralhosting.com/public_html/builds/nightly/$(VersionName)
on:
NightlyBuild: true # deploy on nightly push only
- provider: FTP
protocol: ftp
host: swc.fs2downloads.com
username:
secure: EXg2ADoKzMduZF90ip2Q0g==
protocol: sftp
host: porphyrion.feralhosting.com
username:
secure: 36+bVD8eJgI0BVbi7TZ4zQ==
password:
secure: x0LL0uY9yBAQ7JTARhQ6AA==
folder: swc.fs2downloads.com/builds/test/$(VersionName)
beta: true
secure: CrzmDVca8AGG08iWPA1gOD4Ge06+wJ3rcBagBGclwYQ=
folder: www/datacorder.porphyrion.feralhosting.com/public_html/builds/test/$(VersionName)
on:
TestBuild: true # deploy on test build push only
+4 -4
View File
@@ -77,13 +77,13 @@ cd /tmp/builds
for file in *; do
if [ "$TEST_BUILD" = true ]; then
# Upload to fs2downloads
curl -k "ftp://swc.fs2downloads.com/swc.fs2downloads.com/builds/test/$VERSION_NAME/" --user "$FS2DOWNLOADS_USER:$FS2DOWNLOADS_PASSWORD" -T "$file" --ftp-create-dirs
# Upload to datacorder
curl -k "sftp://porphyrion.feralhosting.com/www/datacorder.porphyrion.feralhosting.com/public_html/builds/test/$VERSION_NAME/" --user "$DATACORDER_USER:$DATACORDER_PASSWORD" -T "$file" --ftp-create-dirs
else
# Upload to indiegames
curl -k "sftp://scp.indiegames.us/~/public_html/builds/nightly/$VERSION_NAME/" --user "$INDIEGAMES_USER:$INDIEGAMES_PASSWORD" -T "$file" --ftp-create-dirs
# Upload to fs2downloads
curl -k "ftp://swc.fs2downloads.com/swc.fs2downloads.com/builds/nightly/$VERSION_NAME/" --user "$FS2DOWNLOADS_USER:$FS2DOWNLOADS_PASSWORD" -T "$file" --ftp-create-dirs
# Upload to datacorder
curl -k "sftp://porphyrion.feralhosting.com/~/www/datacorder.porphyrion.feralhosting.com/public_html/builds/nightly/$VERSION_NAME/" --user "$DATACORDER_USER:$DATACORDER_PASSWORD" -T "$file" --ftp-create-dirs
fi
done
+1 -1
View File
@@ -1,4 +1,4 @@
#!/bin/sh
HERE=$(dirname $(readlink -f "${0}"))
export LD_LIBRARY_PATH="${HERE}"/lib:"$LD_LIBRARY_PATH"
"${HERE}"/bin/$<TARGET_FILE_NAME:Freespace2> $@
exec "${HERE}"/bin/$<TARGET_FILE_NAME:Freespace2> $@
+1 -2
View File
@@ -8,8 +8,7 @@
#cmakedefine SCP_HAVE_MAX_ALIGN_T
#cmakedefine SCP_HAVE_STD_MAX_ALIGN_T
#cmakedefine SCP_HAVE_STD_IS_TRIVIALLY_COPYABLE
#cmakedefine SCP_HAVE_STD_IS_TRIVIALLY_COPYABLE_ARRAY
#cmakedefine01 HAVE_STD_IS_TRIVIALLY_COPYABLE
#cmakedefine01 IS_64BIT
+4 -4
View File
@@ -6,9 +6,9 @@ if (EXISTS "${PROJECT_SOURCE_DIR}/version_override.cmake")
include("${PROJECT_SOURCE_DIR}/version_override.cmake")
endif()
set_if_not_defined(FSO_VERSION_MAJOR 3)
set_if_not_defined(FSO_VERSION_MINOR 8)
set_if_not_defined(FSO_VERSION_BUILD 1)
set_if_not_defined(FSO_VERSION_MAJOR 20)
set_if_not_defined(FSO_VERSION_MINOR 1)
set_if_not_defined(FSO_VERSION_BUILD 0)
# A numeric revision e.g. the CI build number
set_if_not_defined(FSO_VERSION_REVISION 0)
@@ -49,4 +49,4 @@ IF (NOT "${FSO_BUILD_POSTFIX}" STREQUAL "")
ENDIF()
set(CONFIG_POSTFIX "$<$<CONFIG:Release>:>$<$<CONFIG:Debug>:-DEBUG>$<$<CONFIG:FastDebug>:-FASTDBG>")
set(FSO_BINARY_SUFFIX "${FSO_BINARY_SUFFIX}${CONFIG_POSTFIX}")
set(FSO_BINARY_SUFFIX "${FSO_BINARY_SUFFIX}${CONFIG_POSTFIX}")
+13 -1
View File
@@ -28,7 +28,9 @@ TARGET_LINK_LIBRARIES(code PUBLIC ${JPEG_LIBS})
TARGET_LINK_LIBRARIES(code PUBLIC sdl2)
TARGET_LINK_LIBRARIES(code PUBLIC ffmpeg)
if (FSO_BUILD_WITH_FFMPEG)
TARGET_LINK_LIBRARIES(code PUBLIC ffmpeg)
endif()
TARGET_LINK_LIBRARIES(code PUBLIC utfcpp)
@@ -43,6 +45,8 @@ target_link_libraries(code PUBLIC libRocket)
target_link_libraries(code PUBLIC pcp)
target_link_libraries(code PUBLIC vulkan-hpp)
enable_clang_tidy(code)
IF (FSO_USE_SPEECH)
@@ -79,6 +83,14 @@ else()
ENDIF()
endif()
if (FSO_RELEASE_LOGGING)
target_compile_definitions(code PUBLIC SCP_RELEASE_LOGGING)
endif()
if (FSO_BUILD_WITH_FFMPEG)
target_compile_definitions(code PUBLIC WITH_FFMPEG)
endif()
include(util)
configure_cotire(code)
+15 -13
View File
@@ -18,8 +18,7 @@
#include "ship/ship.h"
int Total_goal_target_names = 0;
char Goal_target_names[MAX_GOAL_TARGET_NAMES][NAME_LENGTH];
SCP_vector<char *> Goal_target_names;
ai_info Ai_info[MAX_AI_INFO];
ai_info *Player_ai;
@@ -82,22 +81,25 @@ void set_wingnum(int objnum, int wingnum)
Ai_info[ai_index].wing = wingnum;
}
char *ai_get_goal_target_name(const char *name, int *index)
const char *ai_get_goal_target_name(const char *name, int *index)
{
Assert(name != NULL);
Assert(index != NULL);
int i;
Assertion(name != nullptr && index != nullptr, "Arguments cannot be null!");
for (i=0; i < Total_goal_target_names; i++)
for (int i = 0; i < static_cast<int>(Goal_target_names.size()); ++i) {
if (!stricmp(name, Goal_target_names[i])) {
*index = i;
return Goal_target_names[i];
}
}
Assert(Total_goal_target_names < MAX_GOAL_TARGET_NAMES);
Assertion(strlen(name) <= NAME_LENGTH - 1, "Goal target name %s is too long. Needs to be 31 characters or less.", name);
i = Total_goal_target_names++;
strcpy_s(Goal_target_names[i], name);
*index = i;
return Goal_target_names[i];
*index = static_cast<int>(Goal_target_names.size());
Goal_target_names.push_back(vm_strdup(name));
return Goal_target_names[*index];
}
void ai_clear_goal_target_names()
{
for (auto ptr : Goal_target_names)
vm_free(ptr);
Goal_target_names.clear();
}
+5 -8
View File
@@ -83,7 +83,7 @@ typedef struct ai_goal {
fix time; // time at which this goal was issued.
int priority; // how important is this goal -- number 0 - 100
char *target_name; // name of the thing that this goal acts upon
const char *target_name; // name of the thing that this goal acts upon
int target_name_index; // index of goal_target_name in Goal_target_names[][]
waypoint_list *wp_list; // waypoints that this ship might fly.
int target_instance; // instance of thing this ship might be chasing (currently only used for weapons; note, not the same as objnum!)
@@ -93,19 +93,17 @@ typedef struct ai_goal {
// (AIGF_DOCKER_INDEX_VALID and AIGF_DOCKEE_INDEX_VALID tell us to use indexes; otherwise we use names)
// these are the dockpoints used on the docker and dockee ships, not the ships themselves
union {
char *name;
const char *name;
int index;
} docker;
union {
char *name;
const char *name;
int index;
} dockee;
} ai_goal;
#define MAX_GOAL_TARGET_NAMES 100
#define AIM_CHASE 0
#define AIM_EVADE 1
#define AIM_GET_BEHIND 2
@@ -513,8 +511,6 @@ typedef struct {
#define BURST_DURATION 500 // decay time over which Player->damage_this_burst falls from MAX_BURST_DAMAGE to 0
extern int Mission_all_attack; // !0 means all teams attack all teams.
extern int Total_goal_target_names;
extern char Goal_target_names[MAX_GOAL_TARGET_NAMES][NAME_LENGTH];
extern void update_ai_info_for_hit(int hitter_obj, int hit_obj);
extern void ai_frame_all(void);
@@ -556,7 +552,8 @@ void ai_process( object * obj, int ai_index, float frametime );
int get_wingnum(int objnum);
void set_wingnum(int objnum, int wingnum);
char *ai_get_goal_target_name(const char *name, int *index);
const char *ai_get_goal_target_name(const char *name, int *index);
void ai_clear_goal_target_names();
extern void init_ai_system(void);
extern void ai_attack_object(object *attacker, object *attacked, ship_subsys *ssp, int ship_info_index = -1);
+4
View File
@@ -84,13 +84,17 @@ namespace AI {
Assist_scoring_scales_with_damage,
Beams_damage_weapons,
Big_ships_can_attack_beam_turrets_on_untargeted_ships,
Check_comms_for_non_player_ships,
Disable_linked_fire_penalty,
Disable_player_secondary_doublefire,
Disable_ai_secondary_doublefire,
Disable_weapon_damage_scaling,
Dont_insert_random_turret_fire_delay,
Fix_ai_class_bug,
Fix_ai_path_order_bug,
Fix_heat_seeker_stealth_bug,
Fix_linked_primary_bug,
Fix_ramming_stationary_targets_bug,
Force_beam_turret_fov,
Free_afterburner_use,
Glide_decay_requires_thrust,
+28 -2
View File
@@ -7,11 +7,11 @@
#include "globalincs/pstypes.h"
#include "def_files/def_files.h"
#include "ai/ai_profiles.h"
#include "def_files/def_files.h"
#include "globalincs/pstypes.h"
#include "localization/localize.h"
#include "mod_table/mod_table.h"
#include "parse/parselo.h"
#include "ship/ship.h"
#include "weapon/weapon.h"
@@ -371,10 +371,16 @@ void parse_ai_profiles_tbl(const char *filename)
set_flag(profile, "$navigation subsystem governs warpout capability:", AI::Profile_Flags::Navigation_subsys_governs_warp);
set_flag(profile, "$check communications for non-player ships:", AI::Profile_Flags::Check_comms_for_non_player_ships);
set_flag(profile, "$ignore lower bound for minimum speed of docked ship:", AI::Profile_Flags::No_min_dock_speed_cap);
set_flag(profile, "$disable linked fire penalty:", AI::Profile_Flags::Disable_linked_fire_penalty);
set_flag(profile, "$disable player secondary doublefire:", AI::Profile_Flags::Disable_player_secondary_doublefire);
set_flag(profile, "$disable ai secondary doublefire:", AI::Profile_Flags::Disable_ai_secondary_doublefire);
set_flag(profile, "$disable weapon damage scaling:", AI::Profile_Flags::Disable_weapon_damage_scaling);
set_flag(profile, "$use additive weapon velocity:", AI::Profile_Flags::Use_additive_weapon_velocity);
@@ -391,6 +397,8 @@ void parse_ai_profiles_tbl(const char *filename)
set_flag(profile, "$fix linked primary weapon decision bug:", AI::Profile_Flags::Fix_linked_primary_bug);
set_flag(profile, "$fix ramming stationary targets bug:", AI::Profile_Flags::Fix_ramming_stationary_targets_bug);
set_flag(profile, "$prevent turrets targeting too distant bombs:", AI::Profile_Flags::Prevent_targeting_bombs_beyond_range);
set_flag(profile, "$smart subsystem targeting for turrets:", AI::Profile_Flags::Smart_subsystem_targeting_for_turrets);
@@ -624,4 +632,22 @@ void ai_profile_t::reset()
for (int i = 0; i <= MAX_DETAIL_LEVEL; ++i) {
detail_distance_mult[i] = 0;
}
// via Github #2332, enable bugfixes if we are targeting version 20 and up
if (mod_supports_version(20, 0, 0)) {
flags.set(AI::Profile_Flags::Huge_turret_weapons_ignore_bombs);
flags.set(AI::Profile_Flags::Fix_linked_primary_bug);
flags.set(AI::Profile_Flags::Prevent_targeting_bombs_beyond_range);
flags.set(AI::Profile_Flags::Fix_heat_seeker_stealth_bug);
flags.set(AI::Profile_Flags::Allow_vertical_dodge);
flags.set(AI::Profile_Flags::Fix_ai_class_bug);
flags.set(AI::Profile_Flags::Ai_guards_specific_ship_in_wing);
flags.set(AI::Profile_Flags::Fix_ai_path_order_bug);
flags.set(AI::Profile_Flags::Aspect_invulnerability_fix);
flags.set(AI::Profile_Flags::Use_actual_primary_range);
}
// this flag has been enabled ever since 3.7.2
if (mod_supports_version(3, 7, 2)) {
flags.set(AI::Profile_Flags::Fix_ramming_stationary_targets_bug);
}
}
+45 -24
View File
@@ -66,6 +66,7 @@
#include "ship/ship.h"
#include "ship/shipfx.h"
#include "ship/shiphit.h"
#include "ship/subsysdamage.h"
#include "weapon/beam.h"
#include "weapon/flak.h"
#include "weapon/swarm.h"
@@ -274,7 +275,7 @@ typedef struct {
int team;
int weapon_index;
int max_fire_count;
char *shipname;
const char *shipname;
} huge_fire_info;
SCP_vector<huge_fire_info> Ai_huge_fire_info;
@@ -4652,7 +4653,7 @@ void ai_fly_to_ship()
{
if (aip->mode == AIM_FLY_TO_SHIP || aip->goals[i].ai_mode == AI_GOAL_FLY_TO_SHIP)
{
mprintf(("Ship '%s' told to fly to target ship '%s'",
mprintf(("Ship '%s' told to fly to target ship '%s'\n",
Ships[Pl_objp->instance].ship_name,
aip->goals[i].target_name));
}
@@ -5226,7 +5227,7 @@ static int ai_select_primary_weapon_OLD(const object *objp, Weapon::Info_Flags f
ship *shipp = &Ships[objp->instance];
ship_weapon *swp = &shipp->weapons;
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < ship_info_size());
if (flags == Weapon::Info_Flags::Puncture) {
if (swp->current_primary_bank >= 0) {
@@ -5315,7 +5316,7 @@ int ai_select_primary_weapon(object *objp, object *other_objp, Weapon::Info_Flag
return ai_select_primary_weapon_OLD(objp, flags);
}
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < ship_info_size());
//made it so it only selects puncture weapons if the active goal is to disable something -Bobboau
if ((flags == Weapon::Info_Flags::Puncture) && (Ai_info[shipp->ai_index].goals[0].ai_mode & (AI_GOAL_DISARM_SHIP | AI_GOAL_DISABLE_SHIP)))
@@ -5506,33 +5507,35 @@ void set_primary_weapon_linkage(object *objp)
weapon_info *wip;
shipp = &Ships[objp->instance];
if (Num_weapons > (int) (MAX_WEAPONS * 0.75f)) {
if (shipp->flags[Ship::Ship_Flags::Primary_linked]) {
nprintf(("AI", "Frame %i, ship %s: Unlinking primaries.\n", Framecount, shipp->ship_name));
shipp->flags.remove(Ship::Ship_Flags::Primary_linked);
}
return; // If low on slots, don't link.
}
sip = &Ship_info[shipp->ship_info_index];
aip = &Ai_info[shipp->ai_index];
swp = &shipp->weapons;
shipp->flags.remove(Ship::Ship_Flags::Primary_linked);
shipp->flags.remove(Ship::Ship_Flags::Primary_linked);
// AL: ensure target is a ship!
if ( (aip->target_objnum != -1) && (Objects[aip->target_objnum].type == OBJ_SHIP) ) {
// If trying to destroy a big ship (i.e., not disable/disarm), always unleash all weapons
if ( Ship_info[Ships[Objects[aip->target_objnum].instance].ship_info_index].is_big_ship() ) {
if ( aip->targeted_subsys == NULL ) {
if ( aip->targeted_subsys == nullptr ) {
if (!sip->flags[Ship::Info_Flags::No_primary_linking] ) {
shipp->flags.set(Ship::Ship_Flags::Primary_linked);
}
shipp->flags.set(Ship::Ship_Flags::Secondary_dual_fire);
shipp->flags.set(Ship::Ship_Flags::Secondary_dual_fire);
return;
}
}
}
if (Num_weapons > (int) (MAX_WEAPONS * 0.75f) || sip->flags[Ship::Info_Flags::No_primary_linking]) {
if (shipp->flags[Ship::Ship_Flags::Primary_linked])
nprintf(("AI", "Frame %i, ship %s: Unlinking primaries.\n", Framecount, shipp->ship_name));
shipp->flags.remove(Ship::Ship_Flags::Primary_linked);
return; // If low on slots or primary linking disallowed, don't link.
}
// AL 2-11-98: If ship has a disarm or disable goal, don't link unless both weapons are
// puncture weapons
if ( (aip->active_goal != AI_GOAL_NONE) && (aip->active_goal != AI_ACTIVE_GOAL_DYNAMIC) )
@@ -5634,7 +5637,7 @@ int ai_fire_primary_weapon(object *objp)
ai_info *aip;
object *enemy_objp;
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < ship_info_size());
aip = &Ai_info[shipp->ai_index];
@@ -5672,7 +5675,16 @@ int ai_fire_primary_weapon(object *objp)
float dot;
vec3d v2t;
if ( !(vm_vec_mag_quick(&G_predicted_pos) < AICODE_SMALL_MAGNITUDE ) && !(aip->submode == SM_AVOID) ) {
bool condition;
if (The_mission.ai_profile->flags[AI::Profile_Flags::Fix_ramming_stationary_targets_bug]) {
// fixed by Mantis 3147 - Avoid bashing orientation if trying to avoid a collision.
condition = !(vm_vec_mag_quick(&G_predicted_pos) < AICODE_SMALL_MAGNITUDE) && (aip->submode != SM_AVOID);
} else {
// retail behavior
condition = !(vm_vec_mag_quick(&G_predicted_pos) < AICODE_SMALL_MAGNITUDE);
}
if ( condition ) {
if ( vm_vec_cmp(&G_predicted_pos, &G_fire_pos) ) {
vm_vec_normalized_dir(&v2t, &G_predicted_pos, &G_fire_pos);
dot = vm_vec_dot(&v2t, &objp->orient.vec.fvec);
@@ -6060,7 +6072,7 @@ int ai_fire_secondary_weapon(object *objp)
shipp = &Ships[objp->instance];
swp = &shipp->weapons;
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < ship_info_size());
// Select secondary weapon.
current_bank = swp->current_secondary_bank;
@@ -8222,9 +8234,15 @@ void ai_chase()
if ((real_dot_to_enemy < 0.25f) || (aip->target_time < 1.0f)) {
predicted_enemy_pos = enemy_pos;
} else if (aip->ai_flags[AI::AI_Flags::Seek_lock]) {
set_predicted_enemy_pos(&predicted_enemy_pos, Pl_objp, &aip->last_aim_enemy_pos, &aip->last_aim_enemy_vel, aip); // Set G_fire_pos
predicted_enemy_pos = enemy_pos;
G_predicted_pos = predicted_enemy_pos;
if (The_mission.ai_profile->flags[AI::Profile_Flags::Fix_ramming_stationary_targets_bug]) {
// fixed by Mantis 3147 - Bash orientation if aspect seekers are equipped.
set_predicted_enemy_pos(&predicted_enemy_pos, Pl_objp, &aip->last_aim_enemy_pos, &aip->last_aim_enemy_vel, aip); // Set G_fire_pos
predicted_enemy_pos = enemy_pos;
G_predicted_pos = predicted_enemy_pos;
} else {
// retail behavior
predicted_enemy_pos = enemy_pos;
}
} else {
// Set predicted_enemy_pos.
// See if attacking a subsystem.
@@ -10683,7 +10701,7 @@ void ai_dock()
char *goal_dock_path_name = model_get(goal_sip->model_num)->paths[aip->mp_index].name;
mprintf(("Ship class %s has only %i points on dock path \"%s\". Recommended minimum number of points is 4. "\
"Docking along that path will look strange. You may wish to edit the model.", goal_ship_class_name, aip->path_length, goal_dock_path_name));
"Docking along that path will look strange. You may wish to edit the model.\n", goal_ship_class_name, aip->path_length, goal_dock_path_name));
}
aip->submode = AIS_DOCK_1;
@@ -12550,13 +12568,13 @@ int ai_acquire_emerge_path(object *pl_objp, int parent_objnum, int allowed_path_
polymodel *pm = model_get( Ship_info[parent_shipp->ship_info_index].model_num );
ship_bay *bay = pm->ship_bay;
if ( bay == NULL ) {
WarningEx(LOCATION, "Ship %s was set to arrive from fighter bay on object %s, but no fighter bay exists on that ships' model (%s).\n", shipp->ship_name, parent_shipp->ship_name, pm->filename);
if ( bay == nullptr ) {
Warning(LOCATION, "Ship %s was set to arrive from fighter bay on object %s, but no fighter bay exists on that ships' model (%s).\n", shipp->ship_name, parent_shipp->ship_name, pm->filename);
return -1;
}
if ( bay->num_paths <= 0 ) {
WarningEx(LOCATION, "Ship %s was set to arrive from fighter bay on object %s, but no fighter bay paths exist on that ships' model (%s).\n", shipp->ship_name, parent_shipp->ship_name, pm->filename);
Warning(LOCATION, "Ship %s was set to arrive from fighter bay on object %s, but no fighter bay paths exist on that ships' model (%s).\n", shipp->ship_name, parent_shipp->ship_name, pm->filename);
return -1;
}
@@ -14528,6 +14546,9 @@ void process_friendly_hit_message( int message, object *objp )
if (Ships[objp->instance].flags[Ship::Ship_Flags::No_builtin_messages]) {
index = -1;
}
if (The_mission.ai_profile->flags[AI::Profile_Flags::Check_comms_for_non_player_ships] && hud_communications_state(&Ships[objp->instance]) <= COMM_DAMAGED) {
index = -1;
}
// Karajorma - pick a random ship to send Command messages if command is silenced.
if (index < 0 && (The_mission.flags[Mission::Mission_Flags::No_builtin_command]) ) {
+11 -15
View File
@@ -310,7 +310,7 @@ void ai_clear_wing_goals( int wingnum )
void ai_mission_wing_goal_complete( int wingnum, ai_goal *remove_goalp )
{
int mode, submode, priority, i;
char *name;
const char *name;
ai_goal *aigp;
wing *wingp;
@@ -388,7 +388,7 @@ void ai_goal_purge_invalid_goals( ai_goal *aigp, ai_goal *goal_list, ai_info *ai
{
int i, j;
ai_goal *purge_goal;
char *name;
const char *name;
int mode, ship_index, wingnum;
// get locals for easer access
@@ -1376,7 +1376,7 @@ void ai_copy_mission_wing_goal( ai_goal *aigp, ai_info *aip )
}
if (j >= MAX_AI_GOALS) {
mprintf(("Unable to assign wing goal to ship %s; the ship goals are already filled to capacity", Ships[aip->shipnum].ship_name));
mprintf(("Unable to assign wing goal to ship %s; the ship goals are already filled to capacity\n", Ships[aip->shipnum].ship_name));
}
}
@@ -1413,21 +1413,17 @@ int ai_mission_goal_achievable( int objnum, ai_goal *aigp )
{
ship *shipp = &Ships[objp->instance];
// always valid if has subspace drive
if (!(shipp->flags[Ship::Ship_Flags::No_subspace_drive]))
// always valid if has working subspace drive, not disabled, and not limited by subsystem strength
if ( ship_can_warp_full_check(shipp) )
return AI_GOAL_ACHIEVABLE;
// if no subspace drive, only valid if our mothership is present
// check that we have a mothership and that we can depart to it
if (shipp->departure_location == DEPART_AT_DOCK_BAY)
{
int anchor_shipnum = ship_name_lookup(Parse_names[shipp->departure_anchor]);
if (anchor_shipnum >= 0 && ship_useful_for_departure(anchor_shipnum, shipp->departure_path_mask))
return AI_GOAL_ACHIEVABLE;
// if we can't warp, we can only depart if the ship (or its wing) departs to a fighter bay and the mothership is present
if (ship_can_bay_depart(shipp)) {
return AI_GOAL_ACHIEVABLE;
}
else {
return AI_GOAL_NOT_KNOWN;
}
return AI_GOAL_NOT_KNOWN;
}
+7 -12
View File
@@ -1812,7 +1812,7 @@ bool turret_fire_weapon(int weapon_num, ship_subsys *turret, int parent_objnum,
parent_aip = &Ai_info[Ships[Objects[parent_objnum].instance].ai_index];
parent_ship = &Ships[Objects[parent_objnum].instance];
wip = get_turret_weapon_wip(&turret->weapons, weapon_num);
int turret_weapon_class = WEAPON_INFO_INDEX(wip);
int turret_weapon_class = weapon_info_get_index(wip);
#ifndef NDEBUG
// moved here from check_ok_to_fire
@@ -2544,7 +2544,6 @@ void ai_fire_from_turret(ship *shipp, ship_subsys *ss, int parent_objnum)
// Ok, the turret is lined up... now line up a particular gun.
bool ok_to_fire = false;
bool something_was_ok_to_fire=false;
vec3d tv2e; //so flak can get their jitter without screwing up other guns
if (in_fov ) {
@@ -2581,7 +2580,9 @@ void ai_fire_from_turret(ship *shipp, ship_subsys *ss, int parent_objnum)
ss->turret_next_fire_pos = ffp_pos;
}
ship_get_global_turret_gun_info(&Objects[parent_objnum], ss, &gpos, &gvec, use_angles, &predicted_enemy_pos);
// We're ready to fire... now get down to specifics, like where is the
// actual gun point and normal, not just the one for whole turret.
ship_get_global_turret_gun_info(&Objects[parent_objnum], ss, &gpos, &gvec, use_angles, &predicted_enemy_pos);
// Fire in the direction the turret is facing, not right at the target regardless of turret dir.
vm_vec_sub(&v2e, &predicted_enemy_pos, &gpos);
@@ -2592,12 +2593,6 @@ void ai_fire_from_turret(ship *shipp, ship_subsys *ss, int parent_objnum)
wip = get_turret_weapon_wip(&ss->weapons, valid_weapons[0]);
else
wip = get_turret_weapon_wip(&ss->weapons, valid_weapons[i]);
// We're ready to fire... now get down to specifics, like where is the
// actual gun point and normal, not just the one for whole turret.
// moved here as if there are two weapons with indentical fire stamps
// they would have shared the fire point.
tv2e = gvec;
// make sure to reset this for current weapon
ok_to_fire = false;
@@ -2605,7 +2600,7 @@ void ai_fire_from_turret(ship *shipp, ship_subsys *ss, int parent_objnum)
// if the weapon is a flak gun, add some jitter to its aim so it fires in a "cone"
// to make a cool visual effect and make them less lethal
if(wip->wi_flags[Weapon::Info_Flags::Flak]){
flak_jitter_aim(&tv2e, dist_to_enemy, ship_get_subsystem_strength(shipp, SUBSYSTEM_WEAPONS), wip);
flak_jitter_aim(&v2e, dist_to_enemy, ship_get_subsystem_strength(shipp, SUBSYSTEM_WEAPONS), wip);
}
// Fire if:
@@ -2716,9 +2711,9 @@ void ai_fire_from_turret(ship *shipp, ship_subsys *ss, int parent_objnum)
//Pass along which gun we are using
if (tp->flags[Model::Subsystem_Flags::Turret_salvo])
turret_fire_weapon(valid_weapons[0], ss, parent_objnum, &gpos, &tv2e, &predicted_enemy_pos);
turret_fire_weapon(valid_weapons[0], ss, parent_objnum, &gpos, &v2e, &predicted_enemy_pos);
else
turret_fire_weapon(valid_weapons[i], ss, parent_objnum, &gpos, &tv2e, &predicted_enemy_pos);
turret_fire_weapon(valid_weapons[i], ss, parent_objnum, &gpos, &v2e, &predicted_enemy_pos);
} else {
// make sure salvo fire mode does not turn into autofire
if ((tp->flags[Model::Subsystem_Flags::Turret_salvo]) && ((i + 1) == number_of_firings)) {
+3 -3
View File
@@ -478,7 +478,7 @@ static void asteroid_load(int asteroid_info_index, int asteroid_subtype)
}
else
{
nprintf(("Warning", "For asteroid '%s', detail level mismatch (POF needs %d)", asip->name, pm->n_detail_levels));
nprintf(("Warning", "For asteroid '%s', detail level mismatch (POF needs %d)\n", asip->name, pm->n_detail_levels));
}
}
// Stuff detail level distances.
@@ -1937,11 +1937,11 @@ static void asteroid_parse_tbl()
if (tally != max_asteroids)
{
#ifndef NDEBUG
mprintf(("Asteroid.tbl as parsed:\n"));
for (SCP_vector<SCP_string>::iterator iter = parsed_asteroids.begin();
iter != parsed_asteroids.end(); ++iter)
{
mprintf(("Asteroid.tbl as parsed:\n"));
mprintf(("%s", iter->c_str()));
mprintf(("%s\n", iter->c_str()));
}
#endif
Error(LOCATION,
+2 -2
View File
@@ -218,9 +218,9 @@ bool StartAutopilot()
if (shipp->team != Player_ship->team)
continue;
Assertion((shipp->ship_info_index >= 0) && (shipp->ship_info_index < static_cast<int>(Ship_info.size())),
Assertion((shipp->ship_info_index >= 0) && (shipp->ship_info_index < ship_info_size()),
"Ship '%s' does not have a valid pointer to a ship class. Pointer is %d, which is smaller than 0 or bigger than %d",
shipp->ship_name, shipp->ship_info_index, static_cast<int>(Ship_info.size()));
shipp->ship_name, shipp->ship_info_index, ship_info_size());
ship_info *sip = &Ship_info[shipp->ship_info_index];
if ( !(sip->flags[Ship::Info_Flags::Support]) )
+1 -1
View File
@@ -57,7 +57,7 @@ cf_pathtype Pathtypes[CF_MAX_PATH_TYPES] = {
{ CF_TYPE_MAPS, "data" DIR_SEPARATOR_STR "maps", ".pcx .ani .eff .tga .jpg .png .dds", CF_TYPE_DATA },
{ CF_TYPE_TEXT, "data" DIR_SEPARATOR_STR "text", ".txt .net", CF_TYPE_DATA },
{ CF_TYPE_MODELS, "data" DIR_SEPARATOR_STR "models", ".pof", CF_TYPE_DATA },
{ CF_TYPE_TABLES, "data" DIR_SEPARATOR_STR "tables", ".tbl .tbm", CF_TYPE_DATA },
{ CF_TYPE_TABLES, "data" DIR_SEPARATOR_STR "tables", ".tbl .tbm .lua", CF_TYPE_DATA },
{ CF_TYPE_SOUNDS, "data" DIR_SEPARATOR_STR "sounds", ".wav .ogg", CF_TYPE_DATA },
{ CF_TYPE_SOUNDS_8B22K, "data" DIR_SEPARATOR_STR "sounds" DIR_SEPARATOR_STR "8b22k", ".wav .ogg", CF_TYPE_SOUNDS },
{ CF_TYPE_SOUNDS_16B11K, "data" DIR_SEPARATOR_STR "sounds" DIR_SEPARATOR_STR "16b11k", ".wav .ogg", CF_TYPE_SOUNDS },
+102 -48
View File
@@ -153,22 +153,21 @@ typedef struct
// Please group them by type, ie graphics, gameplay etc, maximum 20 different types
Flag exe_params[] =
{
{ "-nospec", "Disable specular", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-spec", },
{ "-noglow", "Disable glow maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-glow", },
{ "-noenv", "Disable environment maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-env", },
{ "-nonormal", "Disable normal maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-normal" },
{ "-nospec", "Disable specular", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-nospec", },
{ "-noglow", "Disable glow maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noglow", },
{ "-noenv", "Disable environment maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noenv", },
{ "-nonormal", "Disable normal maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-nonormal" },
{ "-emissive_light", "Enable emissive light from ships", true, 0, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-emissive_light" },
{ "-noheight", "Disable height/parallax maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-height" },
{ "-noheight", "Disable height/parallax maps", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noheight" },
{ "-3dshockwave", "Enable 3D shockwaves", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-3dshockwave" },
{ "-no_post_process", "Disable post-processing", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_post_process" },
{ "-soft_particles", "Enable soft particles", true, EASY_ALL_ON, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-soft_particles" },
{ "-fxaa", "Enable FXAA anti-aliasing", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-fxaa" },
{ "-smaa", "Enable SMAA anti-aliasing", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-smaa" },
{ "-nolightshafts", "Disable lightshafts", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-flightshaftsoff"},
{ "-aa", "Enable Post-process anti-aliasing", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-aa" },
{ "-nolightshafts", "Disable lightshafts", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-nolightshafts"},
{ "-fb_explosions", "Enable Framebuffer Shockwaves", true, EASY_ALL_ON, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-fb_explosions", },
{ "-fb_thrusters", "Enable Framebuffer Thrusters", true, EASY_ALL_ON, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-fb_thrusters", },
{ "-no_deferred", "Disable Deferred Lighting", true, EASY_DEFAULT | EASY_HI_MEM_OFF, EASY_ALL_ON | EASY_HI_MEM_ON, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_deferred"},
{ "-enable_shadows", "Enable Shadows", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_shadows"},
{ "-enable_shadows", "Enable Shadows", true, EASY_ALL_ON | EASY_HI_MEM_ON, EASY_DEFAULT | EASY_HI_MEM_OFF, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-enable_shadows"},
{ "-no_vsync", "Disable vertical sync", true, 0, EASY_DEFAULT, "Game Speed", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_vsync", },
@@ -216,12 +215,12 @@ Flag exe_params[] =
{ "-mipmap", "Enable mipmapping", true, 0, EASY_DEFAULT | EASY_HI_MEM_OFF, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-mipmap", },
{ "-use_gldrawelements","Don't use glDrawRangeElements", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-use_gldrawelements", },
{ "-gl_finish", "Fix input lag on some ATI+Linux systems", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-gl_finish", },
{ "-no_geo_effects", "Disable geometry shader for effects", true, 0, EASY_DEFAULT, "Troubleshoot", "", },
{ "-set_cpu_affinity", "Sets processor affinity to config value", true, 0, EASY_DEFAULT, "Troubleshoot", "", },
{ "-no_geo_effects", "Disable geometry shader for effects", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_geo_effects", },
{ "-set_cpu_affinity", "Sets processor affinity to config value", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-set_cpu_affinity", },
{ "-nograb", "Disables mouse grabbing", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-nograb", },
{ "-noshadercache", "Disables the shader cache", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noshadercache", },
#ifdef WIN32
{ "-fix_registry", "Use a different registry path", true, 0, EASY_DEFAULT, "Troubleshoot", "", },
{ "-fix_registry", "Use a different registry path", true, 0, EASY_DEFAULT, "Troubleshoot", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-fix_registry", },
#endif
{ "-ingame_join", "Allow in-game joining", true, 0, EASY_DEFAULT, "Experimental", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-ingame_join", },
@@ -231,7 +230,8 @@ Flag exe_params[] =
{ "-pos", "Show position of camera", false, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-pos", },
{ "-stats", "Show statistics", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-stats", },
{ "-coords", "Show coordinates", false, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-coords", },
{ "-pofspew", "Generate all ibx files immediately", false, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-pofspew", },
{ "-pofspew", "Dump model information to pofspew.txt", false, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-pofspew", },
{ "-weaponspew", "Dump weapon stats and spreadsheets", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-weaponspew", },
{ "-tablecrcs", "Dump table CRCs for multi validation", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-tablecrcs", },
{ "-missioncrcs", "Dump mission CRCs for multi validation", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-missioncrcs", },
{ "-dis_collisions", "Disable collisions", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-dis_collisions", },
@@ -242,13 +242,14 @@ Flag exe_params[] =
{ "-save_render_target", "Save render targets to file", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-save_render_target", },
{ "-verify_vps", "Spew VP CRCs to vp_crcs.txt", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-verify_vps", },
{ "-reparse_mainhall", "Reparse mainhall.tbl when loading halls", false, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-reparse_mainhall", },
{ "-profile_write_file", "Write profiling information to file", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-profile_write_file", },
{ "-noninteractive", "Disables interactive dialogs", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noninteractive", },
{ "-no_unfocused_pause","Don't pause if the window isn't focused", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_unfocused_pause", },
{ "-benchmark_mode", "Puts the game into benchmark mode", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-benchmark_mode", },
{ "-noninteractive", "Disables interactive dialogs", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-noninteractive", },
{ "-profile_frame_time","Profile frame time", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-profile_frame_time", },
{ "-profile_write_file", "Write profiling information to file", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-profile_write_file", },
{ "-json_profiling", "Generate JSON profiling output", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-json_profiling", },
{ "-profile_frame_time","Profile engine subsystems", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-profile_frame_timings", },
{ "-debug_window", "Enable the debug window", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-debug_window", },
{ "-gr_debug", "Output graphics debug information", true, 0, EASY_DEFAULT, "Dev Tool", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-gr_debug", },
};
// clang-format on
@@ -274,6 +275,7 @@ cmdline_parm port_arg("-port", "Multiplayer network port", AT_INT);
cmdline_parm multilog_arg("-multilog", NULL, AT_NONE); // Cmdline_multi_log
cmdline_parm client_dodamage("-clientdamage", NULL, AT_NONE); // Cmdline_client_dodamage
cmdline_parm pof_spew("-pofspew", NULL, AT_NONE); // Cmdline_spew_pof_info
cmdline_parm weapon_spew("-weaponspew", nullptr, AT_NONE); // Cmdline_spew_weapon_stats
cmdline_parm mouse_coords("-coords", NULL, AT_NONE); // Cmdline_mouse_coords
cmdline_parm timeout("-timeout", "Multiplayer network timeout (secs)", AT_INT); // Cmdline_timeout
cmdline_parm bit32_arg("-32bit", "Deprecated", AT_NONE); // (only here for retail compatibility reasons, doesn't actually do anything)
@@ -295,6 +297,7 @@ int Cmdline_multi_stream_chat_to_file = 0;
int Cmdline_network_port = -1;
int Cmdline_restricted_game = 0;
int Cmdline_spew_pof_info = 0;
bool Cmdline_spew_weapon_stats = false;
int Cmdline_start_netgame = 0;
int Cmdline_timeout = -1;
int Cmdline_use_last_pilot = 0;
@@ -321,10 +324,12 @@ cmdline_parm enable_3d_shockwave_arg("-3dshockwave", NULL, AT_NONE);
cmdline_parm softparticles_arg("-soft_particles", NULL, AT_NONE);
cmdline_parm no_postprocess_arg("-no_post_process", "Disables post-processing", AT_NONE);
cmdline_parm bloom_intensity_arg("-bloom_intensity", "Set bloom intensity, requires post-processing", AT_INT);
cmdline_parm fxaa_arg("-fxaa", NULL, AT_NONE);
cmdline_parm fxaa_preset_arg("-fxaa_preset", "FXAA quality (0-9), requires post-processing and -fxaa", AT_INT);
cmdline_parm smaa_arg("-smaa", nullptr, AT_NONE);
cmdline_parm smaa_preset_arg("-smaa_preset", "SMAA quality (0-9), requires post-processing and -smaa", AT_INT);
cmdline_parm post_process_aa_arg("-aa", "Enables post-process antialiasing", AT_NONE);
cmdline_parm post_process_aa_preset_arg("-aa_preset", "Sets the AA effect to use. See the wiki for details", AT_INT);
cmdline_parm deprecated_fxaa_arg("-fxaa", nullptr, AT_NONE);
cmdline_parm deprecated_fxaa_preset_arg("-fxaa_preset", "FXAA quality (0-2), requires post-processing and -fxaa", AT_INT);
cmdline_parm deprecated_smaa_arg("-smaa", nullptr, AT_NONE);
cmdline_parm deprecated_smaa_preset_arg("-smaa_preset", "SMAA quality (0-3), requires post-processing and -smaa", AT_INT);
cmdline_parm fb_explosions_arg("-fb_explosions", NULL, AT_NONE);
cmdline_parm fb_thrusters_arg("-fb_thrusters", NULL, AT_NONE);
cmdline_parm flightshaftsoff_arg("-nolightshafts", NULL, AT_NONE);
@@ -478,6 +483,8 @@ cmdline_parm json_profiling("-json_profiling", NULL, AT_NONE); //Cmdline_json_pr
cmdline_parm show_video_info("-show_video_info", NULL, AT_NONE); //Cmdline_show_video_info
cmdline_parm frame_profile_arg("-profile_frame_time", NULL, AT_NONE); //Cmdline_frame_profile
cmdline_parm debug_window_arg("-debug_window", NULL, AT_NONE); // Cmdline_debug_window
cmdline_parm graphics_debug_output_arg("-gr_debug", nullptr, AT_NONE); // Cmdline_graphics_debug_output
cmdline_parm log_to_stdout_arg("-stdout_log", nullptr, AT_NONE); // Cmdline_log_to_stdout
char *Cmdline_start_mission = NULL;
@@ -507,6 +514,8 @@ bool Cmdline_json_profiling = false;
bool Cmdline_frame_profile = false;
bool Cmdline_show_video_info = false;
bool Cmdline_debug_window = false;
bool Cmdline_graphics_debug_output = false;
bool Cmdline_log_to_stdout = false;
// Other
cmdline_parm get_flags_arg(GET_FLAGS_STRING, "Output the launcher flags file", AT_STRING);
@@ -1662,6 +1671,11 @@ bool SetCmdlineParams()
Cmdline_spew_pof_info = 1;
}
// spew weapon stats
if (weapon_spew.found()) {
Cmdline_spew_weapon_stats = true;
}
// mouse coords
if(mouse_coords.found()){
Cmdline_mouse_coords = 1;
@@ -1858,48 +1872,41 @@ bool SetCmdlineParams()
if ( height_arg.found() ) {
Cmdline_height = 0;
}
if (fxaa_arg.found() ) {
Gr_aa_mode = AntiAliasMode::FXAA_Medium;
if (fxaa_preset_arg.found()) {
auto val = fxaa_preset_arg.get_int();
if (val > 6) {
Gr_aa_mode = AntiAliasMode::FXAA_High;
} else if (val > 3) {
Gr_aa_mode = AntiAliasMode::FXAA_Medium;
} else {
if (post_process_aa_arg.found() || post_process_aa_preset_arg.found()) {
Gr_aa_mode = AntiAliasMode::SMAA_Low;
if (post_process_aa_preset_arg.found()) {
switch (post_process_aa_preset_arg.get_int()) {
case 0:
Gr_aa_mode = AntiAliasMode::FXAA_Low;
}
}
Gr_aa_mode_last_frame = Gr_aa_mode;
}
if (smaa_arg.found()) {
Gr_aa_mode = AntiAliasMode::SMAA_Medium;
if (smaa_preset_arg.found()) {
switch (smaa_preset_arg.get_int()) {
case 0:
break;
case 1:
Gr_aa_mode = AntiAliasMode::FXAA_Medium;
break;
case 2:
Gr_aa_mode = AntiAliasMode::FXAA_High;
break;
case 3:
Gr_aa_mode = AntiAliasMode::SMAA_Low;
break;
case 1:
case 4:
Gr_aa_mode = AntiAliasMode::SMAA_Medium;
break;
case 2:
case 5:
Gr_aa_mode = AntiAliasMode::SMAA_High;
break;
case 3:
Gr_aa_mode = AntiAliasMode::SMAA_Ultra;
break;
default:
case 6:
Gr_aa_mode = AntiAliasMode::SMAA_Ultra;
break;
}
}
}
// If any of the AA presets were chosen, update the _last_frame AA mode to avoid an unnecessary
// shader recompile.
Gr_aa_mode_last_frame = Gr_aa_mode;
if ( glow_arg.found() )
Cmdline_glow = 0;
@@ -2133,6 +2140,14 @@ bool SetCmdlineParams()
Cmdline_debug_window = true;
}
if (graphics_debug_output_arg.found()) {
Cmdline_graphics_debug_output = true;
}
if (log_to_stdout_arg.found()) {
Cmdline_log_to_stdout = true;
}
if (show_video_info.found())
{
Cmdline_show_video_info = true;
@@ -2195,6 +2210,45 @@ bool SetCmdlineParams()
if (deprecated_postprocess_arg.found()) {
Cmdline_deprecated_postprocess = true;
}
if (deprecated_fxaa_arg.found() ) {
Gr_aa_mode = AntiAliasMode::FXAA_Medium;
if (deprecated_fxaa_preset_arg.found()) {
auto val = deprecated_fxaa_preset_arg.get_int();
if (val > 6) {
Gr_aa_mode = AntiAliasMode::FXAA_High;
} else if (val > 3) {
Gr_aa_mode = AntiAliasMode::FXAA_Medium;
} else {
Gr_aa_mode = AntiAliasMode::FXAA_Low;
}
}
}
if (deprecated_smaa_arg.found()) {
Gr_aa_mode = AntiAliasMode::SMAA_Medium;
if (deprecated_smaa_preset_arg.found()) {
switch (deprecated_smaa_preset_arg.get_int()) {
case 0:
Gr_aa_mode = AntiAliasMode::SMAA_Low;
break;
case 1:
Gr_aa_mode = AntiAliasMode::SMAA_Medium;
break;
case 2:
Gr_aa_mode = AntiAliasMode::SMAA_High;
break;
case 3:
Gr_aa_mode = AntiAliasMode::SMAA_Ultra;
break;
default:
Gr_aa_mode = AntiAliasMode::SMAA_Ultra;
break;
}
}
}
return true;
}
+4
View File
@@ -147,5 +147,9 @@ extern bool Cmdline_json_profiling;
extern bool Cmdline_frame_profile;
extern bool Cmdline_show_video_info;
extern bool Cmdline_debug_window;
extern bool Cmdline_graphics_debug_output;
extern bool Cmdline_log_to_stdout;
extern bool Cmdline_spew_weapon_stats;
#endif
+1 -1
View File
@@ -2304,7 +2304,7 @@ int check_control_used(int id, int key)
if ((Control_config[id].key_id == key) || joy_down_count(Control_config[id].joy_id, 1) ||
((Control_config[id].joy_id >= 0) && (Control_config[id].joy_id < MOUSE_NUM_BUTTONS) && mouse_down_count(1 << Control_config[id].joy_id))) {
//mprintf(("Key used %d", key));
//mprintf(("Key used %d\n", key));
control_used(id);
return 1;
}
@@ -17,6 +17,7 @@
#include "io/joy.h"
#include "io/key.h"
#include "localization/localize.h"
#include "options/Option.h"
#include "parse/parselo.h"
// z64: These enumerations MUST equal to those in controlsconfig.cpp...
@@ -32,8 +33,29 @@ int Failed_key_index;
// Joystick configuration
int Joy_dead_zone_size = 10;
auto DeadZoneOption =
options::OptionBuilder<int>("Input.JoystickDeadZone", "Deadzone", "The deadzone of the selected joystick.")
.category("Input")
.range(0, 45)
.level(options::ExpertLevel::Beginner)
.default_val(10)
.bind_to(&Joy_dead_zone_size)
.importance(1)
.finish();
int Joy_sensitivity = 9;
auto SensitivityOption =
options::OptionBuilder<int>("Input.JoystickSensitivity", "Sensitivity", "The sentitivity of the selected joystick.")
.category("Input")
.range(0, 9)
.level(options::ExpertLevel::Beginner)
.default_val(9)
.bind_to(&Joy_sensitivity)
.importance(2)
.finish();
int Invert_axis[JOY_NUM_AXES] = { 0, 0, 0, 0, 0, 0 };
int Invert_axis_defaults[JOY_NUM_AXES] = { 0, 0, 0, 0, 0, 0 };
+1 -1
View File
@@ -126,7 +126,7 @@ void AudioDecoder::handleDecodedFrame(AVFrame* frame) {
auto ret = av_samples_alloc(m_outData, &m_outLinesize, OUT_NUM_CHANNELS, m_outNumSamples,
OUT_SAMPLE_FORMAT, 1);
if (ret < 0) {
mprintf(("FFMPEG: Failed to allocate samples!!!"));
mprintf(("FFMPEG: Failed to allocate samples!!!\n"));
return;
}
+2 -2
View File
@@ -286,7 +286,7 @@ std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& st
if (status->subtitleStream == nullptr) {
// We don't have an external subtitle stream or loading from that file has failed
auto& current_language = Lcl_languages[Lcl_current_lang];
auto& current_language = Lcl_languages[Lcl_current_lang == LCL_UNTRANSLATED ? LCL_DEFAULT : Lcl_current_lang];
for (uint32_t i = 0; i < ctx->nb_streams; ++i) {
auto test_stream = ctx->streams[i];
@@ -428,7 +428,7 @@ std::unique_ptr<InputStream> openInputStream(const SCP_string& name) {
std::unique_ptr<InputStream> openSubtitleStream(const SCP_string& name)
{
auto& current_language = Lcl_languages[Lcl_current_lang];
auto& current_language = Lcl_languages[Lcl_current_lang == LCL_UNTRANSLATED ? LCL_DEFAULT : Lcl_current_lang];
for (auto ext : CHECKED_SUBT_EXTENSIONS) {
SCP_string fileName;
+3 -1
View File
@@ -27,13 +27,15 @@ using namespace cutscene;
const int MAX_AUDIO_BUFFERS = 15;
std::unique_ptr<Decoder> findDecoder(const SCP_string& name, const PlaybackProperties& properties) {
std::unique_ptr<Decoder> findDecoder(__UNUSED const SCP_string& name, __UNUSED const PlaybackProperties& properties) {
#ifdef WITH_FFMPEG
{
std::unique_ptr<Decoder> ffmpeg(new ::cutscene::ffmpeg::FFMPEGDecoder());
if (ffmpeg->initialize(name, properties)) {
return ffmpeg;
}
}
#endif
return nullptr;
}
+5 -4
View File
@@ -240,11 +240,12 @@ void debris_process_post(object * obj, float frame_time)
MONITOR_INC(NumSmallDebris,1);
}
if ( db->lifeleft >= 0.0f) {
if (db->lifeleft >= 0.0f) {
db->lifeleft -= frame_time;
if ( db->lifeleft < 0.0f ) {
debris_start_death_roll(obj, db);
}
}
if ( db->lifeleft < 0.0f ) {
debris_start_death_roll(obj, db);
}
maybe_delete_debris(db); // Make this debris go away if it's very far away.
+1 -2
View File
@@ -468,10 +468,9 @@ void renderAll() {
return;
}
graphics::decal_draw_list draw_list;
auto mission_time = f2fl(Missiontime);
graphics::decal_draw_list draw_list(active_decals.size());
for (auto& decal : active_decals) {
int diffuse_bm = -1;
int glow_bm = -1;
+7 -1
View File
@@ -3,9 +3,15 @@
in vec4 fragTexCoord;
in vec4 fragColor;
out vec4 fragOut0;
uniform sampler2DArray baseMap;
uniform float intensity;
layout (std140) uniform genericData {
vec4 color;
float intensity;
};
void main()
{
+12 -3
View File
@@ -1,11 +1,20 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
in vec4 vertColor;
out vec4 fragTexCoord;
out vec4 fragColor;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
uniform vec4 color;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
layout (std140) uniform genericData {
vec4 color;
float intensity;
};
void main()
{
fragTexCoord = vec4(vertTexCoord.xyz, 0.0);
+10 -3
View File
@@ -1,8 +1,15 @@
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2D bloomed;
uniform float bloom_intensity;
uniform int levels;
layout (std140) uniform genericData {
float bloom_intensity;
int levels;
};
void main() {
vec4 color_out = vec4(0.0, 0.0, 0.0, 1.0);
float factor = 0.0;
@@ -14,4 +21,4 @@ void main() {
color_out.rgb /= factor;
color_out.rgb *= bloom_intensity;
fragOut0 = color_out;
}
}
+15 -8
View File
@@ -1,9 +1,16 @@
out vec4 fragOut0;
uniform float texSize;
uniform float tapSize;
uniform int level;
in vec4 fragTexCoord;
uniform sampler2D tex;
const float TapSize = 1.0;
layout (std140) uniform genericData {
float texSize;
int level;
};
// Gaussian Blur
// 2 passes required
void main()
@@ -20,15 +27,15 @@ void main()
vec4 sum = textureLod(tex, fragTexCoord.xy, float(level)) * BlurWeights[0];
#ifdef PASS_0
for (int i = 1; i < 6; i++) {
sum += textureLod(tex, vec2(clamp(fragTexCoord.x - float(i) * (texSize) * tapSize, 0.0, 1.0), fragTexCoord.y), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(clamp(fragTexCoord.x + float(i) * (texSize) * tapSize, 0.0, 1.0), fragTexCoord.y), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(clamp(fragTexCoord.x - float(i) * (texSize) * TapSize, 0.0, 1.0), fragTexCoord.y), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(clamp(fragTexCoord.x + float(i) * (texSize) * TapSize, 0.0, 1.0), fragTexCoord.y), float(level)) * BlurWeights[i];
}
#endif
#ifdef PASS_1
for (int i = 1; i < 6; i++) {
sum += textureLod(tex, vec2(fragTexCoord.x, clamp(fragTexCoord.y - float(i) * (texSize) * tapSize, 0.0, 1.0)), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(fragTexCoord.x, clamp(fragTexCoord.y + float(i) * (texSize) * tapSize, 0.0, 1.0)), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(fragTexCoord.x, clamp(fragTexCoord.y - float(i) * (texSize) * TapSize, 0.0, 1.0)), float(level)) * BlurWeights[i];
sum += textureLod(tex, vec2(fragTexCoord.x, clamp(fragTexCoord.y + float(i) * (texSize) * TapSize, 0.0, 1.0)), float(level)) * BlurWeights[i];
}
#endif
fragOut0 = sum;
}
}
@@ -6,12 +6,23 @@ in vec4 fragColor;
out vec4 fragOut0;
uniform sampler2DArray baseMap;
uniform int baseMapIndex;
uniform int alphaTexture;
uniform int noTexturing;
uniform int srgb;
uniform float intensity;
uniform float alphaThreshold;
layout (std140) uniform genericData {
mat4 modelMatrix;
vec4 color;
vec4 clipEquation;
int baseMapIndex;
int alphaTexture;
int noTexturing;
int srgb;
float intensity;
float alphaThreshold;
bool clipEnabled;
};
void main()
{
@@ -0,0 +1,38 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
in vec4 vertColor;
out vec4 fragTexCoord;
out vec4 fragColor;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
layout (std140) uniform genericData {
mat4 modelMatrix;
vec4 color;
vec4 clipEquation;
int baseMapIndex;
int alphaTexture;
int noTexturing;
int srgb;
float intensity;
float alphaThreshold;
bool clipEnabled;
};
void main()
{
fragTexCoord = vertTexCoord;
fragColor = vertColor * color;
gl_Position = projMatrix * modelViewMatrix * vertPosition;
if (clipEnabled) {
gl_ClipDistance[0] = dot(clipEquation, modelMatrix * vertPosition);
}
}
+5 -2
View File
@@ -2,8 +2,11 @@
#include "lighting.sdr"
in vec4 vertPosition;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
layout (std140) uniform lightData {
vec3 diffuseLightColor;
@@ -1,13 +1,20 @@
in vec4 fragTexCoord;
in vec4 fragColor;
in float fragOffset;
out vec4 fragOut0;
uniform sampler2DArray baseMap;
uniform sampler2D depthMap;
uniform float window_width;
uniform float window_height;
uniform sampler2D distMap;
uniform sampler2D frameBuffer;
layout (std140) uniform genericData {
float window_width;
float window_height;
float use_offset;
};
void main()
{
vec2 depthCoord = vec2(gl_FragCoord.x / window_width, gl_FragCoord.y / window_height);
@@ -5,9 +5,18 @@ in float vertRadius;
out vec4 fragTexCoord;
out vec4 fragColor;
out float fragOffset;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
uniform float use_offset;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
layout (std140) uniform genericData {
float window_width;
float window_height;
float use_offset;
};
void main()
{
gl_Position = projMatrix * modelViewMatrix * vertPosition;
@@ -1,21 +1,27 @@
#include "gamma.sdr"
uniform sampler2DArray baseMap;
uniform sampler2D depthMap;
uniform float window_width;
uniform float window_height;
uniform float nearZ;
uniform float farZ;
uniform int linear_depth;
uniform int srgb;
uniform int blend_alpha;
in float fragRadius;
in vec4 fragPosition;
in vec4 fragTexCoord;
in vec4 fragColor;
out vec4 fragOut0;
uniform sampler2DArray baseMap;
uniform sampler2D depthMap;
layout (std140) uniform genericData {
float window_width;
float window_height;
float nearZ;
float farZ;
int linear_depth;
int srgb;
int blend_alpha;
};
void main()
{
vec4 fragmentColor = texture(baseMap, fragTexCoord.xyz);
@@ -39,7 +45,7 @@ void main()
fragDepthLinear = ( 2.0 * farZ * nearZ ) / ( farZ + nearZ - gl_FragCoord.z * (farZ-nearZ) );
}
// assume UV of 0.5, 0.5 is the centroid of this sphere volume
float depthOffset = sqrt(pow(fragRadius, 2.0) - pow(offset_len, 2.0));
float depthOffset = sqrt((fragRadius*fragRadius) - (offset_len*offset_len));
float frontDepth = fragDepthLinear - depthOffset;
float backDepth = fragDepthLinear + depthOffset;
float intensity = smoothstep(max(nearZ, frontDepth), backDepth, sceneDepthLinear);
@@ -1,14 +1,21 @@
layout (points) in;
layout (triangle_strip, max_vertices = 4) out;
in vec3 geoUvec[];
in float geoRadius[];
in vec4 geoColor[];
in float geoArrayIndex[];
out float fragRadius;
out vec4 fragPosition;
out vec4 fragTexCoord;
out vec4 fragColor;
uniform mat4 projMatrix;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
void main(void)
{
vec3 forward_vec = vec3(0.0, 0.0, 1.0);
+21 -22
View File
@@ -1,7 +1,9 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
in vec4 vertColor;
in float vertRadius;
#ifdef FLAG_EFFECT_GEOMETRY
in vec3 vertUvec;
out vec3 geoUvec;
@@ -14,28 +16,25 @@ in float vertRadius;
out vec4 fragTexCoord;
out vec4 fragColor;
#endif
#ifdef FLAG_EFFECT_DISTORTION
out float fragOffset;
uniform float use_offset;
#endif
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
void main()
{
#ifdef FLAG_EFFECT_GEOMETRY
geoRadius = vertRadius;
geoUvec = vertUvec;
gl_Position = modelViewMatrix * vertPosition;
geoColor = vertColor;
geoArrayIndex = vertTexCoord.z;
#else
fragRadius = vertRadius;
gl_Position = projMatrix * modelViewMatrix * vertPosition;
fragPosition = modelViewMatrix * vertPosition;
fragTexCoord = vec4(vertTexCoord.xyz, 0.0);
fragColor = vertColor;
#endif
#ifdef FLAG_EFFECT_DISTORTION
fragOffset = vertRadius * use_offset;
#endif
#ifdef FLAG_EFFECT_GEOMETRY
geoRadius = vertRadius;
geoUvec = vertUvec;
gl_Position = modelViewMatrix * vertPosition;
geoColor = vertColor;
geoArrayIndex = vertTexCoord.z;
#else
fragRadius = vertRadius;
gl_Position = projMatrix * modelViewMatrix * vertPosition;
fragPosition = modelViewMatrix * vertPosition;
fragTexCoord = vec4(vertTexCoord.xyz, 0.0);
fragColor = vertColor;
#endif
}
+9 -5
View File
@@ -2,16 +2,20 @@
#include "gamma.sdr"
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2D tex;
uniform sampler2D depth_tex;
uniform float fog_start;
uniform float fog_scale;
uniform vec3 fog_color;
uniform float zNear;
uniform float zFar;
layout (std140) uniform genericData {
vec3 fog_color;
float fog_start;
float fog_scale;
float zNear;
float zFar;
};
void main()
{
+7 -2
View File
@@ -1,9 +1,14 @@
in vec4 vertPosition;
uniform float rt_w;
uniform float rt_h;
out vec2 v_rcpFrame;
noperspective out vec2 v_pos;
layout (std140) uniform genericData {
float rt_w;
float rt_h;
};
void main() {
gl_Position = vertPosition;
v_rcpFrame = vec2(1.0/rt_w, 1.0/rt_h);
+14 -7
View File
@@ -1,13 +1,20 @@
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2D scene;
uniform sampler2D cockpit;
uniform vec2 sun_pos;
uniform float density;
uniform float weight;
uniform float falloff;
uniform float intensity;
uniform float cp_intensity;
layout (std140) uniform genericData {
vec2 sun_pos;
float density;
float weight;
float falloff;
float intensity;
float cp_intensity;
};
void main()
{
vec2 step = vec2( fragTexCoord.st - sun_pos.xy );
@@ -29,4 +36,4 @@ void main()
}
fragOut0 = sum * intensity;
fragOut0.a = 1.0;
}
}
@@ -4,9 +4,13 @@
in vec4 fragTexCoord;
in vec4 fragColor;
out vec4 fragOut0;
uniform sampler2D baseMap;
uniform int noTexturing;
uniform int srgb;
layout (std140) uniform genericData {
int noTexturing;
int srgb;
};
void main()
{
+5 -11
View File
@@ -3,21 +3,15 @@ in vec4 vertTexCoord;
in vec4 vertColor;
out vec4 fragTexCoord;
out vec4 fragColor;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
uniform vec4 color;
uniform mat4 modelMatrix;
uniform bool clipEnabled;
uniform vec4 clipEquation;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
void main()
{
fragTexCoord = vertTexCoord;
fragColor = vertColor * color;
fragColor = vertColor;
gl_Position = projMatrix * modelViewMatrix * vertPosition;
if (clipEnabled) {
gl_ClipDistance[0] = dot(clipEquation, modelMatrix * vertPosition);
}
}
+18 -29
View File
@@ -1,36 +1,25 @@
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2D tex;
uniform float timer;
#ifdef FLAG_DISTORT_NOISE
uniform float noise_amount;
#endif
#ifdef FLAG_SATURATION
uniform float saturation;
#endif
#ifdef FLAG_BRIGHTNESS
uniform float brightness;
#endif
#ifdef FLAG_CONTRAST
uniform float contrast;
#endif
#ifdef FLAG_GRAIN
uniform float film_grain;
#endif
#ifdef FLAG_STRIPES
uniform float tv_stripes;
#endif
#ifdef FLAG_CUTOFF
uniform float cutoff;
#endif
#ifdef FLAG_DITH
uniform float dither;
#endif
#ifdef FLAG_TINT
uniform vec3 tint;
#endif
uniform sampler2D blurred_tex;
uniform sampler2D depth_tex;
layout (std140) uniform genericData {
float timer;
float noise_amount;
float saturation;
float brightness;
float contrast;
float film_grain;
float tv_stripes;
float cutoff;
vec3 tint;
float dither;
};
void main()
{
#ifdef FLAG_DISTORT_NOISE
+1 -3
View File
@@ -1,10 +1,8 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
out vec4 fragTexCoord;
out float blurSize;
uniform float bsize;
void main()
{
fragTexCoord = vertTexCoord;
gl_Position = vertPosition;
}
}
+8 -2
View File
@@ -4,9 +4,15 @@ in vec4 fragColor;
out vec4 fragOut0;
uniform bool textured;
uniform sampler2DArray baseMap;
uniform int baseMapIndex;
layout (std140) uniform genericData {
mat4 modelViewMatrix;
mat4 projMatrix;
bool textured;
int baseMapIndex;
};
void main() {
if (textured) {
+7 -2
View File
@@ -6,8 +6,13 @@ in vec2 vertTexCoord;
out vec2 fragTexCoord;
out vec4 fragColor;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
layout (std140) uniform genericData {
mat4 modelViewMatrix;
mat4 projMatrix;
bool textured;
int baseMapIndex;
};
void main()
{
@@ -1,10 +0,0 @@
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2DArray shadow_map;
//uniform sampler2D shadow_map;
uniform int index;
void main()
{
vec3 texcoord = vec3(fragTexCoord.xy, float(index));
fragOut0 = vec4(texture(shadow_map, texcoord).rgb,1.0);
}
@@ -1,8 +0,0 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
out vec4 fragTexCoord;
void main()
{
fragTexCoord = vertTexCoord;
gl_Position = vertPosition;
}
@@ -1,14 +1,27 @@
#include "gamma.sdr"
const float EMISSIVE_GAIN = 2.0;
in vec4 fragImpactUV;
in float fragNormOffset;
uniform vec4 color;
uniform sampler2DArray shieldMap;
uniform int shieldMapIndex;
uniform int srgb;
out vec4 fragOut0;
#define EMISSIVE_GAIN 2.0
uniform sampler2DArray shieldMap;
layout (std140) uniform genericData {
mat4 shieldModelViewMatrix;
mat4 shieldProjMatrix;
vec3 hitNormal;
int srgb;
vec4 color;
int shieldMapIndex;
};
void main()
{
if(fragNormOffset < 0.0) discard;
@@ -1,12 +1,28 @@
in vec4 vertPosition;
in vec3 vertNormal;
out vec4 fragImpactUV;
out float fragNormOffset;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
uniform vec3 hitNormal;
uniform mat4 shieldModelViewMatrix;
uniform mat4 shieldProjMatrix;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
layout (std140) uniform genericData {
mat4 shieldModelViewMatrix;
mat4 shieldProjMatrix;
vec3 hitNormal;
int srgb;
vec4 color;
int shieldMapIndex;
};
void main()
{
gl_Position = projMatrix * modelViewMatrix * vertPosition;
@@ -15,4 +31,4 @@ void main()
fragImpactUV = shieldProjMatrix * shieldModelViewMatrix * vertPosition;
fragImpactUV += 1.0f;
fragImpactUV *= 0.5f;
}
}
+3 -1
View File
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
+3 -1
View File
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
+3 -1
View File
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
+3 -1
View File
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
@@ -1,5 +1,7 @@
uniform vec2 smaa_rt_metrics;
layout (std140) uniform genericData {
vec2 smaa_rt_metrics;
};
#define SMAA_RT_METRICS vec4(1.0 / smaa_rt_metrics, smaa_rt_metrics)
@@ -4,7 +4,11 @@
in vec4 fragTexCoord;
out vec4 fragOut0;
uniform sampler2D tex;
uniform float exposure;
layout (std140) uniform genericData {
float exposure;
};
vec3 Uncharted2Tonemapping(vec3 hdr_color)
{
float A = 0.15;
+7 -3
View File
@@ -1,10 +1,14 @@
in vec4 vertPosition;
in vec4 vertTexCoord;
out vec4 fragTexCoord;
uniform mat4 modelViewMatrix;
uniform mat4 projMatrix;
layout (std140) uniform matrixData {
mat4 modelViewMatrix;
mat4 projMatrix;
};
void main()
{
fragTexCoord = vertTexCoord;
gl_Position = projMatrix * modelViewMatrix * vertPosition;
}
}
+2 -1
View File
@@ -54,6 +54,7 @@ static auto WarpOption = options::OptionBuilder<bool>("Graphics.3dWarp", "3D War
.bind_to(&Fireball_use_3d_warp)
.importance(65)
.finish();
/**
* Play warp in sound for warp effect
*/
@@ -73,7 +74,7 @@ void fireball_play_warphole_open_sound(int ship_class, fireball *fb)
if(fb->warp_open_sound_index.isValid()) {
sound_index = fb->warp_open_sound_index;
} else if ((ship_class >= 0) && (ship_class < static_cast<int>(Ship_info.size()))) {
} else if ((ship_class >= 0) && (ship_class < ship_info_size())) {
if ( Ship_info[ship_class].is_huge_ship() ) {
sound_index = gamesnd_id(GameSounds::CAPITAL_WARP_IN);
fb->flags |= FBF_WARP_CAPITAL_SIZE;
+44 -15
View File
@@ -1,17 +1,15 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#include "gamesnd/eventmusic.h"
#include "cmdline/cmdline.h"
#include "gamesnd/eventmusic.h"
#include "globalincs/linklist.h"
#include "iff_defs/iff_defs.h"
#include "io/timer.h"
@@ -19,12 +17,12 @@
#include "mission/missiongoals.h"
#include "mission/missionparse.h"
#include "object/object.h"
#include "options/Option.h"
#include "parse/parselo.h"
#include "ship/ship.h"
#include "sound/audiostr.h"
#include "sound/sound.h"
#ifdef _MSC_VER
#pragma optimize("", off)
#endif
@@ -38,6 +36,23 @@ int Event_Music_battle_started = 0;
float Default_music_volume = 0.5f; // range is 0->1
float Master_event_music_volume = Default_music_volume;
static bool music_volume_change_listener(float new_val, bool /*initial*/)
{
Assertion(new_val >= 0.0f && new_val <= 1.0f, "Invalid value %f supplied by options system!", new_val);
event_music_set_volume(new_val);
return true;
}
static auto MusicVolumeOption = options::OptionBuilder<float>("Audio.Music", "Music", "Volume used for playing music")
.category("Audio")
.default_val(Default_music_volume)
.range(0.0f, 1.0f)
.change_listener(music_volume_change_listener)
.importance(1)
.finish();
typedef struct tagSNDPATTERN {
int default_next_pattern; // Needed so the next_pattern member can be reset
int next_pattern; // Next pattern to play at loop time (can be same pattern)
@@ -517,7 +532,7 @@ void event_music_do_frame()
}
// -------------------------------------------------------------------------------------------------
// event_music_level_init()
// event_music_level_start()
//
// Called at the start of a mission (level). Sets up the pattern data, and kicks off the
// first track to play().
@@ -525,7 +540,7 @@ void event_music_do_frame()
// input: force_soundtrack => OPTIONAL parameter (default value -1)
// forces the soundtrack to ignore the music.tbl assignment
//
void event_music_level_init(int force_soundtrack)
void event_music_level_start(int force_soundtrack)
{
int i;
SOUNDTRACK_INFO *strack;
@@ -543,8 +558,7 @@ void event_music_level_init(int force_soundtrack)
if (Event_music_inited == FALSE)
return;
if (force_soundtrack != -1)
Current_soundtrack_num = force_soundtrack;
@@ -629,7 +643,7 @@ void event_music_first_pattern()
}
if ( Event_music_level_inited == FALSE ) {
event_music_level_init();
event_music_level_start();
}
if ( Event_music_level_inited == FALSE ) { //-V581
@@ -690,6 +704,7 @@ void event_music_level_close()
audiostream_close_all(0);
}
Current_soundtrack_num = -1;
Current_pattern = -1;
Event_music_level_inited = FALSE;
Event_Music_battle_started = FALSE;
@@ -1455,7 +1470,7 @@ void event_music_enable()
Event_music_enabled = TRUE;
if ( Event_music_level_inited == FALSE ) {
event_music_level_init();
event_music_level_start();
// start the first pattern to play (delayed)
if ( Game_mode & GM_IN_MISSION ) {
event_music_first_pattern();
@@ -1594,7 +1609,7 @@ int event_music_next_soundtrack(int delta)
new_soundtrack = 0;
event_music_level_close();
event_music_level_init(new_soundtrack);
event_music_level_start(new_soundtrack);
return Current_soundtrack_num;
}
@@ -1619,7 +1634,7 @@ void event_sexp_change_soundtrack(char *name)
event_music_level_close();
Current_soundtrack_num = -1;
event_music_level_init(new_soundtrack);
event_music_level_start(new_soundtrack);
}
// ----------------------------------------------------------------
@@ -1706,6 +1721,20 @@ void event_music_hostile_ship_destroyed()
Battle_over_timestamp = timestamp(BATTLE_CHECK_INTERVAL);
}
void event_music_set_volume(float volume)
{
Assertion(volume >= 0.0f && volume <= 1.0f, "Invalid event music volume %f!", volume);
Master_event_music_volume = volume;
event_music_set_volume_all(Master_event_music_volume);
if (Master_event_music_volume > 0.0f) {
event_music_enable();
} else {
event_music_disable();
}
}
#ifdef _MSC_VER
#pragma optimize("", on)
#endif
+7 -1
View File
@@ -97,7 +97,7 @@ extern int Num_soundtracks;
void event_music_init();
void event_music_close();
void event_music_level_init(int force_soundtrack = -1);
void event_music_level_start(int force_soundtrack = -1);
void event_music_level_close();
void event_music_do_frame();
void event_music_disable();
@@ -129,4 +129,10 @@ int event_music_player_respawn();
int event_music_player_respawn_as_observer();
void event_music_hostile_ship_destroyed();
/**
* @brief Sets the master music volume to the specified value
* @param volume The new music volume value. Must be in the range [0, 1].
*/
void event_music_set_volume(float volume);
#endif /* __EVENT_MUSIC_H__ */
+28 -20
View File
@@ -1207,29 +1207,37 @@ void parse_sound_table(const char* filename)
// parse flyby sound section
if (optional_string("#Flyby Sounds Start"))
{
char species_name_tag[NAME_LENGTH + 2];
int sanity_check = 0;
size_t i;
while (!check_for_string("#Flyby Sounds End") && (sanity_check <= (int)Species_info.size()))
// try parsing sounds for each species
// Note 1: instead of going through Species_info and requiring a sound for each species,
// we now parse the token and extract the species name from it
// Note 2: if a species doesn't have a flyby sound, the flyby code will just not play anything
while (!check_for_string("#Flyby Sounds End"))
{
for (i = 0; i < Species_info.size(); i++)
char species_name_tag[NAME_LENGTH + 2];
stuff_string_until(species_name_tag, ":", NAME_LENGTH + 2);
if (species_name_tag[0] != '$')
{
species_info *species = &Species_info[i];
sprintf(species_name_tag, "$%s:", species->species_name);
if (check_for_string(species_name_tag))
{
gamesnd_parse_line(&species->snd_flyby_fighter, species_name_tag);
gamesnd_parse_line(&species->snd_flyby_bomber, species_name_tag);
sanity_check--;
}
else
{
sanity_check++;
}
error_display(0, "Unexpected token tag %s", species_name_tag);
advance_to_eoln(nullptr);
continue;
}
int idx = species_info_lookup(&species_name_tag[1]);
if (idx < 0)
{
mprintf(("Skipping flyby sound for unknown species %s\n", &species_name_tag[1]));
advance_to_eoln(nullptr);
continue;
}
// now we have a known species
species_info *species = &Species_info[idx];
strcat_s(species_name_tag, ":"); // put back the terminator to restore the entire tag
// parse the two sounds for it
gamesnd_parse_line(&species->snd_flyby_fighter, ":"); // since we stuffed most of the tag, the : is all that remains on this line
gamesnd_parse_line(&species->snd_flyby_bomber, species_name_tag); // for the subsequent line we use required_string on the whole tag
}
required_string("#Flyby Sounds End");
+23 -6
View File
@@ -45,6 +45,12 @@
#define DIR_SEPARATOR_STR "/"
#endif
#ifndef NDEBUG
constexpr bool FSO_DEBUG = true;
#else
constexpr bool FSO_DEBUG = false;
#endif
typedef std::int32_t _fs_time_t; // time_t here is 64-bit and we need 32-bit
typedef std::int32_t fix;
@@ -226,12 +232,17 @@ extern int Global_error_count;
// To debug printf do this:
// mprintf(( "Error opening %s\n", filename ));
#ifndef NDEBUG
#define mprintf(args) outwnd_printf2 args
#define nprintf(args) outwnd_printf args
constexpr bool LoggingEnabled = true;
#else
#define mprintf(args)
#define nprintf(args)
#ifdef SCP_RELEASE_LOGGING
constexpr bool LoggingEnabled = true;
#else
constexpr bool LoggingEnabled = false;
#endif
#endif
#define mprintf(args) do { if (LoggingEnabled) { outwnd_printf2 args; } } while (false)
#define nprintf(args) do { if (LoggingEnabled) { outwnd_printf args; } } while (false)
#define LOCATION __FILE__,__LINE__
@@ -446,7 +457,7 @@ SCP_string dump_stacktrace();
// DEBUG compile time catch for dangerous uses of memset/memcpy/memmove
// This is disabled for VS2013 and lower since that doesn't support the necessary features
#if !defined(NDEBUG) && !defined(USING_THIRD_PARTY_LIBS) && (!defined(_MSC_VER) || _MSC_VER >= 1900)
#if SCP_COMPILER_CXX_AUTO_TYPE && SCP_COMPILER_CXX_STATIC_ASSERT && defined(SCP_HAVE_STD_IS_TRIVIALLY_COPYABLE)
#if SCP_COMPILER_CXX_AUTO_TYPE && SCP_COMPILER_CXX_STATIC_ASSERT && HAVE_STD_IS_TRIVIALLY_COPYABLE
// feature support seems to be: gcc clang msvc
// auto 4.4 2.9 2010
// std::is_trivial 4.5 ? 2012 (2010 only duplicates std::is_pod)
@@ -528,12 +539,18 @@ namespace std
#define memmove memmove_if_trivial_else_error
template<typename T, typename U>
void *memmove_if_trivial_else_error(T *memmove_dest, U *memmove_src, size_t count)
inline void *memmove_if_trivial_else_error(T *memmove_dest, U *memmove_src, size_t count)
{
static_assert(trivial_check<T>::value, "memmove on non-trivial object T");
static_assert(trivial_check<U>::value, "memmove on non-trivial object U");
return ptr_memmove(memmove_dest, memmove_src, count);
}
// Not really needed but else clang thinks ptr_memmove isn't used
inline void *memmove_if_trivial_else_error(void *memmove_dest, void *memmove_src, size_t count)
{
return ptr_memmove(memmove_dest, memmove_src, count);
}
}
// Put into global namespace
using std::memcpy_if_trivial_else_error;
+58 -7
View File
@@ -1,20 +1,20 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#include "globalincs/systemvars.h"
#include "debugconsole/console.h"
#include "globalincs/pstypes.h"
#include "globalincs/systemvars.h"
#include "graphics/2d.h"
#include "io/timer.h"
#include "nebula/neb.h"
#include "options/Option.h"
fix Missiontime;
fix Skybox_timestamp;
@@ -287,9 +287,60 @@ detail_levels Detail_defaults[NUM_DEFAULT_DETAIL_LEVELS] = {
},
};
// Global used to access detail levels in game and libs
detail_levels Detail = Detail_defaults[NUM_DEFAULT_DETAIL_LEVELS-1];
detail_levels Detail = Detail_defaults[NUM_DEFAULT_DETAIL_LEVELS - 1];
const SCP_vector<std::pair<int, SCP_string>> DetailLevelValues = {{ 0, "Minimum" },
{ 1, "Low" },
{ 2, "Medium" },
{ 3, "High" },
{ 4, "Ultra" }, };
const auto ModelDetailOption =
options::OptionBuilder<int>("Graphics.Detail", "Model Detail", "Detail level of models").importance(8).category(
"Graphics").values(DetailLevelValues).default_val(MAX_DETAIL_LEVEL).change_listener([](int val, bool) {
Detail.detail_distance = val;
return true;
}).finish();
const auto TexturesOption = options::OptionBuilder<int>("Graphics.Texture",
"3D Hardware Textures",
"Level of detail of textures").importance(6).category("Graphics").values(
DetailLevelValues).default_val(MAX_DETAIL_LEVEL).change_listener([](int val, bool) {
Detail.hardware_textures = val;
return true;
}).finish();
const auto ParticlesOption = options::OptionBuilder<int>("Graphics.Particles",
"Particles",
"Level of detail for particles").importance(5).category(
"Graphics").values(DetailLevelValues).default_val(MAX_DETAIL_LEVEL).change_listener([](int val, bool) {
Detail.num_particles = val;
return true;
}).finish();
const auto SmallDebrisOption =
options::OptionBuilder<int>("Graphics.SmallDebris", "Impact Effects", "Level of detail of impact effects").category(
"Graphics").values(DetailLevelValues).default_val(MAX_DETAIL_LEVEL).importance(4).change_listener([](int val,
bool) {
Detail.num_small_debris = val;
return true;
}).finish();
const auto ShieldEffectsOption = options::OptionBuilder<int>("Graphics.ShieldEffects",
"Shield Hit Effects",
"Level of detail of shield impacts").importance(3).category(
"Graphics").values(DetailLevelValues).default_val(MAX_DETAIL_LEVEL).change_listener([](int val, bool) {
Detail.shield_effects = val;
return true;
}).finish();
const auto StarsOption =
options::OptionBuilder<int>("Graphics.Stars", "Stars", "Number of stars in the mission").importance(2).category(
"Graphics").values(DetailLevelValues).default_val(MAX_DETAIL_LEVEL).change_listener([](int val, bool) {
Detail.num_stars = val;
return true;
}).finish();
// Call this with:
// 0 - lowest
+3
View File
@@ -147,6 +147,9 @@ SCP_string get_version_string()
case GR_OPENGL:
str += " OpenGL";
break;
case GR_VULKAN:
str += " Vulkan";
break;
}
return str;
+2 -2
View File
@@ -53,9 +53,9 @@ struct version {
int build = 0;
int revision = 0;
version() {}
version() = default;
version(int major, int minor, int build, int revision);
version(int major, int minor = 0, int build = 0, int revision = 0);
bool isValid() const;
+419 -99
View File
@@ -1,58 +1,57 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#ifdef _WIN32
#include <windows.h>
#include <windowsx.h>
#endif
#include <climits>
#include <algorithm>
#include "globalincs/alphacolors.h"
#include "globalincs/systemvars.h"
#include "2d.h"
#include "grinternal.h"
#include "grstub.h"
#include "light.h"
#include "material.h"
#include "matrix.h"
#include "cmdline/cmdline.h"
#include "debugconsole/console.h"
#include "gamesequence/gamesequence.h" //WMC - for scripting hooks in gr_flip()
#include "globalincs/systemvars.h"
#include "graphics/2d.h"
#include "graphics/font.h"
#include "graphics/grbatch.h"
#include "graphics/grinternal.h"
#include "graphics/grstub.h"
#include "graphics/light.h"
#include "graphics/matrix.h"
#include "graphics/opengl/gropengl.h"
#include "graphics/paths/PathRenderer.h"
#include "graphics/util/GPUMemoryHeap.h"
#include "graphics/util/UniformBuffer.h"
#include "graphics/util/UniformBufferManager.h"
#include "io/keycontrol.h" // m!m
#include "io/timer.h"
#include "graphics/vulkan/gr_vulkan.h"
#include "io/mouse.h"
#include "libs/jansson.h"
#include "options/Option.h"
#include "osapi/osapi.h"
#include "parse/parselo.h"
#include "popup/popup.h"
#include "render/3d.h"
#include "scripting/hook_api.h"
#include "scripting/scripting.h"
#include "tracing/tracing.h"
#include "utils/boost/hash_combine.h"
#if ( SDL_VERSION_ATLEAST(1, 2, 7) )
#include <SDL_surface.h>
#include <algorithm>
#include <climits>
#if (SDL_VERSION_ATLEAST(1, 2, 7))
#include "SDL_cpuinfo.h"
#endif
#include "SDL_surface.h"
#include "material.h"
const char *Resolution_prefixes[GR_NUM_RESOLUTIONS] = { "", "2_" };
const char* Resolution_prefixes[GR_NUM_RESOLUTIONS] = {"", "2_"};
screen gr_screen;
@@ -73,12 +72,107 @@ int Gr_inited = 0;
uint Gr_signature = 0;
float Gr_gamma = 1.8f;
int Gr_gamma_int = 180;
float Gr_gamma = 1.0f;
static SCP_vector<float> gamma_value_enumerator()
{
SCP_vector<float> vals;
// We want to divide the possible values into increments of 0.05
constexpr auto UPPER_LIMIT = (int)(5.0 / 0.05);
for (int i = 2; i <= UPPER_LIMIT; ++i) {
vals.push_back(0.05f * i);
}
return vals;
}
static SCP_string gamma_display(float value)
{
SCP_string out;
sprintf(out, "%.2f", value);
return out;
}
static bool gamma_change_listener(float new_val, bool initial)
{
if (!initial) {
// This is not valid for the initial config load since that happens before the graphics system is initialized
gr_set_gamma(new_val);
} else {
Gr_gamma = new_val;
}
return true;
}
static auto GammaOption =
options::OptionBuilder<float>("Graphics.Gamma", "Brightness", "The brighness value used for the game window")
.category("Graphics")
.default_val(1.0f)
.enumerator(gamma_value_enumerator)
.display(gamma_display)
.change_listener(gamma_change_listener)
.finish();
const SCP_vector<std::pair<int, SCP_string>> DetailLevelValues = {{ 0, "Minimum" },
{ 1, "Low" },
{ 2, "Medium" },
{ 3, "High" },
{ 4, "Ultra" }, };
const auto LightingOption = options::OptionBuilder<int>("Graphics.Lighting", "Lighting", "Level of detail of the lighting")
.importance(1)
.category("Graphics")
.values(DetailLevelValues)
.default_val(MAX_DETAIL_LEVEL)
.change_listener([](int val, bool initial) {
Detail.lighting = val;
if (!initial) {
gr_recompile_all_shaders(nullptr);
}
return true;
})
.finish();
os::ViewportState Gr_configured_window_state = os::ViewportState::Windowed;
static bool mode_change_func(os::ViewportState state, bool initial)
{
Gr_configured_window_state = state;
if (initial) {
return false;
}
auto window = os::getMainViewport();
if (window == nullptr) {
return false;
}
window->setState(state);
return true;
}
static auto WindowModeOption = options::OptionBuilder<os::ViewportState>("Graphics.WindowMode", "Window Mode",
"Controls how the game window is created.")
.category("Graphics")
.level(options::ExpertLevel::Beginner)
.values({{os::ViewportState::Fullscreen, "Fullscreen"},
{os::ViewportState::Borderless, "Borderless"},
{os::ViewportState::Windowed, "Windowed"}})
.importance(98)
.default_val(os::ViewportState::Fullscreen)
.change_listener(mode_change_func)
.finish();
const std::shared_ptr<scripting::OverridableHook> OnFrameHook = scripting::OverridableHook::Factory(
"On Frame", "Called every frame as the last action before showing the frame result to the user.", {}, CHA_ONFRAME);
// z-buffer stuff
int gr_zbuffering = 0;
int gr_zbuffering_mode = 0;
int gr_zbuffering = 0;
int gr_zbuffering_mode = 0;
int gr_global_zbuffering = 0;
// stencil buffer stuff
@@ -108,6 +202,8 @@ bool Save_custom_screen_size;
bool Deferred_lighting = false;
bool High_dynamic_range = false;
static ushort* Gr_original_gamma_ramp = nullptr;
static int videodisplay_deserializer(const json_t* value)
{
int id;
@@ -219,7 +315,7 @@ static ResolutionInfo resolution_default()
if (SDL_GetDesktopDisplayMode(VideoDisplayOption->getValue(), &mode) != 0) {
return {};
}
return ResolutionInfo(mode.w, mode.h);
return {(uint32_t)mode.w, (uint32_t)mode.h};
}
static bool resolution_change(const ResolutionInfo& /*info*/, bool initial)
{
@@ -348,6 +444,8 @@ static auto VSyncOption = options::OptionBuilder<bool>("Graphis.VSync", "Vertica
.importance(70)
.finish();
static std::unique_ptr<graphics::util::UniformBufferManager> UniformBufferManager;
// Forward definitions
static void uniform_buffer_managers_init();
static void uniform_buffer_managers_deinit();
@@ -356,7 +454,8 @@ static void uniform_buffer_managers_retire_buffers();
static void gpu_heap_init();
static void gpu_heap_deinit();
void gr_set_screen_scale(int w, int h, int zoom_w, int zoom_h, int max_w, int max_h, int center_w, int center_h, bool force_stretch)
void gr_set_screen_scale(int w, int h, int zoom_w, int zoom_h, int max_w, int max_h, int center_w, int center_h,
bool force_stretch)
{
bool do_zoom = zoom_w > 0 && zoom_h > 0 && (zoom_w != w || zoom_h != h);
@@ -895,6 +994,15 @@ void gr_close()
return;
}
if (Gr_original_gamma_ramp != nullptr && os::getSDLMainWindow() != nullptr) {
SDL_SetWindowGammaRamp(os::getSDLMainWindow(), Gr_original_gamma_ramp, (Gr_original_gamma_ramp + 256),
(Gr_original_gamma_ramp + 512));
}
// This is valid even if Gr_original_gamma_ramp is nullptr
vm_free(Gr_original_gamma_ramp);
Gr_original_gamma_ramp = nullptr;
gpu_heap_deinit();
// Cleanup uniform buffer managers
@@ -1014,12 +1122,108 @@ int gr_get_resolution_class(int width, int height)
}
}
static bool gr_init_sub(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, int mode, int width, int height, int depth, float center_aspect_ratio)
static void init_colors()
{
int bpp = gr_screen.bits_per_pixel;
Assertion((bpp == 16) || (bpp == 32), "Invalid bits-per-pixel value %d!", bpp);
// screen format
switch (bpp) {
case 16: {
Gr_red.bits = 5;
Gr_red.shift = 11;
Gr_red.scale = 8;
Gr_red.mask = 0xF800;
Gr_green.bits = 6;
Gr_green.shift = 5;
Gr_green.scale = 4;
Gr_green.mask = 0x7E0;
Gr_blue.bits = 5;
Gr_blue.shift = 0;
Gr_blue.scale = 8;
Gr_blue.mask = 0x1F;
break;
}
case 32: {
Gr_red.bits = 8;
Gr_red.shift = 16;
Gr_red.scale = 1;
Gr_red.mask = 0xff0000;
Gr_green.bits = 8;
Gr_green.shift = 8;
Gr_green.scale = 1;
Gr_green.mask = 0x00ff00;
Gr_blue.bits = 8;
Gr_blue.shift = 0;
Gr_blue.scale = 1;
Gr_blue.mask = 0x0000ff;
Gr_alpha.bits = 8;
Gr_alpha.shift = 24;
Gr_alpha.mask = 0xff000000;
Gr_alpha.scale = 1;
break;
}
}
// texture format
Gr_t_red.bits = 5;
Gr_t_red.mask = 0x7c00;
Gr_t_red.shift = 10;
Gr_t_red.scale = 8;
Gr_t_green.bits = 5;
Gr_t_green.mask = 0x03e0;
Gr_t_green.shift = 5;
Gr_t_green.scale = 8;
Gr_t_blue.bits = 5;
Gr_t_blue.mask = 0x001f;
Gr_t_blue.shift = 0;
Gr_t_blue.scale = 8;
Gr_t_alpha.bits = 1;
Gr_t_alpha.mask = 0x8000;
Gr_t_alpha.scale = 255;
Gr_t_alpha.shift = 15;
// alpha-texture format
Gr_ta_red.bits = 4;
Gr_ta_red.mask = 0x0f00;
Gr_ta_red.shift = 8;
Gr_ta_red.scale = 17;
Gr_ta_green.bits = 4;
Gr_ta_green.mask = 0x00f0;
Gr_ta_green.shift = 4;
Gr_ta_green.scale = 17;
Gr_ta_blue.bits = 4;
Gr_ta_blue.mask = 0x000f;
Gr_ta_blue.shift = 0;
Gr_ta_blue.scale = 17;
Gr_ta_alpha.bits = 4;
Gr_ta_alpha.mask = 0xf000;
Gr_ta_alpha.shift = 12;
Gr_ta_alpha.scale = 17;
}
static bool gr_init_sub(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, int mode, int width, int height,
int depth, float center_aspect_ratio)
{
int res = GR_1024;
bool rc = false;
memset( &gr_screen, 0, sizeof(screen) );
memset(&gr_screen, 0, sizeof(screen));
float aspect_ratio = (float)width / (float)height;
@@ -1104,26 +1308,31 @@ static bool gr_init_sub(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, i
gr_screen.clip_center_y = (gr_screen.clip_top + gr_screen.clip_bottom) * 0.5f;
if (gr_screen.custom_size) {
gr_unsize_screen_pos( &gr_screen.max_w_unscaled, &gr_screen.max_h_unscaled );
gr_unsize_screen_pos( &gr_screen.max_w_unscaled_zoomed, &gr_screen.max_h_unscaled_zoomed );
gr_unsize_screen_pos( &gr_screen.clip_right_unscaled, &gr_screen.clip_bottom_unscaled );
gr_unsize_screen_pos( &gr_screen.clip_width_unscaled, &gr_screen.clip_height_unscaled );
gr_unsize_screen_pos(&gr_screen.max_w_unscaled, &gr_screen.max_h_unscaled);
gr_unsize_screen_pos(&gr_screen.max_w_unscaled_zoomed, &gr_screen.max_h_unscaled_zoomed);
gr_unsize_screen_pos(&gr_screen.clip_right_unscaled, &gr_screen.clip_bottom_unscaled);
gr_unsize_screen_pos(&gr_screen.clip_width_unscaled, &gr_screen.clip_height_unscaled);
}
gr_screen.save_max_w_unscaled = gr_screen.max_w_unscaled;
gr_screen.save_max_h_unscaled = gr_screen.max_h_unscaled;
gr_screen.save_max_w_unscaled = gr_screen.max_w_unscaled;
gr_screen.save_max_h_unscaled = gr_screen.max_h_unscaled;
gr_screen.save_max_w_unscaled_zoomed = gr_screen.max_w_unscaled_zoomed;
gr_screen.save_max_h_unscaled_zoomed = gr_screen.max_h_unscaled_zoomed;
init_colors();
switch (mode) {
case GR_OPENGL:
rc = gr_opengl_init(std::move(graphicsOps));
break;
case GR_STUB:
rc = gr_stub_init();
break;
default:
Int3(); // Invalid graphics mode
case GR_OPENGL:
rc = gr_opengl_init(std::move(graphicsOps));
break;
case GR_VULKAN:
rc = graphics::vulkan::initialize(std::move(graphicsOps));
break;
case GR_STUB:
rc = gr_stub_init();
break;
default:
Int3(); // Invalid graphics mode
}
if ( !rc ) {
@@ -1245,6 +1454,17 @@ bool gr_init(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, int d_mode,
if (sscanf(ptr + 5, "(%dx%d)x%d ", &width, &height, &depth) != 3) {
Error(LOCATION, "Can't understand 'VideocardFs2open' config entry!");
}
// Get the first 4 characters of the video string which is the chosen API
SCP_string videoApi(ptr, ptr + 4);
if (videoApi == "OGL ") {
d_mode = GR_OPENGL; // GR_OPENGL;
} else if (videoApi == "VK ") {
d_mode = GR_VULKAN;
} else {
ReleaseWarning(LOCATION, "Unknown video API '%s'", videoApi.c_str());
}
}
if (Cmdline_res != nullptr) {
@@ -1368,6 +1588,10 @@ bool gr_init(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, int d_mode,
gpu_heap_init();
mprintf(("Checking graphics capabilities:\n"));
mprintf((" Persistent buffer mapping: %s\n",
gr_is_capable(CAPABILITY_PERSISTENT_BUFFER_MAPPING) ? "Enabled" : "Disabled"));
bool missing_installation = false;
if (!running_unittests && Web_cursor == nullptr) {
if (Is_standalone) {
@@ -1398,6 +1622,17 @@ bool gr_init(std::unique_ptr<os::GraphicsOperations>&& graphicsOps, int d_mode,
gr_set_shader(NULL);
if (!Is_standalone) {
if (Using_in_game_options) {
// The value should have been loaded into the variable already so we can use that here
gr_set_gamma(Gr_gamma);
} else {
// D3D's gamma system now works differently. 1.0 is the default value
ptr = os_config_read_string(nullptr, NOX("GammaD3D"), NOX("1.0"));
gr_set_gamma((float)atof(ptr));
}
}
Gr_inited = 1;
return true;
@@ -1409,15 +1644,6 @@ void gr_force_windowed()
return;
}
switch( gr_screen.mode ) {
case GR_OPENGL:
break;
case GR_STUB:
break;
default:
Int3(); // Invalid graphics mode
}
if ( Os_debugger_running ) {
os_sleep(1000);
}
@@ -1437,7 +1663,7 @@ void gr_activate(int active)
}
if (active) {
if (Cmdline_fullscreen_window||Cmdline_window) {
if (Cmdline_fullscreen_window || Cmdline_window) {
os::getMainViewport()->restore();
} else {
os::getMainViewport()->setState(os::ViewportState::Fullscreen);
@@ -1446,17 +1672,11 @@ void gr_activate(int active)
os::getMainViewport()->minimize();
}
switch( gr_screen.mode ) {
case GR_OPENGL:
extern void gr_opengl_activate(int active);
gr_opengl_activate(active);
break;
case GR_STUB:
break;
default:
Int3(); // Invalid graphics mode
if (active) {
if (!Cmdline_fullscreen_window && !Cmdline_window) {
gr_set_gamma(Gr_gamma);
}
}
}
// color stuff
@@ -1994,7 +2214,7 @@ int poly_list::find_first_vertex_fast(int idx)
if ( first_idx == sorted_indices + n_verts ) {
// if this happens then idx was never in the index list to begin with which is not good
mprintf(("Sorted index list missing index %d!", idx));
mprintf(("Sorted index list missing index %d!\n", idx));
Int3();
return idx;
}
@@ -2377,26 +2597,51 @@ bool poly_list::finder::operator()(const uint a, const uint b)
void gr_set_bitmap(int bitmap_num, int alphablend_mode, int bitblt_mode, float alpha)
{
gr_screen.current_alpha = alpha;
gr_screen.current_alpha = alpha;
gr_screen.current_alphablend_mode = alphablend_mode;
gr_screen.current_bitblt_mode = bitblt_mode;
gr_screen.current_bitmap = bitmap_num;
gr_screen.current_bitblt_mode = bitblt_mode;
gr_screen.current_bitmap = bitmap_num;
}
static void output_uniform_debug_data()
{
int line_height = gr_get_font_height() + 1;
gr_set_color_fast(&Color_bright_white);
gr_printf_no_resize(gr_screen.center_offset_x + 20, gr_screen.center_offset_y + 160,
"Uniform buffer size: " SIZE_T_ARG, UniformBufferManager->getBufferSize());
gr_printf_no_resize(gr_screen.center_offset_x + 20, gr_screen.center_offset_y + 160 + line_height,
"Currently used data: " SIZE_T_ARG, UniformBufferManager->getCurrentlyUsedSize());
}
void gr_flip(bool execute_scripting)
{
TRACE_SCOPE(tracing::PageFlip);
// m!m avoid running CHA_ONFRAME when the "Quit mission" popup is shown. See mantis 2446 for reference
if (execute_scripting && !popup_active()) {
TRACE_SCOPE(tracing::LuaOnFrame);
//WMC - Do conditional hooks. Yippee!
Script_system.RunCondition(CHA_ONFRAME);
//WMC - Do scripting reset stuff
// WMC - Do conditional hooks. Yippee!
OnFrameHook->run();
// WMC - Do scripting reset stuff
Script_system.EndFrame();
}
gr_reset_immediate_buffer();
// Do per frame operations on the matrix state
gr_matrix_on_frame();
gr_reset_clip();
mouse_reset_deltas();
if (Cmdline_graphics_debug_output) {
output_uniform_debug_data();
}
// Use this opportunity for retiring the uniform buffers
uniform_buffer_managers_retire_buffers();
@@ -2413,32 +2658,13 @@ void gr_print_timestamp(int x, int y, fix timestamp, int resize_mode)
gr_string(x, y, time.c_str(), resize_mode);
}
static void uniform_buffer_managers_init() { UniformBufferManager.reset(new graphics::util::UniformBufferManager()); }
static void uniform_buffer_managers_deinit() { UniformBufferManager.reset(); }
static void uniform_buffer_managers_retire_buffers() { UniformBufferManager->onFrameEnd(); }
static std::unique_ptr<graphics::util::UniformBufferManager>
uniform_buffer_managers[static_cast<size_t>(uniform_block_type::NUM_BLOCK_TYPES)];
static void uniform_buffer_managers_init() {
for (size_t i = 0; i < static_cast<size_t>(uniform_block_type::NUM_BLOCK_TYPES); ++i) {
auto enumVal = static_cast<uniform_block_type>(i);
uniform_buffer_managers[i].reset(new graphics::util::UniformBufferManager(enumVal));
}
}
static void uniform_buffer_managers_deinit() {
for (auto& manager: uniform_buffer_managers) {
manager.reset();
}
}
static void uniform_buffer_managers_retire_buffers() {
GR_DEBUG_SCOPE("Retiring unused uniform buffers");
for (auto& manager: uniform_buffer_managers) {
manager->retireBuffers();
}
}
graphics::util::UniformBuffer* gr_get_uniform_buffer(uniform_block_type type) {
return uniform_buffer_managers[static_cast<size_t>(type)]->getBuffer();
graphics::util::UniformBuffer gr_get_uniform_buffer(uniform_block_type type, size_t num_elements, size_t element_size_override)
{
return UniformBufferManager->getUniformBuffer(type, num_elements, element_size_override);
}
SCP_vector<DisplayData> gr_enumerate_displays()
@@ -2597,10 +2823,104 @@ void gr_heap_allocate(GpuHeap heap_type, size_t size, void* data, size_t& offset
handle_out = gpuHeap->bufferHandle();
}
void gr_heap_deallocate(GpuHeap heap_type, size_t data_offset) {
void gr_heap_deallocate(GpuHeap heap_type, size_t data_offset)
{
TRACE_SCOPE(tracing::GpuHeapDeallocate);
auto gpuHeap = get_gpu_heap(heap_type);
gpuHeap->freeGpuData(data_offset);
}
// I feel dirty...
static void make_gamma_ramp(float gamma, ushort* ramp)
{
ushort x, y;
ushort base_ramp[256];
Assert(ramp != nullptr);
// generate the base ramp values first off
// if no gamma set then just do this quickly
if (gamma <= 0.0f) {
memset(ramp, 0, 3 * 256 * sizeof(ushort));
return;
}
// identity gamma, avoid all of the math
else if (gamma == 1.0f || Gr_original_gamma_ramp == nullptr) {
if (Gr_original_gamma_ramp != nullptr) {
memcpy(ramp, Gr_original_gamma_ramp, 3 * 256 * sizeof(ushort));
}
// set identity if no original ramp
else {
for (x = 0; x < 256; x++) {
ramp[x] = (x << 8) | x;
ramp[x + 256] = (x << 8) | x;
ramp[x + 512] = (x << 8) | x;
}
}
return;
}
// for everything else we need to actually figure it up
else {
double g = 1.0 / (double)gamma;
double val;
Assert(Gr_original_gamma_ramp != nullptr);
for (x = 0; x < 256; x++) {
val = (pow(x / 255.0, g) * 65535.0 + 0.5);
CLAMP(val, 0, 65535);
base_ramp[x] = (ushort)val;
}
for (y = 0; y < 3; y++) {
for (x = 0; x < 256; x++) {
val = (base_ramp[x] * 2) - Gr_original_gamma_ramp[x + y * 256];
CLAMP(val, 0, 65535);
ramp[x + y * 256] = (ushort)val;
}
}
}
}
void gr_set_gamma(float gamma)
{
Gr_gamma = gamma;
// new way - but not while running FRED
if (!Fred_running && !Cmdline_no_set_gamma && os::getSDLMainWindow() != nullptr) {
if (Gr_original_gamma_ramp == nullptr) {
// First time we are here so get the current (original) gamma ramp here so we can reset it later
Gr_original_gamma_ramp = (ushort*)vm_malloc(3 * 256 * sizeof(ushort), memory::quiet_alloc);
if (Gr_original_gamma_ramp == nullptr) {
mprintf((" Unable to allocate memory for gamma ramp! Disabling...\n"));
Cmdline_no_set_gamma = 1;
} else {
SDL_GetWindowGammaRamp(os::getSDLMainWindow(), Gr_original_gamma_ramp, (Gr_original_gamma_ramp + 256),
(Gr_original_gamma_ramp + 512));
}
}
auto gamma_ramp = (ushort*)vm_malloc(3 * 256 * sizeof(ushort), memory::quiet_alloc);
if (gamma_ramp == nullptr) {
Int3();
return;
}
memset(gamma_ramp, 0, 3 * 256 * sizeof(ushort));
// Create the Gamma lookup table
make_gamma_ramp(gamma, gamma_ramp);
SDL_SetWindowGammaRamp(os::getSDLMainWindow(), gamma_ramp, (gamma_ramp + 256), (gamma_ramp + 512));
vm_free(gamma_ramp);
}
}
+50 -30
View File
@@ -1,21 +1,20 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#ifndef _GRAPHICS_H
#define _GRAPHICS_H
#include "bmpman/bmpman.h"
#include "cfile/cfile.h"
#include "globalincs/flagset.h"
#include "globalincs/pstypes.h"
#include "bmpman/bmpman.h"
#include "cfile/cfile.h"
#include "graphics/grinternal.h"
#include "graphics/tmapper.h"
#include "io/cursor.h"
@@ -27,7 +26,10 @@ namespace graphics {
namespace util {
class UniformBuffer;
class GPUMemoryHeap;
}
} // namespace util
} // namespace graphics
namespace scripting {
class OverridableHook;
}
extern const float Default_min_draw_distance;
@@ -46,16 +48,16 @@ FLAG_LIST(FramebufferEffects){Thrusters = 0, Shockwaves, NUM_VALUES};
extern flagset<FramebufferEffects> Gr_framebuffer_effects;
enum class AntiAliasMode {
None,
None = 0,
FXAA_Low,
FXAA_Medium,
FXAA_High,
FXAA_Low = 1,
FXAA_Medium = 2,
FXAA_High = 3,
SMAA_Low,
SMAA_Medium,
SMAA_High,
SMAA_Ultra,
SMAA_Low = 4,
SMAA_Medium = 5,
SMAA_High = 6,
SMAA_Ultra = 7,
};
extern AntiAliasMode Gr_aa_mode;
extern AntiAliasMode Gr_aa_mode_last_frame;
@@ -70,6 +72,10 @@ extern bool Gr_enable_vsync;
extern bool Deferred_lighting;
extern bool High_dynamic_range;
extern os::ViewportState Gr_configured_window_state;
extern const std::shared_ptr<scripting::OverridableHook> OnFrameHook;
class material;
class model_material;
class particle_material;
@@ -240,6 +246,8 @@ enum class uniform_block_type {
DecalInfo = 3,
DecalGlobals = 4,
DeferredGlobals = 5,
Matrices = 6,
GenericData = 7,
NUM_BLOCK_TYPES
};
@@ -321,6 +329,7 @@ typedef enum gr_capability {
CAPABILITY_POINT_PARTICLES,
CAPABILITY_TIMESTAMP_QUERY,
CAPABILITY_SEPARATE_BLEND_FUNCTIONS,
CAPABILITY_PERSISTENT_BUFFER_MAPPING,
} gr_capability;
enum class gr_property {
@@ -623,11 +632,7 @@ enum class BufferType {
Uniform
};
enum class BufferUsageHint {
Static,
Dynamic,
Streaming
};
enum class BufferUsageHint { Static, Dynamic, Streaming, PersistentMapping };
/**
* @brief Type of a graphics sync object
@@ -726,9 +731,6 @@ typedef struct screen {
// Frees up a saved screen.
void (*gf_free_screen)(int id);
// Sets the gamma
void (*gf_set_gamma)(float gamma);
// grab a region of the screen. assumes data is large enough
void (*gf_get_region)(int front, int w, int h, ubyte *data);
@@ -759,8 +761,10 @@ typedef struct screen {
int (*gf_create_buffer)(BufferType type, BufferUsageHint usage);
void (*gf_delete_buffer)(int handle);
void (*gf_update_buffer_data)(int handle, size_t size, void* data);
void (*gf_update_buffer_data_offset)(int handle, size_t offset, size_t size, void* data);
void (*gf_update_buffer_data)(int handle, size_t size, const void* data);
void (*gf_update_buffer_data_offset)(int handle, size_t offset, size_t size, const void* data);
void* (*gf_map_buffer)(int handle);
void (*gf_flush_mapped_buffer)(int handle, size_t offset, size_t size);
void (*gf_update_transform_buffer)(void* data, size_t size);
// postprocessing effects
@@ -849,7 +853,8 @@ typedef struct screen {
// # Software Re-added by Kazan --- THIS HAS TO STAY -- It is used by standalone!
#define GR_DEFAULT (-1) // set to use default settings
#define GR_STUB (100)
#define GR_OPENGL (104) // Use OpenGl hardware renderer
#define GR_OPENGL (104) // Use OpenGl hardware renderer
#define GR_VULKAN (105) // Use Vulkan hardware renderer
// resolution constants - always keep resolutions in ascending order and starting from 0
#define GR_NUM_RESOLUTIONS 2
@@ -954,8 +959,6 @@ void gr_set_bitmap(int bitmap_num, int alphablend = GR_ALPHABLEND_NONE, int bitb
#define gr_restore_screen GR_CALL(gr_screen.gf_restore_screen)
#define gr_free_screen GR_CALL(gr_screen.gf_free_screen)
#define gr_set_gamma GR_CALL(gr_screen.gf_set_gamma)
#define gr_get_region GR_CALL(gr_screen.gf_get_region)
#define gr_set_cull GR_CALL(gr_screen.gf_set_cull)
@@ -990,6 +993,11 @@ inline int gr_create_buffer(BufferType type, BufferUsageHint usage)
#define gr_delete_buffer GR_CALL(gr_screen.gf_delete_buffer)
#define gr_update_buffer_data GR_CALL(gr_screen.gf_update_buffer_data)
#define gr_update_buffer_data_offset GR_CALL(gr_screen.gf_update_buffer_data_offset)
inline void* gr_map_buffer(int handle) { return gr_screen.gf_map_buffer(handle); }
inline void gr_flush_mapped_buffer(int handle, size_t offset, size_t size)
{
gr_screen.gf_flush_mapped_buffer(handle, offset, size);
}
#define gr_update_transform_buffer GR_CALL(gr_screen.gf_update_transform_buffer)
#define gr_scene_texture_begin GR_CALL(gr_screen.gf_scene_texture_begin)
@@ -1208,7 +1216,16 @@ enum AnimatedShader {
ANIMATED_SHADER_CLOAK = 2,
};
graphics::util::UniformBuffer* gr_get_uniform_buffer(uniform_block_type type);
/**
* @brief Retreives a uniform buffer for storing uniform block data
* @param type The type of uniform data that will be stored in the buffer
* @param num_elements The number of elements that will be used in the buffer
* @param element_size_override Override what the size of the element should be instead of relying on the preconfigured
* size for that block type
* @return A structure which gives access to a memory buffer where the uniform data can be stored
*/
graphics::util::UniformBuffer gr_get_uniform_buffer(uniform_block_type type, size_t num_elements,
size_t element_size_override = 0);
struct VideoModeData {
uint32_t width = 0;
@@ -1254,6 +1271,9 @@ void gr_heap_allocate(GpuHeap heap_type, size_t size, void* data, size_t& offset
*/
void gr_heap_deallocate(GpuHeap heap_type, size_t data_offset);
void gr_set_gamma(float gamma);
// Include this last to make the 2D rendering function available everywhere
#include "graphics/render.h"
+11 -15
View File
@@ -96,9 +96,10 @@ void decal_draw_list::globalShutdown() {
gr_delete_buffer(box_index_buffer);
}
decal_draw_list::decal_draw_list() {
_buffer = gr_get_uniform_buffer(uniform_block_type::DecalInfo);
auto& aligner = _buffer->aligner();
decal_draw_list::decal_draw_list(size_t num_decals)
{
_buffer = gr_get_uniform_buffer(uniform_block_type::DecalInfo, num_decals);
auto& aligner = _buffer.aligner();
// Initialize header data
auto header = aligner.getHeader<graphics::decal_globals>();
@@ -131,13 +132,12 @@ decal_draw_list::decal_draw_list() {
header->ambientLight.xyz.z += gr_light_emission[2];
}
decal_draw_list::~decal_draw_list() {
_buffer->finished();
}
void decal_draw_list::render() {
GR_DEBUG_SCOPE("Render decals");
TRACE_SCOPE(tracing::RenderDecals);
_buffer->submitData();
_buffer.submitData();
std::sort(_draws.begin(), _draws.end(), decal_draw_list::sort_draws);
@@ -149,20 +149,16 @@ void decal_draw_list::render() {
source.Ibuffer_handle = box_index_buffer;
// Bind the global data only once
gr_bind_uniform_buffer(uniform_block_type::DecalGlobals,
0,
sizeof(graphics::decal_globals),
_buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::DecalGlobals, 0, sizeof(graphics::decal_globals),
_buffer.bufferHandle());
gr_screen.gf_start_decal_pass();
for (auto& draw : _draws) {
GR_DEBUG_SCOPE("Draw single decal");
TRACE_SCOPE(tracing::RenderSingleDecal);
gr_bind_uniform_buffer(uniform_block_type::DecalInfo,
draw.uniform_offset,
sizeof(graphics::decal_info),
_buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::DecalInfo, draw.uniform_offset, sizeof(graphics::decal_info),
_buffer.bufferHandle());
gr_screen.gf_render_decals(&draw.draw_mat, PRIM_TYPE_TRIS, &layout, BOX_NUM_FACES, source);
}
@@ -180,7 +176,7 @@ void decal_draw_list::add_decal(int diffuse_bitmap,
return;
}
auto& aligner = _buffer->aligner();
auto& aligner = _buffer.aligner();
auto info = aligner.addTypedElement<graphics::decal_info>();
info->model_matrix = transform;
@@ -202,7 +198,7 @@ void decal_draw_list::add_decal(int diffuse_bitmap,
info->normal_index = normal_bitmap < 0 ? -1 : bm_get_array_index(normal_bitmap);
decal_draw_info current_draw;
current_draw.uniform_offset = aligner.getCurrentOffset();
current_draw.uniform_offset = _buffer.getBufferOffset(aligner.getCurrentOffset());
material_set_decal(&current_draw.draw_mat,
bm_get_base_frame(diffuse_bitmap),
+5 -10
View File
@@ -15,23 +15,19 @@ class decal_draw_list {
};
SCP_vector<decal_draw_info> _draws;
util::UniformBuffer* _buffer = nullptr;
util::UniformBuffer _buffer;
static bool sort_draws(const decal_draw_info& left, const decal_draw_info& right);
public:
decal_draw_list();
public:
explicit decal_draw_list(size_t num_decals);
~decal_draw_list();
decal_draw_list(const decal_draw_list&) = delete;
decal_draw_list& operator=(const decal_draw_list&) = delete;
void add_decal(int diffuse_bitmap,
int glow_bitmap,
int normal_bitmap,
float decal_timer,
const matrix4& transform,
float base_alpha);
void add_decal(int diffuse_bitmap, int glow_bitmap, int normal_bitmap, float decal_timer, const matrix4& transform,
float base_alpha);
void render();
@@ -39,5 +35,4 @@ class decal_draw_list {
static void globalShutdown();
};
}
+1 -1
View File
@@ -254,7 +254,7 @@ int generic_anim_stream(generic_anim *ga, const bool cache)
}
ga->bitmap_id = bm_load(frame_name);
if(ga->bitmap_id < 0) {
mprintf(("Cannot find first frame for eff streaming. eff Filename: %s", ga->filename));
mprintf(("Cannot find first frame for eff streaming. eff Filename: %s\n", ga->filename));
return -1;
}
if (snprintf(frame_name, MAX_FILENAME_LEN, "%s_0001", ga->filename) >= MAX_FILENAME_LEN) {
-1
View File
@@ -41,7 +41,6 @@ extern color_gun Gr_ta_red, Gr_ta_green, Gr_ta_blue, Gr_ta_alpha;
extern color_gun *Gr_current_red, *Gr_current_green, *Gr_current_blue, *Gr_current_alpha;
extern float Gr_gamma;
extern int Gr_gamma_int;
#define TCACHE_TYPE_AABITMAP 0 // HUD bitmap. All Alpha.
#define TCACHE_TYPE_NORMAL 1 // Normal bitmap. Alpha = 0.
+14 -13
View File
@@ -110,13 +110,9 @@ void gr_stub_save_mouse_area(int /*x*/, int /*y*/, int /*w*/, int /*h*/)
{
}
void gr_stub_update_buffer_data(int /*handle*/, size_t /*size*/, void* /*data*/)
{
}
void gr_stub_update_buffer_data(int /*handle*/, size_t /*size*/, const void* /*data*/) {}
void gr_stub_update_buffer_data_offset(int /*handle*/, size_t /*offset*/, size_t /*size*/, void* /*data*/)
{
}
void gr_stub_update_buffer_data_offset(int /*handle*/, size_t /*offset*/, size_t /*size*/, const void* /*data*/) {}
void gr_stub_update_transform_buffer(void* /*data*/, size_t /*size*/)
{
@@ -141,10 +137,6 @@ int gr_stub_set_color_buffer(int /*mode*/)
return 0;
}
void gr_stub_set_gamma(float /*gamma*/)
{
}
void gr_stub_set_tex_env_scale(float /*scale*/)
{
}
@@ -349,6 +341,15 @@ bool gr_stub_is_capable(gr_capability /*capability*/)
{
return false;
}
bool gr_stub_get_property(gr_property p, void* dest)
{
if (p == gr_property::UNIFORM_BUFFER_OFFSET_ALIGNMENT) {
// This is required by the startup code of the uniform buffer manager
*reinterpret_cast<int*>(dest) = 4;
return true;
}
return false;
};
void gr_stub_push_debug_group(const char*){
}
@@ -429,8 +430,6 @@ bool gr_stub_init()
gr_screen.gf_save_screen = gr_stub_save_screen;
gr_screen.gf_restore_screen = gr_stub_restore_screen;
gr_screen.gf_free_screen = gr_stub_free_screen;
gr_screen.gf_set_gamma = gr_stub_set_gamma;
// UnknownPlayer : Don't recognize this - MAY NEED DEBUGGING
gr_screen.gf_get_region = gr_stub_get_region;
@@ -461,6 +460,8 @@ bool gr_stub_init()
gr_screen.gf_update_transform_buffer = gr_stub_update_transform_buffer;
gr_screen.gf_update_buffer_data = gr_stub_update_buffer_data;
gr_screen.gf_update_buffer_data_offset = gr_stub_update_buffer_data_offset;
gr_screen.gf_map_buffer = [](int) -> void* { return nullptr; };
gr_screen.gf_flush_mapped_buffer = [](int, size_t, size_t) {};
gr_screen.gf_post_process_set_effect = gr_stub_post_process_set_effect;
gr_screen.gf_post_process_set_defaults = gr_stub_post_process_set_defaults;
@@ -504,7 +505,7 @@ bool gr_stub_init()
gr_screen.gf_render_rocket_primitives = gr_stub_render_rocket_primitives;
gr_screen.gf_is_capable = gr_stub_is_capable;
gr_screen.gf_get_property = [](gr_property,void*) { return false; };
gr_screen.gf_get_property = gr_stub_get_property;
gr_screen.gf_push_debug_group = gr_stub_push_debug_group;
gr_screen.gf_pop_debug_group = gr_stub_pop_debug_group;
+2
View File
@@ -134,6 +134,8 @@ void material_set_rocket_interface(interface_material* mat_info, int texture, co
mat_info->set_depth_mode(ZBUFFER_TYPE_NONE);
mat_info->set_blend_mode(ALPHA_BLEND_ALPHA_BLEND_ALPHA);
mat_info->set_texture_type(material::TEX_TYPE_INTERFACE);
}
void material_set_movie(movie_material* mat_info, int y_bm, int u_bm, int v_bm) {
+64 -9
View File
@@ -1,6 +1,10 @@
#include "matrix.h"
#include "graphics/util/UniformBuffer.h"
#include <graphics/util/uniform_structs.h>
transform_stack gr_model_matrix_stack;
matrix4 gr_view_matrix;
matrix4 gr_model_view_matrix;
@@ -11,16 +15,17 @@ matrix4 gr_last_view_matrix;
matrix4 gr_texture_matrix;
matrix4 gr_env_texture_matrix;
static bool gr_env_texture_matrix_set = false;
bool gr_htl_projection_matrix_set = false;
static int modelview_matrix_depth = 1;
static bool htl_view_matrix_set = false;
static int htl_2d_matrix_depth = 0;
static bool htl_2d_matrix_set = false;
static bool htl_view_matrix_set = false;
static int htl_2d_matrix_depth = 0;
static bool htl_2d_matrix_set = false;
static matrix4 create_view_matrix(const vec3d *pos, const matrix *orient)
static bool matrix_uniform_up_to_date = false;
static matrix4 create_view_matrix(const vec3d* pos, const matrix* orient)
{
vec3d scaled_pos;
vec3d inv_pos;
@@ -82,6 +87,8 @@ void gr_start_instance_matrix(const vec3d *offset, const matrix *rotation)
vm_matrix4_x_matrix4(&gr_model_view_matrix, &gr_view_matrix, &model_matrix);
modelview_matrix_depth++;
matrix_uniform_up_to_date = false;
}
void gr_start_angles_instance_matrix(const vec3d *pos, const angles *rotation)
@@ -104,6 +111,8 @@ void gr_end_instance_matrix()
vm_matrix4_x_matrix4(&gr_model_view_matrix, &gr_view_matrix, &model_matrix);
modelview_matrix_depth--;
matrix_uniform_up_to_date = false;
}
// the projection matrix; fov, aspect ratio, near, far
@@ -127,6 +136,8 @@ void gr_set_proj_matrix(float fov, float aspect, float z_near, float z_far) {
}
gr_htl_projection_matrix_set = true;
matrix_uniform_up_to_date = false;
}
void gr_end_proj_matrix() {
@@ -142,6 +153,8 @@ void gr_end_proj_matrix() {
}
gr_htl_projection_matrix_set = false;
matrix_uniform_up_to_date = false;
}
void gr_set_view_matrix(const vec3d *pos, const matrix *orient)
@@ -154,8 +167,6 @@ void gr_set_view_matrix(const vec3d *pos, const matrix *orient)
gr_model_view_matrix = gr_view_matrix;
if (Cmdline_env) {
gr_env_texture_matrix_set = true;
// setup the texture matrix which will make the the envmap keep lined
// up properly with the environment
@@ -177,6 +188,8 @@ void gr_set_view_matrix(const vec3d *pos, const matrix *orient)
modelview_matrix_depth = 2;
htl_view_matrix_set = true;
matrix_uniform_up_to_date = false;
}
void gr_end_view_matrix()
@@ -189,7 +202,8 @@ void gr_end_view_matrix()
modelview_matrix_depth = 1;
htl_view_matrix_set = false;
gr_env_texture_matrix_set = false;
matrix_uniform_up_to_date = false;
}
// set a view and projection matrix for a 2D element
@@ -228,6 +242,8 @@ void gr_set_2d_matrix(/*int x, int y, int w, int h*/)
htl_2d_matrix_set = true;
htl_2d_matrix_depth++;
matrix_uniform_up_to_date = false;
}
// ends a previously set 2d view and projection matrix
@@ -252,6 +268,8 @@ void gr_end_2d_matrix()
htl_2d_matrix_set = false;
htl_2d_matrix_depth = 0;
matrix_uniform_up_to_date = false;
}
static bool scale_matrix_set = false;
@@ -269,6 +287,8 @@ void gr_push_scale_matrix(const vec3d *scale_factor)
auto model_matrix = gr_model_matrix_stack.get_transform();
vm_matrix4_x_matrix4(&gr_model_view_matrix, &gr_view_matrix, &model_matrix);
matrix_uniform_up_to_date = false;
}
void gr_pop_scale_matrix()
@@ -283,6 +303,8 @@ void gr_pop_scale_matrix()
modelview_matrix_depth--;
scale_matrix_set = false;
matrix_uniform_up_to_date = false;
}
void gr_setup_viewport() {
if (Gr_inited) {
@@ -300,6 +322,8 @@ void gr_setup_viewport() {
} else {
create_orthographic_projection_matrix(&gr_projection_matrix, 0, i2fl(gr_screen.max_w), i2fl(gr_screen.max_h), 0, -1, 1);
}
matrix_uniform_up_to_date = false;
}
void gr_reset_matrices() {
vm_matrix4_set_identity(&gr_projection_matrix);
@@ -312,12 +336,43 @@ void gr_reset_matrices() {
gr_model_matrix_stack.clear();
vm_matrix4_set_identity(&gr_texture_matrix);
matrix_uniform_up_to_date = false;
}
void gr_set_texture_panning(float u, float v, bool enable) {
void gr_set_texture_panning(float u, float v, bool enable)
{
vm_matrix4_set_identity(&gr_texture_matrix);
if (enable) {
gr_texture_matrix.a2d[3][0] = u;
gr_texture_matrix.a2d[3][1] = v;
}
}
void gr_matrix_on_frame()
{
// The old uniform state is now out of date and should not be used anymore
matrix_uniform_up_to_date = false;
}
void gr_matrix_set_uniforms()
{
if (matrix_uniform_up_to_date) {
// No changes since last time, no need to update
return;
}
GR_DEBUG_SCOPE("Updating matrix uniforms");
auto uniform_buffer = gr_get_uniform_buffer(uniform_block_type::Matrices, 1);
auto& aligner = uniform_buffer.aligner();
auto matrix_data = aligner.addTypedElement<graphics::matrix_uniforms>();
matrix_data->modelViewMatrix = gr_model_view_matrix;
matrix_data->projMatrix = gr_projection_matrix;
uniform_buffer.submitData();
gr_bind_uniform_buffer(uniform_block_type::Matrices, uniform_buffer.getBufferOffset(0),
sizeof(graphics::matrix_uniforms), uniform_buffer.bufferHandle());
matrix_uniform_up_to_date = true;
}
+13 -3
View File
@@ -9,14 +9,16 @@ extern matrix4 gr_projection_matrix;
extern matrix4 gr_last_projection_matrix;
extern matrix4 gr_env_texture_matrix;
void gr_start_instance_matrix(const vec3d *offset, const matrix *rotation);
void gr_start_angles_instance_matrix(const vec3d *pos, const angles *rotation);
void gr_matrix_on_frame();
void gr_start_instance_matrix(const vec3d* offset, const matrix* rotation);
void gr_start_angles_instance_matrix(const vec3d* pos, const angles* rotation);
void gr_end_instance_matrix();
void gr_set_proj_matrix(float fov, float aspect, float z_near, float z_far);
void gr_end_proj_matrix();
void gr_set_view_matrix(const vec3d *pos, const matrix *orient);
void gr_set_view_matrix(const vec3d* pos, const matrix* orient);
void gr_end_view_matrix();
void gr_set_2d_matrix(/*int x, int y, int w, int h*/);
@@ -32,3 +34,11 @@ void gr_reset_matrices();
extern matrix4 gr_texture_matrix;
void gr_set_texture_panning(float u, float v, bool enable);
/**
* @brief Set current matrix uniforms
*
* Use this before rendering with a shader requiring the matrix uniforms so that the matrix uniform block point has the
* up-to-date data.
*/
void gr_matrix_set_uniforms();
+15 -537
View File
@@ -234,568 +234,46 @@ size_t opengl::ShaderUniforms::findUniform(const SCP_string& name)
if (iter == _uniform_lookup.end()) {
return INVALID_SIZE;
}
else {
} else {
return iter->second;
}
}
void opengl::ShaderUniforms::setUniformi(const SCP_string &name, const int val)
void opengl::ShaderUniforms::setTextureUniform(const SCP_string& name, const int texture_unit)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()),
"The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
bool resident = false;
if (uniform_index != (size_t)-1) {
if (uniform_index != INVALID_SIZE) {
Assert(uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
uniform_bind* bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::INT) {
if (_uniform_data_ints[bind_info->index] == val) {
return;
}
_uniform_data_ints[bind_info->index] = val;
resident = true;
if (bind_info->value == texture_unit) {
return;
}
bind_info->value = texture_unit;
resident = true;
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
_uniform_data_ints.push_back(val);
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_ints.size() - 1;
new_bind.type = uniform_bind::INT;
new_bind.name = name;
new_bind.name = name;
new_bind.value = texture_unit;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform1i(findUniformLocation(name.c_str()), val);
glUniform1i(findUniformLocation(name.c_str()), texture_unit);
}
void opengl::ShaderUniforms::setUniform1iv(const SCP_string &name, const int count, const int *val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
auto uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != INVALID_SIZE) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::INT && bind_info->count == count) {
bool equal = true;
// if the values are close enough, pass.
for (int i = 0; i < count; ++i) {
if (val[i] != _uniform_data_ints[bind_info->index + i]) {
equal = false;
break;
}
}
if (equal) {
return;
}
resident = true;
for (int i = 0; i < count; ++i) {
_uniform_data_ints[bind_info->index + i] = val[i];
}
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
for (int i = 0; i < count; ++i) {
_uniform_data_ints.push_back(val[i]);
}
uniform_bind new_bind;
new_bind.count = count;
new_bind.index = _uniform_data_ints.size() - count;
// new_bind.index = num_matrix_uniforms - count;
new_bind.type = uniform_bind::INT;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform1iv(findUniformLocation(name.c_str()), count, (const GLint*)val);
}
void opengl::ShaderUniforms::setUniformf(const SCP_string &name, const float val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::FLOAT) {
if (fl_equal(_uniform_data_floats[bind_info->index], val)) {
return;
}
_uniform_data_floats[bind_info->index] = val;
resident = true;
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
_uniform_data_floats.push_back(val);
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_floats.size() - 1;
new_bind.type = uniform_bind::FLOAT;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform1f(findUniformLocation(name.c_str()), val);
}
void opengl::ShaderUniforms::setUniform2f(const SCP_string &name, const float x, const float y)
{
vec2d temp;
temp.x = x;
temp.y = y;
setUniform2f(name, temp);
}
void opengl::ShaderUniforms::setUniform2f(const SCP_string &name, const vec2d &val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::VEC2) {
if (vm_vec_equal(_uniform_data_vec2d[bind_info->index], val)) {
return;
}
_uniform_data_vec2d[bind_info->index] = val;
resident = true;
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
_uniform_data_vec2d.push_back(val);
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_vec2d.size() - 1;
new_bind.type = uniform_bind::VEC2;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform2f(findUniformLocation(name.c_str()), val.x, val.y);
}
void opengl::ShaderUniforms::setUniform3f(const SCP_string &name, const float x, const float y, const float z)
{
vec3d temp;
temp.xyz.x = x;
temp.xyz.y = y;
temp.xyz.z = z;
setUniform3f(name, temp);
}
void opengl::ShaderUniforms::setUniform3f(const SCP_string &name, const vec3d &val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::VEC3) {
if (vm_vec_equal(_uniform_data_vec3d[bind_info->index], val)) {
return;
}
_uniform_data_vec3d[bind_info->index] = val;
resident = true;
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
_uniform_data_vec3d.push_back(val);
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_vec3d.size() - 1;
new_bind.type = uniform_bind::VEC3;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform3f(findUniformLocation(name.c_str()), val.a1d[0], val.a1d[1], val.a1d[2]);
}
void opengl::ShaderUniforms::setUniform4f(const SCP_string &name, const float x, const float y, const float z, const float w)
{
vec4 temp;
temp.xyzw.x = x;
temp.xyzw.y = y;
temp.xyzw.z = z;
temp.xyzw.w = w;
setUniform4f(name, temp);
}
void opengl::ShaderUniforms::setUniform4f(const SCP_string &name, const vec4 &val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::VEC4) {
if (vm_vec_equal(_uniform_data_vec4[bind_info->index], val)) {
// if the values are close enough, pass.
return;
}
_uniform_data_vec4[bind_info->index] = val;
resident = true;
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
_uniform_data_vec4.push_back(val);
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_vec4.size() - 1;
new_bind.type = uniform_bind::VEC4;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform4f(findUniformLocation(name.c_str()), val.a1d[0], val.a1d[1], val.a1d[2], val.a1d[3]);
}
void opengl::ShaderUniforms::setUniform1fv(const SCP_string &name, const int count, const float *val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
auto uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != INVALID_SIZE) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::FLOAT && bind_info->count == count) {
bool equal = true;
// if the values are close enough, pass.
for (int i = 0; i < count; ++i) {
if (!fl_equal(val[i], _uniform_data_floats[bind_info->index + i])) {
equal = false;
break;
}
}
if (equal) {
return;
}
resident = true;
for (int i = 0; i < count; ++i) {
_uniform_data_floats[bind_info->index + i] = val[i];
}
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
for (int i = 0; i < count; ++i) {
_uniform_data_floats.push_back(val[i]);
}
uniform_bind new_bind;
new_bind.count = count;
new_bind.index = _uniform_data_floats.size() - count;
// new_bind.index = num_matrix_uniforms - count;
new_bind.type = uniform_bind::FLOAT;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform1fv(findUniformLocation(name.c_str()), count, (const GLfloat*)val);
}
void opengl::ShaderUniforms::setUniform3fv(const SCP_string &name, const int count, const vec3d *val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
auto uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != INVALID_SIZE) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::VEC3 && bind_info->count == count) {
bool equal = true;
// if the values are close enough, pass.
for (int i = 0; i < count; ++i) {
if (!vm_vec_equal(val[i], _uniform_data_vec3d[bind_info->index + i])) {
equal = false;
break;
}
}
if (equal) {
return;
}
resident = true;
for (int i = 0; i < count; ++i) {
_uniform_data_vec3d[bind_info->index + i] = val[i];
}
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
for (int i = 0; i < count; ++i) {
_uniform_data_vec3d.push_back(val[i]);
}
uniform_bind new_bind;
new_bind.count = count;
new_bind.index = _uniform_data_vec3d.size() - count;
// new_bind.index = num_matrix_uniforms - count;
new_bind.type = uniform_bind::VEC3;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform3fv(findUniformLocation(name.c_str()), count, (const GLfloat*)val);
}
void opengl::ShaderUniforms::setUniform4fv(const SCP_string &name, const int count, const vec4 *val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
auto uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != INVALID_SIZE) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::VEC4 && bind_info->count == count) {
bool equal = true;
// if the values are close enough, pass.
for (int i = 0; i < count; ++i) {
if (!vm_vec_equal(val[i], _uniform_data_vec4[bind_info->index + i])) {
equal = false;
break;
}
}
if (equal) {
return;
}
resident = true;
for (int i = 0; i < count; ++i) {
_uniform_data_vec4[bind_info->index + i] = val[i];
}
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
for (int i = 0; i < count; ++i) {
_uniform_data_vec4.push_back(val[i]);
}
uniform_bind new_bind;
new_bind.count = count;
new_bind.index = _uniform_data_vec4.size() - count;
// new_bind.index = num_matrix_uniforms - count;
new_bind.type = uniform_bind::VEC4;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniform4fv(findUniformLocation(name.c_str()), count, (const GLfloat*)val);
}
void opengl::ShaderUniforms::setUniformMatrix4f(const SCP_string &name, const matrix4 &val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::MATRIX4 && bind_info->count == 1) {
if (vm_matrix_equal(_uniform_data_matrix4[bind_info->index], val)) {
return;
}
_uniform_data_matrix4[bind_info->index] = val;
resident = true;
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
//matrix_uniform_data[num_matrix_uniforms] = val;
//memcpy(&(matrix_uniform_data[num_matrix_uniforms]), &val, sizeof(matrix4));
_uniform_data_matrix4.push_back(val);
// num_matrix_uniforms += 1;
uniform_bind new_bind;
new_bind.count = 1;
new_bind.index = _uniform_data_matrix4.size() - 1;
// new_bind.index = num_matrix_uniforms - 1;
new_bind.type = uniform_bind::MATRIX4;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniformMatrix4fv(findUniformLocation(name.c_str()), 1, GL_FALSE, (const GLfloat*)&val);
}
void opengl::ShaderUniforms::setUniformMatrix4fv(const SCP_string &name, const int count, const matrix4 *val)
{
Assertion(GL_state.IsCurrentProgram(_program->getShaderHandle()), "The program must be current before setting uniforms!");
size_t uniform_index = findUniform(name);
bool resident = false;
if (uniform_index != (size_t)-1) {
Assert((size_t)uniform_index < _uniforms.size());
uniform_bind *bind_info = &_uniforms[uniform_index];
if (bind_info->type == uniform_bind::MATRIX4 && bind_info->count == count) {
bool equal = true;
// if the values are close enough, pass.
for (int i = 0; i < count; ++i) {
if (!vm_matrix_equal(val[i], _uniform_data_matrix4[bind_info->index + i])) {
equal = false;
break;
}
}
if (equal) {
return;
}
resident = true;
for (int i = 0; i < count; ++i) {
_uniform_data_matrix4[bind_info->index + i] = val[i];
}
}
}
if (!resident) {
// uniform doesn't exist in our previous uniform block so queue this new value
for (int i = 0; i < count; ++i) {
_uniform_data_matrix4.push_back(val[i]);
}
uniform_bind new_bind;
new_bind.count = count;
new_bind.index = _uniform_data_matrix4.size() - count;
// new_bind.index = num_matrix_uniforms - count;
new_bind.type = uniform_bind::MATRIX4;
new_bind.name = name;
_uniforms.push_back(new_bind);
_uniform_lookup[name] = _uniforms.size() - 1;
}
glUniformMatrix4fv(findUniformLocation(name.c_str()), count, GL_FALSE, (const GLfloat*)val);
}
GLint opengl::ShaderUniforms::findUniformLocation(const SCP_string& name) {
auto iter = _uniform_locations.find(name);
+2 -35
View File
@@ -16,33 +16,13 @@ class ShaderUniforms {
{
SCP_string name;
enum data_type {
INT,
FLOAT,
VEC2,
VEC3,
VEC4,
MATRIX4
};
uniform_bind::data_type type;
size_t index;
int count;
int tranpose;
int value;
};
ShaderProgram* _program;
SCP_vector<uniform_bind> _uniforms;
SCP_vector<int> _uniform_data_ints;
SCP_vector<float> _uniform_data_floats;
SCP_vector<vec2d> _uniform_data_vec2d;
SCP_vector<vec3d> _uniform_data_vec3d;
SCP_vector<vec4> _uniform_data_vec4;
SCP_vector<matrix4> _uniform_data_matrix4;
SCP_unordered_map<SCP_string, size_t> _uniform_lookup;
SCP_unordered_map<SCP_string, GLint> _uniform_locations;
@@ -52,20 +32,7 @@ class ShaderUniforms {
public:
explicit ShaderUniforms(ShaderProgram* shaderProgram);
void setUniformi(const SCP_string &name, const int value);
void setUniform1iv(const SCP_string &name, const int count, const int *val);
void setUniformf(const SCP_string &name, const float value);
void setUniform2f(const SCP_string &name, const float x, const float y);
void setUniform2f(const SCP_string &name, const vec2d &val);
void setUniform3f(const SCP_string &name, const float x, const float y, const float z);
void setUniform3f(const SCP_string &name, const vec3d &value);
void setUniform4f(const SCP_string &name, const float x, const float y, const float z, const float w);
void setUniform4f(const SCP_string &name, const vec4 &val);
void setUniform1fv(const SCP_string &name, const int count, const float *val);
void setUniform3fv(const SCP_string &name, const int count, const vec3d *val);
void setUniform4fv(const SCP_string &name, const int count, const vec4 *val);
void setUniformMatrix4fv(const SCP_string &name, const int count, const matrix4 *value);
void setUniformMatrix4f(const SCP_string &name, const matrix4 &val);
void setTextureUniform(const SCP_string &name, const int texture_unit);
};
enum ShaderStage {
+8 -329
View File
@@ -1,6 +1,7 @@
#include "gropengl.h"
#include "gropenglbmpman.h"
#include "gropengldeferred.h"
#include "gropengldraw.h"
@@ -11,29 +12,21 @@
#include "gropenglsync.h"
#include "gropengltexture.h"
#include "gropengltnl.h"
#include "bmpman/bmpman.h"
#include "cfile/cfile.h"
#include "cmdline/cmdline.h"
#include "ddsutils/ddsutils.h"
#include "debugconsole/console.h"
#include "globalincs/systemvars.h"
#include "graphics/2d.h"
#include "graphics/line.h"
#include "graphics/matrix.h"
#include "graphics/paths/PathRenderer.h"
#include "io/mouse.h"
#include "io/timer.h"
#include "libs/renderdoc/renderdoc.h"
#include "math/floating.h"
#include "model/model.h"
#include "nebula/neb.h"
#include "options/Option.h"
#include "osapi/osapi.h"
#include "osapi/osregistry.h"
#include "pngutils/pngutils.h"
#include "popup/popup.h"
#include "render/3d.h"
#include "tracing/tracing.h"
#if defined(_WIN32)
#include <windows.h>
@@ -60,8 +53,6 @@ bool GL_initted = 0;
//3==NV Radial
int OGL_fogmode = 0;
static ushort *GL_original_gamma_ramp = NULL;
int Use_PBOs = 0;
static ubyte *GL_saved_screen = NULL;
@@ -75,16 +66,6 @@ extern SCP_string Window_title;
extern GLfloat GL_anisotropy;
extern float FreeSpace_gamma;
void gr_opengl_set_gamma(float gamma);
extern float FreeSpace_gamma;
void gr_opengl_set_gamma(float gamma);
static int GL_fullscreen = 0;
static int GL_windowed = 0;
static int GL_minimized = 0;
static GLenum GL_read_format = GL_BGRA;
GLuint GL_vao = 0;
@@ -97,74 +78,6 @@ static std::unique_ptr<os::OpenGLContext> GL_context = nullptr;
static std::unique_ptr<os::GraphicsOperations> graphic_operations = nullptr;
static os::Viewport* current_viewport = nullptr;
static bool mode_change_func(os::ViewportState state, bool initial)
{
if (initial) {
return false;
}
auto window = os::getMainViewport();
if (window == nullptr) {
return false;
}
window->setState(state);
return true;
}
static auto WindowModeOption = options::OptionBuilder<os::ViewportState>("Graphics.WindowMode", "Window Mode",
"Controls how the game window is created.")
.category("Graphics")
.level(options::ExpertLevel::Beginner)
.values({{os::ViewportState::Fullscreen, "Fullscreen"},
{os::ViewportState::Borderless, "Borderless"},
{os::ViewportState::Windowed, "Windowed"}})
.importance(98)
.default_val(os::ViewportState::Fullscreen)
.change_listener(mode_change_func)
.finish();
void opengl_go_fullscreen()
{
if (Cmdline_fullscreen_window || Cmdline_window || GL_fullscreen || Fred_running)
return;
gr_opengl_set_gamma(FreeSpace_gamma);
GL_fullscreen = 1;
GL_minimized = 0;
GL_windowed = 0;
}
void opengl_go_windowed()
{
if ( ( !Cmdline_fullscreen_window && !Cmdline_window ) /*|| GL_windowed*/ || Fred_running )
return;
GL_windowed = 1;
GL_minimized = 0;
GL_fullscreen = 0;
}
void opengl_minimize()
{
GL_minimized = 1;
GL_windowed = 0;
GL_fullscreen = 0;
}
void gr_opengl_activate(int active)
{
if (active) {
if (Cmdline_fullscreen_window||Cmdline_window)
opengl_go_windowed();
else
opengl_go_fullscreen();
} else {
opengl_minimize();
}
}
void gr_opengl_clear()
{
float red = gr_screen.current_clear_color.red / 255.0f;
@@ -190,15 +103,9 @@ void gr_opengl_clear()
void gr_opengl_flip()
{
if ( !GL_initted )
if (!GL_initted)
return;
TRACE_SCOPE(tracing::PageFlip);
gr_reset_clip();
mouse_reset_deltas();
if (Cmdline_gl_finish)
glFinish();
@@ -396,15 +303,6 @@ void gr_opengl_shutdown()
glDeleteVertexArrays(1, &GL_vao);
GL_vao = 0;
if (GL_original_gamma_ramp != NULL && os::getSDLMainWindow() != nullptr) {
SDL_SetWindowGammaRamp( os::getSDLMainWindow(), GL_original_gamma_ramp, (GL_original_gamma_ramp+256), (GL_original_gamma_ramp+512) );
}
if (GL_original_gamma_ramp != NULL) {
vm_free(GL_original_gamma_ramp);
GL_original_gamma_ramp = NULL;
}
graphic_operations->makeOpenGLContextCurrent(nullptr, nullptr);
GL_context = nullptr;
}
@@ -563,89 +461,6 @@ int gr_opengl_alpha_mask_set(int mode, float alpha)
return mode;
}
// I feel dirty...
static void opengl_make_gamma_ramp(float gamma, ushort *ramp)
{
ushort x, y;
ushort base_ramp[256];
Assert( ramp != NULL );
// generate the base ramp values first off
// if no gamma set then just do this quickly
if (gamma <= 0.0f) {
memset( ramp, 0, 3 * 256 * sizeof(ushort) );
return;
}
// identity gamma, avoid all of the math
else if ( (gamma == 1.0f) || (GL_original_gamma_ramp == NULL) ) {
if (GL_original_gamma_ramp != NULL) {
memcpy( ramp, GL_original_gamma_ramp, 3 * 256 * sizeof(ushort) );
}
// set identity if no original ramp
else {
for (x = 0; x < 256; x++) {
ramp[x] = (x << 8) | x;
ramp[x + 256] = (x << 8) | x;
ramp[x + 512] = (x << 8) | x;
}
}
return;
}
// for everything else we need to actually figure it up
else {
double g = 1.0 / (double)gamma;
double val;
Assert( GL_original_gamma_ramp != NULL );
for (x = 0; x < 256; x++) {
val = (pow(x/255.0, g) * 65535.0 + 0.5);
CLAMP( val, 0, 65535 );
base_ramp[x] = (ushort)val;
}
for (y = 0; y < 3; y++) {
for (x = 0; x < 256; x++) {
val = (base_ramp[x] * 2) - GL_original_gamma_ramp[x + y * 256];
CLAMP( val, 0, 65535 );
ramp[x + y * 256] = (ushort)val;
}
}
}
}
void gr_opengl_set_gamma(float gamma)
{
ushort *gamma_ramp = NULL;
Gr_gamma = gamma;
Gr_gamma_int = int (Gr_gamma*10);
// new way - but not while running FRED
if (!Fred_running && !Cmdline_no_set_gamma && os::getSDLMainWindow() != nullptr) {
gamma_ramp = (ushort*) vm_malloc( 3 * 256 * sizeof(ushort), memory::quiet_alloc);
if (gamma_ramp == NULL) {
Int3();
return;
}
memset( gamma_ramp, 0, 3 * 256 * sizeof(ushort) );
// Create the Gamma lookup table
opengl_make_gamma_ramp(gamma, gamma_ramp);
SDL_SetWindowGammaRamp( os::getSDLMainWindow(), gamma_ramp, (gamma_ramp+256), (gamma_ramp+512) );
vm_free(gamma_ramp);
}
}
void gr_opengl_get_region(int /*front*/, int w, int h, ubyte *data)
{
@@ -903,113 +718,6 @@ void gr_opengl_use_viewport(os::Viewport* view) {
int opengl_init_display_device()
{
int bpp = gr_screen.bits_per_pixel;
Assertion((bpp == 16) || (bpp == 32), "Invalid bits-per-pixel value %d!", bpp);
// screen format
switch (bpp) {
case 16: {
Gr_red.bits = 5;
Gr_red.shift = 11;
Gr_red.scale = 8;
Gr_red.mask = 0xF800;
Gr_green.bits = 6;
Gr_green.shift = 5;
Gr_green.scale = 4;
Gr_green.mask = 0x7E0;
Gr_blue.bits = 5;
Gr_blue.shift = 0;
Gr_blue.scale = 8;
Gr_blue.mask = 0x1F;
break;
}
case 32: {
Gr_red.bits = 8;
Gr_red.shift = 16;
Gr_red.scale = 1;
Gr_red.mask = 0xff0000;
Gr_green.bits = 8;
Gr_green.shift = 8;
Gr_green.scale = 1;
Gr_green.mask = 0x00ff00;
Gr_blue.bits = 8;
Gr_blue.shift = 0;
Gr_blue.scale = 1;
Gr_blue.mask = 0x0000ff;
Gr_alpha.bits = 8;
Gr_alpha.shift = 24;
Gr_alpha.mask = 0xff000000;
Gr_alpha.scale = 1;
break;
}
}
// texture format
Gr_t_red.bits = 5;
Gr_t_red.mask = 0x7c00;
Gr_t_red.shift = 10;
Gr_t_red.scale = 8;
Gr_t_green.bits = 5;
Gr_t_green.mask = 0x03e0;
Gr_t_green.shift = 5;
Gr_t_green.scale = 8;
Gr_t_blue.bits = 5;
Gr_t_blue.mask = 0x001f;
Gr_t_blue.shift = 0;
Gr_t_blue.scale = 8;
Gr_t_alpha.bits = 1;
Gr_t_alpha.mask = 0x8000;
Gr_t_alpha.scale = 255;
Gr_t_alpha.shift = 15;
// alpha-texture format
Gr_ta_red.bits = 4;
Gr_ta_red.mask = 0x0f00;
Gr_ta_red.shift = 8;
Gr_ta_red.scale = 17;
Gr_ta_green.bits = 4;
Gr_ta_green.mask = 0x00f0;
Gr_ta_green.shift = 4;
Gr_ta_green.scale = 17;
Gr_ta_blue.bits = 4;
Gr_ta_blue.mask = 0x000f;
Gr_ta_blue.shift = 0;
Gr_ta_blue.scale = 17;
Gr_ta_alpha.bits = 4;
Gr_ta_alpha.mask = 0xf000;
Gr_ta_alpha.shift = 12;
Gr_ta_alpha.scale = 17;
// allocate storage for original gamma settings
if ( !Cmdline_no_set_gamma && (GL_original_gamma_ramp == NULL) ) {
GL_original_gamma_ramp = (ushort*) vm_malloc( 3 * 256 * sizeof(ushort), memory::quiet_alloc);
if (GL_original_gamma_ramp == NULL) {
mprintf((" Unable to allocate memory for gamma ramp! Disabling...\n"));
Cmdline_no_set_gamma = 1;
} else {
// assume identity ramp by default, to be overwritten by true ramp later
for (ushort x = 0; x < 256; x++) {
GL_original_gamma_ramp[x] = GL_original_gamma_ramp[x + 256] = GL_original_gamma_ramp[x + 512] = (x << 8) | x;
}
}
}
os::ViewPortProperties attrs;
attrs.enable_opengl = true;
@@ -1032,7 +740,7 @@ int opengl_init_display_device()
}
if (Using_in_game_options) {
switch (WindowModeOption->getValue()) {
switch (Gr_configured_window_state) {
case os::ViewportState::Windowed:
// That's the default
break;
@@ -1084,11 +792,6 @@ int opengl_init_display_device()
graphic_operations->makeOpenGLContextCurrent(port, GL_context.get());
current_viewport = port;
if (GL_original_gamma_ramp != NULL && os::getSDLMainWindow() != nullptr) {
SDL_GetWindowGammaRamp( os::getSDLMainWindow(), GL_original_gamma_ramp, (GL_original_gamma_ramp+256),
(GL_original_gamma_ramp+512) );
}
return 0;
}
@@ -1118,8 +821,6 @@ void opengl_setup_function_pointers()
gr_screen.gf_restore_screen = gr_opengl_restore_screen;
gr_screen.gf_free_screen = gr_opengl_free_screen;
gr_screen.gf_set_gamma = gr_opengl_set_gamma;
// UnknownPlayer : Don't recognize this - MAY NEED DEBUGGING
gr_screen.gf_get_region = gr_opengl_get_region;
@@ -1147,6 +848,8 @@ void opengl_setup_function_pointers()
gr_screen.gf_delete_buffer = gr_opengl_delete_buffer;
gr_screen.gf_update_buffer_data = gr_opengl_update_buffer_data;
gr_screen.gf_update_buffer_data_offset = gr_opengl_update_buffer_data_offset;
gr_screen.gf_map_buffer = gr_opengl_map_buffer;
gr_screen.gf_flush_mapped_buffer = gr_opengl_flush_mapped_buffer;
gr_screen.gf_bind_uniform_buffer = gr_opengl_bind_uniform_buffer;
gr_screen.gf_update_transform_buffer = gr_opengl_update_transform_buffer;
@@ -1474,12 +1177,6 @@ bool gr_opengl_init(std::unique_ptr<os::GraphicsOperations>&& graphicsOps)
GL_binary_formats.resize(formats);
glGetIntegerv(GL_PROGRAM_BINARY_FORMATS, GL_binary_formats.data());
if (Cmdline_fullscreen_window || Cmdline_window) {
opengl_go_windowed();
} else {
opengl_go_fullscreen();
}
init_extensions();
// init state system (must come AFTER light is set up)
@@ -1607,6 +1304,8 @@ bool gr_opengl_is_capable(gr_capability capability)
return GLAD_GL_ARB_timer_query != 0; // Timestamp queries are available from 3.3 onwards
case CAPABILITY_SEPARATE_BLEND_FUNCTIONS:
return GLAD_GL_ARB_draw_buffers_blend != 0; // We need an OpenGL extension for this
case CAPABILITY_PERSISTENT_BUFFER_MAPPING:
return GLAD_GL_ARB_buffer_storage != 0;
}
return false;
@@ -1671,26 +1370,6 @@ uint opengl_data_type_size(GLenum data_type)
return 0;
}
DCF(ogl_minimize, "Minimizes opengl")
{
bool minimize_ogl = false;
if ( gr_screen.mode != GR_OPENGL ) {
dc_printf("Command only available in OpenGL mode.\n");
return;
}
if (dc_optional_string_either("help", "--help")) {
dc_printf("[bool] If true is passed, then the OpenGL window will minimize.\n");
return;
}
dc_stuff_boolean(&minimize_ogl);
if (minimize_ogl) {
opengl_minimize();
}
}
DCF(ogl_anisotropy, "toggles anisotropic filtering")
{
bool process = true;
+57 -55
View File
@@ -1,28 +1,32 @@
#include "gropengldeferred.h"
#include "ShaderProgram.h"
#include "gropengldraw.h"
#include "gropenglstate.h"
#include "gropengltnl.h"
#include "graphics/2d.h"
#include "gropenglstate.h"
#include "gropengldraw.h"
#include "gropengldeferred.h"
#include "gropengltnl.h"
#include "graphics/matrix.h"
#include "graphics/util/UniformAligner.h"
#include "graphics/util/uniform_structs.h"
#include "graphics/util/UniformBuffer.h"
#include "tracing/tracing.h"
#include "graphics/util/uniform_structs.h"
#include "lighting/lighting.h"
#include "render/3d.h"
#include "ShaderProgram.h"
#include "nebula/neb.h"
#include "mission/missionparse.h"
#include "mission/mission_flags.h"
#include "mission/missionparse.h"
#include "nebula/neb.h"
#include "render/3d.h"
#include "tracing/tracing.h"
void gr_opengl_deferred_init() {
#include <math/bitarray.h>
void gr_opengl_deferred_init()
{
gr_opengl_deferred_light_cylinder_init(16);
gr_opengl_deferred_light_sphere_init(16, 16);
}
void gr_opengl_deferred_shutdown() {
}
void gr_opengl_deferred_shutdown() {}
void opengl_clear_deferred_buffers()
{
@@ -125,9 +129,18 @@ void gr_opengl_deferred_lighting_finish()
std::stable_sort(Lights.begin(), Lights.end(), light_compare_by_type);
using namespace graphics;
// Get a uniform buffer for out data
auto buffer = gr_get_uniform_buffer(uniform_block_type::Lights);
auto& uniformAligner = buffer->aligner();
// We need to precompute how many elements we are going to need
size_t num_data_elements = 0;
for (auto& l : Lights) {
++num_data_elements;
if (l.type == Light_Type::Tube) {
++num_data_elements;
}
}
// Get a uniform buffer for our data
auto buffer = gr_get_uniform_buffer(uniform_block_type::Lights, num_data_elements);
auto& uniformAligner = buffer.aligner();
{
GR_DEBUG_SCOPE("Build buffer data");
@@ -170,6 +183,9 @@ void gr_opengl_deferred_lighting_finish()
light_data->diffuseLightColor = diffuse;
light_data->specLightColor = spec;
// Set a default value for all lights. Only the first directional light will change this.
light_data->enable_shadows = false;
switch (l.type) {
case Light_Type::Directional:
if (Shadow_quality != ShadowQuality::Disabled) {
@@ -199,9 +215,6 @@ void gr_opengl_deferred_lighting_finish()
light_data->coneDir = l.vec2;
FALLTHROUGH;
case Light_Type::Point:
light_data->diffuseLightColor = diffuse;
light_data->specLightColor = spec;
vm_vec_scale(&light_data->specLightColor, static_point_factor);
light_data->lightRadius = MAX(l.rada, l.radb) * 1.25f;
@@ -210,7 +223,6 @@ void gr_opengl_deferred_lighting_finish()
light_data->scale.xyz.z = MAX(l.rada, l.radb) * 1.28f;
break;
case Light_Type::Tube: {
light_data->diffuseLightColor = diffuse;
light_data->lightRadius = l.radb * 1.5f;
light_data->lightType = LT_TUBE;
@@ -243,14 +255,12 @@ void gr_opengl_deferred_lighting_finish()
}
// Uniform data has been assembled, upload it to the GPU and issue the draw calls
buffer->submitData();
buffer.submitData();
}
{
GR_DEBUG_SCOPE("Render light geometry");
gr_bind_uniform_buffer(uniform_block_type::DeferredGlobals,
0,
sizeof(graphics::deferred_global_data),
buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::DeferredGlobals, buffer.getBufferOffset(0),
sizeof(graphics::deferred_global_data), buffer.bufferHandle());
size_t element_index = 0;
for (auto& l : Lights) {
@@ -258,27 +268,21 @@ void gr_opengl_deferred_lighting_finish()
switch (l.type) {
case Light_Type::Directional:
gr_bind_uniform_buffer(uniform_block_type::Lights,
uniformAligner.getOffset(element_index),
sizeof(graphics::deferred_light_data),
buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::Lights, buffer.getAlignerElementOffset(element_index),
sizeof(graphics::deferred_light_data), buffer.bufferHandle());
opengl_draw_full_screen_textured(0.0f, 0.0f, 1.0f, 1.0f);
++element_index;
break;
case Light_Type::Cone:
case Light_Type::Point:
gr_bind_uniform_buffer(uniform_block_type::Lights,
uniformAligner.getOffset(element_index),
sizeof(graphics::deferred_light_data),
buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::Lights, buffer.getAlignerElementOffset(element_index),
sizeof(graphics::deferred_light_data), buffer.bufferHandle());
gr_opengl_draw_deferred_light_sphere(&l.vec);
++element_index;
break;
case Light_Type::Tube:
gr_bind_uniform_buffer(uniform_block_type::Lights,
uniformAligner.getOffset(element_index),
sizeof(graphics::deferred_light_data),
buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::Lights, buffer.getAlignerElementOffset(element_index),
sizeof(graphics::deferred_light_data), buffer.bufferHandle());
vec3d a;
matrix orient;
@@ -289,10 +293,8 @@ void gr_opengl_deferred_lighting_finish()
++element_index;
// The next two draws use the same uniform block element
gr_bind_uniform_buffer(uniform_block_type::Lights,
uniformAligner.getOffset(element_index),
sizeof(graphics::deferred_light_data),
buffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::Lights, buffer.getAlignerElementOffset(element_index),
sizeof(graphics::deferred_light_data), buffer.bufferHandle());
gr_opengl_draw_deferred_light_sphere(&l.vec);
gr_opengl_draw_deferred_light_sphere(&l.vec2);
@@ -302,9 +304,6 @@ void gr_opengl_deferred_lighting_finish()
continue;
}
}
// We don't need the buffer anymore
buffer->finished();
}
gr_end_view_matrix();
@@ -326,13 +325,18 @@ void gr_opengl_deferred_lighting_finish()
unsigned char r, g, b;
neb2_get_fog_color(&r, &g, &b);
Current_shader->program->Uniforms.setUniformi("tex", 0);
Current_shader->program->Uniforms.setUniformi("depth_tex", 1);
Current_shader->program->Uniforms.setUniformf("fog_start", fog_near);
Current_shader->program->Uniforms.setUniformf("fog_scale", 1.0f / (fog_far - fog_near));
Current_shader->program->Uniforms.setUniform3f("fog_color", r / 255.f, g / 255.f, b / 255.f);
Current_shader->program->Uniforms.setUniformf("zNear", Min_draw_distance);
Current_shader->program->Uniforms.setUniformf("zFar", Max_draw_distance);
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
Current_shader->program->Uniforms.setTextureUniform("depth_tex", 1);
opengl_set_generic_uniform_data<graphics::generic_data::fog_data>([&](graphics::generic_data::fog_data* data) {
data->fog_start = fog_near;
data->fog_scale = 1.0f / (fog_far - fog_near);
data->fog_color.xyz.x = r / 255.f;
data->fog_color.xyz.y = g / 255.f;
data->fog_color.xyz.z = b / 255.f;
data->zNear = Min_draw_distance;
data->zFar = Max_draw_distance;
});
opengl_draw_full_screen_textured(0.0f, 0.0f, 1.0f, 1.0f);
} else {
@@ -364,8 +368,7 @@ void gr_opengl_draw_deferred_light_sphere(const vec3d *position)
{
g3_start_instance_matrix(position, &vmd_identity_matrix, true);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
opengl_draw_sphere();
@@ -592,8 +595,7 @@ void gr_opengl_draw_deferred_light_cylinder(const vec3d *position, const matrix
{
g3_start_instance_matrix(position, orient, true);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
vertex_layout vertex_declare;
+15 -12
View File
@@ -611,24 +611,27 @@ void gr_opengl_render_shield_impact(shield_material *material_info, primitive_ty
vm_matrix4_set_inverse_transform(&impact_transform, &impact_orient, &impact_pos);
uint32_t array_index = 0;
if ( material_info->get_texture_map(TM_BASE_TYPE) >= 0 ) {
if (material_info->get_texture_map(TM_BASE_TYPE) >= 0) {
float u_scale, v_scale;
if ( !gr_opengl_tcache_set(material_info->get_texture_map(TM_BASE_TYPE), material_info->get_texture_type(), &u_scale, &v_scale, &array_index) ) {
if (!gr_opengl_tcache_set(material_info->get_texture_map(TM_BASE_TYPE), material_info->get_texture_type(),
&u_scale, &v_scale, &array_index)) {
mprintf(("WARNING: Error setting bitmap texture (%i)!\n", material_info->get_texture_map(TM_BASE_TYPE)));
}
}
Current_shader->program->Uniforms.setUniform3f("hitNormal", impact_orient.vec.fvec);
Current_shader->program->Uniforms.setUniformMatrix4f("shieldProjMatrix", impact_projection);
Current_shader->program->Uniforms.setUniformMatrix4f("shieldModelViewMatrix", impact_transform);
Current_shader->program->Uniforms.setUniformi("shieldMap", 0);
Current_shader->program->Uniforms.setUniformi("shieldMapIndex", array_index);
Current_shader->program->Uniforms.setUniformi("srgb", High_dynamic_range ? 1 : 0);
Current_shader->program->Uniforms.setUniform4f("color", material_info->get_color());
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
opengl_set_generic_uniform_data<graphics::generic_data::shield_impact_data>(
[&](graphics::generic_data::shield_impact_data* data) {
data->hitNormal = impact_orient.vec.fvec;
data->shieldProjMatrix = impact_projection;
data->shieldModelViewMatrix = impact_transform;
data->shieldMapIndex = array_index;
data->srgb = High_dynamic_range ? 1 : 0;
data->color = material_info->get_color();
});
gr_matrix_set_uniforms();
opengl_render_primitives(prim_type, layout, n_verts, buffer_handle, 0, 0);
}
+216 -103
View File
@@ -12,6 +12,7 @@
#include "cmdline/cmdline.h"
#include "def_files/def_files.h"
#include "graphics/util/uniform_structs.h"
#include "io/timer.h"
#include "lighting/lighting.h"
#include "mod_table/mod_table.h"
@@ -23,44 +24,50 @@
extern bool PostProcessing_override;
extern int opengl_check_framebuffer();
//Needed to track where the FXAA shaders are
//In case we don't find the shaders at all, this override is needed
// Needed to track where the FXAA shaders are
// In case we don't find the shaders at all, this override is needed
bool fxaa_unavailable = false;
bool zbuffer_saved = false;
bool zbuffer_saved = false;
// lightshaft parameters
bool ls_on = false;
bool ls_force_off = false;
float ls_density = 0.5f;
float ls_weight = 0.02f;
float ls_falloff = 1.0f;
float ls_intensity = 0.5f;
bool ls_on = false;
bool ls_force_off = false;
float ls_density = 0.5f;
float ls_weight = 0.02f;
float ls_falloff = 1.0f;
float ls_intensity = 0.5f;
float ls_cpintensity = 0.5f * 50 * 0.02f;
int ls_samplenum = 50;
int ls_samplenum = 50;
const int MAX_MIP_BLUR_LEVELS = 4;
typedef struct post_effect_t {
enum class PostEffectUniformType {
Invalid,
NoiseAmount,
Saturation,
Brightness,
Contrast,
FilmGrain,
TvStripes,
Cutoff,
Tint,
Dither,
};
struct post_effect_t {
SCP_string name;
SCP_string uniform_name;
PostEffectUniformType uniform_type = PostEffectUniformType::Invalid;
SCP_string define_name;
float intensity;
float default_intensity;
float div;
float add;
float intensity{0.0f};
float default_intensity{0.0f};
float div{1.0f};
float add{0.0f};
vec3d rgb;
vec3d rgb = vmd_zero_vector;
bool always_on;
post_effect_t() :
intensity(0.0f), default_intensity(0.0f), div(1.0f), add(0.0f),
rgb(),
always_on(false)
{
}
} post_effect_t;
bool always_on{false};
};
SCP_vector<post_effect_t> Post_effects;
@@ -95,10 +102,12 @@ void opengl_post_pass_tonemap()
GR_DEBUG_SCOPE("Tonemapping");
TRACE_SCOPE(tracing::Tonemapping);
opengl_shader_set_current( gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_TONEMAPPING, 0) );
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_TONEMAPPING, 0));
Current_shader->program->Uniforms.setUniformi("tex", 0);
Current_shader->program->Uniforms.setUniformf("exposure", 4.0f);
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
opengl_set_generic_uniform_data<graphics::generic_data::tonemapping_data>(
[](graphics::generic_data::tonemapping_data* data) { data->exposure = 4.0f; });
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, Scene_ldr_texture, 0);
@@ -135,7 +144,7 @@ void opengl_post_pass_bloom()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_BRIGHTPASS, 0));
Current_shader->program->Uniforms.setUniformi("tex", 0);
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_color_texture);
@@ -163,17 +172,19 @@ void opengl_post_pass_bloom()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_BLUR, SDR_FLAG_BLUR_VERTICAL));
}
Current_shader->program->Uniforms.setUniformi("tex", 0);
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, source_tex);
for (int mipmap = 0; mipmap < MAX_MIP_BLUR_LEVELS; ++mipmap) {
int bloom_width = width >> mipmap;
int bloom_width = width >> mipmap;
int bloom_height = height >> mipmap;
Current_shader->program->Uniforms.setUniformf("texSize", (pass) ? 1.0f / i2fl(bloom_width) : 1.0f / i2fl(bloom_height));
Current_shader->program->Uniforms.setUniformi("level", mipmap);
Current_shader->program->Uniforms.setUniformf("tapSize", 1.0f);
opengl_set_generic_uniform_data<graphics::generic_data::blur_data>(
[&](graphics::generic_data::blur_data* data) {
data->texSize = (pass) ? 1.0f / i2fl(bloom_width) : 1.0f / i2fl(bloom_height);
data->level = mipmap;
});
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, dest_tex, mipmap);
@@ -193,9 +204,13 @@ void opengl_post_pass_bloom()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_BLOOM_COMP, 0));
Current_shader->program->Uniforms.setUniformi("tex", 0);
Current_shader->program->Uniforms.setUniformi("levels", MAX_MIP_BLUR_LEVELS);
Current_shader->program->Uniforms.setUniformf("bloom_intensity", Cmdline_bloom_intensity / 100.0f);
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
opengl_set_generic_uniform_data<graphics::generic_data::bloom_composition_data>(
[](graphics::generic_data::bloom_composition_data* data) {
data->levels = MAX_MIP_BLUR_LEVELS;
data->bloom_intensity = Cmdline_bloom_intensity / 100.0f;
});
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Bloom_textures[0]);
@@ -239,29 +254,43 @@ void gr_opengl_post_process_begin()
Post_in_frame = true;
}
void recompile_fxaa_shader() {
if (!gr_is_fxaa_mode(Gr_aa_mode)) {
return;
SCP_vector<shader_type> get_aa_shader_types(AntiAliasMode aa_mode) {
auto stypes = SCP_vector<shader_type>();
if (gr_is_fxaa_mode(aa_mode)) {
stypes.push_back(shader_type::SDR_TYPE_POST_PROCESS_FXAA);
}
else if (gr_is_smaa_mode(aa_mode)) {
stypes.push_back(shader_type::SDR_TYPE_POST_PROCESS_SMAA_BLENDING_WEIGHT);
stypes.push_back(shader_type::SDR_TYPE_POST_PROCESS_SMAA_EDGE);
stypes.push_back(shader_type::SDR_TYPE_POST_PROCESS_SMAA_NEIGHBORHOOD_BLENDING);
}
mprintf(("Recompiling FXAA shader...\n"));
return stypes;
}
// start recompile by grabbing deleting the current shader we have, assuming it's already created
opengl_delete_shader( gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA, 0) );
void recompile_aa_shader() {
mprintf(("Recompiling AA shader(s)...\n"));
// then recreate it again. shader loading code will be updated with the new FXAA presets
gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA, 0);
for (auto sdr : get_aa_shader_types(Gr_aa_mode_last_frame)) {
opengl_delete_shader( gr_opengl_maybe_create_shader(sdr, 0) );
}
for (auto sdr : get_aa_shader_types(Gr_aa_mode)) {
gr_opengl_maybe_create_shader(sdr, 0);
}
Gr_aa_mode_last_frame = Gr_aa_mode;
}
void opengl_post_pass_fxaa() {
void opengl_post_pass_fxaa()
{
GR_DEBUG_SCOPE("FXAA");
TRACE_SCOPE(tracing::FXAA);
//If the preset changed, recompile the shader
// If the preset changed, recompile the shader
if (Gr_aa_mode_last_frame != Gr_aa_mode) {
recompile_fxaa_shader();
recompile_aa_shader();
}
// We only want to draw to ATTACHMENT0
@@ -269,10 +298,10 @@ void opengl_post_pass_fxaa() {
GL_state.ColorMask(true, true, true, true);
// Do a prepass to convert the main shaders' RGBA output into RGBL
opengl_shader_set_current( gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA_PREPASS, 0) );
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA_PREPASS, 0));
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi( "tex", 0 );
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, Scene_luminance_texture, 0);
@@ -281,14 +310,17 @@ void opengl_post_pass_fxaa() {
opengl_draw_full_screen_textured(0.0f, 0.0f, Scene_texture_u_scale, Scene_texture_u_scale);
// set and configure post shader ..
opengl_shader_set_current( gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA, 0) );
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_FXAA, 0));
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, Scene_ldr_texture, 0);
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi( "tex0", 0 );
Current_shader->program->Uniforms.setUniformf( "rt_w", static_cast<float>(Post_texture_width));
Current_shader->program->Uniforms.setUniformf( "rt_h", static_cast<float>(Post_texture_height));
Current_shader->program->Uniforms.setTextureUniform("tex0", 0);
opengl_set_generic_uniform_data<graphics::generic_data::fxaa_data>([](graphics::generic_data::fxaa_data* data) {
data->rt_w = i2fl(Post_texture_width);
data->rt_h = i2fl(Post_texture_height);
});
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_luminance_texture);
@@ -311,9 +343,7 @@ static void smaa_detect_edges()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_SMAA_EDGE, 0));
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi("colorTex", 0);
Current_shader->program->Uniforms.setUniform2f("smaa_rt_metrics", i2fl(Post_texture_width),
i2fl(Post_texture_height));
Current_shader->program->Uniforms.setTextureUniform("colorTex", 0);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_ldr_texture);
@@ -334,11 +364,9 @@ static void smaa_calculate_blending_weights()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_SMAA_BLENDING_WEIGHT, 0));
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi("edgesTex", 0);
Current_shader->program->Uniforms.setUniformi("areaTex", 1);
Current_shader->program->Uniforms.setUniformi("searchTex", 2);
Current_shader->program->Uniforms.setUniform2f("smaa_rt_metrics", i2fl(Post_texture_width),
i2fl(Post_texture_height));
Current_shader->program->Uniforms.setTextureUniform("edgesTex", 0);
Current_shader->program->Uniforms.setTextureUniform("areaTex", 1);
Current_shader->program->Uniforms.setTextureUniform("searchTex", 2);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Smaa_edges_tex);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Smaa_area_tex);
@@ -361,10 +389,8 @@ static void smaa_neighborhood_blending()
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_SMAA_NEIGHBORHOOD_BLENDING, 0));
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi("colorTex", 0);
Current_shader->program->Uniforms.setUniformi("blendTex", 1);
Current_shader->program->Uniforms.setUniform2f("smaa_rt_metrics", i2fl(Post_texture_width),
i2fl(Post_texture_height));
Current_shader->program->Uniforms.setTextureUniform("colorTex", 0);
Current_shader->program->Uniforms.setTextureUniform("blendTex", 1);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_ldr_texture);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Smaa_blend_tex);
@@ -395,10 +421,21 @@ void opengl_post_pass_smaa()
GR_DEBUG_SCOPE("SMAA");
TRACE_SCOPE(tracing::SMAA);
// If the preset changed, recompile the shader
if (Gr_aa_mode_last_frame != Gr_aa_mode) {
recompile_aa_shader();
}
GL_state.PushFramebufferState();
GL_state.ColorMask(true, true, true, true);
// All SMAA stages share the same shader data so we only need this once
opengl_set_generic_uniform_data<graphics::generic_data::smaa_data>([](graphics::generic_data::smaa_data* data) {
data->smaa_rt_metrics.x = i2fl(Post_texture_width);
data->smaa_rt_metrics.y = i2fl(Post_texture_height);
});
smaa_detect_edges();
smaa_calculate_blending_weights();
@@ -444,16 +481,24 @@ void opengl_post_lightshafts()
float dot;
if ( (dot = vm_vec_dot(&light_dir, &Eye_matrix.vec.fvec)) > 0.7f ) {
x = asinf(vm_vec_dot(&light_dir, &Eye_matrix.vec.rvec)) / PI*1.5f + 0.5f; //cant get the coordinates right but this works for the limited glare fov
y = asinf(vm_vec_dot(&light_dir, &Eye_matrix.vec.uvec)) / PI*1.5f*gr_screen.clip_aspect + 0.5f;
Current_shader->program->Uniforms.setUniform2f("sun_pos", x, y);
Current_shader->program->Uniforms.setUniformi("scene", 0);
Current_shader->program->Uniforms.setUniformi("cockpit", 1);
Current_shader->program->Uniforms.setUniformf("density", ls_density);
Current_shader->program->Uniforms.setUniformf("falloff", ls_falloff);
Current_shader->program->Uniforms.setUniformf("weight", ls_weight);
Current_shader->program->Uniforms.setUniformf("intensity", Sun_spot * ls_intensity);
Current_shader->program->Uniforms.setUniformf("cp_intensity", Sun_spot * ls_cpintensity);
x = asinf(vm_vec_dot(&light_dir, &Eye_matrix.vec.rvec)) / PI * 1.5f +
0.5f; // cant get the coordinates right but this works for the limited glare fov
y = asinf(vm_vec_dot(&light_dir, &Eye_matrix.vec.uvec)) / PI * 1.5f * gr_screen.clip_aspect + 0.5f;
opengl_set_generic_uniform_data<graphics::generic_data::lightshaft_data>(
[&](graphics::generic_data::lightshaft_data* data) {
data->sun_pos.x = x;
data->sun_pos.y = y;
data->density = ls_density;
data->falloff = ls_falloff;
data->weight = ls_weight;
data->intensity = Sun_spot * ls_intensity;
data->cp_intensity = Sun_spot * ls_cpintensity;
});
Current_shader->program->Uniforms.setTextureUniform("scene", 0);
Current_shader->program->Uniforms.setTextureUniform("cockpit", 1);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_depth_texture);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Cockpit_depth_texture);
@@ -521,7 +566,7 @@ void gr_opengl_post_process_end()
int post_sdr_handle = Post_active_shader_index;
if ( post_sdr_handle < 0 ) {
if (post_sdr_handle < 0) {
// no active shader index? use the always on shader.
post_sdr_handle = gr_opengl_maybe_create_shader(SDR_TYPE_POST_PROCESS_MAIN, flags);
}
@@ -529,30 +574,57 @@ void gr_opengl_post_process_end()
opengl_shader_set_current(post_sdr_handle);
// basic/default uniforms
Current_shader->program->Uniforms.setUniformi( "tex", 0 );
Current_shader->program->Uniforms.setUniformi( "depth_tex", 1);
Current_shader->program->Uniforms.setUniformf( "timer", static_cast<float>(timer_get_milliseconds() % 100 + 1) );
Current_shader->program->Uniforms.setTextureUniform("tex", 0);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_ldr_texture);
for (size_t idx = 0; idx < Post_effects.size(); idx++) {
if ( GL_shader[post_sdr_handle].flags & (1<<idx) ) {
const char *name = Post_effects[idx].uniform_name.c_str();
float value = Post_effects[idx].intensity;
Current_shader->program->Uniforms.setTextureUniform("depth_tex", 1);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Scene_depth_texture);
if (!(vmd_zero_vector == Post_effects[idx].rgb)) {
Current_shader->program->Uniforms.setUniform3f( name, Post_effects[idx].rgb );
}
else {
Current_shader->program->Uniforms.setUniformf( name, value );
opengl_set_generic_uniform_data<graphics::generic_data::post_data>([&](graphics::generic_data::post_data* data) {
data->timer = i2fl(timer_get_milliseconds() % 100 + 1);
for (size_t idx = 0; idx < Post_effects.size(); idx++) {
if (GL_shader[post_sdr_handle].flags & (1 << idx)) {
float value = Post_effects[idx].intensity;
switch (Post_effects[idx].uniform_type) {
case PostEffectUniformType::Invalid:
// Invalid name specified, do nothing
break;
case PostEffectUniformType::NoiseAmount:
data->noise_amount = value;
break;
case PostEffectUniformType::Saturation:
data->saturation = value;
break;
case PostEffectUniformType::Brightness:
data->brightness = value;
break;
case PostEffectUniformType::Contrast:
data->contrast = value;
break;
case PostEffectUniformType::FilmGrain:
data->film_grain = value;
break;
case PostEffectUniformType::TvStripes:
data->tv_stripes = value;
break;
case PostEffectUniformType::Cutoff:
data->cutoff = value;
break;
case PostEffectUniformType::Dither:
data->dither = value;
break;
case PostEffectUniformType::Tint:
data->tint = Post_effects[idx].rgb;
break;
}
}
}
}
});
// now render it to the screen ...
GL_state.PopFramebufferState();
//GL_state.Texture.Enable(Scene_color_texture);
GL_state.Texture.Enable(0, GL_TEXTURE_2D, Scene_ldr_texture);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Scene_depth_texture);
opengl_draw_full_screen_textured(0.0f, 0.0f, Scene_texture_u_scale, Scene_texture_u_scale);
@@ -716,6 +788,31 @@ void gr_opengl_post_process_restore_zbuffer()
}
}
static PostEffectUniformType mapUniformNameToType(const SCP_string& uniform_name)
{
if (!stricmp(uniform_name.c_str(), "noise_amount")) {
return PostEffectUniformType::NoiseAmount;
} else if (!stricmp(uniform_name.c_str(), "saturation")) {
return PostEffectUniformType::Saturation;
} else if (!stricmp(uniform_name.c_str(), "brightness")) {
return PostEffectUniformType::Brightness;
} else if (!stricmp(uniform_name.c_str(), "contrast")) {
return PostEffectUniformType::Contrast;
} else if (!stricmp(uniform_name.c_str(), "film_grain")) {
return PostEffectUniformType::FilmGrain;
} else if (!stricmp(uniform_name.c_str(), "tv_stripes")) {
return PostEffectUniformType::TvStripes;
} else if (!stricmp(uniform_name.c_str(), "cutoff")) {
return PostEffectUniformType::Cutoff;
} else if (!stricmp(uniform_name.c_str(), "dither")) {
return PostEffectUniformType::Dither;
} else if (!stricmp(uniform_name.c_str(), "tint")) {
return PostEffectUniformType::Tint;
} else {
error_display(0, "Unknown uniform name '%s'!", uniform_name.c_str());
return PostEffectUniformType::Invalid;
}
}
static bool opengl_post_init_table()
{
@@ -733,20 +830,19 @@ static bool opengl_post_init_table()
if (optional_string("#Effects")) {
while (!required_string_one_of(3, "$Name:", "#Ship Effects", "#End")) {
char tbuf[NAME_LENGTH + 1] = { 0 };
post_effect_t eff;
required_string("$Name:");
stuff_string(tbuf, F_NAME, NAME_LENGTH);
eff.name = tbuf;
stuff_string(eff.name, F_NAME);
required_string("$Uniform:");
stuff_string(tbuf, F_NAME, NAME_LENGTH);
eff.uniform_name = tbuf;
SCP_string tbuf;
stuff_string(tbuf, F_NAME);
eff.uniform_type = mapUniformNameToType(tbuf);
required_string("$Define:");
stuff_string(tbuf, F_NAME, NAME_LENGTH);
eff.define_name = tbuf;
stuff_string(eff.define_name, F_NAME);
required_string("$AlwaysOn:");
stuff_boolean(&eff.always_on);
@@ -885,6 +981,23 @@ void set_smaa_defines(SCP_stringstream& sflags)
} else {
sflags << "#define SMAA_GLSL_3\n";
}
switch (Gr_aa_mode) {
case AntiAliasMode::SMAA_Low:
sflags << "#define SMAA_PRESET_LOW\n";
break;
case AntiAliasMode::SMAA_Medium:
sflags << "#define SMAA_PRESET_MEDIUM\n";
break;
case AntiAliasMode::SMAA_High:
sflags << "#define SMAA_PRESET_HIGH\n";
break;
case AntiAliasMode::SMAA_Ultra:
sflags << "#define SMAA_PRESET_ULTRA\n";
break;
default:
UNREACHABLE("Unhandled SMAA mode!");
}
}
void opengl_post_shader_header(SCP_stringstream& sflags, shader_type shader_t, int flags)
{
@@ -1142,7 +1255,7 @@ static bool opengl_post_init_framebuffer()
opengl_setup_bloom_textures();
if (gr_is_smaa_mode(Gr_aa_mode)) {
if (Gr_aa_mode != AntiAliasMode::None) {
setup_smaa_resources();
}
+132 -179
View File
@@ -1,33 +1,35 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#include "graphics/opengl/gropenglshader.h"
#include "ShaderProgram.h"
#include "cfile/cfile.h"
#include "cmdline/cmdline.h"
#include "def_files/def_files.h"
#include "graphics/2d.h"
#include "graphics/matrix.h"
#include "graphics/grinternal.h"
#include "graphics/matrix.h"
#include "graphics/opengl/gropengldraw.h"
#include "graphics/opengl/gropenglpostprocessing.h"
#include "graphics/opengl/gropenglshader.h"
#include "graphics/opengl/gropenglstate.h"
#include "graphics/opengl/gropengltexture.h"
#include "graphics/opengl/gropengltnl.h"
#include "graphics/util/uniform_structs.h"
#include "lighting/lighting.h"
#include "math/vecmat.h"
#include "mod_table/mod_table.h"
#include "render/3d.h"
#include "ShaderProgram.h"
#include <md5.h>
#include <jansson.h>
#include <md5.h>
SCP_vector<opengl_shader_t> GL_shader;
@@ -64,12 +66,14 @@ struct opengl_uniform_block_binding {
};
opengl_uniform_block_binding GL_uniform_blocks[] = {
{ uniform_block_type::Lights, "lightData" },
{ uniform_block_type::ModelData, "modelData" },
{ uniform_block_type::NanoVGData, "NanoVGUniformData" },
{ uniform_block_type::DecalInfo, "decalInfoData" },
{ uniform_block_type::DecalGlobals, "decalGlobalData" },
{ uniform_block_type::DeferredGlobals, "globalDeferredData" },
{uniform_block_type::Lights, "lightData"},
{uniform_block_type::ModelData, "modelData"},
{uniform_block_type::NanoVGData, "NanoVGUniformData"},
{uniform_block_type::DecalInfo, "decalInfoData"},
{uniform_block_type::DecalGlobals, "decalGlobalData"},
{uniform_block_type::DeferredGlobals, "globalDeferredData"},
{uniform_block_type::Matrices, "matrixData"},
{uniform_block_type::GenericData, "genericData"},
};
/**
@@ -81,7 +85,7 @@ static opengl_shader_type_t GL_shader_types[] = {
{ SDR_TYPE_MODEL, "main-v.sdr", "main-f.sdr", "main-g.sdr",
{ opengl_vert_attrib::POSITION, opengl_vert_attrib::TEXCOORD, opengl_vert_attrib::NORMAL, opengl_vert_attrib::TANGENT, opengl_vert_attrib::MODEL_ID }, "Model Rendering" },
{ SDR_TYPE_EFFECT_PARTICLE, "effect-v.sdr", "effect-particle-f.sdr", "effect-screen-g.sdr",
{ SDR_TYPE_EFFECT_PARTICLE, "effect-v.sdr", "effect-f.sdr", "effect-g.sdr",
{ opengl_vert_attrib::POSITION, opengl_vert_attrib::TEXCOORD, opengl_vert_attrib::RADIUS, opengl_vert_attrib::COLOR }, "Particle Effects" },
{ SDR_TYPE_EFFECT_DISTORTION, "effect-distort-v.sdr", "effect-distort-f.sdr", 0,
@@ -129,7 +133,7 @@ static opengl_shader_type_t GL_shader_types[] = {
{ SDR_TYPE_BATCHED_BITMAP, "batched-v.sdr", "batched-f.sdr", nullptr,
{ opengl_vert_attrib::POSITION, opengl_vert_attrib::TEXCOORD, opengl_vert_attrib::COLOR }, "Batched bitmaps" },
{ SDR_TYPE_DEFAULT_MATERIAL, "passthrough-v.sdr", "default-material-f.sdr", nullptr,
{ SDR_TYPE_DEFAULT_MATERIAL, "default-material-v.sdr", "default-material-f.sdr", nullptr,
{ opengl_vert_attrib::POSITION, opengl_vert_attrib::TEXCOORD, opengl_vert_attrib::COLOR }, "Default material" },
{ SDR_TYPE_NANOVG, "nanovg-v.sdr", "nanovg-f.sdr", nullptr,
@@ -160,109 +164,63 @@ static opengl_shader_type_t GL_shader_types[] = {
* When adding a new shader variant for a shader, list all associated uniforms and attributes here
*/
static opengl_shader_variant_t GL_shader_variants[] = {
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_LIGHT, "FLAG_LIGHT",
{ },
"Lighting" },
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_LIGHT, "FLAG_LIGHT", {}, "Lighting"},
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_FOG, "FLAG_FOG",
{ },
"Fog Effect" },
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_FOG, "FLAG_FOG", {}, "Fog Effect"},
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_DIFFUSE_MAP, "FLAG_DIFFUSE_MAP",
{ },
"Diffuse Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_GLOW_MAP, "FLAG_GLOW_MAP",
{ },
"Glow Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_SPEC_MAP, "FLAG_SPEC_MAP",
{ },
"Specular Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_NORMAL_MAP, "FLAG_NORMAL_MAP",
{ },
"Normal Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_HEIGHT_MAP, "FLAG_HEIGHT_MAP",
{ },
"Parallax Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_ENV_MAP, "FLAG_ENV_MAP",
{ },
"Environment Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_ANIMATED, "FLAG_ANIMATED",
{ },
"Animated Effects" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_MISC_MAP, "FLAG_MISC_MAP",
{ },
"Utility mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_TEAMCOLOR, "FLAG_TEAMCOLOR",
{ },
"Team Colors" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_DEFERRED, "FLAG_DEFERRED",
{ },
"Deferred lighting" },
{ SDR_TYPE_MODEL, true, SDR_FLAG_MODEL_SHADOW_MAP, "FLAG_SHADOW_MAP",
{ },
"Shadow Mapping" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_SHADOWS, "FLAG_SHADOWS",
{ },
"Shadows" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_THRUSTER, "FLAG_THRUSTER",
{ },
"Thruster scaling" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_TRANSFORM, "FLAG_TRANSFORM",
{ },
"Submodel Transforms" },
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_CLIP, "FLAG_CLIP",
{ },
"Clip Plane" },
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_DIFFUSE_MAP, "FLAG_DIFFUSE_MAP", {}, "Diffuse Mapping"},
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_HDR, "FLAG_HDR",
{ },
"High Dynamic Range" },
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_GLOW_MAP, "FLAG_GLOW_MAP", {}, "Glow Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_SPEC_MAP, "FLAG_SPEC_MAP", {}, "Specular Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_NORMAL_MAP, "FLAG_NORMAL_MAP", {}, "Normal Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_HEIGHT_MAP, "FLAG_HEIGHT_MAP", {}, "Parallax Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_ENV_MAP, "FLAG_ENV_MAP", {}, "Environment Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_ANIMATED, "FLAG_ANIMATED", {}, "Animated Effects"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_MISC_MAP, "FLAG_MISC_MAP", {}, "Utility mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_TEAMCOLOR, "FLAG_TEAMCOLOR", {}, "Team Colors"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_DEFERRED, "FLAG_DEFERRED", {}, "Deferred lighting"},
{SDR_TYPE_MODEL, true, SDR_FLAG_MODEL_SHADOW_MAP, "FLAG_SHADOW_MAP", {}, "Shadow Mapping"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_SHADOWS, "FLAG_SHADOWS", {}, "Shadows"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_THRUSTER, "FLAG_THRUSTER", {}, "Thruster scaling"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_TRANSFORM, "FLAG_TRANSFORM", {}, "Submodel Transforms"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_CLIP, "FLAG_CLIP", {}, "Clip Plane"},
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_HDR, "FLAG_HDR", {}, "High Dynamic Range"},
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_AMBIENT_MAP, "FLAG_AMBIENT_MAP",
{ },
"Ambient Occlusion Map" },
{ }, "Ambient Occlusion Map"},
{ SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_NORMAL_ALPHA, "FLAG_NORMAL_ALPHA",
{ },
"Normal Alpha" },
{SDR_TYPE_MODEL, false, SDR_FLAG_MODEL_NORMAL_ALPHA, "FLAG_NORMAL_ALPHA", {}, "Normal Alpha"},
{ SDR_TYPE_MODEL, true, SDR_FLAG_MODEL_THICK_OUTLINES, "FLAG_THICK_OUTLINE",
{ },
"Thick outlines" },
{SDR_TYPE_MODEL, true, SDR_FLAG_MODEL_THICK_OUTLINES, "FLAG_THICK_OUTLINE", {}, "Thick outlines"},
{ SDR_TYPE_EFFECT_PARTICLE, true, SDR_FLAG_PARTICLE_POINT_GEN, "FLAG_EFFECT_GEOMETRY",
{ opengl_vert_attrib::UVEC },
"Geometry shader point-based particles" },
{ SDR_TYPE_POST_PROCESS_BLUR, false, SDR_FLAG_BLUR_HORIZONTAL, "PASS_0",
{ },
"Horizontal blur pass" },
{ SDR_TYPE_POST_PROCESS_BLUR, false, SDR_FLAG_BLUR_VERTICAL, "PASS_1",
{ },
"Vertical blur pass" },
{SDR_TYPE_EFFECT_PARTICLE,
true,
SDR_FLAG_PARTICLE_POINT_GEN,
"FLAG_EFFECT_GEOMETRY",
{opengl_vert_attrib::UVEC},
"Geometry shader point-based particles"},
{ SDR_TYPE_NANOVG, false, SDR_FLAG_NANOVG_EDGE_AA, "EDGE_AA",
{ },
"NanoVG edge anti-alias" },
{SDR_TYPE_POST_PROCESS_BLUR, false, SDR_FLAG_BLUR_HORIZONTAL, "PASS_0", {}, "Horizontal blur pass"},
{ SDR_TYPE_DECAL, false, SDR_FLAG_DECAL_USE_NORMAL_MAP, "USE_NORMAL_MAP",
{ },
"Decal use scene normal map" },
{SDR_TYPE_POST_PROCESS_BLUR, false, SDR_FLAG_BLUR_VERTICAL, "PASS_1", {}, "Vertical blur pass"},
{SDR_TYPE_NANOVG, false, SDR_FLAG_NANOVG_EDGE_AA, "EDGE_AA", {}, "NanoVG edge anti-alias"},
{SDR_TYPE_DECAL, false, SDR_FLAG_DECAL_USE_NORMAL_MAP, "USE_NORMAL_MAP", {}, "Decal use scene normal map"},
};
static const int GL_num_shader_variants = sizeof(GL_shader_variants) / sizeof(opengl_shader_variant_t);
@@ -315,7 +273,7 @@ void opengl_shader_set_current(int handle)
opengl_shader_set_current(&GL_shader[handle]);
}
size_t opengl_get_shader_idx(shader_type shader_t, unsigned int flags)
size_t opengl_get_shader_idx(shader_type shader_t, unsigned int flags)
{
auto found = GL_shader_map.find(shader_descriptor_t(shader_t, flags));
if (found != GL_shader_map.end()) {
@@ -350,7 +308,7 @@ void opengl_delete_shader(int sdr_handle)
GL_shader_map.erase(shader_descriptor_t(victim.shader, victim.flags));
GL_shader[sdr_handle].program.reset();
GL_shader[sdr_handle].flags = 0;
GL_shader[sdr_handle].flags2 = 0;
GL_shader[sdr_handle].shader = NUM_SHADER_TYPES;
@@ -614,9 +572,9 @@ static bool load_cached_shader_binary(opengl::ShaderProgram* program, const SCP_
nprintf(("ShaderCache", "Binary file does not exist.\n"));
return false;
}
GR_DEBUG_SCOPE("Loading cached shader");
SCP_vector<uint8_t> buffer;
int length = cfilelength(binary_fp);
buffer.resize((size_t) length);
@@ -647,7 +605,7 @@ static void cache_program_binary(GLuint program, const SCP_string& hash) {
if (!do_shader_caching()) {
return;
}
GR_DEBUG_SCOPE("Saving shader binary");
GLint size;
@@ -701,16 +659,16 @@ static void cache_program_binary(GLuint program, const SCP_string& hash) {
static void opengl_set_default_uniforms(const opengl_shader_t& sdr) {
switch (sdr.shader) {
case SDR_TYPE_DEFERRED_LIGHTING:
Current_shader->program->Uniforms.setUniformi("ColorBuffer", 0);
Current_shader->program->Uniforms.setUniformi("NormalBuffer", 1);
Current_shader->program->Uniforms.setUniformi("PositionBuffer", 2);
Current_shader->program->Uniforms.setUniformi("SpecBuffer", 3);
Current_shader->program->Uniforms.setUniformi("shadow_map", 4);
Current_shader->program->Uniforms.setTextureUniform("ColorBuffer", 0);
Current_shader->program->Uniforms.setTextureUniform("NormalBuffer", 1);
Current_shader->program->Uniforms.setTextureUniform("PositionBuffer", 2);
Current_shader->program->Uniforms.setTextureUniform("SpecBuffer", 3);
Current_shader->program->Uniforms.setTextureUniform("shadow_map", 4);
break;
case SDR_TYPE_PASSTHROUGH_RENDER:
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setUniformi("clipEnabled", 0);
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("clipEnabled", 0);
break;
default:
@@ -1007,76 +965,71 @@ void opengl_shader_set_passthrough(bool textured, bool hdr)
{
opengl_shader_set_current(gr_opengl_maybe_create_shader(SDR_TYPE_PASSTHROUGH_RENDER, 0));
if ( textured ) {
Current_shader->program->Uniforms.setUniformi("noTexturing", 0);
} else {
Current_shader->program->Uniforms.setUniformi("noTexturing", 1);
}
gr_matrix_set_uniforms();
Current_shader->program->Uniforms.setUniformi("alphaTexture", 0);
Current_shader->program->Uniforms.setUniformi("srgb", hdr ? 1 : 0);
Current_shader->program->Uniforms.setUniformf("intensity", 1.0f);
Current_shader->program->Uniforms.setUniformf("alphaThreshold", GL_alpha_threshold);
Current_shader->program->Uniforms.setUniform4f("color", 1.0f, 1.0f, 1.0f, 1.0f);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
opengl_set_generic_uniform_data<graphics::generic_data::passthrough_data>(
[=](graphics::generic_data::passthrough_data* data) {
data->noTexturing = textured ? 0 : 1;
data->srgb = hdr ? 1 : 0;
});
}
void opengl_shader_set_default_material(bool textured, bool alpha, vec4 *clr, float color_scale, uint32_t array_index, const material::clip_plane& clip_plane)
void opengl_shader_set_default_material(bool textured, bool alpha, vec4* clr, float color_scale, uint32_t array_index,
const material::clip_plane& clip_plane)
{
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
if ( textured ) {
Current_shader->program->Uniforms.setUniformi("noTexturing", 0);
Current_shader->program->Uniforms.setUniformi("baseMapIndex", array_index);
} else {
Current_shader->program->Uniforms.setUniformi("noTexturing", 1);
// array_index is probably not valid here
Current_shader->program->Uniforms.setUniformi("baseMapIndex", 0);
}
opengl_set_generic_uniform_data<graphics::generic_data::default_material_data>(
[=](graphics::generic_data::default_material_data* data) {
if (textured) {
data->noTexturing = 0;
data->baseMapIndex = array_index;
} else {
data->noTexturing = 1;
// array_index is probably not valid here
data->baseMapIndex = 0;
}
if ( alpha ) {
Current_shader->program->Uniforms.setUniformi("alphaTexture", 1);
} else {
Current_shader->program->Uniforms.setUniformi("alphaTexture", 0);
}
if (alpha) {
data->alphaTexture = 1;
} else {
data->alphaTexture = 0;
}
if ( High_dynamic_range ) {
Current_shader->program->Uniforms.setUniformi("srgb", 1);
Current_shader->program->Uniforms.setUniformf("intensity", color_scale);
} else {
Current_shader->program->Uniforms.setUniformi("srgb", 0);
Current_shader->program->Uniforms.setUniformf("intensity", 1.0f);
}
if (High_dynamic_range) {
data->srgb = 1;
data->intensity = color_scale;
} else {
data->srgb = 0;
data->intensity = 1.0f;
}
Current_shader->program->Uniforms.setUniformf("alphaThreshold", GL_alpha_threshold);
data->alphaThreshold = GL_alpha_threshold;
if ( clr != NULL ) {
Current_shader->program->Uniforms.setUniform4f("color", *clr);
} else {
Current_shader->program->Uniforms.setUniform4f("color", 1.0f, 1.0f, 1.0f, 1.0f);
}
if (clr != nullptr) {
data->color = *clr;
} else {
data->color.xyzw.x = 1.0f;
data->color.xyzw.y = 1.0f;
data->color.xyzw.z = 1.0f;
data->color.xyzw.w = 1.0f;
}
if (clip_plane.enabled) {
Current_shader->program->Uniforms.setUniformi("clipEnabled", 1);
if (clip_plane.enabled) {
data->clipEnabled = 1;
vec4 clip_equation;
clip_equation.xyzw.x = clip_plane.normal.xyz.x;
clip_equation.xyzw.y = clip_plane.normal.xyz.y;
clip_equation.xyzw.z = clip_plane.normal.xyz.z;
clip_equation.xyzw.w = -vm_vec_dot(&clip_plane.normal, &clip_plane.position);
vec4 clip_equation;
clip_equation.xyzw.x = clip_plane.normal.xyz.x;
clip_equation.xyzw.y = clip_plane.normal.xyz.y;
clip_equation.xyzw.z = clip_plane.normal.xyz.z;
clip_equation.xyzw.w = -vm_vec_dot(&clip_plane.normal, &clip_plane.position);
Current_shader->program->Uniforms.setUniform4f("clipEquation", clip_equation);
Current_shader->program->Uniforms.setUniformMatrix4f("modelMatrix", gr_model_matrix_stack.get_transform());
} else {
Current_shader->program->Uniforms.setUniformi("clipEnabled", 0);
}
data->clipEquation = clip_equation;
data->modelMatrix = gr_model_matrix_stack.get_transform();
} else {
data->clipEnabled = 0;
}
});
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
}
+20 -12
View File
@@ -1,34 +1,29 @@
/*
* Copyright (C) Volition, Inc. 1999. All rights reserved.
*
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* All source code herein is the property of Volition, Inc. You may not sell
* or otherwise commercially exploit the source or things you created based on the
* source.
*
*/
*/
#ifndef _GROPENGLSHADER_H
#define _GROPENGLSHADER_H
#include "globalincs/pstypes.h"
#include "graphics/2d.h"
#include "graphics/opengl/gropengl.h"
#include "graphics/material.h"
#include "graphics/opengl/gropengl.h"
#include "graphics/util/UniformBuffer.h"
#include <string>
#include <glad/glad.h>
namespace opengl {
// Forward definition to avoid cyclic dependency
class ShaderProgram;
}
} // namespace opengl
enum shader_stage {
SDR_STAGE_VERTEX,
SDR_STAGE_FRAGMENT,
SDR_STAGE_GEOMETRY
};
enum shader_stage { SDR_STAGE_VERTEX, SDR_STAGE_FRAGMENT, SDR_STAGE_GEOMETRY };
struct opengl_vert_attrib {
enum attrib_id {
@@ -160,5 +155,18 @@ void opengl_shader_set_passthrough(bool textured, bool hdr);
void opengl_shader_set_default_material(bool textured, bool alpha, vec4* clr, float color_scale, uint32_t array_index, const material::clip_plane& clip_plane);
template <typename T, typename DataCallback>
void opengl_set_generic_uniform_data(DataCallback cb)
{
auto buffer = gr_get_uniform_buffer(uniform_block_type::GenericData, 1, sizeof(T));
auto bufferPtr = buffer.aligner().addTypedElement<T>();
cb(bufferPtr);
buffer.submitData();
gr_bind_uniform_buffer(uniform_block_type::GenericData, buffer.getBufferOffset(0), sizeof(T),
buffer.bufferHandle());
}
#endif // _GROPENGLSHADER_H
-2
View File
@@ -45,9 +45,7 @@ GLint GL_max_renderbuffer_size = 0;
extern int GLOWMAP;
extern int SPECMAP;
extern int CLOAKMAP;
extern int ENVMAP;
extern int Interp_multitex_cloakmap;
static SCP_vector<float> anisotropic_value_enumerator()
{
+153 -133
View File
@@ -37,7 +37,6 @@
#include "weapon/trails.h"
extern int GLOWMAP;
extern int CLOAKMAP;
extern int SPECMAP;
extern int SPECGLOSSMAP;
extern int NORMMAP;
@@ -90,7 +89,8 @@ static opengl_vertex_bind GL_array_binding_data[] =
struct opengl_buffer_object {
GLuint buffer_id;
GLenum type;
GLenum usage;
GLenum gl_usage;
BufferUsageHint usage;
size_t size;
GLuint texture; // for texture buffer objects
@@ -121,7 +121,9 @@ static GLenum convertUsageHint(BufferUsageHint usage) {
return GL_DYNAMIC_DRAW;
case BufferUsageHint::Streaming:
return GL_STREAM_DRAW;
default:
case BufferUsageHint::PersistentMapping:
return GL_NONE; // Dummy value
default:
UNREACHABLE("Unhandled enum value!");
return GL_INVALID_ENUM;
}
@@ -186,12 +188,16 @@ static GLenum convertComparisionFunction(ComparisionFunction func) {
return mode;
}
int opengl_create_buffer_object(GLenum type, GLenum usage)
int opengl_create_buffer_object(GLenum type, GLenum gl_usage, BufferUsageHint usage)
{
GR_DEBUG_SCOPE("Create buffer object");
Assertion(usage != BufferUsageHint::PersistentMapping || GLAD_GL_ARB_buffer_storage != 0,
"Persistent mapping is not supported by this OpenGL implementation!");
opengl_buffer_object buffer_obj;
buffer_obj.gl_usage = gl_usage;
buffer_obj.usage = usage;
buffer_obj.type = type;
buffer_obj.size = 0;
@@ -242,7 +248,7 @@ GLuint opengl_buffer_get_id(GLenum expected_type, int handle) {
return buffer_obj.buffer_id;
}
void gr_opengl_update_buffer_data(int handle, size_t size, void* data)
void gr_opengl_update_buffer_data(int handle, size_t size, const void* data)
{
// This has to be verified by the caller or else we will run into OPenGL errors
Assertion(size > 0, "Buffer updates must include some data!");
@@ -256,31 +262,20 @@ void gr_opengl_update_buffer_data(int handle, size_t size, void* data)
opengl_bind_buffer_object(handle);
if (size <= buffer_obj.size && buffer_obj.type == GL_UNIFORM_BUFFER) {
// Uniform buffer can use unsychronized buffer mapping since those are always synchronized by us
// We also don't care about the previous data and tell OpenGL to map the buffer unsynchronized.
auto ptr = glMapBufferRange(buffer_obj.type,
0,
size,
GL_MAP_WRITE_BIT | GL_MAP_INVALIDATE_BUFFER_BIT | GL_MAP_UNSYNCHRONIZED_BIT);
if (ptr == nullptr) {
// Something went wrong, try subdata instead
glBufferSubData(buffer_obj.type, 0, size, data);
} else {
memcpy(ptr, data, size);
glUnmapBuffer(buffer_obj.type);
}
if (buffer_obj.usage == BufferUsageHint::PersistentMapping) {
Assertion(buffer_obj.size == 0, "Tried to resize a buffer for persistent mapping! This is not allowed.");
Assertion(GLAD_GL_ARB_buffer_storage != 0, "Persistent mapping was used when it wasn't supported!");
glBufferStorage(buffer_obj.type, size, data, GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT);
} else {
GL_vertex_data_in -= buffer_obj.size;
buffer_obj.size = size;
GL_vertex_data_in += buffer_obj.size;
glBufferData(buffer_obj.type, size, data, buffer_obj.usage);
glBufferData(buffer_obj.type, size, data, buffer_obj.gl_usage);
}
GL_vertex_data_in -= buffer_obj.size;
buffer_obj.size = size;
GL_vertex_data_in += buffer_obj.size;
}
void gr_opengl_update_buffer_data_offset(int handle, size_t offset, size_t size, void* data)
void gr_opengl_update_buffer_data_offset(int handle, size_t offset, size_t size, const void* data)
{
GR_DEBUG_SCOPE("Update buffer data with offset");
@@ -289,10 +284,46 @@ void gr_opengl_update_buffer_data_offset(int handle, size_t offset, size_t size,
opengl_buffer_object &buffer_obj = GL_buffer_objects[handle];
Assertion(buffer_obj.usage != BufferUsageHint::PersistentMapping,
"Persistently mapped buffers may not be updated!");
opengl_bind_buffer_object(handle);
glBufferSubData(buffer_obj.type, offset, size, data);
}
void* gr_opengl_map_buffer(int handle)
{
GR_DEBUG_SCOPE("Map buffer");
Assert(handle >= 0);
Assert((size_t)handle < GL_buffer_objects.size());
auto& buffer_obj = GL_buffer_objects[handle];
Assertion(buffer_obj.usage == BufferUsageHint::PersistentMapping,
"Buffer mapping is only supported for persistently mapped buffers!");
Assertion(GLAD_GL_ARB_buffer_storage != 0, "Persistent mapping is not available in this OpenGL context!");
opengl_bind_buffer_object(handle);
return glMapBufferRange(buffer_obj.type, 0, buffer_obj.size,
GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_FLUSH_EXPLICIT_BIT);
}
void gr_opengl_flush_mapped_buffer(int handle, size_t offset, size_t size)
{
GR_DEBUG_SCOPE("Flush mapped buffer");
Assert(handle >= 0);
Assert((size_t)handle < GL_buffer_objects.size());
auto& buffer_obj = GL_buffer_objects[handle];
Assertion(buffer_obj.usage == BufferUsageHint::PersistentMapping,
"Buffer mapping is only supported for persistently mapped buffers!");
Assertion(GLAD_GL_ARB_buffer_storage != 0, "Persistent mapping is not available in this OpenGL context!");
opengl_bind_buffer_object(handle);
glFlushMappedBufferRange(buffer_obj.type, offset, size);
}
void gr_opengl_delete_buffer(int handle)
{
@@ -336,7 +367,7 @@ void gr_opengl_delete_buffer(int handle)
int gr_opengl_create_buffer(BufferType type, BufferUsageHint usage)
{
return opengl_create_buffer_object(convertBufferType(type), convertUsageHint(usage));
return opengl_create_buffer_object(convertBufferType(type), convertUsageHint(usage), usage);
}
void gr_opengl_bind_uniform_buffer(uniform_block_type bind_point, size_t offset, size_t size, int buffer) {
@@ -361,7 +392,8 @@ void gr_opengl_bind_uniform_buffer(uniform_block_type bind_point, size_t offset,
int opengl_create_texture_buffer_object()
{
// create the buffer
int buffer_object_handle = opengl_create_buffer_object(GL_TEXTURE_BUFFER, GL_DYNAMIC_DRAW);
int buffer_object_handle =
opengl_create_buffer_object(GL_TEXTURE_BUFFER, GL_DYNAMIC_DRAW, BufferUsageHint::Dynamic);
opengl_check_for_errors();
@@ -734,8 +766,7 @@ void opengl_tnl_set_material(material* material_info, bool set_base_map, bool se
if (!clip_params.enabled) {
GL_state.ClipDistance(0, false);
} else {
Assertion(Current_shader != NULL && (Current_shader->shader == SDR_TYPE_MODEL
|| Current_shader->shader == SDR_TYPE_PASSTHROUGH_RENDER
Assertion(Current_shader != nullptr && (Current_shader->shader == SDR_TYPE_MODEL
|| Current_shader->shader == SDR_TYPE_DEFAULT_MATERIAL),
"Clip planes are not supported by this shader!");
@@ -787,7 +818,6 @@ void opengl_tnl_set_material(material* material_info, bool set_base_map, bool se
void opengl_tnl_set_model_material(model_material *material_info)
{
float u_scale, v_scale;
int render_pass = 0;
opengl_tnl_set_material(material_info, false, false);
@@ -809,98 +839,78 @@ void opengl_tnl_set_model_material(model_material *material_info)
uint32_t array_index;
if ( Current_shader->flags & SDR_FLAG_MODEL_DIFFUSE_MAP ) {
Current_shader->program->Uniforms.setUniformi("sBasemap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sBasemap", 0);
gr_opengl_tcache_set(material_info->get_texture_map(TM_BASE_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_BASE_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 0);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_GLOW_MAP ) {
Current_shader->program->Uniforms.setUniformi("sGlowmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sGlowmap", 1);
gr_opengl_tcache_set(material_info->get_texture_map(TM_GLOW_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_GLOW_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 1);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_SPEC_MAP ) {
Current_shader->program->Uniforms.setUniformi("sSpecmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sSpecmap", 2);
if ( material_info->get_texture_map(TM_SPEC_GLOSS_TYPE) > 0 ) {
gr_opengl_tcache_set(material_info->get_texture_map(TM_SPEC_GLOSS_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
gr_opengl_tcache_set(material_info->get_texture_map(TM_SPEC_GLOSS_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 2);
} else {
gr_opengl_tcache_set(material_info->get_texture_map(TM_SPECULAR_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
gr_opengl_tcache_set(material_info->get_texture_map(TM_SPECULAR_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 2);
}
++render_pass;
if ( Current_shader->flags & SDR_FLAG_MODEL_ENV_MAP ) {
Current_shader->program->Uniforms.setUniformi("sEnvmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sEnvmap", 3);
gr_opengl_tcache_set(ENVMAP, TCACHE_TYPE_CUBEMAP, &u_scale, &v_scale, &array_index, render_pass);
gr_opengl_tcache_set(ENVMAP, TCACHE_TYPE_CUBEMAP, &u_scale, &v_scale, &array_index, 3);
Assertion(array_index == 0, "Cube map arrays are not supported yet!");
++render_pass;
}
}
if ( Current_shader->flags & SDR_FLAG_MODEL_NORMAL_MAP ) {
Current_shader->program->Uniforms.setUniformi("sNormalmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sNormalmap", 4);
gr_opengl_tcache_set(material_info->get_texture_map(TM_NORMAL_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_NORMAL_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 4);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_HEIGHT_MAP ) {
Current_shader->program->Uniforms.setUniformi("sHeightmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sHeightmap", 5);
gr_opengl_tcache_set(material_info->get_texture_map(TM_HEIGHT_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_HEIGHT_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 5);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_AMBIENT_MAP ) {
Current_shader->program->Uniforms.setUniformi("sAmbientmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sAmbientmap", 6);
gr_opengl_tcache_set(material_info->get_texture_map(TM_AMBIENT_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_AMBIENT_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 6);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_MISC_MAP ) {
Current_shader->program->Uniforms.setUniformi("sMiscmap", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sMiscmap", 7);
gr_opengl_tcache_set(material_info->get_texture_map(TM_MISC_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, render_pass);
++render_pass;
gr_opengl_tcache_set(material_info->get_texture_map(TM_MISC_TYPE), TCACHE_TYPE_NORMAL, &u_scale, &v_scale, &array_index, 7);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_SHADOWS ) {
Current_shader->program->Uniforms.setUniformi("shadow_map", render_pass);
Current_shader->program->Uniforms.setTextureUniform("shadow_map", 8);
GL_state.Texture.Enable(render_pass, GL_TEXTURE_2D_ARRAY, Shadow_map_texture);
++render_pass; // bump!
GL_state.Texture.Enable(8, GL_TEXTURE_2D_ARRAY, Shadow_map_texture);
}
if ( Current_shader->flags & SDR_FLAG_MODEL_ANIMATED ) {
Current_shader->program->Uniforms.setUniformi("sFramebuffer", render_pass);
Current_shader->program->Uniforms.setTextureUniform("sFramebuffer", 9);
if ( Scene_framebuffer_in_frame ) {
GL_state.Texture.Enable(render_pass, GL_TEXTURE_2D, Scene_effect_texture);
GL_state.Texture.Enable(9, GL_TEXTURE_2D, Scene_effect_texture);
glDrawBuffer(GL_COLOR_ATTACHMENT0);
} else {
GL_state.Texture.Enable(render_pass, GL_TEXTURE_2D, Framebuffer_fallback_texture_id);
GL_state.Texture.Enable(9, GL_TEXTURE_2D, Framebuffer_fallback_texture_id);
}
++render_pass;
}
if ( Current_shader->flags & SDR_FLAG_MODEL_TRANSFORM ) {
Current_shader->program->Uniforms.setUniformi("transform_tex", render_pass);
GL_state.Texture.Enable(render_pass, GL_TEXTURE_BUFFER, opengl_get_transform_buffer_texture());
++render_pass;
Current_shader->program->Uniforms.setTextureUniform("transform_tex", 10);
GL_state.Texture.Enable(10, GL_TEXTURE_BUFFER, opengl_get_transform_buffer_texture());
}
if ( Deferred_lighting ) {
@@ -913,25 +923,28 @@ void opengl_tnl_set_material_particle(particle_material * material_info)
{
opengl_tnl_set_material(material_info, true);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setUniformi("depthMap", 1);
Current_shader->program->Uniforms.setUniformf("window_width", (float)gr_screen.max_w);
Current_shader->program->Uniforms.setUniformf("window_height", (float)gr_screen.max_h);
Current_shader->program->Uniforms.setUniformf("nearZ", Min_draw_distance);
Current_shader->program->Uniforms.setUniformf("farZ", Max_draw_distance);
Current_shader->program->Uniforms.setUniformi("srgb", High_dynamic_range ? 1 : 0);
Current_shader->program->Uniforms.setUniformi("blend_alpha", material_info->get_blend_mode() != ALPHA_BLEND_ADDITIVE);
opengl_set_generic_uniform_data<graphics::generic_data::effect_data>(
[&](graphics::generic_data::effect_data* data) {
data->window_width = (float)gr_screen.max_w;
data->window_height = (float)gr_screen.max_h;
data->nearZ = Min_draw_distance;
data->farZ = Max_draw_distance;
data->srgb = High_dynamic_range ? 1 : 0;
data->blend_alpha = material_info->get_blend_mode() != ALPHA_BLEND_ADDITIVE;
if ( Cmdline_no_deferred_lighting ) {
Current_shader->program->Uniforms.setUniformi("linear_depth", 0);
} else {
Current_shader->program->Uniforms.setUniformi("linear_depth", 1);
}
if (Cmdline_no_deferred_lighting) {
data->linear_depth = 0;
} else {
data->linear_depth = 1;
}
});
if ( !Cmdline_no_deferred_lighting ) {
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("depthMap", 1);
if (!Cmdline_no_deferred_lighting) {
Assert(Scene_position_texture != 0);
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Scene_position_texture);
@@ -941,48 +954,52 @@ void opengl_tnl_set_material_particle(particle_material * material_info)
GL_state.Texture.Enable(1, GL_TEXTURE_2D, Scene_depth_texture);
}
}
void opengl_tnl_set_material_batched(batched_bitmap_material* material_info) {
void opengl_tnl_set_material_batched(batched_bitmap_material* material_info)
{
// This material assumes that the array index is supplied via the vertex attributes
opengl_tnl_set_material(material_info, true);
Current_shader->program->Uniforms.setUniformf("intensity", material_info->get_color_scale());
opengl_set_generic_uniform_data<graphics::generic_data::batched_data>(
[&](graphics::generic_data::batched_data* data) {
data->intensity = material_info->get_color_scale();
data->color = material_info->get_color();
});
Current_shader->program->Uniforms.setUniform4f("color", material_info->get_color());
gr_matrix_set_uniforms();
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
}
void opengl_tnl_set_material_distortion(distortion_material* material_info)
{
opengl_tnl_set_material(material_info, true);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setUniformi("depthMap", 1);
Current_shader->program->Uniforms.setUniformf("window_width", (float)gr_screen.max_w);
Current_shader->program->Uniforms.setUniformf("window_height", (float)gr_screen.max_h);
Current_shader->program->Uniforms.setUniformf("nearZ", Min_draw_distance);
Current_shader->program->Uniforms.setUniformf("farZ", Max_draw_distance);
Current_shader->program->Uniforms.setUniformi("frameBuffer", 2);
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("depthMap", 1);
opengl_set_generic_uniform_data<graphics::generic_data::effect_distort_data>(
[&](graphics::generic_data::effect_distort_data* data) {
data->window_width = (float)gr_screen.max_w;
data->window_height = (float)gr_screen.max_h;
if (material_info->get_thruster_rendering()) {
data->use_offset = 1.0f;
} else {
data->use_offset = 0.0f;
}
});
Current_shader->program->Uniforms.setTextureUniform("frameBuffer", 2);
GL_state.Texture.Enable(2, GL_TEXTURE_2D, Scene_effect_texture);
Current_shader->program->Uniforms.setUniformi("distMap", 3);
if(material_info->get_thruster_rendering()) {
Current_shader->program->Uniforms.setTextureUniform("distMap", 3);
if (material_info->get_thruster_rendering()) {
GL_state.Texture.Enable(3, GL_TEXTURE_2D, Distortion_texture[!Distortion_switch]);
Current_shader->program->Uniforms.setUniformf("use_offset", 1.0f);
} else {
// Disable this texture unit
GL_state.Texture.Enable(3, GL_TEXTURE_2D, 0);
Current_shader->program->Uniforms.setUniformf("use_offset", 0.0f);
}
Assert(Scene_depth_texture != 0);
@@ -993,12 +1010,11 @@ void opengl_tnl_set_material_distortion(distortion_material* material_info)
void opengl_tnl_set_material_movie(movie_material* material_info) {
opengl_tnl_set_material(material_info, false);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", gr_model_view_matrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
gr_matrix_set_uniforms();
Current_shader->program->Uniforms.setUniformi("ytex", 0);
Current_shader->program->Uniforms.setUniformi("utex", 1);
Current_shader->program->Uniforms.setUniformi("vtex", 2);
Current_shader->program->Uniforms.setTextureUniform("ytex", 0);
Current_shader->program->Uniforms.setTextureUniform("utex", 1);
Current_shader->program->Uniforms.setTextureUniform("vtex", 2);
float u_scale, v_scale;
uint32_t index;
@@ -1015,7 +1031,7 @@ void opengl_tnl_set_material_movie(movie_material* material_info) {
void opengl_tnl_set_material_nanovg(nanovg_material* material_info) {
opengl_tnl_set_material(material_info, true);
Current_shader->program->Uniforms.setUniformi("nvg_tex", 0);
Current_shader->program->Uniforms.setTextureUniform("nvg_tex", 0);
}
void opengl_tnl_set_material_decal(decal_material* material_info) {
@@ -1030,7 +1046,7 @@ void opengl_tnl_set_material_decal(decal_material* material_info) {
&v_scale,
&array_index,
0)) {
Current_shader->program->Uniforms.setUniformi("diffuseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("diffuseMap", 0);
}
if (gr_opengl_tcache_set(material_info->get_texture_map(TM_GLOW_TYPE),
@@ -1039,7 +1055,7 @@ void opengl_tnl_set_material_decal(decal_material* material_info) {
&v_scale,
&array_index,
1)) {
Current_shader->program->Uniforms.setUniformi("glowMap", 1);
Current_shader->program->Uniforms.setTextureUniform("glowMap", 1);
}
if (gr_opengl_tcache_set(material_info->get_texture_map(TM_NORMAL_TYPE),
@@ -1048,15 +1064,15 @@ void opengl_tnl_set_material_decal(decal_material* material_info) {
&v_scale,
&array_index,
2)) {
Current_shader->program->Uniforms.setUniformi("normalMap", 2);
Current_shader->program->Uniforms.setTextureUniform("normalMap", 2);
}
GL_state.Texture.Enable(3, GL_TEXTURE_2D, Scene_depth_texture);
Current_shader->program->Uniforms.setUniformi("gDepthBuffer", 3);
Current_shader->program->Uniforms.setTextureUniform("gDepthBuffer", 3);
if (Current_shader->flags & SDR_FLAG_DECAL_USE_NORMAL_MAP) {
GL_state.Texture.Enable(4, GL_TEXTURE_2D, Scene_normal_texture);
Current_shader->program->Uniforms.setUniformi("gNormalBuffer", 4);
Current_shader->program->Uniforms.setTextureUniform("gNormalBuffer", 4);
}
}
@@ -1071,21 +1087,25 @@ void opengl_tnl_set_rocketui_material(interface_material* material_info)
opengl_tnl_set_material(material_info, false);
Current_shader->program->Uniforms.setUniformMatrix4f("modelViewMatrix", modelViewMatrix);
Current_shader->program->Uniforms.setUniformMatrix4f("projMatrix", gr_projection_matrix);
Current_shader->program->Uniforms.setUniformi("textured", material_info->is_textured() ? GL_TRUE : GL_FALSE);
Current_shader->program->Uniforms.setUniformi("baseMap", 0);
Current_shader->program->Uniforms.setTextureUniform("baseMap", 0);
uint32_t baseMapIndex = 0;
if (material_info->is_textured()) {
float u_scale, v_scale;
uint32_t array_index;
if (!gr_opengl_tcache_set(material_info->get_texture_map(TM_BASE_TYPE), material_info->get_texture_type(),
&u_scale, &v_scale, &array_index)) {
&u_scale, &v_scale, &baseMapIndex)) {
mprintf(("WARNING: Error setting bitmap texture (%i)!\n", material_info->get_texture_map(TM_BASE_TYPE)));
}
Current_shader->program->Uniforms.setUniformi("baseMapIndex", array_index);
}
opengl_set_generic_uniform_data<graphics::generic_data::rocketui_data>(
[&](graphics::generic_data::rocketui_data* data) {
data->modelViewMatrix = modelViewMatrix;
data->projMatrix = gr_projection_matrix;
data->textured = material_info->is_textured() ? GL_TRUE : GL_FALSE;
data->baseMapIndex = baseMapIndex;
});
}
void gr_opengl_set_viewport(int x, int y, int width, int height) {
+5 -2
View File
@@ -16,6 +16,7 @@
#include "globalincs/pstypes.h"
#include "gropengl.h"
#include "gropenglshader.h"
#include "graphics/shadows.h"
#include "model/model.h"
@@ -46,10 +47,12 @@ struct opengl_vertex_bind {
int gr_opengl_create_buffer(BufferType type, BufferUsageHint usage);
void opengl_bind_buffer_object(int handle);
void gr_opengl_update_buffer_data(int handle, size_t size, void* data);
void gr_opengl_update_buffer_data_offset(int handle, size_t offset, size_t size, void* data);
void gr_opengl_update_buffer_data(int handle, size_t size, const void* data);
void gr_opengl_update_buffer_data_offset(int handle, size_t offset, size_t size, const void* data);
void gr_opengl_delete_buffer(int handle);
void gr_opengl_bind_uniform_buffer(uniform_block_type bind_point, size_t offset, size_t size, int buffer);
void* gr_opengl_map_buffer(int handle);
void gr_opengl_flush_mapped_buffer(int handle, size_t offset, size_t size);
/**
* @brief Retrieves the OpenGL handle of a generic buffer handle
+23 -35
View File
@@ -22,20 +22,20 @@
#include "tracing/tracing.h"
#ifndef NDEBUG
// That is a wrapper function for log prints to be availiable for nanovg components. For now it is stb_truetype.h
// Planted by ksotar with blessing from asarium
extern "C" {
void nvgOldCPrintf(SCP_FORMAT_STRING const char *message, ...) {
SCP_string buf;
va_list args;
va_start(args, message);
vsprintf(buf, message, args);
va_end(args);
outwnd_printf2("%s", message);
if (LoggingEnabled) {
SCP_string buf;
va_list args;
va_start(args, message);
vsprintf(buf, message, args);
va_end(args);
outwnd_printf2("%s", message);
}
}
}
#endif
namespace {
@@ -427,13 +427,13 @@ void NanoVGRenderer::renderFlush() {
gr_set_viewport(0, 0, gr_screen.max_w, gr_screen.max_h);
_uniformBuffer = gr_get_uniform_buffer(uniform_block_type::NanoVGData);
_uniformBuffer = gr_get_uniform_buffer(uniform_block_type::NanoVGData, _uniformData.size());
// This copies the uniform data from our vector into the uniform buffer aligner
for (auto& uniform : _uniformData) {
memcpy(_uniformBuffer->aligner().addTypedElement<nanovg_draw_data>(), &uniform, sizeof(uniform));
memcpy(_uniformBuffer.aligner().addTypedElement<nanovg_draw_data>(), &uniform, sizeof(uniform));
}
_uniformBuffer->submitData();
_uniformBuffer.submitData();
gr_update_buffer_data(_vertexBuffer, sizeof(NVGvertex) * _vertices.size(), _vertices.data());
for (auto& drawCall : _drawCalls) {
@@ -453,8 +453,6 @@ void NanoVGRenderer::renderFlush() {
}
}
_uniformBuffer->finished();
// Reset all data again
renderCancel();
}
@@ -661,10 +659,8 @@ void NanoVGRenderer::drawTriangles(const DrawCall& call) {
auto mat = _trianglesMaterial;
materialSetTexture(mat, call.image);
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::NanoVGData, _uniformBuffer.getAlignerElementOffset(call.uniformIndex),
sizeof(nanovg_draw_data), _uniformBuffer.bufferHandle());
gr_render_nanovg(&mat, PRIM_TYPE_TRIS, &_vertexLayout, call.triangleOffset, call.triangleCount, _vertexBuffer);
}
@@ -675,10 +671,8 @@ void NanoVGRenderer::drawFill(const DrawCall& call) {
auto mat = _fillShapeMaterial;
mat.set_texture_map(TM_BASE_TYPE, -1);
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::NanoVGData, _uniformBuffer.getAlignerElementOffset(call.uniformIndex),
sizeof(nanovg_draw_data), _uniformBuffer.bufferHandle());
auto pathOffset = call.pathOffset;
for (size_t i = 0; i < call.pathCount; ++i) {
@@ -693,9 +687,8 @@ void NanoVGRenderer::drawFill(const DrawCall& call) {
mat = _fillAntiAliasMaterial;
materialSetTexture(mat, call.image);
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex + 1),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
_uniformBuffer.getAlignerElementOffset(call.uniformIndex + 1), sizeof(nanovg_draw_data),
_uniformBuffer.bufferHandle());
// Draw fringes
for (size_t i = 0; i < call.pathCount; ++i) {
@@ -718,10 +711,8 @@ void NanoVGRenderer::drawConvexFill(const DrawCall& call) {
auto mat = _triangleFillMaterial;
materialSetTexture(mat, call.image);
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::NanoVGData, _uniformBuffer.getAlignerElementOffset(call.uniformIndex),
sizeof(nanovg_draw_data), _uniformBuffer.bufferHandle());
auto pathOffset = call.pathOffset;
for (size_t i = 0; i < call.pathCount; ++i) {
@@ -752,9 +743,8 @@ void NanoVGRenderer::drawStroke(const DrawCall& call) {
auto mat = _strokeFillMaterial;
materialSetTexture(mat, call.image);
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex + 1),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
_uniformBuffer.getAlignerElementOffset(call.uniformIndex + 1), sizeof(nanovg_draw_data),
_uniformBuffer.bufferHandle());
auto pathOffset = call.pathOffset;
@@ -769,10 +759,8 @@ void NanoVGRenderer::drawStroke(const DrawCall& call) {
}
// Draw anti-aliased pixels.
gr_bind_uniform_buffer(uniform_block_type::NanoVGData,
_uniformBuffer->aligner().getOffset(call.uniformIndex),
sizeof(nanovg_draw_data),
_uniformBuffer->bufferHandle());
gr_bind_uniform_buffer(uniform_block_type::NanoVGData, _uniformBuffer.getAlignerElementOffset(call.uniformIndex),
sizeof(nanovg_draw_data), _uniformBuffer.bufferHandle());
mat = _strokeAntiaiasMaterial;
materialSetTexture(mat, call.image);
for (size_t i = 0; i < call.pathCount; ++i) {
+1 -1
View File
@@ -71,7 +71,7 @@ class NanoVGRenderer {
int _vertexBuffer = -1;
vertex_layout _vertexLayout;
util::UniformBuffer* _uniformBuffer = nullptr;
util::UniformBuffer _uniformBuffer;
nanovg_material _trianglesMaterial;
nanovg_material _triangleFillMaterial;
+13 -10
View File
@@ -431,10 +431,8 @@ typedef signed int stbtt_int32;
typedef char stbtt__check_size32[sizeof(stbtt_int32) == 4 ? 1 : -1];
typedef char stbtt__check_size16[sizeof(stbtt_int16) == 2 ? 1 : -1];
#ifndef NDEBUG
// Function from NanoVGRenderer.cpp to provide log printing capabilities here.
extern void nvgOldCPrintf(const char *string, ...);
#endif
// Function from NanoVGRenderer.cpp to provide log printing capabilities here.
extern void nvgOldCPrintf(const char *string, ...);
// e.g. #define your own STBTT_ifloor/STBTT_iceil() to avoid math.h
#ifndef STBTT_ifloor
#include <math.h>
@@ -1505,11 +1503,9 @@ STBTT_DEF int stbtt_FindGlyphIndex(const stbtt_fontinfo *info, int unicode_codep
stbtt_uint16 offset, start;
stbtt_uint16 item = (stbtt_uint16)((search - endCount) >> 1);
#ifndef NDEBUG
if (unicode_codepoint > ttUSHORT(data + endCount + 2 * item)) {
nvgOldCPrintf("WARNING: A font character is probably missing. Unicode decimal index is %d.\n", unicode_codepoint);
}
#endif
if (unicode_codepoint > ttUSHORT(data + endCount + 2 * item)) {
nvgOldCPrintf("WARNING: A font character is probably missing. Unicode decimal index is %d.\n", unicode_codepoint);
}
STBTT_assert((unicode_codepoint <= ttUSHORT(data + endCount + 2 * item)) &&
" \
Looks like the font file you're using misses a character. Search the log for 'WARNING: A font character is probably missing.' \
@@ -2130,6 +2126,13 @@ static int stbtt__run_charstring(const stbtt_fontinfo *info, int glyph_index, st
#ifdef __GNUC__
#if __has_include(<features.h>)
#include <features.h>
#ifndef __GNUC_PREREQ
#if defined __GNUC__ && defined __GNUC_MINOR__
#define __GNUC_PREREQ(maj, min) ((__GNUC__ << 16) + __GNUC_MINOR__ >= ((maj) << 16) + (min))
#else
#define __GNUC_PREREQ(maj, min) 0
#endif
#endif
#if __GNUC_PREREQ(8, 0)
__attribute__((fallthrough));
#endif
@@ -4936,4 +4939,4 @@ AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
------------------------------------------------------------------------------
*/
*/
Loaded 100 of 333 files, more files were not shown because too many files have changed in this diff. Show more