mirror of
https://github.com/scp-fs2open/fs2open.github.com.git
synced 2026-11-07 18:31:26 -10:00
Compare commits
62
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f25d95041d | ||
|
|
60047116fd | ||
|
|
4aa33c7b3e | ||
|
|
373dbeb63f | ||
|
|
361cc76c30 | ||
|
|
3f27183d6d | ||
|
|
3d976f53b4 | ||
|
|
e5af389803 | ||
|
|
ba0f2e7f83 | ||
|
|
f0987a4ad1 | ||
|
|
61dd4356f0 | ||
|
|
679f7f20d7 | ||
|
|
a939a73c14 | ||
|
|
3f5ad1239d | ||
|
|
4e715352c9 | ||
|
|
5f538fa514 | ||
|
|
506ba911d0 | ||
|
|
f44cfa06c8 | ||
|
|
eeb6f5b091 | ||
|
|
18cb07dc72 | ||
|
|
3a4df0d89a | ||
|
|
d33f9db1f0 | ||
|
|
75b26ef94b | ||
|
|
398f4d9053 | ||
|
|
069947e397 | ||
|
|
580d67eca7 | ||
|
|
4bf93e08df | ||
|
|
6c475130d1 | ||
|
|
6f0dec4169 | ||
|
|
3b99402a0a | ||
|
|
6c6ade116f | ||
|
|
4f6c834587 | ||
|
|
c486843e5f | ||
|
|
ec93ac4c0e | ||
|
|
2307d05086 | ||
|
|
d3d48ee6fa | ||
|
|
ac7bdbf269 | ||
|
|
ddf00588d6 | ||
|
|
85a2a8f11e | ||
|
|
e76fdea8b9 | ||
|
|
726ce953c7 | ||
|
|
a545a4ec27 | ||
|
|
fc0662a9c4 | ||
|
|
e5685ded86 | ||
|
|
226cbf1204 | ||
|
|
043466309a | ||
|
|
766624600d | ||
|
|
dab9a41f45 | ||
|
|
51d8ab13d8 | ||
|
|
b93d30e12b | ||
|
|
945db25578 | ||
|
|
67de007ecb | ||
|
|
e9a9b3b978 | ||
|
|
e10522a2c7 | ||
|
|
9f33b432fc | ||
|
|
7a0578a797 | ||
|
|
b81825326c | ||
|
|
b8c2c975c0 | ||
|
|
dc0272e664 | ||
|
|
3e329d64dd | ||
|
|
882ac2b1a1 | ||
|
|
b3153df6be |
No files matched your search
@@ -17,18 +17,18 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
container: ghcr.io/scp-fs2open/linux_build:sha-a8ca321
|
||||
steps:
|
||||
- name: Cache Qt
|
||||
id: cache-qt-lin
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt
|
||||
uses: jurplel/install-qt-action@v2
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-lin
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
|
||||
- uses: actions/checkout@v1
|
||||
name: Checkout
|
||||
@@ -107,30 +107,30 @@ jobs:
|
||||
name: Checkout
|
||||
with:
|
||||
submodules: true
|
||||
- name: Cache Qt
|
||||
id: cache-qt-win
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt (32 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.arch == 'Win32' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win32_msvc2017
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
- name: Install Qt (64 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.arch == 'x64' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win64_msvc2017_64
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-win
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt (32 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.arch == 'Win32' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win32_msvc2017
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
# - name: Install Qt (64 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.arch == 'x64' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win64_msvc2017_64
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
|
||||
- name: Configure CMake
|
||||
env:
|
||||
@@ -144,7 +144,7 @@ jobs:
|
||||
|
||||
cmake -DCMAKE_INSTALL_PREFIX="$(pwd)/install" -DFSO_USE_SPEECH="ON" \
|
||||
-DFSO_USE_VOICEREC="ON" -DMSVC_SIMD_INSTRUCTIONS="$SIMD" \
|
||||
-DFSO_BUILD_QTFRED=ON -DFSO_BUILD_TESTS=ON \
|
||||
-DFSO_BUILD_QTFRED=OFF -DFSO_BUILD_TESTS=ON \
|
||||
-DFSO_INSTALL_DEBUG_FILES="ON" -A "$ARCHITECTURE" \
|
||||
-G "Visual Studio 16 2019" -T "v142" ..
|
||||
- name: Compile
|
||||
|
||||
@@ -41,18 +41,18 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
container: ghcr.io/scp-fs2open/linux_build:sha-a8ca321
|
||||
steps:
|
||||
- name: Cache Qt
|
||||
id: cache-qt-lin
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt
|
||||
uses: jurplel/install-qt-action@v2
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-lin
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
|
||||
- uses: actions/checkout@v1
|
||||
name: Checkout
|
||||
@@ -142,30 +142,30 @@ jobs:
|
||||
name: Checkout
|
||||
with:
|
||||
submodules: true
|
||||
- name: Cache Qt
|
||||
id: cache-qt-win
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt (32 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.arch == 'Win32' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win32_msvc2017
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
- name: Install Qt (64 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.arch == 'x64' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win64_msvc2017_64
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-win
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt (32 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.arch == 'Win32' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win32_msvc2017
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
# - name: Install Qt (64 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.arch == 'x64' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win64_msvc2017_64
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
|
||||
- name: Configure CMake
|
||||
env:
|
||||
@@ -179,7 +179,7 @@ jobs:
|
||||
|
||||
cmake -DCMAKE_INSTALL_PREFIX="$(pwd)/install" -DFSO_USE_SPEECH="ON" \
|
||||
-DFSO_USE_VOICEREC="ON" -DMSVC_SIMD_INSTRUCTIONS="$SIMD" \
|
||||
-DFSO_BUILD_QTFRED=ON -DFSO_BUILD_TESTS=ON \
|
||||
-DFSO_BUILD_QTFRED=OFF -DFSO_BUILD_TESTS=ON \
|
||||
-DFSO_INSTALL_DEBUG_FILES="ON" -A "$ARCHITECTURE" \
|
||||
-G "Visual Studio 16 2019" -T "v142" ..
|
||||
- name: Compile
|
||||
|
||||
@@ -24,19 +24,19 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
container: ghcr.io/scp-fs2open/linux_build:sha-e977d36
|
||||
steps:
|
||||
- name: Cache Qt
|
||||
id: cache-qt-lin
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt
|
||||
uses: jurplel/install-qt-action@v2
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
setup-python: 'false'
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-lin
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# cached: ${{ steps.cache-qt-lin.outputs.cache-hit }}
|
||||
# setup-python: 'false'
|
||||
|
||||
- uses: actions/checkout@v1
|
||||
name: Checkout
|
||||
@@ -83,30 +83,30 @@ jobs:
|
||||
name: Checkout
|
||||
with:
|
||||
submodules: true
|
||||
- name: Cache Qt
|
||||
id: cache-qt-win
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ${{ github.workspace }}/../Qt
|
||||
key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
- name: Install Qt (32 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.compiler == 'MSVC' && matrix.arch == 'Win32' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win32_msvc2017
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
- name: Install Qt (64 bit)
|
||||
uses: jurplel/install-qt-action@v2
|
||||
if: ${{ matrix.compiler == 'MSVC' && matrix.arch == 'x64' }}
|
||||
with:
|
||||
version: ${{ env.QT_VERSION }}
|
||||
dir: ${{ github.workspace }}/..
|
||||
arch: win64_msvc2017_64
|
||||
cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
aqtversion: ==0.8
|
||||
# - name: Cache Qt
|
||||
# id: cache-qt-win
|
||||
# uses: actions/cache@v1
|
||||
# with:
|
||||
# path: ${{ github.workspace }}/../Qt
|
||||
# key: ${{ runner.os }}-${{ matrix.arch }}-QtCache-${{ env.QT_VERSION }}
|
||||
# - name: Install Qt (32 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.compiler == 'MSVC' && matrix.arch == 'Win32' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win32_msvc2017
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
# - name: Install Qt (64 bit)
|
||||
# uses: jurplel/install-qt-action@v2
|
||||
# if: ${{ matrix.compiler == 'MSVC' && matrix.arch == 'x64' }}
|
||||
# with:
|
||||
# version: ${{ env.QT_VERSION }}
|
||||
# dir: ${{ github.workspace }}/..
|
||||
# arch: win64_msvc2017_64
|
||||
# cached: ${{ steps.cache-qt-win.outputs.cache-hit }}
|
||||
# aqtversion: ==0.8
|
||||
|
||||
- name: Configure CMake
|
||||
env:
|
||||
@@ -124,7 +124,7 @@ jobs:
|
||||
else
|
||||
cmake -DFSO_USE_SPEECH="ON" -DFSO_FATAL_WARNINGS="ON" -DFSO_USE_VOICEREC="OFF" -DFSO_BUILD_TESTS="ON" \
|
||||
-DMSVC_SIMD_INSTRUCTIONS=SSE2 -DFSO_BUILD_FRED2="ON" -G "Visual Studio 16 2019" \
|
||||
-DFSO_BUILD_QTFRED=ON -T "v142" -A "$ARCHITECTURE" ..
|
||||
-DFSO_BUILD_QTFRED=OFF -T "v142" -A "$ARCHITECTURE" ..
|
||||
fi
|
||||
- name: Compile
|
||||
working-directory: ./build
|
||||
|
||||
@@ -32,4 +32,4 @@ export LD_LIBRARY_PATH
|
||||
|
||||
cmake -G Ninja -DFSO_FATAL_WARNINGS=ON -DCMAKE_EXPORT_COMPILE_COMMANDS=ON $CMAKE_OPTIONS \
|
||||
-DCMAKE_INSTALL_PREFIX="$(pwd)/install" -DFSO_BUILD_APPIMAGE=ON -DCMAKE_BUILD_TYPE=$CONFIGURATION \
|
||||
-DFFMPEG_USE_PRECOMPILED=ON -DFSO_BUILD_TESTS=ON -DFSO_BUILD_INCLUDED_LIBS=ON -DFSO_BUILD_QTFRED=ON ..
|
||||
-DFFMPEG_USE_PRECOMPILED=ON -DFSO_BUILD_TESTS=ON -DFSO_BUILD_INCLUDED_LIBS=ON -DFSO_BUILD_QTFRED=OFF ..
|
||||
+2
-2
@@ -7840,7 +7840,7 @@ void update_aspect_lock_information(ai_info *aip, vec3d *vec_to_enemy, float dis
|
||||
object *aiobjp = &Objects[shipp->objnum];
|
||||
|
||||
// AL 3-7-98: This probably should never happen, but check to ensure that current_secondary_bank is valid
|
||||
if ( (swp->current_secondary_bank < 0) || (swp->current_secondary_bank > swp->num_secondary_banks) ) {
|
||||
if ( (swp->current_secondary_bank < 0) || (swp->current_secondary_bank >= swp->num_secondary_banks) ) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -9065,7 +9065,7 @@ void ai_chase()
|
||||
}
|
||||
}
|
||||
|
||||
if (timestamp_elapsed(swp->next_secondary_fire_stamp[current_bank]) && weapon_can_lock_on_ship(swip, En_objp->instance)) {
|
||||
if (timestamp_elapsed(swp->next_secondary_fire_stamp[current_bank]) && weapon_target_satisfies_lock_restrictions(swip, En_objp)) {
|
||||
if (current_bank >= 0) {
|
||||
float firing_range;
|
||||
|
||||
|
||||
@@ -274,7 +274,6 @@ cmdline_parm gameclosed_arg("-closed", NULL, AT_NONE); // Cmdline_closed_game
|
||||
cmdline_parm gamerestricted_arg("-restricted", NULL, AT_NONE); // Cmdline_restricted_game
|
||||
cmdline_parm port_arg("-port", "Multiplayer network port", AT_INT);
|
||||
cmdline_parm multilog_arg("-multilog", NULL, AT_NONE); // Cmdline_multi_log
|
||||
cmdline_parm client_dodamage("-clientdamage", NULL, AT_NONE); // Cmdline_client_dodamage
|
||||
cmdline_parm pof_spew("-pofspew", NULL, AT_NONE); // Cmdline_spew_pof_info
|
||||
cmdline_parm weapon_spew("-weaponspew", nullptr, AT_STRING); // Cmdline_spew_weapon_stats
|
||||
cmdline_parm mouse_coords("-coords", NULL, AT_NONE); // Cmdline_mouse_coords
|
||||
@@ -287,7 +286,6 @@ char *Cmdline_game_password = NULL;
|
||||
char *Cmdline_rank_above = NULL;
|
||||
char *Cmdline_rank_below = NULL;
|
||||
int Cmdline_cd_check = 1;
|
||||
int Cmdline_client_dodamage = 0;
|
||||
int Cmdline_closed_game = 0;
|
||||
int Cmdline_freespace_no_music = 0;
|
||||
int Cmdline_freespace_no_sound = 0;
|
||||
@@ -812,7 +810,7 @@ void os_validate_parms(int argc, char *argv[])
|
||||
if (!stricmp(token, "-help") || !stricmp(token, "--help") || !stricmp(token, "-h") || !stricmp(token, "-?")) {
|
||||
printf("FreeSpace 2 Open, version %s\n", FS_VERSION_FULL);
|
||||
printf("Website: http://scp.indiegames.us\n");
|
||||
printf("Mantis (bug reporting): http://scp.indiegames.us/mantis/\n\n");
|
||||
printf("Github (bug reporting): https://github.com/scp-fs2open/fs2open.github.com/issues\n\n");
|
||||
printf("Usage: fs2_open [options]\n");
|
||||
|
||||
// not the prettiest thing but the job gets done
|
||||
@@ -1663,12 +1661,6 @@ bool SetCmdlineParams()
|
||||
Cmdline_multi_log = 1;
|
||||
}
|
||||
|
||||
|
||||
// maybe use old-school client damage
|
||||
if(client_dodamage.found()){
|
||||
Cmdline_client_dodamage = 1;
|
||||
}
|
||||
|
||||
// spew pof info
|
||||
if(pof_spew.found()){
|
||||
Cmdline_spew_pof_info = 1;
|
||||
|
||||
@@ -30,7 +30,6 @@ extern char *Cmdline_game_password;
|
||||
extern char *Cmdline_rank_above;
|
||||
extern char *Cmdline_rank_below;
|
||||
extern int Cmdline_cd_check;
|
||||
extern int Cmdline_client_dodamage;
|
||||
extern int Cmdline_closed_game;
|
||||
extern int Cmdline_freespace_no_music;
|
||||
extern int Cmdline_freespace_no_sound;
|
||||
|
||||
@@ -74,6 +74,7 @@ void GetLightInfo(vec3 position, out vec3 lightDir, out float attenuation)
|
||||
if(dist > lightRadius) {
|
||||
discard;
|
||||
}
|
||||
attenuation = 1.0 - clamp(dist / lightRadius, 0.0, 1.0);
|
||||
} else if (lightType == LT_CONE) {
|
||||
float coneDot = dot(normalize(-lightDir), coneDir);
|
||||
if(dualCone) {
|
||||
|
||||
@@ -566,7 +566,7 @@ typedef struct hc_col {
|
||||
ubyte r, g, b;
|
||||
} hc_col;
|
||||
|
||||
hc_col HC_colors[3] =
|
||||
hc_col HC_colors[HUD_COLOR_SIZE] =
|
||||
{
|
||||
{0, 255, 0}, // Green - get RGB from Adam so it matches palette?-??.pcx
|
||||
{67, 123, 203}, // Blue - get RGB from Adam so it matches palette?-??.pcx
|
||||
|
||||
+15
-11
@@ -21,6 +21,7 @@ struct ai_info;
|
||||
#define HUD_COLOR_GREEN 0
|
||||
#define HUD_COLOR_BLUE 1
|
||||
#define HUD_COLOR_AMBER 2
|
||||
#define HUD_COLOR_SIZE 3 // Number of default colors. Keep this up to date.
|
||||
|
||||
// specify the max distance that the radar should detect objects
|
||||
// Index in Radar_ranges[] array to get values
|
||||
@@ -45,19 +46,22 @@ extern int HUD_default_popup_mask2;
|
||||
extern int HUD_config_default_flags;
|
||||
extern int HUD_config_default_flags2;
|
||||
|
||||
/**
|
||||
* @brief Contains core HUD configuration data
|
||||
* @note Is not default init'd. Assumes new player, PLR, or CSG reads will correctly set data.
|
||||
*/
|
||||
typedef struct HUD_CONFIG_TYPE {
|
||||
int show_flags; // whether to show gauge
|
||||
int show_flags2; // whether to show gauge
|
||||
int popup_flags; // whether gauge is popup
|
||||
int popup_flags2; // whether gauge is popup
|
||||
int rp_flags; // see RP_ flags above
|
||||
int rp_dist; // one of RR_ #defines above
|
||||
int is_observer; // 1 or 0, observer mode or not, respectively
|
||||
int main_color; // the main color
|
||||
ubyte num_msg_window_lines;
|
||||
int show_flags; //!< bitfield, whether to show gauge (0 ~ 31)
|
||||
int show_flags2; //!< bitfield, whether to show gauge (32 ~ 63)
|
||||
int popup_flags; //!< bitfield, whether gauge is popup (0 ~ 31)
|
||||
int popup_flags2; //!< bitfield, whether gauge is popup (32 ~ 63)
|
||||
int rp_flags; //!< one of RP_ #defines in hudconfig.h; Chiefly shows/hides non-ship objects
|
||||
int rp_dist; //!< one of RR_ #defines above; Is the maxium radar view distance setting
|
||||
int is_observer; //!< 1 or 0, observer mode or not, respectively
|
||||
int main_color; //!< the default HUD_COLOR selection for all gauges; each gauge may override this with a custom RGB
|
||||
ubyte num_msg_window_lines; //!< Number of message lines. (Deprecated by HudGaugeMessages::Max_lines)
|
||||
|
||||
// colors for all the gauges
|
||||
color clr[NUM_HUD_GAUGES];
|
||||
color clr[NUM_HUD_GAUGES]; //!< colors for all the gauges
|
||||
} HUD_CONFIG_TYPE;
|
||||
|
||||
extern HUD_CONFIG_TYPE HUD_config;
|
||||
|
||||
@@ -924,7 +924,7 @@ void hud_lock_acquire_uncaged_target(lock_info *current_lock, weapon_info *wip)
|
||||
continue;
|
||||
}*/
|
||||
|
||||
if (!weapon_can_lock_on_ship(wip, A->instance)) {
|
||||
if (!weapon_target_satisfies_lock_restrictions(wip, A)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -1042,7 +1042,7 @@ void hud_lock_determine_lock_target(lock_info *lock_slot, weapon_info *wip)
|
||||
return;
|
||||
}
|
||||
|
||||
if ( !weapon_can_lock_on_ship(wip, lock_slot->obj->instance) ) {
|
||||
if ( !weapon_target_satisfies_lock_restrictions(wip, lock_slot->obj) ) {
|
||||
ship_clear_lock(lock_slot);
|
||||
return;
|
||||
}
|
||||
@@ -1110,7 +1110,7 @@ void hud_lock_determine_lock_target(lock_info *lock_slot, weapon_info *wip)
|
||||
return;
|
||||
}
|
||||
|
||||
if ( !weapon_can_lock_on_ship(wip, lock_slot->obj->instance) ) {
|
||||
if ( !weapon_target_satisfies_lock_restrictions(wip, lock_slot->obj) ) {
|
||||
ship_clear_lock(lock_slot);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -5323,17 +5323,18 @@ SCP_string hud_get_ship_class(const ship *shipp)
|
||||
// try to get alt name
|
||||
if (Fred_running) {
|
||||
ship_class_text = Fred_alt_names[shipp-Ships];
|
||||
|
||||
if (ship_class_text.empty()) {
|
||||
ship_class_text = Ship_info[shipp->ship_info_index].get_display_name();
|
||||
}
|
||||
} else {
|
||||
if (shipp->alt_type_index >= 0) {
|
||||
ship_class_text = mission_parse_lookup_alt_index(shipp->alt_type_index);
|
||||
} else {
|
||||
ship_class_text = Ship_info[shipp->ship_info_index].get_display_name();
|
||||
}
|
||||
}
|
||||
|
||||
// maybe get ship class
|
||||
if (ship_class_text.empty()) {
|
||||
ship_class_text = Ship_info[shipp->ship_info_index].get_display_name();
|
||||
}
|
||||
|
||||
if (!Disable_built_in_translations) {
|
||||
// handle translation
|
||||
if (Lcl_gr) {
|
||||
|
||||
@@ -133,6 +133,8 @@ public:
|
||||
int setAmbientFactor(int factor) {
|
||||
ambientFactor = factor;
|
||||
Cmdline_ambient_factor = factor;
|
||||
gr_calculate_ambient_factor();
|
||||
|
||||
return factor;
|
||||
}
|
||||
|
||||
|
||||
+122
-226
@@ -5,7 +5,8 @@
|
||||
* or otherwise commercially exploit the source or things you created based on the
|
||||
* source.
|
||||
*
|
||||
*/
|
||||
*/
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -42,7 +43,7 @@
|
||||
|
||||
#define NUM_BUTTONS 16
|
||||
#define NUM_TABS 3
|
||||
#define LIST_BUTTONS_MAX 42
|
||||
#define LIST_BUTTONS_MAX 50
|
||||
|
||||
#define SHIPS_DATA_MODE (1<<0)
|
||||
#define WEAPONS_DATA_MODE (1<<1)
|
||||
@@ -235,14 +236,10 @@ typedef struct {
|
||||
int textures_loaded; // if the model has textures loaded for it or not (hacky mem management)
|
||||
} tech_list_entry;
|
||||
|
||||
static tech_list_entry *Ship_list = nullptr;
|
||||
static int Ship_list_size = 0;
|
||||
static tech_list_entry *Weapon_list = nullptr;
|
||||
static int Weapon_list_size = 0;
|
||||
static tech_list_entry *Intel_list = nullptr;
|
||||
static int Intel_list_size = 0;
|
||||
static tech_list_entry *Current_list; // points to currently valid display list
|
||||
static int Current_list_size = 0;
|
||||
static SCP_vector<tech_list_entry> Ship_list;
|
||||
static SCP_vector<tech_list_entry> Weapon_list;
|
||||
static SCP_vector<tech_list_entry> Intel_list;
|
||||
static SCP_vector<tech_list_entry>* Current_list = &Ship_list; // A pointer to the current display list
|
||||
|
||||
// slider stuff
|
||||
static UI_SLIDER2 Tech_slider;
|
||||
@@ -274,64 +271,63 @@ void techroom_init_desc(const char *src, int w)
|
||||
|
||||
void techroom_unload_animation()
|
||||
{
|
||||
int i;
|
||||
|
||||
//clear everything, just in case, it will get loaded when needed later
|
||||
if (Weapon_list != NULL) {
|
||||
for (i = 0; i < Weapon_list_size; i++) {
|
||||
if (Weapon_list[i].animation.num_frames != 0) {
|
||||
generic_anim_unload(&Weapon_list[i].animation);
|
||||
}
|
||||
for (auto& list_entry : Weapon_list) {
|
||||
if (list_entry.animation.type != BM_TYPE_NONE && list_entry.has_anim != 0) {
|
||||
generic_anim_unload(&list_entry.animation);
|
||||
}
|
||||
|
||||
if (Weapon_list[i].bitmap >= 0) {
|
||||
bm_release(Weapon_list[i].bitmap);
|
||||
Weapon_list[i].bitmap = -1;
|
||||
}
|
||||
if (list_entry.bitmap >= 0) {
|
||||
bm_release(list_entry.bitmap);
|
||||
list_entry.bitmap = -1;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < Intel_list_size; i++) {
|
||||
if (Intel_list[i].animation.num_frames != 0) {
|
||||
generic_anim_unload(&Intel_list[i].animation);
|
||||
for (auto & intel_entry : Intel_list) {
|
||||
if (intel_entry.animation.type != BM_TYPE_NONE && intel_entry.has_anim != 0) {
|
||||
generic_anim_unload(&intel_entry.animation);
|
||||
}
|
||||
|
||||
if (Intel_list[i].bitmap >= 0) {
|
||||
bm_release(Intel_list[i].bitmap);
|
||||
Intel_list[i].bitmap = -1;
|
||||
if (intel_entry.bitmap >= 0) {
|
||||
bm_release(intel_entry.bitmap);
|
||||
intel_entry.bitmap = -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void techroom_select_new_entry()
|
||||
{
|
||||
Assert(Current_list != NULL);
|
||||
if (Current_list == NULL || Current_list_size <= 0) {
|
||||
if (Current_list->empty()) {
|
||||
Cur_entry_index = Cur_entry = -1;
|
||||
techroom_init_desc(NULL,0);
|
||||
techroom_init_desc(nullptr,0);
|
||||
return;
|
||||
}
|
||||
|
||||
Cur_entry_index = Current_list[Cur_entry].index;
|
||||
Assert(Cur_entry < static_cast<int>(Current_list->size()));
|
||||
|
||||
Cur_entry_index = Current_list->at(Cur_entry).index;
|
||||
Assert( Cur_entry_index >= 0 );
|
||||
|
||||
// if we are in the ships tab, load the ship model
|
||||
if (Tab == SHIPS_DATA_TAB) {
|
||||
ship_info *sip = &Ship_info[Cur_entry_index];
|
||||
|
||||
int i = 0;
|
||||
// little memory management, kinda hacky but it should keep the techroom at around
|
||||
// 100meg rather than the 700+ it can get to with all ships loaded - taylor
|
||||
for (int i=0; i<Current_list_size; i++) {
|
||||
if ((Current_list[i].model_num > -1) && (Current_list[i].textures_loaded)) {
|
||||
for (auto & list_entry : *Current_list) {
|
||||
if ((list_entry.model_num > -1) && (list_entry.textures_loaded)) {
|
||||
// don't unload any spot within 5 of current
|
||||
if ( (i < Cur_entry + 5) && (i > Cur_entry - 5) )
|
||||
if ((i < Cur_entry + 5) && (i > Cur_entry - 5) )
|
||||
continue;
|
||||
|
||||
mprintf(("TECH ROOM: Dumping excess ship textures...\n"));
|
||||
|
||||
model_page_out_textures(Current_list[i].model_num);
|
||||
model_page_out_textures(list_entry.model_num);
|
||||
|
||||
Current_list[i].textures_loaded = 0;
|
||||
list_entry.textures_loaded = 0;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
Techroom_ship_modelnum = model_load(sip->pof_file, sip->n_subsystems, &sip->subsystems[0]);
|
||||
@@ -341,12 +337,14 @@ void techroom_select_new_entry()
|
||||
}
|
||||
Techroom_ship_model_instance = model_create_instance(true, Techroom_ship_modelnum);
|
||||
|
||||
Current_list[Cur_entry].model_num = Techroom_ship_modelnum;
|
||||
model_set_up_techroom_instance(sip, Techroom_ship_model_instance);
|
||||
|
||||
Current_list->at(Cur_entry).model_num = Techroom_ship_modelnum;
|
||||
|
||||
// page in ship textures properly (takes care of nondimming pixels)
|
||||
model_page_in_textures(Techroom_ship_modelnum, Cur_entry_index);
|
||||
|
||||
Current_list[Cur_entry].textures_loaded = 1;
|
||||
Current_list->at(Cur_entry).textures_loaded = 1;
|
||||
} else {
|
||||
Techroom_ship_modelnum = -1;
|
||||
|
||||
@@ -358,19 +356,19 @@ void techroom_select_new_entry()
|
||||
Trackball_mode = 0;
|
||||
|
||||
// load animation here, we now only have one loaded
|
||||
int stream_result = generic_anim_init_and_stream(&Current_list[Cur_entry].animation, Current_list[Cur_entry].tech_anim_filename, bm_get_type(Tech_background_bitmap), true);
|
||||
int stream_result = generic_anim_init_and_stream(&Current_list->at(Cur_entry).animation, Current_list->at(Cur_entry).tech_anim_filename, bm_get_type(Tech_background_bitmap), true);
|
||||
|
||||
if (stream_result >= 0) {
|
||||
Current_list[Cur_entry].has_anim = 1;
|
||||
Current_list->at(Cur_entry).has_anim = 1;
|
||||
} else {
|
||||
// we've failed to load any animation
|
||||
// load an image and treat it like a 1 frame animation
|
||||
Current_list[Cur_entry].bitmap = bm_load(Current_list[Cur_entry].tech_anim_filename);
|
||||
Current_list->at(Cur_entry).bitmap = bm_load(Current_list->at(Cur_entry).tech_anim_filename);
|
||||
}
|
||||
}
|
||||
|
||||
techroom_init_desc(Current_list[Cur_entry].desc, Tech_desc_coords[gr_screen.res][SHIP_W_COORD]);
|
||||
fsspeech_play(FSSPEECH_FROM_TECHROOM, Current_list[Cur_entry].desc);
|
||||
techroom_init_desc(Current_list->at(Cur_entry).desc, Tech_desc_coords[gr_screen.res][SHIP_W_COORD]);
|
||||
fsspeech_play(FSSPEECH_FROM_TECHROOM, Current_list->at(Cur_entry).desc);
|
||||
}
|
||||
|
||||
// write out the current description in the bottom window
|
||||
@@ -432,7 +430,7 @@ void tech_common_render()
|
||||
y = 0;
|
||||
z = List_offset;
|
||||
while (y + font_height <= Tech_list_coords[gr_screen.res][SHIP_H_COORD]) {
|
||||
if (z >= Current_list_size) {
|
||||
if ((z - List_offset) >= LIST_BUTTONS_MAX || z >= static_cast<int>(Current_list->size())) {
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -445,7 +443,7 @@ void tech_common_render()
|
||||
}
|
||||
|
||||
memset( buf, 0, sizeof(buf) );
|
||||
strncpy(buf, Current_list[z].name, sizeof(buf) - 1);
|
||||
strncpy(buf, Current_list->at(z).name, sizeof(buf) - 1);
|
||||
|
||||
if (Lcl_gr && !Disable_built_in_translations)
|
||||
lcl_translate_ship_name_gr(buf);
|
||||
@@ -467,8 +465,6 @@ void tech_common_render()
|
||||
}
|
||||
}
|
||||
|
||||
void light_set_all_relevent();
|
||||
|
||||
void techroom_ships_render(float frametime)
|
||||
{
|
||||
// render all the common stuff
|
||||
@@ -480,7 +476,6 @@ void techroom_ships_render(float frametime)
|
||||
// now render the trackball ship, which is unique to the ships tab
|
||||
float rev_rate = REVOLUTION_RATE;
|
||||
angles rot_angles, view_angles;
|
||||
int i, j;
|
||||
ship_info *sip = &Ship_info[Cur_entry_index];
|
||||
model_render_params render_info;
|
||||
|
||||
@@ -551,31 +546,6 @@ void techroom_ships_render(float frametime)
|
||||
model_clear_instance(Techroom_ship_modelnum);
|
||||
render_info.set_detail_level_lock(0);
|
||||
|
||||
polymodel *pm = model_get(Techroom_ship_modelnum);
|
||||
polymodel_instance *pmi = model_get_instance(Techroom_ship_model_instance);
|
||||
|
||||
for (i = 0; i < sip->n_subsystems; i++) {
|
||||
model_subsystem *msp = &sip->subsystems[i];
|
||||
if (msp->type == SUBSYSTEM_TURRET) {
|
||||
|
||||
float p = 0.0f;
|
||||
float h = 0.0f;
|
||||
|
||||
for (j = 0; j < msp->n_triggers; j++) {
|
||||
|
||||
// special case for turrets
|
||||
p = msp->triggers[j].angle.xyz.x;
|
||||
h = msp->triggers[j].angle.xyz.y;
|
||||
}
|
||||
if ( msp->subobj_num >= 0 ) {
|
||||
model_set_instance_techroom(pm, pmi, msp->subobj_num, 0.0f, h );
|
||||
}
|
||||
if ( (msp->subobj_num != msp->turret_gun_sobj) && (msp->turret_gun_sobj >= 0) ) {
|
||||
model_set_instance_techroom(pm, pmi, msp->turret_gun_sobj, p, 0.0f );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (sip->replacement_textures.size() > 0)
|
||||
{
|
||||
render_info.set_replacement_textures(Techroom_ship_modelnum, sip->replacement_textures);
|
||||
@@ -585,10 +555,12 @@ void techroom_ships_render(float frametime)
|
||||
{
|
||||
gr_reset_clip();
|
||||
|
||||
auto pm = model_get(Techroom_ship_modelnum);
|
||||
|
||||
shadows_start_render(&Eye_matrix, &Eye_position, Proj_fov, gr_screen.clip_aspect, -sip->closeup_pos.xyz.z + pm->rad, -sip->closeup_pos.xyz.z + pm->rad + 200.0f, -sip->closeup_pos.xyz.z + pm->rad + 2000.0f, -sip->closeup_pos.xyz.z + pm->rad + 10000.0f);
|
||||
render_info.set_flags(MR_NO_TEXTURING | MR_NO_LIGHTING | MR_AUTOCENTER);
|
||||
|
||||
model_render_immediate(&render_info, Techroom_ship_modelnum, &Techroom_ship_orient, &vmd_zero_vector);
|
||||
model_render_immediate(&render_info, Techroom_ship_modelnum, Techroom_ship_model_instance, &Techroom_ship_orient, &vmd_zero_vector);
|
||||
shadows_end_render();
|
||||
|
||||
gr_set_clip(Tech_ship_display_coords[gr_screen.res][SHIP_X_COORD], Tech_ship_display_coords[gr_screen.res][SHIP_Y_COORD], Tech_ship_display_coords[gr_screen.res][SHIP_W_COORD], Tech_ship_display_coords[gr_screen.res][SHIP_H_COORD], GR_RESIZE_MENU);
|
||||
@@ -604,7 +576,7 @@ void techroom_ships_render(float frametime)
|
||||
|
||||
render_info.set_flags(render_flags);
|
||||
|
||||
model_render_immediate(&render_info, Techroom_ship_modelnum, &Techroom_ship_orient, &vmd_zero_vector);
|
||||
model_render_immediate(&render_info, Techroom_ship_modelnum, Techroom_ship_model_instance, &Techroom_ship_orient, &vmd_zero_vector);
|
||||
|
||||
Glowpoint_use_depth_buffer = true;
|
||||
|
||||
@@ -626,7 +598,7 @@ void tech_prev_entry()
|
||||
|
||||
Cur_entry--;
|
||||
if (Cur_entry < 0) {
|
||||
Cur_entry = Current_list_size - 1;
|
||||
Cur_entry = static_cast<int>(Current_list->size() - 1);
|
||||
|
||||
// scroll to end of list
|
||||
List_offset = Cur_entry - Tech_list_coords[gr_screen.res][SHIP_H_COORD] / gr_get_font_height() + 1;
|
||||
@@ -654,7 +626,7 @@ void tech_next_entry()
|
||||
techroom_unload_animation();
|
||||
|
||||
Cur_entry++;
|
||||
if (Cur_entry >= Current_list_size) {
|
||||
if (Cur_entry >= static_cast<int>(Current_list->size())) {
|
||||
Cur_entry = 0;
|
||||
|
||||
// scroll to beginning of list
|
||||
@@ -710,7 +682,7 @@ void tech_scroll_list_up()
|
||||
|
||||
void tech_scroll_list_down()
|
||||
{
|
||||
if (List_offset + Tech_list_coords[gr_screen.res][SHIP_H_COORD] / gr_get_font_height() < Current_list_size) {
|
||||
if (List_offset + Tech_list_coords[gr_screen.res][SHIP_H_COORD] / gr_get_font_height() < static_cast<int>(Current_list->size())) {
|
||||
List_offset++;
|
||||
gamesnd_play_iface(InterfaceSounds::SCROLL);
|
||||
} else {
|
||||
@@ -735,27 +707,27 @@ void techroom_anim_render(float frametime)
|
||||
tech_common_render();
|
||||
|
||||
// exit now if there are no entries to show
|
||||
if (Current_list_size == 0 || Cur_entry < 0)
|
||||
if (Current_list->empty() || Cur_entry < 0 || Cur_entry >= static_cast<int>(Current_list->size()))
|
||||
return;
|
||||
|
||||
// render the animation
|
||||
if(Current_list[Cur_entry].animation.num_frames > 0)
|
||||
if(Current_list->at(Cur_entry).animation.num_frames > 0)
|
||||
{
|
||||
//grab dimensions
|
||||
bm_get_info((Current_list[Cur_entry].animation.streaming) ? Current_list[Cur_entry].animation.bitmap_id : Current_list[Cur_entry].animation.first_frame, &x, &y, NULL, NULL, NULL);
|
||||
bm_get_info((Current_list->at(Cur_entry).animation.streaming) ? Current_list->at(Cur_entry).animation.bitmap_id : Current_list->at(Cur_entry).animation.first_frame, &x, &y, nullptr, nullptr, nullptr);
|
||||
//get the centre point - adjust
|
||||
x = Tech_ani_centre_coords[gr_screen.res][0] - x / 2;
|
||||
y = Tech_ani_centre_coords[gr_screen.res][1] - y / 2;
|
||||
generic_anim_render(&Current_list[Cur_entry].animation, frametime, x, y, true);
|
||||
generic_anim_render(&Current_list->at(Cur_entry).animation, frametime, x, y, true);
|
||||
}
|
||||
// if our active item has a bitmap instead of an animation, draw it
|
||||
else if((Cur_entry >= 0) && (Current_list[Cur_entry].bitmap >= 0)){
|
||||
else if((Cur_entry >= 0) && (Current_list->at(Cur_entry).bitmap >= 0)){
|
||||
//grab dimensions
|
||||
bm_get_info(Current_list[Cur_entry].bitmap, &x, &y, NULL, NULL, NULL);
|
||||
bm_get_info(Current_list->at(Cur_entry).bitmap, &x, &y, nullptr, nullptr, nullptr);
|
||||
//get the centre point - adjust
|
||||
x = Tech_ani_centre_coords[gr_screen.res][0] - x / 2;
|
||||
y = Tech_ani_centre_coords[gr_screen.res][1] - y / 2;
|
||||
gr_set_bitmap(Current_list[Cur_entry].bitmap);
|
||||
gr_set_bitmap(Current_list->at(Cur_entry).bitmap);
|
||||
gr_bitmap(x, y, GR_RESIZE_MENU);
|
||||
}
|
||||
}
|
||||
@@ -792,50 +764,40 @@ void techroom_change_tab(int num)
|
||||
|
||||
// load ship info if necessary
|
||||
if ( !Ships_loaded ) {
|
||||
if (Ship_list == NULL) {
|
||||
Ship_list = new tech_list_entry[Ship_info.size()];
|
||||
if (Ship_list.empty()) {
|
||||
Ship_list.reserve(Ship_info.size());
|
||||
}
|
||||
Ship_list_size = 0;
|
||||
|
||||
tech_list_entry temp_entry;
|
||||
|
||||
// we always initially set these values, so keep them outside the loop.
|
||||
temp_entry.bitmap = -1;
|
||||
temp_entry.animation.num_frames = 0; // no anim for ships
|
||||
temp_entry.has_anim = 0; // no anim for ships
|
||||
temp_entry.model_num = -1;
|
||||
temp_entry.textures_loaded = 0;
|
||||
|
||||
for (auto it = Ship_info.begin(); it != Ship_info.end(); ++it)
|
||||
{
|
||||
if (Techroom_show_all || (it->flags & si_mask).any_set())
|
||||
{
|
||||
// this ship should be displayed, fill out the entry struct
|
||||
Ship_list[Ship_list_size].bitmap = -1;
|
||||
Ship_list[Ship_list_size].index = (int)std::distance(Ship_info.begin(), it);
|
||||
Ship_list[Ship_list_size].animation.num_frames = 0; // no anim for ships
|
||||
Ship_list[Ship_list_size].has_anim = 0; // no anim for ships
|
||||
Ship_list[Ship_list_size].name = *it->tech_title ? it->tech_title : it->get_display_name();
|
||||
Ship_list[Ship_list_size].desc = it->tech_desc;
|
||||
Ship_list[Ship_list_size].model_num = -1;
|
||||
Ship_list[Ship_list_size].textures_loaded = 0;
|
||||
temp_entry.index = (int)std::distance(Ship_info.begin(), it);
|
||||
temp_entry.name = *it->tech_title ? it->tech_title : it->get_display_name();
|
||||
temp_entry.desc = it->tech_desc;
|
||||
|
||||
Ship_list_size++;
|
||||
Ship_list.push_back(temp_entry);
|
||||
}
|
||||
}
|
||||
|
||||
// make sure that at least the default entry is cleared out if we didn't grab anything
|
||||
if (!Ship_info.empty() && !Ship_list_size) {
|
||||
Ship_list[0].index = -1;
|
||||
Ship_list[0].desc = NULL;
|
||||
Ship_list[0].name = NULL;
|
||||
Ship_list[0].bitmap = -1;
|
||||
Ship_list[0].has_anim = 0;
|
||||
Ship_list[0].animation.num_frames = 0;
|
||||
Ship_list[0].model_num = -1;
|
||||
Ship_list[0].textures_loaded = 0;
|
||||
}
|
||||
|
||||
Ships_loaded = true;
|
||||
}
|
||||
|
||||
Current_list = Ship_list;
|
||||
Current_list_size = Ship_list_size;
|
||||
Current_list = &Ship_list;
|
||||
|
||||
font_height = gr_get_font_height();
|
||||
max_num_entries_viewable = Tech_list_coords[gr_screen.res][SHIP_H_COORD] / font_height;
|
||||
Tech_slider.set_numberItems(Current_list_size > max_num_entries_viewable ? Current_list_size-max_num_entries_viewable : 0);
|
||||
Tech_slider.set_numberItems((int)Current_list->size() > max_num_entries_viewable ? (int)Current_list->size()-max_num_entries_viewable : 0);
|
||||
|
||||
// no anim to start here
|
||||
break;
|
||||
@@ -844,57 +806,45 @@ void techroom_change_tab(int num)
|
||||
|
||||
// load weapon info & anims if necessary
|
||||
if ( !Weapons_loaded ) {
|
||||
if (Weapon_list == NULL) {
|
||||
Weapon_list = new tech_list_entry[Weapon_info.size()];
|
||||
}
|
||||
Weapon_list_size = 0;
|
||||
Weapon_list.reserve(Weapon_info.size());
|
||||
|
||||
wi_mask.set(multi ? Weapon::Info_Flags::Player_allowed : Weapon::Info_Flags::In_tech_database);
|
||||
wi_mask.set(Weapon::Info_Flags::Default_in_tech_database);
|
||||
|
||||
int i = 0;
|
||||
tech_list_entry temp_entry;
|
||||
|
||||
// we always initially set these values, so keep them outside the loop.
|
||||
temp_entry.has_anim = 1;
|
||||
temp_entry.bitmap = -1;
|
||||
temp_entry.animation.num_frames = 0;
|
||||
temp_entry.model_num = -1;
|
||||
temp_entry.textures_loaded = 0;
|
||||
|
||||
for (auto &wi : Weapon_info)
|
||||
{
|
||||
if (Techroom_show_all || (wi.wi_flags & wi_mask).any_set())
|
||||
{
|
||||
// we have a weapon that should be in the tech db, so fill out the entry struct
|
||||
Weapon_list[Weapon_list_size].index = i;
|
||||
Weapon_list[Weapon_list_size].desc = wi.tech_desc;
|
||||
Weapon_list[Weapon_list_size].has_anim = 1;
|
||||
Weapon_list[Weapon_list_size].name = wi.tech_title[0] ? wi.tech_title : wi.get_display_name();
|
||||
Weapon_list[Weapon_list_size].bitmap = -1;
|
||||
Weapon_list[Weapon_list_size].animation.num_frames = 0;
|
||||
Weapon_list[Weapon_list_size].model_num = -1;
|
||||
Weapon_list[Weapon_list_size].textures_loaded = 0;
|
||||
// we have a weapon that should be in the tech db, so fill out specific info
|
||||
temp_entry.index = i;
|
||||
temp_entry.desc = wi.tech_desc;
|
||||
temp_entry.name = wi.tech_title[0] ? wi.tech_title : wi.get_display_name();
|
||||
// copy the weapon animation filename
|
||||
strncpy(Weapon_list[Weapon_list_size].tech_anim_filename, wi.tech_anim_filename, MAX_FILENAME_LEN - 1);
|
||||
|
||||
++Weapon_list_size;
|
||||
strncpy(temp_entry.tech_anim_filename, wi.tech_anim_filename, MAX_FILENAME_LEN - 1);
|
||||
|
||||
Weapon_list.push_back(temp_entry);
|
||||
}
|
||||
++i;
|
||||
}
|
||||
|
||||
// make sure that at least the default entry is cleared out if we didn't grab anything
|
||||
if (!Weapon_info.empty() && !Weapon_list_size) {
|
||||
Weapon_list[0].index = -1;
|
||||
Weapon_list[0].desc = NULL;
|
||||
Weapon_list[0].name = NULL;
|
||||
Weapon_list[0].bitmap = -1;
|
||||
Weapon_list[0].has_anim = 0;
|
||||
Weapon_list[0].animation.num_frames = 0;
|
||||
Weapon_list[0].model_num = -1;
|
||||
Weapon_list[0].textures_loaded = 0;
|
||||
}
|
||||
|
||||
Weapons_loaded = true;
|
||||
}
|
||||
|
||||
Current_list = Weapon_list;
|
||||
Current_list_size = Weapon_list_size;
|
||||
Current_list = &Weapon_list;
|
||||
|
||||
font_height = gr_get_font_height();
|
||||
max_num_entries_viewable = Tech_list_coords[gr_screen.res][SHIP_H_COORD] / font_height;
|
||||
Tech_slider.set_numberItems(Current_list_size > max_num_entries_viewable ? Current_list_size-max_num_entries_viewable : 0);
|
||||
Tech_slider.set_numberItems(static_cast<int>(Current_list->size()) > max_num_entries_viewable ? static_cast<int>(Current_list->size())-max_num_entries_viewable : 0);
|
||||
|
||||
break;
|
||||
|
||||
@@ -902,60 +852,46 @@ void techroom_change_tab(int num)
|
||||
|
||||
// load intel if necessary
|
||||
if ( !Intel_loaded ) {
|
||||
if (Intel_list == nullptr) {
|
||||
Intel_list = new tech_list_entry[Intel_info.size()];
|
||||
if (Intel_list.empty()) {
|
||||
Intel_list.reserve(Intel_info.size());
|
||||
}
|
||||
|
||||
Intel_list_size = 0;
|
||||
|
||||
int i = 0;
|
||||
tech_list_entry temp_entry;
|
||||
|
||||
// we always initially set these values, so keep them outside the loop.
|
||||
temp_entry.has_anim = 0;
|
||||
temp_entry.model_num = -1;
|
||||
temp_entry.textures_loaded = 0;
|
||||
|
||||
for (auto &ii : Intel_info) {
|
||||
|
||||
if (Techroom_show_all || (ii.flags & IIF_IN_TECH_DATABASE)) {
|
||||
// leave option for no animation if string == "none"
|
||||
if (!strcmp(ii.anim_filename, "none")) {
|
||||
Intel_list[Intel_list_size].has_anim = 0;
|
||||
Intel_list[Intel_list_size].animation.num_frames = 0;
|
||||
temp_entry.animation.num_frames = 0;
|
||||
} else {
|
||||
// try and load as an animation
|
||||
Intel_list[Intel_list_size].has_anim = 0;
|
||||
Intel_list[Intel_list_size].bitmap = -1;
|
||||
strncpy(Intel_list[Intel_list_size].tech_anim_filename, ii.anim_filename, NAME_LENGTH - 1);
|
||||
temp_entry.bitmap = -1;
|
||||
strncpy(temp_entry.tech_anim_filename, ii.anim_filename, NAME_LENGTH - 1);
|
||||
}
|
||||
|
||||
Intel_list[Intel_list_size].desc = ii.desc.c_str();
|
||||
Intel_list[Intel_list_size].index = i;
|
||||
Intel_list[Intel_list_size].name = ii.name;
|
||||
Intel_list[Intel_list_size].model_num = -1;
|
||||
Intel_list[Intel_list_size].textures_loaded = 0;
|
||||
temp_entry.desc = ii.desc.c_str();
|
||||
temp_entry.index = i;
|
||||
temp_entry.name = ii.name;
|
||||
|
||||
Intel_list_size++;
|
||||
Intel_list.push_back(temp_entry);
|
||||
}
|
||||
++i;
|
||||
}
|
||||
|
||||
// make sure that at least the default entry is cleared out if we didn't grab anything
|
||||
if (!Intel_info.empty() && !Intel_list_size) {
|
||||
Intel_list[0].index = -1;
|
||||
Intel_list[0].desc = NULL;
|
||||
Intel_list[0].name = NULL;
|
||||
Intel_list[0].bitmap = -1;
|
||||
Intel_list[0].has_anim = 0;
|
||||
Intel_list[0].animation.num_frames = 0;
|
||||
Intel_list[0].model_num = -1;
|
||||
Intel_list[0].textures_loaded = 0;
|
||||
}
|
||||
|
||||
Intel_loaded = true;
|
||||
}
|
||||
|
||||
// index lookup on intel is a pretty pointless, but it keeps everything
|
||||
// consistent and doesn't really hurt anything
|
||||
Current_list = Intel_list;
|
||||
Current_list_size = Intel_list_size;
|
||||
Current_list = &Intel_list;
|
||||
|
||||
font_height = gr_get_font_height();
|
||||
max_num_entries_viewable = Tech_list_coords[gr_screen.res][SHIP_H_COORD] / font_height;
|
||||
Tech_slider.set_numberItems(Current_list_size > max_num_entries_viewable ? Current_list_size-max_num_entries_viewable : 0);
|
||||
Tech_slider.set_numberItems(static_cast<int>(Current_list->size()) > max_num_entries_viewable ? static_cast<int>(Current_list->size())-max_num_entries_viewable : 0);
|
||||
|
||||
break;
|
||||
}
|
||||
@@ -1123,7 +1059,7 @@ void techroom_intel_reset()
|
||||
|
||||
void techroom_init()
|
||||
{
|
||||
int i, idx;
|
||||
int i;
|
||||
techroom_buttons *b;
|
||||
|
||||
Ships_loaded = false;
|
||||
@@ -1212,9 +1148,9 @@ void techroom_init()
|
||||
Tech_slider.create(&Ui_window, Tech_slider_coords[gr_screen.res][SHIP_X_COORD], Tech_slider_coords[gr_screen.res][SHIP_Y_COORD], Tech_slider_coords[gr_screen.res][SHIP_W_COORD], Tech_slider_coords[gr_screen.res][SHIP_H_COORD], (int)Ship_info.size(), Tech_slider_filename[gr_screen.res], &tech_scroll_list_up, &tech_scroll_list_down, &tech_ship_scroll_capture);
|
||||
|
||||
// zero intel anim/bitmap stuff
|
||||
for(idx=0; idx<Intel_list_size; idx++){
|
||||
Intel_list[idx].animation.num_frames = 0;
|
||||
Intel_list[idx].bitmap = -1;
|
||||
for(auto & intel_item : Intel_list){
|
||||
intel_item.animation.num_frames = 0;
|
||||
intel_item.bitmap = -1;
|
||||
}
|
||||
|
||||
mprintf(("Techroom successfully initialized, now changing tab...\n"));
|
||||
@@ -1223,63 +1159,23 @@ void techroom_init()
|
||||
|
||||
void techroom_lists_reset()
|
||||
{
|
||||
int i;
|
||||
|
||||
//unload the current animation, we load another one for the new current entry
|
||||
if(Tab != SHIPS_DATA_TAB)
|
||||
if (Tab != SHIPS_DATA_TAB)
|
||||
techroom_unload_animation();
|
||||
|
||||
Current_list = NULL;
|
||||
Current_list_size = 0;
|
||||
|
||||
model_free_all();
|
||||
Techroom_ship_modelnum = -1;
|
||||
Techroom_ship_model_instance = -1;
|
||||
|
||||
if (Ship_list != NULL) {
|
||||
delete[] Ship_list;
|
||||
Ship_list = NULL;
|
||||
}
|
||||
|
||||
Ship_list_size = 0;
|
||||
// This can be cleared immediately because there are no anims or bitmaps associated.
|
||||
Ship_list.clear();
|
||||
Ships_loaded = false;
|
||||
|
||||
if (Weapon_list != NULL) {
|
||||
for (i = 0; i < Weapon_list_size; i++) {
|
||||
if (Weapon_list[i].animation.num_frames != 0) {
|
||||
generic_anim_unload(&Weapon_list[i].animation);
|
||||
}
|
||||
|
||||
if (Weapon_list[i].bitmap >= 0) {
|
||||
bm_release(Weapon_list[i].bitmap);
|
||||
Weapon_list[i].bitmap = -1;
|
||||
}
|
||||
}
|
||||
|
||||
delete[] Weapon_list;
|
||||
Weapon_list = NULL;
|
||||
}
|
||||
|
||||
Weapon_list_size = 0;
|
||||
// now that we're sure all the bitmaps are released, clear the vectors.
|
||||
Weapon_list.clear();
|
||||
Weapons_loaded = false;
|
||||
|
||||
if (Intel_list != nullptr) {
|
||||
for (i = 0; i < Intel_list_size; i++) {
|
||||
if (Intel_list[i].animation.num_frames != 0) {
|
||||
generic_anim_unload(&Intel_list[i].animation);
|
||||
}
|
||||
|
||||
if (Intel_list[i].bitmap >= 0) {
|
||||
bm_release(Intel_list[i].bitmap);
|
||||
Intel_list[i].bitmap = -1;
|
||||
}
|
||||
}
|
||||
|
||||
delete[] Intel_list;
|
||||
Intel_list = nullptr;
|
||||
}
|
||||
|
||||
Intel_list_size = 0;
|
||||
Intel_list.clear();
|
||||
Intel_loaded = false;
|
||||
}
|
||||
|
||||
|
||||
@@ -463,6 +463,7 @@ void mission_brief_common_reset()
|
||||
memset( Briefings[i].stages[j].icons, 0, sizeof(brief_icon) * MAX_STAGE_ICONS );
|
||||
Briefings[i].stages[j].icons->ship_class = -1;
|
||||
Briefings[i].stages[j].icons->modelnum = -1;
|
||||
Briefings[i].stages[j].icons->model_instance_num = -1;
|
||||
Briefings[i].stages[j].icons->bitmap_id = -1;
|
||||
}
|
||||
|
||||
|
||||
@@ -114,6 +114,7 @@ typedef struct brief_icon {
|
||||
int hold_x, hold_y; // 2D screen position of icon, used to place animations
|
||||
int ship_class;
|
||||
int modelnum;
|
||||
int model_instance_num;
|
||||
float radius;
|
||||
int type; // ICON_* defines from MissionBriefCommon.h
|
||||
int bitmap_id;
|
||||
|
||||
@@ -1509,6 +1509,8 @@ void parse_briefing(mission * /*pm*/, int flags)
|
||||
find_and_stuff("$team:", &bi->team, F_NAME, temp_team_names, Num_iffs, "team name");
|
||||
|
||||
find_and_stuff("$class:", &bi->ship_class, F_NAME, Ship_class_names, Ship_info.size(), "ship class");
|
||||
bi->modelnum = -1;
|
||||
bi->model_instance_num = -1;
|
||||
|
||||
// Goober5000 - import
|
||||
if (flags & MPF_IMPORT_FSM)
|
||||
@@ -8085,6 +8087,33 @@ void mission_parse_reset_alt()
|
||||
Mission_alt_type_count = 0;
|
||||
}
|
||||
|
||||
// For compatibility purposes some mods want alt names to truncate at the hash symbol. But we can't actually do that at mission load,
|
||||
// since we have to save them again in FRED. So this function processes the names just before the mission starts.
|
||||
// To further complicate things, some mods actually want the hash to be displayed. So this function uses the double-hash as an escape sequence for a single hash.
|
||||
void mission_process_alt_types()
|
||||
{
|
||||
for (int i = 0; i < Mission_alt_type_count; ++i)
|
||||
{
|
||||
// truncate at a single hash
|
||||
end_string_at_first_hash_symbol(Mission_alt_types[i], true);
|
||||
|
||||
// consolidate double hashes
|
||||
auto src = Mission_alt_types[i];
|
||||
auto dest = src;
|
||||
while (*src)
|
||||
{
|
||||
if (*src == '#' && *(src + 1) == '#')
|
||||
dest--;
|
||||
|
||||
++src;
|
||||
++dest;
|
||||
|
||||
if (src != dest)
|
||||
*dest = *src;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Callsign stuff
|
||||
*/
|
||||
|
||||
@@ -518,9 +518,6 @@ int get_parse_name_index(const char *name);
|
||||
// called from freespace game level loop
|
||||
void mission_parse_eval_stuff();
|
||||
|
||||
// function to set the ramaing time left in the mission
|
||||
void mission_parse_set_end_time( int seconds );
|
||||
|
||||
// code to bring in a repair ship.
|
||||
void mission_bring_in_support_ship( object *requester_objp );
|
||||
int mission_is_support_ship_arriving( void );
|
||||
@@ -535,6 +532,7 @@ const char *mission_parse_lookup_alt_index(int index);
|
||||
int mission_parse_add_alt(const char *name);
|
||||
void mission_parse_remove_alt(const char *name);
|
||||
void mission_parse_reset_alt();
|
||||
void mission_process_alt_types();
|
||||
|
||||
// callsign stuff
|
||||
int mission_parse_lookup_callsign(const char *name);
|
||||
|
||||
@@ -704,8 +704,13 @@ brief_icon *brief_get_closeup_icon()
|
||||
// stop showing the closeup view of an icon
|
||||
void brief_turn_off_closeup_icon()
|
||||
{
|
||||
// turn off closup
|
||||
// turn off closeup
|
||||
if ( Closeup_icon != NULL ) {
|
||||
if (Closeup_icon->model_instance_num >= 0) {
|
||||
model_delete_instance(Closeup_icon->model_instance_num);
|
||||
Closeup_icon->model_instance_num = -1;
|
||||
}
|
||||
|
||||
gamesnd_play_iface(InterfaceSounds::BRIEF_ICON_SELECT);
|
||||
Closeup_icon = NULL;
|
||||
Closeup_close_button.disable();
|
||||
@@ -1075,7 +1080,7 @@ void brief_render_closeup(int ship_class, float frametime)
|
||||
render_info.set_flags(MR_AUTOCENTER);
|
||||
}
|
||||
|
||||
model_render_immediate( &render_info, Closeup_icon->modelnum, &Closeup_orient, &Closeup_pos );
|
||||
model_render_immediate( &render_info, Closeup_icon->modelnum, Closeup_icon->model_instance_num, &Closeup_orient, &Closeup_pos );
|
||||
|
||||
The_mission.flags.set(Mission::Mission_Flags::Fullneb, neb_restore);
|
||||
|
||||
@@ -1198,28 +1203,6 @@ void brief_set_closeup_pos(brief_icon * /*bi*/)
|
||||
Closeup_x1 = (int)std::lround(320 - Closeup_coords[gr_screen.res][BRIEF_W_COORD]/2.0f);
|
||||
}
|
||||
|
||||
void brief_get_closeup_ship_modelnum(brief_icon *ci)
|
||||
{
|
||||
object *objp;
|
||||
ship *sp;
|
||||
|
||||
// find the model number for the ship to display
|
||||
for ( objp = GET_FIRST(&obj_used_list); objp !=END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) {
|
||||
|
||||
if ( objp == &obj_used_list || objp->type != OBJ_SHIP ) {
|
||||
continue;
|
||||
}
|
||||
|
||||
sp = &Ships[objp->instance];
|
||||
if ( sp->ship_info_index == ci->ship_class ) {
|
||||
ci->ship_class = sp->ship_info_index;
|
||||
ci->modelnum = Ship_info[sp->ship_info_index].model_num;
|
||||
ci->radius = objp->radius;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------------------------
|
||||
// brief_setup_closeup()
|
||||
//
|
||||
@@ -1234,6 +1217,7 @@ int brief_setup_closeup(brief_icon *bi)
|
||||
Closeup_icon = bi;
|
||||
Closeup_icon->ship_class = bi->ship_class;
|
||||
Closeup_icon->modelnum = -1;
|
||||
Closeup_icon->model_instance_num = -1;
|
||||
|
||||
Closeup_one_revolution_time = ONE_REV_TIME;
|
||||
|
||||
@@ -1270,7 +1254,6 @@ int brief_setup_closeup(brief_icon *bi)
|
||||
Closeup_zoom = 0.5f;
|
||||
break;
|
||||
default:
|
||||
brief_get_closeup_ship_modelnum(Closeup_icon);
|
||||
Assert( Closeup_icon->ship_class != -1 );
|
||||
sip = &Ship_info[Closeup_icon->ship_class];
|
||||
|
||||
@@ -1284,12 +1267,17 @@ int brief_setup_closeup(brief_icon *bi)
|
||||
break;
|
||||
}
|
||||
|
||||
if ( Closeup_icon->modelnum == -1 ) {
|
||||
if ( Closeup_icon->modelnum < 0 ) {
|
||||
if ( sip == NULL ) {
|
||||
Closeup_icon->modelnum = model_load(pof_filename, 0, NULL);
|
||||
} else {
|
||||
Closeup_icon->modelnum = model_load(sip->pof_file, sip->n_subsystems, &sip->subsystems[0]);
|
||||
Closeup_icon->model_instance_num = model_create_instance(true, Closeup_icon->modelnum);
|
||||
model_set_up_techroom_instance(sip, Closeup_icon->model_instance_num);
|
||||
}
|
||||
}
|
||||
|
||||
if ( Closeup_icon->modelnum >= 0 ) {
|
||||
Closeup_icon->radius = model_get_radius(Closeup_icon->modelnum);
|
||||
}
|
||||
|
||||
|
||||
@@ -2414,12 +2414,10 @@ int create_wings()
|
||||
ss_wing_info *wb;
|
||||
ss_slot_info *ws;
|
||||
wing *wp;
|
||||
p_object *p_objp;
|
||||
|
||||
int shipnum, objnum, slot_index;
|
||||
int cleanup_ship_index[MAX_WING_SLOTS];
|
||||
int i,j,k;
|
||||
int found_pobj;
|
||||
|
||||
Assert( (Ss_wings != NULL) && (Wss_slots != NULL) );
|
||||
|
||||
@@ -2451,21 +2449,22 @@ int create_wings()
|
||||
objnum = OBJ_INDEX(Player_obj);
|
||||
shipnum = Objects[objnum].instance;
|
||||
} else {
|
||||
if ( wb->is_late) {
|
||||
found_pobj = 0;
|
||||
for ( p_objp = GET_FIRST(&Ship_arrival_list); p_objp != END_OF_LIST(&Ship_arrival_list); p_objp = GET_NEXT(p_objp) ) {
|
||||
if ( p_objp->wingnum == WING_INDEX(wp) ) {
|
||||
if ( ws->sa_index == POBJ_INDEX(p_objp) ) {
|
||||
p_objp->ship_class = Wss_slots[slot_index].ship_class;
|
||||
wl_update_parse_object_weapons(p_objp, &Wss_slots[i*MAX_WING_SLOTS+j]);
|
||||
found_pobj = 1;
|
||||
break;
|
||||
}
|
||||
// We should always update the parse object information, even if the ship is present at start,
|
||||
// because the wing might have more than one wave or scripting functions might need accurate data
|
||||
bool found_pobj = false;
|
||||
for ( auto &p_obj: Parse_objects ) {
|
||||
if ( p_obj.wingnum == WING_INDEX(wp) ) {
|
||||
if ( p_obj.pos_in_wing == j ) {
|
||||
p_obj.ship_class = Wss_slots[slot_index].ship_class;
|
||||
wl_update_parse_object_weapons(&p_obj, &Wss_slots[i*MAX_WING_SLOTS+j]);
|
||||
found_pobj = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
Assert(found_pobj);
|
||||
}
|
||||
else {
|
||||
Assert(found_pobj);
|
||||
|
||||
if (!wb->is_late) {
|
||||
// AL 10/04/97
|
||||
// Change the ship type of the ship if different than current.
|
||||
// NOTE: This will reset the weapons for this ship. I think this is
|
||||
|
||||
+3
-2
@@ -22,6 +22,7 @@
|
||||
#include "model/model_flags.h"
|
||||
|
||||
class object;
|
||||
class ship_info;
|
||||
class model_render_params;
|
||||
|
||||
extern flag_def_list model_render_flags[];
|
||||
@@ -803,7 +804,7 @@ polymodel *model_get(int model_num);
|
||||
|
||||
polymodel_instance* model_get_instance(int model_instance_num);
|
||||
|
||||
// routine to copy susbsystems. Must be called when subsystems sets are the same -- see ship.cpp
|
||||
// routine to copy subsystems. Must be called when subsystems sets are the same -- see ship.cpp
|
||||
void model_copy_subsystems(int n_subsystems, model_subsystem *d_sp, model_subsystem *s_sp);
|
||||
|
||||
// If MR_FLAG_OUTLINE bit set this color will be used for outlines.
|
||||
@@ -968,7 +969,7 @@ extern void model_clear_instance(int model_num);
|
||||
extern void model_set_submodel_turn_info(submodel_instance *smi, float turn_rate, float turn_accel);
|
||||
|
||||
// Sets the submodel instance data in a submodel
|
||||
extern void model_set_instance_techroom(polymodel *pm, polymodel_instance *pmi, int submodel_num, float angle_1, float angle_2);
|
||||
extern void model_set_up_techroom_instance(ship_info *sip, int model_instance_num);
|
||||
|
||||
void model_update_instance(int model_instance_num, int submodel_num, flagset<Ship::Subsystem_Flags>& flags);
|
||||
void model_update_instance(polymodel *pm, polymodel_instance *pmi, int submodel_num, flagset<Ship::Subsystem_Flags>& flags);
|
||||
|
||||
+86
-21
@@ -462,6 +462,55 @@ void get_user_prop_value(char *buf, char *value)
|
||||
*p1 = c;
|
||||
}
|
||||
|
||||
// Stuff a floating point value pointed at by Mp.
|
||||
// Advances past float characters.
|
||||
int stuff_float_temp(float *f, bool optional)
|
||||
{
|
||||
char *str_start = Mp;
|
||||
char *str_end;
|
||||
|
||||
// since strtof ignores white space anyway, might as well make it explicit
|
||||
ignore_white_space();
|
||||
|
||||
auto result = strtof(Mp, &str_end);
|
||||
bool success = false, comma = false;
|
||||
int retval = 0;
|
||||
|
||||
// no float found?
|
||||
if (result == 0.0f && str_end == Mp)
|
||||
{
|
||||
if (!optional)
|
||||
error_display(1, "Expecting float, found [%.32s].\n", next_tokens());
|
||||
}
|
||||
else
|
||||
{
|
||||
*f = result;
|
||||
success = true;
|
||||
}
|
||||
|
||||
if (success)
|
||||
Mp = str_end;
|
||||
|
||||
if (*Mp == ',')
|
||||
{
|
||||
comma = true;
|
||||
Mp++;
|
||||
}
|
||||
|
||||
if (optional && !success)
|
||||
Mp = str_start;
|
||||
|
||||
if (success)
|
||||
retval = 2;
|
||||
else if (optional)
|
||||
retval = comma ? 1 : 0;
|
||||
else
|
||||
skip_token();
|
||||
|
||||
diag_printf("Stuffed float: %f\n", *f);
|
||||
return retval;
|
||||
}
|
||||
|
||||
// routine to parse out a vec3d from a user property field of an object
|
||||
bool get_user_vec3d_value(char *buf, vec3d *value, bool require_brackets)
|
||||
{
|
||||
@@ -494,11 +543,11 @@ bool get_user_vec3d_value(char *buf, vec3d *value, bool require_brackets)
|
||||
}
|
||||
|
||||
// get comma-separated floats
|
||||
if (stuff_float_optional(&f1) != 2)
|
||||
if (stuff_float_temp(&f1, true) != 2)
|
||||
break;
|
||||
if (stuff_float_optional(&f2) != 2)
|
||||
if (stuff_float_temp(&f2, true) != 2)
|
||||
break;
|
||||
if (stuff_float_optional(&f3) != 2)
|
||||
if (stuff_float_temp(&f3, true) != 2)
|
||||
break;
|
||||
|
||||
if (require_brackets)
|
||||
@@ -2722,6 +2771,9 @@ int model_load(const char *filename, int n_subsystems, model_subsystem *subsyst
|
||||
Assert(pm->submodel[i].num_live_debris < MAX_LIVE_DEBRIS);
|
||||
pm->submodel[i].live_debris[pm->submodel[i].num_live_debris++] = j;
|
||||
pm->submodel[j].is_live_debris = 1;
|
||||
|
||||
// make sure live debris doesn't have a parent
|
||||
pm->submodel[j].parent = -1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4448,28 +4500,41 @@ void model_set_submodel_turn_info(submodel_instance *smi, float turn_rate, float
|
||||
smi->turn_accel = turn_accel;
|
||||
}
|
||||
|
||||
// Sets the submodel instance data in a submodel (for all detail levels)
|
||||
// Techroom version uses two floats of setting rotation angles (for turrets)
|
||||
// instead of using larger but largely unused structures for storing the same data
|
||||
void model_set_instance_techroom(polymodel *pm, polymodel_instance *pmi, int sub_model_num, float angle_1, float angle_2)
|
||||
// Sets the submodel instance data when a tech room model instance is created.
|
||||
// This only needs to be done at creation, not every frame.
|
||||
void model_set_up_techroom_instance(ship_info *sip, int model_instance_num)
|
||||
{
|
||||
Assert( sub_model_num >= 0 );
|
||||
Assert( sub_model_num < pm->n_models );
|
||||
auto pmi = model_get_instance(model_instance_num);
|
||||
auto pm = model_get(pmi->model_num);
|
||||
flagset<Ship::Subsystem_Flags> empty;
|
||||
|
||||
if ( sub_model_num < 0 ) return;
|
||||
if ( sub_model_num >= pm->n_models ) return;
|
||||
bsp_info *sm = &pm->submodel[sub_model_num];
|
||||
auto smi = &pmi->submodel[sub_model_num];
|
||||
for (int i = 0; i < sip->n_subsystems; ++i)
|
||||
{
|
||||
model_subsystem *msp = &sip->subsystems[i];
|
||||
|
||||
// If submodel isn't yet blown off and has a -destroyed replacement model, we prevent
|
||||
// the replacement model from being drawn by marking it as having been blown off
|
||||
if ( sm->my_replacement > -1 && sm->my_replacement != sub_model_num) {
|
||||
pmi->submodel[sm->my_replacement].blown_off = true;
|
||||
for (int j = 0; j < msp->n_triggers; ++j)
|
||||
{
|
||||
if (msp->triggers[j].type == AnimationTriggerType::Initial)
|
||||
{
|
||||
// special case for turrets
|
||||
if (msp->type == SUBSYSTEM_TURRET)
|
||||
{
|
||||
if (msp->subobj_num >= 0)
|
||||
pmi->submodel[msp->subobj_num].angs.h = msp->triggers[j].angle.xyz.y;
|
||||
|
||||
if ((msp->subobj_num != msp->turret_gun_sobj) && (msp->turret_gun_sobj >= 0))
|
||||
pmi->submodel[msp->turret_gun_sobj].angs.p = msp->triggers[j].angle.xyz.x;
|
||||
}
|
||||
// we can't support non-turrets, as in modelanim, because we need a ship subsystem but we don't actually have a ship
|
||||
}
|
||||
}
|
||||
|
||||
if (msp->subobj_num >= 0)
|
||||
model_update_instance(pm, pmi, msp->subobj_num, empty);
|
||||
|
||||
if (msp->turret_gun_sobj >= 0)
|
||||
model_update_instance(pm, pmi, msp->turret_gun_sobj, empty);
|
||||
}
|
||||
|
||||
// Set the angles
|
||||
smi->angs.p = angle_1;
|
||||
smi->angs.h = angle_2;
|
||||
}
|
||||
|
||||
void model_update_instance(int model_instance_num, int submodel_num, flagset<Ship::Subsystem_Flags>& flags)
|
||||
|
||||
+11
-11
@@ -1896,18 +1896,18 @@ void model_render_set_glow_points(polymodel *pm, int objnum)
|
||||
bank->glow_timestamp=time;
|
||||
}
|
||||
|
||||
if ( ( gpo && gpo->off_time_override ) ? gpo->off_time : bank->off_time ) {
|
||||
if ( bank->is_on ) {
|
||||
if( ((gpo && gpo->on_time_override) ? gpo->on_time : bank->on_time) > ((time - ((gpo && gpo->disp_time_override) ? gpo->disp_time : bank->disp_time)) % (((gpo && gpo->on_time_override) ? gpo->on_time : bank->on_time) + ((gpo && gpo->off_time_override) ? gpo->off_time : bank->off_time))) ){
|
||||
int on_time = (gpo && gpo->on_time_override) ? gpo->on_time : bank->on_time;
|
||||
int off_time = (gpo && gpo->off_time_override) ? gpo->off_time : bank->off_time;
|
||||
int disp_time = (gpo && gpo->disp_time_override) ? gpo->disp_time : bank->disp_time;
|
||||
|
||||
|
||||
if (off_time) {
|
||||
bool glow_state = ((time - disp_time) % (on_time + off_time)) < on_time;
|
||||
|
||||
if ( glow_state != bank->is_on )
|
||||
bank->glow_timestamp = time;
|
||||
bank->is_on = 0;
|
||||
}
|
||||
} else {
|
||||
if( ((gpo && gpo->off_time_override)?gpo->off_time:bank->off_time) < ((time - ((gpo && gpo->disp_time_override)?gpo->disp_time:bank->disp_time)) % (((gpo && gpo->on_time_override)?gpo->on_time:bank->on_time) + ((gpo && gpo->off_time_override)?gpo->off_time:bank->off_time))) ){
|
||||
bank->glow_timestamp = time;
|
||||
bank->is_on = 1;
|
||||
}
|
||||
}
|
||||
|
||||
bank->is_on = glow_state;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -69,16 +69,14 @@ static bool check_for_docking_collision(object *objp1, object *objp2)
|
||||
}
|
||||
|
||||
|
||||
if (aip1->mode == AIM_DOCK) {
|
||||
if (dock_check_find_docked_object(&Objects[aip1->goal_objnum], objp2)){
|
||||
if (aip1->mode == AIM_DOCK && aip1->goal_objnum >= 0 && aip1->goal_objnum < MAX_OBJECTS) {
|
||||
if (dock_check_find_docked_object(&Objects[aip1->goal_objnum], objp2))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (aip2->mode == AIM_DOCK) {
|
||||
if (dock_check_find_docked_object(&Objects[aip2->goal_objnum], objp1)){
|
||||
if (aip2->mode == AIM_DOCK && aip2->goal_objnum >= 0 && aip2->goal_objnum < MAX_OBJECTS) {
|
||||
if (dock_check_find_docked_object(&Objects[aip2->goal_objnum], objp1))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
|
||||
@@ -268,30 +268,39 @@ int weapon_will_never_hit( object *obj_weapon, object *other, obj_pair * current
|
||||
// look for two time solutions to Xw = Xs, where Xw = Xw0 + Vwt*t Xs = Xs + Vs*(t+dt), where Vs*dt = radius of ship
|
||||
// Since direction of Vs is unknown, solve for (Vs*t) and find norm of both sides
|
||||
if ( !(wip->wi_flags[Weapon::Info_Flags::Turns]) ) {
|
||||
vec3d delta_x, laser_vel;
|
||||
vec3d delta_x, weapon_vel;
|
||||
float a,b,c, delta_x_dot_vl, delta_t;
|
||||
float root1, root2, root, earliest_time;
|
||||
|
||||
if (max_vel_weapon == max_vel_other) {
|
||||
vm_vec_sub( &delta_x, &obj_weapon->pos, &other->pos );
|
||||
weapon_vel = obj_weapon->phys_info.vel;
|
||||
float weapon_speed = vm_vec_mag(&weapon_vel);
|
||||
|
||||
if (weapon_speed == max_vel_other) {
|
||||
// this will give us NAN using the below formula, so check every frame
|
||||
current_pair->next_check_time = timestamp(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
vm_vec_sub( &delta_x, &obj_weapon->pos, &other->pos );
|
||||
laser_vel = obj_weapon->phys_info.vel;
|
||||
// vm_vec_copy_scale( &laser_vel, &weapon->orient.vec.fvec, max_vel_weapon );
|
||||
delta_t = (other->radius + 10.0f) / max_vel_other; // time to get from center to radius of other obj
|
||||
delta_x_dot_vl = vm_vec_dot( &delta_x, &laser_vel );
|
||||
delta_x_dot_vl = vm_vec_dot( &delta_x, &weapon_vel);
|
||||
|
||||
a = max_vel_weapon*max_vel_weapon - max_vel_other*max_vel_other;
|
||||
a = weapon_speed * weapon_speed - max_vel_other*max_vel_other;
|
||||
b = 2.0f * (delta_x_dot_vl - max_vel_other*max_vel_other*delta_t);
|
||||
c = vm_vec_mag_squared( &delta_x ) - max_vel_other*max_vel_other*delta_t*delta_t;
|
||||
|
||||
float discriminant = b*b - 4.0f*a*c;
|
||||
if ( discriminant < 0) {
|
||||
// never hit
|
||||
return 1;
|
||||
// neither entity passes the other
|
||||
if (c < 0) {
|
||||
// ship outpaces weapon
|
||||
current_pair->next_check_time = timestamp(0); // check next time
|
||||
return 0;
|
||||
} else {
|
||||
// weapon outpaces ship; will never hit
|
||||
return 1;
|
||||
}
|
||||
} else {
|
||||
root = fl_sqrt( discriminant );
|
||||
root1 = (-b + root) / (2.0f * a) * 1000.0f; // get time in ms
|
||||
@@ -299,7 +308,7 @@ int weapon_will_never_hit( object *obj_weapon, object *other, obj_pair * current
|
||||
}
|
||||
|
||||
// standard algorithm
|
||||
if (max_vel_weapon > max_vel_other) {
|
||||
if (weapon_speed > max_vel_other) {
|
||||
// find earliest positive time
|
||||
if ( root1 > root2 ) {
|
||||
float temp = root1;
|
||||
|
||||
+60
-11
@@ -4004,12 +4004,12 @@ void sprintf(SCP_string &dest, const char *format, ...)
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
bool end_string_at_first_hash_symbol(char *src)
|
||||
bool end_string_at_first_hash_symbol(char *src, bool ignore_doubled_hash)
|
||||
{
|
||||
char *p;
|
||||
Assert(src);
|
||||
|
||||
p = get_pointer_to_first_hash_symbol(src);
|
||||
p = get_pointer_to_first_hash_symbol(src, ignore_doubled_hash);
|
||||
if (p)
|
||||
{
|
||||
while ((p != src) && (*(p-1) == ' '))
|
||||
@@ -4023,9 +4023,9 @@ bool end_string_at_first_hash_symbol(char *src)
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
bool end_string_at_first_hash_symbol(SCP_string &src)
|
||||
bool end_string_at_first_hash_symbol(SCP_string &src, bool ignore_doubled_hash)
|
||||
{
|
||||
int index = get_index_of_first_hash_symbol(src);
|
||||
int index = get_index_of_first_hash_symbol(src, ignore_doubled_hash);
|
||||
if (index >= 0)
|
||||
{
|
||||
while (index > 0 && src[index-1] == ' ')
|
||||
@@ -4039,24 +4039,73 @@ bool end_string_at_first_hash_symbol(SCP_string &src)
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
char *get_pointer_to_first_hash_symbol(char *src)
|
||||
char *get_pointer_to_first_hash_symbol(char *src, bool ignore_doubled_hash)
|
||||
{
|
||||
Assert(src);
|
||||
return strchr(src, '#');
|
||||
|
||||
if (ignore_doubled_hash)
|
||||
{
|
||||
for (auto ch = src; *ch; ++ch)
|
||||
{
|
||||
if (*ch == '#')
|
||||
{
|
||||
if (*(ch + 1) == '#')
|
||||
++ch;
|
||||
else
|
||||
return ch;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
else
|
||||
return strchr(src, '#');
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
const char *get_pointer_to_first_hash_symbol(const char *src)
|
||||
const char *get_pointer_to_first_hash_symbol(const char *src, bool ignore_doubled_hash)
|
||||
{
|
||||
Assert(src);
|
||||
return strchr(src, '#');
|
||||
|
||||
if (ignore_doubled_hash)
|
||||
{
|
||||
for (auto ch = src; *ch; ++ch)
|
||||
{
|
||||
if (*ch == '#')
|
||||
{
|
||||
if (*(ch + 1) == '#')
|
||||
++ch;
|
||||
else
|
||||
return ch;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
else
|
||||
return strchr(src, '#');
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
int get_index_of_first_hash_symbol(SCP_string &src)
|
||||
int get_index_of_first_hash_symbol(SCP_string &src, bool ignore_doubled_hash)
|
||||
{
|
||||
size_t pos = src.find('#');
|
||||
return (pos == SCP_string::npos) ? -1 : (int)pos;
|
||||
if (ignore_doubled_hash)
|
||||
{
|
||||
for (auto ch = src.begin(); ch != src.end(); ++ch)
|
||||
{
|
||||
if (*ch == '#')
|
||||
{
|
||||
if ((ch + 1) != src.end() && *(ch + 1) == '#')
|
||||
++ch;
|
||||
else
|
||||
return (int)std::distance(src.begin(), ch);
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
size_t pos = src.find('#');
|
||||
return (pos == SCP_string::npos) ? -1 : (int)pos;
|
||||
}
|
||||
}
|
||||
|
||||
// Goober5000
|
||||
|
||||
@@ -67,11 +67,11 @@ extern int Token_found_flag;
|
||||
#define SEXP_ERROR_CHECK_MODE 2
|
||||
|
||||
// Goober5000 - this seems to be a pretty universal function
|
||||
extern bool end_string_at_first_hash_symbol(char *src);
|
||||
extern bool end_string_at_first_hash_symbol(SCP_string &src);
|
||||
extern char *get_pointer_to_first_hash_symbol(char *src);
|
||||
extern const char *get_pointer_to_first_hash_symbol(const char *src);
|
||||
extern int get_index_of_first_hash_symbol(SCP_string &src);
|
||||
extern bool end_string_at_first_hash_symbol(char *src, bool ignore_doubled_hash = false);
|
||||
extern bool end_string_at_first_hash_symbol(SCP_string &src, bool ignore_doubled_hash = false);
|
||||
extern char *get_pointer_to_first_hash_symbol(char *src, bool ignore_doubled_hash = false);
|
||||
extern const char *get_pointer_to_first_hash_symbol(const char *src, bool ignore_doubled_hash = false);
|
||||
extern int get_index_of_first_hash_symbol(SCP_string &src, bool ignore_doubled_hash = false);
|
||||
|
||||
// white space
|
||||
extern int is_white_space(char ch);
|
||||
|
||||
+16
-3
@@ -966,6 +966,7 @@ void pilotfile::csg_write_redalert()
|
||||
void pilotfile::csg_read_hud()
|
||||
{
|
||||
int idx;
|
||||
int strikes = 0;
|
||||
|
||||
// flags
|
||||
HUD_config.show_flags = cfread_int(cfp);
|
||||
@@ -980,16 +981,28 @@ void pilotfile::csg_read_hud()
|
||||
HUD_config.rp_flags = cfread_int(cfp);
|
||||
HUD_config.rp_dist = cfread_int(cfp);
|
||||
if (HUD_config.rp_dist < 0 || HUD_config.rp_dist >= RR_MAX_RANGES) {
|
||||
Warning(LOCATION, "Campaign file has invalid radar range %d, setting to default.\n", HUD_config.rp_dist);
|
||||
ReleaseWarning(LOCATION, "Campaign file has invalid radar range %d, setting to default.\n", HUD_config.rp_dist);
|
||||
HUD_config.rp_dist = RR_INFINITY;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
// basic colors
|
||||
HUD_config.main_color = cfread_int(cfp);
|
||||
HUD_color_alpha = cfread_int(cfp);
|
||||
if (HUD_config.main_color < 0 || HUD_config.main_color >= HUD_COLOR_SIZE) {
|
||||
ReleaseWarning(LOCATION, "Campaign file has invalid main color selection %i, setting to default.\n", HUD_config.main_color);
|
||||
HUD_config.main_color = HUD_COLOR_GREEN;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
if (HUD_color_alpha < HUD_COLOR_ALPHA_USER_MIN) {
|
||||
HUD_color_alpha = cfread_int(cfp);
|
||||
if (HUD_color_alpha < HUD_COLOR_ALPHA_USER_MIN || HUD_color_alpha > HUD_COLOR_ALPHA_USER_MAX) {
|
||||
ReleaseWarning(LOCATION, "Campaign file has invalid alpha color %i, setting to default.\n", HUD_color_alpha);
|
||||
HUD_color_alpha = HUD_COLOR_ALPHA_DEFAULT;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
if (strikes == 3) {
|
||||
ReleaseWarning(LOCATION, "Campaign file has too many hud config errors, and is likely corrupted. Please verify and save your settings in the hud config menu.");
|
||||
}
|
||||
|
||||
hud_config_record_color(HUD_config.main_color);
|
||||
|
||||
+17
-3
@@ -172,6 +172,7 @@ void pilotfile::plr_write_info()
|
||||
|
||||
void pilotfile::plr_read_hud()
|
||||
{
|
||||
int strikes = 0;
|
||||
// flags
|
||||
HUD_config.show_flags = handler->readInt("show_flags");
|
||||
HUD_config.show_flags2 = handler->readInt("show_flags2");
|
||||
@@ -185,15 +186,28 @@ void pilotfile::plr_read_hud()
|
||||
HUD_config.rp_flags = handler->readInt("rp_flags");
|
||||
HUD_config.rp_dist = handler->readInt("rp_dist");
|
||||
if (HUD_config.rp_dist < 0 || HUD_config.rp_dist >= RR_MAX_RANGES) {
|
||||
Warning(LOCATION, "Player file has invalid radar range %d, setting to default.\n", HUD_config.rp_dist);
|
||||
ReleaseWarning(LOCATION, "Player file has invalid radar range %d, setting to default.\n", HUD_config.rp_dist);
|
||||
HUD_config.rp_dist = RR_INFINITY;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
// basic colors
|
||||
HUD_config.main_color = handler->readInt("main_color");
|
||||
HUD_color_alpha = handler->readInt("color_alpha");
|
||||
if (HUD_config.main_color < 0 || HUD_config.main_color >= HUD_COLOR_SIZE) {
|
||||
ReleaseWarning(LOCATION, "Player file has invalid main color selection %i, setting to default.\n", HUD_config.main_color);
|
||||
HUD_config.main_color = HUD_COLOR_GREEN;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
if (HUD_color_alpha < HUD_COLOR_ALPHA_USER_MIN) {
|
||||
HUD_color_alpha = handler->readInt("color_alpha");
|
||||
if (HUD_color_alpha < HUD_COLOR_ALPHA_USER_MIN || HUD_color_alpha > HUD_COLOR_ALPHA_USER_MAX) {
|
||||
ReleaseWarning(LOCATION, "Player file has invalid alpha color %i, setting to default.\n", HUD_color_alpha);
|
||||
HUD_color_alpha = HUD_COLOR_ALPHA_DEFAULT;
|
||||
strikes++;
|
||||
}
|
||||
|
||||
if (strikes == 3) {
|
||||
ReleaseWarning(LOCATION, "Player file has too many hud config errors, and is likely corrupted. Please verify and save your settings in the hud config menu.");
|
||||
}
|
||||
|
||||
hud_config_set_color(HUD_config.main_color);
|
||||
|
||||
@@ -899,9 +899,16 @@ ADE_FUNC(drawTargetingBrackets, l_Graphics, "object Object, [boolean draw=true,
|
||||
}
|
||||
break;
|
||||
case OBJ_WEAPON:
|
||||
Assert(Weapon_info[Weapons[targetp->instance].weapon_info_index].subtype == WP_MISSILE);
|
||||
modelnum = Weapon_info[Weapons[targetp->instance].weapon_info_index].model_num;
|
||||
bound_rc = model_find_2d_bound_min( modelnum, &targetp->orient, &targetp->pos,&x1,&y1,&x2,&y2 );
|
||||
if (modelnum != -1)
|
||||
bound_rc = model_find_2d_bound_min(modelnum, &targetp->orient, &targetp->pos, &x1, &y1, &x2, &y2);
|
||||
else {
|
||||
vertex vtx;
|
||||
g3_rotate_vertex(&vtx, &targetp->pos);
|
||||
g3_project_vertex(&vtx);
|
||||
x1 = x2 = (int)vtx.screen.xyw.x;
|
||||
y1 = y2 = (int)vtx.screen.xyw.y;
|
||||
}
|
||||
break;
|
||||
case OBJ_ASTEROID:
|
||||
pof = Asteroids[targetp->instance].asteroid_subtype;
|
||||
|
||||
@@ -216,7 +216,7 @@ ADE_VIRTVAR(WeaponClass, l_WeaponBank, "weaponclass", "Class of weapon mounted i
|
||||
if(ADE_SETTING_VAR && weaponclass > -1) {
|
||||
bh->sw->primary_bank_weapons[bh->bank] = weaponclass;
|
||||
if (Weapon_info[weaponclass].wi_flags[Weapon::Info_Flags::Ballistic]) {
|
||||
bh->sw->primary_bank_ammo[bh->bank] = (int)std::lround(bh->sw->primary_bank_capacity[bh->bank] / Weapon_info[weaponclass].cargo_size);
|
||||
bh->sw->primary_bank_start_ammo[bh->bank] = (int)std::lround(bh->sw->primary_bank_capacity[bh->bank] / Weapon_info[weaponclass].cargo_size);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -224,7 +224,7 @@ ADE_VIRTVAR(WeaponClass, l_WeaponBank, "weaponclass", "Class of weapon mounted i
|
||||
case SWH_SECONDARY:
|
||||
if(ADE_SETTING_VAR && weaponclass > -1) {
|
||||
bh->sw->secondary_bank_weapons[bh->bank] = weaponclass;
|
||||
bh->sw->secondary_bank_ammo[bh->bank] = (int)std::lround(bh->sw->secondary_bank_capacity[bh->bank] / Weapon_info[weaponclass].cargo_size);
|
||||
bh->sw->secondary_bank_start_ammo[bh->bank] = (int)std::lround(bh->sw->secondary_bank_capacity[bh->bank] / Weapon_info[weaponclass].cargo_size);
|
||||
}
|
||||
|
||||
return ade_set_args(L, "o", l_Weaponclass.Set(bh->sw->secondary_bank_weapons[bh->bank]));
|
||||
|
||||
@@ -10657,10 +10657,12 @@ void change_ship_type(int n, int ship_type, int by_sexp)
|
||||
if ( by_sexp ) {
|
||||
if (sip_orig->num_primary_banks > sip->num_primary_banks) {
|
||||
sp->weapons.current_primary_bank = 0;
|
||||
sp->weapons.previous_primary_bank = 0;
|
||||
}
|
||||
|
||||
if (sip_orig->num_secondary_banks > sip->num_secondary_banks) {
|
||||
sp->weapons.current_secondary_bank = 0;
|
||||
sp->weapons.previous_secondary_bank = 0;
|
||||
}
|
||||
|
||||
// While we're at it, let's copy over the ETS settings too
|
||||
|
||||
@@ -285,7 +285,7 @@ void shipfx_blow_off_subsystem(object *ship_objp, ship *ship_p, ship_subsys *sub
|
||||
shipfx_blow_up_model(ship_objp, psub->subobj_num, 50, &subobj_pos );
|
||||
|
||||
// create live debris objects, if any
|
||||
// TODO: some MULITPLAYER implcations here!!
|
||||
// TODO: some MULTIPLAYER implcations here!!
|
||||
shipfx_subsystem_maybe_create_live_debris(ship_objp, ship_p, subsys, exp_center, 1.0f);
|
||||
|
||||
int fireball_type = fireball_ship_explosion_type(&Ship_info[ship_p->ship_info_index]);
|
||||
|
||||
@@ -918,6 +918,32 @@ void stars_post_level_init()
|
||||
// FRED doesn't do normal page_in stuff so we need to load up the bitmaps here instead
|
||||
if (Fred_running) {
|
||||
stars_load_all_bitmaps();
|
||||
|
||||
// see whether we are missing any suns or bitmaps
|
||||
for (i = 0; i < (int)Backgrounds.size(); ++i) {
|
||||
SCP_string failed_suns;
|
||||
for (auto &sun : Backgrounds[i].suns) {
|
||||
if (stars_find_sun(sun.filename) < 0) {
|
||||
failed_suns += sun.filename;
|
||||
failed_suns += "\n";
|
||||
}
|
||||
}
|
||||
|
||||
SCP_string failed_bitmaps;
|
||||
for (auto &bitmap : Backgrounds[i].bitmaps) {
|
||||
if (stars_find_bitmap(bitmap.filename) < 0) {
|
||||
failed_bitmaps += bitmap.filename;
|
||||
failed_bitmaps += "\n";
|
||||
}
|
||||
}
|
||||
|
||||
if (!failed_suns.empty()) {
|
||||
Warning(LOCATION, "In Background %d, failed to load the following suns:\n%s", (i + 1), failed_suns.c_str());
|
||||
}
|
||||
if (!failed_bitmaps.empty()) {
|
||||
Warning(LOCATION, "In Background %d, failed to load the following bitmaps:\n%s", (i + 1), failed_bitmaps.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
starfield_generate_bitmap_buffers();
|
||||
@@ -2279,7 +2305,9 @@ int stars_add_sun_entry(starfield_list_entry *sun_ptr)
|
||||
idx = stars_find_sun(sun_ptr->filename);
|
||||
|
||||
if (idx == -1) {
|
||||
Warning(LOCATION, "Trying to add a sun '%s' that does not exist in stars.tbl!", sun_ptr->filename);
|
||||
if (!Fred_running) {
|
||||
Warning(LOCATION, "Trying to add a sun '%s' that does not exist in stars.tbl!", sun_ptr->filename);
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -2373,7 +2401,9 @@ int stars_add_bitmap_entry(starfield_list_entry *sle)
|
||||
idx = stars_find_bitmap(sle->filename);
|
||||
|
||||
if (idx == -1) {
|
||||
Warning(LOCATION, "Trying to add a bitmap '%s' that does not exist in stars.tbl!", sle->filename);
|
||||
if (!Fred_running) {
|
||||
Warning(LOCATION, "Trying to add a bitmap '%s' that does not exist in stars.tbl!", sle->filename);
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -2676,7 +2706,7 @@ int stars_get_first_valid_background()
|
||||
if (stars_find_bitmap(background->bitmaps[j].filename) < 0)
|
||||
{
|
||||
mprintf(("Failed to load bitmap %s for background %d, falling back to background %d\n",
|
||||
background->suns[j].filename, i + 1, i + 2));
|
||||
background->bitmaps[j].filename, i + 1, i + 2));
|
||||
valid = false;
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -676,8 +676,8 @@ void shield_impact_explosion(vec3d *hitpos, object *objp, float radius, int idx)
|
||||
// Swifty - return number of max simultaneous locks
|
||||
int weapon_get_max_missile_seekers(weapon_info *wip);
|
||||
|
||||
// return if this weapon can lock on this ship, based on its type, class, species or iff
|
||||
bool weapon_can_lock_on_ship(weapon_info *wip, int ship_num);
|
||||
// return if this weapon can lock on this target, based on its type, class, species or iff
|
||||
bool weapon_target_satisfies_lock_restrictions(weapon_info *wip, object* target);
|
||||
|
||||
// return if this weapon has iff restrictions, and should ignore normal iff targeting restrictions
|
||||
bool weapon_has_iff_restrictions(weapon_info* wip);
|
||||
|
||||
+10
-12
@@ -4093,9 +4093,8 @@ void find_homing_object(object *weapon_objp, int num)
|
||||
continue;
|
||||
|
||||
homing_object_team = obj_team(objp);
|
||||
bool can_lock_on_ship = objp->type != OBJ_SHIP || weapon_can_lock_on_ship(wip, objp->instance);
|
||||
bool can_attack = weapon_has_iff_restrictions(wip) || iff_x_attacks_y(wp->team, homing_object_team);
|
||||
if (can_lock_on_ship && can_attack)
|
||||
if (weapon_target_satisfies_lock_restrictions(wip, objp) && can_attack)
|
||||
{
|
||||
if ( objp->type == OBJ_SHIP )
|
||||
{
|
||||
@@ -5353,13 +5352,9 @@ void weapon_set_tracking_info(int weapon_objnum, int parent_objnum, int target_o
|
||||
|
||||
if ( parent_objp == NULL || Ships[parent_objp->instance].ai_index >= 0 ) {
|
||||
int target_team = -1;
|
||||
int target_ship_num = -1;
|
||||
if ( target_objnum >= 0 ) {
|
||||
int obj_type = Objects[target_objnum].type;
|
||||
|
||||
if (obj_type == OBJ_SHIP)
|
||||
target_ship_num = Objects[target_objnum].instance;
|
||||
|
||||
if ( (obj_type == OBJ_SHIP) || (obj_type == OBJ_WEAPON) ) {
|
||||
target_team = obj_team(&Objects[target_objnum]);
|
||||
|
||||
@@ -5381,7 +5376,7 @@ void weapon_set_tracking_info(int weapon_objnum, int parent_objnum, int target_o
|
||||
targeting_same = 0;
|
||||
}
|
||||
|
||||
bool can_lock = weapon_has_iff_restrictions(wip) && target_ship_num >= 0 ? weapon_can_lock_on_ship(wip, target_ship_num) :
|
||||
bool can_lock = (weapon_has_iff_restrictions(wip) && target_objnum >= 0) ? weapon_target_satisfies_lock_restrictions(wip, &Objects[target_objnum]) :
|
||||
(!targeting_same || (MULTI_DOGFIGHT && (target_team == Iff_traitor)));
|
||||
|
||||
// Cyborg17 - exclude all invalid object numbers here since in multi, the lock slots can get out of sync.
|
||||
@@ -8691,16 +8686,19 @@ int weapon_get_max_missile_seekers(weapon_info *wip)
|
||||
}
|
||||
|
||||
// returns whether a homing weapon can home on a particular ship
|
||||
bool weapon_can_lock_on_ship(weapon_info* wip, int ship_num)
|
||||
bool weapon_target_satisfies_lock_restrictions(weapon_info* wip, object* target)
|
||||
{
|
||||
if (target->type != OBJ_SHIP)
|
||||
return true;
|
||||
|
||||
auto& restrictions = wip->ship_restrict;
|
||||
// if you didn't specify any restrictions, you can always lock
|
||||
if (restrictions.empty()) return true;
|
||||
|
||||
int type_num = Ship_info[Ships[ship_num].ship_info_index].class_type;
|
||||
int class_num = Ships[ship_num].ship_info_index;
|
||||
int species_num = Ship_info[Ships[ship_num].ship_info_index].species;
|
||||
int iff_num = Ships[ship_num].team;
|
||||
int type_num = Ship_info[Ships[target->instance].ship_info_index].class_type;
|
||||
int class_num = Ships[target->instance].ship_info_index;
|
||||
int species_num = Ship_info[Ships[target->instance].ship_info_index].species;
|
||||
int iff_num = Ships[target->instance].team;
|
||||
|
||||
// otherwise, you're good as long as it matches one of the allowances in the restriction list
|
||||
return std::any_of(restrictions.begin(), restrictions.end(),
|
||||
|
||||
@@ -1044,6 +1044,10 @@ void briefing_editor_dlg::OnMakeIcon()
|
||||
biconp->pos = pos;
|
||||
biconp->flags = 0;
|
||||
biconp->id = Cur_brief_id++;
|
||||
|
||||
biconp->modelnum = -1;
|
||||
biconp->model_instance_num = -1;
|
||||
|
||||
if (ship >= 0) {
|
||||
biconp->ship_class = Ships[ship].ship_info_index;
|
||||
ship_info* sip = &Ship_info[Ships[ship].ship_info_index];
|
||||
|
||||
+13
-11
@@ -1314,6 +1314,8 @@ void game_post_level_init()
|
||||
|
||||
freespace_mission_load_stuff();
|
||||
|
||||
mission_process_alt_types();
|
||||
|
||||
// m!m Make hv.Player available in "On Mission Start" hook
|
||||
if(Player_obj)
|
||||
Script_system.SetHookObject("Player", Player_obj);
|
||||
@@ -1614,6 +1616,11 @@ void game_init()
|
||||
outwnd_init();
|
||||
}
|
||||
|
||||
// Cyborg17 -- This section used to be in game_main(), but in a section before outwnd_init()
|
||||
if (Is_standalone){
|
||||
nprintf(("Network", "Standalone running\n"));
|
||||
}
|
||||
|
||||
// init os stuff next
|
||||
os_init( Osreg_class_name, Window_title.c_str(), Osreg_app_name );
|
||||
|
||||
@@ -4355,16 +4362,16 @@ int game_poll()
|
||||
{
|
||||
if (!Cmdline_no_unfocus_pause)
|
||||
{
|
||||
if (!os_foreground()) {
|
||||
// If we're in a single player game, pause it.
|
||||
// Cyborg17 - Multiplayer *must not* have its time affected by being in the background.
|
||||
// otherwise, ship interpolation will become inaccurate.
|
||||
if (!os_foreground() && !(Game_mode & GM_MULTIPLAYER)) {
|
||||
game_stop_time();
|
||||
os_sleep(1);
|
||||
game_start_time();
|
||||
if ((gameseq_get_state() == GS_STATE_GAME_PLAY) && (!popup_active()) && (!popupdead_is_active())) {
|
||||
game_process_pause_key();
|
||||
|
||||
// If we're in a single player game, pause it.
|
||||
if (!(Game_mode & GM_MULTIPLAYER)){
|
||||
if ((gameseq_get_state() == GS_STATE_GAME_PLAY) && (!popup_active()) && (!popupdead_is_active())) {
|
||||
game_process_pause_key();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -6463,11 +6470,6 @@ int game_main(int argc, char *argv[])
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
if (Is_standalone){
|
||||
nprintf(("Network", "Standalone running\n"));
|
||||
}
|
||||
|
||||
game_init();
|
||||
|
||||
// if networking is unavailable then standalone is useless, so just fail
|
||||
|
||||
@@ -0,0 +1,5 @@
|
||||
set(FSO_VERSION_MAJOR 21)
|
||||
set(FSO_VERSION_MINOR 0)
|
||||
set(FSO_VERSION_BUILD 0)
|
||||
set(FSO_VERSION_REVISION 0)
|
||||
set(FSO_VERSION_REVISION_STR )
|
||||
Reference in new issue
Block a user