mirror of
https://github.com/scp-fs2open/fs2open.github.com.git
synced 2026-11-08 07:28:22 -10:00
Compare commits
301
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5b01036723 | ||
|
|
8a2641181f | ||
|
|
36e8c3b623 | ||
|
|
1c2a136ef7 | ||
|
|
72272cb8cf | ||
|
|
4062f59128 | ||
|
|
24ab091671 | ||
|
|
7cd17205b5 | ||
|
|
d58bd7db69 | ||
|
|
ce11936e56 | ||
|
|
feda97c148 | ||
|
|
a0e85e7ef5 | ||
|
|
6939403262 | ||
|
|
33e8703555 | ||
|
|
8a87d20415 | ||
|
|
b324d2892c | ||
|
|
54bd7e3963 | ||
|
|
b2230f723b | ||
|
|
f75dafde4a | ||
|
|
d70f92e782 | ||
|
|
d7e042b38a | ||
|
|
941a0c3c8a | ||
|
|
edc6b94f7f | ||
|
|
1182a485ac | ||
|
|
3cd2c40331 | ||
|
|
c13cb44df4 | ||
|
|
aede65107b | ||
|
|
197767ce94 | ||
|
|
7924c66d37 | ||
|
|
3106191cea | ||
|
|
8c4ec9b91c | ||
|
|
5bfcd1d063 | ||
|
|
923265988c | ||
|
|
c485ed8199 | ||
|
|
4353d4d47f | ||
|
|
da65a66932 | ||
|
|
7df8313b8b | ||
|
|
187affe004 | ||
|
|
f29cc2ef86 | ||
|
|
97e15ca135 | ||
|
|
868418c100 | ||
|
|
e413b10ce1 | ||
|
|
bdd740eabd | ||
|
|
d24e3c9295 | ||
|
|
13be144495 | ||
|
|
8857c4561a | ||
|
|
af4a2555db | ||
|
|
ae2c4ef098 | ||
|
|
6e509868d2 | ||
|
|
d0bc3cf91d | ||
|
|
10079c88cd | ||
|
|
3aacb6cb42 | ||
|
|
b434776d53 | ||
|
|
20925f23cc | ||
|
|
64a9e3d03a | ||
|
|
fe01372f46 | ||
|
|
7134e22322 | ||
|
|
fac618c7f0 | ||
|
|
b333104f45 | ||
|
|
c0401c24e5 | ||
|
|
2ded9aa35d | ||
|
|
ad54f588bb | ||
|
|
a64ebca805 | ||
|
|
69781cec25 | ||
|
|
137457e570 | ||
|
|
b7f3ba3660 | ||
|
|
bf6cfe61d7 | ||
|
|
990838051a | ||
|
|
597104c479 | ||
|
|
2ee5d21a10 | ||
|
|
8c1d3492eb | ||
|
|
ba5fcb971a | ||
|
|
5359b12b4f | ||
|
|
0fb7345617 | ||
|
|
a34ca578ba | ||
|
|
7f03ac31ae | ||
|
|
25b396f6a0 | ||
|
|
c6e2f94d0b | ||
|
|
9de8d45f19 | ||
|
|
7f5168e9d6 | ||
|
|
490c5d8357 | ||
|
|
011ca4bb85 | ||
|
|
a4f499ce8c | ||
|
|
5578588894 | ||
|
|
dbee42bdec | ||
|
|
783e4b5ab2 | ||
|
|
cea27244dc | ||
|
|
09084395a5 | ||
|
|
886b14e595 | ||
|
|
2fca5fd965 | ||
|
|
69cb4f0136 | ||
|
|
76d36b1c5f | ||
|
|
bf37a36e89 | ||
|
|
6750f0a4cc | ||
|
|
06a21a0f9b | ||
|
|
3d653bd770 | ||
|
|
db3d92732f | ||
|
|
4fbc0d02fa | ||
|
|
c6f75e7d14 | ||
|
|
8f4d2a27db | ||
|
|
c4bb136d80 | ||
|
|
ea2656e75f | ||
|
|
d70672d7bc | ||
|
|
ccc727a148 | ||
|
|
87ac2ca6a3 | ||
|
|
e8bd6b3929 | ||
|
|
4e7756d29f | ||
|
|
fd96dd287d | ||
|
|
dea5fd9f30 | ||
|
|
5ebf48b9b0 | ||
|
|
2dc2c0643f | ||
|
|
e761d8a8e9 | ||
|
|
36b97487c6 | ||
|
|
367825b1e0 | ||
|
|
8f5a364345 | ||
|
|
07a15286b4 | ||
|
|
8e4deb0454 | ||
|
|
aed44067df | ||
|
|
83844222c4 | ||
|
|
ba5233e33b | ||
|
|
b0bb660eb2 | ||
|
|
74f258a9b3 | ||
|
|
d7d3b8c8e2 | ||
|
|
90aeb3651c | ||
|
|
6ee7679dd6 | ||
|
|
5baae08bdf | ||
|
|
646fb64c2f | ||
|
|
7544f321d6 | ||
|
|
b2ff79fb38 | ||
|
|
94c1cf65b3 | ||
|
|
0ce2908ce6 | ||
|
|
32fbe572e4 | ||
|
|
fb0ff8f1d0 | ||
|
|
2cef1d4aa1 | ||
|
|
9dfb8faea3 | ||
|
|
9651e7dca6 | ||
|
|
51557d3aa3 | ||
|
|
521a9b9461 | ||
|
|
130057c64a | ||
|
|
f63e18957b | ||
|
|
df0be20d22 | ||
|
|
cee37e7a2f | ||
|
|
90e16ffed2 | ||
|
|
c2a52174ba | ||
|
|
e389f7669d | ||
|
|
20681f1550 | ||
|
|
be8ea029da | ||
|
|
3dbcebb56e | ||
|
|
37453ae229 | ||
|
|
9d907c99fe | ||
|
|
490ef52b85 | ||
|
|
cf1cc5e862 | ||
|
|
fc0105141b | ||
|
|
9878b48dd3 | ||
|
|
af99fee8fc | ||
|
|
1cc09d5b8b | ||
|
|
d5c5cc6eb3 | ||
|
|
b5bb5097b9 | ||
|
|
f87e5bf318 | ||
|
|
48667f0cbd | ||
|
|
66637ef5cb | ||
|
|
3b2b58e2cc | ||
|
|
d5282ca697 | ||
|
|
6a099d2adc | ||
|
|
6aa1f4899f | ||
|
|
4ec7d21965 | ||
|
|
bd5a4c4348 | ||
|
|
9135a01b1d | ||
|
|
032579923e | ||
|
|
8c1e753991 | ||
|
|
6a4c74084e | ||
|
|
3799ce7d2f | ||
|
|
2e213d5c97 | ||
|
|
0c17177a1e | ||
|
|
93ced64c6f | ||
|
|
4020b7c594 | ||
|
|
13b26fd59f | ||
|
|
15bda8c4ac | ||
|
|
39ab45dc7c | ||
|
|
16a19783ae | ||
|
|
b1bc4ef44f | ||
|
|
08e664a93a | ||
|
|
aeee05c8dd | ||
|
|
1fb3a65a90 | ||
|
|
d53dc195ee | ||
|
|
5b8880daa7 | ||
|
|
b0fc9cb31a | ||
|
|
323354295f | ||
|
|
b1881a700d | ||
|
|
357cd76252 | ||
|
|
30e70db561 | ||
|
|
2c106f8c4b | ||
|
|
73bfb7a97e | ||
|
|
4bead819f9 | ||
|
|
268828f092 | ||
|
|
1614384a6a | ||
|
|
29b6af84cc | ||
|
|
cafee143c4 | ||
|
|
6e21c8a736 | ||
|
|
bb56958dfc | ||
|
|
120750ebd2 | ||
|
|
3430a1c438 | ||
|
|
1dc2e848cd | ||
|
|
305429bf8b | ||
|
|
ae149b6061 | ||
|
|
429858d02e | ||
|
|
1448277c29 | ||
|
|
b848823a2f | ||
|
|
61c533559b | ||
|
|
04b0f5bb75 | ||
|
|
fdbba84a5b | ||
|
|
e92121bed4 | ||
|
|
079ad97987 | ||
|
|
7ae276fe6a | ||
|
|
45ddc8ac44 | ||
|
|
6fa422c5e7 | ||
|
|
35c830062d | ||
|
|
243a5bb473 | ||
|
|
09abbe1789 | ||
|
|
ad52278a67 | ||
|
|
e0a9c88241 | ||
|
|
f45dcfc09a | ||
|
|
2036ebd3a0 | ||
|
|
469270d4b6 | ||
|
|
e59df5d83c | ||
|
|
880e03e5d1 | ||
|
|
c1196f8286 | ||
|
|
40cd9e4c07 | ||
|
|
a90e480b61 | ||
|
|
142ae846f4 | ||
|
|
7a827dcb0e | ||
|
|
619cb607d0 | ||
|
|
56c34eee6d | ||
|
|
379031534d | ||
|
|
64b08f51c0 | ||
|
|
adfa12a706 | ||
|
|
d71a589b0f | ||
|
|
5118d94d5d | ||
|
|
17179d5b0b | ||
|
|
bd3632d1bf | ||
|
|
eeed22b91a | ||
|
|
48873185ce | ||
|
|
e28ebc2a6c | ||
|
|
dcac9e7223 | ||
|
|
0b4ca71eba | ||
|
|
24c3c439d5 | ||
|
|
706973cb6b | ||
|
|
91a5bfa74a | ||
|
|
f7b0f93c00 | ||
|
|
2721c452c4 | ||
|
|
1030e29ef7 | ||
|
|
8f06e338a4 | ||
|
|
d1a6b48beb | ||
|
|
ce8fc0a373 | ||
|
|
991f131376 | ||
|
|
ed7917cb26 | ||
|
|
e6e6288423 | ||
|
|
48a6361586 | ||
|
|
8a2faa8b99 | ||
|
|
7d139f9e80 | ||
|
|
cf93aa43c5 | ||
|
|
89e3533106 | ||
|
|
a3f9febdc4 | ||
|
|
3c738312de | ||
|
|
363d6d3ba0 | ||
|
|
5578825bf3 | ||
|
|
9b5710e8c3 | ||
|
|
b527dd5449 | ||
|
|
175668e2bb | ||
|
|
cbf3052094 | ||
|
|
3507cf96d1 | ||
|
|
e624f6c1a8 | ||
|
|
371aad8f8c | ||
|
|
cb3fd31db4 | ||
|
|
e2e7eac0c6 | ||
|
|
80faaf88b0 | ||
|
|
fb0f7dd7de | ||
|
|
62aae9d793 | ||
|
|
15663a3551 | ||
|
|
6df837e7f3 | ||
|
|
512d08e443 | ||
|
|
504abeb305 | ||
|
|
2ae2f2910c | ||
|
|
3b4fbde8e6 | ||
|
|
2d01cd2366 | ||
|
|
2beb136ecf | ||
|
|
c728cc40b2 | ||
|
|
d13ddb387f | ||
|
|
666c177dec | ||
|
|
d5ba2369a2 | ||
|
|
7bf7a8fc66 | ||
|
|
5258066545 | ||
|
|
55c1c3ce9d | ||
|
|
2bddcf8344 | ||
|
|
758ca86f6f | ||
|
|
6406e2fbd4 | ||
|
|
18c2dbbde9 | ||
|
|
ef6c5d4da7 | ||
|
|
cb960a3416 | ||
|
|
194d944108 | ||
|
|
9ac97f2422 |
No files matched your search
@@ -0,0 +1,99 @@
|
||||
---
|
||||
Language: Cpp
|
||||
# BasedOnStyle: LLVM
|
||||
AccessModifierOffset: -2
|
||||
AlignAfterOpenBracket: Align
|
||||
AlignConsecutiveAssignments: true
|
||||
AlignConsecutiveDeclarations: false
|
||||
AlignEscapedNewlinesLeft: false
|
||||
AlignOperands: true
|
||||
AlignTrailingComments: true
|
||||
AllowAllParametersOfDeclarationOnNextLine: true
|
||||
AllowShortBlocksOnASingleLine: false
|
||||
AllowShortCaseLabelsOnASingleLine: false
|
||||
AllowShortFunctionsOnASingleLine: All
|
||||
AllowShortIfStatementsOnASingleLine: false
|
||||
AllowShortLoopsOnASingleLine: false
|
||||
AlwaysBreakAfterDefinitionReturnType: None
|
||||
AlwaysBreakAfterReturnType: None
|
||||
AlwaysBreakBeforeMultilineStrings: false
|
||||
AlwaysBreakTemplateDeclarations: true
|
||||
BinPackArguments: true
|
||||
BinPackParameters: true
|
||||
BraceWrapping:
|
||||
AfterClass: false
|
||||
AfterControlStatement: false
|
||||
AfterEnum: false
|
||||
AfterFunction: true
|
||||
AfterNamespace: false
|
||||
AfterObjCDeclaration: false
|
||||
AfterStruct: false
|
||||
AfterUnion: false
|
||||
BeforeCatch: false
|
||||
BeforeElse: false
|
||||
IndentBraces: false
|
||||
BreakBeforeBinaryOperators: None
|
||||
BreakBeforeBraces: Custom
|
||||
BreakBeforeTernaryOperators: true
|
||||
BreakConstructorInitializersBeforeComma: false
|
||||
BreakAfterJavaFieldAnnotations: false
|
||||
BreakStringLiterals: true
|
||||
ColumnLimit: 120
|
||||
CommentPragmas: '^ IWYU pragma:'
|
||||
ConstructorInitializerAllOnOneLineOrOnePerLine: false
|
||||
ConstructorInitializerIndentWidth: 4
|
||||
ContinuationIndentWidth: 4
|
||||
Cpp11BracedListStyle: true
|
||||
DerivePointerAlignment: false
|
||||
DisableFormat: false
|
||||
ForEachMacros: [ foreach, Q_FOREACH, BOOST_FOREACH ]
|
||||
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
|
||||
Priority: 1
|
||||
- Regex: '^".*\.(h)"$' # standard engine includes
|
||||
Priority: 2
|
||||
- Regex: '.*' # Catch all in case something is unhandled above
|
||||
Priority: 3
|
||||
IncludeIsMainRegex: '$'
|
||||
IndentCaseLabels: false
|
||||
IndentWidth: 4
|
||||
IndentWrappedFunctionNames: false
|
||||
JavaScriptQuotes: Leave
|
||||
JavaScriptWrapImports: true
|
||||
KeepEmptyLinesAtTheStartOfBlocks: true
|
||||
MacroBlockBegin: ''
|
||||
MacroBlockEnd: ''
|
||||
MaxEmptyLinesToKeep: 1
|
||||
NamespaceIndentation: None
|
||||
ObjCBlockIndentWidth: 2
|
||||
ObjCSpaceAfterProperty: false
|
||||
ObjCSpaceBeforeProtocolList: true
|
||||
PenaltyBreakBeforeFirstCallParameter: 19
|
||||
PenaltyBreakComment: 300
|
||||
PenaltyBreakFirstLessLess: 120
|
||||
PenaltyBreakString: 1000
|
||||
PenaltyExcessCharacter: 1000000
|
||||
PenaltyReturnTypeOnItsOwnLine: 60
|
||||
PointerAlignment: Left
|
||||
ReflowComments: true
|
||||
SortIncludes: true
|
||||
SpaceAfterCStyleCast: false
|
||||
SpaceAfterTemplateKeyword: true
|
||||
SpaceBeforeAssignmentOperators: true
|
||||
SpaceBeforeParens: ControlStatements
|
||||
SpaceInEmptyParentheses: false
|
||||
SpacesBeforeTrailingComments: 1
|
||||
SpacesInAngles: false
|
||||
SpacesInContainerLiterals: true
|
||||
SpacesInCStyleCastParentheses: false
|
||||
SpacesInParentheses: false
|
||||
SpacesInSquareBrackets: false
|
||||
Standard: Cpp11
|
||||
TabWidth: 4
|
||||
UseTab: ForIndentation
|
||||
...
|
||||
|
||||
+11
-15
@@ -1,27 +1,23 @@
|
||||
---
|
||||
Checks: "-*,\
|
||||
modernize-use-override,\
|
||||
modernize-*,\
|
||||
-modernize-raw-string-literal,\
|
||||
-modernize-use-using,\
|
||||
-modernize-make-unique,\
|
||||
performance-*,\
|
||||
-performance-type-promotion-in-math-fn,\
|
||||
misc-assert-side-effect,\
|
||||
misc-bool-pointer-implicit-conversion,\
|
||||
misc-definitions-in-headers,\
|
||||
misc-fold-init-type,\
|
||||
misc-forward-declaration-namespace,\
|
||||
misc-inaccurate-erase,\
|
||||
misc-inefficient-algorithm,\
|
||||
misc-macro-repeated-side-effects,\
|
||||
misc-misplaced-const,\
|
||||
misc-move-forwarding-reference,\
|
||||
misc-multiple-statement-macro,\
|
||||
misc-new-delete-overloads,\
|
||||
misc-noexcept-move-constructor,\
|
||||
misc-*,\
|
||||
-misc-macro-parentheses,\
|
||||
-misc-misplaced-widening-cast,\
|
||||
-misc-static-assert,\
|
||||
"
|
||||
WarningsAsErrors: ''
|
||||
HeaderFilterRegex: '.*'
|
||||
HeaderFilterRegex: 'code/.*$|freespace2/.*$|qtfred/.*$|test/src/.*$|build/.*$'
|
||||
AnalyzeTemporaryDtors: false
|
||||
CheckOptions:
|
||||
- key: 'misc-assert-side-effect.AssertMacros'
|
||||
value: 'assert,Assert,Assertion'
|
||||
- key: 'modernize-use-emplace.ContainersWithPushBack'
|
||||
value: 'std::vector;std::deque;std::list;SCP_vector;SCP_deque;SCP_list'
|
||||
...
|
||||
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
|
||||
build:
|
||||
image: teaci/msys$$arch
|
||||
pull: true
|
||||
shell: mingw$$arch
|
||||
commands:
|
||||
- git submodule update --init --recursive
|
||||
- if [ $$arch = 32 ]; then target=i686; fi
|
||||
- if [ $$arch = 64 ]; then target=x86_64; fi
|
||||
- pacman -S --needed --noconfirm --noprogressbar mingw-w64-${target}-pkg-config mingw-w64-${target}-cmake
|
||||
- mkdir build && cd build
|
||||
- cmake -G"Unix Makefiles" -DCMAKE_BUILD_TYPE=$$CONFIGURATION -DFSO_USE_SPEECH=OFF -DFSO_USE_VOICEREC=OFF -DFSO_FATAL_WARNINGS=ON -DFSO_BUILD_FRED2=OFF ..
|
||||
- make -j$(nproc) all
|
||||
|
||||
matrix:
|
||||
arch:
|
||||
- 64
|
||||
- 32
|
||||
CONFIGURATION:
|
||||
- Debug
|
||||
- Release
|
||||
+10
-8
@@ -3,7 +3,7 @@ sudo: required
|
||||
dist: trusty
|
||||
cache:
|
||||
directories:
|
||||
- $HOME/cmake-3.6
|
||||
- $HOME/cmake-3.8
|
||||
- $HOME/.ccache
|
||||
addons:
|
||||
apt:
|
||||
@@ -76,17 +76,17 @@ matrix:
|
||||
- *global_deps
|
||||
- g++-5
|
||||
- os: linux
|
||||
env: CONFIGURATION="Debug" CC=gcc-7 CXX=g++-7
|
||||
env: CONFIGURATION="Debug" CC=gcc-8 CXX=g++-8
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt571-trusty'
|
||||
packages:
|
||||
- g++-7
|
||||
- g++-8
|
||||
- *global_deps
|
||||
- os: linux
|
||||
env: CONFIGURATION="Debug" CC=clang-4.0 CXX=clang++-4.0 CMAKE_OPTIONS="-DENABLE_CLANG_TIDY=ON -DCLANG_TIDY_EXE=/usr/bin/clang-tidy-4.0"
|
||||
env: CONFIGURATION="Debug" CC=clang-4.0 CXX=clang++-4.0 CMAKE_OPTIONS="-DCMAKE_EXPORT_COMPILE_COMMANDS=ON"
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
@@ -98,6 +98,9 @@ matrix:
|
||||
- clang-4.0
|
||||
- clang-tidy-4.0
|
||||
- libc++-dev
|
||||
script:
|
||||
- ./ci/travis/script.sh
|
||||
- ./ci/travis/clang_tidy.sh
|
||||
- os: osx
|
||||
env: CONFIGURATION="Debug"
|
||||
|
||||
@@ -112,17 +115,17 @@ matrix:
|
||||
- *global_deps
|
||||
- g++-5
|
||||
- os: linux
|
||||
env: CONFIGURATION="Release" CC=gcc-7 CXX=g++-7
|
||||
env: CONFIGURATION="Release" CC=gcc-8 CXX=g++-8
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
- sourceline: 'ppa:beineri/opt-qt571-trusty'
|
||||
packages:
|
||||
- g++-7
|
||||
- g++-8
|
||||
- *global_deps
|
||||
- os: linux
|
||||
env: CONFIGURATION="Release" CC=clang-4.0 CXX=clang++-4.0 CMAKE_OPTIONS="-DENABLE_CLANG_TIDY=ON -DCLANG_TIDY_EXE=/usr/bin/clang-tidy-4.0"
|
||||
env: CONFIGURATION="Release" CC=clang-4.0 CXX=clang++-4.0
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
@@ -132,7 +135,6 @@ matrix:
|
||||
packages:
|
||||
- *global_deps
|
||||
- clang-4.0
|
||||
- clang-tidy-4.0
|
||||
- libc++-dev
|
||||
- os: osx
|
||||
env: CONFIGURATION="Release"
|
||||
|
||||
@@ -116,6 +116,8 @@ SET(FSO_RUN_ARGUMENTS "" CACHE STRING "Additional arguments passed to a generate
|
||||
|
||||
option(FSO_INSTALL_DEBUG_FILES "Install some debug files (currently only PDB files on windows)" OFF)
|
||||
|
||||
option(ENABLE_COTIRE "Enable cotire for faster compilation. Enabled by default." ON)
|
||||
|
||||
MARK_AS_ADVANCED(FORCE FSO_CMAKE_DEBUG)
|
||||
MARK_AS_ADVANCED(FORCE FSO_BUILD_INCLUDED_LIBS)
|
||||
MARK_AS_ADVANCED(FORCE FSO_USE_OPENALSOFT)
|
||||
@@ -123,6 +125,7 @@ MARK_AS_ADVANCED(FORCE FSO_USE_LUAJIT)
|
||||
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)
|
||||
|
||||
# Include cotire file from https://github.com/sakra/cotire/
|
||||
include(cotire)
|
||||
@@ -188,6 +191,7 @@ include(doxygen)
|
||||
IF (WIN32)
|
||||
message(STATUS "Using text to speech: ${FSO_USE_SPEECH}")
|
||||
message(STATUS "Using voice recogition: ${FSO_USE_VOICEREC}")
|
||||
message(STATUS "Building FRED2: ${FSO_BUILD_FRED2}")
|
||||
elseif(UNIX)
|
||||
message(STATUS "Building AppImage: ${FSO_BUILD_APPIMAGE}")
|
||||
ENDIF()
|
||||
|
||||
+5
-4
@@ -1,4 +1,5 @@
|
||||
version: 1.0.0.{build}
|
||||
image: Visual Studio 2015
|
||||
configuration:
|
||||
- Debug
|
||||
- Release
|
||||
@@ -6,13 +7,13 @@ clone_depth: 10
|
||||
environment:
|
||||
matrix:
|
||||
- BuildID: 0
|
||||
CMAKE_GENERATOR: Visual Studio 12 2013
|
||||
PlatformToolset: v120_xp
|
||||
QT_DIR: C:\Qt\5.7\msvc2013
|
||||
CMAKE_GENERATOR: Visual Studio 14 2015
|
||||
PlatformToolset: v140_xp
|
||||
QT_DIR: C:\Qt\5.9.5\msvc2015
|
||||
- BuildID: 1
|
||||
CMAKE_GENERATOR: Visual Studio 14 2015 Win64
|
||||
PlatformToolset: v140_xp
|
||||
QT_DIR: C:\Qt\5.7\msvc2015_64
|
||||
QT_DIR: C:\Qt\5.9.5\msvc2015_64
|
||||
before_build:
|
||||
- git submodule update --init --recursive
|
||||
build_script:
|
||||
|
||||
@@ -14,7 +14,7 @@ $NightlyConfigurations = @(
|
||||
PackageType="Win64";
|
||||
Toolset="v140_xp";
|
||||
SimdType="SSE2";
|
||||
QtDir="C:\Qt\5.7\msvc2015_64";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015_64";
|
||||
SourcePackage=$false;
|
||||
},
|
||||
[BuildConfig]@{
|
||||
@@ -22,7 +22,7 @@ $NightlyConfigurations = @(
|
||||
PackageType="Win32";
|
||||
Toolset="v140_xp";
|
||||
SimdType="SSE2";
|
||||
QtDir="C:\Qt\5.7\msvc2015";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015";
|
||||
SourcePackage=$false;
|
||||
}
|
||||
)
|
||||
@@ -32,7 +32,7 @@ $ReleaseConfigurations = @(
|
||||
PackageType="Win32";
|
||||
Toolset="v140_xp";
|
||||
SimdType="SSE2";
|
||||
QtDir="C:\Qt\5.7\msvc2015";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015";
|
||||
SourcePackage=$true;
|
||||
}
|
||||
[BuildConfig]@{
|
||||
@@ -40,7 +40,7 @@ $ReleaseConfigurations = @(
|
||||
PackageType="Win32-AVX";
|
||||
Toolset="v140_xp";
|
||||
SimdType="AVX";
|
||||
QtDir="C:\Qt\5.7\msvc2015";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015";
|
||||
SourcePackage=$false;
|
||||
}
|
||||
[BuildConfig]@{
|
||||
@@ -48,7 +48,7 @@ $ReleaseConfigurations = @(
|
||||
PackageType="Win64";
|
||||
Toolset="v140_xp";
|
||||
SimdType="SSE2";
|
||||
QtDir="C:\Qt\5.7\msvc2015_64";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015_64";
|
||||
SourcePackage=$false;
|
||||
}
|
||||
[BuildConfig]@{
|
||||
@@ -56,7 +56,7 @@ $ReleaseConfigurations = @(
|
||||
PackageType="Win64-AVX";
|
||||
Toolset="v140_xp";
|
||||
SimdType="AVX";
|
||||
QtDir="C:\Qt\5.7\msvc2015_64";
|
||||
QtDir="C:\Qt\5.9.5\msvc2015_64";
|
||||
SourcePackage=$false;
|
||||
}
|
||||
)
|
||||
@@ -148,7 +148,7 @@ if ($DeployBuild) {
|
||||
Push-AppveyorArtifact "$($PackageName)-builds-$($buildConfig.PackageType).zip"
|
||||
} else {
|
||||
cmake -DFSO_USE_SPEECH="ON" -DFSO_FATAL_WARNINGS="ON" -DFSO_USE_VOICEREC="ON" -DFSO_BUILD_TESTS="ON" -DMSVC_SIMD_INSTRUCTIONS=SSE2 `
|
||||
-DFSO_BUILD_QTFRED=ON -DQT5_INSTALL_ROOT="$env:QT_DIR" -DFSO_BUILD_FRED2="OFF" `
|
||||
-DFSO_BUILD_QTFRED=ON -DQT5_INSTALL_ROOT="$env:QT_DIR" -DFSO_BUILD_FRED2="ON" `
|
||||
-G "$Env:CMAKE_GENERATOR" -T "$Env:PlatformToolset" ..
|
||||
|
||||
cmake --build . --config "$Env:CONFIGURATION" -- /verbosity:minimal
|
||||
|
||||
Executable
+141
@@ -0,0 +1,141 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
#===- clang-tidy-diff.py - ClangTidy Diff Checker ------------*- python -*--===#
|
||||
#
|
||||
# The LLVM Compiler Infrastructure
|
||||
#
|
||||
# This file is distributed under the University of Illinois Open Source
|
||||
# License. See LICENSE.TXT for details.
|
||||
#
|
||||
#===------------------------------------------------------------------------===#
|
||||
|
||||
r"""
|
||||
ClangTidy Diff Checker
|
||||
======================
|
||||
|
||||
This script reads input from a unified diff, runs clang-tidy on all changed
|
||||
files and outputs clang-tidy warnings in changed lines only. This is useful to
|
||||
detect clang-tidy regressions in the lines touched by a specific patch.
|
||||
Example usage for git/svn users:
|
||||
|
||||
git diff -U0 HEAD^ | clang-tidy-diff.py -p1
|
||||
svn diff --diff-cmd=diff -x-U0 | \
|
||||
clang-tidy-diff.py -fix -checks=-*,modernize-use-override
|
||||
|
||||
"""
|
||||
|
||||
import argparse
|
||||
import json
|
||||
import re
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description=
|
||||
'Run clang-tidy against changed files, and '
|
||||
'output diagnostics only for modified '
|
||||
'lines.')
|
||||
parser.add_argument('-clang-tidy-binary', metavar='PATH',
|
||||
default='clang-tidy',
|
||||
help='path to clang-tidy binary')
|
||||
parser.add_argument('-p', metavar='NUM', default=0,
|
||||
help='strip the smallest prefix containing P slashes')
|
||||
parser.add_argument('-regex', metavar='PATTERN', default=None,
|
||||
help='custom pattern selecting file paths to check '
|
||||
'(case sensitive, overrides -iregex)')
|
||||
parser.add_argument('-iregex', metavar='PATTERN', default=
|
||||
r'.*\.(cpp|cc|c\+\+|cxx|c|cl|h|hpp|m|mm|inc)',
|
||||
help='custom pattern selecting file paths to check '
|
||||
'(case insensitive, overridden by -regex)')
|
||||
|
||||
parser.add_argument('-fix', action='store_true', default=False,
|
||||
help='apply suggested fixes')
|
||||
parser.add_argument('-checks',
|
||||
help='checks filter, when not specified, use clang-tidy '
|
||||
'default',
|
||||
default='')
|
||||
parser.add_argument('-path', dest='build_path',
|
||||
help='Path used to read a compile command database.')
|
||||
parser.add_argument('-extra-arg', dest='extra_arg',
|
||||
action='append', default=[],
|
||||
help='Additional argument to append to the compiler '
|
||||
'command line.')
|
||||
parser.add_argument('-extra-arg-before', dest='extra_arg_before',
|
||||
action='append', default=[],
|
||||
help='Additional argument to prepend to the compiler '
|
||||
'command line.')
|
||||
parser.add_argument('-quiet', action='store_true', default=False,
|
||||
help='Run clang-tidy in quiet mode')
|
||||
clang_tidy_args = []
|
||||
argv = sys.argv[1:]
|
||||
if '--' in argv:
|
||||
clang_tidy_args.extend(argv[argv.index('--'):])
|
||||
argv = argv[:argv.index('--')]
|
||||
|
||||
args = parser.parse_args(argv)
|
||||
|
||||
# Extract changed lines for each file.
|
||||
filename = None
|
||||
lines_by_file = {}
|
||||
for line in sys.stdin:
|
||||
match = re.search('^\+\+\+\ \"?(.*?/){%s}([^ \t\n\"]*)' % args.p, line)
|
||||
if match:
|
||||
filename = match.group(2)
|
||||
if filename == None:
|
||||
continue
|
||||
|
||||
if args.regex is not None:
|
||||
if not re.match('^%s$' % args.regex, filename):
|
||||
continue
|
||||
else:
|
||||
if not re.match('^%s$' % args.iregex, filename, re.IGNORECASE):
|
||||
continue
|
||||
|
||||
match = re.search('^@@.*\+(\d+)(,(\d+))?', line)
|
||||
if match:
|
||||
start_line = int(match.group(1))
|
||||
line_count = 1
|
||||
if match.group(3):
|
||||
line_count = int(match.group(3))
|
||||
if line_count == 0:
|
||||
continue
|
||||
end_line = start_line + line_count - 1;
|
||||
lines_by_file.setdefault(filename, []).append([start_line, end_line])
|
||||
|
||||
if len(lines_by_file) == 0:
|
||||
print("No relevant changes found.")
|
||||
sys.exit(0)
|
||||
|
||||
line_filter_json = json.dumps(
|
||||
[{"name" : name, "lines" : lines_by_file[name]} for name in lines_by_file],
|
||||
separators = (',', ':'))
|
||||
|
||||
quote = "";
|
||||
if sys.platform == 'win32':
|
||||
line_filter_json=re.sub(r'"', r'"""', line_filter_json)
|
||||
else:
|
||||
quote = "'";
|
||||
|
||||
# Run clang-tidy on files containing changes.
|
||||
command = [args.clang_tidy_binary]
|
||||
command.append('-line-filter=' + quote + line_filter_json + quote)
|
||||
if args.fix:
|
||||
command.append('-fix')
|
||||
if args.checks != '':
|
||||
command.append('-checks=' + quote + args.checks + quote)
|
||||
if args.quiet:
|
||||
command.append('-quiet')
|
||||
if args.build_path is not None:
|
||||
command.append('-p=%s' % args.build_path)
|
||||
command.extend(lines_by_file.keys())
|
||||
for arg in args.extra_arg:
|
||||
command.append('-extra-arg=%s' % arg)
|
||||
for arg in args.extra_arg_before:
|
||||
command.append('-extra-arg-before=%s' % arg)
|
||||
command.extend(clang_tidy_args)
|
||||
|
||||
sys.exit(subprocess.call(' '.join(command), shell=True))
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
Executable
+24
@@ -0,0 +1,24 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
set -e
|
||||
|
||||
if ! git rev-list $TRAVIS_COMMIT_RANGE 2>1 >/dev/null; then
|
||||
echo "\$TRAVIS_COMMIT_RANGE ($TRAVIS_COMMIT_RANGE) is not valid for this build (probably caused by a rebase)."
|
||||
exit 0
|
||||
fi
|
||||
|
||||
cd "$TRAVIS_BUILD_DIR"
|
||||
|
||||
echo "Running clang-tidy on changed files"
|
||||
git diff -U0 --no-color $TRAVIS_COMMIT_RANGE | \
|
||||
$TRAVIS_BUILD_DIR/ci/travis/clang-tidy-diff.py -path "$TRAVIS_BUILD_DIR/build" -p1 \
|
||||
-regex 'code/.*$|freespace2/.*$|qtfred/.*$|test/src/.*$|build/.*$|tools/.*' \
|
||||
-clang-tidy-binary /usr/bin/clang-tidy-4.0 2>/dev/null | \
|
||||
tee clang-tidy-output.txt
|
||||
|
||||
if [[ -n $(grep "warning: " clang-tidy-output.txt) ]] || [[ -n $(grep "error: " clang-tidy-output.txt) ]]; then
|
||||
echo "Errors or warnings were detected in the clang-tidy output!"
|
||||
exit 1
|
||||
else
|
||||
echo -e "\033[1;32m\xE2\x9C\x93 passed:\033[0m clang-tidy test succeeded";
|
||||
fi
|
||||
@@ -4,14 +4,14 @@ set -ex
|
||||
|
||||
FILENAME=
|
||||
if [ "$TRAVIS_OS_NAME" = "linux" ]; then
|
||||
if [ ! -d "$HOME/cmake-3.6/bin" ]; then
|
||||
if [ ! -d "$HOME/cmake-3.8/bin" ]; then
|
||||
# If the cache does not currently contain CMake then download and install it
|
||||
mkdir -p $HOME/cmake-3.6/
|
||||
mkdir -p $HOME/cmake-3.8/
|
||||
|
||||
wget -O /tmp/cmake.tar.gz --no-check-certificate https://cmake.org/files/v3.6/cmake-3.6.0-Linux-x86_64.tar.gz
|
||||
tar -xzf /tmp/cmake.tar.gz -C $HOME/cmake-3.6/ --strip-components=1
|
||||
wget -O /tmp/cmake.tar.gz --no-check-certificate https://cmake.org/files/v3.8/cmake-3.8.2-Linux-x86_64.tar.gz
|
||||
tar -xzf /tmp/cmake.tar.gz -C $HOME/cmake-3.8/ --strip-components=1
|
||||
fi
|
||||
export PATH=$HOME/cmake-3.6/bin:$PATH
|
||||
export PATH=$HOME/cmake-3.8/bin:$PATH
|
||||
|
||||
cd $HOME
|
||||
|
||||
|
||||
+7
-2
@@ -7,8 +7,13 @@ cd build
|
||||
if [ "$TRAVIS_OS_NAME" = "linux" ]; then
|
||||
ninja -k 20 all
|
||||
|
||||
valgrind --leak-check=full --error-exitcode=1 --gen-suppressions=all \
|
||||
--suppressions="$TRAVIS_BUILD_DIR/ci/travis/valgrind.supp" ./bin/unittests --gtest_shuffle
|
||||
|
||||
if [ "$CONFIGURATION" = "Debug" ]; then
|
||||
valgrind --leak-check=full --error-exitcode=1 --gen-suppressions=all \
|
||||
--suppressions="$TRAVIS_BUILD_DIR/ci/travis/valgrind.supp" ./bin/unittests --gtest_shuffle
|
||||
else
|
||||
./bin/unittests --gtest_shuffle
|
||||
fi
|
||||
elif [ "$TRAVIS_OS_NAME" = "osx" ]; then
|
||||
cmake --build . --config "$CONFIGURATION" | tee build.log | xcpretty
|
||||
XCODE_RET=${PIPESTATUS[0]}
|
||||
|
||||
@@ -25,4 +25,12 @@
|
||||
fun:_dl_init
|
||||
fun:dl_open_worker
|
||||
fun:_dl_catch_error
|
||||
}
|
||||
}
|
||||
{
|
||||
CLang Lua unitialized value error
|
||||
Memcheck:Cond
|
||||
...
|
||||
fun:luaH_get
|
||||
fun:lua_rawget
|
||||
fun:_ZN12_GLOBAL__N_117ade_index_handlerEP9lua_State
|
||||
}
|
||||
@@ -41,5 +41,8 @@ CHECK_FUNCTION_EXISTS(strlwr HAVE_STRLWR)
|
||||
|
||||
CHECK_INCLUDE_FILE("strings.h" HAVE_STRINGS_H)
|
||||
|
||||
check_symbol_exists(snprintf "stdio.h" HAVE_SNPRINTF)
|
||||
check_symbol_exists(_snprintf "stdio.h" HAVE__SNPRINTF)
|
||||
|
||||
set(PLATFORM_CHECK_HEADER "${GENERATED_SOURCE_DIR}/platformChecks.h")
|
||||
CONFIGURE_FILE(${CMAKE_CURRENT_LIST_DIR}/platformChecks.h.in "${PLATFORM_CHECK_HEADER}")
|
||||
@@ -25,4 +25,7 @@
|
||||
#cmakedefine01 HAVE_CHAR32_T
|
||||
#cmakedefine01 HAVE_UNICODE_CHAR_LITERAL
|
||||
|
||||
#cmakedefine01 HAVE_SNPRINTF
|
||||
#cmakedefine01 HAVE__SNPRINTF
|
||||
|
||||
#endif // __PLATFORM_CHECKS_H__
|
||||
@@ -73,14 +73,12 @@ set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wreturn-type")
|
||||
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-char-subscripts")
|
||||
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-unused-parameter")
|
||||
|
||||
check_cxx_compiler_flag(-Wshift-negative-value SUPPORTS_SHIFT_NEGATIVE_VALUE)
|
||||
if(SUPPORTS_SHIFT_NEGATIVE_VALUE)
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-shift-negative-value")
|
||||
endif()
|
||||
|
||||
set(COMPILER_FLAGS_RELEASE "-O2 -Wno-unused-variable")
|
||||
set(COMPILER_FLAGS_RELEASE "-O2 -Wno-unused-variable -Wno-unused-parameter")
|
||||
|
||||
set(COMPILER_FLAGS_DEBUG "-O0 -g -Wshadow")
|
||||
|
||||
|
||||
@@ -85,9 +85,18 @@ set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wreturn-type")
|
||||
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-deprecated -Wno-char-subscripts")
|
||||
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-unused-parameter")
|
||||
# These two warnings cause a lot of false-positives in the FSO code base
|
||||
check_cxx_compiler_flag(-Wstringop-truncation SUPPORTS_STRINGOP_TRUNCATION)
|
||||
if(SUPPORTS_STRINGOP_TRUNCATION)
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-stringop-truncation")
|
||||
endif()
|
||||
|
||||
set(COMPILER_FLAGS_RELEASE "-O2 -Wno-unused-variable -Wno-unused-but-set-variable -Wno-array-bounds -Wno-empty-body -Wno-clobbered")
|
||||
check_cxx_compiler_flag(-Wstringop-overflow SUPPORTS_STRINGOP_OVERFLOW)
|
||||
if(SUPPORTS_STRINGOP_TRUNCATION)
|
||||
set(COMPILER_FLAGS "${COMPILER_FLAGS} -Wno-stringop-overflow")
|
||||
endif()
|
||||
|
||||
set(COMPILER_FLAGS_RELEASE "-O2 -Wno-unused-variable -Wno-unused-but-set-variable -Wno-array-bounds -Wno-empty-body -Wno-clobbered -Wno-unused-parameter")
|
||||
|
||||
set(COMPILER_FLAGS_DEBUG "-O0 -g -Wshadow")
|
||||
|
||||
@@ -105,6 +114,7 @@ set(CMAKE_EXE_LINKER_FLAGS "")
|
||||
|
||||
IF (MINGW)
|
||||
SET(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -static -static-libgcc -static-libstdc++ -Wl,--enable-auto-import")
|
||||
target_compile_definitions(compiler INTERFACE __USE_MINGW_ANSI_STDIO=1)
|
||||
ENDIF(MINGW)
|
||||
|
||||
if (SANITIZE_FLAGS)
|
||||
@@ -131,4 +141,4 @@ if (FSO_FATAL_WARNINGS)
|
||||
endif()
|
||||
|
||||
# Always define this to make sure that the fixed width format macros are available
|
||||
target_compile_definitions(compiler INTERFACE __STDC_FORMAT_MACROS)
|
||||
target_compile_definitions(compiler INTERFACE __STDC_FORMAT_MACROS=1)
|
||||
+15
-3
@@ -141,10 +141,12 @@ macro(set_if_not_defined VAR VALUE)
|
||||
endmacro(set_if_not_defined)
|
||||
|
||||
macro(configure_cotire target)
|
||||
# Disable unity build as it doesn't work well for us
|
||||
set_target_properties(${target} PROPERTIES COTIRE_ADD_UNITY_BUILD FALSE)
|
||||
if(ENABLE_COTIRE)
|
||||
# Disable unity build as it doesn't work well for us
|
||||
set_target_properties(${target} PROPERTIES COTIRE_ADD_UNITY_BUILD FALSE)
|
||||
|
||||
cotire(${target})
|
||||
cotire(${target})
|
||||
endif()
|
||||
endmacro(configure_cotire)
|
||||
|
||||
macro(add_target_copy_files)
|
||||
@@ -223,3 +225,13 @@ function(list_target_dependencies _target _out_var)
|
||||
list(REMOVE_DUPLICATES out_list)
|
||||
set(${_out_var} ${out_list} PARENT_SCOPE)
|
||||
endfunction(list_target_dependencies)
|
||||
|
||||
macro(add_file_folder FOLDER_NAME)
|
||||
string(MAKE_C_IDENTIFIER "${FOLDER_NAME}" VARIABLE_NAME)
|
||||
set(files_${VARIABLE_NAME} ${files_${VARIABLE_NAME}} ${ARGN})
|
||||
|
||||
string(REPLACE "/" "\\" FIXED_FOLDER_FILE "${FOLDER_NAME}")
|
||||
|
||||
source_group("${FIXED_FOLDER_FILE}" FILES ${ARGN})
|
||||
set(source_files ${source_files} ${ARGN})
|
||||
endmacro(add_file_folder)
|
||||
+18
-2
@@ -3,7 +3,7 @@ INCLUDE(source_groups.cmake)
|
||||
|
||||
INCLUDE(voice_rec.cmake)
|
||||
|
||||
ADD_LIBRARY(code STATIC ${file_root} ${VOICE_REC_FILES})
|
||||
ADD_LIBRARY(code STATIC ${source_files} ${VOICE_REC_FILES})
|
||||
|
||||
target_compile_features(code PUBLIC ${REQUIRED_CXX_FEATURES})
|
||||
|
||||
@@ -37,6 +37,8 @@ TARGET_LINK_LIBRARIES(code PUBLIC compiler)
|
||||
|
||||
target_link_libraries(code PUBLIC md5)
|
||||
|
||||
target_link_libraries(code PUBLIC discord-rpc)
|
||||
|
||||
enable_clang_tidy(code)
|
||||
|
||||
IF (FSO_USE_SPEECH)
|
||||
@@ -57,7 +59,21 @@ IF(FSO_BUILD_TOOLS)
|
||||
ADD_SUBDIRECTORY(cfileextractor)
|
||||
ENDIF(FSO_BUILD_TOOLS)
|
||||
|
||||
set_target_properties(code PROPERTIES COTIRE_CXX_PREFIX_HEADER_INIT "prefix_header.h")
|
||||
if (ENABLE_COTIRE)
|
||||
set_target_properties(code PROPERTIES COTIRE_CXX_PREFIX_HEADER_INIT "${CMAKE_CURRENT_SOURCE_DIR}/prefix_header.h")
|
||||
else()
|
||||
if("${CMAKE_CXX_COMPILER_ID}" STREQUAL "GNU")
|
||||
target_compile_options(code PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:-include${CMAKE_CURRENT_SOURCE_DIR}/prefix_header.h>")
|
||||
elseif("${CMAKE_CXX_COMPILER_ID}" STREQUAL "MSVC")
|
||||
target_compile_options(code PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:/FI ${CMAKE_CURRENT_SOURCE_DIR}/prefix_header.h>")
|
||||
elseif("${CMAKE_CXX_COMPILER_ID}" STREQUAL "Clang")
|
||||
target_compile_options(code PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:-include${CMAKE_CURRENT_SOURCE_DIR}/prefix_header.h>")
|
||||
elseif("${CMAKE_CXX_COMPILER_ID}" STREQUAL "AppleClang")
|
||||
target_compile_options(code PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:-include${CMAKE_CURRENT_SOURCE_DIR}/prefix_header.h>")
|
||||
ELSE()
|
||||
MESSAGE("Unknown compiler for global includes. This will probably break the build.")
|
||||
ENDIF()
|
||||
endif()
|
||||
|
||||
include(util)
|
||||
configure_cotire(code)
|
||||
|
||||
+4
-4
@@ -567,9 +567,9 @@ extern void ai_dock_with_object(object *docker, int docker_index, object *dockee
|
||||
extern void ai_stay_still(object *still_objp, vec3d *view_pos);
|
||||
extern void ai_do_default_behavior(object *obj);
|
||||
extern void ai_start_waypoints(object *objp, waypoint_list *wp_list, int wp_flags);
|
||||
extern void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hitpos, int shield_quadrant, vec3d *hit_normal);
|
||||
extern void ai_ship_destroy(int shipnum, Ship::Exit_Flags method);
|
||||
extern void ai_turn_towards_vector(vec3d *dest, object *objp, float frametime, float turn_time, vec3d *slide_vec, vec3d *rel_pos, float bank_override, int flags, vec3d *rvec = NULL, int sexp_flags = 0);
|
||||
extern void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hit_normal);
|
||||
extern void ai_ship_destroy(int shipnum);
|
||||
extern void ai_turn_towards_vector(vec3d *dest, object *objp, float turn_time, vec3d *slide_vec, vec3d *rel_pos, float bank_override, int flags, vec3d *rvec = nullptr, int sexp_flags = 0);
|
||||
extern void init_ai_object(int objnum);
|
||||
extern void ai_init(void); // Call this one to parse ai.tbl.
|
||||
extern void ai_level_init(void); // Call before each level to reset AI
|
||||
@@ -622,7 +622,7 @@ extern float ai_path();
|
||||
extern void evade_weapon();
|
||||
extern int might_collide_with_ship(object *obj1, object *obj2, float dot_to_enemy, float dist_to_enemy, float duration);
|
||||
extern int ai_fire_primary_weapon(object *objp); //changed to return weather it fired-Bobboau
|
||||
extern int ai_fire_secondary_weapon(object *objp, int priority1 = -1, int priority2 = -1);
|
||||
extern int ai_fire_secondary_weapon(object *objp);
|
||||
extern float ai_get_weapon_dist(ship_weapon *swp);
|
||||
extern void turn_towards_point(object *objp, vec3d *point, vec3d *slide_vec, float bank_override);
|
||||
extern int ai_maybe_fire_afterburner(object *objp, ai_info *aip);
|
||||
|
||||
@@ -110,6 +110,7 @@ namespace AI {
|
||||
Smart_subsystem_targeting_for_turrets,
|
||||
Strict_turred_tagged_only_targeting,
|
||||
Turrets_ignore_target_radius,
|
||||
Use_actual_primary_range,
|
||||
Use_additive_weapon_velocity,
|
||||
Use_newtonian_dampening,
|
||||
Use_only_single_fov_for_turrets,
|
||||
|
||||
@@ -458,6 +458,8 @@ void parse_ai_profiles_tbl(const char *filename)
|
||||
|
||||
set_flag(profile, "$ai can slow down when attacking big ships:", AI::Profile_Flags::Ai_can_slow_down_attacking_big_ships);
|
||||
|
||||
set_flag(profile, "$use actual primary range:", AI::Profile_Flags::Use_actual_primary_range);
|
||||
|
||||
profile->bay_arrive_speed_mult = 1.0f;
|
||||
profile->bay_depart_speed_mult = 1.0f;
|
||||
if (optional_string("$bay arrive speed multiplier:")) {
|
||||
|
||||
+18
-24
@@ -64,10 +64,11 @@ void ai_big_chase_attack(ai_info *aip, ship_info *sip, vec3d *enemy_pos, float d
|
||||
void ai_big_avoid_ship();
|
||||
int ai_big_maybe_follow_subsys_path(int do_dot_check=1);
|
||||
void ai_big_strafe_position();
|
||||
static int ai_big_strafe_maybe_retreat(const vec3d *target_pos);
|
||||
|
||||
extern int model_which_octant_distant_many( vec3d *pnt, int model_num,matrix *model_orient, vec3d * model_pos, polymodel **pm, int *octs);
|
||||
extern void compute_desired_rvec(vec3d *rvec, vec3d *goal_pos, vec3d *cur_pos);
|
||||
extern void big_ship_collide_recover_start(object *objp, object *big_objp, vec3d *collide_pos, vec3d *collision_normal);
|
||||
extern void big_ship_collide_recover_start(object *objp, object *big_objp, vec3d *collision_normal);
|
||||
|
||||
|
||||
// Called by ai_big_pick_attack_point.
|
||||
@@ -631,7 +632,7 @@ void ai_big_chase_attack(ai_info *aip, ship_info *sip, vec3d *enemy_pos, float d
|
||||
else
|
||||
rvec = NULL;
|
||||
|
||||
ai_turn_towards_vector(enemy_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, rel_pos, 0.0f, 0, rvec);
|
||||
ai_turn_towards_vector(enemy_pos, Pl_objp, sip->srotation_time, nullptr, rel_pos, 0.0f, 0, rvec);
|
||||
|
||||
// calc range of primary weapon
|
||||
weapon_travel_dist = ai_get_weapon_dist(&Ships[Pl_objp->instance].weapons);
|
||||
@@ -707,14 +708,14 @@ extern float set_secondary_fire_delay(ai_info *aip, ship *shipp, weapon_info *sw
|
||||
extern void ai_choose_secondary_weapon(object *objp, ai_info *aip, object *en_objp);
|
||||
extern int maybe_avoid_big_ship(object *objp, object *ignore_objp, ai_info *aip, vec3d *goal_point, float delta_time);
|
||||
|
||||
extern void maybe_cheat_fire_synaptic(object *objp, ai_info *aip);
|
||||
extern void maybe_cheat_fire_synaptic(object *objp);
|
||||
|
||||
// Determine if Pl_objp should fire weapons at current target, based on input parameters
|
||||
//
|
||||
// dist_to_enemy => distance (in m) to attack point on current target
|
||||
// dot_to_enemy => dot product between fvec of Pl_objp and vector from Pl_objp to attack point
|
||||
//
|
||||
void ai_big_maybe_fire_weapons(float dist_to_enemy, float dot_to_enemy, vec3d *firing_pos, vec3d *enemy_pos, vec3d *enemy_vel)
|
||||
static void ai_big_maybe_fire_weapons(float dist_to_enemy, float dot_to_enemy)
|
||||
{
|
||||
ai_info *aip;
|
||||
ship_weapon *swp;
|
||||
@@ -845,8 +846,6 @@ void ai_big_switch_to_chase_mode(ai_info *aip)
|
||||
aip->submode_start_time = Missiontime;
|
||||
}
|
||||
|
||||
extern int ai_big_strafe_maybe_retreat(float dist, vec3d *target_pos);
|
||||
|
||||
// Make object Pl_objp chase object En_objp, which is a big ship, not a small ship.
|
||||
void ai_big_chase()
|
||||
{
|
||||
@@ -859,7 +858,7 @@ void ai_big_chase()
|
||||
|
||||
Assert(aip->mode == AIM_CHASE);
|
||||
|
||||
maybe_cheat_fire_synaptic(Pl_objp, aip);
|
||||
maybe_cheat_fire_synaptic(Pl_objp);
|
||||
|
||||
ai_set_positions(Pl_objp, En_objp, aip, &player_pos, &enemy_pos);
|
||||
|
||||
@@ -882,7 +881,7 @@ void ai_big_chase()
|
||||
dot_to_enemy = vm_vec_dot(&vec_to_enemy, &Pl_objp->orient.vec.fvec);
|
||||
|
||||
if (aip->ai_flags[AI::AI_Flags::Target_collision]) {
|
||||
if ( ai_big_strafe_maybe_retreat(dist_to_enemy, &enemy_pos) ) {
|
||||
if ( ai_big_strafe_maybe_retreat(&enemy_pos) ) {
|
||||
aip->mode = AIM_STRAFE;
|
||||
aip->submode_parm0 = Missiontime; // use parm0 as time strafe mode entered (i.e. MODE start time)
|
||||
aip->submode = AIS_STRAFE_AVOID;
|
||||
@@ -1045,7 +1044,7 @@ void ai_big_chase()
|
||||
if ((dist_normal_to_enemy < ATTACK_COLLIDE_AVOID_DIST + speed_dist) || (time_to_enemy < ATTACK_COLLIDE_AVOID_TIME) ) {
|
||||
// get away, simulate crsh recovery (don't use avoid)
|
||||
// accelerate_ship(aip, -1.0f);
|
||||
big_ship_collide_recover_start(Pl_objp, En_objp, &Pl_objp->pos, NULL);
|
||||
big_ship_collide_recover_start(Pl_objp, En_objp, nullptr);
|
||||
// aip->submode = SM_AVOID;
|
||||
// aip->submode_start_time = Missiontime;
|
||||
} else if ((dist_normal_to_enemy < ATTACK_COLLIDE_SLOW_DIST) || (time_to_enemy < ATTACK_COLLIDE_SLOW_TIME) ) {
|
||||
@@ -1144,7 +1143,7 @@ void ai_big_chase()
|
||||
// TODO: investigate why ships fire (and aren't close to hitting ship) when following a path near
|
||||
// a big ship
|
||||
if (aip->mode != AIM_EVADE && aip->path_start == -1 ) {
|
||||
ai_big_maybe_fire_weapons(dist_to_enemy, dot_to_enemy, &player_pos, &predicted_enemy_pos, &En_objp->phys_info.vel);
|
||||
ai_big_maybe_fire_weapons(dist_to_enemy, dot_to_enemy);
|
||||
} else {
|
||||
if (flFrametime < 1.0f)
|
||||
aip->time_enemy_in_range *= (1.0f - flFrametime);
|
||||
@@ -1153,11 +1152,6 @@ void ai_big_chase()
|
||||
}
|
||||
}
|
||||
|
||||
void ai_big_ship(object *objp)
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
|
||||
// all three parms are output parameters
|
||||
// Enemy object is En_objp
|
||||
// pos => world pos of attack point
|
||||
@@ -1228,7 +1222,7 @@ void ai_big_attack_get_data(vec3d *enemy_pos, float *dist_to_enemy, float *dot_t
|
||||
|
||||
// check to see if Pl_objp has gotten too close to attacking point.. if so, break off by entering
|
||||
// AIS_STRAFE_RETREAT
|
||||
int ai_big_strafe_maybe_retreat(float dist, vec3d *target_pos)
|
||||
static int ai_big_strafe_maybe_retreat(const vec3d *target_pos)
|
||||
{
|
||||
ai_info *aip;
|
||||
aip = &Ai_info[Ships[Pl_objp->instance].ai_index];
|
||||
@@ -1258,7 +1252,7 @@ int ai_big_strafe_maybe_retreat(float dist, vec3d *target_pos)
|
||||
if (aip->ai_flags[AI::AI_Flags::Target_collision]) {
|
||||
// use standard collision resolution
|
||||
aip->ai_flags.remove(AI::AI_Flags::Target_collision);
|
||||
big_ship_collide_recover_start(Pl_objp, En_objp, &Pl_objp->pos, NULL);
|
||||
big_ship_collide_recover_start(Pl_objp, En_objp, nullptr);
|
||||
} else {
|
||||
// too close for comfort so fly to box point + 300
|
||||
aip->submode = AIS_STRAFE_RETREAT1;
|
||||
@@ -1298,12 +1292,12 @@ void ai_big_strafe_attack()
|
||||
}
|
||||
|
||||
ai_big_attack_get_data(&target_pos, &target_dist, &target_dot);
|
||||
if ( ai_big_strafe_maybe_retreat(target_dist, &target_pos) )
|
||||
if ( ai_big_strafe_maybe_retreat(&target_pos) )
|
||||
return;
|
||||
|
||||
if (aip->ai_flags[AI::AI_Flags::Kamikaze]) {
|
||||
if (target_dist < 1200.0f) {
|
||||
ai_turn_towards_vector(&target_pos, Pl_objp, flFrametime, Ship_info[Ships[Pl_objp->instance].ship_info_index].srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&target_pos, Pl_objp, Ship_info[Ships[Pl_objp->instance].ship_info_index].srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
accelerate_ship(aip, 1.0f);
|
||||
if ((target_dist < 400.0f) && ai_maybe_fire_afterburner(Pl_objp, aip)) {
|
||||
afterburners_start(Pl_objp);
|
||||
@@ -1347,7 +1341,7 @@ void ai_big_strafe_attack()
|
||||
}
|
||||
|
||||
// maybe fire weapons at target
|
||||
ai_big_maybe_fire_weapons(target_dist, target_dot, &Pl_objp->pos, &En_objp->pos, &En_objp->phys_info.vel);
|
||||
ai_big_maybe_fire_weapons(target_dist, target_dot);
|
||||
turn_towards_point(Pl_objp, &target_pos, NULL, 0.0f);
|
||||
|
||||
fix last_hit = Missiontime - aip->last_hit_time;
|
||||
@@ -1493,7 +1487,7 @@ void ai_big_strafe_glide_attack()
|
||||
vm_vec_sub2(&target_pos, &En_objp->pos);
|
||||
|
||||
turn_towards_point(Pl_objp, &target_pos, NULL, 0.0f);
|
||||
ai_big_maybe_fire_weapons(target_dist, target_dot, &Pl_objp->pos, &En_objp->pos, &En_objp->phys_info.vel);
|
||||
ai_big_maybe_fire_weapons(target_dist, target_dot);
|
||||
}
|
||||
|
||||
// if haven't been hit in quite a while, leave strafe mode
|
||||
@@ -1517,7 +1511,7 @@ void ai_big_strafe_avoid()
|
||||
mode_time = Missiontime - aip->submode_start_time;
|
||||
|
||||
ai_big_attack_get_data(&target_pos, &target_dist, &target_dot);
|
||||
if ( ai_big_strafe_maybe_retreat(target_dist, &target_pos) )
|
||||
if ( ai_big_strafe_maybe_retreat(&target_pos) )
|
||||
return;
|
||||
|
||||
if ( mode_time > fl2f(0.5)) {
|
||||
@@ -1704,7 +1698,7 @@ void ai_big_strafe()
|
||||
//
|
||||
// Check if weapon_objnum was fired by Pl_objp's target, and whether Pl_objp's target is a big ship, if
|
||||
// so, enter AIM_STRAFE
|
||||
int ai_big_maybe_enter_strafe_mode(object *pl_objp, int weapon_objnum, int consider_target_only)
|
||||
int ai_big_maybe_enter_strafe_mode(const object *pl_objp, int weapon_objnum)
|
||||
{
|
||||
ai_info *aip;
|
||||
ship_info *sip;
|
||||
@@ -1778,7 +1772,7 @@ int ai_big_maybe_enter_strafe_mode(object *pl_objp, int weapon_objnum, int consi
|
||||
// Consider attacking a turret, if a turret actually fired the weapon
|
||||
// input: ship_objp => ship that will attack the turret
|
||||
// weapon_objp =>
|
||||
void ai_big_strafe_maybe_attack_turret(object *ship_objp, object *weapon_objp)
|
||||
void ai_big_strafe_maybe_attack_turret(const object *ship_objp, const object *weapon_objp)
|
||||
{
|
||||
ai_info *aip;
|
||||
object *parent_objp;
|
||||
|
||||
+2
-3
@@ -17,14 +17,13 @@ struct ai_info;
|
||||
struct vec3d;
|
||||
class ship_subsys;
|
||||
|
||||
void ai_big_ship(object *objp);
|
||||
void ai_big_chase();
|
||||
void ai_big_subsys_path_cleanup(ai_info *aip);
|
||||
|
||||
// strafe functions
|
||||
void ai_big_strafe();
|
||||
int ai_big_maybe_enter_strafe_mode(object *objp, int weapon_objnum, int consider_target_only=0);
|
||||
void ai_big_strafe_maybe_attack_turret(object *ship_objp, object *weapon_objp);
|
||||
int ai_big_maybe_enter_strafe_mode(const object *objp, int weapon_objnum);
|
||||
void ai_big_strafe_maybe_attack_turret(const object *ship_objp, const object *weapon_objp);
|
||||
void ai_big_pick_attack_point(object *objp, object *attacker_objp, vec3d *attack_point, float fov=1.0f);
|
||||
void ai_big_pick_attack_point_turret(object *objp, ship_subsys *ssp, vec3d *gpos, vec3d *gvec, vec3d *attack_point, float weapon_travel_dist, float fov=1.0f);
|
||||
|
||||
|
||||
+74
-102
@@ -68,7 +68,7 @@
|
||||
#include "weapon/swarm.h"
|
||||
#include "weapon/weapon.h"
|
||||
#include <map>
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
|
||||
#ifdef _MSC_VER
|
||||
@@ -764,6 +764,8 @@ void parse_ai_class()
|
||||
set_aic_flag(aicp, "$all ships manage shields:", AI::Profile_Flags::All_ships_manage_shields);
|
||||
|
||||
set_aic_flag(aicp, "$ai can slow down when attacking big ships:", AI::Profile_Flags::Ai_can_slow_down_attacking_big_ships);
|
||||
|
||||
set_aic_flag(aicp, "$use actual primary range:", AI::Profile_Flags::Use_actual_primary_range);
|
||||
}
|
||||
|
||||
void reset_ai_class_names()
|
||||
@@ -1132,7 +1134,7 @@ void ai_update_danger_weapon(int attacked_objnum, int weapon_objnum)
|
||||
|
||||
// If rvec != NULL, use it to match bank by calling vm_matrix_interpolate.
|
||||
// (rvec defaults to NULL)
|
||||
void ai_turn_towards_vector(vec3d *dest, object *objp, float frametime, float turn_time, vec3d *slide_vec, vec3d *rel_pos, float bank_override, int flags, vec3d *rvec, int sexp_flags)
|
||||
void ai_turn_towards_vector(vec3d *dest, object *objp, float turn_time, vec3d *slide_vec, vec3d *rel_pos, float bank_override, int flags, vec3d *rvec, int sexp_flags)
|
||||
{
|
||||
matrix curr_orient;
|
||||
vec3d vel_in, vel_out, desired_fvec, src;
|
||||
@@ -1500,12 +1502,12 @@ void turn_towards_point(object *objp, vec3d *point, vec3d *slide_vec, float bank
|
||||
if (aip->ai_flags[AI::AI_Flags::Formation_object, AI::AI_Flags::Formation_wing]) {
|
||||
if (&Objects[aip->goal_objnum] != objp) {
|
||||
float rotvel_z = objp->phys_info.rotvel.xyz.z;
|
||||
ai_turn_towards_vector(point, objp, flFrametime, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, slide_vec, NULL, bank_override, 0);
|
||||
ai_turn_towards_vector(point, objp, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, slide_vec, nullptr, bank_override, 0);
|
||||
objp->phys_info.rotvel.xyz.z = rotvel_z;
|
||||
}
|
||||
} else {
|
||||
// normal turn
|
||||
ai_turn_towards_vector(point, objp, flFrametime, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, slide_vec, NULL, bank_override, 0);
|
||||
ai_turn_towards_vector(point, objp, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, slide_vec, nullptr, bank_override, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1520,7 +1522,7 @@ void turn_away_from_point(object *objp, vec3d *point, float bank_override)
|
||||
vm_vec_sub(&opposite_point, &objp->pos, point);
|
||||
vm_vec_add2(&opposite_point, &objp->pos);
|
||||
|
||||
ai_turn_towards_vector(&opposite_point, objp, flFrametime, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, NULL, NULL, bank_override, AITTV_FAST);
|
||||
ai_turn_towards_vector(&opposite_point, objp, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, nullptr, nullptr, bank_override, AITTV_FAST);
|
||||
}
|
||||
|
||||
|
||||
@@ -3448,35 +3450,6 @@ float compute_time_to_enemy(float dist_to_enemy, object *pobjp)
|
||||
return time_to_enemy + flFrametime;
|
||||
}
|
||||
|
||||
// Stuff *dot and *tts.
|
||||
// *dot is always computed. If dot is less than zero, the magnitude is
|
||||
// incorrect, not having been divided by distance.
|
||||
// If *dot is > 0.0f, then tts is computed. This is the time it will take object
|
||||
// *objp to get to *pos, assuming it moves right at it.
|
||||
void fds_aux(float *dot, float *tts, vec3d *pos, float dtime, object *objp)
|
||||
{
|
||||
vec3d v2s;
|
||||
|
||||
vm_vec_sub(&v2s, pos, &objp->pos);
|
||||
*dot = vm_vec_dot(&v2s, &objp->orient.vec.fvec);
|
||||
|
||||
if (*dot > 0.0f) {
|
||||
float dist;
|
||||
|
||||
dist = vm_vec_dist(&objp->pos, pos);
|
||||
|
||||
if (dist > 0.1f)
|
||||
*dot /= dist;
|
||||
else
|
||||
*dot = 1.0f;
|
||||
|
||||
if (objp->phys_info.speed > 0.1f)
|
||||
*tts = dist / objp->phys_info.speed;
|
||||
else
|
||||
*tts = dist * 100.0f;
|
||||
}
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
void ai_set_positions(object *pl_objp, object *en_objp, ai_info *aip, vec3d *player_pos, vec3d *enemy_pos)
|
||||
{
|
||||
@@ -3892,7 +3865,7 @@ float ai_path_0()
|
||||
}
|
||||
|
||||
if (dist_to_goal > 0.1f)
|
||||
ai_turn_towards_vector(&gcvp, Pl_objp, flFrametime, sip->srotation_time, slop_vec, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&gcvp, Pl_objp, sip->srotation_time, slop_vec, nullptr, 0.0f, 0);
|
||||
|
||||
// Code to control speed is MUCH less forgiving in path following than in waypoint
|
||||
// following. Must be very close to path or might hit objects.
|
||||
@@ -4034,10 +4007,10 @@ float ai_path_1()
|
||||
if (r <= 1.0f) {
|
||||
vec3d midpoint;
|
||||
vm_vec_avg3(&midpoint, &gcvp, &closest_point, &closest_point);
|
||||
ai_turn_towards_vector(&midpoint, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0, prvec);
|
||||
ai_turn_towards_vector(&midpoint, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0, prvec);
|
||||
}
|
||||
else {
|
||||
ai_turn_towards_vector(&gcvp, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0, prvec);
|
||||
ai_turn_towards_vector(&gcvp, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0, prvec);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4382,11 +4355,11 @@ void ai_fly_to_target_position(vec3d* target_pos, bool* pl_done_p=NULL, bool* pl
|
||||
vm_vector_2_matrix(&Pl_objp->orient, &perp, NULL, NULL);
|
||||
} else {
|
||||
vm_vec_scale_add(&perp, &Pl_objp->pos, &Autopilot_flight_leader->phys_info.vel, 1000.0f);
|
||||
ai_turn_towards_vector(&perp, Pl_objp, flFrametime, sip->srotation_time*3.0f*scale, slop_vec, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&perp, Pl_objp, sip->srotation_time*3.0f*scale, slop_vec, nullptr, 0.0f, 0);
|
||||
}
|
||||
} else {
|
||||
if (dist_to_goal > 0.1f) {
|
||||
ai_turn_towards_vector(target_pos, Pl_objp, flFrametime, sip->srotation_time*3.0f*scale, slop_vec, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(target_pos, Pl_objp, sip->srotation_time*3.0f*scale, slop_vec, nullptr, 0.0f, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5051,7 +5024,7 @@ void slide_face_ship()
|
||||
|
||||
dist = vm_vec_normalized_dir(&vec_from_enemy, &Pl_objp->pos, &En_objp->pos);
|
||||
|
||||
ai_turn_towards_vector(&En_objp->pos, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&En_objp->pos, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
|
||||
dot_from_enemy = vm_vec_dot(&vec_from_enemy, &En_objp->orient.vec.fvec);
|
||||
|
||||
@@ -5234,7 +5207,7 @@ vec3d G_predicted_pos, G_fire_pos;
|
||||
// Else
|
||||
// Select Any ol' weapon.
|
||||
// Returns primary_bank index.
|
||||
int ai_select_primary_weapon_OLD(object *objp, object *other_objp, Weapon::Info_Flags flags)
|
||||
static int ai_select_primary_weapon_OLD(const object *objp, Weapon::Info_Flags flags)
|
||||
{
|
||||
ship *shipp = &Ships[objp->instance];
|
||||
ship_weapon *swp = &shipp->weapons;
|
||||
@@ -5325,7 +5298,7 @@ int ai_select_primary_weapon(object *objp, object *other_objp, Weapon::Info_Flag
|
||||
//not using the new AI, use the old version of this function instead.
|
||||
if (!(Ai_info[shipp->ai_index].ai_profile_flags[AI::Profile_Flags::Smart_primary_weapon_selection]))
|
||||
{
|
||||
return ai_select_primary_weapon_OLD(objp, other_objp, flags);
|
||||
return ai_select_primary_weapon_OLD(objp, flags);
|
||||
}
|
||||
|
||||
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
|
||||
@@ -6051,8 +6024,7 @@ int check_ok_to_fire(int objnum, int target_objnum, weapon_info *wip)
|
||||
// --------------------------------------------------------------------------
|
||||
// Fire a secondary weapon.
|
||||
// Maybe choose to fire a different one.
|
||||
// priority1 and priority2 are optional parameters with defaults = -1
|
||||
int ai_fire_secondary_weapon(object *objp, int priority1, int priority2)
|
||||
int ai_fire_secondary_weapon(object *objp)
|
||||
{
|
||||
ship_weapon *swp;
|
||||
ship *shipp;
|
||||
@@ -6072,7 +6044,7 @@ int ai_fire_secondary_weapon(object *objp, int priority1, int priority2)
|
||||
Assert( shipp->ship_info_index >= 0 && shipp->ship_info_index < static_cast<int>(Ship_info.size()));
|
||||
|
||||
// Select secondary weapon.
|
||||
current_bank = swp->current_secondary_bank; //ai_select_secondary_weapon(objp, swp, priority1, priority2);
|
||||
current_bank = swp->current_secondary_bank;
|
||||
|
||||
if (current_bank == -1) {
|
||||
return rval;
|
||||
@@ -6539,14 +6511,14 @@ void ai_chase_ct()
|
||||
vm_vec_add2(&tvec, &Pl_objp->orient.vec.rvec);
|
||||
}
|
||||
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
accelerate_ship(aip, 1.0f);
|
||||
}
|
||||
|
||||
/**
|
||||
* ATTACK submode handler for chase mode.
|
||||
*/
|
||||
void ai_chase_eb(ai_info *aip, ship_info *sip, vec3d *predicted_enemy_pos, float dist_to_enemy)
|
||||
static void ai_chase_eb(ai_info *aip, ship_info *sip, vec3d *predicted_enemy_pos)
|
||||
{
|
||||
vec3d _pep;
|
||||
float dot_to_enemy, dot_from_enemy;
|
||||
@@ -6558,7 +6530,7 @@ void ai_chase_eb(ai_info *aip, ship_info *sip, vec3d *predicted_enemy_pos, float
|
||||
if ((dot_to_enemy > dot_from_enemy + 0.1f) || (dot_to_enemy > 0.9f))
|
||||
vm_vec_scale_add(&_pep, &Pl_objp->pos, &En_objp->orient.vec.fvec, 100.0f);
|
||||
|
||||
ai_turn_towards_vector(&_pep, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&_pep, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
|
||||
accelerate_ship(aip, 0.0f);
|
||||
}
|
||||
@@ -6755,7 +6727,7 @@ void attack_set_accel(ai_info *aip, ship_info *sip, float dist_to_enemy, float d
|
||||
|
||||
// Pl_objp (aip) tries to get behind En_objp.
|
||||
// New on 2/21/98: If this ship can move backwards and slide, maybe do that to get behind.
|
||||
void get_behind_ship(ai_info *aip, ship_info *sip, float dist_to_enemy)
|
||||
static void get_behind_ship(ai_info *aip, ship_info *sip)
|
||||
{
|
||||
vec3d new_pos;
|
||||
float dot;
|
||||
@@ -6764,7 +6736,7 @@ void get_behind_ship(ai_info *aip, ship_info *sip, float dist_to_enemy)
|
||||
vm_vec_normalized_dir(&vec_from_enemy, &Pl_objp->pos, &En_objp->pos);
|
||||
|
||||
vm_vec_scale_add(&new_pos, &En_objp->pos, &En_objp->orient.vec.fvec, -100.0f); // Pick point 100 units behind.
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
|
||||
dot = vm_vec_dot(&vec_from_enemy, &En_objp->orient.vec.fvec);
|
||||
|
||||
@@ -6783,7 +6755,7 @@ int avoid_player(object *objp, vec3d *goal_pos)
|
||||
if (aip->ai_flags[AI::AI_Flags::Avoiding_small_ship]) {
|
||||
ship_info *sip = &Ship_info[Ships[objp->instance].ship_info_index];
|
||||
|
||||
ai_turn_towards_vector(&aip->avoid_goal_point, objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&aip->avoid_goal_point, objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
accelerate_ship(aip, 0.5f);
|
||||
return 1;
|
||||
}
|
||||
@@ -6981,7 +6953,7 @@ int maybe_avoid_big_ship(object *objp, object *ignore_objp, ai_info *aip, vec3d
|
||||
|
||||
vec3d v2g;
|
||||
|
||||
ai_turn_towards_vector(&aip->avoid_goal_point, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&aip->avoid_goal_point, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
vm_vec_normalized_dir(&v2g, &aip->avoid_goal_point, &Pl_objp->pos);
|
||||
float dot = vm_vec_dot(&objp->orient.vec.fvec, &v2g);
|
||||
float d2 = (1.0f + dot) * (1.0f + dot);
|
||||
@@ -7073,7 +7045,7 @@ void ai_stealth_find()
|
||||
}
|
||||
}
|
||||
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -7083,9 +7055,9 @@ void ai_stealth_find()
|
||||
if (dist_to_enemy > 500.0f) {
|
||||
vec3d rvec;
|
||||
compute_desired_rvec(&rvec, &new_pos, &Pl_objp->pos);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0, &rvec);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0, &rvec);
|
||||
} else {
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
}
|
||||
|
||||
dot_from_enemy = -vm_vec_dot(&vec_to_enemy, &En_objp->orient.vec.fvec);
|
||||
@@ -7213,7 +7185,7 @@ void ai_stealth_sweep()
|
||||
return;
|
||||
}
|
||||
|
||||
ai_turn_towards_vector(&goal_pt, Pl_objp, flFrametime, sip->srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&goal_pt, Pl_objp, sip->srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
|
||||
float dot = 1.0f;
|
||||
if (dist_to_goal < 100) {
|
||||
@@ -7273,9 +7245,9 @@ void ai_chase_attack(ai_info *aip, ship_info *sip, vec3d *predicted_enemy_pos, f
|
||||
if (dist_to_enemy > 500.0f) {
|
||||
vec3d rvec;
|
||||
compute_desired_rvec(&rvec, predicted_enemy_pos, &Pl_objp->pos);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, rel_pos, bank_override, 0, &rvec);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, rel_pos, bank_override, 0, &rvec);
|
||||
} else {
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, flFrametime, sip->srotation_time, NULL, rel_pos, bank_override, 0);
|
||||
ai_turn_towards_vector(&new_pos, Pl_objp, sip->srotation_time, nullptr, rel_pos, bank_override, 0);
|
||||
}
|
||||
|
||||
attack_set_accel(aip, sip, dist_to_enemy, dot_to_enemy, dot_from_enemy);
|
||||
@@ -7313,7 +7285,7 @@ void ai_chase_es(ai_info *aip, ship_info *sip)
|
||||
|
||||
float bank_override = Pl_objp->phys_info.speed;
|
||||
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, flFrametime/2, sip->srotation_time, NULL, NULL, bank_override, 0);
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, sip->srotation_time, nullptr, nullptr, bank_override, 0);
|
||||
accelerate_ship(aip, 1.0f);
|
||||
}
|
||||
|
||||
@@ -7339,7 +7311,7 @@ void ai_chase_ga(ai_info *aip, ship_info *sip)
|
||||
|
||||
bank_override = Pl_objp->phys_info.speed;
|
||||
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, flFrametime/2, sip->srotation_time, NULL, NULL, bank_override, 0);
|
||||
ai_turn_towards_vector(&tvec, Pl_objp, sip->srotation_time, nullptr, nullptr, bank_override, 0);
|
||||
|
||||
accelerate_ship(aip, 2.0f);
|
||||
|
||||
@@ -8001,7 +7973,7 @@ void ai_cruiser_chase()
|
||||
|
||||
// kamikaze - ram and explode
|
||||
if (aip->ai_flags[AI::AI_Flags::Kamikaze]) {
|
||||
ai_turn_towards_vector(&En_objp->pos, Pl_objp, flFrametime, turn_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&En_objp->pos, Pl_objp, turn_time, nullptr, nullptr, 0.0f, 0);
|
||||
accelerate_ship(aip, 1.0f);
|
||||
}
|
||||
|
||||
@@ -8041,7 +8013,7 @@ void ai_cruiser_chase()
|
||||
}
|
||||
|
||||
// now move as desired
|
||||
ai_turn_towards_vector(&goal_pos, Pl_objp, flFrametime, turn_time, NULL, NULL, 0.0f, 0, rvecp);
|
||||
ai_turn_towards_vector(&goal_pos, Pl_objp, turn_time, nullptr, nullptr, 0.0f, 0, rvecp);
|
||||
accelerate_ship(aip, accel);
|
||||
|
||||
// maybe switch to new mode
|
||||
@@ -8322,7 +8294,7 @@ void ai_chase()
|
||||
break;
|
||||
|
||||
case SM_EVADE_BRAKE:
|
||||
ai_chase_eb(aip, sip, &predicted_enemy_pos, dist_to_enemy);
|
||||
ai_chase_eb(aip, sip, &predicted_enemy_pos);
|
||||
break;
|
||||
|
||||
case SM_EVADE:
|
||||
@@ -8334,7 +8306,7 @@ void ai_chase()
|
||||
break;
|
||||
|
||||
case SM_GET_BEHIND:
|
||||
get_behind_ship(aip, sip, dist_to_enemy);
|
||||
get_behind_ship(aip, sip);
|
||||
break;
|
||||
|
||||
case SM_GET_AWAY: // Used to get away from opponent to prevent endless circling.
|
||||
@@ -8768,7 +8740,11 @@ void ai_chase()
|
||||
scale = (scale - 0.6f) * 1.5f;
|
||||
else
|
||||
scale = 0.0f;
|
||||
if (dist_to_enemy < pwip->max_speed * (1.0f + scale)) {
|
||||
float range = pwip->max_speed * (1.0f + scale);
|
||||
if (aip->ai_profile_flags[AI::Profile_Flags::Use_actual_primary_range]) {
|
||||
range = std::min( {range, pwip->max_speed * pwip->lifetime, pwip->weapon_range} );
|
||||
}
|
||||
if (dist_to_enemy < range) {
|
||||
if(ai_fire_primary_weapon(Pl_objp) == 1){
|
||||
has_fired = 1;
|
||||
}else{
|
||||
@@ -9329,7 +9305,7 @@ float dock_orient_and_approach(object *docker_objp, int docker_index, object *do
|
||||
{
|
||||
float dot, accel;
|
||||
float turn_time = Ship_info[Ships[docker_objp->instance].ship_info_index].srotation_time;
|
||||
ai_turn_towards_vector(&goal_point, docker_objp, flFrametime, turn_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&goal_point, docker_objp, turn_time, nullptr, nullptr, 0.0f, 0);
|
||||
|
||||
dot = vm_vec_dot(&docker_objp->orient.vec.fvec, &away_vec);
|
||||
accel = 0.1f;
|
||||
@@ -9964,7 +9940,7 @@ void ai_big_guard()
|
||||
}
|
||||
|
||||
// got the point, now let's go there
|
||||
ai_turn_towards_vector(&goal_pt, Pl_objp, flFrametime, Ship_info[Ships[Pl_objp->instance].ship_info_index].srotation_time, NULL, NULL, 0.0f, 0);
|
||||
ai_turn_towards_vector(&goal_pt, Pl_objp, Ship_info[Ships[Pl_objp->instance].ship_info_index].srotation_time, nullptr, nullptr, 0.0f, 0);
|
||||
accelerate_ship(aip, 1.0f);
|
||||
|
||||
if ((aip->ai_flags[AI::AI_Flags::Free_afterburner_use]) && !(shipp->flags[Ship::Ship_Flags::Afterburner_locked]) && (cur_guard_rad > 1.1f * max_guard_dist)) {
|
||||
@@ -10088,7 +10064,7 @@ void ai_guard()
|
||||
|
||||
// quite far away, so try to go straight to
|
||||
compute_desired_rvec(&rvec, &goal_point, &Pl_objp->pos);
|
||||
ai_turn_towards_vector(&goal_point, Pl_objp, flFrametime, Ship_info[shipp->ship_info_index].srotation_time, NULL, NULL, 0.0f, 0, &rvec);
|
||||
ai_turn_towards_vector(&goal_point, Pl_objp, Ship_info[shipp->ship_info_index].srotation_time, nullptr, nullptr, 0.0f, 0, &rvec);
|
||||
|
||||
if ((aip->ai_flags[AI::AI_Flags::Free_afterburner_use]) && !(shipp->flags[Ship::Ship_Flags::Afterburner_locked]) && (accel_scale * (0.25f + dist_to_goal_point/700.0f) > 0.8f)) {
|
||||
if (ai_maybe_fire_afterburner(Pl_objp, aip)) {
|
||||
@@ -10713,8 +10689,8 @@ void ai_dock()
|
||||
char *goal_ship_class_name = goal_sip->name;
|
||||
char *goal_dock_path_name = model_get(goal_sip->model_num)->paths[aip->mp_index].name;
|
||||
|
||||
Warning(LOCATION, "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);
|
||||
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));
|
||||
}
|
||||
|
||||
aip->submode = AIS_DOCK_1;
|
||||
@@ -10839,7 +10815,7 @@ void ai_dock()
|
||||
|
||||
if (aip->submode == AIS_DOCK_3) {
|
||||
// Play a ship docking attach sound
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DOCK_ATTACH), &Pl_objp->pos, &View_position );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DOCK_ATTACH), &Pl_objp->pos, &View_position );
|
||||
|
||||
// start the dock animation
|
||||
model_anim_start_type(shipp, TRIGGER_TYPE_DOCKED, docker_index, 1);
|
||||
@@ -10966,7 +10942,7 @@ void ai_dock()
|
||||
ai_find_path(Pl_objp, OBJ_INDEX(goal_objp), path_num, 0);
|
||||
|
||||
// Play a ship docking detach sound
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DOCK_DETACH), &Pl_objp->pos, &View_position );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DOCK_DETACH), &Pl_objp->pos, &View_position );
|
||||
|
||||
aip->submode = AIS_UNDOCK_1;
|
||||
aip->submode_start_time = Missiontime;
|
||||
@@ -10986,7 +10962,7 @@ void ai_dock()
|
||||
// play the depart sound, but only once, since this mode is called multiple times per frame
|
||||
if ( !(aigp->flags[AI::Goal_Flags::Depart_sound_played]))
|
||||
{
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DOCK_DEPART), &Pl_objp->pos, &View_position );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DOCK_DEPART), &Pl_objp->pos, &View_position );
|
||||
aigp->flags.set(AI::Goal_Flags::Depart_sound_played);
|
||||
}
|
||||
|
||||
@@ -11385,7 +11361,7 @@ float gwlr_1(object *objp, ai_info *aip)
|
||||
/**
|
||||
* Compute the largest radius of a ship forming on *objp's wing.
|
||||
*/
|
||||
float gwlr_object_1(object *objp, ai_info *aip)
|
||||
static float gwlr_object_1(object *objp)
|
||||
{
|
||||
float max_radius;
|
||||
object *o;
|
||||
@@ -11418,7 +11394,7 @@ float get_wing_largest_radius(object *objp, int formation_object_flag)
|
||||
aip = &Ai_info[shipp->ai_index];
|
||||
|
||||
if (formation_object_flag) {
|
||||
return gwlr_object_1(objp, aip);
|
||||
return gwlr_object_1(objp);
|
||||
} else {
|
||||
return gwlr_1(objp, aip);
|
||||
}
|
||||
@@ -12191,7 +12167,7 @@ void ai_maybe_launch_cmeasure(object *objp, ai_info *aip)
|
||||
}
|
||||
|
||||
// --------------------------------------------------------------------------
|
||||
void ai_preprocess_ignore_objnum(object *objp, ai_info *aip)
|
||||
static void ai_preprocess_ignore_objnum(ai_info *aip)
|
||||
{
|
||||
if (aip->ai_flags[AI::AI_Flags::Temporary_ignore])
|
||||
{
|
||||
@@ -13024,7 +13000,7 @@ void ai_execute_behavior(ai_info *aip)
|
||||
ship *shipp = &Ships[aip->shipnum];
|
||||
ship_info *sip = &Ship_info[shipp->ship_info_index];
|
||||
|
||||
if (strnicmp(shipp->ship_name, INSTRUCTOR_SHIP_NAME, strlen(INSTRUCTOR_SHIP_NAME))) {
|
||||
if (strnicmp(shipp->ship_name, INSTRUCTOR_SHIP_NAME, strlen(INSTRUCTOR_SHIP_NAME)) != 0) {
|
||||
if (sip->is_big_or_huge()) {
|
||||
aip->mode = AIM_NONE;
|
||||
} else {
|
||||
@@ -13064,7 +13040,6 @@ void ai_execute_behavior(ai_info *aip)
|
||||
case AIM_NONE:
|
||||
break;
|
||||
case AIM_BIGSHIP:
|
||||
ai_big_ship(Pl_objp);
|
||||
break;
|
||||
case AIM_PATH: {
|
||||
int path_num;
|
||||
@@ -13441,7 +13416,7 @@ void ai_warp_out(object *objp)
|
||||
|
||||
// Return object index of weapon that could produce a shockwave that should be known about to *objp.
|
||||
// Return nearest one.
|
||||
int ai_find_shockwave_weapon(object *objp, ai_info *aip)
|
||||
static int ai_find_shockwave_weapon(const object *objp)
|
||||
{
|
||||
missile_obj *mo;
|
||||
float nearest_dist = 999999.9f;
|
||||
@@ -13507,7 +13482,7 @@ void ai_announce_ship_dying(object *dying_objp)
|
||||
|
||||
// Return object index of weapon that could produce a shockwave that should be known about to *objp.
|
||||
// Return nearest one.
|
||||
int ai_find_shockwave_ship(object *objp, ai_info *aip)
|
||||
static int ai_find_shockwave_ship(object *objp)
|
||||
{
|
||||
ship_obj *so;
|
||||
float nearest_dist = 999999.9f;
|
||||
@@ -13550,7 +13525,7 @@ int aas_1(object *objp, ai_info *aip, vec3d *safe_pos)
|
||||
// If we don't currently know of a weapon to avoid, try to find one.
|
||||
// If we can't find one, then clear the bit so we don't keep coming here.
|
||||
if (aip->shockwave_object == -1) {
|
||||
int shockwave_weapon = ai_find_shockwave_weapon(objp, aip);
|
||||
int shockwave_weapon = ai_find_shockwave_weapon(objp);
|
||||
if (shockwave_weapon == -1) {
|
||||
aip->ai_flags.remove(AI::AI_Flags::Avoid_shockwave_weapon);
|
||||
return 0;
|
||||
@@ -13639,7 +13614,7 @@ int aas_1(object *objp, ai_info *aip, vec3d *safe_pos)
|
||||
}
|
||||
} else if (aip->ai_flags[AI::AI_Flags::Avoid_shockwave_ship]) {
|
||||
if (aip->shockwave_object == -1) {
|
||||
int shockwave_ship = ai_find_shockwave_ship(objp, aip);
|
||||
int shockwave_ship = ai_find_shockwave_ship(objp);
|
||||
if (shockwave_ship == -1) {
|
||||
aip->ai_flags.remove(AI::AI_Flags::Avoid_shockwave_ship);
|
||||
return 0;
|
||||
@@ -13869,7 +13844,7 @@ int maybe_big_ship_collide_recover_frame(object *objp, ai_info *aip)
|
||||
vec3d v2g;
|
||||
|
||||
if (aip->ai_flags[AI::AI_Flags::Big_ship_collide_recover_1]) {
|
||||
ai_turn_towards_vector(&aip->big_recover_pos_1, objp, flFrametime, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, NULL, NULL, 0.0f, 0, NULL);
|
||||
ai_turn_towards_vector(&aip->big_recover_pos_1, objp, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, nullptr, nullptr, 0.0f, 0, nullptr);
|
||||
dist = vm_vec_normalized_dir(&v2g, &aip->big_recover_pos_1, &objp->pos);
|
||||
dot = vm_vec_dot(&objp->orient.vec.fvec, &v2g);
|
||||
accelerate_ship(aip, dot);
|
||||
@@ -13883,7 +13858,7 @@ int maybe_big_ship_collide_recover_frame(object *objp, ai_info *aip)
|
||||
return 1;
|
||||
|
||||
} else if (aip->ai_flags[AI::AI_Flags::Big_ship_collide_recover_2]) {
|
||||
ai_turn_towards_vector(&aip->big_recover_pos_2, objp, flFrametime, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, NULL, NULL, 0.0f, 0, NULL);
|
||||
ai_turn_towards_vector(&aip->big_recover_pos_2, objp, Ship_info[Ships[objp->instance].ship_info_index].srotation_time, nullptr, nullptr, 0.0f, 0, nullptr);
|
||||
dist = vm_vec_normalized_dir(&v2g, &aip->big_recover_pos_2, &objp->pos);
|
||||
dot = vm_vec_dot(&objp->orient.vec.fvec, &v2g);
|
||||
accelerate_ship(aip, dot);
|
||||
@@ -14003,7 +13978,7 @@ void ai_frame(int objnum)
|
||||
if (maybe_big_ship_collide_recover_frame(Pl_objp, aip))
|
||||
return;
|
||||
|
||||
ai_preprocess_ignore_objnum(Pl_objp, aip);
|
||||
ai_preprocess_ignore_objnum(aip);
|
||||
target_objnum = set_target_objnum(aip, aip->target_objnum);
|
||||
|
||||
Assert(objnum != target_objnum);
|
||||
@@ -14158,7 +14133,7 @@ void ai_frame(int objnum)
|
||||
}
|
||||
}
|
||||
|
||||
void ai_control_info_check( object *obj, ai_info *aip )
|
||||
static void ai_control_info_check(ai_info *aip)
|
||||
{
|
||||
if(aip->ai_override_flags.none_set())
|
||||
return;
|
||||
@@ -14259,7 +14234,7 @@ void ai_process( object * obj, int ai_index, float frametime )
|
||||
|
||||
if (rfc == 1) {
|
||||
// Wanderer - sexp based override goes here - only if rfc is valid though
|
||||
ai_control_info_check(obj, aip);
|
||||
ai_control_info_check(aip);
|
||||
vec3d copy_desired_rotvel = obj->phys_info.rotvel;
|
||||
physics_read_flying_controls( &obj->orient, &obj->phys_info, &AI_ci, frametime);
|
||||
// if obj is in formation and not flight leader, don't update rotvel
|
||||
@@ -14794,10 +14769,10 @@ int firing_aspect_seeking_bomb(object *objp)
|
||||
return 0;
|
||||
}
|
||||
|
||||
// *objp collided with big ship *big_objp at global point *collide_pos
|
||||
// Make it fly away from the collision point.
|
||||
// *objp collided with big ship *big_objp at some global point.
|
||||
// Make it fly away from the collision point.
|
||||
// collision_normal is NULL, when a collision is imminent and we just want to bug out.
|
||||
void big_ship_collide_recover_start(object *objp, object *big_objp, vec3d *collide_pos, vec3d *collision_normal)
|
||||
void big_ship_collide_recover_start(object *objp, object *big_objp, vec3d *collision_normal)
|
||||
{
|
||||
ai_info *aip;
|
||||
|
||||
@@ -14886,9 +14861,9 @@ void ai_update_lethality(object *pship_obj, object *other_obj, float damage)
|
||||
|
||||
|
||||
/**
|
||||
* Object *objp_ship was hit by either weapon *objp_weapon or collided into by ship hit_objp at point *hitpos.
|
||||
* Object *objp_ship was hit by either weapon *objp_weapon or collided into by ship hit_objp
|
||||
*/
|
||||
void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hitpos, int shield_quadrant, vec3d *hit_normal)
|
||||
void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hit_normal)
|
||||
{
|
||||
int hitter_objnum = -2;
|
||||
object *objp_hitter = NULL;
|
||||
@@ -14930,7 +14905,7 @@ void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hitpos, int shield_
|
||||
// And the current object is _not_ a big ship
|
||||
if (!Ship_info[Ships[objp_ship->instance].ship_info_index].is_big_or_huge()) {
|
||||
// Recover from hitting a big ship. Note, if two big ships collide, they just pound away at each other. Oh well. Recovery looks dumb and it's very late.
|
||||
big_ship_collide_recover_start(objp_ship, hit_objp, hitpos, hit_normal);
|
||||
big_ship_collide_recover_start(objp_ship, hit_objp, hit_normal);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -15067,7 +15042,7 @@ void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hitpos, int shield_
|
||||
return;
|
||||
|
||||
if ( (hit_objp->type == OBJ_WEAPON) && !(aip->ai_flags[AI::AI_Flags::No_dynamic]) ) {
|
||||
if ( ai_big_maybe_enter_strafe_mode(objp_ship, OBJ_INDEX(hit_objp), 1) )
|
||||
if ( ai_big_maybe_enter_strafe_mode(objp_ship, OBJ_INDEX(hit_objp)) )
|
||||
return;
|
||||
}
|
||||
break;
|
||||
@@ -15187,10 +15162,7 @@ void ai_ship_hit(object *objp_ship, object *hit_objp, vec3d *hitpos, int shield_
|
||||
|
||||
// Ship shipnum has been destroyed.
|
||||
// Cleanup.
|
||||
// the parameter 'method' is used to tell is this ship was destroyed or it departed normally.
|
||||
// This function will get called in either case, and there are things that should be done if
|
||||
// the ship actually gets destroyed which shouldn't get done if it departed.
|
||||
void ai_ship_destroy(int shipnum, Ship::Exit_Flags method)
|
||||
void ai_ship_destroy(int shipnum)
|
||||
{
|
||||
int objnum;
|
||||
object *other_objp;
|
||||
@@ -15441,7 +15413,7 @@ int ai_issue_rearm_request(object *requester_objp)
|
||||
// we aren't able to do anything!
|
||||
else {
|
||||
Assert(result == 4);
|
||||
Assertion(false, "This case should have already been caught by the is_support_allowed precheck!");
|
||||
UNREACHABLE("This case should have already been caught by the is_support_allowed precheck!");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
@@ -15510,7 +15482,7 @@ int ai_return_path_num_from_dockbay(object *dockee_objp, int dockbay_index)
|
||||
/**
|
||||
* Actually go ahead and fire the synaptics.
|
||||
*/
|
||||
void cheat_fire_synaptic(object *objp, ship *shipp, ai_info *aip)
|
||||
static void cheat_fire_synaptic(object *objp, ship *shipp)
|
||||
{
|
||||
ship_weapon *swp;
|
||||
swp = &shipp->weapons;
|
||||
@@ -15532,7 +15504,7 @@ void cheat_fire_synaptic(object *objp, ship *shipp, ai_info *aip)
|
||||
// if they're near one or more enemies
|
||||
// every so often
|
||||
// fire a synaptic if they have one.
|
||||
void maybe_cheat_fire_synaptic(object *objp, ai_info *aip)
|
||||
void maybe_cheat_fire_synaptic(object *objp)
|
||||
{
|
||||
// Only do in subspace missions.
|
||||
if (!(The_mission.flags[Mission::Mission_Flags::Subspace]))
|
||||
@@ -15564,7 +15536,7 @@ void maybe_cheat_fire_synaptic(object *objp, ai_info *aip)
|
||||
int count = num_nearby_fighters(iff_get_attackee_mask(obj_team(objp)), &objp->pos, 1500.0f);
|
||||
|
||||
if (count > 0)
|
||||
cheat_fire_synaptic(objp, shipp, aip);
|
||||
cheat_fire_synaptic(objp, shipp);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+4
-4
@@ -125,7 +125,7 @@ const char *Ai_goal_text(int goal)
|
||||
case AI_GOAL_REARM_REPAIR:
|
||||
return XSTR( "rearm ", 484);
|
||||
case AI_GOAL_FLY_TO_SHIP:
|
||||
return XSTR( "rendezvous with ", -1);
|
||||
return XSTR( "rendezvous with ", 1597);
|
||||
}
|
||||
|
||||
// Avoid compiler warning
|
||||
@@ -414,7 +414,7 @@ void ai_goal_purge_invalid_goals( ai_goal *aigp, ai_goal *goal_list, ai_info *ai
|
||||
if ( purge_ai_mode == AI_GOAL_CHASE_SHIP_CLASS ) {
|
||||
// if the target of the purge goal is the same class of ship we are concerned about, then we have a match;
|
||||
// if it is not, then we can continue (see standard ship check below)
|
||||
if ( stricmp(purge_goal->target_name, Ship_info[Ships[ship_index].ship_info_index].name) )
|
||||
if ( stricmp(purge_goal->target_name, Ship_info[Ships[ship_index].ship_info_index].name) != 0 )
|
||||
continue;
|
||||
}
|
||||
// standard goals operating on either wings or ships
|
||||
@@ -426,7 +426,7 @@ void ai_goal_purge_invalid_goals( ai_goal *aigp, ai_goal *goal_list, ai_info *ai
|
||||
// don't match, we can continue; if the wing is valid, don't process if the wing numbers
|
||||
// are different.
|
||||
if ( purge_wing == -1 ) {
|
||||
if ( stricmp(purge_goal->target_name, name ) )
|
||||
if ( stricmp(purge_goal->target_name, name ) != 0 )
|
||||
continue;
|
||||
} else if ( purge_wing != wingnum )
|
||||
continue;
|
||||
@@ -1263,7 +1263,7 @@ void ai_add_wing_goal_sexp(int sexp, int type, int wingnum)
|
||||
// this name can be a shipname or a wingname)
|
||||
// docker_point and dockee_point are used for the AI_GOAL_DOCK command to tell two ships where to dock
|
||||
// immediate means to process this order right away
|
||||
void ai_add_goal_ship_internal( ai_info *aip, int goal_type, char *name, int docker_point, int dockee_point, int immediate )
|
||||
void ai_add_goal_ship_internal( ai_info *aip, int goal_type, char *name, int /*docker_point*/, int /*dockee_point*/, int immediate )
|
||||
{
|
||||
int gindex;
|
||||
ai_goal *aigp;
|
||||
|
||||
@@ -24,7 +24,7 @@
|
||||
#include "weapon/swarm.h"
|
||||
#include "weapon/weapon.h"
|
||||
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
|
||||
// How close a turret has to be point at its target before it
|
||||
@@ -243,7 +243,7 @@ int bomb_headed_towards_ship(object *bomb_objp, object *ship_objp)
|
||||
* @note All non-negative return values are expressed in what I like to call "widx"s.
|
||||
* @return -1 if unable to find a weapon for the target at all.
|
||||
*/
|
||||
int turret_select_best_weapon(ship_subsys *turret, object *target)
|
||||
int turret_select_best_weapon(ship_subsys *turret, object * /*target*/)
|
||||
{
|
||||
//TODO: Fill this out with extraodinary gun-picking algorithms
|
||||
if(turret->weapons.num_primary_banks > 0)
|
||||
@@ -2048,7 +2048,7 @@ bool turret_fire_weapon(int weapon_num, ship_subsys *turret, int parent_objnum,
|
||||
}
|
||||
}
|
||||
|
||||
if ( wip->launch_snd != -1 ) {
|
||||
if ( wip->launch_snd.isValid() ) {
|
||||
// Don't play turret firing sound if turret sits on player ship... it gets annoying.
|
||||
if ( parent_objnum != OBJ_INDEX(Player_obj) || (turret->flags[Ship::Subsystem_Flags::Play_sound_for_player]) ) {
|
||||
snd_play_3d( gamesnd_get_game_sound(wip->launch_snd), turret_pos, &View_position );
|
||||
@@ -2135,7 +2135,7 @@ void turret_swarm_fire_from_turret(turret_swarm_info *tsi)
|
||||
}
|
||||
|
||||
// maybe sound
|
||||
if ( Weapon_info[tsi->weapon_class].launch_snd != -1 ) {
|
||||
if ( Weapon_info[tsi->weapon_class].launch_snd.isValid() ) {
|
||||
// Don't play turret firing sound if turret sits on player ship... it gets annoying.
|
||||
if ( tsi->parent_objnum != OBJ_INDEX(Player_obj) ) {
|
||||
snd_play_3d( gamesnd_get_game_sound(Weapon_info[tsi->weapon_class].launch_snd), &turret_pos, &View_position );
|
||||
|
||||
@@ -274,9 +274,9 @@ int anim_show_next_frame(anim_instance *instance, float frametime)
|
||||
percent_through = instance->time_elapsed / time;
|
||||
|
||||
if(instance->direction == ANIM_DIRECT_FORWARD)
|
||||
new_frame_num = instance->start_at - 1 + fl2i(percent_through * n_frames + 0.5f);
|
||||
new_frame_num = instance->start_at - 1 + (int) lround(percent_through * n_frames);
|
||||
else
|
||||
new_frame_num = instance->start_at - 1 - fl2i(percent_through * n_frames + 0.5f);
|
||||
new_frame_num = instance->start_at - 1 - (int) lround(percent_through * n_frames);
|
||||
|
||||
frame_save = instance->frame_num;
|
||||
|
||||
|
||||
+40
-102
@@ -76,7 +76,7 @@ float Asteroid_icon_closeup_zoom;
|
||||
/**
|
||||
* Force updating of pair stuff for asteroid *objp.
|
||||
*/
|
||||
void asteroid_update_collide(object *objp)
|
||||
static void asteroid_update_collide(object *objp)
|
||||
{
|
||||
// Asteroid has wrapped, update collide objnum and flags
|
||||
Asteroids[objp->instance].collide_objnum = -1;
|
||||
@@ -87,7 +87,7 @@ void asteroid_update_collide(object *objp)
|
||||
/**
|
||||
* Clear out the ::Asteroid_obj_list
|
||||
*/
|
||||
void asteroid_obj_list_init()
|
||||
static void asteroid_obj_list_init()
|
||||
{
|
||||
int i;
|
||||
|
||||
@@ -101,7 +101,7 @@ void asteroid_obj_list_init()
|
||||
* Add a node from the Asteroid_obj_list.
|
||||
* Only called from ::weapon_create()
|
||||
*/
|
||||
int asteroid_obj_list_add(int objnum)
|
||||
static int asteroid_obj_list_add(int objnum)
|
||||
{
|
||||
int index;
|
||||
|
||||
@@ -123,7 +123,7 @@ int asteroid_obj_list_add(int objnum)
|
||||
* Remove a node from the Asteroid_obj_list.
|
||||
* Only called from ::weapon_delete()
|
||||
*/
|
||||
void asteroid_obj_list_remove(object * obj)
|
||||
static void asteroid_obj_list_remove(object * obj)
|
||||
{
|
||||
int index = obj->instance;
|
||||
|
||||
@@ -138,7 +138,7 @@ void asteroid_obj_list_remove(object * obj)
|
||||
/**
|
||||
* Prevent speed from getting too huge so it's hard to catch up to an asteroid.
|
||||
*/
|
||||
float asteroid_cap_speed(int asteroid_info_index, float speed)
|
||||
static float asteroid_cap_speed(int asteroid_info_index, float speed)
|
||||
{
|
||||
float max, double_max;
|
||||
|
||||
@@ -164,7 +164,7 @@ float asteroid_cap_speed(int asteroid_info_index, float speed)
|
||||
* Sum together the following: 1 inside x, 2 inside y, 4 inside z
|
||||
* inside only when sum = 7
|
||||
*/
|
||||
int asteroid_in_inner_bound_with_axes(asteroid_field *asfieldp, vec3d *pos, float delta)
|
||||
static int asteroid_in_inner_bound_with_axes(asteroid_field *asfieldp, vec3d *pos, float delta)
|
||||
{
|
||||
Assert(asfieldp->has_inner_bound);
|
||||
|
||||
@@ -188,7 +188,7 @@ int asteroid_in_inner_bound_with_axes(asteroid_field *asfieldp, vec3d *pos, floa
|
||||
* Check if asteroid is within inner bound
|
||||
* @return 0 if not inside or no inner bound, 1 if inside inner bound
|
||||
*/
|
||||
int asteroid_in_inner_bound(asteroid_field *asfieldp, vec3d *pos, float delta) {
|
||||
static int asteroid_in_inner_bound(asteroid_field *asfieldp, vec3d *pos, float delta) {
|
||||
|
||||
if (!asfieldp->has_inner_bound) {
|
||||
return 0;
|
||||
@@ -202,7 +202,7 @@ int asteroid_in_inner_bound(asteroid_field *asfieldp, vec3d *pos, float delta) {
|
||||
*
|
||||
* Moves to the other side of the inner box a distance delta from edge of box
|
||||
*/
|
||||
void inner_bound_pos_fixup(asteroid_field *asfieldp, vec3d *pos)
|
||||
static void inner_bound_pos_fixup(asteroid_field *asfieldp, vec3d *pos)
|
||||
{
|
||||
if (!asteroid_in_inner_bound(asfieldp, pos, 0)) {
|
||||
return;
|
||||
@@ -446,7 +446,7 @@ void asteroid_sub_create(object *parent_objp, int asteroid_type, vec3d *relvec)
|
||||
/**
|
||||
* Load in an asteroid model
|
||||
*/
|
||||
void asteroid_load(int asteroid_info_index, int asteroid_subtype)
|
||||
static void asteroid_load(int asteroid_info_index, int asteroid_subtype)
|
||||
{
|
||||
int i;
|
||||
asteroid_info *asip;
|
||||
@@ -487,26 +487,12 @@ void asteroid_load(int asteroid_info_index, int asteroid_subtype)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Randomly choose a debris model within the current group
|
||||
*/
|
||||
int get_debris_from_same_group(int index) {
|
||||
int group_base, group_offset;
|
||||
|
||||
group_base = (index / NUM_DEBRIS_SIZES) * NUM_DEBRIS_SIZES;
|
||||
group_offset = index - group_base;
|
||||
|
||||
// group base + offset
|
||||
// offset is formed by adding 1 or 2 (since 3 in model group) and mapping back in the 0-2 range
|
||||
return group_base + ((group_offset + rand()%(NUM_DEBRIS_SIZES-1) + 1) % NUM_DEBRIS_SIZES);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a weight that depends on asteroid size.
|
||||
*
|
||||
* The weight is then used to determine the frequencty of different sizes of ship debris
|
||||
*/
|
||||
int get_debris_weight(int ship_debris_index)
|
||||
static int get_debris_weight(int ship_debris_index)
|
||||
{
|
||||
int size = ship_debris_index % NUM_DEBRIS_SIZES;
|
||||
switch (size)
|
||||
@@ -626,7 +612,7 @@ void asteroid_create_all()
|
||||
}
|
||||
|
||||
/**
|
||||
* Init asteriod system for the level, called from ::game_level_init()
|
||||
* Init asteroid system for the level, called from ::game_level_init()
|
||||
*/
|
||||
void asteroid_level_init()
|
||||
{
|
||||
@@ -645,7 +631,7 @@ void asteroid_level_init()
|
||||
*
|
||||
* @return !0 if asteroid should be wrapped, 0 otherwise.
|
||||
*/
|
||||
int asteroid_should_wrap(object *objp, asteroid_field *asfieldp)
|
||||
static int asteroid_should_wrap(object *objp, asteroid_field *asfieldp)
|
||||
{
|
||||
if ( MULTIPLAYER_CLIENT )
|
||||
return 0;
|
||||
@@ -690,7 +676,7 @@ int asteroid_should_wrap(object *objp, asteroid_field *asfieldp)
|
||||
/**
|
||||
* Wrap an asteroid from one end of the asteroid field to the other
|
||||
*/
|
||||
void asteroid_wrap_pos(object *objp, asteroid_field *asfieldp)
|
||||
static void asteroid_wrap_pos(object *objp, asteroid_field *asfieldp)
|
||||
{
|
||||
if (objp->pos.xyz.x < asfieldp->min_bound.xyz.x) {
|
||||
objp->pos.xyz.x = asfieldp->max_bound.xyz.x + (objp->pos.xyz.x - asfieldp->min_bound.xyz.x);
|
||||
@@ -727,7 +713,7 @@ void asteroid_wrap_pos(object *objp, asteroid_field *asfieldp)
|
||||
*
|
||||
* @return !0 if this asteroid is a target for any ship, otherwise return 0
|
||||
*/
|
||||
int asteroid_is_targeted(object *objp)
|
||||
static int asteroid_is_targeted(object *objp)
|
||||
{
|
||||
ship_obj *so;
|
||||
object *ship_objp;
|
||||
@@ -748,7 +734,7 @@ int asteroid_is_targeted(object *objp)
|
||||
/**
|
||||
* Create an asteroid that will hit object *objp in delta_time seconds
|
||||
*/
|
||||
void asteroid_aim_at_target(object *objp, object *asteroid_objp, float delta_time)
|
||||
static void asteroid_aim_at_target(object *objp, object *asteroid_objp, float delta_time)
|
||||
{
|
||||
vec3d predicted_center_pos;
|
||||
vec3d rand_vec;
|
||||
@@ -776,7 +762,7 @@ void asteroid_aim_at_target(object *objp, object *asteroid_objp, float delta_tim
|
||||
*
|
||||
* @param count asteroids already targeted on
|
||||
*/
|
||||
void maybe_throw_asteroid(int count)
|
||||
static void maybe_throw_asteroid(int count)
|
||||
{
|
||||
if (!timestamp_elapsed(Next_asteroid_throw)) {
|
||||
return;
|
||||
@@ -850,7 +836,7 @@ void asteroid_delete( object * obj )
|
||||
* See if we should reposition the asteroid.
|
||||
* Only reposition if oustide the bounding volume and the player isn't looking towards the asteroid.
|
||||
*/
|
||||
void asteroid_maybe_reposition(object *objp, asteroid_field *asfieldp)
|
||||
static void asteroid_maybe_reposition(object *objp, asteroid_field *asfieldp)
|
||||
{
|
||||
// passive field does not wrap
|
||||
if (asfieldp->field_type == FT_PASSIVE) {
|
||||
@@ -903,7 +889,7 @@ void asteroid_maybe_reposition(object *objp, asteroid_field *asfieldp)
|
||||
}
|
||||
}
|
||||
|
||||
void lerp(float *goal, float f1, float f2, float scale)
|
||||
static void lerp(float *goal, float f1, float f2, float scale)
|
||||
{
|
||||
*goal = (f2 - f1) * scale + f1;
|
||||
}
|
||||
@@ -1207,7 +1193,7 @@ void asteroid_render(object * obj, model_draw_list *scene)
|
||||
/**
|
||||
* Create a normalized vector generally in the direction from *hitpos to other_obj->pos
|
||||
*/
|
||||
void asc_get_relvec(vec3d *relvec, object *other_obj, vec3d *hitpos)
|
||||
static void asc_get_relvec(vec3d *relvec, object *other_obj, vec3d *hitpos)
|
||||
{
|
||||
vec3d tvec, rand_vec;
|
||||
int count = 0;
|
||||
@@ -1229,7 +1215,7 @@ void asc_get_relvec(vec3d *relvec, object *other_obj, vec3d *hitpos)
|
||||
/**
|
||||
* Return multiplier on asteroid radius for fireball
|
||||
*/
|
||||
float asteroid_get_fireball_scale_multiplier(int num)
|
||||
static float asteroid_get_fireball_scale_multiplier(int num)
|
||||
{
|
||||
if (Asteroids[num].flags & AF_USED) {
|
||||
asteroid_info *asip = &Asteroid_info[Asteroids[num].asteroid_type];
|
||||
@@ -1258,7 +1244,7 @@ float asteroid_get_fireball_scale_multiplier(int num)
|
||||
* Create asteroid explosion
|
||||
* @return expected time for explosion anim to last, in seconds
|
||||
*/
|
||||
float asteroid_create_explosion(object *objp)
|
||||
static float asteroid_create_explosion(object *objp)
|
||||
{
|
||||
int fireball_objnum;
|
||||
float explosion_life, fireball_scale_multiplier;
|
||||
@@ -1290,23 +1276,23 @@ float asteroid_create_explosion(object *objp)
|
||||
/**
|
||||
* Play sound when asteroid explodes
|
||||
*/
|
||||
void asteriod_explode_sound(object *objp, int type, int play_loud)
|
||||
static void asteroid_explode_sound(object *objp, int type, int play_loud)
|
||||
{
|
||||
int sound_index = -1;
|
||||
gamesnd_id sound_index;
|
||||
float range_factor = 1.0f; // how many times sound should traver farther than normal
|
||||
|
||||
if (type % NUM_DEBRIS_SIZES <= 1)
|
||||
{
|
||||
sound_index = SND_ASTEROID_EXPLODE_SMALL;
|
||||
sound_index = gamesnd_id(GameSounds::ASTEROID_EXPLODE_SMALL);
|
||||
range_factor = 5.0;
|
||||
}
|
||||
else
|
||||
{
|
||||
sound_index = SND_ASTEROID_EXPLODE_LARGE;
|
||||
sound_index = gamesnd_id(GameSounds::ASTEROID_EXPLODE_LARGE);
|
||||
range_factor = 10.0f;
|
||||
}
|
||||
|
||||
Assert(sound_index != -1);
|
||||
Assert(sound_index.isValid());
|
||||
|
||||
if ( !play_loud ) {
|
||||
range_factor = 1.0f;
|
||||
@@ -1318,9 +1304,9 @@ void asteriod_explode_sound(object *objp, int type, int play_loud)
|
||||
/**
|
||||
* Do the area effect for an asteroid exploding
|
||||
*
|
||||
* @param asteroid_objp object pointer to asteriod causing explosion
|
||||
* @param asteroid_objp object pointer to asteroid causing explosion
|
||||
*/
|
||||
void asteroid_do_area_effect(object *asteroid_objp)
|
||||
static void asteroid_do_area_effect(object *asteroid_objp)
|
||||
{
|
||||
object *ship_objp;
|
||||
float damage, blast;
|
||||
@@ -1382,7 +1368,7 @@ void asteroid_hit( object * pasteroid_obj, object * other_obj, vec3d * hitpos, f
|
||||
|
||||
explosion_life = asteroid_create_explosion(pasteroid_obj);
|
||||
|
||||
asteriod_explode_sound(pasteroid_obj, asp->asteroid_type, play_loud_collision);
|
||||
asteroid_explode_sound(pasteroid_obj, asp->asteroid_type, play_loud_collision);
|
||||
asteroid_do_area_effect(pasteroid_obj);
|
||||
|
||||
asp->final_death_time = timestamp( fl2i(explosion_life*1000.0f)/5 ); // Wait till 30% of vclip time before breaking the asteroid up.
|
||||
@@ -1401,7 +1387,7 @@ void asteroid_hit( object * pasteroid_obj, object * other_obj, vec3d * hitpos, f
|
||||
weapon_info *wip;
|
||||
wip = &Weapon_info[Weapons[other_obj->instance].weapon_info_index];
|
||||
// If the weapon didn't play any impact animation, play custom asteroid impact animation
|
||||
if ( wip->impact_weapon_expl_effect < 0 ) {
|
||||
if (!wip->impact_weapon_expl_effect.isValid()) {
|
||||
particle::create( hitpos, &vmd_zero_vector, 0.0f, Asteroid_impact_explosion_radius, particle::PARTICLE_BITMAP, Asteroid_impact_explosion_ani );
|
||||
}
|
||||
}
|
||||
@@ -1432,35 +1418,6 @@ void asteroid_level_close()
|
||||
DCF_BOOL2(asteroids, Asteroids_enabled, "enables or disables asteroids", "Usage: asteroids [bool]\nTurns asteroid system on/off. If nothing passed, then toggles it.\n");
|
||||
|
||||
|
||||
void hud_target_asteroid()
|
||||
{
|
||||
int i;
|
||||
int start_index = 0, end_index = MAX_ASTEROIDS;
|
||||
|
||||
if (Player_ai->target_objnum != -1) {
|
||||
if (Objects[Player_ai->target_objnum].type == OBJ_ASTEROID) {
|
||||
start_index = Objects[Player_ai->target_objnum].instance+1;
|
||||
end_index = start_index-1;
|
||||
if (end_index < 0)
|
||||
end_index = MAX_ASTEROIDS;
|
||||
}
|
||||
}
|
||||
|
||||
i = start_index;
|
||||
while (i != end_index) {
|
||||
if (i == MAX_ASTEROIDS)
|
||||
i = 0;
|
||||
|
||||
if (Asteroids[i].flags & AF_USED) {
|
||||
Assert(Objects[Asteroids[i].objnum].type == OBJ_ASTEROID);
|
||||
set_target_objnum( Player_ai, Asteroids[i].objnum);
|
||||
break;
|
||||
}
|
||||
|
||||
i++;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the number of active asteroids
|
||||
*/
|
||||
@@ -1473,7 +1430,7 @@ int asteroid_count()
|
||||
* See if asteroid should split up.
|
||||
* We delay splitting up to allow the explosion animation to play for a bit.
|
||||
*/
|
||||
void asteroid_maybe_break_up(object *pasteroid_obj)
|
||||
static void asteroid_maybe_break_up(object *pasteroid_obj)
|
||||
{
|
||||
asteroid *asp;
|
||||
asteroid_info *asip;
|
||||
@@ -1595,26 +1552,7 @@ void asteroid_maybe_break_up(object *pasteroid_obj)
|
||||
}
|
||||
}
|
||||
|
||||
int asteroid_get_random_in_cone(vec3d *pos, vec3d *dir, float ang, int danger)
|
||||
{
|
||||
int idx;
|
||||
vec3d asteroid_dir;
|
||||
|
||||
// just pick the first asteroid which satisfies our condition
|
||||
for(idx=0; idx<Num_asteroids; idx++){
|
||||
vm_vec_sub(&asteroid_dir, &Objects[Asteroids[idx].objnum].pos, pos);
|
||||
vm_vec_normalize_quick(&asteroid_dir);
|
||||
|
||||
// if it satisfies the condition
|
||||
if(vm_vec_dot(dir, &asteroid_dir) >= ang){
|
||||
return idx;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
void asteroid_test_collide(object *pasteroid_obj, object *pship_obj, mc_info *mc, bool lazy = false)
|
||||
static void asteroid_test_collide(object *pasteroid_obj, object *pship_obj, mc_info *mc, bool lazy = false)
|
||||
{
|
||||
float asteroid_ray_dist;
|
||||
vec3d asteroid_fvec, terminus;
|
||||
@@ -1656,7 +1594,7 @@ void asteroid_test_collide(object *pasteroid_obj, object *pship_obj, mc_info *mc
|
||||
*
|
||||
* @return !0 if the asteroid will collide with the escort
|
||||
*/
|
||||
int asteroid_will_collide(object *pasteroid_obj, object *escort_objp)
|
||||
static int asteroid_will_collide(object *pasteroid_obj, object *escort_objp)
|
||||
{
|
||||
mc_info mc;
|
||||
mc_info_init(&mc);
|
||||
@@ -1674,7 +1612,7 @@ int asteroid_will_collide(object *pasteroid_obj, object *escort_objp)
|
||||
* Warn if asteroid on collision path with ship
|
||||
* @return !0 if we should warn about asteroid hitting ship, otherwise return 0
|
||||
*/
|
||||
int asteroid_valid_ship_to_warn_collide(ship *shipp)
|
||||
static int asteroid_valid_ship_to_warn_collide(ship *shipp)
|
||||
{
|
||||
if ( !(Ship_info[shipp->ship_info_index].is_big_or_huge()) ) {
|
||||
return 0;
|
||||
@@ -1696,7 +1634,7 @@ int asteroid_valid_ship_to_warn_collide(ship *shipp)
|
||||
* See if asteroid will collide with a large ship on the escort list in the next
|
||||
* ASTEROID_MIN_COLLIDE_TIME seconds.
|
||||
*/
|
||||
void asteroid_update_collide_flag(object *asteroid_objp)
|
||||
static void asteroid_update_collide_flag(object *asteroid_objp)
|
||||
{
|
||||
int i, num_escorts, escort_objnum, will_collide=0;
|
||||
ship *escort_shipp;
|
||||
@@ -1735,7 +1673,7 @@ void asteroid_update_collide_flag(object *asteroid_objp)
|
||||
/**
|
||||
* Ensure that the collide objnum for the asteroid is still valid
|
||||
*/
|
||||
void asteroid_verify_collide_objnum(asteroid *asp)
|
||||
static void asteroid_verify_collide_objnum(asteroid *asp)
|
||||
{
|
||||
if ( asp->collide_objnum >= 0 ) {
|
||||
if ( Objects[asp->collide_objnum].signature != asp->collide_objsig ) {
|
||||
@@ -1815,7 +1753,7 @@ float asteroid_time_to_impact(object *asteroid_objp)
|
||||
/**
|
||||
* Read in a single asteroid section from asteroid.tbl
|
||||
*/
|
||||
void asteroid_parse_section(asteroid_info *asip)
|
||||
static void asteroid_parse_section(asteroid_info *asip)
|
||||
{
|
||||
required_string("$Name:");
|
||||
stuff_string(asip->name, F_NAME, NAME_LENGTH);
|
||||
@@ -1915,7 +1853,7 @@ to do with the debris of ships that explode, however these
|
||||
are the same debris and asteroids that get flung at a ship
|
||||
that is being protected.
|
||||
*/
|
||||
void asteroid_parse_tbl()
|
||||
static void asteroid_parse_tbl()
|
||||
{
|
||||
char impact_ani_file[MAX_FILENAME_LEN];
|
||||
|
||||
@@ -2066,7 +2004,7 @@ void asteroid_parse_tbl()
|
||||
/**
|
||||
* Return number of asteroids expected to collide with a ship.
|
||||
*/
|
||||
int count_incident_asteroids()
|
||||
static int count_incident_asteroids()
|
||||
{
|
||||
object *asteroid_objp;
|
||||
int count;
|
||||
@@ -2090,7 +2028,7 @@ int count_incident_asteroids()
|
||||
* Pick object to throw asteroids at.
|
||||
* Pick any capital or big ship inside the bounds of the asteroid field.
|
||||
*/
|
||||
int set_asteroid_throw_objnum()
|
||||
static int set_asteroid_throw_objnum()
|
||||
{
|
||||
if (Asteroid_field.num_initial_asteroids < 1)
|
||||
return -1;
|
||||
|
||||
@@ -163,7 +163,6 @@ int asteroid_collide_objnum(object *asteroid_objp);
|
||||
float asteroid_time_to_impact(object *asteroid_objp);
|
||||
void asteroid_show_brackets();
|
||||
void asteroid_target_closest_danger();
|
||||
int asteroid_get_random_in_cone(vec3d *pos, vec3d *dir, float ang, int danger = 0);
|
||||
|
||||
// need to extern for multiplayer
|
||||
void asteroid_sub_create(object *parent_objp, int asteroid_type, vec3d *relvec);
|
||||
|
||||
@@ -1231,7 +1231,7 @@ void send_autopilot_msg(char *msg, char *snd)
|
||||
audio_handle = -1;
|
||||
}
|
||||
|
||||
if (msg[0] != '\0' && strcmp(msg, "none"))
|
||||
if (msg[0] != '\0' && strcmp(msg, "none") != 0)
|
||||
change_message("autopilot builtin message", msg, -1, 0);
|
||||
|
||||
// load sound
|
||||
@@ -1246,7 +1246,7 @@ void send_autopilot_msg(char *msg, char *snd)
|
||||
audiostream_play(audio_handle, (Master_event_music_volume * aav_music_volume), 0);
|
||||
}
|
||||
|
||||
if (msg[0] != '\0' && strcmp(msg, "none"))
|
||||
if (msg[0] != '\0' && strcmp(msg, "none") != 0)
|
||||
message_training_queue("autopilot builtin message", timestamp(0), 5); // display message for five seconds
|
||||
}
|
||||
|
||||
|
||||
@@ -23,6 +23,16 @@
|
||||
|
||||
#include "bmpman/bmpman.h"
|
||||
|
||||
#include <array>
|
||||
|
||||
/**
|
||||
* @brief Container class for graphics API specific bitmap data
|
||||
*/
|
||||
class gr_bitmap_info {
|
||||
public:
|
||||
virtual ~gr_bitmap_info() = 0;
|
||||
};
|
||||
|
||||
union bm_extra_info {
|
||||
struct {
|
||||
// Stuff needed for animations
|
||||
@@ -90,17 +100,35 @@ struct bitmap_entry {
|
||||
#endif
|
||||
};
|
||||
|
||||
extern bitmap_entry* bm_bitmaps;
|
||||
struct bitmap_slot {
|
||||
bitmap_entry entry;
|
||||
|
||||
gr_bitmap_info* gr_info = nullptr;
|
||||
};
|
||||
|
||||
// image specific lock functions
|
||||
void bm_lock_ani( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_dds( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_png( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_apng( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_jpg( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_pcx( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_tga( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_user( int handle, int bitmapnum, bitmap_entry *be, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_ani( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_dds( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_png( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_apng( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_jpg( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_pcx( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_tga( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
void bm_lock_user( int handle, bitmap_slot *bs, bitmap *bmp, int bpp, ubyte flags );
|
||||
|
||||
const size_t BM_BLOCK_SIZE = 4096;
|
||||
|
||||
extern SCP_vector<std::array<bitmap_slot, BM_BLOCK_SIZE>> bm_blocks;
|
||||
|
||||
bitmap_slot* bm_get_slot(int handle, bool separate_ani_frames = true);
|
||||
|
||||
inline bitmap_entry* bm_get_entry(int handle, bool separate_ani_frames = true) {
|
||||
return &bm_get_slot(handle, separate_ani_frames)->entry;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T* bm_get_gr_info(int handle, bool separate_ani_frames = true) {
|
||||
return static_cast<T*>(bm_get_slot(handle, separate_ani_frames)->gr_info);
|
||||
}
|
||||
|
||||
#endif // __BM_INTERNAL_H__
|
||||
+732
-734
File diff suppressed because it is too large.
Load diff
+16
-49
@@ -32,23 +32,6 @@
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief How many bitmaps the game can handle by default
|
||||
*
|
||||
* @attention MAX_BITMAPS shouldn't need to be bumped again. With the fixed bm_release() and it's proper use even the
|
||||
* largest missions should stay under this number. With the largest retail missions and wasteful content we should
|
||||
* still have about 20% of the slots free. If it still goes over then it's something the artists need to fix.
|
||||
* For instance the Terran Mara fighter, with -spec and -glow and using the Shinepack, needs 117 bitmap slots alone.
|
||||
* 111 of those is just for the glowmaps. This number can be greatly reduced if the number of ani frames for another
|
||||
* LOD than LOD0 has fewer or no ani frames. A 37 frame glow ani for LOD2 is little more than a waste of resources.
|
||||
* Future reports of texture corruption should be initially approached with content as the cause and not code.
|
||||
* If anything we could/should reduce MAX_BITMAPS in the future. Where it's at now should accomidate even the
|
||||
* largest mods. -- Taylor
|
||||
*/
|
||||
#define DEFAULT_MAX_BITMAPS 4750
|
||||
|
||||
extern int MAX_BITMAPS;
|
||||
|
||||
// Flag positions for bitmap.flags
|
||||
// ***** NOTE: bitmap.flags is an 8-bit value, no more BMP_TEX_* flags can be added unless the type is changed!! ******
|
||||
#define BMP_AABITMAP (1<<0) //!< antialiased bitmap
|
||||
@@ -115,6 +98,10 @@ struct bitmap
|
||||
*/
|
||||
};
|
||||
|
||||
// Forward definition for the graphics API
|
||||
struct bitmap_entry;
|
||||
struct bitmap_slot;
|
||||
|
||||
extern size_t bm_texture_ram; //!< how many bytes of textures are used.
|
||||
|
||||
extern int Bm_paging; //!< Bool type that indicates if BMPMAN is currently paging.
|
||||
@@ -143,22 +130,6 @@ void bm_init();
|
||||
*/
|
||||
void bm_close();
|
||||
|
||||
/**
|
||||
* Gets the cache slot of the bitmap indexed by handle.
|
||||
*
|
||||
* @details if the bitmap is an ani, gets the first frame
|
||||
*
|
||||
* @returns The cache slot index of the bitmap if handle is valid
|
||||
*
|
||||
* @note If the handle is invalid, an Assert() fails
|
||||
*/
|
||||
int bm_get_cache_slot(int bitmap_id, int separate_ani_frames);
|
||||
|
||||
/**
|
||||
* @brief Gets the next available bitmap slot.
|
||||
*/
|
||||
int bm_get_next_handle();
|
||||
|
||||
#define BMP_FLAG_RENDER_TARGET_STATIC (1<<0)
|
||||
#define BMP_FLAG_RENDER_TARGET_DYNAMIC (1<<1)
|
||||
#define BMP_FLAG_CUBEMAP (1<<2)
|
||||
@@ -412,13 +383,6 @@ void bm_get_filename(int bitmapnum, char *filename);
|
||||
*/
|
||||
const char *bm_get_filename(int handle);
|
||||
|
||||
/**
|
||||
* @brief Loads all data for all bitmaps that have been requested to be loaded
|
||||
*
|
||||
* @note This function is not defined.
|
||||
*/
|
||||
void bm_gfx_load_all();
|
||||
|
||||
/**
|
||||
* @brief Unloads all used bitmaps, should only ever be called by game_shutdown()
|
||||
*
|
||||
@@ -437,15 +401,6 @@ void bm_unload_all();
|
||||
*/
|
||||
void bm_get_palette(int handle, ubyte *pal, char *name);
|
||||
|
||||
/**
|
||||
* @brief Hack to get a pixel from a bitmap
|
||||
*
|
||||
* @details only works good in 8bpp mode
|
||||
*
|
||||
* @note This function is not defined.
|
||||
*/
|
||||
void bm_gfx_get_pixel(int bitmap, float u, float v, ubyte *r, ubyte *g, ubyte *b);
|
||||
|
||||
/**
|
||||
* @brief (DEBUG) Gets memory size, in bytes, of the locked bitmaps
|
||||
*
|
||||
@@ -741,6 +696,18 @@ int bm_get_array_index(const int handle);
|
||||
*/
|
||||
int bmpman_count_bitmaps();
|
||||
|
||||
/**
|
||||
* @brief Counts how many slots are available to the bmpman system
|
||||
*
|
||||
* Since the number of slots is dynamic now, this should be used for determining the total amount of available slots at
|
||||
* the moment.
|
||||
*
|
||||
* @warning This is entirely for debugging and logging purposes. It should not be used in actual engine code.
|
||||
*
|
||||
* @return The number of available slots
|
||||
*/
|
||||
int bmpman_count_available_slots();
|
||||
|
||||
/**
|
||||
* @brief Checks if the given filename is a valid effect or texture file name
|
||||
*
|
||||
|
||||
@@ -245,12 +245,12 @@ void camera::set_rotation_facing(vec3d *in_target, float in_rotation_time, float
|
||||
set_rotation(&temp_matrix, in_rotation_time, in_rotation_acceleration_time, in_rotation_deceleration_time);
|
||||
}
|
||||
|
||||
void camera::set_rotation_velocity(angles *in_rotation_rate, float in_acceleration_time)
|
||||
void camera::set_rotation_velocity(angles * /*in_rotation_rate*/, float /*in_acceleration_time*/)
|
||||
{
|
||||
Error(LOCATION, "This function is disabled until further notice.");
|
||||
}
|
||||
|
||||
void camera::do_frame(float in_frametime)
|
||||
void camera::do_frame(float /*in_frametime*/)
|
||||
{
|
||||
|
||||
}
|
||||
@@ -802,7 +802,7 @@ void subtitle::clone(const subtitle &sub)
|
||||
post_shaded = sub.post_shaded;
|
||||
}
|
||||
|
||||
const subtitle &subtitle::operator=(const subtitle &sub)
|
||||
subtitle& subtitle::operator=(const subtitle &sub)
|
||||
{
|
||||
if (this != &sub) {
|
||||
if (image_id != -1) {
|
||||
|
||||
@@ -143,7 +143,7 @@ public:
|
||||
~subtitle();
|
||||
|
||||
subtitle(const subtitle &sub) { clone(sub); }
|
||||
const subtitle &operator=(const subtitle &sub);
|
||||
subtitle& operator=(const subtitle &sub);
|
||||
|
||||
void do_frame(float frametime);
|
||||
bool is_post_shaded( ) { return post_shaded; }
|
||||
|
||||
+42
-48
@@ -10,10 +10,10 @@
|
||||
|
||||
#define _CFILE_INTERNAL
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <errno.h>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <cstdio>
|
||||
#include <cerrno>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#ifdef _WIN32
|
||||
@@ -33,21 +33,21 @@
|
||||
#include "cfile/cfilesystem.h"
|
||||
#include "osapi/osapi.h"
|
||||
#include "parse/encrypt.h"
|
||||
#include "cfilesystem.h"
|
||||
|
||||
|
||||
#include <limits>
|
||||
|
||||
char Cfile_root_dir[CFILE_ROOT_DIRECTORY_LEN] = "";
|
||||
char Cfile_user_dir[CFILE_ROOT_DIRECTORY_LEN] = "";
|
||||
#ifdef SCP_UNIX
|
||||
char Cfile_user_dir_legacy[CFILE_ROOT_DIRECTORY_LEN] = "";
|
||||
#endif
|
||||
|
||||
// During cfile_init, verify that Pathtypes[n].index == n for each item
|
||||
// Each path must have a valid parent that can be tracable all the way back to the root
|
||||
// Each path must have a valid parent that can be tracable all the way back to the root
|
||||
// so that we can create directories when we need to.
|
||||
//
|
||||
// Please make sure extensions are all lower-case, or we'll break unix compatibility
|
||||
//
|
||||
// clang-format off
|
||||
cf_pathtype Pathtypes[CF_MAX_PATH_TYPES] = {
|
||||
// What type this is Path Extensions Parent type
|
||||
{ CF_TYPE_INVALID, NULL, NULL, CF_TYPE_INVALID },
|
||||
@@ -69,7 +69,7 @@ cf_pathtype Pathtypes[CF_MAX_PATH_TYPES] = {
|
||||
{ CF_TYPE_VOICE_SPECIAL, "data" DIR_SEPARATOR_STR "voice" DIR_SEPARATOR_STR "special", ".wav .ogg", CF_TYPE_VOICE },
|
||||
{ CF_TYPE_VOICE_TRAINING, "data" DIR_SEPARATOR_STR "voice" DIR_SEPARATOR_STR "training", ".wav .ogg", CF_TYPE_VOICE },
|
||||
{ CF_TYPE_MUSIC, "data" DIR_SEPARATOR_STR "music", ".wav .ogg", CF_TYPE_DATA },
|
||||
{ CF_TYPE_MOVIES, "data" DIR_SEPARATOR_STR "movies", ".mve .msb .ogg .mp4", CF_TYPE_DATA },
|
||||
{ CF_TYPE_MOVIES, "data" DIR_SEPARATOR_STR "movies", ".mve .msb .ogg .mp4 .srt .webm .png",CF_TYPE_DATA },
|
||||
{ CF_TYPE_INTERFACE, "data" DIR_SEPARATOR_STR "interface", ".pcx .ani .dds .tga .eff .png .jpg", CF_TYPE_DATA },
|
||||
{ CF_TYPE_FONT, "data" DIR_SEPARATOR_STR "fonts", ".vf .ttf", CF_TYPE_DATA },
|
||||
{ CF_TYPE_EFFECTS, "data" DIR_SEPARATOR_STR "effects", ".ani .eff .pcx .neb .tga .jpg .png .dds .sdr", CF_TYPE_DATA },
|
||||
@@ -90,7 +90,7 @@ cf_pathtype Pathtypes[CF_MAX_PATH_TYPES] = {
|
||||
{ CF_TYPE_FICTION, "data" DIR_SEPARATOR_STR "fiction", ".txt", CF_TYPE_DATA },
|
||||
{ CF_TYPE_FREDDOCS, "data" DIR_SEPARATOR_STR "freddocs", ".html", CF_TYPE_DATA },
|
||||
};
|
||||
|
||||
// clang-format on
|
||||
|
||||
#define CFILE_STACK_MAX 8
|
||||
|
||||
@@ -224,14 +224,8 @@ int cfile_init(const char *exe_dir, const char *cdrom_dir)
|
||||
cfile_chdir(buf);
|
||||
|
||||
// set root directory
|
||||
strncpy(Cfile_root_dir, buf, CFILE_ROOT_DIRECTORY_LEN-1);
|
||||
strncpy(Cfile_user_dir, os_get_config_path().c_str(), CFILE_ROOT_DIRECTORY_LEN-1);
|
||||
|
||||
#ifdef SCP_UNIX
|
||||
// Initialize path of old pilot files
|
||||
extern const char* Osreg_user_dir_legacy;
|
||||
snprintf(Cfile_user_dir_legacy, CFILE_ROOT_DIRECTORY_LEN-1, "%s/%s/", getenv("HOME"), Osreg_user_dir_legacy);
|
||||
#endif
|
||||
strcpy_s(Cfile_root_dir, buf);
|
||||
strcpy_s(Cfile_user_dir, os_get_config_path().c_str());
|
||||
|
||||
for (i = 0; i < MAX_CFILE_BLOCKS; i++) {
|
||||
Cfile_block_list[i].type = CFILE_BLOCK_UNUSED;
|
||||
@@ -356,8 +350,7 @@ int cfile_push_chdir(int type)
|
||||
return -1;
|
||||
}
|
||||
|
||||
strncpy(Cfile_stack[Cfile_stack_pos++], OriginalDirectory,
|
||||
CFILE_ROOT_DIRECTORY_LEN - 1);
|
||||
strcpy_s(Cfile_stack[Cfile_stack_pos++], OriginalDirectory);
|
||||
|
||||
cf_create_default_path_string(dir, sizeof(dir) - 1, type, NULL);
|
||||
|
||||
@@ -467,7 +460,7 @@ char *cf_add_ext(const char *filename, const char *ext)
|
||||
size_t elen = strlen(ext);
|
||||
Assert(flen < MAX_PATH_LEN);
|
||||
strcpy_s(path, filename);
|
||||
if ((flen < 4) || stricmp(path + flen - elen, ext)) {
|
||||
if ((flen < 4) || stricmp(path + flen - elen, ext) != 0) {
|
||||
Assert(flen + elen < MAX_PATH_LEN);
|
||||
strcat_s(path, ext);
|
||||
}
|
||||
@@ -480,17 +473,17 @@ char *cf_add_ext(const char *filename, const char *ext)
|
||||
*
|
||||
* @param filename Name of file to delete
|
||||
* @param path_type Path type (CF_TYPE_xxx)
|
||||
* @param location_flags Where to search for the location of the file to delete
|
||||
*
|
||||
* @return 0 on failure, 1 on success
|
||||
*/
|
||||
int cf_delete(const char *filename, int path_type)
|
||||
int cf_delete(const char *filename, int path_type, uint32_t location_flags)
|
||||
{
|
||||
char longname[MAX_PATH_LEN];
|
||||
|
||||
Assert(CF_TYPE_SPECIFIED(path_type));
|
||||
|
||||
cf_create_default_path_string(longname, sizeof(longname) - 1,
|
||||
path_type, filename);
|
||||
cf_create_default_path_string(longname, sizeof(longname) - 1, path_type, filename, false, location_flags);
|
||||
|
||||
return (_unlink(longname) != -1);
|
||||
}
|
||||
@@ -516,12 +509,12 @@ int cf_access(const char *filename, int dir_type, int mode)
|
||||
// If offset equates to boolean true, it was found in a VP and the logic will negate the function return
|
||||
int cf_exists(const char *filename, int dir_type)
|
||||
{
|
||||
size_t offset = 1;
|
||||
|
||||
if ( (filename == NULL) || !strlen(filename) )
|
||||
return 0;
|
||||
|
||||
return (cf_find_file_location(filename, dir_type, 0, NULL, NULL, &offset) && !offset);
|
||||
auto find_res = cf_find_file_location(filename, dir_type);
|
||||
|
||||
return find_res.found && !find_res.offset;
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
@@ -532,7 +525,7 @@ int cf_exists_full(const char *filename, int dir_type)
|
||||
if ( (filename == NULL) || !strlen(filename) )
|
||||
return 0;
|
||||
|
||||
return cf_find_file_location(filename, dir_type, 0, NULL, NULL, NULL);
|
||||
return cf_find_file_location(filename, dir_type).found;
|
||||
}
|
||||
|
||||
// same as the above, but with extension check
|
||||
@@ -544,7 +537,7 @@ int cf_exists_full_ext(const char *filename, int dir_type, const int num_ext, co
|
||||
if ( (num_ext <= 0) || (ext_list == NULL) )
|
||||
return 0;
|
||||
|
||||
return (cf_find_file_location_ext(filename, num_ext, ext_list, dir_type, 0, NULL, NULL, NULL) != -1);
|
||||
return cf_find_file_location_ext(filename, num_ext, ext_list, dir_type).found;
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
@@ -561,7 +554,7 @@ void cf_attrib(const char *filename, int set, int clear, int dir_type)
|
||||
fclose(fp);
|
||||
|
||||
DWORD z = GetFileAttributes(longname);
|
||||
SetFileAttributes(longname, z | set & ~clear);
|
||||
SetFileAttributes(longname, z | (set & ~clear));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -618,7 +611,7 @@ static void mkdir_recursive(const char *path) {
|
||||
|
||||
// Creates the directory path if it doesn't exist. Even creates all its
|
||||
// parent paths.
|
||||
void cf_create_directory( int dir_type )
|
||||
void cf_create_directory(int dir_type, uint32_t location_flags)
|
||||
{
|
||||
int num_dirs = 0;
|
||||
int dir_tree[CF_MAX_PATH_TYPES];
|
||||
@@ -640,7 +633,7 @@ void cf_create_directory( int dir_type )
|
||||
int i;
|
||||
|
||||
for (i=num_dirs-1; i>=0; i-- ) {
|
||||
cf_create_default_path_string( longname, sizeof(longname)-1, dir_tree[i], NULL );
|
||||
cf_create_default_path_string(longname, sizeof(longname) - 1, dir_tree[i], nullptr, false, location_flags);
|
||||
if (stat(longname, &statbuf) != 0) {
|
||||
mprintf(( "CFILE: Creating new directory '%s'\n", longname ));
|
||||
mkdir_recursive(longname);
|
||||
@@ -667,14 +660,13 @@ extern int game_cd_changed();
|
||||
// error ==> NULL
|
||||
//
|
||||
|
||||
CFILE *_cfopen(const char* source, int line, const char *file_path, const char *mode, int type, int dir_type, bool localize)
|
||||
CFILE* _cfopen(const char* source, int line, const char* file_path, const char* mode, int type, int dir_type,
|
||||
bool localize, uint32_t location_flags)
|
||||
{
|
||||
/* Bobboau, what is this doing here? 31 is way too short... - Goober5000
|
||||
if( strlen(file_path) > 31 )
|
||||
Error(LOCATION, "file name %s too long, \nmust be less than 31 charicters", file_path);*/
|
||||
|
||||
char longname[_MAX_PATH];
|
||||
|
||||
if ( !cfile_inited ) {
|
||||
Int3();
|
||||
return NULL;
|
||||
@@ -686,7 +678,7 @@ CFILE *_cfopen(const char* source, int line, const char *file_path, const char *
|
||||
Assert( mode != NULL );
|
||||
|
||||
// Can only open read-only binary files in memory mapped mode.
|
||||
if ( (type & CFILE_MEMORY_MAPPED) && strcmp(mode,"rb") ) {
|
||||
if ( (type & CFILE_MEMORY_MAPPED) && strcmp(mode,"rb") != 0 ) {
|
||||
Int3();
|
||||
return NULL;
|
||||
}
|
||||
@@ -696,6 +688,8 @@ CFILE *_cfopen(const char* source, int line, const char *file_path, const char *
|
||||
// the harddisk. No fancy packfile stuff here!
|
||||
|
||||
if ( strchr(mode,'w') || strchr(mode,'+') || strchr(mode,'a') ) {
|
||||
char longname[_MAX_PATH];
|
||||
|
||||
// For write-only files, require a full path or a path type
|
||||
#ifdef SCP_UNIX
|
||||
if ( strpbrk(file_path, "/") ) {
|
||||
@@ -709,9 +703,9 @@ CFILE *_cfopen(const char* source, int line, const char *file_path, const char *
|
||||
Assert( dir_type != CF_TYPE_ANY );
|
||||
|
||||
// Create the directory if necessary
|
||||
cf_create_directory( dir_type );
|
||||
cf_create_directory(dir_type, location_flags);
|
||||
|
||||
cf_create_default_path_string( longname, sizeof(longname)-1, dir_type, file_path );
|
||||
cf_create_default_path_string(longname, sizeof(longname) - 1, dir_type, file_path, false, location_flags);
|
||||
}
|
||||
Assert( !(type & CFILE_MEMORY_MAPPED) );
|
||||
|
||||
@@ -761,30 +755,29 @@ CFILE *_cfopen(const char* source, int line, const char *file_path, const char *
|
||||
//================================================
|
||||
// Search for file on disk, on cdrom, or in a packfile
|
||||
|
||||
size_t offset, size;
|
||||
char copy_file_path[MAX_PATH_LEN]; // FIX change in memory from cf_find_file_location
|
||||
strcpy_s(copy_file_path, file_path);
|
||||
|
||||
const void* file_data = nullptr;
|
||||
if ( cf_find_file_location( copy_file_path, dir_type, sizeof(longname) - 1, longname, &size, &offset, localize, &file_data ) ) {
|
||||
auto find_res = cf_find_file_location( copy_file_path, dir_type, localize, location_flags );
|
||||
if ( find_res.found ) {
|
||||
|
||||
// Fount it, now create a cfile out of it
|
||||
nprintf(("CFileDebug", "Requested file %s found at: %s\n", file_path, longname));
|
||||
|
||||
nprintf(("CFileDebug", "Requested file %s found at: %s\n", file_path, find_res.full_name.c_str()));
|
||||
|
||||
if ( type & CFILE_MEMORY_MAPPED ) {
|
||||
|
||||
// Can't open memory mapped files out of pack or memory files
|
||||
if ( offset == 0 && file_data != nullptr ) {
|
||||
if ( find_res.offset == 0 && find_res.data_ptr != nullptr ) {
|
||||
#if defined _WIN32
|
||||
HANDLE hFile;
|
||||
|
||||
hFile = CreateFile(longname, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
|
||||
hFile = CreateFile(find_res.full_name.c_str(), GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
|
||||
|
||||
if (hFile != INVALID_HANDLE_VALUE) {
|
||||
return cf_open_mapped_fill_cfblock(source, line, hFile, dir_type);
|
||||
}
|
||||
#elif defined SCP_UNIX
|
||||
FILE *fp = fopen( longname, "rb" );
|
||||
FILE* fp = fopen(find_res.full_name.c_str(), "rb");
|
||||
if (fp) {
|
||||
return cf_open_mapped_fill_cfblock(source, line, fp, dir_type);
|
||||
}
|
||||
@@ -793,7 +786,8 @@ CFILE *_cfopen(const char* source, int line, const char *file_path, const char *
|
||||
|
||||
} else {
|
||||
// since cfopen_special already has all the code to handle the opening we can just use that here
|
||||
return _cfopen_special(source, line, longname, mode, size, offset, file_data, dir_type);
|
||||
return _cfopen_special(source, line, find_res.full_name.c_str(), mode, find_res.size, find_res.offset,
|
||||
find_res.data_ptr, dir_type);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -901,7 +895,7 @@ static int cfget_cfile_block()
|
||||
mprintf(("Out of cfile blocks! Currently opened files:\n"));
|
||||
dump_opened_files();
|
||||
|
||||
Assertion(false, "There are no more free cfile blocks. This means that there are too many files opened by FSO.\n"
|
||||
UNREACHABLE("There are no more free cfile blocks. This means that there are too many files opened by FSO.\n"
|
||||
"This is probably caused by a programming or scripting error where a file does not get closed."); // out of free cfile blocks
|
||||
return -1;
|
||||
}
|
||||
|
||||
+92
-13
@@ -95,6 +95,64 @@ typedef struct {
|
||||
#define CF_SORT_TIME 2
|
||||
#define CF_SORT_REVERSE 3
|
||||
|
||||
/**
|
||||
* @brief Contains a collection of flags for specifying from where a CFILE should be opened
|
||||
*
|
||||
* There are two types of flags. CF_LOCATION_GAME_ROOT and CF_LOCATION_USER_ROOT specify in which basic root directory
|
||||
* CFile should search for files.
|
||||
*
|
||||
* The remaining flags control what type of location may be used for the operation. It's possible to restrict the
|
||||
* location to the primary mod, the remaining mods or the top-level root directory.
|
||||
*/
|
||||
enum CFileLocationFlags {
|
||||
CF_LOCATION_ROOT_GAME = 1 << 0, //!< The game root location. This is the location of the game data (e.g. FS2 retail)
|
||||
/**
|
||||
* @brief The user directories.
|
||||
*
|
||||
* If the engine is in portable mode then using this flag exclusively will result in a failure to open files!
|
||||
*/
|
||||
CF_LOCATION_ROOT_USER = 1 << 1,
|
||||
|
||||
/**
|
||||
* @brief The memory root
|
||||
*
|
||||
* This contains all the built-in files available to the engine.
|
||||
*/
|
||||
CF_LOCATION_ROOT_MEMORY = 1 << 2,
|
||||
|
||||
/**
|
||||
* @brief Mask for extracting root type from a location bit field
|
||||
*/
|
||||
CF_LOCATION_ROOT_MASK = 0xFFFF,
|
||||
|
||||
CF_LOCATION_TYPE_ROOT = 1 << 16, //!< The basic, top-level root location
|
||||
/**
|
||||
* @brief The primary mod location.
|
||||
*
|
||||
* This is the mod that appears first on the command line. If there are no mods then the root location is considered
|
||||
* to be the primary mod
|
||||
*/
|
||||
CF_LOCATION_TYPE_PRIMARY_MOD = 1 << 17,
|
||||
/**
|
||||
* @brief The remaining mods.
|
||||
*
|
||||
* If there are no mods on the command line then this might not include any valid location.
|
||||
*/
|
||||
CF_LOCATION_TYPE_SECONDARY_MODS = 1 << 18,
|
||||
|
||||
/**
|
||||
* @brief Bitmask for extracting the type from a location bit field
|
||||
*/
|
||||
CF_LOCATION_TYPE_MASK = 0xFFFF0000,
|
||||
|
||||
/**
|
||||
* @brief A combination of all flags
|
||||
*
|
||||
* This should be used when the default behavior without any location filtering is desired.
|
||||
*/
|
||||
CF_LOCATION_ALL = CF_LOCATION_ROOT_MASK | CF_LOCATION_TYPE_MASK
|
||||
};
|
||||
|
||||
#define cfread_fix(file) (fix)cfread_int(file)
|
||||
#define cfwrite_fix(i,file) cfwrite_int(i,file)
|
||||
|
||||
@@ -111,9 +169,6 @@ extern const char *Get_file_list_child;
|
||||
#define CFILE_ROOT_DIRECTORY_LEN 256
|
||||
extern char Cfile_root_dir[CFILE_ROOT_DIRECTORY_LEN];
|
||||
extern char Cfile_user_dir[CFILE_ROOT_DIRECTORY_LEN];
|
||||
#ifdef SCP_UNIX
|
||||
extern char Cfile_user_dir_legacy[CFILE_ROOT_DIRECTORY_LEN];
|
||||
#endif
|
||||
|
||||
//================= LOW-LEVEL FUNCTIONS ==================
|
||||
int cfile_init(const char *exe_dir, const char *cdrom_dir=NULL);
|
||||
@@ -130,11 +185,10 @@ char *cf_add_ext(const char *filename, const char *ext);
|
||||
// return CF_TYPE (directory location type) of a CFILE you called cfopen() successfully on.
|
||||
int cf_get_dir_type(CFILE *cfile);
|
||||
|
||||
|
||||
// Opens the file. If no path is given, use the extension to look into the
|
||||
// default path. If mode is NULL, delete the file.
|
||||
CFILE *_cfopen(const char* source_file, int line, const char *filename, const char *mode,
|
||||
int type = CFILE_NORMAL, int dir_type = CF_TYPE_ANY, bool localize = false);
|
||||
// default path. If mode is NULL, delete the file.
|
||||
CFILE* _cfopen(const char* source_file, int line, const char* filename, const char* mode, int type = CFILE_NORMAL,
|
||||
int dir_type = CF_TYPE_ANY, bool localize = false, uint32_t location_flags = CF_LOCATION_ALL);
|
||||
#define cfopen(...) _cfopen(LOCATION, __VA_ARGS__) // Pass source location to the function
|
||||
|
||||
// like cfopen(), but it accepts a fully qualified path only (ie, the result of a cf_find_file_location() call)
|
||||
@@ -156,7 +210,7 @@ void cf_set_version( CFILE * cfile, int version );
|
||||
void cf_set_max_read_len(CFILE *cfile, size_t len);
|
||||
|
||||
// Deletes a file. Returns 0 on error, 1 if successful
|
||||
int cf_delete(const char *filename, int dir_type);
|
||||
int cf_delete(const char *filename, int dir_type, uint32_t location_flags = CF_LOCATION_ALL);
|
||||
|
||||
// Same as _access function to read a file's access bits
|
||||
int cf_access(const char *filename, int dir_type, int mode);
|
||||
@@ -311,12 +365,26 @@ int cfwrite_string(const char *buf, CFILE *file);
|
||||
*/
|
||||
int cfwrite_string_len(const char *buf, CFILE *file);
|
||||
|
||||
int cf_get_file_list( SCP_vector<SCP_string> &list, int pathtype, const char *filter, int sort = CF_SORT_NONE, SCP_vector<file_list_info> *info = NULL );
|
||||
int cf_get_file_list( int max, char **list, int type, const char *filter, int sort = CF_SORT_NONE, file_list_info *info = NULL );
|
||||
int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char **list, int type, const char *filter, int sort = CF_SORT_NONE, file_list_info *info = NULL );
|
||||
int cf_get_file_list(SCP_vector<SCP_string>& list, int pathtype, const char* filter, int sort = CF_SORT_NONE,
|
||||
SCP_vector<file_list_info>* info = nullptr, uint32_t location_flags = CF_LOCATION_ALL);
|
||||
int cf_get_file_list(int max, char** list, int type, const char* filter, int sort = CF_SORT_NONE,
|
||||
file_list_info* info = nullptr, uint32_t location_flags = CF_LOCATION_ALL);
|
||||
int cf_get_file_list_preallocated(int max, char arr[][MAX_FILENAME_LEN], char** list, int type, const char* filter,
|
||||
int sort = CF_SORT_NONE, file_list_info* info = nullptr,
|
||||
uint32_t location_flags = CF_LOCATION_ALL);
|
||||
void cf_sort_filenames( int n, char **list, int sort, file_list_info *info = NULL );
|
||||
void cf_sort_filenames( SCP_vector<SCP_string> &list, int sort, SCP_vector<file_list_info> *info = NULL );
|
||||
|
||||
struct CFileLocation {
|
||||
bool found = false;
|
||||
SCP_string full_name;
|
||||
size_t size = 0;
|
||||
size_t offset = 0;
|
||||
const void* data_ptr = nullptr;
|
||||
|
||||
explicit CFileLocation(bool found_in = false) : found(found_in) {}
|
||||
};
|
||||
|
||||
// Searches for a file. Follows all rules and precedence and searches
|
||||
// CD's and pack files.
|
||||
// Input: filespace - Filename & extension
|
||||
@@ -326,7 +394,17 @@ void cf_sort_filenames( SCP_vector<SCP_string> &list, int sort, SCP_vector<file_
|
||||
// size - File size
|
||||
// offset - Offset into pack file. 0 if not a packfile.
|
||||
// Returns: If not found returns 0.
|
||||
int cf_find_file_location( const char *filespec, int pathtype, int max_out, char *pack_filename, size_t *size, size_t *offset, bool localize = false, const void** data_out = nullptr);
|
||||
CFileLocation cf_find_file_location(const char* filespec, int pathtype, bool localize = false,
|
||||
uint32_t location_flags = CF_LOCATION_ALL);
|
||||
|
||||
struct CFileLocationExt : public CFileLocation {
|
||||
int extension_index = -1;
|
||||
|
||||
explicit CFileLocationExt(int extension_index_in = -1)
|
||||
: CFileLocation(extension_index_in >= 0), extension_index(extension_index_in)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
// Searches for a file. Follows all rules and precedence and searches
|
||||
// CD's and pack files. Searches all locations in order for first filename using ext filter list.
|
||||
@@ -340,7 +418,8 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
// offset - Offset into pack file. 0 if not a packfile.
|
||||
// Returns: If not found returns -1, else returns offset into ext_list.
|
||||
// (NOTE: This function is exponentially slow, so don't use it unless truely needed!!)
|
||||
int cf_find_file_location_ext(const char *filename, const int ext_num, const char **ext_list, int pathtype, int max_out = 0, char *pack_filename = NULL, size_t *size = NULL, size_t *offset = NULL, bool localize = false, const void** data_out = nullptr);
|
||||
CFileLocationExt cf_find_file_location_ext(const char* filename, const int ext_num, const char** ext_list, int pathtype,
|
||||
bool localize = false);
|
||||
|
||||
// Functions to change directories
|
||||
int cfile_chdir(const char *dir);
|
||||
|
||||
@@ -11,9 +11,9 @@
|
||||
|
||||
#define _CFILE_INTERNAL
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <cstdio>
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <io.h>
|
||||
|
||||
@@ -9,9 +9,9 @@
|
||||
|
||||
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <cstdio>
|
||||
#include <string>
|
||||
#include <algorithm>
|
||||
|
||||
|
||||
+269
-215
@@ -9,10 +9,10 @@
|
||||
|
||||
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdio.h>
|
||||
#include <errno.h>
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
#include <cstdio>
|
||||
#include <cerrno>
|
||||
#include <sstream>
|
||||
#include <algorithm>
|
||||
|
||||
@@ -48,9 +48,6 @@ enum CfileRootType {
|
||||
CF_ROOTTYPE_MEMORY = 2,
|
||||
};
|
||||
|
||||
// for a defined and specifically set location to get/send pilot/campaign files
|
||||
SCP_string Pilot_file_path;
|
||||
|
||||
// Created by:
|
||||
// specifying hard drive tree
|
||||
// searching for pack files on hard drive // Found by searching all known paths
|
||||
@@ -59,6 +56,7 @@ SCP_string Pilot_file_path;
|
||||
typedef struct cf_root {
|
||||
char path[CF_MAX_PATHNAME_LENGTH]; // Contains something like c:\projects\freespace or c:\projects\freespace\freespace.vp
|
||||
int roottype; // CF_ROOTTYPE_PATH = Path, CF_ROOTTYPE_PACK =Pack file, CF_ROOTTYPE_MEMORY=In memory
|
||||
uint32_t location_flags;
|
||||
} cf_root;
|
||||
|
||||
// convenient type for sorting (see cf_build_pack_list())
|
||||
@@ -347,9 +345,9 @@ void cf_build_pack_list( cf_root *root )
|
||||
std::sort(temp_roots_sort, temp_roots_sort + temp_root_count, cf_packfile_sort_func);
|
||||
|
||||
// now insert them all into the real root list properly
|
||||
cf_root *new_root;
|
||||
for (i = 0; i < temp_root_count; i++) {
|
||||
new_root = cf_create_root();
|
||||
auto new_root = cf_create_root();
|
||||
new_root->location_flags = root->location_flags;
|
||||
strcpy_s( new_root->path, root->path );
|
||||
|
||||
#ifndef NDEBUG
|
||||
@@ -378,10 +376,11 @@ static char normalize_directory_separator(char in)
|
||||
return in;
|
||||
}
|
||||
|
||||
static void cf_add_mod_roots(const char* rootDirectory)
|
||||
static void cf_add_mod_roots(const char* rootDirectory, uint32_t basic_location)
|
||||
{
|
||||
if (Cmdline_mod)
|
||||
{
|
||||
bool primary = true;
|
||||
for (const char* cur_pos=Cmdline_mod; strlen(cur_pos) != 0; cur_pos+= (strlen(cur_pos)+1))
|
||||
{
|
||||
SCP_stringstream ss;
|
||||
@@ -405,9 +404,16 @@ static void cf_add_mod_roots(const char* rootDirectory)
|
||||
cf_root* root = cf_create_root();
|
||||
|
||||
strncpy(root->path, rootPath.c_str(), CF_MAX_PATHNAME_LENGTH-1);
|
||||
if (primary) {
|
||||
root->location_flags = basic_location | CF_LOCATION_TYPE_PRIMARY_MOD;
|
||||
} else {
|
||||
root->location_flags = basic_location | CF_LOCATION_TYPE_SECONDARY_MODS;
|
||||
}
|
||||
|
||||
root->roottype = CF_ROOTTYPE_PATH;
|
||||
cf_build_pack_list(root);
|
||||
|
||||
primary = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -425,10 +431,16 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
#ifdef WIN32
|
||||
// Nothing to do here, Windows uses the current directory as the base
|
||||
#else
|
||||
cf_add_mod_roots(Cfile_user_dir_legacy);
|
||||
cf_add_mod_roots(os_get_legacy_user_dir(), CF_LOCATION_ROOT_USER);
|
||||
|
||||
root = cf_create_root();
|
||||
strncpy(root->path, Cfile_user_dir_legacy, CF_MAX_PATHNAME_LENGTH - 1);
|
||||
strncpy(root->path, os_get_legacy_user_dir(), CF_MAX_PATHNAME_LENGTH - 1);
|
||||
|
||||
root->location_flags |= CF_LOCATION_ROOT_USER | CF_LOCATION_TYPE_ROOT;
|
||||
if (Cmdline_mod == nullptr || strlen(Cmdline_mod) <= 0) {
|
||||
// If there are no mods then the root is the primary mod
|
||||
root->location_flags |= CF_LOCATION_TYPE_PRIMARY_MOD;
|
||||
}
|
||||
|
||||
// do we already have a slash? as in the case of a root directory install
|
||||
if ((strlen(root->path) < (CF_MAX_PATHNAME_LENGTH - 1)) && (root->path[strlen(root->path) - 1] != DIR_SEPARATOR_CHAR)) {
|
||||
@@ -436,10 +448,6 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
}
|
||||
root->roottype = CF_ROOTTYPE_PATH;
|
||||
|
||||
// If it wasn't set before, set the pilot path
|
||||
if (Pilot_file_path.empty())
|
||||
Pilot_file_path = root->path;
|
||||
|
||||
// Next, check any VP files under the current directory.
|
||||
cf_build_pack_list(root);
|
||||
#endif
|
||||
@@ -449,13 +457,19 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
{
|
||||
// =========================================================================
|
||||
// now look for mods under the users HOME directory to use before system ones
|
||||
cf_add_mod_roots(Cfile_user_dir);
|
||||
cf_add_mod_roots(Cfile_user_dir, CF_LOCATION_ROOT_USER);
|
||||
// =========================================================================
|
||||
|
||||
// =========================================================================
|
||||
// set users HOME directory as default for loading and saving files
|
||||
root = cf_create_root();
|
||||
strncpy(root->path, Cfile_user_dir, CF_MAX_PATHNAME_LENGTH - 1);
|
||||
strcpy_s(root->path, Cfile_user_dir);
|
||||
|
||||
root->location_flags |= CF_LOCATION_ROOT_USER | CF_LOCATION_TYPE_ROOT;
|
||||
if (Cmdline_mod == nullptr || strlen(Cmdline_mod) <= 0) {
|
||||
// If there are no mods then the root is the primary mod
|
||||
root->location_flags |= CF_LOCATION_TYPE_PRIMARY_MOD;
|
||||
}
|
||||
|
||||
// do we already have a slash? as in the case of a root directory install
|
||||
if ((strlen(root->path) < (CF_MAX_PATHNAME_LENGTH - 1)) && (root->path[strlen(root->path) - 1] != DIR_SEPARATOR_CHAR)) {
|
||||
@@ -463,10 +477,6 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
}
|
||||
root->roottype = CF_ROOTTYPE_PATH;
|
||||
|
||||
// set the default player location to here
|
||||
if (Pilot_file_path.empty())
|
||||
Pilot_file_path = root->path;
|
||||
|
||||
// Next, check any VP files under the current directory.
|
||||
cf_build_pack_list(root);
|
||||
// =========================================================================
|
||||
@@ -477,11 +487,17 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
if ( !_getcwd(working_directory, CF_MAX_PATHNAME_LENGTH ) ) {
|
||||
Error(LOCATION, "Can't get current working directory -- %d", errno );
|
||||
}
|
||||
|
||||
cf_add_mod_roots(working_directory);
|
||||
|
||||
cf_add_mod_roots(working_directory, CF_LOCATION_ROOT_GAME);
|
||||
|
||||
root = cf_create_root();
|
||||
|
||||
|
||||
root->location_flags |= CF_LOCATION_ROOT_GAME | CF_LOCATION_TYPE_ROOT;
|
||||
if (Cmdline_mod == nullptr || strlen(Cmdline_mod) <= 0) {
|
||||
// If there are no mods then the root is the primary mod
|
||||
root->location_flags |= CF_LOCATION_TYPE_PRIMARY_MOD;
|
||||
}
|
||||
|
||||
strcpy_s(root->path, working_directory);
|
||||
|
||||
size_t path_len = strlen(root->path);
|
||||
@@ -493,10 +509,6 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
|
||||
root->roottype = CF_ROOTTYPE_PATH;
|
||||
|
||||
// If the path wasn't set before use the working directory
|
||||
if ( Pilot_file_path.empty() )
|
||||
Pilot_file_path = root->path;
|
||||
|
||||
//======================================================
|
||||
// Next, check any VP files under the current directory.
|
||||
cf_build_pack_list(root);
|
||||
@@ -517,6 +529,7 @@ void cf_build_root_list(const char *cdrom_dir)
|
||||
|
||||
// The final root is the in-memory root
|
||||
root = cf_create_root();
|
||||
root->location_flags = CF_LOCATION_ROOT_MEMORY | CF_LOCATION_TYPE_ROOT;
|
||||
memset(root->path, 0, sizeof(root->path));
|
||||
root->roottype = CF_ROOTTYPE_MEMORY;
|
||||
|
||||
@@ -649,7 +662,7 @@ void cf_search_root_path(int root_index)
|
||||
struct dirent *dir = nullptr;
|
||||
while ((dir = readdir (parentDirP)) != nullptr) {
|
||||
|
||||
if (stricmp(search_name, dir->d_name)) {
|
||||
if (stricmp(search_name, dir->d_name) != 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -977,15 +990,12 @@ void cf_free_secondary_filelist()
|
||||
*
|
||||
* @param filespec Filename & extension
|
||||
* @param pathtype See CF_TYPE_ defines in CFILE.H
|
||||
* @param max_out Maximum string length that should be stuffed into pack_filename
|
||||
* @param pack_filename OUTPUT: Absolute path and filename of this file. Could be a packfile or the actual file.
|
||||
* @param size OUTPUT: File size
|
||||
* @param offset OUTPUT: Offset into pack file. 0 if not a packfile.
|
||||
* @param localize Undertake localization
|
||||
* @param location_flags Specifies where to search for the specified flag
|
||||
*
|
||||
* @return If not found returns 0.
|
||||
* @return A structure which describes the found file
|
||||
*/
|
||||
int cf_find_file_location( const char *filespec, int pathtype, int max_out, char *pack_filename, size_t *size, size_t *offset, bool localize, const void** data_out )
|
||||
CFileLocation cf_find_file_location(const char* filespec, int pathtype, bool localize, uint32_t location_flags)
|
||||
{
|
||||
int i;
|
||||
uint ui;
|
||||
@@ -993,7 +1003,6 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
char longname[MAX_PATH_LEN];
|
||||
|
||||
Assert( (filespec != NULL) && (strlen(filespec) > 0) ); //-V805
|
||||
Assert( (pack_filename == NULL) || (max_out > 1) );
|
||||
|
||||
// see if we have something other than just a filename
|
||||
// our current rules say that any file that specifies a direct
|
||||
@@ -1009,16 +1018,15 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
#endif
|
||||
FILE *fp = fopen(filespec, "rb" );
|
||||
if (fp) {
|
||||
if ( size ) *size = filelength(fileno(fp));
|
||||
if ( offset ) *offset = 0;
|
||||
if ( pack_filename ) {
|
||||
strncpy( pack_filename, filespec, max_out );
|
||||
}
|
||||
CFileLocation res(true);
|
||||
res.size = static_cast<size_t>(filelength(fileno(fp)));
|
||||
res.offset = 0;
|
||||
res.full_name = filespec;
|
||||
fclose(fp);
|
||||
return 1;
|
||||
return res;
|
||||
}
|
||||
|
||||
return 0; // If they give a full path, fail if not found.
|
||||
return CFileLocation(); // If they give a full path, fail if not found.
|
||||
}
|
||||
|
||||
// Search the hard drive for files first.
|
||||
@@ -1057,43 +1065,39 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
}
|
||||
|
||||
if (cfs_slow_search) {
|
||||
cf_create_default_path_string( longname, sizeof(longname)-1, search_order[ui], filespec, localize );
|
||||
cf_create_default_path_string(longname, sizeof(longname) - 1, search_order[ui], filespec, localize,
|
||||
location_flags);
|
||||
|
||||
#if defined _WIN32
|
||||
_finddata_t findstruct;
|
||||
|
||||
intptr_t findhandle = _findfirst(longname, &findstruct);
|
||||
if (findhandle != -1) {
|
||||
if (size)
|
||||
*size = findstruct.size;
|
||||
CFileLocation res;
|
||||
res.found = true;
|
||||
res.size = static_cast<size_t>(findstruct.size);
|
||||
|
||||
_findclose(findhandle);
|
||||
|
||||
if (offset)
|
||||
*offset = 0;
|
||||
res.offset = 0;
|
||||
res.full_name = longname;
|
||||
|
||||
if (pack_filename)
|
||||
strncpy( pack_filename, longname, max_out );
|
||||
|
||||
return 1;
|
||||
return res;
|
||||
}
|
||||
#endif
|
||||
{
|
||||
FILE *fp = fopen(longname, "rb" );
|
||||
|
||||
if (fp) {
|
||||
if (size)
|
||||
*size = filelength( fileno(fp) );
|
||||
CFileLocation res(true);
|
||||
res.size = static_cast<size_t>(filelength( fileno(fp) ));
|
||||
|
||||
fclose(fp);
|
||||
|
||||
if (offset)
|
||||
*offset = 0;
|
||||
res.offset = 0;
|
||||
res.full_name = longname;
|
||||
|
||||
if (pack_filename)
|
||||
strncpy(pack_filename, longname, max_out);
|
||||
|
||||
return 1;
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1107,6 +1111,15 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
if ( (pathtype != CF_TYPE_ANY) && (pathtype != f->pathtype_index) )
|
||||
continue;
|
||||
|
||||
if (location_flags != CF_LOCATION_ALL) {
|
||||
// If a location flag was specified we need to check if the root of this file satisfies the request
|
||||
auto root = cf_get_root(f->root_index);
|
||||
|
||||
if (!cf_check_location_flags(root->location_flags, location_flags)) {
|
||||
// Root does not satisfy location flags
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (localize) {
|
||||
// create localized filespec
|
||||
@@ -1114,70 +1127,58 @@ int cf_find_file_location( const char *filespec, int pathtype, int max_out, char
|
||||
|
||||
if ( lcl_add_dir_to_path_with_filename(longname, MAX_PATH_LEN - 1) ) {
|
||||
if ( !stricmp(longname, f->name_ext) ) {
|
||||
if (size)
|
||||
*size = f->size;
|
||||
CFileLocation res(true);
|
||||
res.size = static_cast<size_t>(f->size);
|
||||
res.offset = (size_t)f->pack_offset;
|
||||
res.data_ptr = f->data;
|
||||
|
||||
if (offset)
|
||||
*offset = (size_t)f->pack_offset;
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
res.full_name = Pathtypes[f->pathtype_index].path;
|
||||
res.full_name += DIR_SEPARATOR_STR;
|
||||
res.full_name += f->name_ext;
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
res.full_name = f->real_name;
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
if (data_out)
|
||||
*data_out = f->data;
|
||||
|
||||
if (pack_filename) {
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
strncpy(pack_filename, Pathtypes[f->pathtype_index].path, max_out);
|
||||
strncat(pack_filename, DIR_SEPARATOR_STR, max_out);
|
||||
strncat(pack_filename, f->name_ext, max_out);
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
strncpy( pack_filename, f->real_name, max_out );
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
strncpy( pack_filename, r->path, max_out );
|
||||
}
|
||||
res.full_name = r->path;
|
||||
}
|
||||
|
||||
return 1;
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// file either not localized or localized version not found
|
||||
if ( !stricmp(filespec, f->name_ext) ) {
|
||||
if (size)
|
||||
*size = f->size;
|
||||
CFileLocation res(true);
|
||||
res.size = static_cast<size_t>(f->size);
|
||||
res.offset = (size_t)f->pack_offset;
|
||||
res.data_ptr = f->data;
|
||||
|
||||
if (offset)
|
||||
*offset = (size_t)f->pack_offset;
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
res.full_name = Pathtypes[f->pathtype_index].path;
|
||||
res.full_name += DIR_SEPARATOR_STR;
|
||||
res.full_name += f->name_ext;
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
res.full_name = f->real_name;
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
if (data_out)
|
||||
*data_out = f->data;
|
||||
|
||||
if (pack_filename) {
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
strncpy(pack_filename, Pathtypes[f->pathtype_index].path, max_out);
|
||||
strncat(pack_filename, DIR_SEPARATOR_STR, max_out);
|
||||
strncat(pack_filename, f->name_ext, max_out);
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
strncpy( pack_filename, f->real_name, max_out );
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
strncpy( pack_filename, r->path, max_out );
|
||||
}
|
||||
res.full_name = r->path;
|
||||
}
|
||||
|
||||
return 1;
|
||||
return res;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
return CFileLocation();
|
||||
}
|
||||
|
||||
// -- from parselo.cpp --
|
||||
@@ -1194,14 +1195,11 @@ extern char *stristr(char *str, const char *substr);
|
||||
* @param ext_list Extension filter list
|
||||
* @param pathtype See CF_TYPE_ defines in CFILE.H
|
||||
* @param max_out Maximum string length that should be stuffed into pack_filename
|
||||
* @param pack_filename OUTPUT: Absolute path and filename of this file. Could be a packfile or the actual file.
|
||||
* @param size OUTPUT: File size
|
||||
* @param offset OUTPUT: Offset into pack file. 0 if not a packfile.
|
||||
* @param localize Undertake localization
|
||||
*
|
||||
* @return If not found returns -1, else returns offset into ext_list.
|
||||
* @return A structure containing information about the found file
|
||||
*/
|
||||
int cf_find_file_location_ext( const char *filename, const int ext_num, const char **ext_list, int pathtype, int max_out, char *pack_filename, size_t *size, size_t *offset, bool localize, const void** data_out)
|
||||
CFileLocationExt cf_find_file_location_ext( const char *filename, const int ext_num, const char **ext_list, int pathtype, bool localize)
|
||||
{
|
||||
int cur_ext, i;
|
||||
uint ui;
|
||||
@@ -1213,7 +1211,6 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
Assert( (filename != NULL) && (strlen(filename) < MAX_FILENAME_LEN) );
|
||||
Assert( (ext_list != NULL) && (ext_num > 1) ); // if we are searching for just one ext
|
||||
// then this is the wrong function to use
|
||||
Assert( (pack_filename == NULL) || (max_out > 1) );
|
||||
|
||||
|
||||
// if we have a full path already then fail. this function if for searching via filter only!
|
||||
@@ -1223,7 +1220,7 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
if ( strpbrk(filename,"/\\:") ) { // do we have a full path already?
|
||||
#endif
|
||||
Int3();
|
||||
return 0;
|
||||
return CFileLocationExt();
|
||||
}
|
||||
|
||||
// Search the hard drive for files first.
|
||||
@@ -1281,44 +1278,35 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
|
||||
#if defined _WIN32
|
||||
_finddata_t findstruct;
|
||||
|
||||
intptr_t findhandle = _findfirst(longname, &findstruct);
|
||||
if (findhandle != -1) {
|
||||
if (size)
|
||||
*size = findstruct.size;
|
||||
|
||||
if (data_out)
|
||||
*data_out = nullptr;
|
||||
CFileLocationExt res(cur_ext);
|
||||
res.found = true;
|
||||
res.size = static_cast<size_t>(findstruct.size);
|
||||
|
||||
_findclose(findhandle);
|
||||
|
||||
if (offset)
|
||||
*offset = 0;
|
||||
res.offset = 0;
|
||||
res.full_name = longname;
|
||||
|
||||
if (pack_filename)
|
||||
strncpy( pack_filename, longname, max_out );
|
||||
|
||||
return cur_ext;
|
||||
return res;
|
||||
}
|
||||
#endif
|
||||
{
|
||||
FILE *fp = fopen(longname, "rb" );
|
||||
|
||||
if (fp) {
|
||||
if (size)
|
||||
*size = filelength( fileno(fp) );
|
||||
|
||||
if (data_out)
|
||||
*data_out = nullptr;
|
||||
CFileLocationExt res(cur_ext);
|
||||
res.found = true;
|
||||
res.size = static_cast<size_t>(filelength( fileno(fp) ));
|
||||
|
||||
fclose(fp);
|
||||
|
||||
if (offset)
|
||||
*offset = 0;
|
||||
res.offset = 0;
|
||||
res.full_name = longname;
|
||||
|
||||
if (pack_filename)
|
||||
strncpy(pack_filename, longname, max_out);
|
||||
|
||||
return cur_ext;
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1359,7 +1347,7 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
continue;
|
||||
|
||||
// ... check that we match the base filename
|
||||
if ( strnicmp(f->name_ext, filespec, filespec_len) )
|
||||
if ( strnicmp(f->name_ext, filespec, filespec_len) != 0 )
|
||||
continue;
|
||||
|
||||
// ... make sure that it's one of our supported types
|
||||
@@ -1403,76 +1391,62 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
|
||||
if ( lcl_add_dir_to_path_with_filename(longname, MAX_PATH_LEN - 1) ) {
|
||||
if ( !stricmp(longname, f->name_ext) ) {
|
||||
if (size)
|
||||
*size = f->size;
|
||||
CFileLocationExt res(cur_ext);
|
||||
res.found = true;
|
||||
res.size = static_cast<size_t>(f->size);
|
||||
res.offset = (size_t)f->pack_offset;
|
||||
res.data_ptr = f->data;
|
||||
|
||||
if (offset)
|
||||
*offset = f->pack_offset;
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
res.full_name = Pathtypes[f->pathtype_index].path;
|
||||
res.full_name += DIR_SEPARATOR_STR;
|
||||
res.full_name += f->name_ext;
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
res.full_name = f->real_name;
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
if (data_out)
|
||||
*data_out = f->data;
|
||||
|
||||
if (pack_filename) {
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
strncpy(pack_filename, Pathtypes[f->pathtype_index].path, max_out);
|
||||
strncat(pack_filename, DIR_SEPARATOR_STR, max_out);
|
||||
strncat(pack_filename, f->name_ext, max_out);
|
||||
}
|
||||
else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
strncpy(pack_filename, f->real_name, max_out);
|
||||
}
|
||||
else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
strncpy(pack_filename, r->path, max_out);
|
||||
}
|
||||
res.full_name = r->path;
|
||||
}
|
||||
|
||||
// found it, so cleanup and return
|
||||
file_list_index.clear();
|
||||
|
||||
return cur_ext;
|
||||
return res;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// file either not localized or localized version not found
|
||||
if ( !stricmp(filespec, f->name_ext) ) {
|
||||
if (size)
|
||||
*size = f->size;
|
||||
CFileLocationExt res(cur_ext);
|
||||
res.found = true;
|
||||
res.size = static_cast<size_t>(f->size);
|
||||
res.offset = (size_t)f->pack_offset;
|
||||
res.data_ptr = f->data;
|
||||
|
||||
if (offset)
|
||||
*offset = f->pack_offset;
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
res.full_name = Pathtypes[f->pathtype_index].path;
|
||||
res.full_name += DIR_SEPARATOR_STR;
|
||||
res.full_name += f->name_ext;
|
||||
} else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
res.full_name = f->real_name;
|
||||
} else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
if (data_out)
|
||||
*data_out = f->data;
|
||||
|
||||
if (pack_filename) {
|
||||
if (f->data != nullptr) {
|
||||
// This is an in-memory file so we just copy the pathtype name + file name
|
||||
strncpy(pack_filename, Pathtypes[f->pathtype_index].path, max_out);
|
||||
strncat(pack_filename, DIR_SEPARATOR_STR, max_out);
|
||||
strncat(pack_filename, f->name_ext, max_out);
|
||||
}
|
||||
else if (f->pack_offset < 1) {
|
||||
// This is a real file, return the actual file path
|
||||
strncpy(pack_filename, f->real_name, max_out);
|
||||
}
|
||||
else {
|
||||
// File is in a pack file
|
||||
cf_root *r = cf_get_root(f->root_index);
|
||||
|
||||
strncpy(pack_filename, r->path, max_out);
|
||||
}
|
||||
res.full_name = r->path;
|
||||
}
|
||||
|
||||
// found it, so cleanup and return
|
||||
file_list_index.clear();
|
||||
|
||||
return cur_ext;
|
||||
return res;
|
||||
}
|
||||
|
||||
// ok, we're still here, so strip off the extension again in order to
|
||||
@@ -1483,7 +1457,7 @@ int cf_find_file_location_ext( const char *filename, const int ext_num, const ch
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
return CFileLocationExt();
|
||||
}
|
||||
|
||||
|
||||
@@ -1582,7 +1556,8 @@ static int cf_file_already_in_list( SCP_vector<SCP_string> &list, const char *fi
|
||||
// This one has a 'type', which is a CF_TYPE_* value. Because this specifies the directory
|
||||
// location, 'filter' only needs to be the filter itself, with no path information.
|
||||
// See above descriptions of cf_get_file_list() for more information about how it all works.
|
||||
int cf_get_file_list( SCP_vector<SCP_string> &list, int pathtype, const char *filter, int sort, SCP_vector<file_list_info> *info )
|
||||
int cf_get_file_list(SCP_vector<SCP_string>& list, int pathtype, const char* filter, int sort,
|
||||
SCP_vector<file_list_info>* info, uint32_t location_flags)
|
||||
{
|
||||
char *ptr;
|
||||
uint i;
|
||||
@@ -1610,7 +1585,8 @@ int cf_get_file_list( SCP_vector<SCP_string> &list, int pathtype, const char *fi
|
||||
}
|
||||
|
||||
#if defined _WIN32
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, (char*)Get_file_list_child );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, (char*)Get_file_list_child, false,
|
||||
location_flags);
|
||||
strcat_s(filespec, DIR_SEPARATOR_STR);
|
||||
strcat_s(filespec, filter);
|
||||
|
||||
@@ -1650,7 +1626,8 @@ int cf_get_file_list( SCP_vector<SCP_string> &list, int pathtype, const char *fi
|
||||
}
|
||||
|
||||
#elif defined SCP_UNIX
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, (char*)Get_file_list_child );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, (char*)Get_file_list_child, false,
|
||||
location_flags);
|
||||
|
||||
DIR *dirp;
|
||||
struct dirent *dir;
|
||||
@@ -1718,6 +1695,16 @@ int cf_get_file_list( SCP_vector<SCP_string> &list, int pathtype, const char *fi
|
||||
continue;
|
||||
}
|
||||
|
||||
if (location_flags != CF_LOCATION_ALL) {
|
||||
// If a location flag was specified we need to check if the root of this file satisfies the request
|
||||
auto root = cf_get_root(f->root_index);
|
||||
|
||||
if (!cf_check_location_flags(root->location_flags, location_flags)) {
|
||||
// Root does not satisfy location flags
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if ( !cf_matches_spec( filter,f->name_ext)) {
|
||||
continue;
|
||||
}
|
||||
@@ -1795,7 +1782,8 @@ int cf_file_already_in_list( int num_files, char **list, const char *filename )
|
||||
// This one has a 'type', which is a CF_TYPE_* value. Because this specifies the directory
|
||||
// location, 'filter' only needs to be the filter itself, with no path information.
|
||||
// See above descriptions of cf_get_file_list() for more information about how it all works.
|
||||
int cf_get_file_list( int max, char **list, int pathtype, const char *filter, int sort, file_list_info *info )
|
||||
int cf_get_file_list(int max, char** list, int pathtype, const char* filter, int sort, file_list_info* info,
|
||||
uint32_t location_flags)
|
||||
{
|
||||
char *ptr;
|
||||
uint i;
|
||||
@@ -1818,7 +1806,7 @@ int cf_get_file_list( int max, char **list, int pathtype, const char *filter, in
|
||||
char filespec[MAX_PATH_LEN];
|
||||
|
||||
#if defined _WIN32
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, filter );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, filter, false, location_flags);
|
||||
|
||||
_finddata_t find;
|
||||
intptr_t find_handle;
|
||||
@@ -1859,7 +1847,7 @@ int cf_get_file_list( int max, char **list, int pathtype, const char *filter, in
|
||||
}
|
||||
|
||||
#elif defined SCP_UNIX
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, NULL );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, nullptr, false, location_flags);
|
||||
|
||||
DIR *dirp;
|
||||
struct dirent *dir;
|
||||
@@ -1932,6 +1920,16 @@ int cf_get_file_list( int max, char **list, int pathtype, const char *filter, in
|
||||
continue;
|
||||
}
|
||||
|
||||
if (location_flags != CF_LOCATION_ALL) {
|
||||
// If a location flag was specified we need to check if the root of this file satisfies the request
|
||||
auto root = cf_get_root(f->root_index);
|
||||
|
||||
if (!cf_check_location_flags(root->location_flags, location_flags)) {
|
||||
// Root does not satisfy location flags
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (num_files >= max)
|
||||
break;
|
||||
|
||||
@@ -2015,7 +2013,8 @@ int cf_file_already_in_list_preallocated( int num_files, char arr[][MAX_FILENAME
|
||||
// This one has a 'type', which is a CF_TYPE_* value. Because this specifies the directory
|
||||
// location, 'filter' only needs to be the filter itself, with no path information.
|
||||
// See above descriptions of cf_get_file_list() for more information about how it all works.
|
||||
int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char **list, int pathtype, const char *filter, int sort, file_list_info *info )
|
||||
int cf_get_file_list_preallocated(int max, char arr[][MAX_FILENAME_LEN], char** list, int pathtype, const char* filter,
|
||||
int sort, file_list_info* info, uint32_t location_flags)
|
||||
{
|
||||
int num_files = 0, own_flag = 0;
|
||||
|
||||
@@ -2044,7 +2043,7 @@ int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char *
|
||||
|
||||
// Search the default directories
|
||||
#if defined _WIN32
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, filter );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, filter, false, location_flags);
|
||||
|
||||
intptr_t find_handle;
|
||||
_finddata_t find;
|
||||
@@ -2085,7 +2084,7 @@ int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char *
|
||||
}
|
||||
|
||||
#elif defined SCP_UNIX
|
||||
cf_create_default_path_string( filespec, sizeof(filespec)-1, pathtype, NULL );
|
||||
cf_create_default_path_string(filespec, sizeof(filespec) - 1, pathtype, nullptr, false, location_flags);
|
||||
|
||||
DIR *dirp;
|
||||
struct dirent *dir;
|
||||
@@ -2121,7 +2120,7 @@ int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char *
|
||||
|
||||
if ( !Get_file_list_filter || (*Get_file_list_filter)(dir->d_name) ) {
|
||||
|
||||
strncpy(arr[num_files], dir->d_name, MAX_FILENAME_LEN - 1 );
|
||||
strcpy_s(arr[num_files], dir->d_name );
|
||||
char *ptr = strrchr(arr[num_files], '.');
|
||||
if ( ptr ) {
|
||||
*ptr = 0;
|
||||
@@ -2156,6 +2155,16 @@ int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char *
|
||||
continue;
|
||||
}
|
||||
|
||||
if (location_flags != CF_LOCATION_ALL) {
|
||||
// If a location flag was specified we need to check if the root of this file satisfies the request
|
||||
auto root = cf_get_root(f->root_index);
|
||||
|
||||
if (!cf_check_location_flags(root->location_flags, location_flags)) {
|
||||
// Root does not satisfy location flags
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (num_files >= max)
|
||||
|
||||
break;
|
||||
@@ -2222,7 +2231,8 @@ int cf_get_file_list_preallocated( int max, char arr[][MAX_FILENAME_LEN], char *
|
||||
// filename - optional, if set, tacks the filename onto end of path.
|
||||
// Output: path - Fully qualified pathname.
|
||||
//Returns 0 if the result would be too long (invalid result)
|
||||
int cf_create_default_path_string(char *path, uint path_max, int pathtype, const char *filename, bool localize )
|
||||
int cf_create_default_path_string(char* path, uint path_max, int pathtype, const char* filename, bool localize,
|
||||
uint32_t location_flags)
|
||||
{
|
||||
#ifdef SCP_UNIX
|
||||
if ( filename && strpbrk(filename,"/") ) {
|
||||
@@ -2233,7 +2243,22 @@ int cf_create_default_path_string(char *path, uint path_max, int pathtype, const
|
||||
strncpy( path, filename, path_max );
|
||||
|
||||
} else {
|
||||
cf_root *root = cf_get_root(0);
|
||||
cf_root* root = nullptr;
|
||||
|
||||
for (auto i = 0; i < Num_roots; ++i) {
|
||||
auto current_root = cf_get_root(i);
|
||||
|
||||
if (current_root->roottype != CF_ROOTTYPE_PATH) {
|
||||
// We want a "real" path here so only path roots are valid
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cf_check_location_flags(current_root->location_flags, location_flags)) {
|
||||
// We found a valid root
|
||||
root = current_root;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!root) {
|
||||
Assert( filename != NULL );
|
||||
@@ -2243,12 +2268,7 @@ int cf_create_default_path_string(char *path, uint path_max, int pathtype, const
|
||||
|
||||
Assert(CF_TYPE_SPECIFIED(pathtype));
|
||||
|
||||
// force a specific directory to search for player files
|
||||
if ( (pathtype == CF_TYPE_PLAYERS) || (pathtype == CF_TYPE_SINGLE_PLAYERS) || (pathtype == CF_TYPE_MULTI_PLAYERS) ) {
|
||||
strncpy(path, Pilot_file_path.c_str(), path_max);
|
||||
} else {
|
||||
strncpy(path, root->path, path_max);
|
||||
}
|
||||
strncpy(path, root->path, path_max);
|
||||
|
||||
strcat_s(path, path_max, Pathtypes[pathtype].path);
|
||||
|
||||
@@ -2294,7 +2314,8 @@ int cf_create_default_path_string(char *path, uint path_max, int pathtype, const
|
||||
// filename - optional, if set, tacks the filename onto end of path.
|
||||
// Output: path - Fully qualified pathname.
|
||||
//Returns 0 if the result would be too long (invalid result)
|
||||
int cf_create_default_path_string( SCP_string &path, int pathtype, const char *filename, bool localize )
|
||||
int cf_create_default_path_string(SCP_string& path, int pathtype, const char* filename, bool /*localize*/,
|
||||
uint32_t location_flags)
|
||||
{
|
||||
#ifdef SCP_UNIX
|
||||
if ( filename && strpbrk(filename,"/") ) {
|
||||
@@ -2305,7 +2326,22 @@ int cf_create_default_path_string( SCP_string &path, int pathtype, const char *f
|
||||
path.assign(filename);
|
||||
|
||||
} else {
|
||||
cf_root *root = cf_get_root(0);
|
||||
cf_root* root = nullptr;
|
||||
|
||||
for (auto i = 0; i < Num_roots; ++i) {
|
||||
auto current_root = cf_get_root(i);
|
||||
|
||||
if (current_root->roottype != CF_ROOTTYPE_PATH) {
|
||||
// We want a "real" path here so only path roots are valid
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cf_check_location_flags(current_root->location_flags, location_flags)) {
|
||||
// We found a valid root
|
||||
root = current_root;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!root) {
|
||||
Assert( filename != NULL );
|
||||
@@ -2316,12 +2352,7 @@ int cf_create_default_path_string( SCP_string &path, int pathtype, const char *f
|
||||
Assert(CF_TYPE_SPECIFIED(pathtype));
|
||||
std::ostringstream s_path;
|
||||
|
||||
// force a specific directory to search for player files
|
||||
if ( (pathtype == CF_TYPE_PLAYERS) || (pathtype == CF_TYPE_SINGLE_PLAYERS) || (pathtype == CF_TYPE_MULTI_PLAYERS) ) {
|
||||
s_path << Pilot_file_path;
|
||||
} else {
|
||||
s_path << root->path;
|
||||
}
|
||||
s_path << root->path;
|
||||
|
||||
s_path << Pathtypes[pathtype].path;
|
||||
|
||||
@@ -2386,3 +2417,26 @@ void cfile_spew_pack_file_crcs()
|
||||
|
||||
fclose(out);
|
||||
}
|
||||
|
||||
bool cf_check_location_flags(uint32_t check_flags, uint32_t desired_flags)
|
||||
{
|
||||
Assertion((check_flags & CF_LOCATION_ROOT_MASK) != 0, "check_flags must have a valid root value");
|
||||
Assertion((check_flags & CF_LOCATION_TYPE_MASK) != 0, "check_flags must have a valid type value");
|
||||
|
||||
auto check_root = check_flags & CF_LOCATION_ROOT_MASK;
|
||||
auto desired_root_flags = desired_flags & CF_LOCATION_ROOT_MASK;
|
||||
|
||||
// If the root part is not set then assume that every root matches
|
||||
if (desired_root_flags != 0 && (check_root & desired_root_flags) == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto check_type = check_flags & CF_LOCATION_TYPE_MASK;
|
||||
auto desired_type_flags = desired_flags & CF_LOCATION_TYPE_MASK;
|
||||
|
||||
if (desired_type_flags != 0 && (check_type & desired_type_flags) == 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -29,6 +29,8 @@ typedef struct cf_pathtype {
|
||||
// During cfile_init, verify that Pathtypes[n].index == n for each item
|
||||
extern cf_pathtype Pathtypes[CF_MAX_PATH_TYPES];
|
||||
|
||||
bool cf_check_location_flags(uint32_t check_flags, uint32_t desired_flags);
|
||||
|
||||
// Returns the default storage path for files given a
|
||||
// particular pathtype. In other words, the path to
|
||||
// the unpacked, non-cd'd, stored on hard drive path.
|
||||
@@ -39,7 +41,9 @@ extern cf_pathtype Pathtypes[CF_MAX_PATH_TYPES];
|
||||
// filename - optional, if set, tacks the filename onto end of path.
|
||||
// Output: path - Fully qualified pathname.
|
||||
//Returns 0 if result would be too long (invalid result)
|
||||
int cf_create_default_path_string( char *path, uint path_max, int pathtype, const char *filename=NULL, bool localize = false);
|
||||
int cf_create_default_path_string( SCP_string &path, int pathtype, const char *filename=NULL, bool localize = false );
|
||||
int cf_create_default_path_string(char* path, uint path_max, int pathtype, const char* filename = nullptr,
|
||||
bool localize = false, uint32_t location_flags = CF_LOCATION_ALL);
|
||||
int cf_create_default_path_string(SCP_string& path, int pathtype, const char* filename = nullptr, bool localize = false,
|
||||
uint32_t location_flags = CF_LOCATION_ALL);
|
||||
|
||||
#endif //_CFILESYSTEM_H
|
||||
+13
-10
@@ -39,8 +39,8 @@
|
||||
#include <dirent.h>
|
||||
#endif
|
||||
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <cstring>
|
||||
#include <cstdlib>
|
||||
#include <cstdio>
|
||||
|
||||
#include <jansson.h>
|
||||
@@ -173,7 +173,6 @@ Flag exe_params[] =
|
||||
{ "-no_deferred", "Disable Deferred Lighting", true, EASY_DEFAULT_MEM, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_deferred"},
|
||||
{ "-enable_shadows", "Enable Shadows", true, EASY_MEM_ALL_ON, EASY_DEFAULT, "Graphics", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-no_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", },
|
||||
{ "-cache_bitmaps", "Cache bitmaps between missions", true, 0, EASY_DEFAULT_MEM, "Game Speed", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-cache_bitmaps", },
|
||||
|
||||
{ "-dualscanlines", "Add another pair of scanning lines", true, 0, EASY_DEFAULT, "HUD", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-dualscanlines", },
|
||||
{ "-targetinfo", "Enable info next to target", true, 0, EASY_DEFAULT, "HUD", "http://www.hard-light.net/wiki/index.php/Command-Line_Reference#-targetinfo", },
|
||||
@@ -363,11 +362,9 @@ int Cmdline_no_deferred_lighting = 0;
|
||||
int Cmdline_aniso_level = 0;
|
||||
|
||||
// Game Speed related
|
||||
cmdline_parm cache_bitmaps_arg("-cache_bitmaps", NULL, AT_NONE); // Cmdline_cache_bitmaps
|
||||
cmdline_parm no_fpscap("-no_fps_capping", "Don't limit frames-per-second", AT_NONE); // Cmdline_NoFPSCap
|
||||
cmdline_parm no_vsync_arg("-no_vsync", NULL, AT_NONE); // Cmdline_no_vsync
|
||||
|
||||
int Cmdline_cache_bitmaps = 0; // caching of bitmaps between missions (faster loads, can hit swap on reload with <512 Meg RAM though) - taylor
|
||||
int Cmdline_NoFPSCap = 0; // Disable FPS capping - kazan
|
||||
int Cmdline_no_vsync = 0;
|
||||
|
||||
@@ -546,6 +543,7 @@ cmdline_parm deprecated_htl_arg("-nohtl", "Deprecated", AT_NONE);
|
||||
cmdline_parm deprecated_brieflighting_arg("-brief_lighting", "Deprecated", AT_NONE);
|
||||
cmdline_parm deprecated_sndpreload_arg("-snd_preload", "Deprecated", AT_NONE);
|
||||
cmdline_parm deprecated_missile_lighting_arg("-missile_lighting", "Deprecated", AT_NONE);
|
||||
cmdline_parm deprecated_cache_bitmaps_arg("-cache_bitmaps", "Deprecated", AT_NONE);
|
||||
|
||||
int Cmdline_deprecated_spec = 0;
|
||||
int Cmdline_deprecated_glow = 0;
|
||||
@@ -556,6 +554,7 @@ int Cmdline_deprecated_jpgtga = 0;
|
||||
int Cmdline_deprecated_nohtl = 0;
|
||||
bool Cmdline_deprecated_brief_lighting = 0;
|
||||
bool Cmdline_deprecated_missile_lighting = false;
|
||||
bool Cmdline_deprecated_cache_bitmaps = false;
|
||||
|
||||
#ifndef NDEBUG
|
||||
// NOTE: this assumes that os_init() has already been called but isn't a fatal error if it hasn't
|
||||
@@ -626,6 +625,10 @@ void cmdline_debug_print_cmdline()
|
||||
{
|
||||
mprintf(("Deprecated flag '-missile_lighting' found. Please remove from your cmdline.\n"));
|
||||
}
|
||||
|
||||
if (Cmdline_deprecated_cache_bitmaps) {
|
||||
mprintf(("Deprecated flag '-cache_bitmaps' found. Please remove from your cmdline.\n"));
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -818,7 +821,7 @@ void os_validate_parms(int argc, char *argv[])
|
||||
size_t sp = 0;
|
||||
for (parmp = GET_FIRST(&Parm_list); parmp !=END_OF_LIST(&Parm_list); parmp = GET_NEXT(parmp) ) {
|
||||
// don't output deprecated flags
|
||||
if (stricmp("deprecated", parmp->help)) {
|
||||
if (stricmp("deprecated", parmp->help) != 0) {
|
||||
sp = strlen(parmp->name);
|
||||
if (parmp->arg_type != AT_NONE) {
|
||||
atp = strlen(cmdline_arg_types[parmp->arg_type]);
|
||||
@@ -1965,10 +1968,6 @@ bool SetCmdlineParams()
|
||||
Cmdline_ballistic_gauge = 1;
|
||||
}
|
||||
|
||||
if ( cache_bitmaps_arg.found() ) {
|
||||
Cmdline_cache_bitmaps = 1;
|
||||
}
|
||||
|
||||
if(old_collision_system.found())
|
||||
Cmdline_old_collision_sys = 1;
|
||||
|
||||
@@ -2159,6 +2158,10 @@ bool SetCmdlineParams()
|
||||
Cmdline_deprecated_missile_lighting = true;
|
||||
}
|
||||
|
||||
if (deprecated_cache_bitmaps_arg.found()) {
|
||||
Cmdline_deprecated_cache_bitmaps = true;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -82,7 +82,6 @@ extern int Cmdline_no_emissive;
|
||||
extern int Cmdline_aniso_level;
|
||||
|
||||
// Game Speed related
|
||||
extern int Cmdline_cache_bitmaps;
|
||||
extern int Cmdline_NoFPSCap;
|
||||
extern int Cmdline_no_vsync;
|
||||
|
||||
|
||||
@@ -92,7 +92,7 @@ void cmeasure_maybe_alert_success(object *objp)
|
||||
|
||||
if ( objp->parent == OBJ_INDEX(Player_obj) ) {
|
||||
hud_start_text_flash(XSTR("Evaded", 1430), 800);
|
||||
snd_play(gamesnd_get_game_sound(ship_get_sound(Player_obj, SND_MISSILE_EVADED_POPUP)));
|
||||
snd_play(gamesnd_get_game_sound(ship_get_sound(Player_obj, GameSounds::MISSILE_EVADED_POPUP)));
|
||||
} else if ( Objects[objp->parent].flags[Object::Object_Flags::Player_ship] ) {
|
||||
send_countermeasure_success_packet( objp->parent );
|
||||
}
|
||||
|
||||
@@ -356,7 +356,7 @@ DCF_BOOL(show_controls_info, Show_controls_info);
|
||||
|
||||
static int Axes_origin[JOY_NUM_AXES];
|
||||
|
||||
static int joy_get_unscaled_reading(int raw, int axn)
|
||||
static int joy_get_unscaled_reading(int raw)
|
||||
{
|
||||
int rng;
|
||||
|
||||
@@ -615,7 +615,7 @@ int control_config_undo_last()
|
||||
int i, z, tab;
|
||||
|
||||
if (!Config_item_undo) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -664,7 +664,7 @@ int control_config_undo_last()
|
||||
free_undo_block();
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -715,7 +715,7 @@ int control_config_remove_binding()
|
||||
config_item_undo *ptr;
|
||||
|
||||
if (Selected_line < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -723,7 +723,7 @@ int control_config_remove_binding()
|
||||
if (z & JOY_AXIS) {
|
||||
z &= ~JOY_AXIS;
|
||||
if (Axis_map_to[z] < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -731,13 +731,13 @@ int control_config_remove_binding()
|
||||
Axis_map_to[z] = -1;
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
Selected_item = -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if ((Control_config[z].joy_id < 0) && (Control_config[z].key_id < 0)) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -755,7 +755,7 @@ int control_config_remove_binding()
|
||||
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
Selected_item = -1;
|
||||
return 0;
|
||||
}
|
||||
@@ -766,7 +766,7 @@ int control_config_clear_other()
|
||||
config_item_undo *ptr;
|
||||
|
||||
if (Selected_line < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -776,7 +776,7 @@ int control_config_clear_other()
|
||||
|
||||
z &= ~JOY_AXIS;
|
||||
if (Axis_map_to[z] < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -787,7 +787,7 @@ int control_config_clear_other()
|
||||
}
|
||||
|
||||
if (!total) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -808,7 +808,7 @@ int control_config_clear_other()
|
||||
}
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -820,12 +820,12 @@ int control_config_clear_other()
|
||||
}
|
||||
}
|
||||
if (!total) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ((Control_config[z].joy_id < 0) && (Control_config[z].key_id < 0)) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -850,7 +850,7 @@ int control_config_clear_other()
|
||||
}
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -867,7 +867,7 @@ int control_config_clear_all()
|
||||
}
|
||||
|
||||
if (!total) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -888,7 +888,7 @@ int control_config_clear_all()
|
||||
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_RESET_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::RESET_PRESSED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -945,7 +945,7 @@ int control_config_do_reset()
|
||||
}
|
||||
|
||||
if (!total && !cycling_presets) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -981,7 +981,7 @@ int control_config_do_reset()
|
||||
|
||||
control_config_conflict_check();
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_RESET_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::RESET_PRESSED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1026,10 +1026,10 @@ void control_config_scroll_screen_up()
|
||||
}
|
||||
|
||||
Selected_item = -1;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1042,10 +1042,10 @@ void control_config_scroll_line_up()
|
||||
}
|
||||
|
||||
Selected_item = -1;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1059,10 +1059,10 @@ void control_config_scroll_screen_down()
|
||||
}
|
||||
|
||||
Selected_item = -1;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1076,10 +1076,10 @@ void control_config_scroll_line_down()
|
||||
}
|
||||
|
||||
Selected_item = -1;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1091,13 +1091,13 @@ void control_config_toggle_modifier(int bit)
|
||||
Assert(!(z & JOY_AXIS));
|
||||
k = Control_config[z].key_id;
|
||||
if (k < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return;
|
||||
}
|
||||
|
||||
control_config_bind_key(z, k ^ bit);
|
||||
control_config_conflict_check();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
}
|
||||
|
||||
void control_config_toggle_invert()
|
||||
@@ -1118,7 +1118,7 @@ void control_config_do_bind()
|
||||
game_flush();
|
||||
// if ((Selected_line < 0) || (Cc_lines[Selected_line].cc_index & JOY_AXIS)) {
|
||||
if (Selected_line < 0) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1142,7 +1142,7 @@ void control_config_do_bind()
|
||||
Search_mode = 0;
|
||||
Last_key = -1;
|
||||
Axis_override = -1;
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
}
|
||||
|
||||
void control_config_do_search()
|
||||
@@ -1166,7 +1166,7 @@ void control_config_do_search()
|
||||
Binding_mode = 0;
|
||||
Search_mode = 1;
|
||||
Last_key = -1;
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
}
|
||||
|
||||
void control_config_do_cancel(int fail = 0)
|
||||
@@ -1189,9 +1189,9 @@ void control_config_do_cancel(int fail = 0)
|
||||
|
||||
Binding_mode = Search_mode = 0;
|
||||
if (fail){
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
} else {
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1206,13 +1206,13 @@ int control_config_accept()
|
||||
}
|
||||
|
||||
if (i < NUM_TABS) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
hud_squadmsg_save_keys(); // rebuild map for saving/restoring keys in squadmsg mode
|
||||
gameseq_post_event(GS_EVENT_PREVIOUS_STATE);
|
||||
gamesnd_play_iface(SND_COMMIT_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::COMMIT_PRESSED);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1237,7 +1237,7 @@ void control_config_button_pressed(int n)
|
||||
Tab = n;
|
||||
Scroll_offset = Selected_line = 0;
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_SCREEN_MODE_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::SCREEN_MODE_PRESSED);
|
||||
break;
|
||||
|
||||
case BIND_BUTTON:
|
||||
@@ -1250,17 +1250,17 @@ void control_config_button_pressed(int n)
|
||||
|
||||
case SHIFT_TOGGLE:
|
||||
control_config_toggle_modifier(KEY_SHIFTED);
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
break;
|
||||
|
||||
case ALT_TOGGLE:
|
||||
control_config_toggle_modifier(KEY_ALTED);
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
break;
|
||||
|
||||
case INVERT_AXIS:
|
||||
control_config_toggle_invert();
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
break;
|
||||
|
||||
case SCROLL_UP_BUTTON:
|
||||
@@ -1281,7 +1281,7 @@ void control_config_button_pressed(int n)
|
||||
|
||||
case HELP_BUTTON:
|
||||
launch_context_help();
|
||||
gamesnd_play_iface(SND_HELP_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::HELP_PRESSED);
|
||||
break;
|
||||
|
||||
case RESET_BUTTON:
|
||||
@@ -1799,7 +1799,7 @@ void control_config_do_frame(float frametime)
|
||||
|
||||
Scroll_offset = Selected_line = 0;
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_SCREEN_MODE_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::SCREEN_MODE_PRESSED);
|
||||
break;
|
||||
|
||||
case KEY_TAB: // activate next tab
|
||||
@@ -1810,7 +1810,7 @@ void control_config_do_frame(float frametime)
|
||||
|
||||
Scroll_offset = Selected_line = 0;
|
||||
control_config_list_prepare();
|
||||
gamesnd_play_iface(SND_SCREEN_MODE_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::SCREEN_MODE_PRESSED);
|
||||
break;
|
||||
|
||||
case KEY_LEFT:
|
||||
@@ -1825,7 +1825,7 @@ void control_config_do_frame(float frametime)
|
||||
}
|
||||
}
|
||||
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
break;
|
||||
|
||||
case KEY_RIGHT:
|
||||
@@ -1837,7 +1837,7 @@ void control_config_do_frame(float frametime)
|
||||
} else if (Selected_item > 1) {
|
||||
Selected_item = -1;
|
||||
}
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
break;
|
||||
|
||||
case KEY_BACKSP: // undo
|
||||
@@ -1873,7 +1873,7 @@ void control_config_do_frame(float frametime)
|
||||
Selected_item = 1;
|
||||
}
|
||||
|
||||
gamesnd_play_iface(SND_USER_SELECT);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_SELECT);
|
||||
}
|
||||
|
||||
if (List_buttons[i].double_clicked()) {
|
||||
@@ -2379,7 +2379,7 @@ void control_get_axes_readings(int *h, int *p, int *b, int *ta, int *tr)
|
||||
|
||||
*ta = 0;
|
||||
if (Axis_map_to[3] >= 0) {
|
||||
*ta = joy_get_unscaled_reading(axes_values[Axis_map_to[3]], Axis_map_to[3]);
|
||||
*ta = joy_get_unscaled_reading(axes_values[Axis_map_to[3]]);
|
||||
}
|
||||
|
||||
*tr = 0;
|
||||
|
||||
@@ -7,8 +7,8 @@
|
||||
*
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdarg.h>
|
||||
#include <cstdio>
|
||||
#include <cstdarg>
|
||||
|
||||
#include "cfile/cfile.h"
|
||||
#include "controlconfig/controlsconfig.h"
|
||||
@@ -201,7 +201,7 @@ config_item Control_config[CCFG_MAX + 1] = {
|
||||
|
||||
const char *Scan_code_text_german[] = {
|
||||
"", "Esc", "1", "2", "3", "4", "5", "6",
|
||||
"7", "8", "9", "0", "Akzent '", "Eszett", "R\x81""cktaste", "Tab",
|
||||
"7", "8", "9", "0", "Akzent '", "Eszett", "R\x81""cktaste", "Tab", // NOLINT
|
||||
"Q", "W", "E", "R", "T", "Z", "U", "I",
|
||||
"O", "P", "\x9A", "+", "Eingabe", "Strg Links", "A", "S",
|
||||
|
||||
@@ -251,8 +251,8 @@ const char *Joy_button_text_german[] = {
|
||||
};
|
||||
|
||||
const char *Scan_code_text_french[] = {
|
||||
"", "\x90""chap", "1", "2", "3", "4", "5", "6",
|
||||
"7", "8", "9", "0", "-", "=", "Fl\x82""che Ret.", "Tab",
|
||||
"", "\x90""chap", "1", "2", "3", "4", "5", "6", // NOLINT
|
||||
"7", "8", "9", "0", "-", "=", "Fl\x82""che Ret.", "Tab", // NOLINT
|
||||
"Q", "W", "E", "R", "T", "Y", "U", "I",
|
||||
"O", "P", "[", "]", "Entr\x82""e", "Ctrl Gauche", "A", "S",
|
||||
|
||||
|
||||
@@ -3,6 +3,12 @@
|
||||
#include <memory>
|
||||
|
||||
namespace cutscene {
|
||||
FrameSize::FrameSize(size_t in_width, size_t in_height, size_t in_stride)
|
||||
: width(in_width), height(in_height), stride(in_stride)
|
||||
{
|
||||
}
|
||||
FrameSize::FrameSize() = default;
|
||||
|
||||
Decoder::Decoder() : m_decoding(true) {
|
||||
}
|
||||
|
||||
|
||||
+21
-14
@@ -10,28 +10,26 @@ struct FrameSize {
|
||||
size_t width = 0;
|
||||
size_t height = 0;
|
||||
size_t stride = 0;
|
||||
|
||||
FrameSize(size_t width, size_t in_height, size_t in_stride);
|
||||
FrameSize();
|
||||
};
|
||||
|
||||
class VideoFrame {
|
||||
protected:
|
||||
VideoFrame() {}
|
||||
VideoFrame() = default;
|
||||
|
||||
public:
|
||||
virtual ~VideoFrame() {}
|
||||
public:
|
||||
virtual ~VideoFrame() = default;
|
||||
|
||||
double frameTime = -1.0;
|
||||
int id = -1;
|
||||
|
||||
FrameSize ySize;
|
||||
FrameSize uvSize;
|
||||
virtual size_t getPlaneNumber() = 0;
|
||||
|
||||
struct DataPointers {
|
||||
ubyte* y;
|
||||
ubyte* u;
|
||||
ubyte* v;
|
||||
};
|
||||
virtual FrameSize getPlaneSize(size_t plane) = 0;
|
||||
|
||||
virtual DataPointers getDataPointers() = 0;
|
||||
virtual void* getPlaneData(size_t plane) = 0;
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -43,10 +41,19 @@ using FramePtr = std::unique_ptr<T>;
|
||||
|
||||
typedef std::unique_ptr<VideoFrame> VideoFramePtr;
|
||||
|
||||
enum class FramePixelFormat {
|
||||
Invalid,
|
||||
YUV420,
|
||||
BGR,
|
||||
BGRA
|
||||
};
|
||||
|
||||
struct MovieProperties {
|
||||
FrameSize size;
|
||||
|
||||
float fps = -1.0f;
|
||||
|
||||
FramePixelFormat pixelFormat = FramePixelFormat::Invalid;
|
||||
};
|
||||
|
||||
struct AudioFrame {
|
||||
@@ -105,7 +112,7 @@ class Decoder {
|
||||
* @brief Returns the properties of the video
|
||||
* @return The properties
|
||||
*/
|
||||
virtual MovieProperties getProperties() = 0;
|
||||
virtual MovieProperties getProperties() const = 0;
|
||||
|
||||
/**
|
||||
* @brief Starts decoding the video
|
||||
@@ -116,9 +123,9 @@ class Decoder {
|
||||
* @brief Determines if the video has audio
|
||||
* @return @c true if audio is included in the video
|
||||
*/
|
||||
virtual bool hasAudio() = 0;
|
||||
virtual bool hasAudio() const = 0;
|
||||
|
||||
virtual bool hasSubtitles() = 0;
|
||||
virtual bool hasSubtitles() const = 0;
|
||||
|
||||
/**
|
||||
* @brief Ends decoding of the video file
|
||||
|
||||
@@ -14,46 +14,85 @@ struct movie_vertex {
|
||||
|
||||
namespace cutscene {
|
||||
namespace player {
|
||||
VideoPresenter::VideoPresenter(const MovieProperties& props) {
|
||||
VideoPresenter::VideoPresenter(const MovieProperties& props) : _properties(props)
|
||||
{
|
||||
GR_DEBUG_SCOPE("Init video");
|
||||
|
||||
_planeTextureHandles.fill(-1);
|
||||
|
||||
auto w = static_cast<int>(props.size.width);
|
||||
auto h = static_cast<int>(props.size.height);
|
||||
|
||||
// Create buffer textures
|
||||
_yTexBuffer.reset(new uint8_t[w * h]);
|
||||
_ytex = bm_create(8, w, h, _yTexBuffer.get(), BMP_AABITMAP);
|
||||
switch (props.pixelFormat) {
|
||||
case FramePixelFormat::YUV420:
|
||||
_planeTextureBuffers[0].reset(new uint8_t[w * h]);
|
||||
_planeTextureHandles[0] = bm_create(8, w, h, _planeTextureBuffers[0].get(), BMP_AABITMAP);
|
||||
|
||||
_uTexBuffer.reset(new uint8_t[w / 2 * h / 2]);
|
||||
_utex = bm_create(8, w / 2, h / 2, _uTexBuffer.get(), BMP_AABITMAP);
|
||||
_planeTextureBuffers[1].reset(new uint8_t[w / 2 * h / 2]);
|
||||
_planeTextureHandles[1] = bm_create(8, w / 2, h / 2, _planeTextureBuffers[1].get(), BMP_AABITMAP);
|
||||
|
||||
_vTexBuffer.reset(new uint8_t[w / 2 * h / 2]);
|
||||
_vtex = bm_create(8, w / 2, h / 2, _vTexBuffer.get(), BMP_AABITMAP);
|
||||
_planeTextureBuffers[2].reset(new uint8_t[w / 2 * h / 2]);
|
||||
_planeTextureHandles[2] = bm_create(8, w / 2, h / 2, _planeTextureBuffers[2].get(), BMP_AABITMAP);
|
||||
|
||||
material_set_movie(&_render_material, _ytex, _utex, _vtex);
|
||||
material_set_movie(&_movie_material, _planeTextureHandles[0], _planeTextureHandles[1], _planeTextureHandles[2]);
|
||||
break;
|
||||
case FramePixelFormat::BGR:
|
||||
_planeTextureBuffers[0].reset(new uint8_t[w * h * 3]);
|
||||
_planeTextureHandles[0] = bm_create(24, w, h, _planeTextureBuffers[0].get(), 0);
|
||||
|
||||
material_set_unlit(&_rgb_material, _planeTextureHandles[0], 1.0f, false, false);
|
||||
break;
|
||||
case FramePixelFormat::BGRA:
|
||||
_planeTextureBuffers[0].reset(new uint8_t[w * h * 4]);
|
||||
_planeTextureHandles[0] = bm_create(32, w, h, _planeTextureBuffers[0].get(), 0);
|
||||
|
||||
material_set_unlit(&_rgb_material, _planeTextureHandles[0], 1.0f, true, false);
|
||||
break;
|
||||
default:
|
||||
UNREACHABLE("Unhandled enum value!");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
VideoPresenter::~VideoPresenter() {
|
||||
GR_DEBUG_SCOPE("Deinit video");
|
||||
|
||||
bm_release(_ytex);
|
||||
bm_release(_utex);
|
||||
bm_release(_vtex);
|
||||
|
||||
_ytex = _utex = _vtex = -1;
|
||||
for (auto& handle : _planeTextureHandles) {
|
||||
if (handle > 0) {
|
||||
bm_release(handle);
|
||||
handle = -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void VideoPresenter::uploadVideoFrame(const VideoFramePtr& frame) {
|
||||
GR_DEBUG_SCOPE("Update video frame");
|
||||
auto ptrs = frame->getDataPointers();
|
||||
|
||||
memcpy(_yTexBuffer.get(), ptrs.y, frame->ySize.stride * frame->ySize.height);
|
||||
memcpy(_uTexBuffer.get(), ptrs.u, frame->uvSize.stride * frame->uvSize.height);
|
||||
memcpy(_vTexBuffer.get(), ptrs.v, frame->uvSize.stride * frame->uvSize.height);
|
||||
for (size_t i = 0; i < frame->getPlaneNumber(); ++i) {
|
||||
auto size = frame->getPlaneSize(i);
|
||||
auto data = frame->getPlaneData(i);
|
||||
|
||||
gr_update_texture(_ytex, 8, _yTexBuffer.get(), (int) frame->ySize.width, (int) frame->ySize.height);
|
||||
gr_update_texture(_utex, 8, _uTexBuffer.get(), (int) frame->uvSize.width, (int) frame->uvSize.height);
|
||||
gr_update_texture(_vtex, 8, _vTexBuffer.get(), (int) frame->uvSize.width, (int) frame->uvSize.height);
|
||||
memcpy(_planeTextureBuffers[i].get(), data, size.stride * size.height);
|
||||
|
||||
int bpp = 0;
|
||||
switch (_properties.pixelFormat) {
|
||||
case FramePixelFormat::YUV420:
|
||||
bpp = 8;
|
||||
break;
|
||||
case FramePixelFormat::BGR:
|
||||
bpp = 24;
|
||||
break;
|
||||
case FramePixelFormat::BGRA:
|
||||
bpp = 32;
|
||||
break;
|
||||
default:
|
||||
UNREACHABLE("Unhandled enum value!");
|
||||
break;
|
||||
}
|
||||
|
||||
gr_update_texture(_planeTextureHandles[i], bpp, _planeTextureBuffers[i].get(), static_cast<int>(size.width),
|
||||
static_cast<int>(size.height));
|
||||
}
|
||||
}
|
||||
|
||||
void VideoPresenter::displayFrame(float x1, float y1, float x2, float y2) {
|
||||
@@ -85,10 +124,14 @@ void VideoPresenter::displayFrame(float x1, float y1, float x2, float y2) {
|
||||
auto offset = gr_add_to_immediate_buffer(sizeof(vertex_data), vertex_data);
|
||||
|
||||
vertex_layout layout;
|
||||
layout.add_vertex_component(vertex_format_data::POSITION2, sizeof(vertex_data[0]), offset + offsetof(movie_vertex, pos));
|
||||
layout.add_vertex_component(vertex_format_data::TEX_COORD2, sizeof(vertex_data[0]), offset + offsetof(movie_vertex, uv));
|
||||
layout.add_vertex_component(vertex_format_data::POSITION2, sizeof(vertex_data[0]), offsetof(movie_vertex, pos));
|
||||
layout.add_vertex_component(vertex_format_data::TEX_COORD2, sizeof(vertex_data[0]), offsetof(movie_vertex, uv));
|
||||
|
||||
gr_render_movie(&_render_material, PRIM_TYPE_TRISTRIP, &layout, 4, gr_immediate_buffer_handle);
|
||||
if (_properties.pixelFormat == FramePixelFormat::YUV420) {
|
||||
gr_render_movie(&_movie_material, PRIM_TYPE_TRISTRIP, &layout, 4, gr_immediate_buffer_handle, offset);
|
||||
} else {
|
||||
gr_render_primitives(&_rgb_material, PRIM_TYPE_TRISTRIP, &layout, 0, 4, gr_immediate_buffer_handle, offset);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -12,16 +12,13 @@ namespace cutscene {
|
||||
namespace player {
|
||||
|
||||
class VideoPresenter {
|
||||
int _ytex = -1;
|
||||
std::unique_ptr<uint8_t[]> _yTexBuffer;
|
||||
MovieProperties _properties;
|
||||
|
||||
int _utex = -1;
|
||||
std::unique_ptr<uint8_t[]> _uTexBuffer;
|
||||
std::array<int, 3> _planeTextureHandles;
|
||||
std::array<std::unique_ptr<uint8_t[]>, 3> _planeTextureBuffers;
|
||||
|
||||
int _vtex = -1;
|
||||
std::unique_ptr<uint8_t[]> _vTexBuffer;
|
||||
|
||||
movie_material _render_material;
|
||||
movie_material _movie_material;
|
||||
material _rgb_material; // Material used when a RGB/RGBA movie is played
|
||||
public:
|
||||
explicit VideoPresenter(const MovieProperties& props);
|
||||
|
||||
|
||||
+12
-12
@@ -286,10 +286,10 @@ void cutscenes_screen_scroll_line_up()
|
||||
if (Selected_line)
|
||||
{
|
||||
Selected_line--;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
|
||||
if (Selected_line < Scroll_offset)
|
||||
Scroll_offset = Selected_line;
|
||||
@@ -302,10 +302,10 @@ void cutscenes_screen_scroll_line_down()
|
||||
if (Selected_line < (int) Cutscene_list.size() - 1)
|
||||
{
|
||||
Selected_line++;
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
|
||||
h = Cutscene_list_coords[gr_screen.res][3] / gr_get_font_height();
|
||||
if (Selected_line >= Scroll_offset + h)
|
||||
@@ -328,11 +328,11 @@ void cutscenes_screen_scroll_screen_up()
|
||||
Selected_line--;
|
||||
}
|
||||
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
|
||||
} else
|
||||
{
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -349,10 +349,10 @@ void cutscenes_screen_scroll_screen_down()
|
||||
Selected_line = Scroll_offset;
|
||||
}
|
||||
|
||||
gamesnd_play_iface(SND_SCROLL);
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
} else
|
||||
{
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -361,17 +361,17 @@ int cutscenes_screen_button_pressed(int n)
|
||||
switch (n)
|
||||
{
|
||||
case TECH_DATABASE_BUTTON:
|
||||
gamesnd_play_iface(SND_SWITCH_SCREENS);
|
||||
gamesnd_play_iface(InterfaceSounds::SWITCH_SCREENS);
|
||||
gameseq_post_event(GS_EVENT_TECH_MENU);
|
||||
return 1;
|
||||
|
||||
case SIMULATOR_BUTTON:
|
||||
gamesnd_play_iface(SND_SWITCH_SCREENS);
|
||||
gamesnd_play_iface(InterfaceSounds::SWITCH_SCREENS);
|
||||
gameseq_post_event(GS_EVENT_SIMULATOR_ROOM);
|
||||
return 1;
|
||||
|
||||
case CREDITS_BUTTON:
|
||||
gamesnd_play_iface(SND_SWITCH_SCREENS);
|
||||
gamesnd_play_iface(InterfaceSounds::SWITCH_SCREENS);
|
||||
gameseq_post_event(GS_EVENT_CREDITS);
|
||||
return 1;
|
||||
|
||||
@@ -388,7 +388,7 @@ int cutscenes_screen_button_pressed(int n)
|
||||
break;
|
||||
|
||||
case EXIT_BUTTON:
|
||||
gamesnd_play_iface(SND_COMMIT_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::COMMIT_PRESSED);
|
||||
gameseq_post_event(GS_EVENT_MAIN_MENU);
|
||||
game_flush();
|
||||
break;
|
||||
|
||||
@@ -55,6 +55,9 @@ int resample_convert(SwrContext* ctx, uint8_t** output,
|
||||
#ifdef WITH_LIBAV
|
||||
return avresample_convert(ctx, output, out_plane_size, out_samples, input, in_plane_size, in_samples);
|
||||
#else
|
||||
(void)out_plane_size;
|
||||
(void)in_plane_size;
|
||||
|
||||
return swr_convert(ctx, output, out_samples, (const uint8_t**) input, in_samples);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "cutscene/ffmpeg/VideoDecoder.h"
|
||||
#include "cutscene/ffmpeg/SubtitleDecoder.h"
|
||||
|
||||
#include "FFMPEGDecoder.h"
|
||||
#include "localization/localize.h"
|
||||
|
||||
using namespace libs::ffmpeg;
|
||||
@@ -32,15 +33,18 @@ class AVPacketScope
|
||||
}
|
||||
};
|
||||
|
||||
const char* CHECKED_EXTENSIONS[] = {
|
||||
"webm",
|
||||
"mp4",
|
||||
"ogg",
|
||||
"mve"
|
||||
};
|
||||
const char* CHECKED_EXTENSIONS[] = {"webm", "mp4", "ogg",
|
||||
"png", // This is designed to be used with APNG animations
|
||||
"mve"};
|
||||
|
||||
const char* CHECKED_SUBT_EXTENSIONS[] = {"srt"};
|
||||
|
||||
double getFrameRate(AVStream* stream, AVCodecContext* codecCtx) {
|
||||
#if LIBAVCODEC_VERSION_INT > AV_VERSION_INT(58, 3, 102)
|
||||
auto fps = av_q2d(stream->r_frame_rate);
|
||||
#else
|
||||
auto fps = av_q2d(av_stream_get_r_frame_rate(stream));
|
||||
#endif
|
||||
|
||||
if (fps < 0.000001)
|
||||
{
|
||||
@@ -58,45 +62,111 @@ double getFrameRate(AVStream* stream, AVCodecContext* codecCtx) {
|
||||
CodecContextParameters getCodecParameters(AVStream* stream) {
|
||||
CodecContextParameters paras;
|
||||
#if LIBAVCODEC_VERSION_INT > AV_VERSION_INT(57, 24, 255)
|
||||
paras.width = stream->codecpar->width;
|
||||
paras.height = stream->codecpar->height;
|
||||
paras.width = stream->codecpar->width;
|
||||
paras.height = stream->codecpar->height;
|
||||
paras.pixel_format = (AVPixelFormat)stream->codecpar->format;
|
||||
|
||||
paras.channel_layout = stream->codecpar->channel_layout;
|
||||
paras.sample_rate = stream->codecpar->sample_rate;
|
||||
paras.audio_format = (AVSampleFormat)stream->codecpar->format;
|
||||
paras.sample_rate = stream->codecpar->sample_rate;
|
||||
paras.audio_format = (AVSampleFormat)stream->codecpar->format;
|
||||
|
||||
paras.codec_id = stream->codecpar->codec_id;
|
||||
paras.codec_id = stream->codecpar->codec_id;
|
||||
#else
|
||||
paras.width = stream->codec->width;
|
||||
paras.height = stream->codec->height;
|
||||
paras.width = stream->codec->width;
|
||||
paras.height = stream->codec->height;
|
||||
paras.pixel_format = stream->codec->pix_fmt;
|
||||
|
||||
paras.channel_layout = stream->codec->channel_layout;
|
||||
paras.sample_rate = stream->codec->sample_rate;
|
||||
paras.audio_format = stream->codec->sample_fmt;
|
||||
paras.sample_rate = stream->codec->sample_rate;
|
||||
paras.audio_format = stream->codec->sample_fmt;
|
||||
|
||||
paras.codec_id = stream->codec->codec_id;
|
||||
paras.codec_id = stream->codec->codec_id;
|
||||
#endif
|
||||
return paras;
|
||||
return paras;
|
||||
}
|
||||
|
||||
SCP_string normalizeLanguage(const char* langauge_name) {
|
||||
if (!stricmp(langauge_name, "eng")) {
|
||||
return "English";
|
||||
}
|
||||
if (!stricmp(langauge_name, "ger")) {
|
||||
return "German";
|
||||
}
|
||||
if (!stricmp(langauge_name, "spa")) {
|
||||
return "Spanish";
|
||||
}
|
||||
if (!stricmp(langauge_name, "eng")) {
|
||||
return "English";
|
||||
}
|
||||
if (!stricmp(langauge_name, "ger")) {
|
||||
return "German";
|
||||
}
|
||||
if (!stricmp(langauge_name, "spa")) {
|
||||
return "Spanish";
|
||||
}
|
||||
|
||||
// Print to log so that we can find the actual value more easily later
|
||||
mprintf(("FFmpeg log: Found unknown language value '%s'!\n", langauge_name));
|
||||
// Print to log so that we can find the actual value more easily later
|
||||
mprintf(("FFmpeg log: Found unknown language value '%s'!\n", langauge_name));
|
||||
|
||||
// Default to english for everything else
|
||||
return "English";
|
||||
// Default to english for everything else
|
||||
return "English";
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Given a FFmpeg pixel format returns the format it should be converted to
|
||||
* @param in_fmt The input format
|
||||
* @return The output format
|
||||
*/
|
||||
AVPixelFormat getConversionFormat(AVPixelFormat in_fmt)
|
||||
{
|
||||
switch (in_fmt) {
|
||||
case AV_PIX_FMT_RGB24:
|
||||
case AV_PIX_FMT_BGR24:
|
||||
case AV_PIX_FMT_BGR8:
|
||||
case AV_PIX_FMT_BGR4:
|
||||
case AV_PIX_FMT_BGR4_BYTE:
|
||||
case AV_PIX_FMT_RGB8:
|
||||
case AV_PIX_FMT_RGB4:
|
||||
case AV_PIX_FMT_RGB4_BYTE:
|
||||
case AV_PIX_FMT_RGB48BE:
|
||||
case AV_PIX_FMT_RGB48LE:
|
||||
case AV_PIX_FMT_RGB565BE:
|
||||
case AV_PIX_FMT_RGB565LE:
|
||||
case AV_PIX_FMT_RGB555BE:
|
||||
case AV_PIX_FMT_RGB555LE:
|
||||
case AV_PIX_FMT_BGR565BE:
|
||||
case AV_PIX_FMT_BGR565LE:
|
||||
case AV_PIX_FMT_BGR555BE:
|
||||
case AV_PIX_FMT_BGR555LE:
|
||||
case AV_PIX_FMT_RGB444LE:
|
||||
case AV_PIX_FMT_RGB444BE:
|
||||
case AV_PIX_FMT_BGR444LE:
|
||||
case AV_PIX_FMT_BGR444BE:
|
||||
case AV_PIX_FMT_BGR48BE:
|
||||
case AV_PIX_FMT_BGR48LE:
|
||||
case AV_PIX_FMT_0RGB:
|
||||
case AV_PIX_FMT_RGB0:
|
||||
case AV_PIX_FMT_0BGR:
|
||||
case AV_PIX_FMT_BGR0:
|
||||
return AV_PIX_FMT_BGR24;
|
||||
|
||||
case AV_PIX_FMT_RGBA64BE:
|
||||
case AV_PIX_FMT_RGBA64LE:
|
||||
case AV_PIX_FMT_BGRA64BE:
|
||||
case AV_PIX_FMT_BGRA64LE:
|
||||
case AV_PIX_FMT_ARGB:
|
||||
case AV_PIX_FMT_RGBA:
|
||||
case AV_PIX_FMT_ABGR:
|
||||
case AV_PIX_FMT_BGRA:
|
||||
return AV_PIX_FMT_BGRA;
|
||||
|
||||
default:
|
||||
// Assume that everything else is converted to YUV 420
|
||||
return AV_PIX_FMT_YUV420P;
|
||||
}
|
||||
}
|
||||
|
||||
FramePixelFormat getPixelFormat(AVPixelFormat fmt)
|
||||
{
|
||||
switch (fmt) {
|
||||
case AV_PIX_FMT_BGR24:
|
||||
return FramePixelFormat::BGR;
|
||||
case AV_PIX_FMT_BGRA:
|
||||
return FramePixelFormat::BGRA;
|
||||
default:
|
||||
return FramePixelFormat::YUV420;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -143,7 +213,9 @@ std::unique_ptr<InputStream> openStream(const SCP_string& name) {
|
||||
return input;
|
||||
}
|
||||
|
||||
std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& stream) {
|
||||
std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& stream,
|
||||
std::unique_ptr<InputStream>& subt)
|
||||
{
|
||||
std::unique_ptr<DecoderStatus> status(new DecoderStatus());
|
||||
|
||||
auto ctx = stream->m_ctx->ctx();
|
||||
@@ -165,7 +237,7 @@ std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& st
|
||||
if (audioStream < 0) {
|
||||
if (audioStream == AVERROR_STREAM_NOT_FOUND) {
|
||||
mprintf(("FFmpeg: No audio stream found in file!\n"));
|
||||
} else if (videoStream == AVERROR_DECODER_NOT_FOUND) {
|
||||
} else if (audioStream == AVERROR_DECODER_NOT_FOUND) {
|
||||
mprintf(("FFmpeg: Codec for audio stream could not be found!\n"));
|
||||
} else {
|
||||
mprintf(("FFmpeg: Unknown error while finding audio stream!\n"));
|
||||
@@ -180,28 +252,50 @@ std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& st
|
||||
status->audioStream = ctx->streams[audioStream];
|
||||
}
|
||||
|
||||
auto& current_language = Lcl_languages[Lcl_current_lang];
|
||||
for (uint32_t i = 0; i < ctx->nb_streams; ++i) {
|
||||
auto test_stream = ctx->streams[i];
|
||||
if (subt) {
|
||||
auto subtCtx = subt->m_ctx->ctx();
|
||||
|
||||
auto subtStream = av_find_best_stream(subtCtx, AVMEDIA_TYPE_SUBTITLE, -1, -1, nullptr, 0);
|
||||
if (subtStream < 0) {
|
||||
if (subtStream == AVERROR_STREAM_NOT_FOUND) {
|
||||
mprintf(("FFmpeg: No subtitle stream found in subtitle file!\n"));
|
||||
} else if (subtStream == AVERROR_DECODER_NOT_FOUND) {
|
||||
mprintf(("FFmpeg: Codec for subtitle stream could not be found!\n"));
|
||||
} else {
|
||||
mprintf(("FFmpeg: Unknown error while finding subtitle stream!\n"));
|
||||
}
|
||||
} else {
|
||||
status->subtitleStream = subtCtx->streams[subtStream];
|
||||
status->externalSubtitles = true;
|
||||
status->subtitleStreamIndex = subtStream;
|
||||
}
|
||||
}
|
||||
|
||||
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];
|
||||
for (uint32_t i = 0; i < ctx->nb_streams; ++i) {
|
||||
auto test_stream = ctx->streams[i];
|
||||
|
||||
#if LIBAVCODEC_VERSION_INT > AV_VERSION_INT(57, 24, 255)
|
||||
auto& pars = test_stream->codecpar;
|
||||
auto& pars = test_stream->codecpar;
|
||||
|
||||
if (!(pars->codec_type == AVMEDIA_TYPE_SUBTITLE)) {
|
||||
continue;
|
||||
}
|
||||
if (!(pars->codec_type == AVMEDIA_TYPE_SUBTITLE)) {
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
AVDictionaryEntry* tag = nullptr;
|
||||
if ((tag = av_dict_get(test_stream->metadata, "language", nullptr, 0)) == nullptr) {
|
||||
continue;
|
||||
}
|
||||
AVDictionaryEntry* tag = nullptr;
|
||||
if ((tag = av_dict_get(test_stream->metadata, "language", nullptr, 0)) == nullptr) {
|
||||
continue;
|
||||
}
|
||||
|
||||
auto normalized_language = normalizeLanguage(tag->value);
|
||||
auto normalized_language = normalizeLanguage(tag->value);
|
||||
|
||||
if (!stricmp(normalized_language.c_str(), current_language.lang_name)) {
|
||||
status->subtitleStreamIndex = i;
|
||||
status->subtitleStream = test_stream;
|
||||
break;
|
||||
if (!stricmp(normalized_language.c_str(), current_language.lang_name)) {
|
||||
status->subtitleStreamIndex = i;
|
||||
status->subtitleStream = test_stream;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -263,36 +357,37 @@ std::unique_ptr<DecoderStatus> initializeStatus(std::unique_ptr<InputStream>& st
|
||||
status->audioCodec->name ? status->audioCodec->name : "<Unknown>"));
|
||||
}
|
||||
|
||||
if (status->subtitleStreamIndex >= 0) {
|
||||
// Not really sure if this makes sense for subtitles but it shouldn't break anything...
|
||||
status->subtitleCodecPars = getCodecParameters(status->subtitleStream);
|
||||
if (status->subtitleStream != nullptr) {
|
||||
// Not really sure if this makes sense for subtitles but it shouldn't break anything...
|
||||
status->subtitleCodecPars = getCodecParameters(status->subtitleStream);
|
||||
|
||||
status->subtitleCodec = avcodec_find_decoder(status->subtitleCodecPars.codec_id);
|
||||
status->subtitleCodec = avcodec_find_decoder(status->subtitleCodecPars.codec_id);
|
||||
|
||||
#if LIBAVCODEC_VERSION_INT > AV_VERSION_INT(57, 24, 255)
|
||||
status->subtitleCodecCtx = avcodec_alloc_context3(status->subtitleCodec);
|
||||
status->subtitleCodecCtx = avcodec_alloc_context3(status->subtitleCodec);
|
||||
|
||||
err = avcodec_parameters_to_context(status->subtitleCodecCtx, status->subtitleStream->codecpar);
|
||||
if (err < 0) {
|
||||
char errorStr[512];
|
||||
av_strerror(err, errorStr, sizeof(errorStr));
|
||||
mprintf(("FFMPEG: Failed to copy context parameters! Error: %s\n", errorStr));
|
||||
return nullptr;
|
||||
}
|
||||
err = avcodec_parameters_to_context(status->subtitleCodecCtx, status->subtitleStream->codecpar);
|
||||
if (err < 0) {
|
||||
char errorStr[512];
|
||||
av_strerror(err, errorStr, sizeof(errorStr));
|
||||
mprintf(("FFMPEG: Failed to copy context parameters! Error: %s\n", errorStr));
|
||||
return nullptr;
|
||||
}
|
||||
#else
|
||||
status->subtitleCodecCtx = status->subtitleStream->codec;
|
||||
status->subtitleCodecCtx = status->subtitleStream->codec;
|
||||
#endif
|
||||
|
||||
err = avcodec_open2(status->subtitleCodecCtx, status->subtitleCodec, nullptr);
|
||||
if (err < 0) {
|
||||
char errorStr[512];
|
||||
av_strerror(err, errorStr, sizeof(errorStr));
|
||||
mprintf(("FFMPEG: Failed to open subtitle codec! Error: %s\n", errorStr));
|
||||
}
|
||||
err = avcodec_open2(status->subtitleCodecCtx, status->subtitleCodec, nullptr);
|
||||
if (err < 0) {
|
||||
char errorStr[512];
|
||||
av_strerror(err, errorStr, sizeof(errorStr));
|
||||
mprintf(("FFMPEG: Failed to open subtitle codec! Error: %s\n", errorStr));
|
||||
}
|
||||
|
||||
mprintf(("FFmpeg: Using subtitle codec %s (%s).\n", status->subtitleCodec->long_name ? status->subtitleCodec->long_name : "<Unknown>",
|
||||
status->subtitleCodec->name ? status->subtitleCodec->name : "<Unknown>"));
|
||||
}
|
||||
mprintf(("FFmpeg: Using subtitle codec %s (%s).\n",
|
||||
status->subtitleCodec->long_name ? status->subtitleCodec->long_name : "<Unknown>",
|
||||
status->subtitleCodec->name ? status->subtitleCodec->name : "<Unknown>"));
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
@@ -312,6 +407,28 @@ std::unique_ptr<InputStream> openInputStream(const SCP_string& name) {
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
std::unique_ptr<InputStream> openSubtitleStream(const SCP_string& name)
|
||||
{
|
||||
auto& current_language = Lcl_languages[Lcl_current_lang];
|
||||
|
||||
for (auto ext : CHECKED_SUBT_EXTENSIONS) {
|
||||
SCP_string fileName;
|
||||
if (strlen(current_language.lang_ext) == 0) {
|
||||
fileName = name + "." + ext;
|
||||
} else {
|
||||
fileName = name + "-" + current_language.lang_ext + "." + ext;
|
||||
}
|
||||
|
||||
auto input = openStream(fileName);
|
||||
|
||||
if (input) {
|
||||
return input;
|
||||
}
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
bool FFMPEGDecoder::initialize(const SCP_string& fileName) {
|
||||
@@ -331,8 +448,10 @@ bool FFMPEGDecoder::initialize(const SCP_string& fileName) {
|
||||
return false;
|
||||
}
|
||||
|
||||
auto subt = openSubtitleStream(movieName);
|
||||
|
||||
// We now have a valid input stream, try to find the correct streams
|
||||
auto status = initializeStatus(input);
|
||||
auto status = initializeStatus(input, subt);
|
||||
if (!status) {
|
||||
return false;
|
||||
}
|
||||
@@ -342,32 +461,44 @@ bool FFMPEGDecoder::initialize(const SCP_string& fileName) {
|
||||
|
||||
// We're done, now just put the pointer into this
|
||||
std::swap(m_input, input);
|
||||
std::swap(m_subtitleInput, subt);
|
||||
std::swap(m_status, status);
|
||||
return true;
|
||||
}
|
||||
|
||||
MovieProperties FFMPEGDecoder::getProperties() {
|
||||
MovieProperties FFMPEGDecoder::getProperties() const
|
||||
{
|
||||
MovieProperties props;
|
||||
props.size.width = static_cast<size_t>(m_status->videoCodecPars.width);
|
||||
props.size.height = static_cast<size_t>(m_status->videoCodecPars.height);
|
||||
|
||||
props.fps = static_cast<float>(getFrameRate(m_status->videoStream, m_status->videoCodecCtx));
|
||||
|
||||
props.pixelFormat = getPixelFormat(getConversionFormat(m_status->videoCodecPars.pixel_format));
|
||||
|
||||
return props;
|
||||
}
|
||||
|
||||
void FFMPEGDecoder::startDecoding() {
|
||||
std::unique_ptr<VideoDecoder> videoDecoder(new VideoDecoder(m_status.get()));
|
||||
std::unique_ptr<VideoDecoder> videoDecoder(new VideoDecoder(m_status.get(), getConversionFormat(m_status->videoCodecPars.pixel_format)));
|
||||
|
||||
std::unique_ptr<AudioDecoder> audioDecoder;
|
||||
std::unique_ptr<SubtitleDecoder> subtitleDecoder;
|
||||
std::unique_ptr<SubtitleDecoder> subtitleDecoder;
|
||||
|
||||
if (hasAudio()) {
|
||||
audioDecoder.reset(new AudioDecoder(m_status.get()));
|
||||
}
|
||||
if (hasSubtitles()) {
|
||||
subtitleDecoder.reset(new SubtitleDecoder(m_status.get()));
|
||||
}
|
||||
if (hasSubtitles()) {
|
||||
subtitleDecoder.reset(new SubtitleDecoder(m_status.get()));
|
||||
}
|
||||
|
||||
std::unique_ptr<std::thread> subtitle_thread;
|
||||
if (hasExternalSubtitle()) {
|
||||
// Start a new thread for the subtitles since otherwise we would need to make sure that neither of the input
|
||||
// streames starves while the other waits for more space in the queues
|
||||
subtitle_thread.reset(
|
||||
new std::thread([this, &subtitleDecoder]() { runSubtitleDecoder(subtitleDecoder.get()); }));
|
||||
}
|
||||
|
||||
auto ctx = m_input->m_ctx->ctx();
|
||||
AVPacket packet;
|
||||
@@ -375,13 +506,13 @@ void FFMPEGDecoder::startDecoding() {
|
||||
auto read_err = av_read_frame(ctx, &packet);
|
||||
AVPacketScope scope(&packet);
|
||||
|
||||
if (avio_feof(ctx->pb) != 0) {
|
||||
// EOF!!
|
||||
break;
|
||||
} else if (read_err < 0) {
|
||||
if (read_err < 0) {
|
||||
if (read_err == AVERROR_EOF) {
|
||||
// Finished reading -> break out of loop
|
||||
break;
|
||||
} else if (avio_feof(ctx->pb) != 0) {
|
||||
// Also EOF!
|
||||
break;
|
||||
} else {
|
||||
// Some kind of other error, try to continue reading
|
||||
char errorStr[512];
|
||||
@@ -408,13 +539,13 @@ void FFMPEGDecoder::startDecoding() {
|
||||
pushAudioData(std::move(ptr));
|
||||
}
|
||||
} else if (subtitleDecoder && packet.stream_index == m_status->subtitleStreamIndex) {
|
||||
subtitleDecoder->decodePacket(&packet);
|
||||
subtitleDecoder->decodePacket(&packet);
|
||||
|
||||
SubtitleFramePtr ptr;
|
||||
while((ptr = subtitleDecoder->getFrame()) != nullptr) {
|
||||
pushSubtitleData(std::move(ptr));
|
||||
}
|
||||
}
|
||||
SubtitleFramePtr ptr;
|
||||
while ((ptr = subtitleDecoder->getFrame()) != nullptr) {
|
||||
pushSubtitleData(std::move(ptr));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (isDecoding()) {
|
||||
@@ -434,16 +565,18 @@ void FFMPEGDecoder::startDecoding() {
|
||||
}
|
||||
}
|
||||
|
||||
if (subtitle_thread) {
|
||||
subtitle_thread->join();
|
||||
}
|
||||
|
||||
stopDecoder();
|
||||
}
|
||||
|
||||
bool FFMPEGDecoder::hasAudio() {
|
||||
return m_status->audioStreamIndex >= 0;
|
||||
}
|
||||
bool FFMPEGDecoder::hasAudio() const { return m_status->audioStreamIndex >= 0; }
|
||||
|
||||
bool FFMPEGDecoder::hasSubtitles() {
|
||||
return m_status->subtitleStreamIndex >= 0;
|
||||
}
|
||||
bool FFMPEGDecoder::hasSubtitles() const { return m_status->subtitleStream != nullptr; }
|
||||
|
||||
bool FFMPEGDecoder::hasExternalSubtitle() const { return m_status->externalSubtitles; }
|
||||
|
||||
void FFMPEGDecoder::close() {
|
||||
if (m_status) {
|
||||
@@ -454,6 +587,56 @@ void FFMPEGDecoder::close() {
|
||||
// This will delete the InputStream pointer and free all data
|
||||
m_input = nullptr;
|
||||
}
|
||||
|
||||
if (m_subtitleInput) {
|
||||
m_subtitleInput = nullptr;
|
||||
}
|
||||
}
|
||||
void FFMPEGDecoder::runSubtitleDecoder(SubtitleDecoder* decoder)
|
||||
{
|
||||
auto ctx = m_subtitleInput->m_ctx->ctx();
|
||||
AVPacket packet;
|
||||
|
||||
while (isDecoding()) {
|
||||
auto read_err = av_read_frame(ctx, &packet);
|
||||
AVPacketScope scope(&packet);
|
||||
|
||||
if (read_err < 0) {
|
||||
if (read_err == AVERROR_EOF) {
|
||||
// Finished reading -> break out of loop
|
||||
break;
|
||||
} else if (avio_feof(ctx->pb) != 0) {
|
||||
// Also EOF!
|
||||
break;
|
||||
} else {
|
||||
// Some kind of other error, try to continue reading
|
||||
char errorStr[512];
|
||||
av_strerror(read_err, errorStr, sizeof(errorStr));
|
||||
mprintf(("FFMPEG: Failed to read frame! Error: %s\n", errorStr));
|
||||
|
||||
// Skip packet
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (packet.stream_index == m_status->subtitleStreamIndex) {
|
||||
decoder->decodePacket(&packet);
|
||||
|
||||
SubtitleFramePtr ptr;
|
||||
while ((ptr = decoder->getFrame()) != nullptr) {
|
||||
pushSubtitleData(std::move(ptr));
|
||||
}
|
||||
}
|
||||
}
|
||||
if (isDecoding()) {
|
||||
// If we are still alive then read the last frames from the decoders
|
||||
decoder->finishDecoding();
|
||||
|
||||
SubtitleFramePtr ptr;
|
||||
while ((ptr = decoder->getFrame()) != nullptr) {
|
||||
pushSubtitleData(std::move(ptr));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -8,26 +8,34 @@ struct InputStream;
|
||||
|
||||
struct DecoderStatus;
|
||||
|
||||
class SubtitleDecoder;
|
||||
|
||||
class FFMPEGDecoder: public Decoder {
|
||||
private:
|
||||
std::unique_ptr<InputStream> m_input;
|
||||
|
||||
std::unique_ptr<InputStream> m_subtitleInput;
|
||||
|
||||
std::unique_ptr<DecoderStatus> m_status;
|
||||
|
||||
public:
|
||||
bool hasExternalSubtitle() const;
|
||||
|
||||
void runSubtitleDecoder(SubtitleDecoder* decoder);
|
||||
|
||||
public:
|
||||
FFMPEGDecoder();
|
||||
|
||||
~FFMPEGDecoder() override;
|
||||
|
||||
bool initialize(const SCP_string& fileName) override;
|
||||
|
||||
MovieProperties getProperties() override;
|
||||
MovieProperties getProperties() const override;
|
||||
|
||||
void startDecoding() override;
|
||||
|
||||
bool hasAudio() override;
|
||||
bool hasAudio() const override;
|
||||
|
||||
bool hasSubtitles() override;
|
||||
bool hasSubtitles() const override;
|
||||
|
||||
void close() override;
|
||||
};
|
||||
|
||||
@@ -31,7 +31,25 @@ void SubtitleDecoder::decodePacket(AVPacket* packet) {
|
||||
}
|
||||
}
|
||||
void SubtitleDecoder::finishDecoding() {
|
||||
// Handle those decoders that have a delay
|
||||
AVPacket nullPacket;
|
||||
memset(&nullPacket, 0, sizeof(nullPacket));
|
||||
nullPacket.data = nullptr;
|
||||
nullPacket.size = 0;
|
||||
|
||||
AVSubtitle subtitle;
|
||||
while (true) {
|
||||
int finishedFrame = 1;
|
||||
auto err = avcodec_decode_subtitle2(m_status->subtitleCodecCtx, &subtitle, &finishedFrame, &nullPacket);
|
||||
|
||||
if (err < 0 || !finishedFrame) {
|
||||
break;
|
||||
}
|
||||
|
||||
pushSubtitleFrame(&nullPacket, &subtitle);
|
||||
|
||||
avsubtitle_free(&subtitle);
|
||||
}
|
||||
}
|
||||
void SubtitleDecoder::pushSubtitleFrame(AVPacket* packet, AVSubtitle* subtitle) {
|
||||
if (subtitle->format != 1) {
|
||||
|
||||
@@ -3,11 +3,9 @@
|
||||
#include "tracing/tracing.h"
|
||||
|
||||
namespace {
|
||||
const AVPixelFormat DESTINATION_FORMAT = AV_PIX_FMT_YUV420P;
|
||||
|
||||
SwsContext* getSWSContext(int width, int height, AVPixelFormat fmt) {
|
||||
return sws_getContext(width, height, fmt, width, height, DESTINATION_FORMAT,
|
||||
SWS_BILINEAR, nullptr, nullptr, nullptr);
|
||||
SwsContext* getSWSContext(int width, int height, AVPixelFormat fmt, AVPixelFormat destination_fmt)
|
||||
{
|
||||
return sws_getContext(width, height, fmt, width, height, destination_fmt, SWS_BILINEAR, nullptr, nullptr, nullptr);
|
||||
}
|
||||
|
||||
double getFrameTime(int64_t pts, AVRational time_base) {
|
||||
@@ -18,34 +16,53 @@ double getFrameTime(int64_t pts, AVRational time_base) {
|
||||
namespace cutscene {
|
||||
namespace ffmpeg {
|
||||
class FFMPEGVideoFrame: public VideoFrame {
|
||||
public:
|
||||
FFMPEGVideoFrame() : frame(nullptr) {
|
||||
}
|
||||
size_t _width;
|
||||
size_t _height;
|
||||
AVFrame* _frame;
|
||||
|
||||
public:
|
||||
FFMPEGVideoFrame(size_t width, size_t height, AVFrame* frame) : _width(width), _height(height), _frame(frame) {}
|
||||
|
||||
~FFMPEGVideoFrame() override {
|
||||
if (frame != nullptr) {
|
||||
av_freep(&frame->data[0]);
|
||||
av_frame_free(&frame);
|
||||
if (_frame != nullptr) {
|
||||
av_freep(&_frame->data[0]);
|
||||
av_frame_free(&_frame);
|
||||
}
|
||||
}
|
||||
|
||||
DataPointers getDataPointers() override {
|
||||
DataPointers ptrs;
|
||||
ptrs.y = frame->data[0];
|
||||
ptrs.u = frame->data[1];
|
||||
ptrs.v = frame->data[2];
|
||||
|
||||
return ptrs;
|
||||
size_t getPlaneNumber() override
|
||||
{
|
||||
switch (_frame->format) {
|
||||
case AV_PIX_FMT_YUV420P:
|
||||
// YUV data is planar
|
||||
return 3;
|
||||
default:
|
||||
// Everything else is packed
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
FrameSize getPlaneSize(size_t plane) override
|
||||
{
|
||||
switch (_frame->format) {
|
||||
case AV_PIX_FMT_YUV420P: {
|
||||
// YUV data is planar
|
||||
auto width = plane > 0 ? _width / 2 : _width;
|
||||
auto height = plane > 0 ? _height / 2 : _height;
|
||||
|
||||
AVFrame* frame;
|
||||
return {width, height, (size_t)_frame->linesize[plane]};
|
||||
}
|
||||
default:
|
||||
// Everything else is packed
|
||||
return {_width, _height, (size_t)_frame->linesize[plane]};
|
||||
}
|
||||
}
|
||||
void* getPlaneData(size_t plane) override { return _frame->data[plane]; }
|
||||
};
|
||||
|
||||
VideoDecoder::VideoDecoder(DecoderStatus* status)
|
||||
: FFMPEGStreamDecoder(status),
|
||||
m_frameId(0) {
|
||||
VideoDecoder::VideoDecoder(DecoderStatus* status, AVPixelFormat destination_fmt)
|
||||
: FFMPEGStreamDecoder(status), m_frameId(0), m_destinationFormat(destination_fmt)
|
||||
{
|
||||
m_swsCtx = getSWSContext(m_status->videoCodecPars.width, m_status->videoCodecPars.height,
|
||||
m_status->videoCodecPars.pixel_format);
|
||||
m_status->videoCodecPars.pixel_format, destination_fmt);
|
||||
}
|
||||
|
||||
VideoDecoder::~VideoDecoder() {
|
||||
@@ -53,53 +70,32 @@ VideoDecoder::~VideoDecoder() {
|
||||
}
|
||||
|
||||
void VideoDecoder::convertAndPushPicture(const AVFrame* frame) {
|
||||
// Allocate a picture to hold the YUV data
|
||||
// Allocate a picture to hold the destination data
|
||||
AVFrame* yuvFrame = av_frame_alloc();
|
||||
av_frame_copy(yuvFrame, frame);
|
||||
yuvFrame->format = DESTINATION_FORMAT;
|
||||
yuvFrame->format = m_destinationFormat;
|
||||
|
||||
av_image_alloc(yuvFrame->data,
|
||||
yuvFrame->linesize,
|
||||
m_status->videoCodecPars.width,
|
||||
m_status->videoCodecPars.height,
|
||||
DESTINATION_FORMAT,
|
||||
1);
|
||||
av_image_alloc(yuvFrame->data, yuvFrame->linesize, m_status->videoCodecPars.width, m_status->videoCodecPars.height,
|
||||
m_destinationFormat, 1);
|
||||
|
||||
std::unique_ptr<FFMPEGVideoFrame> videoFramePtr(new FFMPEGVideoFrame());
|
||||
|
||||
if (m_status->videoCodecPars.pixel_format == DESTINATION_FORMAT) {
|
||||
av_image_copy(yuvFrame->data,
|
||||
yuvFrame->linesize,
|
||||
(const uint8_t**) (frame->data),
|
||||
frame->linesize,
|
||||
DESTINATION_FORMAT,
|
||||
m_status->videoCodecPars.width,
|
||||
m_status->videoCodecPars.height);
|
||||
if (m_status->videoCodecPars.pixel_format == m_destinationFormat) {
|
||||
av_image_copy(yuvFrame->data, yuvFrame->linesize, (const uint8_t**)(frame->data), frame->linesize,
|
||||
m_destinationFormat, m_status->videoCodecPars.width, m_status->videoCodecPars.height);
|
||||
} else {
|
||||
// Convert frame to YUV
|
||||
sws_scale(
|
||||
m_swsCtx,
|
||||
(uint8_t const* const*) frame->data,
|
||||
frame->linesize,
|
||||
0,
|
||||
m_status->videoCodecPars.height,
|
||||
yuvFrame->data,
|
||||
yuvFrame->linesize
|
||||
);
|
||||
// Convert frame to destination format
|
||||
sws_scale(m_swsCtx, (uint8_t const* const*)frame->data, frame->linesize, 0, m_status->videoCodecPars.height,
|
||||
yuvFrame->data, yuvFrame->linesize);
|
||||
}
|
||||
|
||||
std::unique_ptr<FFMPEGVideoFrame> videoFramePtr(
|
||||
new FFMPEGVideoFrame(static_cast<size_t>(m_status->videoCodecPars.width),
|
||||
static_cast<size_t>(m_status->videoCodecPars.height), yuvFrame));
|
||||
videoFramePtr->id = ++m_frameId;
|
||||
#if LIBAVCODEC_VERSION_INT > AV_VERSION_INT(58, 3, 102)
|
||||
videoFramePtr->frameTime = getFrameTime(frame->best_effort_timestamp, m_status->videoStream->time_base);
|
||||
#else
|
||||
videoFramePtr->frameTime = getFrameTime(av_frame_get_best_effort_timestamp(frame), m_status->videoStream->time_base);
|
||||
videoFramePtr->frame = yuvFrame;
|
||||
|
||||
videoFramePtr->ySize.height = static_cast<size_t>(m_status->videoCodecPars.height);
|
||||
videoFramePtr->ySize.width = static_cast<size_t>(m_status->videoCodecPars.width);
|
||||
videoFramePtr->ySize.stride = static_cast<size_t>(yuvFrame->linesize[0]);
|
||||
|
||||
// 420P means that the UV channels have half the width and height
|
||||
videoFramePtr->uvSize.height = static_cast<size_t>(m_status->videoCodecPars.height / 2);
|
||||
videoFramePtr->uvSize.width = static_cast<size_t>(m_status->videoCodecPars.width / 2);
|
||||
videoFramePtr->uvSize.stride = static_cast<size_t>(yuvFrame->linesize[1]);
|
||||
#endif
|
||||
|
||||
pushFrame(VideoFramePtr(videoFramePtr.release()));
|
||||
}
|
||||
|
||||
@@ -9,11 +9,12 @@ class VideoDecoder: public FFMPEGStreamDecoder<VideoFrame> {
|
||||
private:
|
||||
int m_frameId;
|
||||
SwsContext* m_swsCtx;
|
||||
AVPixelFormat m_destinationFormat;
|
||||
|
||||
void convertAndPushPicture(const AVFrame* frame);
|
||||
|
||||
public:
|
||||
explicit VideoDecoder(DecoderStatus* status);
|
||||
explicit VideoDecoder(DecoderStatus* status, AVPixelFormat destination_fmt);
|
||||
|
||||
~VideoDecoder() override;
|
||||
|
||||
|
||||
@@ -33,6 +33,8 @@ struct DecoderStatus {
|
||||
AVCodec* audioCodec = nullptr;
|
||||
AVCodecContext* audioCodecCtx = nullptr;
|
||||
|
||||
// Subtitles are a bit different since they max come from a different file
|
||||
bool externalSubtitles = false;
|
||||
int subtitleStreamIndex = -1;
|
||||
AVStream* subtitleStream = nullptr;
|
||||
CodecContextParameters subtitleCodecPars;
|
||||
|
||||
@@ -202,10 +202,12 @@ void movie_display_loop(Player* player, PlaybackState* state) {
|
||||
auto passed = timestamp - lastDisplayTimestamp;
|
||||
lastDisplayTimestamp = timestamp;
|
||||
|
||||
// Play as long as the player reports that there is more to display
|
||||
state->playing = player->update(passed);
|
||||
if (player->isPlaybackReady()) {
|
||||
// Play as long as the player reports that there is more to display
|
||||
state->playing = player->update(passed);
|
||||
|
||||
displayVideo(player, state);
|
||||
displayVideo(player, state);
|
||||
}
|
||||
|
||||
processEvents(state);
|
||||
|
||||
|
||||
+21
-18
@@ -17,6 +17,7 @@
|
||||
#include "io/key.h"
|
||||
#include "io/timer.h"
|
||||
|
||||
#include "player.h"
|
||||
#include "parse/parselo.h"
|
||||
|
||||
using namespace cutscene::player;
|
||||
@@ -28,7 +29,7 @@ const int MAX_AUDIO_BUFFERS = 15;
|
||||
|
||||
std::unique_ptr<Decoder> findDecoder(const SCP_string& name) {
|
||||
{
|
||||
std::unique_ptr<Decoder> ffmpeg(new ffmpeg::FFMPEGDecoder());
|
||||
std::unique_ptr<Decoder> ffmpeg(new ::cutscene::ffmpeg::FFMPEGDecoder());
|
||||
if (ffmpeg->initialize(name)) {
|
||||
return ffmpeg;
|
||||
}
|
||||
@@ -272,8 +273,21 @@ bool shouldBeginPlayback(Decoder* decoder) {
|
||||
}
|
||||
|
||||
namespace cutscene {
|
||||
Player::Player(std::unique_ptr<Decoder>&& decoder) : m_decoder(std::move(decoder)) {
|
||||
initPlayback();
|
||||
Player::Player(std::unique_ptr<Decoder>&& decoder, bool enable_audio) : m_decoder(std::move(decoder))
|
||||
{
|
||||
Assertion(!m_state.videoInited,
|
||||
"Internal State has been initialized before! Create a new player for replaying a movie.");
|
||||
|
||||
m_decoderThread.reset(new std::thread(std::bind(&Player::decoderThread, this)));
|
||||
|
||||
m_state.props = m_decoder->getProperties();
|
||||
m_state.decoder = m_decoder.get();
|
||||
|
||||
videoPlaybackInit(&m_state);
|
||||
|
||||
if (enable_audio) {
|
||||
audioPlaybackInit(&m_state);
|
||||
}
|
||||
}
|
||||
|
||||
Player::~Player() {
|
||||
@@ -315,19 +329,6 @@ bool Player::processDecoderData() {
|
||||
|
||||
return decoding || pendingAudio || pendingVideo;
|
||||
}
|
||||
|
||||
void Player::initPlayback() {
|
||||
Assertion(!m_state.videoInited, "Internal State has been initialized before! Create a new player for replaying a movie.");
|
||||
|
||||
m_decoderThread.reset(new std::thread(std::bind(&Player::decoderThread, this)));
|
||||
|
||||
m_state.props = m_decoder->getProperties();
|
||||
m_state.decoder = m_decoder.get();
|
||||
|
||||
videoPlaybackInit(&m_state);
|
||||
|
||||
audioPlaybackInit(&m_state);
|
||||
}
|
||||
bool Player::update(uint64_t diff_time_micro) {
|
||||
if (m_state.playbackHasBegun) {
|
||||
m_state.playback_time += diff_time_micro;
|
||||
@@ -354,7 +355,8 @@ void Player::decoderThread() {
|
||||
}
|
||||
}
|
||||
|
||||
std::unique_ptr<Player> Player::newPlayer(const SCP_string& name) {
|
||||
std::unique_ptr<Player> Player::newPlayer(const SCP_string& name, bool enable_audio)
|
||||
{
|
||||
mprintf(("Creating player for movie '%s'.\n", name.c_str()));
|
||||
|
||||
auto decoder = findDecoder(name);
|
||||
@@ -362,7 +364,7 @@ std::unique_ptr<Player> Player::newPlayer(const SCP_string& name) {
|
||||
if (decoder == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
return std::unique_ptr<Player>(new Player(std::move(decoder)));
|
||||
return std::unique_ptr<Player>(new Player(std::move(decoder), enable_audio));
|
||||
}
|
||||
const PlayerState& Player::getInternalState() const {
|
||||
return m_state;
|
||||
@@ -386,4 +388,5 @@ SCP_string Player::getCurrentSubtitle() {
|
||||
return m_state.currentSubtitle->text;
|
||||
}
|
||||
}
|
||||
bool Player::isPlaybackReady() const { return m_state.playbackHasBegun || shouldBeginPlayback(m_decoder.get()); }
|
||||
}
|
||||
+21
-12
@@ -52,7 +52,7 @@ struct PlayerState {
|
||||
* @brief A movie player
|
||||
*/
|
||||
class Player {
|
||||
private:
|
||||
private:
|
||||
std::unique_ptr<Decoder> m_decoder;
|
||||
|
||||
std::unique_ptr<std::thread> m_decoderThread;
|
||||
@@ -61,13 +61,11 @@ class Player {
|
||||
|
||||
bool processDecoderData();
|
||||
|
||||
private:
|
||||
private:
|
||||
void decoderThread();
|
||||
|
||||
void initPlayback();
|
||||
|
||||
public:
|
||||
explicit Player(std::unique_ptr<Decoder>&& decoder);
|
||||
public:
|
||||
explicit Player(std::unique_ptr<Decoder>&& decoder, bool enable_audio = true);
|
||||
|
||||
~Player();
|
||||
|
||||
@@ -97,6 +95,12 @@ class Player {
|
||||
*/
|
||||
const MovieProperties& getMovieProperties() const;
|
||||
|
||||
/**
|
||||
* @brief Determines if this player can start displaying video.
|
||||
* @return true if the cutscene is ready, false otherwise
|
||||
*/
|
||||
bool isPlaybackReady() const;
|
||||
|
||||
/**
|
||||
* @brief Draws the current movie frame at the specified coordinates.
|
||||
*
|
||||
@@ -109,6 +113,10 @@ class Player {
|
||||
*/
|
||||
void draw(float x1, float y1, float x2, float y2);
|
||||
|
||||
/**
|
||||
* @brief Gets the subtitle text that should be displayed now
|
||||
* @return The text, encoded in UTF-8
|
||||
*/
|
||||
SCP_string getCurrentSubtitle();
|
||||
|
||||
/**
|
||||
@@ -119,11 +127,12 @@ class Player {
|
||||
void stopPlayback();
|
||||
|
||||
/**
|
||||
* @brief Creates a player
|
||||
* The player is configured to play the movie with the specified name
|
||||
* @param name The movie to play
|
||||
* @return @c nullptr if the specified movie could not be opened, a valid Player pointer otherwise
|
||||
*/
|
||||
static std::unique_ptr<Player> newPlayer(const SCP_string& name);
|
||||
* @brief Creates a player
|
||||
* The player is configured to play the movie with the specified name
|
||||
* @param name The movie to play
|
||||
* @param enable_audio Enable audio for this player instance
|
||||
* @return @c nullptr if the specified movie could not be opened, a valid Player pointer otherwise
|
||||
*/
|
||||
static std::unique_ptr<Player> newPlayer(const SCP_string& name, bool enable_audio = true);
|
||||
};
|
||||
}
|
||||
@@ -74,7 +74,7 @@ static void debris_start_death_roll(object *debris_obj, debris *debris_p)
|
||||
|
||||
// only play debris destroy sound if hull piece and it has been around for at least 2 seconds
|
||||
if ( Missiontime > debris_p->time_started + 2*F1_0 ) {
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_MISSILE_IMPACT1), &debris_obj->pos, &View_position, debris_obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(gamesnd_id(GameSounds::MISSILE_IMPACT1)), &debris_obj->pos, &View_position, debris_obj->radius );
|
||||
|
||||
}
|
||||
}
|
||||
@@ -238,7 +238,7 @@ void debris_process_post(object * obj, float frame_time)
|
||||
radar_plot_object( obj );
|
||||
|
||||
if ( timestamp_elapsed(db->sound_delay) ) {
|
||||
obj_snd_assign(objnum, SND_DEBRIS, &vmd_zero_vector, 0);
|
||||
obj_snd_assign(objnum, GameSounds::DEBRIS, &vmd_zero_vector, 0);
|
||||
db->sound_delay = 0;
|
||||
}
|
||||
} else {
|
||||
@@ -324,19 +324,19 @@ void debris_process_post(object * obj, float frame_time)
|
||||
//Play a sound effect
|
||||
if ( lifetime > 750 ) {
|
||||
// 1.00 second effect
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DEBRIS_ARC_05), &snd_pos, &View_position, obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DEBRIS_ARC_05), &snd_pos, &View_position, obj->radius );
|
||||
} else if ( lifetime > 500 ) {
|
||||
// 0.75 second effect
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DEBRIS_ARC_04), &snd_pos, &View_position, obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DEBRIS_ARC_04), &snd_pos, &View_position, obj->radius );
|
||||
} else if ( lifetime > 250 ) {
|
||||
// 0.50 second effect
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DEBRIS_ARC_03), &snd_pos, &View_position, obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DEBRIS_ARC_03), &snd_pos, &View_position, obj->radius );
|
||||
} else if ( lifetime > 100 ) {
|
||||
// 0.25 second effect
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DEBRIS_ARC_02), &snd_pos, &View_position, obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DEBRIS_ARC_02), &snd_pos, &View_position, obj->radius );
|
||||
} else {
|
||||
// 0.10 second effect
|
||||
snd_play_3d( gamesnd_get_game_sound(SND_DEBRIS_ARC_01), &snd_pos, &View_position, obj->radius );
|
||||
snd_play_3d( gamesnd_get_game_sound(GameSounds::DEBRIS_ARC_01), &snd_pos, &View_position, obj->radius );
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -693,7 +693,7 @@ object *debris_create(object *source_obj, int model_num, int submodel_num, vec3d
|
||||
* Alas, poor debris_obj got whacked. Fortunately, we know who did it, where and how hard, so we
|
||||
* can do something about it.
|
||||
*/
|
||||
void debris_hit(object *debris_obj, object *other_obj, vec3d *hitpos, float damage)
|
||||
void debris_hit(object *debris_obj, object * /*other_obj*/, vec3d *hitpos, float damage)
|
||||
{
|
||||
debris *debris_p = &Debris[debris_obj->instance];
|
||||
|
||||
|
||||
@@ -162,7 +162,7 @@ void dc_do_command(SCP_string *cmd_str)
|
||||
try {
|
||||
dc_commands[i]->func(); // Run the command!
|
||||
|
||||
} catch (errParseString err) {
|
||||
} catch (const errParseString& err) {
|
||||
dc_printf("Require string(s) not found: \n");
|
||||
for (uint j = 0; j < err.expected_tokens.size(); ++j) {
|
||||
dc_printf("%i: %s\n", j, err.expected_tokens[j].c_str());
|
||||
@@ -170,7 +170,7 @@ void dc_do_command(SCP_string *cmd_str)
|
||||
|
||||
dc_printf("Found '%s' instead\n", err.found_token.c_str());
|
||||
|
||||
} catch (errParse err) {
|
||||
} catch (const errParse& err) {
|
||||
dc_printf("Invalid argument. Expected %s, found '%s'\n", token_str[err.expected_type], err.found_token.c_str());
|
||||
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
#include <cmath>
|
||||
#include <cstdarg>
|
||||
#include <cstring>
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
|
||||
// ========================= LOCALS =========================
|
||||
|
||||
@@ -33,7 +33,7 @@ layout (std140) uniform modelData {
|
||||
|
||||
model_light lights[MAX_LIGHTS];
|
||||
|
||||
float extrudeWidth;
|
||||
float outlineWidth;
|
||||
float fogStart;
|
||||
float fogScale;
|
||||
int buffer_matrix_offset;
|
||||
@@ -105,11 +105,6 @@ in VertexOutput {
|
||||
#endif
|
||||
#ifdef FLAG_FOG
|
||||
float fogDist;
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
float notVisible;
|
||||
#endif
|
||||
#endif
|
||||
vec4 position;
|
||||
vec3 normal;
|
||||
@@ -215,11 +210,6 @@ vec3 CalculateLighting(vec3 normal, vec3 diffuseMaterial, vec3 specularMaterial,
|
||||
|
||||
void main()
|
||||
{
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
if(vertIn.notVisible >= 0.9) { discard; }
|
||||
#endif
|
||||
#endif
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
// need depth and depth squared for variance shadow maps
|
||||
fragOut0 = vec4(vertIn.position.z, vertIn.position.z * vertIn.position.z * VARIANCE_SHADOW_SCALE_INV, 0.0, 1.0);
|
||||
@@ -381,8 +371,10 @@ void main()
|
||||
#ifdef FLAG_DIFFUSE_MAP
|
||||
if(blend_alpha == 1) finalFogColor *= baseColor.a;
|
||||
#endif
|
||||
baseColor.rgb = mix(baseColor.rgb, finalFogColor, vertIn.fogDist);
|
||||
emissiveColor.rgb = mix(emissiveColor.rgb, finalFogColor, vertIn.fogDist);
|
||||
// This code will only be used by the forward renderer so we apply the fog effect to both the emissive and the base
|
||||
// color.
|
||||
baseColor.rgb = mix(emissiveColor.rgb + baseColor.rgb, finalFogColor, vertIn.fogDist);
|
||||
emissiveColor.rgb = vec3(0.0); // Zero the emissive color since it has already been added by the previous line
|
||||
specColor.rgb *= vertIn.fogDist;
|
||||
#endif
|
||||
|
||||
@@ -424,6 +416,7 @@ void main()
|
||||
// emissive colors won't be added later when we are using forward rendering so we need to do that here
|
||||
baseColor.rgb += emissiveColor.rgb;
|
||||
#endif
|
||||
|
||||
fragOut0 = baseColor;
|
||||
#ifdef FLAG_DEFERRED
|
||||
fragOut1 = vec4(vertIn.position.xyz, 1.0);
|
||||
|
||||
@@ -1,9 +1,18 @@
|
||||
#extension GL_ARB_gpu_shader5: enable
|
||||
|
||||
#ifdef FLAG_THICK_OUTLINE
|
||||
layout (triangles) in;
|
||||
// For every triangle line we generate 2 triangles which can be done with 4 vertices so in total we will need 12 vertices
|
||||
layout (triangle_strip, max_vertices = 12) out;
|
||||
#else
|
||||
layout (triangles) in;
|
||||
layout (triangle_strip, max_vertices = 3) out;
|
||||
#ifdef GL_ARB_gpu_shader5
|
||||
#endif
|
||||
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
#ifdef GL_ARB_gpu_shader5
|
||||
layout(invocations = 4) in;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define MAX_LIGHTS 8
|
||||
@@ -33,7 +42,7 @@ layout (std140) uniform modelData {
|
||||
|
||||
model_light lights[MAX_LIGHTS];
|
||||
|
||||
float extrudeWidth;
|
||||
float outlineWidth;
|
||||
float fogStart;
|
||||
float fogScale;
|
||||
int buffer_matrix_offset;
|
||||
@@ -106,15 +115,13 @@ in VertexOutput {
|
||||
#ifdef FLAG_FOG
|
||||
float fogDist;
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
float notVisible;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
#if !defined(GL_ARB_gpu_shader5)
|
||||
float instance;
|
||||
#endif
|
||||
#ifdef FLAG_TRANSFORM
|
||||
float clipModel;
|
||||
#endif
|
||||
#else
|
||||
vec4 position;
|
||||
#endif
|
||||
@@ -135,11 +142,6 @@ out VertexOutput {
|
||||
#endif
|
||||
#ifdef FLAG_FOG
|
||||
float fogDist;
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
float notVisible;
|
||||
#endif
|
||||
#endif
|
||||
vec4 position;
|
||||
vec3 normal;
|
||||
@@ -150,6 +152,7 @@ out VertexOutput {
|
||||
#endif
|
||||
} vertOut;
|
||||
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
void main(void)
|
||||
{
|
||||
#ifdef GL_ARB_gpu_shader5
|
||||
@@ -159,14 +162,25 @@ void main(void)
|
||||
#endif
|
||||
for(int vert = 0; vert < gl_in.length(); vert++)
|
||||
{
|
||||
#ifdef FLAG_TRANSFORM
|
||||
if (vertIn[vert].clipModel > 0.9) {
|
||||
// If the model was clipped in the vertex shader then we do not apply the shadow projection matrix here
|
||||
gl_Position = gl_in[vert].gl_Position;
|
||||
} else {
|
||||
gl_Position = shadow_proj_matrix[instanceID] * gl_in[vert].gl_Position;
|
||||
}
|
||||
#else
|
||||
gl_Position = shadow_proj_matrix[instanceID] * gl_in[vert].gl_Position;
|
||||
#endif
|
||||
if(gl_Position.z < -1.0)
|
||||
gl_Position.z = -1.0;
|
||||
|
||||
vertOut.position = gl_in[vert].gl_Position;
|
||||
vertOut.normal = vertIn[vert].normal;
|
||||
vertOut.texCoord = vertIn[vert].texCoord;
|
||||
|
||||
gl_Layer = instanceID;
|
||||
|
||||
#ifdef FLAG_ENV_MAP
|
||||
vertOut.envReflect = vertIn[vert].envReflect;
|
||||
#endif
|
||||
@@ -183,19 +197,66 @@ void main(void)
|
||||
vertOut.shadowUV[3] = vertIn[vert].shadowUV[3];
|
||||
vertOut.shadowPos = vertIn[vert].shadowPos;
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
vertOut.notVisible = vertIn[vert].notVisible;
|
||||
#endif
|
||||
#ifdef FLAG_CLIP
|
||||
#if defined(FLAG_CLIP)
|
||||
gl_ClipDistance[0] = gl_in[vert].gl_ClipDistance[0];
|
||||
#endif
|
||||
#else
|
||||
#if defined(FLAG_CLIP) || defined(FLAG_TRANSFORM)
|
||||
gl_ClipDistance[0] = gl_in[vert].gl_ClipDistance[0];
|
||||
#endif
|
||||
#endif
|
||||
EmitVertex();
|
||||
}
|
||||
EndPrimitive();
|
||||
}
|
||||
#elif defined(FLAG_THICK_OUTLINE)
|
||||
const vec2 pixelOffsetDir[4] = vec2[](
|
||||
vec2(0.0, 1.0),
|
||||
vec2(1.0, 1.0),
|
||||
vec2(1.0, -1.0),
|
||||
vec2(0.0, -1.0)
|
||||
);
|
||||
void main(void)
|
||||
{
|
||||
for(int vert = 0; vert < gl_in.length(); vert++)
|
||||
{
|
||||
int nextVert = (vert + 1) % gl_in.length();
|
||||
vec4 clip = gl_in[vert].gl_Position;
|
||||
vec4 diff = gl_in[nextVert].gl_Position - clip; // vector from vert to the next vertex in the list
|
||||
vec2 normal = normalize(vec2(diff.y, -diff.x)); // Computing the normal of a 2D vector is actually rather simple...
|
||||
for (int lineVert = 0; lineVert < 4; ++lineVert)
|
||||
{
|
||||
// This is the pixel offset along the normal axis
|
||||
vec2 yOffPixel = pixelOffsetDir[lineVert].y * normal * (outlineWidth / 2.0);
|
||||
// This is the offset of the vertex along the vector between this vertex and the next one in the triangle
|
||||
vec2 xOff = pixelOffsetDir[lineVert].x * diff.xy;
|
||||
|
||||
// This is the final offset in clip space
|
||||
vec2 finalOffset = xOff + yOffPixel * vec2(vpwidth, vpheight) * clip.w;
|
||||
|
||||
gl_Position = vec4(clip.xyz + vec3(finalOffset, 0.0), clip.w);
|
||||
vertOut.position = vertIn[vert].position;
|
||||
vertOut.normal = vertIn[vert].normal;
|
||||
vertOut.texCoord = vertIn[vert].texCoord;
|
||||
|
||||
#ifdef FLAG_ENV_MAP
|
||||
vertOut.envReflect = vertIn[vert].envReflect;
|
||||
#endif
|
||||
#ifdef FLAG_NORMAL_MAP
|
||||
vertOut.tangentMatrix = vertIn[vert].tangentMatrix;
|
||||
#endif
|
||||
#ifdef FLAG_FOG
|
||||
vertOut.fogDist = vertIn[vert].fogDist;
|
||||
#endif
|
||||
#ifdef FLAG_SHADOWS
|
||||
vertOut.shadowUV[0] = vertIn[vert].shadowUV[0];
|
||||
vertOut.shadowUV[1] = vertIn[vert].shadowUV[1];
|
||||
vertOut.shadowUV[2] = vertIn[vert].shadowUV[2];
|
||||
vertOut.shadowUV[3] = vertIn[vert].shadowUV[3];
|
||||
vertOut.shadowPos = vertIn[vert].shadowPos;
|
||||
#endif
|
||||
#if defined(FLAG_CLIP)
|
||||
gl_ClipDistance[0] = gl_in[vert].gl_ClipDistance[0];
|
||||
#endif
|
||||
EmitVertex();
|
||||
}
|
||||
|
||||
EndPrimitive();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@@ -36,7 +36,7 @@ layout (std140) uniform modelData {
|
||||
|
||||
model_light lights[MAX_LIGHTS];
|
||||
|
||||
float extrudeWidth;
|
||||
float outlineWidth;
|
||||
float fogStart;
|
||||
float fogScale;
|
||||
int buffer_matrix_offset;
|
||||
@@ -113,15 +113,15 @@ out VertexOutput {
|
||||
#ifdef FLAG_FOG
|
||||
float fogDist;
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
float notVisible;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
#if !defined(GL_ARB_gpu_shader5)
|
||||
float instance;
|
||||
#endif
|
||||
#ifdef FLAG_TRANSFORM
|
||||
// This flag is needed to let the geometry shader know that it doesn't need to apply the
|
||||
// shadow projection to gl_Position
|
||||
float clipModel;
|
||||
#endif
|
||||
#else
|
||||
vec4 position;
|
||||
#endif
|
||||
@@ -152,19 +152,9 @@ void main()
|
||||
vec4 texCoord;
|
||||
mat4 orient = mat4(1.0);
|
||||
mat4 scale = mat4(1.0);
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
#ifdef FLAG_TRANSFORM
|
||||
#ifdef FLAG_TRANSFORM
|
||||
bool clipModel;
|
||||
getModelTransform(orient, clipModel, int(vertModelID), buffer_matrix_offset);
|
||||
vertOut.notVisible = clipModel ? 1.0 : 0.0;
|
||||
#endif
|
||||
#else
|
||||
#ifdef FLAG_TRANSFORM
|
||||
bool clipModel;
|
||||
getModelTransform(orient, clipModel, int(vertModelID), buffer_matrix_offset);
|
||||
#else
|
||||
bool clipModel = false;
|
||||
#endif
|
||||
#endif
|
||||
texCoord = textureMatrix * vertTexCoord;
|
||||
vec4 vertex = vertPosition;
|
||||
@@ -188,9 +178,6 @@ void main()
|
||||
#else
|
||||
gl_Position = projMatrix * position;
|
||||
#endif
|
||||
#ifdef FLAG_NORMAL_EXTRUDE
|
||||
gl_Position.xy += (mat3(projMatrix) * normal.xyz).xy * gl_Position.z * extrudeWidth;
|
||||
#endif
|
||||
#ifdef FLAG_SHADOWS
|
||||
vec4 shadowPos = shadow_mv_matrix * modelMatrix * orient * vertPosition;
|
||||
vertOut.shadowPos = shadow_mv_matrix * modelMatrix * orient * vertPosition;
|
||||
@@ -213,31 +200,28 @@ void main()
|
||||
#ifdef FLAG_FOG
|
||||
vertOut.fogDist = clamp((gl_Position.z - fogStart) * 0.75 * fogScale, 0.0, 1.0);
|
||||
#endif
|
||||
#ifdef WORKAROUND_CLIPPING_PLANES
|
||||
if(use_clip_plane) {
|
||||
gl_ClipDistance[0] = dot(clip_equation, modelMatrix * orient * vertex);
|
||||
} else {
|
||||
gl_ClipDistance[0] = 1.0;
|
||||
}
|
||||
#else
|
||||
#ifdef FLAG_CLIP
|
||||
#ifdef FLAG_TRANSFORM
|
||||
if (clipModel) {
|
||||
gl_ClipDistance[0] = -1.0;
|
||||
} else if(use_clip_plane) {
|
||||
// Clip this model by moving all vertices outside the clip volume
|
||||
gl_Position = vec4(vec3(-2.0), 1.0);
|
||||
}
|
||||
#ifdef FLAG_SHADOW_MAP
|
||||
vertOut.clipModel = clipModel ? 1.0 : 0.0;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef FLAG_CLIP
|
||||
if(use_clip_plane) {
|
||||
gl_ClipDistance[0] = dot(clip_equation, modelMatrix * orient * vertex);
|
||||
} else {
|
||||
gl_ClipDistance[0] = 1.0;
|
||||
}
|
||||
#elif defined(FLAG_TRANSFORM)
|
||||
gl_ClipDistance[0] = clipModel ? -1.0 : 1.0;
|
||||
#endif
|
||||
#endif
|
||||
#ifndef FLAG_SHADOW_MAP
|
||||
#ifndef FLAG_SHADOW_MAP
|
||||
vertOut.position = position;
|
||||
vertOut.normal = normal;
|
||||
vertOut.texCoord = texCoord;
|
||||
#else
|
||||
#else
|
||||
vertOut.normal = normal;
|
||||
vertOut.texCoord = texCoord;
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
local exts = {
|
||||
"",
|
||||
".lua",
|
||||
".lc"
|
||||
}
|
||||
|
||||
local function cfileLoader(name)
|
||||
local file = nil
|
||||
|
||||
for i,v in ipairs(exts) do
|
||||
local real_name = name .. v
|
||||
file = cf.openFile(real_name, "r", "data/scripts")
|
||||
|
||||
if (file:isValid()) then
|
||||
name = real_name
|
||||
break;
|
||||
end
|
||||
end
|
||||
|
||||
if (file == nil or not file:isValid()) then
|
||||
return "Module '" .. name .. "' is not known by the CFile system"
|
||||
end
|
||||
|
||||
local content = file:read("*a")
|
||||
file:close()
|
||||
|
||||
local func, err = loadstring(content, name)
|
||||
|
||||
if err then
|
||||
return err
|
||||
end
|
||||
|
||||
return func
|
||||
end
|
||||
|
||||
table.insert(package.loaders, 2, cfileLoader)
|
||||
@@ -5,7 +5,7 @@ IF(MSVC)
|
||||
set(RES_CONTENT)
|
||||
set(ARRAY_ELEMENTS)
|
||||
|
||||
FOREACH(file ${file_root_def_files_files})
|
||||
FOREACH(file ${default_files_files})
|
||||
set(INPUT_NAME "${CMAKE_CURRENT_SOURCE_DIR}/${file}")
|
||||
SET(OUTPUT "${GENERATED_SOURCE_DIR}/code/${file}")
|
||||
file(RELATIVE_PATH RELATIVE_FILE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/def_files" "${INPUT_NAME}")
|
||||
@@ -39,7 +39,7 @@ else()
|
||||
set(INCLUDE_LIST)
|
||||
set(ARRAY_ELEMENTS)
|
||||
|
||||
FOREACH(file ${file_root_def_files_files})
|
||||
FOREACH(file ${default_files_files})
|
||||
set(INPUT_NAME "${CMAKE_CURRENT_SOURCE_DIR}/${file}")
|
||||
SET(OUTPUT "${GENERATED_SOURCE_DIR}/code/${file}")
|
||||
file(RELATIVE_PATH RELATIVE_FILE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/def_files" "${INPUT_NAME}")
|
||||
@@ -51,6 +51,10 @@ else()
|
||||
# Retrieve the path type name from the relative path
|
||||
GET_FILENAME_COMPONENT(PATH_TYPE "${RELATIVE_FILE_PATH}" DIRECTORY)
|
||||
file(TO_NATIVE_PATH "${PATH_TYPE}" PATH_TYPE)
|
||||
if (MINGW)
|
||||
# There is a bug in CMake where it thinks MinGW uses forward slashes for paths but we need backslashes for Windows builds
|
||||
string(REPLACE "/" "\\\\" PATH_TYPE "${PATH_TYPE}")
|
||||
endif()
|
||||
GET_FILENAME_COMPONENT(FILE_NAME "${RELATIVE_FILE_PATH}" NAME)
|
||||
|
||||
string(MAKE_C_IDENTIFIER "${RELATIVE_FILE_PATH}" FIELD_NAME)
|
||||
@@ -69,7 +73,8 @@ else()
|
||||
ADD_CUSTOM_COMMAND(
|
||||
OUTPUT ${ALL_OUTPUTS}
|
||||
COMMAND embedfile "${INPUT_NAME}" "${OUTPUT}" "${FIELD_NAME}"
|
||||
DEPENDS "${INPUT_NAME}"
|
||||
MAIN_DEPENDENCY "${INPUT_NAME}"
|
||||
DEPENDS embedfile
|
||||
COMMENT "Generating string file for ${INPUT_NAME}"
|
||||
)
|
||||
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
|
||||
#include "events.h"
|
||||
|
||||
namespace events {
|
||||
|
||||
util::event<void> EngineUpdate;
|
||||
|
||||
util::event<void> EngineShutdown;
|
||||
|
||||
util::event<void, int, int> GameLeaveState;
|
||||
|
||||
util::event<void, int, int> GameEnterState;
|
||||
|
||||
util::event<void, const char*> GameMissionLoad;
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
#pragma once
|
||||
|
||||
#include "utils/event.h"
|
||||
|
||||
namespace events {
|
||||
|
||||
extern util::event<void> EngineUpdate;
|
||||
|
||||
extern util::event<void> EngineShutdown;
|
||||
|
||||
extern util::event<void, int, int> GameLeaveState;
|
||||
|
||||
extern util::event<void, int, int> GameEnterState;
|
||||
|
||||
extern util::event<void, const char*> GameMissionLoad;
|
||||
}
|
||||
+10
-10
@@ -23,7 +23,7 @@
|
||||
#include "ship/ship.h"
|
||||
#include "tracing/Monitor.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <cstdlib>
|
||||
|
||||
|
||||
// make use of the LOD checker for tbl/tbm parsing (from weapons.cpp)
|
||||
@@ -63,7 +63,7 @@ int Warp_ball_bitmap = -1;
|
||||
*/
|
||||
void fireball_play_warphole_open_sound(int ship_class, fireball *fb)
|
||||
{
|
||||
int sound_index;
|
||||
gamesnd_id sound_index;
|
||||
float range_multiplier = 1.0f;
|
||||
object *fireball_objp;
|
||||
|
||||
@@ -73,13 +73,13 @@ void fireball_play_warphole_open_sound(int ship_class, fireball *fb)
|
||||
}
|
||||
fireball_objp = &Objects[fb->objnum];
|
||||
|
||||
sound_index = SND_WARP_IN;
|
||||
sound_index = gamesnd_id(GameSounds::WARP_IN);
|
||||
|
||||
if(fb->warp_open_sound_index > -1) {
|
||||
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()))) {
|
||||
if ( Ship_info[ship_class].is_huge_ship() ) {
|
||||
sound_index = SND_CAPITAL_WARP_IN;
|
||||
sound_index = gamesnd_id(GameSounds::CAPITAL_WARP_IN);
|
||||
fb->flags |= FBF_WARP_CAPITAL_SIZE;
|
||||
} else if ( Ship_info[ship_class].is_big_ship() ) {
|
||||
range_multiplier = 6.0f;
|
||||
@@ -95,18 +95,18 @@ void fireball_play_warphole_open_sound(int ship_class, fireball *fb)
|
||||
*/
|
||||
void fireball_play_warphole_close_sound(fireball *fb)
|
||||
{
|
||||
int sound_index;
|
||||
gamesnd_id sound_index;
|
||||
|
||||
object *fireball_objp;
|
||||
|
||||
fireball_objp = &Objects[fb->objnum];
|
||||
|
||||
sound_index = SND_WARP_OUT;
|
||||
sound_index = gamesnd_id(GameSounds::WARP_OUT);
|
||||
|
||||
if ( fb->warp_close_sound_index > -1 ) {
|
||||
if ( fb->warp_close_sound_index.isValid() ) {
|
||||
sound_index = fb->warp_close_sound_index;
|
||||
} else if ( fb->flags & FBF_WARP_CAPITAL_SIZE ) {
|
||||
sound_index = SND_CAPITAL_WARP_OUT;
|
||||
sound_index = gamesnd_id(GameSounds::CAPITAL_WARP_OUT);
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
@@ -696,7 +696,7 @@ int fireball_get_lod(vec3d *pos, fireball_info *fd, float size)
|
||||
/**
|
||||
* Create a fireball, return object index.
|
||||
*/
|
||||
int fireball_create( vec3d * pos, int fireball_type, int render_type, int parent_obj, float size, int reverse, vec3d *velocity, float warp_lifetime, int ship_class, matrix *orient_override, int low_res, int extra_flags, int warp_open_sound, int warp_close_sound)
|
||||
int fireball_create( vec3d * pos, int fireball_type, int render_type, int parent_obj, float size, int reverse, vec3d *velocity, float warp_lifetime, int ship_class, matrix *orient_override, int low_res, int extra_flags, gamesnd_id warp_open_sound, gamesnd_id warp_close_sound)
|
||||
{
|
||||
int n, objnum, fb_lod;
|
||||
object *obj;
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
|
||||
#include "globalincs/pstypes.h"
|
||||
#include "model/modelrender.h"
|
||||
#include "gamesnd/gamesnd.h"
|
||||
|
||||
class object;
|
||||
class ship_info;
|
||||
@@ -71,8 +72,8 @@ typedef struct fireball {
|
||||
char lod; // current LOD
|
||||
float time_elapsed; // in seconds
|
||||
float total_time; // total lifetime of animation in seconds
|
||||
int warp_open_sound_index; // for warp-effect - Goober5000
|
||||
int warp_close_sound_index; // for warp-effect - Goober5000
|
||||
gamesnd_id warp_open_sound_index; // for warp-effect - Goober5000
|
||||
gamesnd_id warp_close_sound_index; // for warp-effect - Goober5000
|
||||
} fireball;
|
||||
// end move
|
||||
|
||||
@@ -84,7 +85,7 @@ void fireball_process_post(object * obj, float frame_time);
|
||||
// reversed is for warp_in/out effects
|
||||
// Velocity: If not NULL, the fireball will move at a constant velocity.
|
||||
// warp_lifetime: If warp_lifetime > 0.0f then makes the explosion loop so it lasts this long. Only works for warp effect
|
||||
int fireball_create(vec3d *pos, int fireball_type, int render_type, int parent_obj, float size, int reversed=0, vec3d *velocity=NULL, float warp_lifetime=0.0f, int ship_class=-1, matrix *orient=NULL, int low_res=0, int extra_flags=0, int warp_open_sound=-1, int warp_close_sound=-1);
|
||||
int fireball_create(vec3d *pos, int fireball_type, int render_type, int parent_obj, float size, int reversed=0, vec3d *velocity=NULL, float warp_lifetime=0.0f, int ship_class=-1, matrix *orient=NULL, int low_res=0, int extra_flags=0, gamesnd_id warp_open_sound=gamesnd_id(), gamesnd_id warp_close_sound=gamesnd_id());
|
||||
void fireball_render_plane(int plane);
|
||||
void fireball_close();
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include "graphics/2d.h"
|
||||
#include "graphics/font.h"
|
||||
#include "io/timer.h"
|
||||
#include "mission/missionparse.h"
|
||||
#include "mod_table/mod_table.h"
|
||||
#include "network/multi.h"
|
||||
#include "network/multi_log.h"
|
||||
@@ -38,13 +39,13 @@
|
||||
|
||||
#ifndef WIN32
|
||||
#include <cstdio>
|
||||
#include <stdlib.h>
|
||||
#include <cstdlib>
|
||||
#include <unistd.h>
|
||||
#include <cerrno>
|
||||
#endif
|
||||
|
||||
#include <string>
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
|
||||
#define FS2NETD_DEFAULT_PORT "12009"
|
||||
@@ -545,7 +546,7 @@ static void fs2netd_handle_ping()
|
||||
// make sure that we are good to go
|
||||
if ( !Is_connected ) {
|
||||
if (!Is_standalone) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
popup(PF_USE_AFFIRMATIVE_ICON | PF_TITLE_BIG | PF_TITLE_RED, 1, POPUP_OK, "ERROR:\nLost connection to the FS2NetD server!");
|
||||
}
|
||||
|
||||
@@ -587,7 +588,7 @@ static void fs2netd_handle_ping()
|
||||
// make sure that we are good to go
|
||||
if ( !Is_connected ) {
|
||||
if (!Is_standalone) {
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
popup(PF_USE_AFFIRMATIVE_ICON | PF_TITLE_BIG | PF_TITLE_RED, 1, POPUP_OK, "ERROR:\nLost connection to the FS2NetD server!");
|
||||
}
|
||||
|
||||
@@ -638,7 +639,7 @@ static void fs2netd_handle_messages()
|
||||
os_sleep(20);
|
||||
}
|
||||
|
||||
if ( (bytes_read == 0) || (bytes_read < BASE_PACKET_SIZE) ) {
|
||||
if ( (bytes_read < BASE_PACKET_SIZE) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1100,7 +1101,7 @@ void fs2netd_store_stats()
|
||||
if (Duplicate_login_detected) {
|
||||
Duplicate_login_detected = false;
|
||||
multi_display_chat_msg( XSTR("<Duplicate login detected - stats have been tossed>", 1582), 0, 0 );
|
||||
ml_string( XSTR("<Duplicate login detected - stats have been tossed>", 1583) );
|
||||
ml_string( XSTR("<Duplicate login detected - stats have been tossed>", 1582) );
|
||||
fs2netd_store_stats_results();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -30,7 +30,7 @@
|
||||
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
|
||||
extern SCP_vector<crc_valid_status> Table_valid_status;
|
||||
|
||||
@@ -23,15 +23,15 @@
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <netdb.h>
|
||||
#include <stdlib.h>
|
||||
#include <cstdlib>
|
||||
#include <unistd.h>
|
||||
#include <cerrno>
|
||||
#include <sys/ioctl.h>
|
||||
#include <signal.h>
|
||||
#include <csignal>
|
||||
#ifdef SCP_SOLARIS
|
||||
#include <sys/filio.h>
|
||||
#endif
|
||||
#include <ctype.h>
|
||||
#include <cctype>
|
||||
|
||||
#define WSAGetLastError() (errno)
|
||||
#define RESTART(syscall) \
|
||||
@@ -94,7 +94,7 @@ int FS2NetD_ConnectToServer(const char *host, const char *port)
|
||||
|
||||
mySocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
|
||||
|
||||
if (mySocket == SOCKET_ERROR) {
|
||||
if (mySocket == (SOCKET)SOCKET_ERROR) {
|
||||
#ifdef SCP_UNIX
|
||||
my_error = errno;
|
||||
ml_printf("FS2NetD ERROR: Couldn't get socket (\"%s\")!", strerror(my_error));
|
||||
|
||||
@@ -8,8 +8,8 @@
|
||||
*/
|
||||
|
||||
|
||||
#include <string.h>
|
||||
#include <setjmp.h>
|
||||
#include <cstring>
|
||||
#include <csetjmp>
|
||||
|
||||
#include "controlconfig/controlsconfig.h"
|
||||
#include "debugconsole/console.h"
|
||||
@@ -483,7 +483,7 @@ void parse_helptbl(const char *filename)
|
||||
break;
|
||||
case 4: // $end
|
||||
default:
|
||||
Assertion(false, "This should never happen.\n");
|
||||
UNREACHABLE("This should never happen.\n");
|
||||
break;
|
||||
}
|
||||
} // end while
|
||||
|
||||
@@ -255,7 +255,7 @@ void gameplay_help_goto_prev_screen()
|
||||
if (Current_help_page < GP_FIRST_SCREEN) {
|
||||
Current_help_page = Gp_last_screen;
|
||||
}
|
||||
gamesnd_play_iface(SND_SWITCH_SCREENS);
|
||||
gamesnd_play_iface(InterfaceSounds::SWITCH_SCREENS);
|
||||
|
||||
}
|
||||
|
||||
@@ -266,7 +266,7 @@ void gameplay_help_goto_next_screen()
|
||||
if (Current_help_page > Gp_last_screen) {
|
||||
Current_help_page = GP_FIRST_SCREEN;
|
||||
}
|
||||
gamesnd_play_iface(SND_SWITCH_SCREENS);
|
||||
gamesnd_play_iface(InterfaceSounds::SWITCH_SCREENS);
|
||||
}
|
||||
|
||||
// called when the screen is exited
|
||||
@@ -321,7 +321,7 @@ void gameplay_help_button_pressed(int n)
|
||||
|
||||
case CONTINUE_BUTTON:
|
||||
gameplay_help_leave();
|
||||
gamesnd_play_iface(SND_COMMIT_PRESSED);
|
||||
gamesnd_play_iface(InterfaceSounds::COMMIT_PRESSED);
|
||||
break;
|
||||
|
||||
default:
|
||||
@@ -790,7 +790,7 @@ void gameplay_help_draw_text()
|
||||
}
|
||||
|
||||
// gameplay_help_do_frame() is the function that displays help when acutally playing the game
|
||||
void gameplay_help_do_frame(float frametime)
|
||||
void gameplay_help_do_frame(float /*frametime*/)
|
||||
{
|
||||
int i, k;
|
||||
|
||||
|
||||
@@ -1340,7 +1340,7 @@ void parse_menumusic()
|
||||
if(optional_string("$Filename:"))
|
||||
{
|
||||
stuff_string(fname, F_LNAME, MAX_FILENAME_LEN);
|
||||
if ( strnicmp(fname, NOX("none.wav"), 4) ) {
|
||||
if ( strnicmp(fname, NOX("none.wav"), 4) != 0 ) {
|
||||
strcpy_s( Spooled_music[idx].filename, fname );
|
||||
}
|
||||
else
|
||||
|
||||
+110
-110
@@ -8,7 +8,7 @@
|
||||
*/
|
||||
|
||||
#include <sstream>
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
|
||||
#include "gamesnd/gamesnd.h"
|
||||
#include "localization/localize.h"
|
||||
@@ -19,7 +19,7 @@
|
||||
|
||||
SCP_vector<game_snd> Snds;
|
||||
SCP_vector<game_snd> Snds_iface;
|
||||
SCP_vector<int> Snds_iface_handle;
|
||||
SCP_vector<sound_handle> Snds_iface_handle;
|
||||
|
||||
// jg18 - default priorities and limits for retail gameplay sounds
|
||||
static const int NUM_RETAIL_GAMEPLAY_SOUNDS = 192; // indices 0-191, from retail sounds.tbl
|
||||
@@ -258,12 +258,12 @@ void gamesnd_add_retail_default_enhanced_sound_data()
|
||||
}
|
||||
}
|
||||
|
||||
void gamesnd_play_iface(int n)
|
||||
void gamesnd_play_iface(interface_snd_id n)
|
||||
{
|
||||
if (Snds_iface_handle[n] >= 0)
|
||||
snd_stop(Snds_iface_handle[n]);
|
||||
if (Snds_iface_handle[n.value()].isValid())
|
||||
snd_stop(Snds_iface_handle[n.value()]);
|
||||
|
||||
Snds_iface_handle[n] = snd_play(gamesnd_get_interface_sound(n));
|
||||
Snds_iface_handle[n.value()] = snd_play(gamesnd_get_interface_sound(n));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -288,7 +288,7 @@ int gamesnd_lookup_name(const char* name, const SCP_vector<game_snd>& sounds)
|
||||
|
||||
for(SCP_vector<game_snd>::const_iterator snd = sounds.begin(); snd != sounds.end(); ++snd)
|
||||
{
|
||||
if (!snd->name.compare(name))
|
||||
if (snd->name == name)
|
||||
{
|
||||
return i;
|
||||
}
|
||||
@@ -299,7 +299,7 @@ int gamesnd_lookup_name(const char* name, const SCP_vector<game_snd>& sounds)
|
||||
}
|
||||
|
||||
// WMC - now ignores file extension.
|
||||
int gamesnd_get_by_name(const char* name)
|
||||
gamesnd_id gamesnd_get_by_name(const char* name)
|
||||
{
|
||||
Assert( Snds.size() <= INT_MAX );
|
||||
|
||||
@@ -308,14 +308,13 @@ int gamesnd_get_by_name(const char* name)
|
||||
if (index < 0)
|
||||
{
|
||||
int i = 0;
|
||||
for(SCP_vector<game_snd>::iterator snd = Snds.begin(); snd != Snds.end(); ++snd)
|
||||
{
|
||||
if (snd->sound_entries.size() != 1) {
|
||||
for (auto& Snd : Snds) {
|
||||
if (Snd.sound_entries.size() != 1) {
|
||||
// Ignore game sounds with more than one sound entry
|
||||
continue;
|
||||
}
|
||||
|
||||
auto& entry = snd->sound_entries.front();
|
||||
auto& entry = Snd.sound_entries.front();
|
||||
char *p = strrchr( entry.filename, '.' );
|
||||
if(p == NULL)
|
||||
{
|
||||
@@ -335,27 +334,26 @@ int gamesnd_get_by_name(const char* name)
|
||||
}
|
||||
}
|
||||
|
||||
return index;
|
||||
return gamesnd_id(index);
|
||||
}
|
||||
|
||||
int gamesnd_get_by_iface_name(const char* name)
|
||||
interface_snd_id gamesnd_get_by_iface_name(const char* name)
|
||||
{
|
||||
Assert( Snds_iface.size() <= INT_MAX );
|
||||
Assert( Snds_iface.size() == Snds_iface_handle.size() );
|
||||
|
||||
int index = gamesnd_lookup_name(name, Snds_iface);
|
||||
auto index = gamesnd_lookup_name(name, Snds_iface);
|
||||
|
||||
if (index < 0)
|
||||
{
|
||||
int i = 0;
|
||||
for(SCP_vector<game_snd>::iterator snd = Snds_iface.begin(); snd != Snds_iface.end(); ++snd)
|
||||
{
|
||||
if (snd->sound_entries.size() != 1) {
|
||||
for (auto& snd : Snds_iface) {
|
||||
if (snd.sound_entries.size() != 1) {
|
||||
// Ignore game sounds with more than one sound entry
|
||||
continue;
|
||||
}
|
||||
|
||||
auto& entry = snd->sound_entries.front();
|
||||
auto& entry = snd.sound_entries.front();
|
||||
char *p = strrchr( entry.filename, '.' );
|
||||
if(p == NULL)
|
||||
{
|
||||
@@ -375,71 +373,36 @@ int gamesnd_get_by_iface_name(const char* name)
|
||||
}
|
||||
}
|
||||
|
||||
return index;
|
||||
return interface_snd_id(index);
|
||||
}
|
||||
|
||||
int gamesnd_get_by_tbl_index(int index)
|
||||
gamesnd_id gamesnd_get_by_tbl_index(int index)
|
||||
{
|
||||
char temp[11];
|
||||
sprintf(temp, "%i", index);
|
||||
|
||||
return gamesnd_lookup_name(temp, Snds);
|
||||
auto idx = gamesnd_lookup_name(temp, Snds);
|
||||
|
||||
if (idx < 0) {
|
||||
return gamesnd_id();
|
||||
} else {
|
||||
return gamesnd_id(idx);
|
||||
}
|
||||
}
|
||||
|
||||
int gamesnd_get_by_iface_tbl_index(int index)
|
||||
interface_snd_id gamesnd_get_by_iface_tbl_index(int index)
|
||||
{
|
||||
Assert( Snds_iface.size() == Snds_iface_handle.size() );
|
||||
|
||||
char temp[11];
|
||||
sprintf(temp, "%i", index);
|
||||
|
||||
return gamesnd_lookup_name(temp, Snds_iface);
|
||||
}
|
||||
auto idx = gamesnd_lookup_name(temp, Snds_iface);
|
||||
|
||||
/**
|
||||
* Helper function for parse_sound and parse_sound_list. Do not use directly.
|
||||
*
|
||||
* @param tag Tag
|
||||
* @param idx_dest Sound index destination
|
||||
* @param object_name Object name being parsed
|
||||
* @param buf Buffer holding string to be parsed
|
||||
* @param flags See the parse_sound_flags enum
|
||||
*
|
||||
*/
|
||||
void parse_sound_core(const char* tag, int *idx_dest, const char* object_name, const char* buf, parse_sound_flags flags)
|
||||
{
|
||||
int idx;
|
||||
|
||||
if(flags & PARSE_SOUND_INTERFACE_SOUND)
|
||||
idx = gamesnd_get_by_iface_name(buf);
|
||||
else
|
||||
idx = gamesnd_get_by_name(buf);
|
||||
|
||||
if(idx != -1)
|
||||
{
|
||||
(*idx_dest) = idx;
|
||||
}
|
||||
|
||||
size_t size_to_check = 0;
|
||||
|
||||
if(flags & PARSE_SOUND_INTERFACE_SOUND)
|
||||
{
|
||||
size_to_check = Snds_iface.size();
|
||||
Assert( Snds_iface.size() == Snds_iface_handle.size() );
|
||||
}
|
||||
else
|
||||
{
|
||||
size_to_check = Snds.size();
|
||||
}
|
||||
|
||||
Assert( size_to_check <= INT_MAX );
|
||||
|
||||
//Ensure sound is in range
|
||||
if((*idx_dest) < -1 || (*idx_dest) >= (int)size_to_check)
|
||||
{
|
||||
(*idx_dest) = -1;
|
||||
Warning(LOCATION, "%s sound index out of range on '%s'. Must be between 0 and " SIZE_T_ARG ". Forcing to -1 (Nonexistent sound).\n",
|
||||
tag, object_name, size_to_check);
|
||||
if (idx < 0) {
|
||||
return interface_snd_id();
|
||||
} else {
|
||||
return interface_snd_id(idx);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -451,18 +414,49 @@ void parse_sound_core(const char* tag, int *idx_dest, const char* object_name, c
|
||||
*
|
||||
* @param tag Tag
|
||||
* @param idx_dest Sound index destination
|
||||
* @param object_name Object name being parsed
|
||||
* @param flags See the parse_sound_flags enum
|
||||
*
|
||||
*/
|
||||
void parse_sound(const char* tag, int *idx_dest, const char* object_name, parse_sound_flags flags)
|
||||
{
|
||||
void parse_game_sound(const char* tag, gamesnd_id* idx_dest) {
|
||||
if(optional_string(tag))
|
||||
{
|
||||
char buf[MAX_FILENAME_LEN];
|
||||
stuff_string(buf, F_NAME, MAX_FILENAME_LEN);
|
||||
SCP_string buf;
|
||||
stuff_string(buf, F_NAME);
|
||||
|
||||
parse_sound_core(tag, idx_dest, object_name, buf, flags);
|
||||
*idx_dest = gamesnd_get_by_name(buf.c_str());
|
||||
|
||||
// The special case "-1" is needed to silence warnings where sounds are intentionally removed
|
||||
if (!idx_dest->isValid() && buf != "-1") {
|
||||
error_display(0, "Could not find game sound with name '%s'!", buf.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse a sound. When using this function for a table entry,
|
||||
* required_string and optional_string aren't needed, as this function deals with
|
||||
* that as its tag parameter, just make sure that the destination sound index can
|
||||
* handle -1 if things don't work out.
|
||||
*
|
||||
* @param tag Tag
|
||||
* @param idx_dest Sound index destination
|
||||
* @param flags See the parse_sound_flags enum
|
||||
*
|
||||
*/
|
||||
void parse_iface_sound(const char* tag, interface_snd_id* idx_dest) {
|
||||
Assert( Snds_iface.size() == Snds_iface_handle.size() );
|
||||
|
||||
if(optional_string(tag))
|
||||
{
|
||||
SCP_string buf;
|
||||
stuff_string(buf, F_NAME);
|
||||
|
||||
*idx_dest = gamesnd_get_by_iface_name(buf.c_str());
|
||||
|
||||
// The special case "-1" is needed to silence warnings where sounds are intentionally removed
|
||||
if (!idx_dest->isValid() && buf != "-1") {
|
||||
error_display(0, "Could not find interface sound with name '%s'!", buf.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -478,14 +472,14 @@ void parse_sound(const char* tag, int *idx_dest, const char* object_name, parse_
|
||||
* @param flags See the parse_sound_flags enum
|
||||
*
|
||||
*/
|
||||
void parse_sound_list(const char* tag, SCP_vector<int>& destination, const char* object_name, parse_sound_flags flags)
|
||||
void parse_iface_sound_list(const char* tag, SCP_vector<interface_snd_id>& destination, const char* object_name, bool scp_list)
|
||||
{
|
||||
if(optional_string(tag))
|
||||
{
|
||||
int check=0;
|
||||
|
||||
//if we're using the old format, parse the first entry separately
|
||||
if(!(flags & PARSE_SOUND_SCP_SOUND_LIST))
|
||||
if(!scp_list)
|
||||
{
|
||||
stuff_int(&check);
|
||||
}
|
||||
@@ -493,20 +487,24 @@ void parse_sound_list(const char* tag, SCP_vector<int>& destination, const char*
|
||||
//now read the rest of the entries on the line
|
||||
for(size_t i=0; !check_for_eoln(); i++)
|
||||
{
|
||||
char buf[MAX_FILENAME_LEN];
|
||||
stuff_string_white(buf, MAX_FILENAME_LEN);
|
||||
SCP_string buf;
|
||||
stuff_string_white(buf);
|
||||
|
||||
//we do this conditionally to avoid adding needless entries when reparsing
|
||||
if(destination.size() <= i)
|
||||
{
|
||||
destination.push_back(-1);
|
||||
destination.push_back(interface_snd_id());
|
||||
}
|
||||
|
||||
parse_sound_core(tag, &destination.at(i), object_name, buf, flags);
|
||||
destination[i] = gamesnd_get_by_iface_name(buf.c_str());
|
||||
|
||||
if (!destination[i].isValid()) {
|
||||
error_display(0, "Could not find interface sound with name '%s'!", buf.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
//if we're using the old format, double check the size)
|
||||
if(!(flags & PARSE_SOUND_SCP_SOUND_LIST) && (destination.size() != (unsigned)check))
|
||||
if(!scp_list && (destination.size() != (unsigned)check))
|
||||
{
|
||||
mprintf(("%s in '%s' has " SIZE_T_ARG " entries. This does not match entered size of %i.", tag, object_name, destination.size(), check));
|
||||
}
|
||||
@@ -529,7 +527,7 @@ void gamesnd_preload_common_sounds()
|
||||
for (SCP_vector<game_snd>::iterator gs = Snds.begin(); gs != Snds.end(); ++gs) {
|
||||
if ( gs->preload ) {
|
||||
for (auto& entry : gs->sound_entries) {
|
||||
if ( entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4) ) {
|
||||
if ( entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4) != 0 ) {
|
||||
game_busy( NOX("** preloading common game sounds **") ); // Animate loading cursor... does nothing if loading screen not active.
|
||||
entry.id = snd_load(&entry, gs->flags);
|
||||
}
|
||||
@@ -550,7 +548,7 @@ void gamesnd_load_gameplay_sounds()
|
||||
for (SCP_vector<game_snd>::iterator gs = Snds.begin(); gs != Snds.end(); ++gs) {
|
||||
if ( !gs->preload ) { // don't try to load anything that's already preloaded
|
||||
for (auto& entry : gs->sound_entries) {
|
||||
if (entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4)) {
|
||||
if (entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4) != 0) {
|
||||
game_busy(NOX("** preloading gameplay sounds **")); // Animate loading cursor... does nothing if loading screen not active.
|
||||
entry.id = snd_load(&entry, gs->flags);
|
||||
}
|
||||
@@ -567,9 +565,9 @@ void gamesnd_unload_gameplay_sounds()
|
||||
Assert( Snds.size() <= INT_MAX );
|
||||
for (SCP_vector<game_snd>::iterator gs = Snds.begin(); gs != Snds.end(); ++gs) {
|
||||
for (auto& entry : gs->sound_entries) {
|
||||
if (entry.id != -1) {
|
||||
if (entry.id.isValid()) {
|
||||
snd_unload(entry.id);
|
||||
entry.id = -1;
|
||||
entry.id = sound_load_id::invalid();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -586,7 +584,7 @@ void gamesnd_load_interface_sounds()
|
||||
Assert( Snds_iface.size() < INT_MAX );
|
||||
for (SCP_vector<game_snd>::iterator si = Snds_iface.begin(); si != Snds_iface.end(); ++si) {
|
||||
for (auto& entry : si->sound_entries) {
|
||||
if ( entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4) ) {
|
||||
if ( entry.filename[0] != 0 && strnicmp(entry.filename, NOX("none.wav"), 4) != 0 ) {
|
||||
entry.id = snd_load(&entry, si->flags);
|
||||
}
|
||||
}
|
||||
@@ -601,9 +599,9 @@ void gamesnd_unload_interface_sounds()
|
||||
Assert( Snds_iface.size() < INT_MAX );
|
||||
for (SCP_vector<game_snd>::iterator si = Snds_iface.begin(); si != Snds_iface.end(); ++si) {
|
||||
for (auto& entry : si->sound_entries) {
|
||||
if ( entry.id != -1 ) {
|
||||
if (entry.id.isValid()) {
|
||||
snd_unload( entry.id );
|
||||
entry.id = -1;
|
||||
entry.id = sound_load_id::invalid();
|
||||
entry.id_sig = -1;
|
||||
}
|
||||
}
|
||||
@@ -619,6 +617,9 @@ void parse_gamesnd_old(game_snd* gs)
|
||||
gs->sound_entries.resize(1);
|
||||
auto& entry = gs->sound_entries.back();
|
||||
|
||||
// Default pitch is 1.0. This is set here in case we don't have a valid file name
|
||||
gs->pitch_range = util::UniformFloatRange(1.0f);
|
||||
|
||||
stuff_string(entry.filename, F_NAME, MAX_FILENAME_LEN, ",");
|
||||
|
||||
if (!stricmp(entry.filename, NOX("empty")))
|
||||
@@ -675,9 +676,6 @@ void parse_gamesnd_old(game_snd* gs)
|
||||
}
|
||||
}
|
||||
|
||||
// Default pitch is 1.0
|
||||
gs->pitch_range = util::UniformFloatRange(1.0f);
|
||||
|
||||
// check for extra values per Mantis #2408
|
||||
ignore_gray_space();
|
||||
if (stuff_int_optional(&temp, true) == 2)
|
||||
@@ -842,6 +840,9 @@ void parse_gamesnd_new(game_snd* gs, bool no_create)
|
||||
// New extended format found
|
||||
stuff_string(name, F_NAME, MAX_FILENAME_LEN);
|
||||
|
||||
// Default pitch is 1.0. This is set here in case we don't have a valid file name
|
||||
gs->pitch_range = util::UniformFloatRange(1.0f);
|
||||
|
||||
if (!stricmp(name, NOX("empty")))
|
||||
{
|
||||
entry->filename[0] = 0;
|
||||
@@ -849,7 +850,7 @@ void parse_gamesnd_new(game_snd* gs, bool no_create)
|
||||
}
|
||||
|
||||
// If the name _doesn't_ match <same> put it into gs->filename;
|
||||
if (stricmp(name, "<same>"))
|
||||
if (stricmp(name, "<same>") != 0)
|
||||
{
|
||||
strcpy_s(entry->filename, name);
|
||||
}
|
||||
@@ -916,9 +917,6 @@ void parse_gamesnd_new(game_snd* gs, bool no_create)
|
||||
error_display(1, "Invalid enhanced sound limit: %d\n", temp_limit);
|
||||
}
|
||||
}
|
||||
|
||||
// Default pitch is 1.0
|
||||
gs->pitch_range = util::UniformFloatRange(1.0f);
|
||||
}
|
||||
|
||||
void gamesnd_parse_entry(game_snd *gs, bool no_create, SCP_vector<game_snd> *lookupVector)
|
||||
@@ -1199,7 +1197,7 @@ void parse_sound_table(const char* filename)
|
||||
if (gamesnd_parse_line(&tempSound, "$Name:", &Snds_iface))
|
||||
{
|
||||
Snds_iface.push_back(game_snd(tempSound));
|
||||
Snds_iface_handle.push_back(-1);
|
||||
Snds_iface_handle.push_back(sound_handle::invalid());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1291,7 +1289,7 @@ void gamesnd_close()
|
||||
*/
|
||||
void common_play_highlight_sound()
|
||||
{
|
||||
gamesnd_play_iface(SND_USER_OVER);
|
||||
gamesnd_play_iface(InterfaceSounds::USER_OVER);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1299,30 +1297,32 @@ void common_play_highlight_sound()
|
||||
*/
|
||||
void gamesnd_play_error_beep()
|
||||
{
|
||||
gamesnd_play_iface(SND_GENERAL_FAIL);
|
||||
gamesnd_play_iface(InterfaceSounds::GENERAL_FAIL);
|
||||
}
|
||||
|
||||
game_snd* gamesnd_get_game_sound(int handle) {
|
||||
Assertion(handle >= 0 && handle < (int) Snds.size(), "Invalid game sound handle %d detected!", handle);
|
||||
return &Snds[handle];
|
||||
game_snd* gamesnd_get_game_sound(gamesnd_id handle) {
|
||||
Assertion(handle.isValid(), "Invalid game sound handle detected!");
|
||||
Assertion(handle.value() < (int) Snds.size(), "Invalid game sound handle %d detected!", handle.value());
|
||||
return &Snds[handle.value()];
|
||||
}
|
||||
game_snd* gamesnd_get_interface_sound(int handle) {
|
||||
Assertion(handle >= 0 && handle < (int) Snds_iface.size(), "Invalid interface sound handle %d detected!", handle);
|
||||
return &Snds_iface[handle];
|
||||
game_snd* gamesnd_get_interface_sound(interface_snd_id handle) {
|
||||
Assertion(handle.isValid(), "Invalid interface sound handle detected!");
|
||||
Assertion(handle.value() < (int) Snds_iface.size(), "Invalid interface sound handle %d detected!", handle.value());
|
||||
return &Snds_iface[handle.value()];
|
||||
}
|
||||
|
||||
bool gamesnd_game_sound_valid(int sound) {
|
||||
return sound >= 0 && sound < (int) Snds.size();
|
||||
bool gamesnd_game_sound_valid(gamesnd_id sound) {
|
||||
return sound.isValid() && sound.value() < (int) Snds.size();
|
||||
}
|
||||
bool gamesnd_interface_sound_valid(int sound) {
|
||||
return sound >= 0 && sound < (int) Snds_iface.size();
|
||||
bool gamesnd_interface_sound_valid(interface_snd_id sound) {
|
||||
return sound.isValid() && sound.value() < (int) Snds_iface.size();
|
||||
}
|
||||
|
||||
float gamesnd_get_max_duration(game_snd* gs) {
|
||||
int max_length = 0;
|
||||
|
||||
for (auto& entry : gs->sound_entries) {
|
||||
if (entry.id < 0) {
|
||||
if (!entry.id.isValid()) {
|
||||
// Lazily load unloaded sound entries when required
|
||||
entry.id = snd_load(&entry, gs->flags);
|
||||
}
|
||||
|
||||
+335
-310
@@ -12,42 +12,8 @@
|
||||
#ifndef __GAMESND_H__
|
||||
#define __GAMESND_H__
|
||||
|
||||
#include "mission/missionparse.h"
|
||||
#include "sound/sound.h"
|
||||
|
||||
|
||||
void gamesnd_parse_soundstbl(); // Loads in general game sounds from sounds.tbl
|
||||
void gamesnd_close(); // close out gamesnd... only call from game_shutdown()!
|
||||
void gamesnd_load_gameplay_sounds();
|
||||
void gamesnd_unload_gameplay_sounds();
|
||||
void gamesnd_load_interface_sounds();
|
||||
void gamesnd_unload_interface_sounds();
|
||||
void gamesnd_preload_common_sounds();
|
||||
void gamesnd_load_gameplay_sounds();
|
||||
void gamesnd_unload_gameplay_sounds();
|
||||
void gamesnd_play_iface(int n);
|
||||
void gamesnd_play_error_beep();
|
||||
int gamesnd_get_by_name(const char* name);
|
||||
int gamesnd_get_by_iface_name(const char* name);
|
||||
int gamesnd_get_by_tbl_index(int index);
|
||||
int gamesnd_get_by_iface_tbl_index(int index);
|
||||
|
||||
//flags for parse_sound and parse_sound_list
|
||||
enum parse_sound_flags
|
||||
{
|
||||
PARSE_SOUND_GENERAL_SOUND = 0, //!< search for sound in the general table in sound.tbl
|
||||
PARSE_SOUND_INTERFACE_SOUND = (1 << 0), //!< Search for sound in the interface part of sounds.tbl
|
||||
PARSE_SOUND_SCP_SOUND_LIST = (1 << 1), //!< Parse the list of sounds SCP style (just indexes and/or files names, no count first)
|
||||
PARSE_SOUND_MAX
|
||||
};
|
||||
|
||||
//This should handle NO_SOUND just fine since it doesn't directly access lowlevel code
|
||||
//Does all parsing for a sound
|
||||
void parse_sound(const char* tag, int* idx_dest, const char* object_name, parse_sound_flags = PARSE_SOUND_GENERAL_SOUND);
|
||||
void parse_sound_list(const char* tag, SCP_vector<int>& destination, const char* object_name, parse_sound_flags = PARSE_SOUND_GENERAL_SOUND);
|
||||
|
||||
// this is a callback, so it needs to be a real function
|
||||
void common_play_highlight_sound();
|
||||
#include "utils/id.h"
|
||||
|
||||
/**
|
||||
* symbolic names for misc. game sounds.
|
||||
@@ -61,325 +27,384 @@ void common_play_highlight_sound();
|
||||
* Then add a symbolic name to the appropriate position in the enum below
|
||||
* and add an entry to sounds.tbl. If there is no .wav file for the sound yet, specify sound_hook.wav in sounds.tbl.
|
||||
*/
|
||||
enum GameSoundsIndex {
|
||||
SND_MISSILE_TRACKING = 0, //!< Missle tracking to acquire a lock (looped)
|
||||
SND_MISSILE_LOCK = 1, //!< Missle lock (non-looping)
|
||||
SND_PRIMARY_CYCLE = 2, //!< cycle primary weapon
|
||||
SND_SECONDARY_CYCLE = 3, //!< cycle secondary weapon
|
||||
SND_ENGINE = 4, //!< engine sound (as heard in cockpit)
|
||||
SND_CARGO_REVEAL = 5, //!< cargo revealed
|
||||
SND_DEATH_ROLL = 6, //!< ship death roll
|
||||
SND_SHIP_EXPLODE_1 = 7, //!< ship explosion 1
|
||||
SND_TARGET_ACQUIRE = 8, //!< target acquried
|
||||
SND_ENERGY_ADJUST = 9, //!< energy level change success
|
||||
SND_ENERGY_ADJUST_FAIL = 10, //!< energy level change fail
|
||||
SND_ENERGY_TRANS = 11, //!< energy transfer success
|
||||
SND_ENERGY_TRANS_FAIL = 12, //!< energy transfer fail
|
||||
SND_FULL_THROTTLE = 13, //!< set full throttle
|
||||
SND_ZERO_THROTTLE = 14, //!< set zero throttle
|
||||
SND_THROTTLE_UP = 15, //!< set 1/3 or 2/3 throttle (up)
|
||||
SND_THROTTLE_DOWN = 16, //!< set 1/3 or 2/3 throttle (down)
|
||||
SND_DOCK_APPROACH = 17, //!< dock approach retros
|
||||
SND_DOCK_ATTACH = 18, //!< dock attach
|
||||
SND_DOCK_DETACH = 19, //!< dock detach
|
||||
SND_DOCK_DEPART = 20, //!< dock depart retros
|
||||
SND_ABURN_ENGAGE = 21, //!< afterburner engage
|
||||
SND_ABURN_LOOP = 22, //!< afterburner burn sound (looped)
|
||||
SND_VAPORIZED = 23, //!< Destroyed by a beam (vaporized)
|
||||
SND_ABURN_FAIL = 24, //!< afterburner fail (no fuel when aburn pressed)
|
||||
SND_HEATLOCK_WARN = 25, //!< heat-seeker launch warning
|
||||
SND_OUT_OF_MISSLES = 26, //!< tried to fire a missle when none are left
|
||||
SND_OUT_OF_WEAPON_ENERGY = 27, //!< tried to fire lasers when not enough energy left
|
||||
SND_TARGET_FAIL = 28, //!< target fail sound (i.e. press targeting key, but nothing happens)
|
||||
SND_SQUADMSGING_ON = 29, //!< squadmate message menu appears
|
||||
SND_SQUADMSGING_OFF = 30, //!< squadmate message menu disappears
|
||||
SND_DEBRIS = 31, //!< debris sound (persistant, looping)
|
||||
SND_SUBSYS_DIE_1 = 32, //!< subsystem gets destroyed on player ship
|
||||
SND_MISSILE_START_LOAD = 33, //!< missle start load (during rearm/repair)
|
||||
SND_MISSILE_LOAD = 34, //!< missle load (during rearm/repair)
|
||||
SND_SHIP_REPAIR = 35, //!< ship is being repaired (during rearm/repair)
|
||||
SND_PLAYER_HIT_LASER = 36, //!< player ship is hit by laser fire
|
||||
SND_PLAYER_HIT_MISSILE = 37, //!< player ship is hit by missile
|
||||
SND_CMEASURE_CYCLE = 38, //!< countermeasure cycle
|
||||
SND_SHIELD_HIT = 39, //!< shield hit
|
||||
SND_SHIELD_HIT_YOU = 40, //!< player shield is hit
|
||||
SND_GAME_MOUSE_CLICK = 41, //!< mouse click
|
||||
SND_ASPECTLOCK_WARN = 42, //!< aspect launch warning
|
||||
SND_SHIELD_XFER_OK = 43, //!< shield quadrant transfer successful
|
||||
SND_ENGINE_WASH = 44, //!< Engine wash (looped)
|
||||
SND_WARP_IN = 45, //!< warp hole opening up for arriving
|
||||
SND_WARP_OUT = 46, //!< warp hole opening up for departing (Same as warp in for now)
|
||||
SND_PLAYER_WARP_FAIL = 47, //!< player warp has failed
|
||||
SND_STATIC = 48, //!< hud gauge static
|
||||
SND_SHIP_EXPLODE_2 = 49, //!< ship explosion 2
|
||||
SND_PLAYER_WARP_OUT = 50, //!< ship is warping out in 3rd person
|
||||
SND_SHIP_SHIP_HEAVY = 51, //!< heavy ship-ship collide sound
|
||||
SND_SHIP_SHIP_LIGHT = 52, //!< light ship-ship collide sound
|
||||
SND_SHIP_SHIP_SHIELD = 53, //!< shield ship-ship collide overlay sound
|
||||
SND_THREAT_FLASH = 54, //!< missile threat indicator flashes
|
||||
SND_PROXIMITY_WARNING = 55, //!< proximity warning (heat seeker)
|
||||
SND_PROXIMITY_ASPECT_WARNING = 56, //!< proximity warning (aspect)
|
||||
SND_DIRECTIVE_COMPLETE = 57, //!< directive complete
|
||||
SND_SUBSYS_EXPLODE = 58, //!< other ship subsystem destroyed
|
||||
SND_CAPSHIP_EXPLODE = 59, //!< captial ship explosion
|
||||
SND_CAPSHIP_SUBSYS_EXPLODE = 60, //!< captial ship subsystem destroyed
|
||||
SND_LARGESHIP_WARPOUT = 61, //!< large ship warps out
|
||||
SND_ASTEROID_EXPLODE_LARGE = 62, //!< large asteroid blows up
|
||||
SND_ASTEROID_EXPLODE_SMALL = 63, //!< small asteroid blows up
|
||||
SND_CUE_VOICE = 64, //!< sound to indicate voice is about to start
|
||||
SND_END_VOICE = 65, //!< sound to indicate voice has ended
|
||||
SND_CARGO_SCAN = 66, //!< cargo scanning (looped)
|
||||
SND_WEAPON_FLYBY = 67, //!< weapon flyby sound
|
||||
SND_ASTEROID = 68, //!< asteroid sound (persistant, looped)
|
||||
SND_CAPITAL_WARP_IN = 69, //!< capital warp hole opening
|
||||
SND_CAPITAL_WARP_OUT = 70, //!< capital warp hole closing
|
||||
SND_ENGINE_LOOP_LARGE = 71, //!< LARGE engine ambient
|
||||
SND_SUBSPACE_LEFT_CHANNEL = 72, //!< subspace ambient sound (left channel) (looped)
|
||||
SND_SUBSPACE_RIGHT_CHANNEL = 73, //!< subspace ambient sound (right channel) (looped)
|
||||
SND_MISSILE_EVADED_POPUP = 74, //!< "evaded" HUD popup
|
||||
SND_ENGINE_LOOP_HUGE = 75, //!< HUGE engine ambient
|
||||
enum class GameSounds {
|
||||
MISSILE_TRACKING = 0, //!< Missle tracking to acquire a lock (looped)
|
||||
MISSILE_LOCK = 1, //!< Missle lock (non-looping)
|
||||
PRIMARY_CYCLE = 2, //!< cycle primary weapon
|
||||
SECONDARY_CYCLE = 3, //!< cycle secondary weapon
|
||||
ENGINE = 4, //!< engine sound (as heard in cockpit)
|
||||
CARGO_REVEAL = 5, //!< cargo revealed
|
||||
DEATH_ROLL = 6, //!< ship death roll
|
||||
SHIP_EXPLODE_1 = 7, //!< ship explosion 1
|
||||
TARGET_ACQUIRE = 8, //!< target acquried
|
||||
ENERGY_ADJUST = 9, //!< energy level change success
|
||||
ENERGY_ADJUST_FAIL = 10, //!< energy level change fail
|
||||
ENERGY_TRANS = 11, //!< energy transfer success
|
||||
ENERGY_TRANS_FAIL = 12, //!< energy transfer fail
|
||||
FULL_THROTTLE = 13, //!< set full throttle
|
||||
ZERO_THROTTLE = 14, //!< set zero throttle
|
||||
THROTTLE_UP = 15, //!< set 1/3 or 2/3 throttle (up)
|
||||
THROTTLE_DOWN = 16, //!< set 1/3 or 2/3 throttle (down)
|
||||
DOCK_APPROACH = 17, //!< dock approach retros
|
||||
DOCK_ATTACH = 18, //!< dock attach
|
||||
DOCK_DETACH = 19, //!< dock detach
|
||||
DOCK_DEPART = 20, //!< dock depart retros
|
||||
ABURN_ENGAGE = 21, //!< afterburner engage
|
||||
ABURN_LOOP = 22, //!< afterburner burn sound (looped)
|
||||
VAPORIZED = 23, //!< Destroyed by a beam (vaporized)
|
||||
ABURN_FAIL = 24, //!< afterburner fail (no fuel when aburn pressed)
|
||||
HEATLOCK_WARN = 25, //!< heat-seeker launch warning
|
||||
OUT_OF_MISSLES = 26, //!< tried to fire a missle when none are left
|
||||
OUT_OF_WEAPON_ENERGY = 27, //!< tried to fire lasers when not enough energy left
|
||||
TARGET_FAIL = 28, //!< target fail sound (i.e. press targeting key, but nothing happens)
|
||||
SQUADMSGING_ON = 29, //!< squadmate message menu appears
|
||||
SQUADMSGING_OFF = 30, //!< squadmate message menu disappears
|
||||
DEBRIS = 31, //!< debris sound (persistant, looping)
|
||||
SUBSYS_DIE_1 = 32, //!< subsystem gets destroyed on player ship
|
||||
MISSILE_START_LOAD = 33, //!< missle start load (during rearm/repair)
|
||||
MISSILE_LOAD = 34, //!< missle load (during rearm/repair)
|
||||
SHIP_REPAIR = 35, //!< ship is being repaired (during rearm/repair)
|
||||
PLAYER_HIT_LASER = 36, //!< player ship is hit by laser fire
|
||||
PLAYER_HIT_MISSILE = 37, //!< player ship is hit by missile
|
||||
CMEASURE_CYCLE = 38, //!< countermeasure cycle
|
||||
SHIELD_HIT = 39, //!< shield hit
|
||||
SHIELD_HIT_YOU = 40, //!< player shield is hit
|
||||
GAME_MOUSE_CLICK = 41, //!< mouse click
|
||||
ASPECTLOCK_WARN = 42, //!< aspect launch warning
|
||||
SHIELD_XFER_OK = 43, //!< shield quadrant transfer successful
|
||||
ENGINE_WASH = 44, //!< Engine wash (looped)
|
||||
WARP_IN = 45, //!< warp hole opening up for arriving
|
||||
WARP_OUT = 46, //!< warp hole opening up for departing (Same as warp in for now)
|
||||
PLAYER_WARP_FAIL = 47, //!< player warp has failed
|
||||
STATIC = 48, //!< hud gauge static
|
||||
SHIP_EXPLODE_2 = 49, //!< ship explosion 2
|
||||
PLAYER_WARP_OUT = 50, //!< ship is warping out in 3rd person
|
||||
SHIP_SHIP_HEAVY = 51, //!< heavy ship-ship collide sound
|
||||
SHIP_SHIP_LIGHT = 52, //!< light ship-ship collide sound
|
||||
SHIP_SHIP_SHIELD = 53, //!< shield ship-ship collide overlay sound
|
||||
THREAT_FLASH = 54, //!< missile threat indicator flashes
|
||||
PROXIMITY_WARNING = 55, //!< proximity warning (heat seeker)
|
||||
PROXIMITY_ASPECT_WARNING = 56, //!< proximity warning (aspect)
|
||||
DIRECTIVE_COMPLETE = 57, //!< directive complete
|
||||
SUBSYS_EXPLODE = 58, //!< other ship subsystem destroyed
|
||||
CAPSHIP_EXPLODE = 59, //!< captial ship explosion
|
||||
CAPSHIP_SUBSYS_EXPLODE = 60, //!< captial ship subsystem destroyed
|
||||
LARGESHIP_WARPOUT = 61, //!< large ship warps out
|
||||
ASTEROID_EXPLODE_LARGE = 62, //!< large asteroid blows up
|
||||
ASTEROID_EXPLODE_SMALL = 63, //!< small asteroid blows up
|
||||
CUE_VOICE = 64, //!< sound to indicate voice is about to start
|
||||
END_VOICE = 65, //!< sound to indicate voice has ended
|
||||
CARGO_SCAN = 66, //!< cargo scanning (looped)
|
||||
WEAPON_FLYBY = 67, //!< weapon flyby sound
|
||||
ASTEROID = 68, //!< asteroid sound (persistant, looped)
|
||||
CAPITAL_WARP_IN = 69, //!< capital warp hole opening
|
||||
CAPITAL_WARP_OUT = 70, //!< capital warp hole closing
|
||||
ENGINE_LOOP_LARGE = 71, //!< LARGE engine ambient
|
||||
SUBSPACE_LEFT_CHANNEL = 72, //!< subspace ambient sound (left channel) (looped)
|
||||
SUBSPACE_RIGHT_CHANNEL = 73, //!< subspace ambient sound (right channel) (looped)
|
||||
MISSILE_EVADED_POPUP = 74, //!< "evaded" HUD popup
|
||||
ENGINE_LOOP_HUGE = 75, //!< HUGE engine ambient
|
||||
//Weapons section
|
||||
SND_LIGHT_LASER_FIRE = 76, //!< SD-4 Sidearm laser fired
|
||||
SND_LIGHT_LASER_IMPACT = 77, //!< DR-2 Scalpel fired
|
||||
SND_HVY_LASER_FIRE = 78, //!< Flail II fired
|
||||
SND_HVY_LASER_IMPACT = 79, //!< Prometheus R laser fired
|
||||
SND_MASSDRV_FIRED = 80, //!< Prometheus S laser fired
|
||||
SND_MASSDRV_IMPACT = 81, //!< GTW-66 Newton Cannon fired
|
||||
SND_FLAIL_FIRED = 82, //!< UD-8 Kayser Laser fired
|
||||
SND_FLAIL_IMPACT = 83, //!< GTW-19 Circe laser fired
|
||||
SND_NEUTRON_FLUX_FIRED = 84, //!< GTW-83 Lich laser fired
|
||||
SND_NEUTRON_FLUX_IMPACT = 85, //!< Laser impact
|
||||
SND_DEBUG_LASER_FIRED = 86, //!< Subach-HLV Vasudan laser
|
||||
SND_ROCKEYE_FIRED = 87, //!< rockeye missile launch
|
||||
SND_MISSILE_IMPACT1 = 88, //!< missile impact 1
|
||||
SND_MAG_MISSILE_LAUNCH = 89, //!< mag pulse missile launch
|
||||
SND_FURY_MISSILE_LAUNCH = 90, //!< fury missile launch
|
||||
SND_SHRIKE_MISSILE_LAUNCH = 91, //!< shrike missile launch
|
||||
SND_ANGEL_MISSILE_LAUNCH = 92, //!< angel fire missile launch
|
||||
SND_CLUSTER_MISSILE_LAUNCH = 93, //!< cluster bomb launch
|
||||
SND_CLUSTERB_MISSILE_LAUNCH = 94, //!< cluster baby bomb launch
|
||||
SND_STILETTO_MISSILE_LAUNCH = 95, //!< stiletto bomb launch
|
||||
SND_TSUNAMI_MISSILE_LAUNCH = 96, //!< tsunami bomb launch
|
||||
SND_HARBINGER_MISSILE_LAUNCH = 97, //!< harbinger bomb launch
|
||||
SND_MEGAWOKKA_MISSILE_LAUNCH = 98, //!< mega wokka launch
|
||||
SND_CMEASURE1_LAUNCH = 99, //!< countermeasure 1 launch
|
||||
SND_SHIVAN_LIGHT_LASER_FIRE = 100,//!< Shivan light laser
|
||||
SND_SHOCKWAVE_EXPLODE = 101,//!< shockwave ignition
|
||||
SND_SWARM_MISSILE_LAUNCH = 102,//!< swarm missile sound
|
||||
SND_UNDEFINED_103 = 103,//!< Shivan heavy laser
|
||||
SND_UNDEFINED_104 = 104,//!< Vasudan SuperCap engine
|
||||
SND_UNDEFINED_105 = 105,//!< Shivan SuperCap engine
|
||||
SND_UNDEFINED_106 = 106,//!< Terran SuperCap engine
|
||||
SND_UNDEFINED_107 = 107,//!< Vasudan light laser fired
|
||||
SND_UNDEFINED_108 = 108,//!< Shivan heavy laser
|
||||
SND_SHOCKWAVE_IMPACT = 109,//!< shockwave impact
|
||||
SND_UNDEFINED_110 = 110,//!< TERRAN TURRET 1
|
||||
SND_UNDEFINED_111 = 111,//!< TERRAN TURRET 2
|
||||
SND_UNDEFINED_112 = 112,//!< VASUDAN TURRET 1
|
||||
SND_UNDEFINED_113 = 113,//!< VASUDAN TURRET 2
|
||||
SND_UNDEFINED_114 = 114,//!< SHIVAN TURRET 1
|
||||
SND_TARG_LASER_LOOP = 115,//!< targeting laser loop sound
|
||||
SND_FLAK_FIRE = 116,//!< Flak Gun Launch
|
||||
SND_SHIELD_BREAKER = 117,//!< Flak Gun Impact
|
||||
SND_EMP_MISSILE = 118,//!< EMP Missle
|
||||
SND_AUTOCANNON_LOOP = 119,//!< Escape Pod Drone
|
||||
SND_AUTOCANNON_SHOT = 120,//!< Beam Hit 1
|
||||
SND_BEAM_LOOP = 121,//!< beam loop
|
||||
SND_BEAM_UP = 122,//!< beam power up
|
||||
SND_BEAM_DOWN = 123,//!< beam power down
|
||||
SND_BEAM_SHOT = 124,//!< Beam shot 1
|
||||
SND_BEAM_VAPORIZE = 125,//!< Beam shot 2
|
||||
LIGHT_LASER_FIRE = 76, //!< SD-4 Sidearm laser fired
|
||||
LIGHT_LASER_IMPACT = 77, //!< DR-2 Scalpel fired
|
||||
HVY_LASER_FIRE = 78, //!< Flail II fired
|
||||
HVY_LASER_IMPACT = 79, //!< Prometheus R laser fired
|
||||
MASSDRV_FIRED = 80, //!< Prometheus S laser fired
|
||||
MASSDRV_IMPACT = 81, //!< GTW-66 Newton Cannon fired
|
||||
FLAIL_FIRED = 82, //!< UD-8 Kayser Laser fired
|
||||
FLAIL_IMPACT = 83, //!< GTW-19 Circe laser fired
|
||||
NEUTRON_FLUX_FIRED = 84, //!< GTW-83 Lich laser fired
|
||||
NEUTRON_FLUX_IMPACT = 85, //!< Laser impact
|
||||
DEBUG_LASER_FIRED = 86, //!< Subach-HLV Vasudan laser
|
||||
ROCKEYE_FIRED = 87, //!< rockeye missile launch
|
||||
MISSILE_IMPACT1 = 88, //!< missile impact 1
|
||||
MAG_MISSILE_LAUNCH = 89, //!< mag pulse missile launch
|
||||
FURY_MISSILE_LAUNCH = 90, //!< fury missile launch
|
||||
SHRIKE_MISSILE_LAUNCH = 91, //!< shrike missile launch
|
||||
ANGEL_MISSILE_LAUNCH = 92, //!< angel fire missile launch
|
||||
CLUSTER_MISSILE_LAUNCH = 93, //!< cluster bomb launch
|
||||
CLUSTERB_MISSILE_LAUNCH = 94, //!< cluster baby bomb launch
|
||||
STILETTO_MISSILE_LAUNCH = 95, //!< stiletto bomb launch
|
||||
TSUNAMI_MISSILE_LAUNCH = 96, //!< tsunami bomb launch
|
||||
HARBINGER_MISSILE_LAUNCH = 97, //!< harbinger bomb launch
|
||||
MEGAWOKKA_MISSILE_LAUNCH = 98, //!< mega wokka launch
|
||||
CMEASURE1_LAUNCH = 99, //!< countermeasure 1 launch
|
||||
SHIVAN_LIGHT_LASER_FIRE = 100,//!< Shivan light laser
|
||||
SHOCKWAVE_EXPLODE = 101,//!< shockwave ignition
|
||||
SWARM_MISSILE_LAUNCH = 102,//!< swarm missile sound
|
||||
UNDEFINED_103 = 103,//!< Shivan heavy laser
|
||||
UNDEFINED_104 = 104,//!< Vasudan SuperCap engine
|
||||
UNDEFINED_105 = 105,//!< Shivan SuperCap engine
|
||||
UNDEFINED_106 = 106,//!< Terran SuperCap engine
|
||||
UNDEFINED_107 = 107,//!< Vasudan light laser fired
|
||||
UNDEFINED_108 = 108,//!< Shivan heavy laser
|
||||
SHOCKWAVE_IMPACT = 109,//!< shockwave impact
|
||||
UNDEFINED_110 = 110,//!< TERRAN TURRET 1
|
||||
UNDEFINED_111 = 111,//!< TERRAN TURRET 2
|
||||
UNDEFINED_112 = 112,//!< VASUDAN TURRET 1
|
||||
UNDEFINED_113 = 113,//!< VASUDAN TURRET 2
|
||||
UNDEFINED_114 = 114,//!< SHIVAN TURRET 1
|
||||
TARG_LASER_LOOP = 115,//!< targeting laser loop sound
|
||||
FLAK_FIRE = 116,//!< Flak Gun Launch
|
||||
SHIELD_BREAKER = 117,//!< Flak Gun Impact
|
||||
EMP_MISSILE = 118,//!< EMP Missle
|
||||
AUTOCANNON_LOOP = 119,//!< Escape Pod Drone
|
||||
AUTOCANNON_SHOT = 120,//!< Beam Hit 1
|
||||
BEAM_LOOP = 121,//!< beam loop
|
||||
BEAM_UP = 122,//!< beam power up
|
||||
BEAM_DOWN = 123,//!< beam power down
|
||||
BEAM_SHOT = 124,//!< Beam shot 1
|
||||
BEAM_VAPORIZE = 125,//!< Beam shot 2
|
||||
//Ship Engine Sounds section
|
||||
SND_TERRAN_FIGHTER_ENG = 126,//!< Terran fighter engine
|
||||
SND_TERRAN_BOMBER_ENG = 127,//!< Terran bomber engine
|
||||
SND_TERRAN_CAPITAL_ENG = 128,//!< Terran cruiser engine
|
||||
SND_SPECIESB_FIGHTER_ENG = 129,//!< Vasudan fighter engine
|
||||
SND_SPECIESB_BOMBER_ENG = 130,//!< Vasudan bomber engine
|
||||
SND_SPECIESB_CAPITAL_ENG = 131,//!< Vasudan cruiser engine
|
||||
SND_SHIVAN_FIGHTER_ENG = 132,//!< Shivan fighter engine
|
||||
SND_SHIVAN_BOMBER_ENG = 133,//!< Shivan bomber engine
|
||||
SND_SHIVAN_CAPITAL_ENG = 134,//!< Shivan cruiser engine
|
||||
SND_REPAIR_SHIP_ENG = 135,//!< Repair ship beacon/engine sound
|
||||
SND_UNDEFINED_136 = 136,//!< Terran capital engine
|
||||
SND_UNDEFINED_137 = 137,//!< Vasudan capital engine
|
||||
SND_UNDEFINED_138 = 138,//!< Shivan capital engine
|
||||
TERRAN_FIGHTER_ENG = 126,//!< Terran fighter engine
|
||||
TERRAN_BOMBER_ENG = 127,//!< Terran bomber engine
|
||||
TERRAN_CAPITAL_ENG = 128,//!< Terran cruiser engine
|
||||
SPECIESB_FIGHTER_ENG = 129,//!< Vasudan fighter engine
|
||||
SPECIESB_BOMBER_ENG = 130,//!< Vasudan bomber engine
|
||||
SPECIESB_CAPITAL_ENG = 131,//!< Vasudan cruiser engine
|
||||
SHIVAN_FIGHTER_ENG = 132,//!< Shivan fighter engine
|
||||
SHIVAN_BOMBER_ENG = 133,//!< Shivan bomber engine
|
||||
SHIVAN_CAPITAL_ENG = 134,//!< Shivan cruiser engine
|
||||
REPAIR_SHIP_ENG = 135,//!< Repair ship beacon/engine sound
|
||||
UNDEFINED_136 = 136,//!< Terran capital engine
|
||||
UNDEFINED_137 = 137,//!< Vasudan capital engine
|
||||
UNDEFINED_138 = 138,//!< Shivan capital engine
|
||||
// Electrical arc sound fx on the debris pieces
|
||||
SND_DEBRIS_ARC_01 = 139,//!< 0.10 second spark sound effect
|
||||
SND_DEBRIS_ARC_02 = 140,//!< 0.25 second spark sound effect
|
||||
SND_DEBRIS_ARC_03 = 141,//!< 0.50 second spark sound effect
|
||||
SND_DEBRIS_ARC_04 = 142,//!< 0.75 second spark sound effect
|
||||
SND_DEBRIS_ARC_05 = 143,//!< 1.00 second spark sound effect
|
||||
DEBRIS_ARC_01 = 139,//!< 0.10 second spark sound effect
|
||||
DEBRIS_ARC_02 = 140,//!< 0.25 second spark sound effect
|
||||
DEBRIS_ARC_03 = 141,//!< 0.50 second spark sound effect
|
||||
DEBRIS_ARC_04 = 142,//!< 0.75 second spark sound effect
|
||||
DEBRIS_ARC_05 = 143,//!< 1.00 second spark sound effect
|
||||
// Beam Sounds
|
||||
SND_UNDEFINED_144 = 144,//!< LTerSlash beam loop
|
||||
SND_UNDEFINED_145 = 145,//!< TerSlash beam loop
|
||||
SND_UNDEFINED_146 = 146,//!< SGreen beam loop
|
||||
SND_UNDEFINED_147 = 147,//!< BGreen beem loop
|
||||
SND_UNDEFINED_148 = 148,//!< BFGreen been loop
|
||||
SND_UNDEFINED_149 = 149,//!< Antifighter beam loop
|
||||
SND_UNDEFINED_150 = 150,//!< 1 sec warm up
|
||||
SND_UNDEFINED_151 = 151,//!< 1.5 sec warm up
|
||||
SND_UNDEFINED_152 = 152,//!< 2.5 sec warm up
|
||||
SND_UNDEFINED_153 = 153,//!< 3 sec warm up
|
||||
SND_UNDEFINED_154 = 154,//!< 3.5 sec warm up
|
||||
SND_UNDEFINED_155 = 155,//!< 5 sec warm up
|
||||
SND_UNDEFINED_156 = 156,//!< LTerSlash warm down
|
||||
SND_UNDEFINED_157 = 157,//!< TerSlash warm down
|
||||
SND_UNDEFINED_158 = 158,//!< SGreen warm down
|
||||
SND_UNDEFINED_159 = 159,//!< BGreen warm down
|
||||
SND_UNDEFINED_160 = 160,//!< BFGreen warm down
|
||||
SND_UNDEFINED_161 = 161,//!< T_AntiFtr warm down
|
||||
UNDEFINED_144 = 144,//!< LTerSlash beam loop
|
||||
UNDEFINED_145 = 145,//!< TerSlash beam loop
|
||||
UNDEFINED_146 = 146,//!< SGreen beam loop
|
||||
UNDEFINED_147 = 147,//!< BGreen beem loop
|
||||
UNDEFINED_148 = 148,//!< BFGreen been loop
|
||||
UNDEFINED_149 = 149,//!< Antifighter beam loop
|
||||
UNDEFINED_150 = 150,//!< 1 sec warm up
|
||||
UNDEFINED_151 = 151,//!< 1.5 sec warm up
|
||||
UNDEFINED_152 = 152,//!< 2.5 sec warm up
|
||||
UNDEFINED_153 = 153,//!< 3 sec warm up
|
||||
UNDEFINED_154 = 154,//!< 3.5 sec warm up
|
||||
UNDEFINED_155 = 155,//!< 5 sec warm up
|
||||
UNDEFINED_156 = 156,//!< LTerSlash warm down
|
||||
UNDEFINED_157 = 157,//!< TerSlash warm down
|
||||
UNDEFINED_158 = 158,//!< SGreen warm down
|
||||
UNDEFINED_159 = 159,//!< BGreen warm down
|
||||
UNDEFINED_160 = 160,//!< BFGreen warm down
|
||||
UNDEFINED_161 = 161,//!< T_AntiFtr warm down
|
||||
|
||||
SND_COPILOT = 162,//!< copilot (SCP)
|
||||
SND_UNDEFINED_163 = 163,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_164 = 164,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_165 = 165,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_166 = 166,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_167 = 167,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_168 = 168,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_169 = 169,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_170 = 170,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_171 = 171,//!< (Empty in Retail)
|
||||
SND_UNDEFINED_172 = 172,//!< (Empty in Retail)
|
||||
SND_SUPERNOVA_1 = 173,//!< SuperNova (distant)
|
||||
SND_SUPERNOVA_2 = 174,//!< SuperNova (shockwave)
|
||||
SND_UNDEFINED_175 = 175,//!< Shivan large engine
|
||||
SND_UNDEFINED_176 = 176,//!< Shivan large engine
|
||||
SND_UNDEFINED_177 = 177,//!< SRed beam loop
|
||||
SND_UNDEFINED_178 = 178,//!< LRed beam loop
|
||||
SND_UNDEFINED_179 = 179,//!< Antifighter beam loop
|
||||
SND_LIGHTNING_1 = 180,//!< Thunder 1 sound in neblua
|
||||
SND_LIGHTNING_2 = 181,//!< Thunder 2 sound in neblua
|
||||
SND_UNDEFINED_182 = 182,//!< 1 sec warm up
|
||||
SND_UNDEFINED_183 = 183,//!< 1.5 sec warm up
|
||||
SND_UNDEFINED_184 = 184,//!< 3 sec warm up
|
||||
SND_UNDEFINED_185 = 185,//!< Shivan Commnode
|
||||
SND_UNDEFINED_186 = 186,//!< Volition PirateShip
|
||||
SND_UNDEFINED_187 = 187,//!< SRed warm down
|
||||
SND_UNDEFINED_188 = 188,//!< LRed warm down
|
||||
SND_UNDEFINED_189 = 189,//!< AntiFtr warm down
|
||||
SND_UNDEFINED_190 = 190,//!< Instellation 1
|
||||
SND_UNDEFINED_191 = 191,//!< Instellation 2
|
||||
SND_UNDEFINED_192 = 192,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_193 = 193,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_194 = 194,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_195 = 195,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_196 = 196,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_197 = 197,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_198 = 198,//!< (Undefined in Retail)
|
||||
SND_UNDEFINED_199 = 199,//!< (Undefined in Retail)
|
||||
COPILOT = 162,//!< copilot (SCP)
|
||||
UNDEFINED_163 = 163,//!< (Empty in Retail)
|
||||
UNDEFINED_164 = 164,//!< (Empty in Retail)
|
||||
UNDEFINED_165 = 165,//!< (Empty in Retail)
|
||||
UNDEFINED_166 = 166,//!< (Empty in Retail)
|
||||
UNDEFINED_167 = 167,//!< (Empty in Retail)
|
||||
UNDEFINED_168 = 168,//!< (Empty in Retail)
|
||||
UNDEFINED_169 = 169,//!< (Empty in Retail)
|
||||
UNDEFINED_170 = 170,//!< (Empty in Retail)
|
||||
UNDEFINED_171 = 171,//!< (Empty in Retail)
|
||||
UNDEFINED_172 = 172,//!< (Empty in Retail)
|
||||
SUPERNOVA_1 = 173,//!< SuperNova (distant)
|
||||
SUPERNOVA_2 = 174,//!< SuperNova (shockwave)
|
||||
UNDEFINED_175 = 175,//!< Shivan large engine
|
||||
UNDEFINED_176 = 176,//!< Shivan large engine
|
||||
UNDEFINED_177 = 177,//!< SRed beam loop
|
||||
UNDEFINED_178 = 178,//!< LRed beam loop
|
||||
UNDEFINED_179 = 179,//!< Antifighter beam loop
|
||||
LIGHTNING_1 = 180,//!< Thunder 1 sound in neblua
|
||||
LIGHTNING_2 = 181,//!< Thunder 2 sound in neblua
|
||||
UNDEFINED_182 = 182,//!< 1 sec warm up
|
||||
UNDEFINED_183 = 183,//!< 1.5 sec warm up
|
||||
UNDEFINED_184 = 184,//!< 3 sec warm up
|
||||
UNDEFINED_185 = 185,//!< Shivan Commnode
|
||||
UNDEFINED_186 = 186,//!< Volition PirateShip
|
||||
UNDEFINED_187 = 187,//!< SRed warm down
|
||||
UNDEFINED_188 = 188,//!< LRed warm down
|
||||
UNDEFINED_189 = 189,//!< AntiFtr warm down
|
||||
UNDEFINED_190 = 190,//!< Instellation 1
|
||||
UNDEFINED_191 = 191,//!< Instellation 2
|
||||
UNDEFINED_192 = 192,//!< (Undefined in Retail)
|
||||
UNDEFINED_193 = 193,//!< (Undefined in Retail)
|
||||
UNDEFINED_194 = 194,//!< (Undefined in Retail)
|
||||
UNDEFINED_195 = 195,//!< (Undefined in Retail)
|
||||
UNDEFINED_196 = 196,//!< (Undefined in Retail)
|
||||
UNDEFINED_197 = 197,//!< (Undefined in Retail)
|
||||
UNDEFINED_198 = 198,//!< (Undefined in Retail)
|
||||
UNDEFINED_199 = 199,//!< (Undefined in Retail)
|
||||
|
||||
SND_BALLISTIC_START_LOAD = 200,//!< (SCP)
|
||||
SND_BALLISTIC_LOAD = 201,//!< (SCP)
|
||||
BALLISTIC_START_LOAD = 200,//!< (SCP)
|
||||
BALLISTIC_LOAD = 201,//!< (SCP)
|
||||
|
||||
/**
|
||||
* Keep this below all defined enum values
|
||||
*/
|
||||
MIN_GAME_SOUNDS = 202
|
||||
MIN_GAME_SOUNDS = 202
|
||||
};
|
||||
|
||||
/**
|
||||
* Interface sounds
|
||||
*/
|
||||
enum InterfaceSoundsIndex {
|
||||
SND_IFACE_MOUSE_CLICK =0, //!< mouse click
|
||||
SND_ICON_PICKUP =1, //!< pick up a ship icon (Empty in Retail)
|
||||
SND_ICON_DROP_ON_WING =2, //!< drop a ship icon on a wing slot
|
||||
SND_ICON_DROP =3, //!< drop a ship icon back to the list
|
||||
SND_SCREEN_MODE_PRESSED =4, //!< press briefing, ship selection or weapons bar (top-left)
|
||||
SND_SWITCH_SCREENS =5, //!< Switching to a new screen, but not commit
|
||||
SND_HELP_PRESSED =6, //!< help pressed
|
||||
SND_COMMIT_PRESSED =7, //!< commit pressed
|
||||
SND_PREV_NEXT_PRESSED =8, //!< prev/next pressed
|
||||
SND_SCROLL =9, //!< scroll pressed (and scroll)
|
||||
SND_GENERAL_FAIL =10,//!< general failure sound for any event
|
||||
SND_SHIP_ICON_CHANGE =11,//!< ship animation starts (ie text and ship first appear)
|
||||
SND_MAIN_HALL_AMBIENT =12,//!< ambient sound for the Terran main hall (looping)
|
||||
SND_BTN_SLIDE =13,//!< ambient sound for the Vasudan main hall (looping)
|
||||
SND_BRIEF_STAGE_CHG =14,//!< brief stage change
|
||||
SND_BRIEF_STAGE_CHG_FAIL =15,//!< brief stage change fail
|
||||
SND_BRIEF_ICON_SELECT =16,//!< selet brief icon
|
||||
SND_USER_OVER =17,//!< user_over (mouse over a control)
|
||||
SND_USER_SELECT =18,//!< user_click (mouse selects a control)
|
||||
SND_RESET_PRESSED =19,//!< reset (or similar button) pressed
|
||||
SND_BRIEF_TEXT_WIPE =20,//!< briefing text wipe
|
||||
SND_VASUDAN_PA_1 =21,//!< main hall - elevator
|
||||
SND_WEAPON_ANIM_START =22,//!< weapon animation starts
|
||||
SND_MAIN_HALL_DOOR_OPEN =23,//!< door in main hall opens
|
||||
SND_MAIN_HALL_DOOR_CLOSE =24,//!< door in main hall closes
|
||||
SND_GLOW_OPEN =25,//!< glow in main hall opens
|
||||
SND_VASUDAN_PA_2 =26,//!< main hall - crane 1
|
||||
SND_AMBIENT_MENU =27,//!< ambient sound for menus off the main hall (looping)
|
||||
SND_POPUP_APPEAR =28,//!< popup dialog box appeared
|
||||
SND_POPUP_DISAPPEAR =29,//!< popup dialog box goes away
|
||||
SND_VOICE_SLIDER_CLIP =30,//!< voice clip played when volume slider changes
|
||||
SND_VASUDAN_PA_3 =31,//!< main hall - crane 2
|
||||
SND_MAIN_HALL_GET_PEPSI =32,//!< main hall options - mouse on
|
||||
SND_MAIN_HALL_LIFT_UP =33,//!< main hall options - mouse off
|
||||
SND_MAIN_HALL_WELD1 =34,//!< main hall tech room - mouse on
|
||||
SND_MAIN_HALL_WELD2 =35,//!< main hall tech room - mouse off
|
||||
SND_MAIN_HALL_WELD3 =36,//!< main hall exit open
|
||||
SND_MAIN_HALL_WELD4 =37,//!< main hall exit close
|
||||
SND_MAIN_HALL_INT1 =38,//!< main hall random intercom 1
|
||||
SND_MAIN_HALL_INT2 =39,//!< main hall random intercom 2
|
||||
SND_MAIN_HALL_INT3 =40,//!< main hall random intercom 3
|
||||
SND_ICON_HIGHLIGHT =41,//!< spinning highlight in briefing
|
||||
SND_BRIEFING_STATIC =42,//!< static in a briefing stage cut
|
||||
SND_MAIN_HALL2_CRANE1_1 =43,//!< main hall campaign - mouse on
|
||||
SND_MAIN_HALL2_CRANE1_2 =44,//!< main hall campaign - mouse off
|
||||
SND_MAIN_HALL2_CRANE2_1 =45,//!< vasudan hall - hatch open
|
||||
SND_MAIN_HALL2_CRANE2_2 =46,//!< vasudan hall - hatch close
|
||||
SND_MAIN_HALL2_CAR1 =47,//!< vasudan hall - roll open
|
||||
SND_MAIN_HALL2_CAR2 =48,//!< vasudan hall - roll close
|
||||
SND_MAIN_HALL2_INT1 =49,//!< vasudan hall - lift up
|
||||
SND_MAIN_HALL2_INT2 =50,//!< vasudan hall - lift down
|
||||
SND_MAIN_HALL2_INT3 =51,//!< vasudan hall - glow on
|
||||
SND_INTERFACE_UNDEFINED_52 =52,//!< vasudan hall - glow off
|
||||
SND_INTERFACE_UNDEFINED_53 =53,//!< vasudan hall - skiff loop
|
||||
SND_INTERFACE_UNDEFINED_54 =54,//!< vasudan hall - screen on
|
||||
SND_INTERFACE_UNDEFINED_55 =55,//!< vasudan hall - screen off
|
||||
SND_INTERFACE_UNDEFINED_56 =56,//!< vasudan hall - vasudan greeting
|
||||
SND_INTERFACE_UNDEFINED_57 =57,//!< vasudan hall - vasudan bye
|
||||
SND_INTERFACE_UNDEFINED_58 =58,//!< vasudan hall - vasudan pa 1
|
||||
SND_INTERFACE_UNDEFINED_59 =59,//!< vasudan hall - vasudan pa 2
|
||||
SND_INTERFACE_UNDEFINED_60 =60,//!< vasudan hall - vasudan pa 3
|
||||
SND_VASUDAN_BUP =61,//!< bup bup bup-bup bup bup
|
||||
SND_INTERFACE_UNDEFINED_62 =62,//!< thankyou
|
||||
SND_INTERFACE_UNDEFINED_63 =62,//!< vasudan hall - exit open
|
||||
SND_INTERFACE_UNDEFINED_64 =62,//!< vasudan hall - exit close
|
||||
enum InterfaceSounds {
|
||||
IFACE_MOUSE_CLICK =0, //!< mouse click
|
||||
ICON_PICKUP =1, //!< pick up a ship icon (Empty in Retail)
|
||||
ICON_DROP_ON_WING =2, //!< drop a ship icon on a wing slot
|
||||
ICON_DROP =3, //!< drop a ship icon back to the list
|
||||
SCREEN_MODE_PRESSED =4, //!< press briefing, ship selection or weapons bar (top-left)
|
||||
SWITCH_SCREENS =5, //!< Switching to a new screen, but not commit
|
||||
HELP_PRESSED =6, //!< help pressed
|
||||
COMMIT_PRESSED =7, //!< commit pressed
|
||||
PREV_NEXT_PRESSED =8, //!< prev/next pressed
|
||||
SCROLL =9, //!< scroll pressed (and scroll)
|
||||
GENERAL_FAIL =10,//!< general failure sound for any event
|
||||
SHIP_ICON_CHANGE =11,//!< ship animation starts (ie text and ship first appear)
|
||||
MAIN_HALL_AMBIENT =12,//!< ambient sound for the Terran main hall (looping)
|
||||
BTN_SLIDE =13,//!< ambient sound for the Vasudan main hall (looping)
|
||||
BRIEF_STAGE_CHG =14,//!< brief stage change
|
||||
BRIEF_STAGE_CHG_FAIL =15,//!< brief stage change fail
|
||||
BRIEF_ICON_SELECT =16,//!< selet brief icon
|
||||
USER_OVER =17,//!< user_over (mouse over a control)
|
||||
USER_SELECT =18,//!< user_click (mouse selects a control)
|
||||
RESET_PRESSED =19,//!< reset (or similar button) pressed
|
||||
BRIEF_TEXT_WIPE =20,//!< briefing text wipe
|
||||
VASUDAN_PA_1 =21,//!< main hall - elevator
|
||||
WEAPON_ANIM_START =22,//!< weapon animation starts
|
||||
MAIN_HALL_DOOR_OPEN =23,//!< door in main hall opens
|
||||
MAIN_HALL_DOOR_CLOSE =24,//!< door in main hall closes
|
||||
GLOW_OPEN =25,//!< glow in main hall opens
|
||||
VASUDAN_PA_2 =26,//!< main hall - crane 1
|
||||
AMBIENT_MENU =27,//!< ambient sound for menus off the main hall (looping)
|
||||
POPUP_APPEAR =28,//!< popup dialog box appeared
|
||||
POPUP_DISAPPEAR =29,//!< popup dialog box goes away
|
||||
VOICE_SLIDER_CLIP =30,//!< voice clip played when volume slider changes
|
||||
VASUDAN_PA_3 =31,//!< main hall - crane 2
|
||||
MAIN_HALL_GET_PEPSI =32,//!< main hall options - mouse on
|
||||
MAIN_HALL_LIFT_UP =33,//!< main hall options - mouse off
|
||||
MAIN_HALL_WELD1 =34,//!< main hall tech room - mouse on
|
||||
MAIN_HALL_WELD2 =35,//!< main hall tech room - mouse off
|
||||
MAIN_HALL_WELD3 =36,//!< main hall exit open
|
||||
MAIN_HALL_WELD4 =37,//!< main hall exit close
|
||||
MAIN_HALL_INT1 =38,//!< main hall random intercom 1
|
||||
MAIN_HALL_INT2 =39,//!< main hall random intercom 2
|
||||
MAIN_HALL_INT3 =40,//!< main hall random intercom 3
|
||||
ICON_HIGHLIGHT =41,//!< spinning highlight in briefing
|
||||
BRIEFING_STATIC =42,//!< static in a briefing stage cut
|
||||
MAIN_HALL2_CRANE1_1 =43,//!< main hall campaign - mouse on
|
||||
MAIN_HALL2_CRANE1_2 =44,//!< main hall campaign - mouse off
|
||||
MAIN_HALL2_CRANE2_1 =45,//!< vasudan hall - hatch open
|
||||
MAIN_HALL2_CRANE2_2 =46,//!< vasudan hall - hatch close
|
||||
MAIN_HALL2_CAR1 =47,//!< vasudan hall - roll open
|
||||
MAIN_HALL2_CAR2 =48,//!< vasudan hall - roll close
|
||||
MAIN_HALL2_INT1 =49,//!< vasudan hall - lift up
|
||||
MAIN_HALL2_INT2 =50,//!< vasudan hall - lift down
|
||||
MAIN_HALL2_INT3 =51,//!< vasudan hall - glow on
|
||||
INTERFACE_UNDEFINED_52 =52,//!< vasudan hall - glow off
|
||||
INTERFACE_UNDEFINED_53 =53,//!< vasudan hall - skiff loop
|
||||
INTERFACE_UNDEFINED_54 =54,//!< vasudan hall - screen on
|
||||
INTERFACE_UNDEFINED_55 =55,//!< vasudan hall - screen off
|
||||
INTERFACE_UNDEFINED_56 =56,//!< vasudan hall - vasudan greeting
|
||||
INTERFACE_UNDEFINED_57 =57,//!< vasudan hall - vasudan bye
|
||||
INTERFACE_UNDEFINED_58 =58,//!< vasudan hall - vasudan pa 1
|
||||
INTERFACE_UNDEFINED_59 =59,//!< vasudan hall - vasudan pa 2
|
||||
INTERFACE_UNDEFINED_60 =60,//!< vasudan hall - vasudan pa 3
|
||||
VASUDAN_BUP =61,//!< bup bup bup-bup bup bup
|
||||
INTERFACE_UNDEFINED_62 =62,//!< thankyou
|
||||
INTERFACE_UNDEFINED_63 =62,//!< vasudan hall - exit open
|
||||
INTERFACE_UNDEFINED_64 =62,//!< vasudan hall - exit close
|
||||
|
||||
/**
|
||||
* Keep this below all defined enum values
|
||||
*/
|
||||
MIN_INTERFACE_SOUNDS =70 //!< MIN_INTERFACE_SOUNDS
|
||||
MIN_INTERFACE_SOUNDS =70 //!< MIN_INTERFACE_SOUNDS
|
||||
};
|
||||
|
||||
// These two id types are defined as sublcasses so that type safe implicit conversions are possible from the predefined
|
||||
// sound enum values
|
||||
|
||||
struct gamesnd_id_tag{};
|
||||
/**
|
||||
* @brief A game sound handle type
|
||||
*
|
||||
* This allows implicit conversions from the GameSounds enum class.
|
||||
*/
|
||||
class gamesnd_id : public util::ID<gamesnd_id_tag, int, -1> {
|
||||
public:
|
||||
/*implicit*/ gamesnd_id(GameSounds snd) : util::ID<gamesnd_id_tag, int, -1>(static_cast<int>(snd)) {}
|
||||
explicit gamesnd_id(int val) : ID(val) {
|
||||
}
|
||||
gamesnd_id() {
|
||||
}
|
||||
};
|
||||
|
||||
struct interface_snd_tag{};
|
||||
/**
|
||||
* @brief A interface sound handle type
|
||||
*
|
||||
* This allows implicit conversions from the InterfaceSounds enum class.
|
||||
*/
|
||||
class interface_snd_id : public util::ID<interface_snd_tag, int, -1> {
|
||||
public:
|
||||
/*implicit*/ interface_snd_id(InterfaceSounds snd) : util::ID<interface_snd_tag, int, -1>(static_cast<int>(snd)) {}
|
||||
interface_snd_id() {
|
||||
}
|
||||
explicit interface_snd_id(int val) : ID(val) {
|
||||
}
|
||||
};
|
||||
|
||||
void gamesnd_parse_soundstbl(); // Loads in general game sounds from sounds.tbl
|
||||
void gamesnd_close(); // close out gamesnd... only call from game_shutdown()!
|
||||
void gamesnd_load_gameplay_sounds();
|
||||
void gamesnd_unload_gameplay_sounds();
|
||||
void gamesnd_load_interface_sounds();
|
||||
void gamesnd_unload_interface_sounds();
|
||||
void gamesnd_preload_common_sounds();
|
||||
void gamesnd_load_gameplay_sounds();
|
||||
void gamesnd_unload_gameplay_sounds();
|
||||
void gamesnd_play_iface(interface_snd_id n);
|
||||
void gamesnd_play_error_beep();
|
||||
gamesnd_id gamesnd_get_by_name(const char* name);
|
||||
interface_snd_id gamesnd_get_by_iface_name(const char* name);
|
||||
gamesnd_id gamesnd_get_by_tbl_index(int index);
|
||||
interface_snd_id gamesnd_get_by_iface_tbl_index(int index);
|
||||
|
||||
//This should handle NO_SOUND just fine since it doesn't directly access lowlevel code
|
||||
//Does all parsing for a sound
|
||||
void parse_game_sound(const char* tag, gamesnd_id* idx_dest);
|
||||
|
||||
void parse_iface_sound(const char* tag, interface_snd_id* idx_dest);
|
||||
void parse_iface_sound_list(const char* tag, SCP_vector<interface_snd_id>& destination, const char* object_name, bool scp_list = false);
|
||||
|
||||
// this is a callback, so it needs to be a real function
|
||||
void common_play_highlight_sound();
|
||||
|
||||
/**
|
||||
* @brief Gets a pointer to the game sound with the specified handle
|
||||
* @param handle The sound handle
|
||||
* @return The game sound handle
|
||||
*/
|
||||
game_snd* gamesnd_get_game_sound(int handle);
|
||||
game_snd* gamesnd_get_game_sound(gamesnd_id handle);
|
||||
|
||||
/**
|
||||
* @brief Gets a pointer to the interface sound with the specified handle
|
||||
* @param handle The sound handle
|
||||
* @return The interface sound handle
|
||||
*/
|
||||
game_snd* gamesnd_get_interface_sound(int handle);
|
||||
game_snd* gamesnd_get_interface_sound(interface_snd_id handle);
|
||||
|
||||
/**
|
||||
* @brief Checks if the given sound handle is a valid game sound handle
|
||||
* @param sound The handle to check
|
||||
* @return @c true if the handle is valid
|
||||
*/
|
||||
bool gamesnd_game_sound_valid(int sound);
|
||||
bool gamesnd_game_sound_valid(gamesnd_id sound);
|
||||
|
||||
/**
|
||||
* @brief Checks if the given sound handle is a valid interface sound handle
|
||||
* @param sound The handle to check
|
||||
* @return @c true if the handle is valid
|
||||
*/
|
||||
bool gamesnd_interface_sound_valid(int sound);
|
||||
bool gamesnd_interface_sound_valid(interface_snd_id sound);
|
||||
|
||||
/**
|
||||
* @brief Determines the maximum time this game sound may take to be played.
|
||||
|
||||
@@ -467,7 +467,7 @@ void parse_everything_else(const char *filename)
|
||||
// We have a string; it should be the name of a color to use.
|
||||
stuff_string(temp, F_NAME);
|
||||
for (j = 0; j < TOTAL_COLORS; j++) {
|
||||
if (!temp.compare(COLOR_NAMES[j])) {
|
||||
if (temp == COLOR_NAMES[j]) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -549,7 +549,7 @@ void parse_everything_else(const char *filename)
|
||||
// We have a string; it should be the name of a color to use.
|
||||
stuff_string(temp, F_NAME);
|
||||
for (j = 0; j < TOTAL_COLORS; j++) {
|
||||
if (!temp.compare(COLOR_NAMES[j])) {
|
||||
if (temp == COLOR_NAMES[j]) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -578,7 +578,7 @@ void parse_everything_else(const char *filename)
|
||||
}
|
||||
break;
|
||||
default:
|
||||
Assertion(false, "MageKing17 made a coding error somewhere, and you should laugh at him (and report this error).\n");
|
||||
UNREACHABLE("MageKing17 made a coding error somewhere, and you should laugh at him (and report this error).\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <stddef.h>
|
||||
#include <cstddef>
|
||||
#include <cstdlib>
|
||||
|
||||
#include "globalincs/pstypes.h"
|
||||
|
||||
@@ -261,14 +261,14 @@ extern int Global_error_count;
|
||||
// Disabling this functionality is dangerous, crazy values can run rampent unchecked and the longer its disabled
|
||||
// the more likely you are to have problems getting it working again.
|
||||
#if defined(NDEBUG)
|
||||
# define Assert(expr) do { ASSUME(expr); } while (0)
|
||||
# define Assert(expr) do { ASSUME(expr); } while (false)
|
||||
#else
|
||||
# define Assert(expr) do {\
|
||||
if (!(expr)) {\
|
||||
os::dialogs::AssertMessage(#expr,__FILE__,__LINE__);\
|
||||
}\
|
||||
ASSUME( expr );\
|
||||
} while (0)
|
||||
} while (false)
|
||||
#endif
|
||||
/*******************NEVER COMMENT Assert ************************************************/
|
||||
|
||||
@@ -434,7 +434,7 @@ public:
|
||||
// - is not "none"
|
||||
// - is not "<none>"
|
||||
inline bool VALID_FNAME(const char* x) {
|
||||
return strlen((x)) && stricmp((x), "none") && stricmp((x), "<none>");
|
||||
return strlen((x)) && stricmp((x), "none") != 0 && stricmp((x), "<none>") != 0;
|
||||
}
|
||||
/**
|
||||
* @brief Checks if the specified string may be a valid file name
|
||||
@@ -462,9 +462,8 @@ inline bool VALID_FNAME(const SCP_string& x) {
|
||||
SCP_string dump_stacktrace();
|
||||
|
||||
// DEBUG compile time catch for dangerous uses of memset/memcpy/memmove
|
||||
// would prefer std::is_trivially_copyable but it's not supported by gcc yet
|
||||
// ref: http://gcc.gnu.org/onlinedocs/libstdc++/manual/status.html
|
||||
#if !defined(NDEBUG) && !defined(USING_THIRD_PARTY_LIBS)
|
||||
// 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(HAVE_STD_IS_TRIVIALLY_COPYABLE)
|
||||
// feature support seems to be: gcc clang msvc
|
||||
// auto 4.4 2.9 2010
|
||||
@@ -480,15 +479,8 @@ SCP_string dump_stacktrace();
|
||||
// Put into std to be compatible with code that uses std::mem*
|
||||
namespace std
|
||||
{
|
||||
|
||||
// This is a separate check which also checks if arrays are trivially copyable since Visual Studio 2013 thinks they are not
|
||||
#if SCP_COMPILER_IS_MSVC && _MSC_VER <= 1800
|
||||
template<typename T>
|
||||
using trivial_check = std::is_trivial<T>;
|
||||
#else
|
||||
template<typename T>
|
||||
using trivial_check = std::is_trivially_copyable<T>;
|
||||
#endif
|
||||
template<typename T>
|
||||
using trivial_check = std::is_trivially_copyable<T>;
|
||||
|
||||
template<typename T>
|
||||
void *memset_if_trivial_else_error(T *memset_data, int ch, size_t count)
|
||||
|
||||
@@ -20,8 +20,8 @@
|
||||
*/
|
||||
|
||||
/* errno_t, EINVAL, ERANGE, etc.. */
|
||||
#include <errno.h>
|
||||
#include <stdlib.h> /* size_t */
|
||||
#include <cerrno>
|
||||
#include <cstdlib> /* size_t */
|
||||
|
||||
/* Because errno_t is not (yet) standard, we define it here like this */
|
||||
typedef int errno_t;
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
#define _SYSTEMVARS_H
|
||||
|
||||
#include "globalincs/pstypes.h"
|
||||
#include "math.h"
|
||||
#include <cmath>
|
||||
|
||||
#include <cstdint>
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
#define ASSUME(x)
|
||||
|
||||
#if defined(NDEBUG)
|
||||
# define Assertion(expr, msg, ...) do { } while (0)
|
||||
# define Assertion(expr, msg, ...) do { } while (false)
|
||||
#else
|
||||
/*
|
||||
* NOTE: Assertion() can only use its proper functionality in compilers
|
||||
@@ -43,7 +43,7 @@
|
||||
if (!(expr)) { \
|
||||
os::dialogs::AssertMessage(#expr, __FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} \
|
||||
} while (0)
|
||||
} while (false)
|
||||
#endif
|
||||
|
||||
/* C++11 Standard Detection */
|
||||
@@ -81,3 +81,12 @@
|
||||
#define CLANG_ANALYZER_NORETURN
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define UNREACHABLE(msg, ...) \
|
||||
do { \
|
||||
os::dialogs::Error(__FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} while (false)
|
||||
#else
|
||||
#define UNREACHABLE(msg, ...) __builtin_unreachable()
|
||||
#endif
|
||||
@@ -63,3 +63,10 @@
|
||||
* @brief Specifies that an analyzer should consider this function as no-return
|
||||
*/
|
||||
#define CLANG_ANALYZER_NORETURN
|
||||
|
||||
/**
|
||||
* @brief Specifies that the code at which point this macro appears at is unreachable
|
||||
* @param msg The message to display in debug mode
|
||||
* @param ... Format arguments for the message
|
||||
*/
|
||||
#define UNREACHABLE(msg, ...)
|
||||
@@ -32,7 +32,7 @@
|
||||
#define ASSUME(x)
|
||||
|
||||
#if defined(NDEBUG)
|
||||
# define Assertion(expr, msg, ...) do {} while (0)
|
||||
# define Assertion(expr, msg, ...) do {} while (false)
|
||||
#else
|
||||
/*
|
||||
* NOTE: Assertion() can only use its proper functionality in compilers
|
||||
@@ -43,7 +43,7 @@
|
||||
if (!(expr)) { \
|
||||
os::dialogs::AssertMessage(#expr, __FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} \
|
||||
} while (0)
|
||||
} while (false)
|
||||
#endif
|
||||
|
||||
/* C++11 Standard Detection */
|
||||
@@ -72,3 +72,12 @@
|
||||
#endif
|
||||
|
||||
#define CLANG_ANALYZER_NORETURN
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define UNREACHABLE(msg, ...) \
|
||||
do { \
|
||||
os::dialogs::Error(__FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} while (false)
|
||||
#else
|
||||
#define UNREACHABLE(msg, ...) __builtin_unreachable()
|
||||
#endif
|
||||
@@ -17,8 +17,10 @@
|
||||
* the detected toolchain.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#define SCP_FORMAT_STRING
|
||||
#define SCP_FORMAT_STRING_ARGS(x,y) __attribute__((format(printf, x, y)))
|
||||
#define SCP_FORMAT_STRING_ARGS(x,y) __attribute__((format(__MINGW_PRINTF_FORMAT, x, y)))
|
||||
|
||||
#define __UNUSED __attribute__((__unused__))
|
||||
#define __ALIGNED(x) __attribute__((__aligned__(x)))
|
||||
@@ -32,7 +34,7 @@
|
||||
#define ASSUME(x)
|
||||
|
||||
#if defined(NDEBUG)
|
||||
# define Assertion(expr, msg, ...) do {} while (0)
|
||||
# define Assertion(expr, msg, ...) do {} while (false)
|
||||
#else
|
||||
/*
|
||||
* NOTE: Assertion() can only use its proper functionality in compilers
|
||||
@@ -43,7 +45,7 @@
|
||||
if (!(expr)) { \
|
||||
os::dialogs::AssertMessage(#expr, __FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} \
|
||||
} while (0)
|
||||
} while (false)
|
||||
#endif
|
||||
|
||||
/* C++11 Standard Detection */
|
||||
@@ -58,14 +60,21 @@
|
||||
#define likely(x) __builtin_expect((long) !!(x), 1L)
|
||||
#define unlikely(x) __builtin_expect((long) !!(x), 0L)
|
||||
|
||||
#define __STDC_FORMAT_MACROS 1
|
||||
|
||||
#define USED_VARIABLE __attribute__((used))
|
||||
|
||||
#if SCP_COMPILER_VERSION_MAJOR >= 7
|
||||
#define FALLTHROUGH [[fallthough]]
|
||||
#define FALLTHROUGH __attribute__((fallthrough))
|
||||
#else
|
||||
#define FALLTHROUGH
|
||||
#endif
|
||||
|
||||
#define CLANG_ANALYZER_NORETURN
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define UNREACHABLE(msg, ...) \
|
||||
do { \
|
||||
os::dialogs::Error(__FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} while (false)
|
||||
#else
|
||||
#define UNREACHABLE(msg, ...) __builtin_unreachable()
|
||||
#endif
|
||||
@@ -38,9 +38,9 @@
|
||||
|
||||
#if defined(NDEBUG)
|
||||
# if _MSC_VER >= 1400 /* MSVC 2005 or newer */
|
||||
# define Assertion(expr, msg, ...) do { ASSUME(expr); } while (0)
|
||||
# define Assertion(expr, msg, ...) do { ASSUME(expr); } while (false)
|
||||
# else
|
||||
# define Assertion(expr, msg) do {} while (0)
|
||||
# define Assertion(expr, msg) do {} while (false)
|
||||
# endif
|
||||
#else
|
||||
/*
|
||||
@@ -53,13 +53,13 @@
|
||||
if (!(expr)) { \
|
||||
os::dialogs::AssertMessage(#expr, __FILE__, __LINE__, msg, __VA_ARGS__); \
|
||||
} \
|
||||
} while (0)
|
||||
} while (false)
|
||||
# else /* Older MSVC compilers */
|
||||
# define Assertion(expr, msg) \
|
||||
do { \
|
||||
if (!(expr)) { \
|
||||
os::dialogs::AssertMessage(#expr, __FILE__, __LINE__); \
|
||||
} while (0)
|
||||
} while (false)
|
||||
# endif
|
||||
#endif
|
||||
|
||||
@@ -71,8 +71,8 @@
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#define PTRDIFF_T_ARG "%Iu"
|
||||
#define SIZE_T_ARG "%Id"
|
||||
#define SIZE_T_ARG "%Iu"
|
||||
#define PTRDIFF_T_ARG "%Id"
|
||||
|
||||
#define likely(x)
|
||||
#define unlikely(x)
|
||||
@@ -82,3 +82,13 @@
|
||||
#define FALLTHROUGH
|
||||
|
||||
#define CLANG_ANALYZER_NORETURN
|
||||
|
||||
|
||||
#ifndef NDEBUG
|
||||
#define UNREACHABLE(msg, ...) \
|
||||
do { \
|
||||
os::dialogs::Error(__FILE__, __LINE__, msg, ##__VA_ARGS__); \
|
||||
} while (false)
|
||||
#else
|
||||
#define UNREACHABLE(msg, ...) __assume(false)
|
||||
#endif
|
||||
+10
-10
@@ -14,22 +14,22 @@
|
||||
#include <windowsx.h>
|
||||
#endif
|
||||
|
||||
#include <limits.h>
|
||||
#include <climits>
|
||||
#include <algorithm>
|
||||
|
||||
#include "cmdline/cmdline.h"
|
||||
#include "debugconsole/console.h"
|
||||
#include "gamesequence/gamesequence.h" //WMC - for scripting hooks in gr_flip()
|
||||
#include "gamesequence/gamesequence.h" //WMC - for scripting hooks in gr_flip()
|
||||
#include "globalincs/systemvars.h"
|
||||
#include "graphics/2d.h"
|
||||
#include "graphics/matrix.h"
|
||||
#include "graphics/light.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/opengl/gropengldraw.h"
|
||||
#include "graphics/grstub.h"
|
||||
#include "graphics/paths/PathRenderer.h"
|
||||
#include "graphics/util/GPUMemoryHeap.h"
|
||||
#include "graphics/util/UniformBuffer.h"
|
||||
@@ -37,9 +37,10 @@
|
||||
#include "io/keycontrol.h" // m!m
|
||||
#include "io/timer.h"
|
||||
#include "osapi/osapi.h"
|
||||
#include "scripting/scripting.h"
|
||||
#include "parse/parselo.h"
|
||||
#include "popup/popup.h"
|
||||
#include "render/3d.h"
|
||||
#include "scripting/scripting.h"
|
||||
#include "tracing/tracing.h"
|
||||
#include "utils/boost/hash_combine.h"
|
||||
|
||||
@@ -693,7 +694,7 @@ DCF(clear_color, "set clear color r, g, b")
|
||||
gr_set_clear_color(r, g, b);
|
||||
}
|
||||
|
||||
void gr_set_palette_internal( const char *name, ubyte * palette, int restrict_font_to_128 )
|
||||
void gr_set_palette_internal( const char * /*name*/, ubyte * palette, int /*restrict_font_to_128*/ )
|
||||
{
|
||||
if ( palette == NULL ) {
|
||||
// Create a default palette
|
||||
@@ -2031,7 +2032,7 @@ void poly_list::make_index_buffer(SCP_vector<int> &vertex_list)
|
||||
(*this) = buffer_list_internal;
|
||||
}
|
||||
|
||||
poly_list& poly_list::operator = (poly_list &other_list)
|
||||
poly_list& poly_list::operator = (const poly_list &other_list)
|
||||
{
|
||||
allocate(other_list.n_verts);
|
||||
|
||||
@@ -2152,8 +2153,7 @@ void gr_set_bitmap(int bitmap_num, int alphablend_mode, int bitblt_mode, float a
|
||||
void gr_flip(bool execute_scripting)
|
||||
{
|
||||
// m!m avoid running CHA_ONFRAME when the "Quit mission" popup is shown. See mantis 2446 for reference
|
||||
if (execute_scripting && !quit_mission_popup_shown)
|
||||
{
|
||||
if (execute_scripting && !popup_active()) {
|
||||
TRACE_SCOPE(tracing::LuaOnFrame);
|
||||
|
||||
//WMC - Do conditional hooks. Yippee!
|
||||
|
||||
+46
-46
@@ -186,7 +186,7 @@ enum shader_type {
|
||||
#define SDR_FLAG_MODEL_HDR (1<<18)
|
||||
#define SDR_FLAG_MODEL_AMBIENT_MAP (1<<19)
|
||||
#define SDR_FLAG_MODEL_NORMAL_ALPHA (1<<20)
|
||||
#define SDR_FLAG_MODEL_NORMAL_EXTRUDE (1<<21)
|
||||
#define SDR_FLAG_MODEL_THICK_OUTLINES (1<<21) // Renders the model geometry as an outline with configurable line width
|
||||
|
||||
#define SDR_FLAG_PARTICLE_POINT_GEN (1<<0)
|
||||
|
||||
@@ -365,7 +365,7 @@ class poly_list {
|
||||
public:
|
||||
poly_list(): n_verts(0), vert(NULL), norm(NULL), tsb(NULL), submodels(NULL), sorted_indices(NULL), currently_allocated(0) {}
|
||||
~poly_list();
|
||||
poly_list& operator = (poly_list&);
|
||||
poly_list& operator=(const poly_list&);
|
||||
|
||||
void allocate(int size);
|
||||
void make_index_buffer(SCP_vector<int> &vertex_list);
|
||||
@@ -709,14 +709,14 @@ typedef struct screen {
|
||||
void (*gf_set_clear_color)(int r, int g, int b);
|
||||
|
||||
// Here be the bitmap functions
|
||||
void (*gf_bm_free_data)(int n, bool release);
|
||||
void (*gf_bm_create)(int n);
|
||||
void (*gf_bm_init)(int n);
|
||||
void (*gf_bm_free_data)(bitmap_slot* slot, bool release);
|
||||
void (*gf_bm_create)(bitmap_slot* slot);
|
||||
void (*gf_bm_init)(bitmap_slot* slot);
|
||||
void (*gf_bm_page_in_start)();
|
||||
bool (*gf_bm_data)(int n, bitmap* bm);
|
||||
bool (*gf_bm_data)(int handle, bitmap* bm);
|
||||
|
||||
int (*gf_bm_make_render_target)(int n, int *width, int *height, int *bpp, int *mm_lvl, int flags );
|
||||
int (*gf_bm_set_render_target)(int n, int face);
|
||||
int (*gf_bm_make_render_target)(int handle, int *width, int *height, int *bpp, int *mm_lvl, int flags );
|
||||
int (*gf_bm_set_render_target)(int handle, int face);
|
||||
|
||||
void (*gf_translate_texture_matrix)(int unit, const vec3d *shift);
|
||||
void (*gf_push_texture_matrix)(int unit);
|
||||
@@ -776,7 +776,7 @@ typedef struct screen {
|
||||
void (*gf_render_primitives)(material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle, size_t buffer_offset);
|
||||
void (*gf_render_primitives_particle)(particle_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle);
|
||||
void (*gf_render_primitives_distortion)(distortion_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle);
|
||||
void (*gf_render_movie)(movie_material* material_info, primitive_type prim_type, vertex_layout* layout, int n_verts, int buffer);
|
||||
void (*gf_render_movie)(movie_material* material_info, primitive_type prim_type, vertex_layout* layout, int n_verts, int buffer, size_t buffer_offset);
|
||||
void (*gf_render_primitives_batched)(batched_bitmap_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle);
|
||||
void (*gf_render_nanovg)(nanovg_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle);
|
||||
void (*gf_render_decals)(decal_material* material_info, primitive_type prim_type, vertex_layout* layout, int num_elements, const indexed_vertex_source& buffers);
|
||||
@@ -942,67 +942,67 @@ void gr_shield_icon(coord2d coords[6], const int resize_mode = GR_RESIZE_FULL);
|
||||
|
||||
|
||||
// Here be the bitmap functions
|
||||
#define gr_bm_free_data GR_CALL(*gr_screen.gf_bm_free_data)
|
||||
#define gr_bm_create GR_CALL(*gr_screen.gf_bm_create)
|
||||
#define gr_bm_init GR_CALL(*gr_screen.gf_bm_init)
|
||||
#define gr_bm_page_in_start GR_CALL(*gr_screen.gf_bm_page_in_start)
|
||||
#define gr_bm_data GR_CALL(*gr_screen.gf_bm_data)
|
||||
#define gr_bm_free_data GR_CALL(gr_screen.gf_bm_free_data)
|
||||
#define gr_bm_create GR_CALL(gr_screen.gf_bm_create)
|
||||
#define gr_bm_init GR_CALL(gr_screen.gf_bm_init)
|
||||
#define gr_bm_page_in_start GR_CALL(gr_screen.gf_bm_page_in_start)
|
||||
#define gr_bm_data GR_CALL(gr_screen.gf_bm_data)
|
||||
|
||||
#define gr_bm_make_render_target GR_CALL(*gr_screen.gf_bm_make_render_target)
|
||||
#define gr_bm_make_render_target GR_CALL(gr_screen.gf_bm_make_render_target)
|
||||
|
||||
__inline int gr_bm_set_render_target(int n, int face = -1)
|
||||
{
|
||||
return (*gr_screen.gf_bm_set_render_target)(n, face);
|
||||
}
|
||||
|
||||
#define gr_set_texture_addressing GR_CALL(*gr_screen.gf_set_texture_addressing)
|
||||
#define gr_set_texture_addressing GR_CALL(gr_screen.gf_set_texture_addressing)
|
||||
|
||||
inline int gr_create_buffer(BufferType type, BufferUsageHint usage)
|
||||
{
|
||||
return (*gr_screen.gf_create_buffer)(type, 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)
|
||||
#define gr_update_transform_buffer GR_CALL(*gr_screen.gf_update_transform_buffer)
|
||||
#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)
|
||||
#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)
|
||||
#define gr_scene_texture_end GR_CALL(*gr_screen.gf_scene_texture_end)
|
||||
#define gr_copy_effect_texture GR_CALL(*gr_screen.gf_copy_effect_texture)
|
||||
#define gr_scene_texture_begin GR_CALL(gr_screen.gf_scene_texture_begin)
|
||||
#define gr_scene_texture_end GR_CALL(gr_screen.gf_scene_texture_end)
|
||||
#define gr_copy_effect_texture GR_CALL(gr_screen.gf_copy_effect_texture)
|
||||
|
||||
#define gr_post_process_set_effect GR_CALL(*gr_screen.gf_post_process_set_effect)
|
||||
#define gr_post_process_set_defaults GR_CALL(*gr_screen.gf_post_process_set_defaults)
|
||||
#define gr_post_process_begin GR_CALL(*gr_screen.gf_post_process_begin)
|
||||
#define gr_post_process_end GR_CALL(*gr_screen.gf_post_process_end)
|
||||
#define gr_post_process_save_zbuffer GR_CALL(*gr_screen.gf_post_process_save_zbuffer)
|
||||
#define gr_post_process_set_effect GR_CALL(gr_screen.gf_post_process_set_effect)
|
||||
#define gr_post_process_set_defaults GR_CALL(gr_screen.gf_post_process_set_defaults)
|
||||
#define gr_post_process_begin GR_CALL(gr_screen.gf_post_process_begin)
|
||||
#define gr_post_process_end GR_CALL(gr_screen.gf_post_process_end)
|
||||
#define gr_post_process_save_zbuffer GR_CALL(gr_screen.gf_post_process_save_zbuffer)
|
||||
inline void gr_post_process_restore_zbuffer() {
|
||||
gr_screen.gf_post_process_restore_zbuffer();
|
||||
}
|
||||
|
||||
#define gr_deferred_lighting_begin GR_CALL(*gr_screen.gf_deferred_lighting_begin)
|
||||
#define gr_deferred_lighting_end GR_CALL(*gr_screen.gf_deferred_lighting_end)
|
||||
#define gr_deferred_lighting_finish GR_CALL(*gr_screen.gf_deferred_lighting_finish)
|
||||
#define gr_deferred_lighting_begin GR_CALL(gr_screen.gf_deferred_lighting_begin)
|
||||
#define gr_deferred_lighting_end GR_CALL(gr_screen.gf_deferred_lighting_end)
|
||||
#define gr_deferred_lighting_finish GR_CALL(gr_screen.gf_deferred_lighting_finish)
|
||||
|
||||
#define gr_zbias GR_CALL(*gr_screen.gf_zbias)
|
||||
#define gr_set_fill_mode GR_CALL(*gr_screen.gf_set_fill_mode)
|
||||
#define gr_zbias GR_CALL(gr_screen.gf_zbias)
|
||||
#define gr_set_fill_mode GR_CALL(gr_screen.gf_set_fill_mode)
|
||||
|
||||
#define gr_set_line_width GR_CALL(*gr_screen.gf_set_line_width)
|
||||
#define gr_set_line_width GR_CALL(gr_screen.gf_set_line_width)
|
||||
|
||||
#define gr_sphere GR_CALL(*gr_screen.gf_sphere)
|
||||
#define gr_sphere GR_CALL(gr_screen.gf_sphere)
|
||||
|
||||
#define gr_maybe_create_shader GR_CALL(*gr_screen.gf_maybe_create_shader)
|
||||
#define gr_recompile_all_shaders GR_CALL(*gr_screen.gf_recompile_all_shaders)
|
||||
#define gr_set_animated_effect GR_CALL(*gr_screen.gf_set_animated_effect)
|
||||
#define gr_maybe_create_shader GR_CALL(gr_screen.gf_maybe_create_shader)
|
||||
#define gr_recompile_all_shaders GR_CALL(gr_screen.gf_recompile_all_shaders)
|
||||
#define gr_set_animated_effect GR_CALL(gr_screen.gf_set_animated_effect)
|
||||
|
||||
#define gr_clear_states GR_CALL(*gr_screen.gf_clear_states)
|
||||
#define gr_clear_states GR_CALL(gr_screen.gf_clear_states)
|
||||
|
||||
#define gr_update_texture GR_CALL(*gr_screen.gf_update_texture)
|
||||
#define gr_get_bitmap_from_texture GR_CALL(*gr_screen.gf_get_bitmap_from_texture)
|
||||
#define gr_update_texture GR_CALL(gr_screen.gf_update_texture)
|
||||
#define gr_get_bitmap_from_texture GR_CALL(gr_screen.gf_get_bitmap_from_texture)
|
||||
|
||||
#define gr_shadow_map_start GR_CALL(*gr_screen.gf_shadow_map_start)
|
||||
#define gr_shadow_map_end GR_CALL(*gr_screen.gf_shadow_map_end)
|
||||
#define gr_render_shield_impact GR_CALL(*gr_screen.gf_render_shield_impact)
|
||||
#define gr_shadow_map_start GR_CALL(gr_screen.gf_shadow_map_start)
|
||||
#define gr_shadow_map_end GR_CALL(gr_screen.gf_shadow_map_end)
|
||||
#define gr_render_shield_impact GR_CALL(gr_screen.gf_render_shield_impact)
|
||||
|
||||
__inline void gr_render_primitives(material* material_info, primitive_type prim_type, vertex_layout* layout, int vert_offset, int n_verts, int buffer_handle = -1, size_t buffer_offset = 0)
|
||||
{
|
||||
@@ -1029,9 +1029,9 @@ __inline void gr_render_primitives_distortion(distortion_material* material_info
|
||||
(*gr_screen.gf_render_primitives_distortion)(material_info, prim_type, layout, offset, n_verts, buffer_handle);
|
||||
}
|
||||
|
||||
inline void gr_render_movie(movie_material* material_info, primitive_type prim_type, vertex_layout* layout, int n_verts, int buffer)
|
||||
inline void gr_render_movie(movie_material* material_info, primitive_type prim_type, vertex_layout* layout, int n_verts, int buffer, size_t buffer_offset = 0)
|
||||
{
|
||||
(*gr_screen.gf_render_movie)(material_info, prim_type, layout, n_verts, buffer);
|
||||
(*gr_screen.gf_render_movie)(material_info, prim_type, layout, n_verts, buffer, buffer_offset);
|
||||
}
|
||||
|
||||
__inline void gr_render_model(model_material* material_info, indexed_vertex_source *vert_source, vertex_buffer* bufferp, size_t texi)
|
||||
|
||||
@@ -172,7 +172,7 @@ void decal_draw_list::render() {
|
||||
void decal_draw_list::add_decal(int diffuse_bitmap,
|
||||
int glow_bitmap,
|
||||
int normal_bitmap,
|
||||
float decal_timer,
|
||||
float /*decal_timer*/,
|
||||
const matrix4& transform,
|
||||
float base_alpha) {
|
||||
if (!check_box_in_view(transform)) {
|
||||
|
||||
@@ -158,32 +158,28 @@ int generic_anim_stream(generic_anim *ga, const bool cache)
|
||||
{
|
||||
CFILE *img_cfp = NULL;
|
||||
int anim_fps = 0;
|
||||
char full_path[MAX_PATH];
|
||||
size_t size = 0, offset = 0;
|
||||
const void* file_data = nullptr;
|
||||
const int NUM_TYPES = 3;
|
||||
const ubyte type_list[NUM_TYPES] = {BM_TYPE_EFF, BM_TYPE_ANI, BM_TYPE_PNG};
|
||||
const char *ext_list[NUM_TYPES] = {".eff", ".ani", ".png"};
|
||||
int rval = -1;
|
||||
int bpp;
|
||||
|
||||
ga->type = BM_TYPE_NONE;
|
||||
|
||||
rval = cf_find_file_location_ext(ga->filename, NUM_TYPES, ext_list, CF_TYPE_ANY, sizeof(full_path) - 1, full_path, &size, &offset, 0, &file_data);
|
||||
auto res = cf_find_file_location_ext(ga->filename, NUM_TYPES, ext_list, CF_TYPE_ANY, false);
|
||||
|
||||
// could not be found, or is invalid for some reason
|
||||
if ( (rval < 0) || (rval >= NUM_TYPES) )
|
||||
if ( !res.found )
|
||||
return -1;
|
||||
|
||||
//make sure we can open it
|
||||
img_cfp = cfopen_special(full_path, "rb", size, offset, file_data, CF_TYPE_ANY);
|
||||
img_cfp = cfopen_special(res.full_name.c_str(), "rb", res.size, res.offset, res.data_ptr, CF_TYPE_ANY);
|
||||
|
||||
if (img_cfp == NULL) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
strcat_s(ga->filename, ext_list[rval]);
|
||||
ga->type = type_list[rval];
|
||||
strcat_s(ga->filename, ext_list[res.extension_index]);
|
||||
ga->type = type_list[res.extension_index];
|
||||
//seek to the end
|
||||
cfseek(img_cfp, 0, CF_SEEK_END);
|
||||
|
||||
|
||||
@@ -137,7 +137,7 @@ void geometry_batcher::clone(const geometry_batcher &geo)
|
||||
}
|
||||
}
|
||||
|
||||
const geometry_batcher &geometry_batcher::operator=(const geometry_batcher &geo)
|
||||
geometry_batcher& geometry_batcher::operator=(const geometry_batcher &geo)
|
||||
{
|
||||
if (this != &geo) {
|
||||
clone(geo);
|
||||
@@ -522,7 +522,7 @@ float geometry_batcher::draw_laser(vec3d *p0, float width1, vec3d *p1, float wid
|
||||
return center.xyz.z;
|
||||
}
|
||||
|
||||
void geometry_batcher::render(int flags, float radius)
|
||||
void geometry_batcher::render(int /*flags*/, float /*radius*/)
|
||||
{
|
||||
|
||||
}
|
||||
@@ -553,12 +553,12 @@ void geometry_batcher::load_buffer(effect_vertex* buffer, int *n_verts)
|
||||
*n_verts = *n_verts + verts_to_render;
|
||||
}
|
||||
|
||||
void geometry_batcher::render_buffer(int buffer_handle, int flags)
|
||||
void geometry_batcher::render_buffer(int /*buffer_handle*/, int /*flags*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void geometry_shader_batcher::render_buffer(int buffer_handle, int flags)
|
||||
void geometry_shader_batcher::render_buffer(int /*buffer_handle*/, int /*flags*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ public:
|
||||
~geometry_batcher();
|
||||
|
||||
geometry_batcher(const geometry_batcher &geo) { clone(geo); }
|
||||
const geometry_batcher &operator=(const geometry_batcher &geo);
|
||||
geometry_batcher& operator=(const geometry_batcher &geo);
|
||||
|
||||
// initial memory space needed
|
||||
// NOTE: This MUST be called BEFORE calling any of the draw_*() functions!!
|
||||
@@ -68,8 +68,6 @@ public:
|
||||
|
||||
// determine if we even need to try and render this (helpful for particle system)
|
||||
int need_to_render() { return n_to_render; }
|
||||
|
||||
void operator =(int){}
|
||||
};
|
||||
|
||||
class geometry_shader_batcher
|
||||
|
||||
+64
-64
@@ -28,12 +28,12 @@ int gr_stub_create_buffer(BufferType, BufferUsageHint)
|
||||
return -1;
|
||||
}
|
||||
|
||||
void gr_stub_delete_buffer(int handle)
|
||||
void gr_stub_delete_buffer(int /*handle*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
int gr_stub_preload(int bitmap_num, int is_aabitmap)
|
||||
int gr_stub_preload(int /*bitmap_num*/, int /*is_aabitmap*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
@@ -48,21 +48,21 @@ int gr_stub_zbuffer_get()
|
||||
return 0;
|
||||
}
|
||||
|
||||
int gr_stub_zbuffer_set(int mode)
|
||||
int gr_stub_zbuffer_set(int /*mode*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
void gr_set_fill_mode_stub(int mode)
|
||||
void gr_set_fill_mode_stub(int /*mode*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_activate(int active)
|
||||
void gr_stub_activate(int /*active*/)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
void gr_stub_cleanup(int minimize)
|
||||
void gr_stub_cleanup(int /*minimize*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -74,19 +74,19 @@ void gr_stub_flip()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_fog_set(int fog_mode, int r, int g, int b, float fog_near, float fog_far)
|
||||
void gr_stub_fog_set(int /*fog_mode*/, int /*r*/, int /*g*/, int /*b*/, float /*fog_near*/, float /*fog_far*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_free_screen(int id)
|
||||
void gr_stub_free_screen(int /*id*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_get_region(int front, int w, int h, ubyte *data)
|
||||
void gr_stub_get_region(int /*front*/, int /*w*/, int /*h*/, ubyte * /*data*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_pop_texture_matrix(int unit)
|
||||
void gr_stub_pop_texture_matrix(int /*unit*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -94,15 +94,15 @@ void gr_stub_preload_init()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_print_screen(const char *filename)
|
||||
void gr_stub_print_screen(const char * /*filename*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_push_texture_matrix(int unit)
|
||||
void gr_stub_push_texture_matrix(int /*unit*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_rect(int x, int y, int w, int h, int resize_mode)
|
||||
void gr_stub_rect(int /*x*/, int /*y*/, int /*w*/, int /*h*/, int /*resize_mode*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -110,78 +110,78 @@ void gr_stub_reset_clip()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_restore_screen(int id)
|
||||
void gr_stub_restore_screen(int /*id*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_save_mouse_area(int x, int y, int w, int h)
|
||||
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*/, 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*/, void* /*data*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_update_transform_buffer(void* data, size_t size)
|
||||
void gr_stub_update_transform_buffer(void* /*data*/, size_t /*size*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void gr_stub_set_clear_color(int r, int g, int b)
|
||||
void gr_stub_set_clear_color(int /*r*/, int /*g*/, int /*b*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_set_clip(int x, int y, int w, int h, int resize_mode)
|
||||
void gr_stub_set_clip(int /*x*/, int /*y*/, int /*w*/, int /*h*/, int /*resize_mode*/)
|
||||
{
|
||||
}
|
||||
|
||||
int gr_stub_set_cull(int cull)
|
||||
int gr_stub_set_cull(int /*cull*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int gr_stub_set_color_buffer(int mode)
|
||||
int gr_stub_set_color_buffer(int /*mode*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
void gr_stub_set_gamma(float gamma)
|
||||
void gr_stub_set_gamma(float /*gamma*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_set_tex_env_scale(float scale)
|
||||
void gr_stub_set_tex_env_scale(float /*scale*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_set_texture_addressing(int mode)
|
||||
void gr_stub_set_texture_addressing(int /*mode*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_stuff_fog_coord(vertex *v)
|
||||
void gr_stub_stuff_fog_coord(vertex * /*v*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_stuff_secondary_color(vertex *v, ubyte fr, ubyte fg, ubyte fb)
|
||||
void gr_stub_stuff_secondary_color(vertex * /*v*/, ubyte /*fr*/, ubyte /*fg*/, ubyte /*fb*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_translate_texture_matrix(int unit, const vec3d *shift)
|
||||
void gr_stub_translate_texture_matrix(int /*unit*/, const vec3d * /*shift*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_zbias_stub(int bias)
|
||||
void gr_stub_zbias_stub(int /*bias*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_zbuffer_clear(int mode)
|
||||
void gr_stub_zbuffer_clear(int /*mode*/)
|
||||
{
|
||||
}
|
||||
|
||||
int gr_stub_stencil_set(int mode)
|
||||
int gr_stub_stencil_set(int /*mode*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
@@ -190,7 +190,7 @@ void gr_stub_stencil_clear()
|
||||
{
|
||||
}
|
||||
|
||||
int gr_stub_alpha_mask_set(int mode, float alpha)
|
||||
int gr_stub_alpha_mask_set(int /*mode*/, float /*alpha*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
@@ -199,7 +199,7 @@ int gr_stub_alpha_mask_set(int mode, float alpha)
|
||||
{
|
||||
}*/
|
||||
|
||||
void gr_stub_post_process_set_effect(const char *name, int x, const vec3d *rgb)
|
||||
void gr_stub_post_process_set_effect(const char * /*name*/, int /*x*/, const vec3d * /*rgb*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -247,11 +247,11 @@ void gr_stub_deferred_lighting_finish()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_set_line_width(float width)
|
||||
void gr_stub_set_line_width(float /*width*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_draw_sphere(material *material_def, float rad)
|
||||
void gr_stub_draw_sphere(material * /*material_def*/, float /*rad*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -259,34 +259,34 @@ void gr_stub_clear_states()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_update_texture(int bitmap_handle, int bpp, const ubyte *data, int width, int height)
|
||||
void gr_stub_update_texture(int /*bitmap_handle*/, int /*bpp*/, const ubyte * /*data*/, int /*width*/, int /*height*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_get_bitmap_from_texture(void* data_out, int bitmap_num)
|
||||
void gr_stub_get_bitmap_from_texture(void* /*data_out*/, int /*bitmap_num*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
int gr_stub_bm_make_render_target(int n, int *width, int *height, int *bpp, int *mm_lvl, int flags)
|
||||
int gr_stub_bm_make_render_target(int /*n*/, int * /*width*/, int * /*height*/, int * /*bpp*/, int * /*mm_lvl*/, int /*flags*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int gr_stub_bm_set_render_target(int n, int face)
|
||||
int gr_stub_bm_set_render_target(int /*n*/, int /*face*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
void gr_stub_bm_create(int n)
|
||||
void gr_stub_bm_create(bitmap_slot* /*slot*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_bm_free_data(int n, bool release)
|
||||
void gr_stub_bm_free_data(bitmap_slot* /*slot*/, bool /*release*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_bm_init(int n)
|
||||
void gr_stub_bm_init(bitmap_slot* /*slot*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -294,16 +294,16 @@ void gr_stub_bm_page_in_start()
|
||||
{
|
||||
}
|
||||
|
||||
bool gr_stub_bm_data(int n, bitmap* bm)
|
||||
bool gr_stub_bm_data(int /*n*/, bitmap* /*bm*/)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
int gr_stub_maybe_create_shader(shader_type shader_t, unsigned int flags) {
|
||||
int gr_stub_maybe_create_shader(shader_type /*shader_t*/, unsigned int /*flags*/) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
void gr_stub_shadow_map_start(matrix4 *shadow_view_matrix, const matrix* light_matrix)
|
||||
void gr_stub_shadow_map_start(matrix4 * /*shadow_view_matrix*/, const matrix* /*light_matrix*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -311,47 +311,47 @@ void gr_stub_shadow_map_end()
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_render_shield_impact(shield_material *material_info, primitive_type prim_type, vertex_layout *layout, int buffer_handle, int n_verts)
|
||||
void gr_stub_render_shield_impact(shield_material * /*material_info*/, primitive_type /*prim_type*/, vertex_layout * /*layout*/, int /*buffer_handle*/, int /*n_verts*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void gr_stub_render_model(model_material* material_info, indexed_vertex_source *vert_source, vertex_buffer* bufferp, size_t texi)
|
||||
void gr_stub_render_model(model_material* /*material_info*/, indexed_vertex_source * /*vert_source*/, vertex_buffer* /*bufferp*/, size_t /*texi*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void gr_stub_render_primitives(material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle, size_t buffer_offset)
|
||||
void gr_stub_render_primitives(material* /*material_info*/, primitive_type /*prim_type*/, vertex_layout* /*layout*/, int /*offset*/, int /*n_verts*/, int /*buffer_handle*/, size_t /*buffer_offset*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void gr_stub_render_primitives_particle(particle_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle)
|
||||
void gr_stub_render_primitives_particle(particle_material* /*material_info*/, primitive_type /*prim_type*/, vertex_layout* /*layout*/, int /*offset*/, int /*n_verts*/, int /*buffer_handle*/)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void gr_stub_render_primitives_distortion(distortion_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle)
|
||||
void gr_stub_render_primitives_distortion(distortion_material* /*material_info*/, primitive_type /*prim_type*/, vertex_layout* /*layout*/, int /*offset*/, int /*n_verts*/, int /*buffer_handle*/)
|
||||
{
|
||||
|
||||
}
|
||||
void gr_stub_render_movie(movie_material* material_info, primitive_type prim_type, vertex_layout* layout, int n_verts, int buffer)
|
||||
void gr_stub_render_movie(movie_material* /*material_info*/, primitive_type /*prim_type*/, vertex_layout* /*layout*/, int /*n_verts*/, int /*buffer*/, size_t /*buffer_offset*/)
|
||||
{
|
||||
}
|
||||
|
||||
void gr_stub_render_nanovg(nanovg_material* material_info,
|
||||
primitive_type prim_type,
|
||||
vertex_layout* layout,
|
||||
int offset,
|
||||
int n_verts,
|
||||
int buffer_handle) {
|
||||
void gr_stub_render_nanovg(nanovg_material* /*material_info*/,
|
||||
primitive_type /*prim_type*/,
|
||||
vertex_layout* /*layout*/,
|
||||
int /*offset*/,
|
||||
int /*n_verts*/,
|
||||
int /*buffer_handle*/) {
|
||||
}
|
||||
|
||||
void gr_stub_render_primitives_batched(batched_bitmap_material* material_info, primitive_type prim_type, vertex_layout* layout, int offset, int n_verts, int buffer_handle)
|
||||
void gr_stub_render_primitives_batched(batched_bitmap_material* /*material_info*/, primitive_type /*prim_type*/, vertex_layout* /*layout*/, int /*offset*/, int /*n_verts*/, int /*buffer_handle*/)
|
||||
{
|
||||
}
|
||||
|
||||
bool gr_stub_is_capable(gr_capability capability)
|
||||
bool gr_stub_is_capable(gr_capability /*capability*/)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
@@ -367,21 +367,21 @@ int gr_stub_create_query_object()
|
||||
return -1;
|
||||
}
|
||||
|
||||
void gr_stub_query_value(int obj, QueryType type)
|
||||
void gr_stub_query_value(int /*obj*/, QueryType /*type*/)
|
||||
{
|
||||
}
|
||||
|
||||
bool gr_stub_query_value_available(int obj)
|
||||
bool gr_stub_query_value_available(int /*obj*/)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
std::uint64_t gr_stub_get_query_value(int obj)
|
||||
std::uint64_t gr_stub_get_query_value(int /*obj*/)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
void gr_stub_delete_query_object(int obj)
|
||||
void gr_stub_delete_query_object(int /*obj*/)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -524,7 +524,7 @@ bool gr_stub_init()
|
||||
gr_screen.gf_get_query_value = gr_stub_get_query_value;
|
||||
gr_screen.gf_delete_query_object = gr_stub_delete_query_object;
|
||||
|
||||
gr_screen.gf_create_viewport = [](const os::ViewPortProperties& props) {
|
||||
gr_screen.gf_create_viewport = [](const os::ViewPortProperties&) {
|
||||
return std::unique_ptr<os::Viewport>();
|
||||
};
|
||||
gr_screen.gf_use_viewport = [](os::Viewport*) {
|
||||
|
||||
@@ -293,7 +293,7 @@ void gr_light_init() {
|
||||
gr_lights.reserve(1024);
|
||||
}
|
||||
|
||||
void gr_set_lighting(bool set, bool state) {
|
||||
void gr_set_lighting(bool /*set*/, bool state) {
|
||||
if (!state) {
|
||||
return;
|
||||
}
|
||||
|
||||
+12
-23
@@ -635,27 +635,6 @@ float model_material::get_normal_alpha_max() const
|
||||
return Normal_alpha_max;
|
||||
}
|
||||
|
||||
void model_material::set_normal_extrude(float width)
|
||||
{
|
||||
Normal_extrude = true;
|
||||
Normal_extrude_width = width;
|
||||
}
|
||||
|
||||
void model_material::set_normal_extrude()
|
||||
{
|
||||
Normal_extrude = false;
|
||||
}
|
||||
|
||||
bool model_material::is_normal_extrude_active() const
|
||||
{
|
||||
return Normal_extrude;
|
||||
}
|
||||
|
||||
float model_material::get_normal_extrude_width() const
|
||||
{
|
||||
return Normal_extrude_width;
|
||||
}
|
||||
|
||||
void model_material::set_fog(int r, int g, int b, float _near, float _far)
|
||||
{
|
||||
Fog_params.enabled = true;
|
||||
@@ -681,6 +660,16 @@ const model_material::fog& model_material::get_fog() const
|
||||
return Fog_params;
|
||||
}
|
||||
|
||||
void model_material::set_outline_thickness(float thickness) {
|
||||
Outline_thickness = thickness;
|
||||
}
|
||||
float model_material::get_outline_thickness() const {
|
||||
return Outline_thickness;
|
||||
}
|
||||
bool model_material::uses_thick_outlines() const {
|
||||
return Outline_thickness > 0.0f;
|
||||
}
|
||||
|
||||
uint model_material::get_shader_flags() const
|
||||
{
|
||||
uint Shader_flags = 0;
|
||||
@@ -768,8 +757,8 @@ uint model_material::get_shader_flags() const
|
||||
Shader_flags |= SDR_FLAG_MODEL_NORMAL_ALPHA;
|
||||
}
|
||||
|
||||
if ( Normal_extrude ) {
|
||||
Shader_flags |= SDR_FLAG_MODEL_NORMAL_EXTRUDE;
|
||||
if ( uses_thick_outlines() ) {
|
||||
Shader_flags |= SDR_FLAG_MODEL_THICK_OUTLINES;
|
||||
}
|
||||
|
||||
return Shader_flags;
|
||||
|
||||
Loaded 100 of 620 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user