mirror of
https://git.do.srb2.org/KartKrew/Kart-Public.git
synced 2025-01-15 22:21:26 +00:00
Merge remote-tracking branch 'origin/master' into map-by-name
This commit is contained in:
commit
51cb3c9008
106 changed files with 2648 additions and 1959 deletions
|
@ -3,7 +3,7 @@ jobs:
|
|||
build:
|
||||
working_directory: /root/SRB2
|
||||
docker:
|
||||
- image: debian:jessie
|
||||
- image: debian:stretch
|
||||
environment:
|
||||
CC: ccache gcc -m32
|
||||
PKG_CONFIG_LIBDIR: /usr/lib/i386-linux-gnu/pkgconfig
|
||||
|
@ -36,14 +36,20 @@ jobs:
|
|||
- v1-SRB2-APT
|
||||
- run:
|
||||
name: Install SDK
|
||||
command: apt-get -qq -y install git build-essential nasm libpng12-dev:i386 libsdl2-mixer-dev:i386 libgme-dev:i386 gettext ccache wget gcc-multilib upx
|
||||
command: apt-get -qq -y --no-install-recommends install git build-essential nasm libpng-dev:i386 libsdl2-mixer-dev:i386 libgme-dev:i386 gettext ccache wget gcc-multilib upx openssh-client
|
||||
- save_cache:
|
||||
key: v1-SRB2-APT
|
||||
paths:
|
||||
- /var/cache/apt/archives
|
||||
- checkout
|
||||
- run:
|
||||
name: Clean build
|
||||
name: Compile without network support and BLUA
|
||||
command: make -C src LINUX=1 ERRORMODE=1 -k NONET=1 NO_LUA=1
|
||||
- run:
|
||||
name: wipe build
|
||||
command: make -C src LINUX=1 cleandep
|
||||
- run:
|
||||
name: rebuild depend
|
||||
command: make -C src LINUX=1 clean
|
||||
- restore_cache:
|
||||
keys:
|
||||
|
|
44
.travis.yml
44
.travis.yml
|
@ -26,6 +26,7 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-4.4
|
||||
compiler: gcc-4.4
|
||||
env: GCC44=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-4.4 (Ubuntu/Linaro 4.4.7-8ubuntu1) 4.4.7
|
||||
- os: linux
|
||||
|
@ -39,6 +40,7 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-4.6
|
||||
compiler: gcc-4.6
|
||||
env: GCC46=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-4.6 (Ubuntu/Linaro 4.6.4-6ubuntu2) 4.6.4
|
||||
- os: linux
|
||||
|
@ -52,10 +54,12 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-4.7
|
||||
compiler: gcc-4.7
|
||||
env: GCC47=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-4.7
|
||||
- os: linux
|
||||
compiler: gcc
|
||||
env: GCC48=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc (Ubuntu 4.8.4-2ubuntu1~14.04) 4.8.4
|
||||
- os: linux
|
||||
|
@ -71,6 +75,7 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-4.8
|
||||
compiler: gcc-4.8
|
||||
env: GCC48=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-4.8 (Ubuntu 4.8.5-2ubuntu1~14.04.1) 4.8.5
|
||||
- os: linux
|
||||
|
@ -86,7 +91,7 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-7
|
||||
compiler: gcc-7
|
||||
env: WFLAGS="-Wno-tautological-compare -Wno-error=implicit-fallthrough -Wno-implicit-fallthrough"
|
||||
env: WFLAGS="-Wno-tautological-compare -Wno-error=implicit-fallthrough -Wno-implicit-fallthrough" GCC72=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-7 (Ubuntu 7.2.0-1ubuntu1~14.04) 7.2.0 20170802
|
||||
- os: linux
|
||||
|
@ -102,7 +107,7 @@ matrix:
|
|||
- p7zip-full
|
||||
- gcc-8
|
||||
compiler: gcc-8
|
||||
env: WFLAGS="-Wno-tautological-compare -Wno-error=implicit-fallthrough -Wno-implicit-fallthrough -Wno-error=format-overflow"
|
||||
env: WFLAGS="-Wno-tautological-compare -Wno-error=implicit-fallthrough -Wno-implicit-fallthrough -Wno-error=format-overflow" GCC81=1
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#gcc-8 (Ubuntu 7.2.0-1ubuntu1~14.04) 8.1.0
|
||||
- os: linux
|
||||
|
@ -249,17 +254,21 @@ matrix:
|
|||
# osx_image: xcode7.2
|
||||
# if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
# #Apple LLVM version 7.0.2 (clang-700.1.81)
|
||||
# - os: osx
|
||||
# osx_image: xcode7.3
|
||||
# #Apple LLVM version 7.3.0 (clang-703.0.31)
|
||||
# - os: osx
|
||||
# osx_image: xcode7.3
|
||||
# #Apple LLVM version 7.3.0 (clang-703.0.31)
|
||||
- os: osx
|
||||
osx_image: xcode7.3
|
||||
if: env(DPL_ENABLED) != "1" OR env(DPL_TERMINATE_TESTS) != "1" OR NOT branch =~ /^.*deployer.*$/
|
||||
#Apple LLVM version 7.3.0 (clang-703.0.31)
|
||||
#Default: macOS 10.13 and Xcode 9.4.1
|
||||
|
||||
|
||||
################################
|
||||
# Deployer Buildbots - OSX
|
||||
################################
|
||||
- os: osx
|
||||
osx_image: xcode7.3
|
||||
if: env(DPL_ENABLED) = "1" AND (env(_DPL_JOB_ENABLED) = "1" OR env(DPL_JOB_ENABLE_ALL) = "1")
|
||||
AND (branch =~ /^.*deployer.*$/ OR (tag IS present AND env(DPL_TAG_ENABLED) = "1"))
|
||||
AND env(DPL_TERMINATE_MAIN) != "1"
|
||||
|
@ -559,6 +568,16 @@ addons:
|
|||
- libgme-dev
|
||||
- zlib1g-dev
|
||||
- p7zip-full
|
||||
homebrew:
|
||||
taps:
|
||||
- mazmazz/srb2
|
||||
packages:
|
||||
- sdl2_mixer
|
||||
- game-music-emu
|
||||
- p7zip
|
||||
- cmake
|
||||
update: true
|
||||
|
||||
|
||||
|
||||
before_install:
|
||||
|
@ -591,18 +610,10 @@ install:
|
|||
# * `sdl2_mixer` requires options from the formula tap https://github.com/mazmazz/homebrew-srb2
|
||||
# * `brew postinstall` runs post-install scripts after building a bottle
|
||||
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then
|
||||
brew update;
|
||||
brew tap mazmazz/srb2;
|
||||
fi;
|
||||
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then
|
||||
if [[ "$__DPL_ACTIVE" != "1" ]]; then
|
||||
brew install sdl2 sdl2_mixer game-music-emu p7zip;
|
||||
brew install cmake||true;
|
||||
else
|
||||
brew install --build-bottle sdl2 game-music-emu p7zip;
|
||||
if [[ "$__DPL_ACTIVE" == "1" ]]; then
|
||||
brew install --build-bottle sdl2 game-music-emu;
|
||||
brew install --build-bottle mazmazz/srb2/sdl2_mixer --with-flac --with-mpg123;
|
||||
brew postinstall sdl2 game-music-emu p7zip mazmazz/srb2/sdl2_mixer;
|
||||
brew install cmake||true;
|
||||
brew postinstall sdl2 game-music-emu mazmazz/srb2/sdl2_mixer;
|
||||
fi;
|
||||
fi
|
||||
- mkdir -p $HOME/srb2_cache
|
||||
|
@ -667,7 +678,6 @@ before_script:
|
|||
-DCPACK_PACKAGE_VENDOR="${PROGRAM_VENDOR}"
|
||||
-DSRB2_SDL2_EXE_NAME="${PROGRAM_FILENAME}"
|
||||
|
||||
|
||||
script:
|
||||
# Build our Makefile from Cmake!
|
||||
- if [[ "$__DPL_ACTIVE" == "1" ]]; then
|
||||
|
|
|
@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.0)
|
|||
# DO NOT CHANGE THIS SRB2 STRING! Some variable names depend on this string.
|
||||
# Version change is fine.
|
||||
project(SRB2
|
||||
VERSION 1.0.2
|
||||
VERSION 1.0.4
|
||||
LANGUAGES C)
|
||||
|
||||
if(${PROJECT_SOURCE_DIR} MATCHES ${PROJECT_BINARY_DIR})
|
||||
|
@ -56,13 +56,19 @@ macro(copy_files_to_build_dir target dlllist_var)
|
|||
endif()
|
||||
endmacro()
|
||||
|
||||
# 64-bit check
|
||||
if(${CMAKE_SIZEOF_VOID_P} EQUAL 8)
|
||||
# bitness check
|
||||
set(SRB2_SYSTEM_BITS 0)
|
||||
if(CMAKE_SIZEOF_VOID_P EQUAL 8)
|
||||
message(STATUS "Target is 64-bit")
|
||||
set(SRB2_SYSTEM_BITS 64)
|
||||
else()
|
||||
endif()
|
||||
if(CMAKE_SIZEOF_VOID_P EQUAL 4)
|
||||
message(STATUS "Target is 32-bit")
|
||||
set(SRB2_SYSTEM_BITS 32)
|
||||
endif()
|
||||
if(${SRB2_SYSTEM_BITS} EQUAL 0)
|
||||
message(STATUS "Target bitness is unknown")
|
||||
endif()
|
||||
|
||||
# OS macros
|
||||
if (UNIX)
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
version: 1.0.2.{branch}-{build}
|
||||
version: 1.0.4.{branch}-{build}
|
||||
os: MinGW
|
||||
|
||||
environment:
|
||||
|
@ -29,7 +29,7 @@ environment:
|
|||
##############################
|
||||
DPL_ENABLED: 0
|
||||
DPL_TAG_ENABLED: 0
|
||||
DPL_INSTALLER_NAME: srb2kart-v102
|
||||
DPL_INSTALLER_NAME: srb2kart-v104
|
||||
# Asset handling is barebones vs. Travis Deployer. We operate on 7z only.
|
||||
# Include the README files and the OpenGL batch in the main and patch archives.
|
||||
# The x86/x64 archives contain the DLL binaries.
|
||||
|
|
Binary file not shown.
Binary file not shown.
|
@ -4,7 +4,7 @@ project(libgme)
|
|||
include (CheckCXXCompilerFlag)
|
||||
|
||||
# When version is changed, also change the one in gme/gme.h to match
|
||||
set(GME_VERSION 0.6.0 CACHE INTERNAL "libgme Version")
|
||||
set(GME_VERSION 0.6.2 CACHE INTERNAL "libgme Version")
|
||||
|
||||
# 2.6+ always assumes FATAL_ERROR, but 2.4 and below don't.
|
||||
# Of course, 2.4 might work, in which case you're welcome to drop
|
||||
|
@ -57,6 +57,8 @@ if (USE_GME_NSFE AND NOT USE_GME_NSF)
|
|||
SET(USE_GME_NSF 1 CACHE BOOL "Enable NES NSF music emulation" FORCE)
|
||||
endif()
|
||||
|
||||
option(BUILD_SHARED_LIBS "Build shared library (set to OFF for static library)" ON)
|
||||
|
||||
# Check for GCC "visibility" support.
|
||||
if (CMAKE_COMPILER_IS_GNUCXX)
|
||||
check_cxx_compiler_flag (-fvisibility=hidden __LIBGME_TEST_VISIBILITY)
|
||||
|
@ -79,10 +81,10 @@ if (CMAKE_COMPILER_IS_GNUCXX)
|
|||
endif()
|
||||
endif()
|
||||
endif() # test visibility
|
||||
endif (CMAKE_COMPILER_IS_GNUCXX)
|
||||
|
||||
# Cache this result
|
||||
set( LIBGME_HAVE_GCC_VISIBILITY ${ENABLE_VISIBILITY} CACHE BOOL "GCC support for hidden visibility")
|
||||
# Cache this result
|
||||
set( LIBGME_HAVE_GCC_VISIBILITY ${ENABLE_VISIBILITY} CACHE BOOL "GCC support for hidden visibility")
|
||||
endif (CMAKE_COMPILER_IS_GNUCXX)
|
||||
|
||||
# Shared library defined here
|
||||
add_subdirectory(gme)
|
||||
|
|
|
@ -1,262 +1,5 @@
|
|||
Game_Music_Emu Change Log
|
||||
-------------------------
|
||||
|
||||
Game_Music_Emu 0.6.0
|
||||
--------------------
|
||||
|
||||
- Note: A 0.5.6 release was referenced but never tagged or packaged.
|
||||
|
||||
- SPC improvements:
|
||||
- Switched to newer snes_spc 0.9.0 for SPC emulation. Uses fast DSP.
|
||||
- Fixed Spc_Emu::gain().
|
||||
- Fixed support for files <0x10200 bytes.
|
||||
|
||||
- Other bugfixes:
|
||||
- Fixed a couple of GBS bugs, one involving access of memory after
|
||||
realloc.
|
||||
- Blip_Buffer works on systems where 'double' is a single-precision
|
||||
floating-point type.
|
||||
- Fix uninitialized buffer size in dual_resampler.
|
||||
- Compilation warnings squashed out as of clang 3.3-pre and gcc 4.7.2.
|
||||
|
||||
- API changes/additions:
|
||||
- Removed documentation of C++ interface, as the C interface in gme.h is
|
||||
the only supported one.
|
||||
- Added gme_enable_accuracy() for enabling more accurate sound emulation
|
||||
options (currently affects SPC only).
|
||||
|
||||
- Build system improvements:
|
||||
- Add pkg_config support.
|
||||
- Fix build on case-insensitive systems.
|
||||
- Allow for install on Cygwin.
|
||||
- Fix install on multilib systems, such as many 64-bit distros (CMake must
|
||||
be able to figure out your system's libsuffix, if any).
|
||||
- C++ implementation symbols are not leaked into the resultant library
|
||||
file (requires symbol visibility support).
|
||||
|
||||
- Sample player improvements:
|
||||
- Can toggle fast/accurate emulation (with the 'A' key).
|
||||
|
||||
Game_Music_Emu 0.5.5
|
||||
--------------------
|
||||
- CMake build support has been added. You can build Game_Music_Emu as
|
||||
a shared library and install it so that you do not have to include your
|
||||
own copy if you know libgme will be present on your target system.
|
||||
Requires CMake 2.6 or higher.
|
||||
|
||||
|
||||
Game_Music_Emu 0.5.2
|
||||
--------------------
|
||||
- *TONS* of changes and improvements. You should re-read the new header
|
||||
files and documentation as the changes will allow you to simplify your
|
||||
code a lot (it might even be simpler to just rewrite it). Existing code
|
||||
should continue to work without changes in most cases (see Deprecated
|
||||
features in gme.txt).
|
||||
|
||||
- New file formats: AY, HES, KSS, SAP, NSFE
|
||||
|
||||
- All-new comprehensive C interface (also usable from C++). Simplifies
|
||||
many things, especially file loading, and brings everything together in
|
||||
one header file (gme.h).
|
||||
|
||||
- Information tags and track names and times can be accessed for all
|
||||
game music formats
|
||||
|
||||
- New features supported by all emulators: end of track fading,
|
||||
automatic silence detection, adjustable song tempo, seek to new time in
|
||||
track
|
||||
|
||||
- Updated mini player example to support track names and times, echo,
|
||||
tempo, and channel muting, and added visual waveform display
|
||||
|
||||
- Improved configuration to use blargg_config.h, which you can modify
|
||||
and keep when you update to a newer libary version. Includes flag for
|
||||
library to automatically handle gzipped files using zlib (so you don't
|
||||
need to use Gzip_File_Reader anymore).
|
||||
|
||||
- GBS: Fixed wave channel to not reset waveform when APU is powered off
|
||||
(affected Garfield). Also improved invalid bank selection (affected Game
|
||||
& Watch and others).
|
||||
|
||||
- VGM: Added support for alternate noise shifter register
|
||||
configurations, used by other systems like the BBC Micro.
|
||||
|
||||
- SPC: Removed IPL ROM dump from emulator, as none of the SPC files I
|
||||
scanned needed it, and an SPC file can include a copy if necessary. Also
|
||||
re-enabled supposed clamping in gaussian interpolation between the third
|
||||
and fourth lookups, though I don't know whether it matters
|
||||
|
||||
- Added Music_Emu::load_mem() to use music data already in memory
|
||||
(without copying it)
|
||||
|
||||
- Added Music_Emu::warning(), which reports minor problems when loading
|
||||
and playing a music file
|
||||
|
||||
- Added Music_Emu::set_gain() for uniform adjustment of gain. Can only
|
||||
be set during initialization, so not useful as a general volume control.
|
||||
|
||||
- Added custom operator new to ensure that no exceptions are thrown in
|
||||
the library (I'd use std::nothrow if it were part of pre-ISO (ARM) C++)
|
||||
|
||||
- Added BLIP_BUFFER_FAST flag to blargg_config.h to use a lower quality
|
||||
bandlimited synthesis in "classic" emulators, which might help
|
||||
performance on ancient processors (measure first!). Don't use this
|
||||
unless absolutely necessary, as quality suffers.
|
||||
|
||||
- Improved performance a bit for x86 platforms
|
||||
|
||||
- Text files now in DOS newline format so they will open in Notepad
|
||||
properly
|
||||
|
||||
- Removed requirement that file header structures not have any padding
|
||||
added to the end
|
||||
|
||||
- Fixed common bug in all CPU emulators where negative program counter
|
||||
could crash emulator (occurred during a negative branch from the
|
||||
beginning of memory). Also fixed related bug in Z80 emulator for
|
||||
IX/IY+displacement mode.
|
||||
|
||||
- Eliminated all warnings when compiling on gcc 4.0. The following
|
||||
generates no diagnostics:
|
||||
|
||||
gcc -S gme/*.cpp -o /dev/null -ansi -fno-gnu-keywords
|
||||
-fno-nonansi-builtins -pedantic -W -Wabi -Wall -Wcast-align
|
||||
-Wcast-qual -Wchar-subscripts -Wdisabled-optimization -Werror
|
||||
-Winline -Wlong-long -Wmultichar -Winvalid-offsetof
|
||||
-Wnon-virtual-dtor -Woverloaded-virtual -Wparentheses
|
||||
-Wpointer-arith -Wredundant-decls -Wreorder -Wsign-compare
|
||||
-Wsign-promo -Wunknown-pragmas -Wwrite-strings
|
||||
|
||||
|
||||
Game_Music_Emu 0.3.0
|
||||
--------------------
|
||||
- Added more demos, including music player using the SDL multimedia
|
||||
library for sound, and improved documentation
|
||||
|
||||
- All: Improved interface to emulators to allow simpler setup and
|
||||
loading. Instead of various init() functions, all now support
|
||||
set_sample_rate( long rate ) and load( const char* file_path ).
|
||||
|
||||
- All: Removed error return from start_track() and play(), and added
|
||||
error_count() to get the total number of emulation errors since the
|
||||
track was last started. See demos for examples of new usage.
|
||||
|
||||
- All: Fixed mute_voices() muting to be preserved after loading files
|
||||
and starting tracks, instead of being cleared as it was whenever a track
|
||||
was started
|
||||
|
||||
- VGM: Rewrote Vgm_Emu to support Sega Genesis/Mega Drive FM sound at
|
||||
any sample rate with optional FM oversampling, support for alternate
|
||||
YM2612 sound cores, and support for optional YM2413
|
||||
|
||||
- VGM: Added tempo control, useful for slowing 60Hz NTSC Sega Genesis
|
||||
music to 50Hz PAL
|
||||
|
||||
- VGM: Removed Vgm_Emu::track_data(), since I realized that this
|
||||
information is already present in the VGM header (oops!)
|
||||
|
||||
- GYM: Changed Gym_Emu::track_length() operation (see Gym_Emu.h)
|
||||
|
||||
- NSF: Added support for Sunsoft FME-7 sound chip used by Gimmick
|
||||
soundtrack
|
||||
|
||||
- NSF: Fixed Namco 106 problems with Final Lap and others
|
||||
|
||||
- Moved library sources to gme/ directory to reduce clutter, and merged
|
||||
boost/ functionality into blargg_common.h
|
||||
|
||||
- Added Gzip_File_Reader for transparently using gzipped files
|
||||
|
||||
|
||||
Game_Music_Emu 0.2.4
|
||||
--------------------
|
||||
- Created a discussion forum for problems and feedback:
|
||||
http://groups-beta.google.com/group/blargg-sound-libs
|
||||
|
||||
- Changed error return value of Blip_Buffer::sample_rate() (also for
|
||||
Stereo_Buffer, Effects_Buffer, etc.) to blargg_err_t (defined in
|
||||
blargg_common.h), to make error reporting consistent with other
|
||||
functions. This means the "no error" return value is the opposite of
|
||||
what it was before, which will break current code which checks the error
|
||||
return value:
|
||||
|
||||
// current code (broken)
|
||||
if ( !buf.sample_rate( samples_per_sec ) )
|
||||
out_of_memory();
|
||||
|
||||
// quick-and-dirty fix (just remove the ! operation)
|
||||
if ( buf.sample_rate( samples_per_sec ) )
|
||||
out_of_memory();
|
||||
|
||||
// proper fix
|
||||
blargg_err_t error = buf.sample_rate( samples_per_sec );
|
||||
if ( error )
|
||||
report_error( error );
|
||||
|
||||
- Implemented workaround for MSVC++ 6 compiler limitations, allowing it
|
||||
to work on that compiler again
|
||||
|
||||
- Added sample clamping to avoid wrap-around at high volumes, allowing
|
||||
higher volume with little distortion
|
||||
|
||||
- Added to-do list and design notes
|
||||
|
||||
- Added Music_Emu::skip( long sample_count ) to skip ahead in current
|
||||
track
|
||||
|
||||
- Added Gym_Emu::track_length() and Vgm_Emu::track_length() for
|
||||
determining the length of non-looped GYM and VGM files
|
||||
|
||||
- Partially implemented DMC non-linearity when its value is directly set
|
||||
using $4011, which reduces previously over-emphasized "popping" of
|
||||
percussion on some games (TMNT II in particular)
|
||||
|
||||
- Fixed Fir_Resampler, used for SPC and GYM playback (was incorrectly
|
||||
using abs() instead of fabs()...argh)
|
||||
|
||||
- Fixed SPC emulation bugs: eliminated clicks in Plok! soundtrack and
|
||||
now stops sample slightly earlier than the end, as the SNES does. Fixed
|
||||
a totally broken CPU addressing mode.
|
||||
|
||||
- Fixed Konami VRC6 saw wave (was very broken before). Now VRC6 music
|
||||
sounds decent
|
||||
|
||||
- Fixed a minor GBS emulation bug
|
||||
|
||||
- Fixed GYM loop point bug when track was restarted before loop point
|
||||
had been reached
|
||||
|
||||
- Made default GBS frequency equalization less muffled
|
||||
|
||||
- Added pseudo-surround effect removal for SPC files
|
||||
|
||||
- Added Music_Emu::voice_names() which returns names for each voice.
|
||||
|
||||
- Added BLARGG_SOURCE_BEGIN which allows custom compiler options to be
|
||||
easily set for library sources
|
||||
|
||||
- Changed assignment of expansion sound chips in Nsf_Emu to be spread
|
||||
more evenly when using Effects_Buffer
|
||||
|
||||
- Changed 'size_t' values in Blip_Buffer interface to 'long'
|
||||
|
||||
- Changed demo to generate a WAVE sound file rather than an AIFF file
|
||||
|
||||
|
||||
Game_Music_Emu 0.2.0
|
||||
--------------------
|
||||
- Redid framework and rewrote/cleaned up emulators
|
||||
|
||||
- Changed licensing to GNU Lesser General Public License (LGPL)
|
||||
|
||||
- Added Sega Genesis GYM and Super Nintendo SPC emulators
|
||||
|
||||
- Added Namco-106 and Konami VRC6 sound chip support to NSF emulator
|
||||
|
||||
- Eliminated use of static mutable data in emulators, allowing
|
||||
multi-instance safety
|
||||
|
||||
|
||||
Game_Music_Emu 0.1.0
|
||||
--------------------
|
||||
- First release
|
||||
Please see the git version history (e.g. git shortlog tags/0.6.0..tags/0.6.1)
|
||||
for the accurate change log.
|
||||
|
|
|
@ -1,7 +1,5 @@
|
|||
/* C example that opens a game music file and records 10 seconds to "out.wav" */
|
||||
|
||||
static char filename [] = "test.nsf"; /* opens this file (can be any music type) */
|
||||
|
||||
#include "gme/gme.h"
|
||||
|
||||
#include "Wave_Writer.h" /* wave_ functions for writing sound file */
|
||||
|
@ -10,10 +8,15 @@ static char filename [] = "test.nsf"; /* opens this file (can be any music type)
|
|||
|
||||
void handle_error( const char* str );
|
||||
|
||||
int main()
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
const char *filename = "test.nsf"; /* Default file to open */
|
||||
if ( argc >= 2 )
|
||||
filename = argv[1];
|
||||
|
||||
long sample_rate = 44100; /* number of samples per second */
|
||||
int track = 0; /* index of track to play (0 = first) */
|
||||
/* index of track to play (0 = first) */
|
||||
int track = argc >= 3 ? atoi(argv[2]) : 0;
|
||||
|
||||
/* Open music file in new emulator */
|
||||
Music_Emu* emu;
|
||||
|
|
|
@ -1,7 +1,5 @@
|
|||
// C++ example that opens a game music file and records 10 seconds to "out.wav"
|
||||
|
||||
static char filename [] = "test.nsf"; /* opens this file (can be any music type) */
|
||||
|
||||
#include "gme/Music_Emu.h"
|
||||
|
||||
#include "Wave_Writer.h"
|
||||
|
@ -10,10 +8,15 @@ static char filename [] = "test.nsf"; /* opens this file (can be any music type)
|
|||
|
||||
void handle_error( const char* str );
|
||||
|
||||
int main()
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
const char *filename = "test.nsf"; /* Default file to open */
|
||||
if ( argc >= 2 )
|
||||
filename = argv[1];
|
||||
|
||||
long sample_rate = 44100; // number of samples per second
|
||||
int track = 0; // index of track to play (0 = first)
|
||||
// index of track to play (0 = first)
|
||||
int track = argc >= 3 ? atoi(argv[2]) : 0;
|
||||
|
||||
// Determine file type
|
||||
gme_type_t file_type;
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
Game_Music_Emu 0.6.0
|
||||
Game_Music_Emu 0.6.2
|
||||
--------------------
|
||||
Author : Shay Green <gblargg@gmail.com>
|
||||
Website: http://www.slack.net/~ant/libs/
|
||||
Forum : http://groups.google.com/group/blargg-sound-libs
|
||||
Source : https://code.google.com/p/game-music-emu/
|
||||
License: GNU Lesser General Public License (LGPL)
|
||||
Author : Shay Green <gblargg@gmail.com>
|
||||
Maintainer : Michael Pyne <mpyne@purinchu.net>
|
||||
Website : https://bitbucket.org/mpyne/game-music-emu/
|
||||
Source : https://bitbucket.org/mpyne/game-music-emu/
|
||||
License : GNU Lesser General Public License (LGPL), see LICENSE.txt
|
||||
|
||||
Contents
|
||||
--------
|
||||
|
|
|
@ -143,7 +143,7 @@ add_definitions(-DBLARGG_BUILD_DLL)
|
|||
include_directories(${CMAKE_CURRENT_BINARY_DIR})
|
||||
|
||||
# Add library to be compiled.
|
||||
add_library(gme SHARED ${libgme_SRCS})
|
||||
add_library(gme ${libgme_SRCS})
|
||||
|
||||
# The version is the release. The "soversion" is the API version. As long
|
||||
# as only build fixes are performed (i.e. no backwards-incompatible changes
|
||||
|
@ -159,4 +159,4 @@ install(TARGETS gme LIBRARY DESTINATION lib${LIB_SUFFIX}
|
|||
ARCHIVE DESTINATION lib) # DLL platforms
|
||||
|
||||
install(FILES ${EXPORTED_HEADERS} DESTINATION include/gme)
|
||||
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/libgme.pc DESTINATION lib/pkgconfig)
|
||||
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/libgme.pc DESTINATION lib${LIB_SUFFIX}/pkgconfig)
|
||||
|
|
|
@ -22,8 +22,13 @@ Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */
|
|||
|
||||
const char Data_Reader::eof_error [] = "Unexpected end of file";
|
||||
|
||||
#define RETURN_VALIDITY_CHECK( cond ) \
|
||||
do { if ( unlikely( !(cond) ) ) return "Corrupt file"; } while(0)
|
||||
|
||||
blargg_err_t Data_Reader::read( void* p, long s )
|
||||
{
|
||||
RETURN_VALIDITY_CHECK( s > 0 );
|
||||
|
||||
long result = read_avail( p, s );
|
||||
if ( result != s )
|
||||
{
|
||||
|
@ -38,6 +43,8 @@ blargg_err_t Data_Reader::read( void* p, long s )
|
|||
|
||||
blargg_err_t Data_Reader::skip( long count )
|
||||
{
|
||||
RETURN_VALIDITY_CHECK( count >= 0 );
|
||||
|
||||
char buf [512];
|
||||
while ( count )
|
||||
{
|
||||
|
@ -54,7 +61,8 @@ long File_Reader::remain() const { return size() - tell(); }
|
|||
|
||||
blargg_err_t File_Reader::skip( long n )
|
||||
{
|
||||
assert( n >= 0 );
|
||||
RETURN_VALIDITY_CHECK( n >= 0 );
|
||||
|
||||
if ( !n )
|
||||
return 0;
|
||||
return seek( tell() + n );
|
||||
|
@ -67,13 +75,14 @@ Subset_Reader::Subset_Reader( Data_Reader* dr, long size )
|
|||
in = dr;
|
||||
remain_ = dr->remain();
|
||||
if ( remain_ > size )
|
||||
remain_ = size;
|
||||
remain_ = max( 0l, size );
|
||||
}
|
||||
|
||||
long Subset_Reader::remain() const { return remain_; }
|
||||
|
||||
long Subset_Reader::read_avail( void* p, long s )
|
||||
{
|
||||
s = max( 0l, s );
|
||||
if ( s > remain_ )
|
||||
s = remain_;
|
||||
remain_ -= s;
|
||||
|
@ -85,7 +94,7 @@ long Subset_Reader::read_avail( void* p, long s )
|
|||
Remaining_Reader::Remaining_Reader( void const* h, long size, Data_Reader* r )
|
||||
{
|
||||
header = (char const*) h;
|
||||
header_end = header + size;
|
||||
header_end = header + max( 0l, size );
|
||||
in = r;
|
||||
}
|
||||
|
||||
|
@ -93,6 +102,7 @@ long Remaining_Reader::remain() const { return header_end - header + in->remain(
|
|||
|
||||
long Remaining_Reader::read_first( void* out, long count )
|
||||
{
|
||||
count = max( 0l, count );
|
||||
long first = header_end - header;
|
||||
if ( first )
|
||||
{
|
||||
|
@ -107,8 +117,9 @@ long Remaining_Reader::read_first( void* out, long count )
|
|||
|
||||
long Remaining_Reader::read_avail( void* out, long count )
|
||||
{
|
||||
count = max( 0l, count );
|
||||
long first = read_first( out, count );
|
||||
long second = count - first;
|
||||
long second = max( 0l, count - first );
|
||||
if ( second )
|
||||
{
|
||||
second = in->read_avail( (char*) out + first, second );
|
||||
|
@ -120,8 +131,9 @@ long Remaining_Reader::read_avail( void* out, long count )
|
|||
|
||||
blargg_err_t Remaining_Reader::read( void* out, long count )
|
||||
{
|
||||
count = max( 0l, count );
|
||||
long first = read_first( out, count );
|
||||
long second = count - first;
|
||||
long second = max( 0l, count - first );
|
||||
if ( !second )
|
||||
return 0;
|
||||
return in->read( (char*) out + first, second );
|
||||
|
@ -131,7 +143,7 @@ blargg_err_t Remaining_Reader::read( void* out, long count )
|
|||
|
||||
Mem_File_Reader::Mem_File_Reader( const void* p, long s ) :
|
||||
begin( (const char*) p ),
|
||||
size_( s )
|
||||
size_( max( 0l, s ) )
|
||||
{
|
||||
pos = 0;
|
||||
}
|
||||
|
@ -141,6 +153,7 @@ long Mem_File_Reader::size() const { return size_; }
|
|||
long Mem_File_Reader::read_avail( void* p, long s )
|
||||
{
|
||||
long r = remain();
|
||||
s = max( 0l, s );
|
||||
if ( s > r )
|
||||
s = r;
|
||||
memcpy( p, begin + pos, s );
|
||||
|
@ -152,6 +165,7 @@ long Mem_File_Reader::tell() const { return pos; }
|
|||
|
||||
blargg_err_t Mem_File_Reader::seek( long n )
|
||||
{
|
||||
RETURN_VALIDITY_CHECK( n >= 0 );
|
||||
if ( n > size_ )
|
||||
return eof_error;
|
||||
pos = n;
|
||||
|
@ -164,7 +178,7 @@ Callback_Reader::Callback_Reader( callback_t c, long size, void* d ) :
|
|||
callback( c ),
|
||||
data( d )
|
||||
{
|
||||
remain_ = size;
|
||||
remain_ = max( 0l, size );
|
||||
}
|
||||
|
||||
long Callback_Reader::remain() const { return remain_; }
|
||||
|
@ -173,13 +187,14 @@ long Callback_Reader::read_avail( void* out, long count )
|
|||
{
|
||||
if ( count > remain_ )
|
||||
count = remain_;
|
||||
if ( Callback_Reader::read( out, count ) )
|
||||
if ( count < 0 || Callback_Reader::read( out, count ) )
|
||||
count = -1;
|
||||
return count;
|
||||
}
|
||||
|
||||
blargg_err_t Callback_Reader::read( void* out, long count )
|
||||
{
|
||||
RETURN_VALIDITY_CHECK( count >= 0 );
|
||||
if ( count > remain_ )
|
||||
return eof_error;
|
||||
return callback( data, out, count );
|
||||
|
@ -210,11 +225,12 @@ long Std_File_Reader::size() const
|
|||
|
||||
long Std_File_Reader::read_avail( void* p, long s )
|
||||
{
|
||||
return fread( p, 1, s, (FILE*) file_ );
|
||||
return fread( p, 1, max( 0l, s ), (FILE*) file_ );
|
||||
}
|
||||
|
||||
blargg_err_t Std_File_Reader::read( void* p, long s )
|
||||
{
|
||||
RETURN_VALIDITY_CHECK( s > 0 );
|
||||
if ( s == (long) fread( p, 1, s, (FILE*) file_ ) )
|
||||
return 0;
|
||||
if ( feof( (FILE*) file_ ) )
|
||||
|
|
|
@ -129,6 +129,8 @@ private:
|
|||
};
|
||||
|
||||
#ifdef HAVE_ZLIB_H
|
||||
#include <zlib.h>
|
||||
|
||||
// Gzip compressed file reader
|
||||
class Gzip_File_Reader : public File_Reader {
|
||||
public:
|
||||
|
@ -143,7 +145,7 @@ public:
|
|||
long tell() const;
|
||||
blargg_err_t seek( long );
|
||||
private:
|
||||
void* file_;
|
||||
gzFile file_;
|
||||
long size_;
|
||||
};
|
||||
#endif
|
||||
|
|
|
@ -178,6 +178,11 @@ blargg_long Music_Emu::msec_to_samples( blargg_long msec ) const
|
|||
return (sec * sample_rate() + msec * sample_rate() / 1000) * stereo;
|
||||
}
|
||||
|
||||
long Music_Emu::tell_samples() const
|
||||
{
|
||||
return out_time;
|
||||
}
|
||||
|
||||
long Music_Emu::tell() const
|
||||
{
|
||||
blargg_long rate = sample_rate() * stereo;
|
||||
|
@ -185,14 +190,18 @@ long Music_Emu::tell() const
|
|||
return sec * 1000 + (out_time - sec * rate) * 1000 / rate;
|
||||
}
|
||||
|
||||
blargg_err_t Music_Emu::seek( long msec )
|
||||
blargg_err_t Music_Emu::seek_samples( long time )
|
||||
{
|
||||
blargg_long time = msec_to_samples( msec );
|
||||
if ( time < out_time )
|
||||
RETURN_ERR( start_track( current_track_ ) );
|
||||
return skip( time - out_time );
|
||||
}
|
||||
|
||||
blargg_err_t Music_Emu::seek( long msec )
|
||||
{
|
||||
return seek_samples( msec_to_samples( msec ) );
|
||||
}
|
||||
|
||||
blargg_err_t Music_Emu::skip( long count )
|
||||
{
|
||||
require( current_track() >= 0 ); // start_track() must have been called already
|
||||
|
|
|
@ -41,9 +41,15 @@ public:
|
|||
// Number of milliseconds (1000 msec = 1 second) played since beginning of track
|
||||
long tell() const;
|
||||
|
||||
// Number of samples generated since beginning of track
|
||||
long tell_samples() const;
|
||||
|
||||
// Seek to new time in track. Seeking backwards or far forward can take a while.
|
||||
blargg_err_t seek( long msec );
|
||||
|
||||
// Equivalent to restarting track then skipping n samples
|
||||
blargg_err_t seek_samples( long n );
|
||||
|
||||
// Skip n samples
|
||||
blargg_err_t skip( long n );
|
||||
|
||||
|
|
|
@ -134,6 +134,9 @@ blargg_err_t Nsfe_Info::load( Data_Reader& in, Nsf_Emu* nsf_emu )
|
|||
RETURN_ERR( in.read( block_header, sizeof block_header ) );
|
||||
blargg_long size = get_le32( block_header [0] );
|
||||
blargg_long tag = get_le32( block_header [1] );
|
||||
|
||||
if ( size <= 0 )
|
||||
return "Corrupt file";
|
||||
|
||||
//debug_printf( "tag: %c%c%c%c\n", char(tag), char(tag>>8), char(tag>>16), char(tag>>24) );
|
||||
|
||||
|
|
|
@ -433,9 +433,7 @@ void Snes_Spc::cpu_write( int data, int addr, rel_time_t time )
|
|||
#endif
|
||||
|
||||
// Registers other than $F2 and $F4-$F7
|
||||
//if ( reg != 2 && reg != 4 && reg != 5 && reg != 6 && reg != 7 )
|
||||
// TODO: this is a bit on the fragile side
|
||||
if ( ((~0x2F00 << (bits_in_int - 16)) << reg) < 0 ) // 36%
|
||||
if ( reg != 2 && (reg < 4 || reg > 7) ) // 36%
|
||||
cpu_write_smp_reg( data, time, reg );
|
||||
}
|
||||
// High mem/address wrap-around
|
||||
|
|
|
@ -76,8 +76,8 @@ Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */
|
|||
// TODO: remove non-wrapping versions?
|
||||
#define SPC_NO_SP_WRAPAROUND 0
|
||||
|
||||
#define SET_SP( v ) (sp = ram + 0x101 + (v))
|
||||
#define GET_SP() (sp - 0x101 - ram)
|
||||
#define SET_SP( v ) (sp = ram + 0x101 + ((uint8_t) v))
|
||||
#define GET_SP() (uint8_t (sp - 0x101 - ram))
|
||||
|
||||
#if SPC_NO_SP_WRAPAROUND
|
||||
#define PUSH16( v ) (sp -= 2, SET_LE16( sp, v ))
|
||||
|
@ -485,7 +485,7 @@ loop:
|
|||
|
||||
case 0xAF: // MOV (X)+,A
|
||||
WRITE_DP( 0, x, a + no_read_before_write );
|
||||
x++;
|
||||
x = (uint8_t) (x + 1);
|
||||
goto loop;
|
||||
|
||||
// 5. 8-BIT LOGIC OPERATION COMMANDS
|
||||
|
@ -808,7 +808,7 @@ loop:
|
|||
unsigned temp = y * a;
|
||||
a = (uint8_t) temp;
|
||||
nz = ((temp >> 1) | temp) & 0x7F;
|
||||
y = temp >> 8;
|
||||
y = (uint8_t) (temp >> 8);
|
||||
nz |= y;
|
||||
goto loop;
|
||||
}
|
||||
|
@ -838,6 +838,7 @@ loop:
|
|||
|
||||
nz = (uint8_t) a;
|
||||
a = (uint8_t) a;
|
||||
y = (uint8_t) y;
|
||||
|
||||
goto loop;
|
||||
}
|
||||
|
@ -1004,7 +1005,7 @@ loop:
|
|||
case 0x7F: // RET1
|
||||
temp = *sp;
|
||||
SET_PC( GET_LE16( sp + 1 ) );
|
||||
sp += 3;
|
||||
SET_SP( GET_SP() + 3 );
|
||||
goto set_psw;
|
||||
case 0x8E: // POP PSW
|
||||
POP( temp );
|
||||
|
|
|
@ -18,6 +18,19 @@ all other #include lines. */
|
|||
#undef require
|
||||
#define require( expr ) assert( expr )
|
||||
|
||||
// Use to provide hints to compiler for optimized code layout in situations where we
|
||||
// can almost always expect a conditional to go one way or the other. Should only be
|
||||
// used in situations where an unexpected branch is truly exceptional though!
|
||||
#undef likely
|
||||
#undef unlikely
|
||||
#ifdef __GNUC__
|
||||
#define likely( x ) __builtin_expect(x, 1)
|
||||
#define unlikely( x ) __builtin_expect(x, 0)
|
||||
#else
|
||||
#define likely( x ) (x)
|
||||
#define unlikely( x ) (x)
|
||||
#endif
|
||||
|
||||
// Like printf() except output goes to debug log file. Might be defined to do
|
||||
// nothing (not even evaluate its arguments).
|
||||
// void debug_printf( const char* format, ... );
|
||||
|
|
|
@ -337,7 +337,9 @@ BLARGG_EXPORT gme_err_t gme_play ( Music_Emu* me, int n, short* p )
|
|||
BLARGG_EXPORT void gme_set_fade ( Music_Emu* me, int start_msec ) { me->set_fade( start_msec ); }
|
||||
BLARGG_EXPORT int gme_track_ended ( Music_Emu const* me ) { return me->track_ended(); }
|
||||
BLARGG_EXPORT int gme_tell ( Music_Emu const* me ) { return me->tell(); }
|
||||
BLARGG_EXPORT int gme_tell_samples ( Music_Emu const* me ) { return me->tell_samples(); }
|
||||
BLARGG_EXPORT gme_err_t gme_seek ( Music_Emu* me, int msec ) { return me->seek( msec ); }
|
||||
BLARGG_EXPORT gme_err_t gme_seek_samples ( Music_Emu* me, int n ) { return me->seek_samples( n ); }
|
||||
BLARGG_EXPORT int gme_voice_count ( Music_Emu const* me ) { return me->voice_count(); }
|
||||
BLARGG_EXPORT void gme_ignore_silence ( Music_Emu* me, int disable ) { me->ignore_silence( disable != 0 ); }
|
||||
BLARGG_EXPORT void gme_set_tempo ( Music_Emu* me, double t ) { me->set_tempo( t ); }
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/* Game music emulator library C interface (also usable from C++) */
|
||||
|
||||
/* Game_Music_Emu 0.6.0 */
|
||||
/* Game_Music_Emu 0.6.1 */
|
||||
#ifndef GME_H
|
||||
#define GME_H
|
||||
|
||||
|
@ -8,7 +8,7 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define GME_VERSION 0x000600 /* 1 byte major, 1 byte minor, 1 byte patch-level */
|
||||
#define GME_VERSION 0x000601 /* 1 byte major, 1 byte minor, 1 byte patch-level */
|
||||
|
||||
/* Error string returned by library functions, or NULL if no error (success) */
|
||||
typedef const char* gme_err_t;
|
||||
|
@ -47,9 +47,15 @@ int gme_track_ended( Music_Emu const* );
|
|||
/* Number of milliseconds (1000 = one second) played since beginning of track */
|
||||
int gme_tell( Music_Emu const* );
|
||||
|
||||
/* Number of samples generated since beginning of track */
|
||||
int gme_tell_samples( Music_Emu const* );
|
||||
|
||||
/* Seek to new time in track. Seeking backwards or far forward can take a while. */
|
||||
gme_err_t gme_seek( Music_Emu*, int msec );
|
||||
|
||||
/* Equivalent to restarting track then skipping n samples */
|
||||
gme_err_t gme_seek_samples( Music_Emu*, int n );
|
||||
|
||||
|
||||
/******** Informational ********/
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
# later are used by pkg-config.
|
||||
prefix=@CMAKE_INSTALL_PREFIX@
|
||||
exec_prefix=${prefix}
|
||||
lib_suffix=
|
||||
lib_suffix=@LIB_SUFFIX@
|
||||
libdir=${exec_prefix}/lib${lib_suffix}
|
||||
includedir=${prefix}/include
|
||||
|
||||
|
@ -13,3 +13,4 @@ URL: http://code.google.com/p/game-music-emu/
|
|||
Version: @GME_VERSION@
|
||||
Cflags: -I${includedir}
|
||||
Libs: -L${libdir} -lgme
|
||||
Libs.private: -lstdc++
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/* Game music emulator library C interface (also usable from C++) */
|
||||
|
||||
/* Game_Music_Emu 0.6.0 */
|
||||
/* Game_Music_Emu 0.6.1 */
|
||||
#ifndef GME_H
|
||||
#define GME_H
|
||||
|
||||
|
@ -8,7 +8,7 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define GME_VERSION 0x000600 /* 1 byte major, 1 byte minor, 1 byte patch-level */
|
||||
#define GME_VERSION 0x000601 /* 1 byte major, 1 byte minor, 1 byte patch-level */
|
||||
|
||||
/* Error string returned by library functions, or NULL if no error (success) */
|
||||
typedef const char* gme_err_t;
|
||||
|
@ -47,9 +47,15 @@ int gme_track_ended( Music_Emu const* );
|
|||
/* Number of milliseconds (1000 = one second) played since beginning of track */
|
||||
int gme_tell( Music_Emu const* );
|
||||
|
||||
/* Number of samples generated since beginning of track */
|
||||
int gme_tell_samples( Music_Emu const* );
|
||||
|
||||
/* Seek to new time in track. Seeking backwards or far forward can take a while. */
|
||||
gme_err_t gme_seek( Music_Emu*, int msec );
|
||||
|
||||
/* Equivalent to restarting track then skipping n samples */
|
||||
gme_err_t gme_seek_samples( Music_Emu*, int n );
|
||||
|
||||
|
||||
/******** Informational ********/
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
Game_Music_Emu 0.6.0: Game Music Emulators
|
||||
Game_Music_Emu 0.6.2: Game Music Emulators
|
||||
------------------------------------------
|
||||
Game_Music_Emu is a collection of video game music file emulators that
|
||||
support the following formats and systems:
|
||||
|
@ -34,30 +34,45 @@ several architectures, Mac OS, MorphOS, Xbox, PlayStation Portable,
|
|||
GP2X, and Nintendo DS.
|
||||
|
||||
Author : Shay Green <gblargg@gmail.com>
|
||||
Website: http://www.slack.net/~ant/
|
||||
Forum : http://groups.google.com/group/blargg-sound-libs
|
||||
Website: https://bitbucket.org/mpyne/game-music-emu/wiki/Home
|
||||
License: GNU Lesser General Public License (LGPL)
|
||||
|
||||
Current Maintainer: Michael Pyne <mpyne@purinchu.net>
|
||||
|
||||
Getting Started
|
||||
---------------
|
||||
Build a program consisting of demo/basics.c, demo/Wave_Writer.cpp, and
|
||||
all source files in gme/. If you have CMake 2.6 or later, execute
|
||||
all source files in gme/.
|
||||
|
||||
run cmake
|
||||
cd demo
|
||||
run make
|
||||
Or, if you have CMake 2.6 or later, execute at a command prompt (from the
|
||||
extracted source directory):
|
||||
|
||||
Be sure "test.nsf" is in the same directory as the program. Running it
|
||||
mkdir build
|
||||
cd build
|
||||
cmake ../ # <-- Pass any needed CMake flags here
|
||||
make # To build the library
|
||||
cd demo
|
||||
make # To build the demo itself
|
||||
|
||||
Be sure "test.nsf" is in the same directory as the demo program. Running it
|
||||
should generate the recording "out.wav".
|
||||
|
||||
You can use "make install" to install the library. To choose where to install
|
||||
the library to, use the CMake argument "-DCMAKE_INSTALL_PREFIX=/usr/local"
|
||||
(and replace /usr/local with the base path you wish to use). Alternately, you
|
||||
can specify the base path to install to when you run "make install" by passing
|
||||
'DESTDIR=/usr/local' on the make install command line (again, replace
|
||||
/usr/local as appropriate).
|
||||
|
||||
To build a static library instead of shared (the default), pass
|
||||
-DBUILD_SHARED_LIBS=OFF to the cmake command when running cmake.
|
||||
|
||||
A slightly more extensive demo application is available in the player/
|
||||
directory. It requires SDL to build.
|
||||
|
||||
Read gme.txt for more information. Post to the discussion forum for
|
||||
assistance.
|
||||
|
||||
|
||||
Files
|
||||
-----
|
||||
gme.txt General notes about the library
|
||||
|
|
Binary file not shown.
Binary file not shown.
|
@ -7,6 +7,10 @@
|
|||
# and other things
|
||||
#
|
||||
|
||||
ifdef GCC81
|
||||
GCC80=1
|
||||
endif
|
||||
|
||||
ifdef GCC80
|
||||
GCC72=1
|
||||
endif
|
||||
|
@ -116,6 +120,7 @@ WFLAGS+=-Wfloat-equal
|
|||
#WFLAGS+=-Wtraditional
|
||||
ifdef VCHELP
|
||||
WFLAGS+=-Wdeclaration-after-statement
|
||||
WFLAGS+=-Wno-error=declaration-after-statement
|
||||
endif
|
||||
WFLAGS+=-Wundef
|
||||
ifndef GCC295
|
||||
|
@ -189,12 +194,6 @@ ifdef GCC46
|
|||
WFLAGS+=-Wno-suggest-attribute=noreturn
|
||||
endif
|
||||
|
||||
ifndef MINGW
|
||||
ifdef GCC45
|
||||
WFLAGS+=-Wunsuffixed-float-constants
|
||||
endif
|
||||
endif
|
||||
|
||||
ifdef NOLDWARNING
|
||||
LDFLAGS+=-Wl,--as-needed
|
||||
endif
|
||||
|
@ -208,6 +207,9 @@ WFLAGS+=$(OLDWFLAGS)
|
|||
ifdef GCC43
|
||||
#WFLAGS+=-Wno-error=clobbered
|
||||
endif
|
||||
ifdef GCC44
|
||||
WFLAGS+=-Wno-error=array-bounds
|
||||
endif
|
||||
ifdef GCC46
|
||||
WFLAGS+=-Wno-error=suggest-attribute=noreturn
|
||||
endif
|
||||
|
|
|
@ -1254,7 +1254,8 @@ found:
|
|||
|
||||
var->string = var->zstring = Z_StrDup(valstr);
|
||||
|
||||
if (override)
|
||||
if (var->flags & CV_PASSWORD); // Don't change value for password field
|
||||
else if (override)
|
||||
var->value = overrideval;
|
||||
else if (var->flags & CV_FLOAT)
|
||||
{
|
||||
|
|
|
@ -95,7 +95,8 @@ typedef enum
|
|||
CV_HIDEN = 1024, // variable is not part of the cvar list so cannot be accessed by the console
|
||||
// can only be set when we have the pointer to it
|
||||
// used on menus
|
||||
CV_CHEAT = 2048 // Don't let this be used in multiplayer unless cheats are on.
|
||||
CV_CHEAT = 2048, // Don't let this be used in multiplayer unless cheats are on.
|
||||
CV_PASSWORD = 4096 // Password field
|
||||
} cvflags_t;
|
||||
|
||||
typedef struct CV_PossibleValue_s
|
||||
|
|
|
@ -37,7 +37,7 @@
|
|||
* Last updated 2015 / 05 / 03 - SRB2 v2.1.15 - srb2.srb
|
||||
* Last updated 2018 / 12 / 23 - SRB2 v2.1.22 - patch.dta
|
||||
* Last updated 2019 / 01 / 18 - Kart v1.0.2 - Main assets
|
||||
* Last updated 2019 / 02 / 04 - Kart v1.0.3 - patch.kart
|
||||
* Last updated 2019 / 03 / 11 - Kart v1.0.4 - patch.kart
|
||||
*/
|
||||
|
||||
// Base SRB2 hashes
|
||||
|
@ -52,7 +52,7 @@
|
|||
#define ASSET_HASH_CHARS_KART "e2c428347dde52858a3dacd29fc5b964"
|
||||
#define ASSET_HASH_MAPS_KART "1335cd064656aedca359cfbb5233ac4a"
|
||||
#ifdef USE_PATCH_KART
|
||||
#define ASSET_HASH_PATCH_KART "e06c1c90e5645c886026311964f8e1f5"
|
||||
#define ASSET_HASH_PATCH_KART "b5f48e1abccfa47a5745199182e2fef4"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
|
|
@ -544,6 +544,22 @@ static void CON_MoveConsole(void)
|
|||
}
|
||||
}
|
||||
|
||||
INT32 CON_ShiftChar(INT32 ch)
|
||||
{
|
||||
if ((ch >= 'a' && ch <= 'z') || (ch >= 'A' && ch <= 'Z'))
|
||||
{
|
||||
if (shiftdown ^ capslock)
|
||||
ch = shiftxform[ch];
|
||||
}
|
||||
else // if we're holding shift we should still shift non letter symbols
|
||||
{
|
||||
if (shiftdown)
|
||||
ch = shiftxform[ch];
|
||||
}
|
||||
|
||||
return ch;
|
||||
}
|
||||
|
||||
// Clear time of console heads up messages
|
||||
//
|
||||
void CON_ClearHUD(void)
|
||||
|
@ -1084,16 +1100,6 @@ boolean CON_Responder(event_t *ev)
|
|||
else if (key == KEY_KPADSLASH)
|
||||
key = '/';
|
||||
|
||||
// capslock
|
||||
if (key == KEY_CAPSLOCK) // it's a toggle.
|
||||
{
|
||||
if (capslock)
|
||||
capslock = false;
|
||||
else
|
||||
capslock = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
// same capslock code as hu_stuff.c's HU_responder. Check there for details.
|
||||
if ((key >= 'a' && key <= 'z') || (key >= 'A' && key <= 'Z'))
|
||||
{
|
||||
|
|
|
@ -44,6 +44,8 @@ extern UINT8 *yellowmap, *purplemap, *greenmap, *bluemap, *graymap, *redmap, *or
|
|||
// Console bg color (auto updated to match)
|
||||
extern UINT8 *consolebgmap;
|
||||
|
||||
INT32 CON_ShiftChar(INT32 ch);
|
||||
|
||||
void CON_SetupBackColormap(void);
|
||||
void CON_ClearHUD(void); // clear heads up messages
|
||||
|
||||
|
|
410
src/d_clisrv.c
410
src/d_clisrv.c
|
@ -22,6 +22,7 @@
|
|||
#include "i_video.h"
|
||||
#include "d_net.h"
|
||||
#include "d_main.h"
|
||||
#include "d_event.h"
|
||||
#include "g_game.h"
|
||||
#include "hu_stuff.h"
|
||||
#include "keys.h"
|
||||
|
@ -72,6 +73,7 @@
|
|||
#define PREDICTIONQUEUE BACKUPTICS
|
||||
#define PREDICTIONMASK (PREDICTIONQUEUE-1)
|
||||
#define MAX_REASONLENGTH 30
|
||||
#define FORCECLOSE 0x8000
|
||||
|
||||
boolean server = true; // true or false but !server == client
|
||||
#define client (!server)
|
||||
|
@ -93,6 +95,7 @@ static tic_t freezetimeout[MAXNETNODES]; // Until when can this node freeze the
|
|||
UINT16 pingmeasurecount = 1;
|
||||
UINT32 realpingtable[MAXPLAYERS]; //the base table of ping where an average will be sent to everyone.
|
||||
UINT32 playerpingtable[MAXPLAYERS]; //table of player latency values.
|
||||
tic_t servermaxping = 800; // server's max ping. Defaults to 800
|
||||
#endif
|
||||
SINT8 nodetoplayer[MAXNETNODES];
|
||||
SINT8 nodetoplayer2[MAXNETNODES]; // say the numplayer for this node if any (splitscreen)
|
||||
|
@ -648,6 +651,8 @@ static inline void resynch_write_player(resynch_pak *rsp, const size_t i)
|
|||
|
||||
rsp->jointime = (tic_t)LONG(players[i].jointime);
|
||||
|
||||
rsp->splitscreenindex = players[i].splitscreenindex;
|
||||
|
||||
rsp->hasmo = false;
|
||||
//Transfer important mo information if the player has a body.
|
||||
//This lets us resync players even if they are dead.
|
||||
|
@ -783,6 +788,8 @@ static void resynch_read_player(resynch_pak *rsp)
|
|||
|
||||
players[i].jointime = (tic_t)LONG(rsp->jointime);
|
||||
|
||||
players[i].splitscreenindex = rsp->splitscreenindex;
|
||||
|
||||
//We get a packet for each player in game.
|
||||
if (!playeringame[i])
|
||||
return;
|
||||
|
@ -1121,12 +1128,22 @@ typedef enum
|
|||
CL_DOWNLOADSAVEGAME,
|
||||
#endif
|
||||
CL_CONNECTED,
|
||||
CL_ABORTED
|
||||
CL_ABORTED,
|
||||
CL_ASKDOWNLOADFILES,
|
||||
CL_WAITDOWNLOADFILESRESPONSE,
|
||||
CL_CHALLENGE
|
||||
} cl_mode_t;
|
||||
|
||||
static void GetPackets(void);
|
||||
|
||||
static cl_mode_t cl_mode = CL_SEARCHING;
|
||||
static boolean cl_needsdownload = false;
|
||||
|
||||
static UINT8 cl_challengenum = 0;
|
||||
static UINT8 cl_challengequestion[MD5_LEN+1];
|
||||
static char cl_challengepassword[65];
|
||||
static UINT8 cl_challengeanswer[MD5_LEN+1];
|
||||
static UINT8 cl_challengeattempted = 0;
|
||||
|
||||
// Player name send/load
|
||||
|
||||
|
@ -1163,6 +1180,8 @@ static void CV_LoadPlayerNames(UINT8 **p)
|
|||
}
|
||||
|
||||
#ifdef CLIENT_LOADINGSCREEN
|
||||
static UINT32 SL_SearchServer(INT32 node);
|
||||
|
||||
//
|
||||
// CL_DrawConnectionStatus
|
||||
//
|
||||
|
@ -1186,11 +1205,42 @@ static inline void CL_DrawConnectionStatus(void)
|
|||
// 15 pal entries total.
|
||||
const char *cltext;
|
||||
|
||||
for (i = 0; i < 16; ++i)
|
||||
V_DrawFill((BASEVIDWIDTH/2-128) + (i * 16), BASEVIDHEIGHT-24, 16, 8, palstart + ((animtime - i) & 15));
|
||||
if (cl_mode != CL_CHALLENGE)
|
||||
for (i = 0; i < 16; ++i)
|
||||
V_DrawFill((BASEVIDWIDTH/2-128) + (i * 16), BASEVIDHEIGHT-24, 16, 8, palstart + ((animtime - i) & 15));
|
||||
|
||||
switch (cl_mode)
|
||||
{
|
||||
case CL_CHALLENGE:
|
||||
{
|
||||
char asterisks[33];
|
||||
size_t sl = min(32, strlen(cl_challengepassword));
|
||||
UINT32 serverid;
|
||||
|
||||
memset(asterisks, '*', sl);
|
||||
memset(asterisks+sl, 0, 33-sl);
|
||||
|
||||
V_DrawString(BASEVIDWIDTH/2-128, BASEVIDHEIGHT-24, V_MONOSPACE|V_ALLOWLOWERCASE, asterisks);
|
||||
V_DrawFixedPatch((BASEVIDWIDTH/2) << FRACBITS, (BASEVIDHEIGHT/2) << FRACBITS, FRACUNIT, 0, W_CachePatchName("BSRVLOCK", PU_CACHE), NULL);
|
||||
|
||||
serverid = SL_SearchServer(servernode);
|
||||
|
||||
if (serverid == UINT32_MAX)
|
||||
{
|
||||
M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT/2-8, 32, 1);
|
||||
V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2, V_REDMAP, M_GetText("This server is password protected."));
|
||||
}
|
||||
else
|
||||
{
|
||||
M_DrawTextBox(BASEVIDWIDTH/2-128-8, BASEVIDHEIGHT/2-8, 32, 3);
|
||||
V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2, V_REDMAP, M_GetText("This server,"));
|
||||
V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2+8, V_ALLOWLOWERCASE, serverlist[serverid].info.servername);
|
||||
V_DrawCenteredString(BASEVIDWIDTH/2, BASEVIDHEIGHT/2+16, V_REDMAP, M_GetText("is password protected."));
|
||||
}
|
||||
|
||||
cltext = M_GetText(cl_challengeattempted ? "Incorrect password. Please try again." : "Please enter the server password.");
|
||||
}
|
||||
break;
|
||||
#ifdef JOININGAME
|
||||
case CL_DOWNLOADSAVEGAME:
|
||||
if (lastfilenum != -1)
|
||||
|
@ -1210,6 +1260,9 @@ static inline void CL_DrawConnectionStatus(void)
|
|||
case CL_WAITJOINRESPONSE:
|
||||
cltext = M_GetText("Requesting to join...");
|
||||
break;
|
||||
case CL_ASKDOWNLOADFILES:
|
||||
case CL_WAITDOWNLOADFILESRESPONSE:
|
||||
cltext = M_GetText("Waiting to download files...");
|
||||
default:
|
||||
cltext = M_GetText("Connecting to server...");
|
||||
break;
|
||||
|
@ -1287,6 +1340,9 @@ static boolean CL_SendJoin(void)
|
|||
netbuffer->u.clientcfg.localplayers = localplayers;
|
||||
netbuffer->u.clientcfg.version = VERSION;
|
||||
netbuffer->u.clientcfg.subversion = SUBVERSION;
|
||||
netbuffer->u.clientcfg.needsdownload = cl_needsdownload;
|
||||
netbuffer->u.clientcfg.challengenum = cl_challengenum;
|
||||
memcpy(netbuffer->u.clientcfg.challengeanswer, cl_challengeanswer, MD5_LEN);
|
||||
|
||||
return HSendPacket(servernode, true, 0, sizeof (clientconfig_pak));
|
||||
}
|
||||
|
@ -1307,7 +1363,13 @@ static void SV_SendServerInfo(INT32 node, tic_t servertime)
|
|||
netbuffer->u.serverinfo.gametype = (UINT8)(G_BattleGametype() ? VANILLA_GT_MATCH : VANILLA_GT_RACE); // SRB2Kart: Vanilla's gametype constants for MS support
|
||||
netbuffer->u.serverinfo.modifiedgame = (UINT8)modifiedgame;
|
||||
netbuffer->u.serverinfo.cheatsenabled = CV_CheatsEnabled();
|
||||
netbuffer->u.serverinfo.isdedicated = (UINT8)dedicated;
|
||||
|
||||
netbuffer->u.serverinfo.kartvars = (UINT8) (
|
||||
(cv_kartspeed.value & SV_SPEEDMASK) |
|
||||
(dedicated ? SV_DEDICATED : 0) |
|
||||
(D_IsJoinPasswordOn() ? SV_PASSWORD : 0)
|
||||
);
|
||||
|
||||
strncpy(netbuffer->u.serverinfo.servername, cv_servername.string,
|
||||
MAXSERVERNAME);
|
||||
strncpy(netbuffer->u.serverinfo.mapname, G_BuildMapName(gamemap), 7);
|
||||
|
@ -1389,33 +1451,13 @@ static void SV_SendPlayerInfo(INT32 node)
|
|||
continue;
|
||||
}
|
||||
|
||||
netbuffer->u.playerinfo[i].node = (UINT8)playernode[i];
|
||||
netbuffer->u.playerinfo[i].node = i;
|
||||
strncpy(netbuffer->u.playerinfo[i].name, (const char *)&player_names[i], MAXPLAYERNAME+1);
|
||||
netbuffer->u.playerinfo[i].name[MAXPLAYERNAME] = '\0';
|
||||
|
||||
//fetch IP address
|
||||
{
|
||||
const char *claddress;
|
||||
UINT32 numericaddress[4];
|
||||
|
||||
memset(netbuffer->u.playerinfo[i].address, 0, 4);
|
||||
if (playernode[i] == 0)
|
||||
{
|
||||
//127.0.0.1
|
||||
netbuffer->u.playerinfo[i].address[0] = 127;
|
||||
netbuffer->u.playerinfo[i].address[3] = 1;
|
||||
}
|
||||
else if (playernode[i] > 0 && I_GetNodeAddress && (claddress = I_GetNodeAddress(playernode[i])) != NULL)
|
||||
{
|
||||
if (sscanf(claddress, "%d.%d.%d.%d", &numericaddress[0], &numericaddress[1], &numericaddress[2], &numericaddress[3]) < 4)
|
||||
goto badaddress;
|
||||
netbuffer->u.playerinfo[i].address[0] = (UINT8)numericaddress[0];
|
||||
netbuffer->u.playerinfo[i].address[1] = (UINT8)numericaddress[1];
|
||||
netbuffer->u.playerinfo[i].address[2] = (UINT8)numericaddress[2];
|
||||
netbuffer->u.playerinfo[i].address[3] = (UINT8)numericaddress[3];
|
||||
}
|
||||
}
|
||||
badaddress:
|
||||
//No, don't do that, you fuckface.
|
||||
memset(netbuffer->u.playerinfo[i].address, 0, 4);
|
||||
|
||||
if (G_GametypeHasTeams())
|
||||
{
|
||||
|
@ -1740,8 +1782,6 @@ static void SendAskInfo(INT32 node, boolean viams)
|
|||
serverelem_t serverlist[MAXSERVERLIST];
|
||||
UINT32 serverlistcount = 0;
|
||||
|
||||
#define FORCECLOSE 0x8000
|
||||
|
||||
static void SL_ClearServerList(INT32 connectedserver)
|
||||
{
|
||||
UINT32 i;
|
||||
|
@ -1867,7 +1907,7 @@ void CL_UpdateServerList(boolean internetsearch, INT32 room)
|
|||
/** Called by CL_ServerConnectionTicker
|
||||
*
|
||||
* \param viams ???
|
||||
* \param asksent ???
|
||||
* \param asksent The last time we asked the server to join. We re-ask every second in case our request got lost in transmit.
|
||||
* \return False if the connection was aborted
|
||||
* \sa CL_ServerConnectionTicker
|
||||
* \sa CL_ConnectToServer
|
||||
|
@ -1960,9 +2000,12 @@ static boolean CL_ServerConnectionSearchTicker(boolean viams, tic_t *asksent)
|
|||
), NULL, MM_NOTHING);
|
||||
return false;
|
||||
}
|
||||
|
||||
cl_mode = CL_ASKDOWNLOADFILES;
|
||||
|
||||
// no problem if can't send packet, we will retry later
|
||||
if (CL_SendRequestFile())
|
||||
cl_mode = CL_DOWNLOADFILES;
|
||||
//if (CL_SendRequestFile())
|
||||
// cl_mode = CL_DOWNLOADFILES;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -1992,7 +2035,7 @@ static boolean CL_ServerConnectionSearchTicker(boolean viams, tic_t *asksent)
|
|||
* \param viams ???
|
||||
* \param tmpsave The name of the gamestate file???
|
||||
* \param oldtic Used for knowing when to poll events and redraw
|
||||
* \param asksent ???
|
||||
* \param asksent The last time we asked the server to join. We re-ask every second in case our request got lost in transmit.
|
||||
* \return False if the connection was aborted
|
||||
* \sa CL_ServerConnectionSearchTicker
|
||||
* \sa CL_ConnectToServer
|
||||
|
@ -2030,6 +2073,7 @@ static boolean CL_ServerConnectionTicker(boolean viams, const char *tmpsave, tic
|
|||
/* FALLTHRU */
|
||||
|
||||
case CL_ASKJOIN:
|
||||
cl_needsdownload = false;
|
||||
CL_LoadServerFiles();
|
||||
#ifdef JOININGAME
|
||||
// prepare structures to save the file
|
||||
|
@ -2038,9 +2082,23 @@ static boolean CL_ServerConnectionTicker(boolean viams, const char *tmpsave, tic
|
|||
CL_PrepareDownloadSaveGame(tmpsave);
|
||||
#endif
|
||||
if (CL_SendJoin())
|
||||
{
|
||||
*asksent = I_GetTime();
|
||||
cl_mode = CL_WAITJOINRESPONSE;
|
||||
}
|
||||
break;
|
||||
|
||||
case CL_ASKDOWNLOADFILES:
|
||||
cl_needsdownload = true;
|
||||
|
||||
if (CL_SendJoin())
|
||||
{
|
||||
*asksent = I_GetTime();
|
||||
cl_mode = CL_WAITDOWNLOADFILESRESPONSE;
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
#ifdef JOININGAME
|
||||
case CL_DOWNLOADSAVEGAME:
|
||||
// At this state, the first (and only) needed file is the gamestate
|
||||
|
@ -2054,7 +2112,19 @@ static boolean CL_ServerConnectionTicker(boolean viams, const char *tmpsave, tic
|
|||
break;
|
||||
#endif
|
||||
|
||||
case CL_CHALLENGE:
|
||||
(*asksent) = I_GetTime() - NEWTICRATE; // Send password immediately upon entering
|
||||
break;
|
||||
|
||||
case CL_WAITJOINRESPONSE:
|
||||
case CL_WAITDOWNLOADFILESRESPONSE:
|
||||
if (*asksent + NEWTICRATE < I_GetTime() && CL_SendJoin())
|
||||
{
|
||||
*asksent = I_GetTime();
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case CL_CONNECTED:
|
||||
default:
|
||||
break;
|
||||
|
@ -2072,20 +2142,10 @@ static boolean CL_ServerConnectionTicker(boolean viams, const char *tmpsave, tic
|
|||
// Call it only once by tic
|
||||
if (*oldtic != I_GetTime())
|
||||
{
|
||||
INT32 key;
|
||||
|
||||
I_OsPolling();
|
||||
key = I_GetKey();
|
||||
// Only ESC and non-keyboard keys abort connection
|
||||
if (key == KEY_ESCAPE || key >= KEY_MOUSE1)
|
||||
{
|
||||
CONS_Printf(M_GetText("Network game synchronization aborted.\n"));
|
||||
// M_StartMessage(M_GetText("Network game synchronization aborted.\n\nPress ESC\n"), NULL, MM_NOTHING);
|
||||
D_QuitNetGame();
|
||||
CL_Reset();
|
||||
D_StartTitle();
|
||||
D_ProcessEvents();
|
||||
if (gamestate != GS_WAITINGPLAYERS)
|
||||
return false;
|
||||
}
|
||||
|
||||
// why are these here? this is for servers, we're a client
|
||||
//if (key == 's' && server)
|
||||
|
@ -2114,6 +2174,71 @@ static boolean CL_ServerConnectionTicker(boolean viams, const char *tmpsave, tic
|
|||
return true;
|
||||
}
|
||||
|
||||
boolean CL_Responder(event_t *ev)
|
||||
{
|
||||
size_t len;
|
||||
INT32 ch;
|
||||
|
||||
if (!(client && cl_mode != CL_CONNECTED && cl_mode != CL_ABORTED))
|
||||
return false; // Don't do anything outside of the connection screen
|
||||
|
||||
if (ev->type != ev_keydown)
|
||||
return false;
|
||||
|
||||
ch = (INT32)ev->data1;
|
||||
|
||||
// Only ESC and non-keyboard keys abort connection
|
||||
if (ch == KEY_ESCAPE || ch >= KEY_MOUSE1)
|
||||
{
|
||||
CONS_Printf(M_GetText("Network game synchronization aborted.\n"));
|
||||
//M_StartMessage(M_GetText("Network game synchronization aborted.\n\nPress ESC\n"), NULL, MM_NOTHING);
|
||||
D_QuitNetGame();
|
||||
CL_Reset();
|
||||
D_StartTitle();
|
||||
return true;
|
||||
}
|
||||
|
||||
if (cl_mode != CL_CHALLENGE)
|
||||
return false;
|
||||
|
||||
if ((ch >= HU_FONTSTART && ch <= HU_FONTEND && hu_font[ch-HU_FONTSTART])
|
||||
|| ch == ' ') // Allow spaces, of course
|
||||
{
|
||||
len = strlen(cl_challengepassword);
|
||||
if (len < 64)
|
||||
{
|
||||
cl_challengepassword[len+1] = 0;
|
||||
cl_challengepassword[len] = CON_ShiftChar(ch);
|
||||
}
|
||||
|
||||
cl_challengeattempted = 0;
|
||||
}
|
||||
else if (ch == KEY_BACKSPACE)
|
||||
{
|
||||
len = strlen(cl_challengepassword);
|
||||
|
||||
if (len > 0)
|
||||
cl_challengepassword[len-1] = 0;
|
||||
|
||||
cl_challengeattempted = 0;
|
||||
}
|
||||
else if (ch == KEY_ENTER)
|
||||
{
|
||||
netgame = true;
|
||||
multiplayer = true;
|
||||
|
||||
#ifndef NONET
|
||||
SL_ClearServerList(servernode);
|
||||
#endif
|
||||
cl_mode = CL_SEARCHING;
|
||||
|
||||
D_ComputeChallengeAnswer(cl_challengequestion, cl_challengepassword, cl_challengeanswer);
|
||||
cl_challengeattempted = 1;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Use adaptive send using net_bandwidth and stat.sendbytes
|
||||
*
|
||||
* \param viams ???
|
||||
|
@ -2134,6 +2259,7 @@ static void CL_ConnectToServer(boolean viams)
|
|||
#endif
|
||||
|
||||
cl_mode = CL_SEARCHING;
|
||||
cl_challengenum = 0;
|
||||
|
||||
#ifdef CLIENT_LOADINGSCREEN
|
||||
lastfilenum = -1;
|
||||
|
@ -2191,6 +2317,8 @@ static void CL_ConnectToServer(boolean viams)
|
|||
SL_ClearServerList(servernode);
|
||||
#endif
|
||||
|
||||
cl_challengeattempted = 0;
|
||||
|
||||
do
|
||||
{
|
||||
// If the connection was aborted for some reason, leave
|
||||
|
@ -2542,6 +2670,8 @@ static void CL_RemovePlayer(INT32 playernum, INT32 reason)
|
|||
|
||||
#ifdef HAVE_BLUA
|
||||
LUAh_PlayerQuit(&players[playernum], reason); // Lua hook for player quitting
|
||||
#else
|
||||
(void)reason;
|
||||
#endif
|
||||
|
||||
// Reset player data
|
||||
|
@ -2725,7 +2855,10 @@ static void Command_Ban(void)
|
|||
else
|
||||
{
|
||||
if (server) // only the server is allowed to do this right now
|
||||
{
|
||||
Ban_Add(COM_Argv(2));
|
||||
D_SaveBan(); // save the ban list
|
||||
}
|
||||
|
||||
if (COM_Argc() == 2)
|
||||
{
|
||||
|
@ -2756,6 +2889,42 @@ static void Command_Ban(void)
|
|||
|
||||
}
|
||||
|
||||
static void Command_BanIP(void)
|
||||
{
|
||||
if (COM_Argc() < 2)
|
||||
{
|
||||
CONS_Printf(M_GetText("banip <ip> <reason>: ban an ip address\n"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (server) // Only the server can use this, otherwise does nothing.
|
||||
{
|
||||
const char *address = (COM_Argv(1));
|
||||
const char *reason;
|
||||
|
||||
if (COM_Argc() == 2)
|
||||
reason = NULL;
|
||||
else
|
||||
reason = COM_Argv(2);
|
||||
|
||||
|
||||
if (I_SetBanAddress && I_SetBanAddress(address, NULL))
|
||||
{
|
||||
if (reason)
|
||||
CONS_Printf("Banned IP address %s for: %s\n", address, reason);
|
||||
else
|
||||
CONS_Printf("Banned IP address %s\n", address);
|
||||
|
||||
Ban_Add(reason);
|
||||
D_SaveBan();
|
||||
}
|
||||
else
|
||||
{
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void Command_Kick(void)
|
||||
{
|
||||
if (COM_Argc() < 2)
|
||||
|
@ -3062,6 +3231,7 @@ void D_ClientServerInit(void)
|
|||
COM_AddCommand("getplayernum", Command_GetPlayerNum);
|
||||
COM_AddCommand("kick", Command_Kick);
|
||||
COM_AddCommand("ban", Command_Ban);
|
||||
COM_AddCommand("banip", Command_BanIP);
|
||||
COM_AddCommand("clearbans", Command_ClearBans);
|
||||
COM_AddCommand("showbanlist", Command_ShowBan);
|
||||
COM_AddCommand("reloadbans", Command_ReloadBan);
|
||||
|
@ -3095,6 +3265,9 @@ void D_ClientServerInit(void)
|
|||
gametic = 0;
|
||||
localgametic = 0;
|
||||
|
||||
memset(cl_challengequestion, 0x00, MD5_LEN+1);
|
||||
memset(cl_challengeanswer, 0x00, MD5_LEN+1);
|
||||
|
||||
// do not send anything before the real begin
|
||||
SV_StopServer();
|
||||
SV_ResetServer();
|
||||
|
@ -3316,6 +3489,8 @@ static void Got_AddPlayer(UINT8 **p, INT32 playernum)
|
|||
addedtogame = true;
|
||||
}
|
||||
|
||||
players[newplayernum].splitscreenindex = splitscreenplayer;
|
||||
|
||||
if (netgame)
|
||||
{
|
||||
if (server && cv_showjoinaddress.value)
|
||||
|
@ -3582,6 +3757,33 @@ static void HandleConnect(SINT8 node)
|
|||
boolean newnode = false;
|
||||
#endif
|
||||
|
||||
if (node != servernode && !nodeingame[node] && D_IsJoinPasswordOn())
|
||||
{
|
||||
// Ensure node sent the correct password challenge
|
||||
boolean passed = false;
|
||||
|
||||
if (netbuffer->u.clientcfg.challengenum && D_VerifyJoinPasswordChallenge(netbuffer->u.clientcfg.challengenum, netbuffer->u.clientcfg.challengeanswer))
|
||||
passed = true;
|
||||
|
||||
if (!passed)
|
||||
{
|
||||
D_MakeJoinPasswordChallenge(&netbuffer->u.joinchallenge.challengenum, netbuffer->u.joinchallenge.question);
|
||||
|
||||
netbuffer->packettype = PT_JOINCHALLENGE;
|
||||
HSendPacket(node, true, 0, sizeof(joinchallenge_pak));
|
||||
Net_CloseConnection(node);
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (netbuffer->u.clientcfg.needsdownload)
|
||||
{
|
||||
netbuffer->packettype = PT_DOWNLOADFILESOKAY;
|
||||
HSendPacket(node, true, 0, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
// client authorised to join
|
||||
nodewaiting[node] = (UINT8)(netbuffer->u.clientcfg.localplayers - playerpernode[node]);
|
||||
if (!nodeingame[node])
|
||||
|
@ -3590,6 +3792,7 @@ static void HandleConnect(SINT8 node)
|
|||
#ifndef NONET
|
||||
newnode = true;
|
||||
#endif
|
||||
|
||||
SV_AddNode(node);
|
||||
|
||||
/// \note Wait what???
|
||||
|
@ -3745,6 +3948,43 @@ static void HandlePacketFromAwayNode(SINT8 node)
|
|||
Net_CloseConnection(node);
|
||||
break;
|
||||
|
||||
case PT_JOINCHALLENGE:
|
||||
if (server && serverrunning)
|
||||
{ // But wait I thought I'm the server?
|
||||
Net_CloseConnection(node);
|
||||
break;
|
||||
}
|
||||
SERVERONLY
|
||||
if (cl_mode == CL_WAITJOINRESPONSE || cl_mode == CL_WAITDOWNLOADFILESRESPONSE)
|
||||
{
|
||||
cl_challengenum = netbuffer->u.joinchallenge.challengenum;
|
||||
memcpy(cl_challengequestion, netbuffer->u.joinchallenge.question, 16);
|
||||
|
||||
Net_CloseConnection(node|FORCECLOSE); // Don't need to stay connected while challenging
|
||||
|
||||
cl_mode = CL_CHALLENGE;
|
||||
|
||||
switch (cl_challengeattempted)
|
||||
{
|
||||
case 2:
|
||||
// We already sent a correct password, so throw it back up again.
|
||||
D_ComputeChallengeAnswer(cl_challengequestion, cl_challengepassword, cl_challengeanswer);
|
||||
cl_mode = CL_ASKJOIN;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
// We entered the wrong password!
|
||||
S_StartSound(NULL, sfx_s26d);
|
||||
break;
|
||||
|
||||
default:
|
||||
// First entry to the password screen.
|
||||
S_StartSound(NULL, sfx_s224);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case PT_SERVERREFUSE: // Negative response of client join request
|
||||
if (server && serverrunning)
|
||||
{ // But wait I thought I'm the server?
|
||||
|
@ -3773,6 +4013,41 @@ static void HandlePacketFromAwayNode(SINT8 node)
|
|||
}
|
||||
break;
|
||||
|
||||
case PT_DOWNLOADFILESOKAY:
|
||||
if (server && serverrunning)
|
||||
{ // But wait I thought I'm the server?
|
||||
Net_CloseConnection(node);
|
||||
break;
|
||||
}
|
||||
|
||||
SERVERONLY
|
||||
|
||||
// This should've already been checked, but just to be safe...
|
||||
if (!CL_CheckDownloadable())
|
||||
{
|
||||
D_QuitNetGame();
|
||||
CL_Reset();
|
||||
D_StartTitle();
|
||||
M_StartMessage(M_GetText(
|
||||
"You cannot connect to this server\n"
|
||||
"because you cannot download the files\n"
|
||||
"that you are missing from the server.\n\n"
|
||||
"See the console or log file for\n"
|
||||
"more details.\n\n"
|
||||
"Press ESC\n"
|
||||
), NULL, MM_NOTHING);
|
||||
break;
|
||||
}
|
||||
|
||||
if (cl_challengeattempted == 1) // Successful password noise.
|
||||
S_StartSound(NULL, sfx_s221);
|
||||
|
||||
cl_challengeattempted = 2;
|
||||
CONS_Printf("trying to download\n");
|
||||
if (CL_SendRequestFile())
|
||||
cl_mode = CL_DOWNLOADFILES;
|
||||
break;
|
||||
|
||||
case PT_SERVERCFG: // Positive response of client join request
|
||||
{
|
||||
INT32 j;
|
||||
|
@ -3788,6 +4063,9 @@ static void HandlePacketFromAwayNode(SINT8 node)
|
|||
if (cl_mode != CL_WAITJOINRESPONSE)
|
||||
break;
|
||||
|
||||
if (cl_challengeattempted == 1) // Successful password noise.
|
||||
S_StartSound(NULL, sfx_s221);
|
||||
|
||||
if (client)
|
||||
{
|
||||
maketic = gametic = neededtic = (tic_t)LONG(netbuffer->u.servercfg.gametic);
|
||||
|
@ -4353,10 +4631,12 @@ FILESTAMP
|
|||
//Update client ping table from the server.
|
||||
if (client)
|
||||
{
|
||||
INT32 i;
|
||||
UINT8 i;
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
if (playeringame[i])
|
||||
playerpingtable[i] = (tic_t)netbuffer->u.pingtable[i];
|
||||
|
||||
servermaxping = (tic_t)netbuffer->u.pingtable[MAXPLAYERS];
|
||||
}
|
||||
|
||||
break;
|
||||
|
@ -4999,6 +5279,18 @@ void TryRunTics(tic_t realtics)
|
|||
}
|
||||
|
||||
#ifdef NEWPING
|
||||
|
||||
/* Ping Update except better:
|
||||
We call this once per second and check for people's pings. If their ping happens to be too high, we increment some timer and kick them out.
|
||||
If they're not lagging, decrement the timer by 1. Of course, reset all of this if they leave.
|
||||
|
||||
Why do we do that? Well, I'm a person with unfortunately sometimes unstable internet and happen to keep getting kicked very unconveniently for very short high spikes. (700+ ms)
|
||||
Because my spikes are so high, the average ping is exponentially higher too (700s really add up...!) which leads me to getting kicked for a short burst of spiking.
|
||||
With this change here, this doesn't happen anymore as it checks if my ping has been CONSISTENTLY bad for long enough before killing me.
|
||||
*/
|
||||
|
||||
static INT32 pingtimeout[MAXPLAYERS];
|
||||
|
||||
static inline void PingUpdate(void)
|
||||
{
|
||||
INT32 i;
|
||||
|
@ -5019,6 +5311,9 @@ static inline void PingUpdate(void)
|
|||
laggers[i] = true;
|
||||
numlaggers++;
|
||||
}
|
||||
else
|
||||
pingtimeout[i] = 0;
|
||||
|
||||
}
|
||||
|
||||
//kick lagging players... unless everyone but the server's ping sucks.
|
||||
|
@ -5029,12 +5324,20 @@ static inline void PingUpdate(void)
|
|||
{
|
||||
if (playeringame[i] && laggers[i])
|
||||
{
|
||||
XBOXSTATIC char buf[2];
|
||||
pingtimeout[i]++;
|
||||
if (pingtimeout[i] > cv_pingtimeout.value) // ok your net has been bad for too long, you deserve to die.
|
||||
{
|
||||
XBOXSTATIC char buf[2];
|
||||
|
||||
buf[0] = (char)i;
|
||||
buf[1] = KICK_MSG_PING_HIGH;
|
||||
SendNetXCmd(XD_KICK, &buf, 2);
|
||||
pingtimeout[i] = 0;
|
||||
|
||||
buf[0] = (char)i;
|
||||
buf[1] = KICK_MSG_PING_HIGH;
|
||||
SendNetXCmd(XD_KICK, &buf, 2);
|
||||
}
|
||||
}
|
||||
else // you aren't lagging, but you aren't free yet. In case you'll keep spiking, we just make the timer go back down. (Very unstable net must still get kicked).
|
||||
pingtimeout[i] = (pingtimeout[i] == 0 ? 0 : pingtimeout[i]-1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -5049,10 +5352,13 @@ static inline void PingUpdate(void)
|
|||
realpingtable[i] = 0; //Reset each as we go.
|
||||
}
|
||||
|
||||
// send the server's maxping as last element of our ping table. This is useful to let us know when we're about to get kicked.
|
||||
netbuffer->u.pingtable[MAXPLAYERS] = cv_maxping.value;
|
||||
|
||||
//send out our ping packets
|
||||
for (i = 0; i < MAXNETNODES; i++)
|
||||
if (nodeingame[i])
|
||||
HSendPacket(i, true, 0, sizeof(INT32) * MAXPLAYERS);
|
||||
HSendPacket(i, true, 0, sizeof(INT32) * (MAXPLAYERS+1));
|
||||
|
||||
pingmeasurecount = 1; //Reset count
|
||||
}
|
||||
|
@ -5066,7 +5372,7 @@ static void UpdatePingTable(void)
|
|||
INT32 i;
|
||||
if (server)
|
||||
{
|
||||
if (netgame && !(gametime % 255))
|
||||
if (netgame && !(gametime % 35)) // update once per second.
|
||||
PingUpdate();
|
||||
// update node latency values so we can take an average later.
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
|
|
|
@ -13,11 +13,14 @@
|
|||
#ifndef __D_CLISRV__
|
||||
#define __D_CLISRV__
|
||||
|
||||
#include "d_event.h"
|
||||
#include "d_ticcmd.h"
|
||||
#include "d_netcmd.h"
|
||||
#include "tables.h"
|
||||
#include "d_player.h"
|
||||
|
||||
#include "md5.h"
|
||||
|
||||
// Network play related stuff.
|
||||
// There is a data struct that stores network
|
||||
// communication related stuff, and another
|
||||
|
@ -73,6 +76,9 @@ typedef enum
|
|||
PT_CLIENT4MIS,
|
||||
PT_BASICKEEPALIVE,// Keep the network alive during wipes, as tics aren't advanced and NetUpdate isn't called
|
||||
|
||||
PT_JOINCHALLENGE, // You must give a password to joinnnnn
|
||||
PT_DOWNLOADFILESOKAY, // You can download files from the server....
|
||||
|
||||
PT_CANFAIL, // This is kind of a priority. Anything bigger than CANFAIL
|
||||
// allows HSendPacket(*, true, *, *) to return false.
|
||||
// In addition, this packet can't occupy all the available slots.
|
||||
|
@ -283,6 +289,8 @@ typedef struct
|
|||
|
||||
tic_t jointime;
|
||||
|
||||
UINT8 splitscreenindex;
|
||||
|
||||
//player->mo stuff
|
||||
UINT8 hasmo; // Boolean
|
||||
|
||||
|
@ -351,9 +359,21 @@ typedef struct
|
|||
UINT8 version; // Different versions don't work
|
||||
UINT8 subversion; // Contains build version
|
||||
UINT8 localplayers;
|
||||
UINT8 mode;
|
||||
UINT8 needsdownload;
|
||||
UINT8 challengenum; // Non-zero if trying to join with a password attempt
|
||||
UINT8 challengeanswer[MD5_LEN]; // Join challenge
|
||||
} ATTRPACK clientconfig_pak;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
UINT8 challengenum; // Number to send back in join attempt
|
||||
UINT8 question[MD5_LEN]; // Challenge data to be manipulated and answered with
|
||||
} ATTRPACK joinchallenge_pak;
|
||||
|
||||
#define SV_SPEEDMASK 0x03
|
||||
#define SV_DEDICATED 0x40
|
||||
#define SV_PASSWORD 0x80
|
||||
|
||||
#define MAXSERVERNAME 32
|
||||
#define MAXFILENEEDED 915
|
||||
// This packet is too large
|
||||
|
@ -366,7 +386,7 @@ typedef struct
|
|||
UINT8 gametype;
|
||||
UINT8 modifiedgame;
|
||||
UINT8 cheatsenabled;
|
||||
UINT8 isdedicated;
|
||||
UINT8 kartvars; // Previously isdedicated, now appropriated for our own nefarious purposes
|
||||
UINT8 fileneedednum;
|
||||
SINT8 adminplayer;
|
||||
tic_t time;
|
||||
|
@ -445,15 +465,16 @@ typedef struct
|
|||
UINT8 resynchgot; //
|
||||
UINT8 textcmd[MAXTEXTCMD+1]; // 66049 bytes (wut??? 64k??? More like 257 bytes...)
|
||||
filetx_pak filetxpak; // 139 bytes
|
||||
clientconfig_pak clientcfg; // 136 bytes
|
||||
clientconfig_pak clientcfg; // 153 bytes
|
||||
joinchallenge_pak joinchallenge; // 17 bytes
|
||||
serverinfo_pak serverinfo; // 1024 bytes
|
||||
serverrefuse_pak serverrefuse; // 65025 bytes (somehow I feel like those values are garbage...)
|
||||
askinfo_pak askinfo; // 61 bytes
|
||||
msaskinfo_pak msaskinfo; // 22 bytes
|
||||
plrinfo playerinfo[MAXPLAYERS]; // 1152 bytes (I'd say 36~38)
|
||||
plrconfig playerconfig[MAXPLAYERS]; // (up to) 896 bytes (welp they ARE)
|
||||
plrinfo playerinfo[MAXPLAYERS]; // 576 bytes(?)
|
||||
plrconfig playerconfig[MAXPLAYERS]; // (up to) 528 bytes(?)
|
||||
#ifdef NEWPING
|
||||
UINT32 pingtable[MAXPLAYERS]; // 128 bytes
|
||||
UINT32 pingtable[MAXPLAYERS+1]; // 68 bytes
|
||||
#endif
|
||||
} u; // This is needed to pack diff packet types data together
|
||||
} ATTRPACK doomdata_t;
|
||||
|
@ -519,6 +540,7 @@ extern tic_t jointimeout;
|
|||
extern UINT16 pingmeasurecount;
|
||||
extern UINT32 realpingtable[MAXPLAYERS];
|
||||
extern UINT32 playerpingtable[MAXPLAYERS];
|
||||
extern tic_t servermaxping;
|
||||
#endif
|
||||
|
||||
extern consvar_t
|
||||
|
@ -552,6 +574,7 @@ void CL_RemoveSplitscreenPlayer(UINT8 p);
|
|||
void CL_Reset(void);
|
||||
void CL_ClearPlayer(INT32 playernum);
|
||||
void CL_UpdateServerList(boolean internetsearch, INT32 room);
|
||||
boolean CL_Responder(event_t *ev);
|
||||
// Is there a game running
|
||||
boolean Playing(void);
|
||||
|
||||
|
|
113
src/d_main.c
113
src/d_main.c
|
@ -111,6 +111,7 @@ UINT8 window_notinfocus = false;
|
|||
//static INT32 demosequence;
|
||||
static const char *pagename = "MAP1PIC";
|
||||
static char *startupwadfiles[MAX_WADFILES];
|
||||
static char *startuppwads[MAX_WADFILES];
|
||||
|
||||
boolean devparm = false; // started game with -devparm
|
||||
|
||||
|
@ -203,6 +204,8 @@ static inline void D_ModifierKeyResponder(event_t *ev)
|
|||
case KEY_RCTRL: ctrldown |= 0x2; return;
|
||||
case KEY_LALT: altdown |= 0x1; return;
|
||||
case KEY_RALT: altdown |= 0x2; return;
|
||||
case KEY_CAPSLOCK: capslock = !capslock; return;
|
||||
|
||||
default: return;
|
||||
}
|
||||
else if (ev->type == ev_keyup) switch (ev->data1)
|
||||
|
@ -236,6 +239,9 @@ void D_ProcessEvents(void)
|
|||
if (M_ScreenshotResponder(ev))
|
||||
continue; // ate the event
|
||||
|
||||
if (CL_Responder(ev))
|
||||
continue;
|
||||
|
||||
if (gameaction == ga_nothing && gamestate == GS_TITLESCREEN)
|
||||
{
|
||||
if (cht_Responder(ev))
|
||||
|
@ -824,12 +830,12 @@ void D_StartTitle(void)
|
|||
//
|
||||
// D_AddFile
|
||||
//
|
||||
static void D_AddFile(const char *file)
|
||||
static void D_AddFile(const char *file, char **filearray)
|
||||
{
|
||||
size_t pnumwadfiles;
|
||||
char *newfile;
|
||||
|
||||
for (pnumwadfiles = 0; startupwadfiles[pnumwadfiles]; pnumwadfiles++)
|
||||
for (pnumwadfiles = 0; filearray[pnumwadfiles]; pnumwadfiles++)
|
||||
;
|
||||
|
||||
newfile = malloc(strlen(file) + 1);
|
||||
|
@ -839,16 +845,16 @@ static void D_AddFile(const char *file)
|
|||
}
|
||||
strcpy(newfile, file);
|
||||
|
||||
startupwadfiles[pnumwadfiles] = newfile;
|
||||
filearray[pnumwadfiles] = newfile;
|
||||
}
|
||||
|
||||
static inline void D_CleanFile(void)
|
||||
static inline void D_CleanFile(char **filearray)
|
||||
{
|
||||
size_t pnumwadfiles;
|
||||
for (pnumwadfiles = 0; startupwadfiles[pnumwadfiles]; pnumwadfiles++)
|
||||
for (pnumwadfiles = 0; filearray[pnumwadfiles]; pnumwadfiles++)
|
||||
{
|
||||
free(startupwadfiles[pnumwadfiles]);
|
||||
startupwadfiles[pnumwadfiles] = NULL;
|
||||
free(filearray[pnumwadfiles]);
|
||||
filearray[pnumwadfiles] = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -908,9 +914,9 @@ static void IdentifyVersion(void)
|
|||
|
||||
// Load the IWAD
|
||||
if (srb2wad2 != NULL && FIL_ReadFileOK(srb2wad2))
|
||||
D_AddFile(srb2wad2);
|
||||
D_AddFile(srb2wad2, startupwadfiles);
|
||||
else if (srb2wad1 != NULL && FIL_ReadFileOK(srb2wad1))
|
||||
D_AddFile(srb2wad1);
|
||||
D_AddFile(srb2wad1, startupwadfiles);
|
||||
else
|
||||
I_Error("SRB2.SRB/SRB2.WAD not found! Expected in %s, ss files: %s or %s\n", srb2waddir, srb2wad1, srb2wad2);
|
||||
|
||||
|
@ -927,12 +933,12 @@ static void IdentifyVersion(void)
|
|||
D_AddFile(va(pandf,srb2waddir,"patch.dta"));
|
||||
#endif
|
||||
|
||||
D_AddFile(va(pandf,srb2waddir,"gfx.kart"));
|
||||
D_AddFile(va(pandf,srb2waddir,"textures.kart"));
|
||||
D_AddFile(va(pandf,srb2waddir,"chars.kart"));
|
||||
D_AddFile(va(pandf,srb2waddir,"maps.kart"));
|
||||
D_AddFile(va(pandf,srb2waddir,"gfx.kart"), startupwadfiles);
|
||||
D_AddFile(va(pandf,srb2waddir,"textures.kart"), startupwadfiles);
|
||||
D_AddFile(va(pandf,srb2waddir,"chars.kart"), startupwadfiles);
|
||||
D_AddFile(va(pandf,srb2waddir,"maps.kart"), startupwadfiles);
|
||||
#ifdef USE_PATCH_KART
|
||||
D_AddFile(va(pandf,srb2waddir,"patch.kart"));
|
||||
D_AddFile(va(pandf,srb2waddir,"patch.kart"), startupwadfiles);
|
||||
#endif
|
||||
|
||||
#if !defined (HAVE_SDL) || defined (HAVE_MIXER)
|
||||
|
@ -941,7 +947,7 @@ static void IdentifyVersion(void)
|
|||
const char *musicpath = va(pandf,srb2waddir,str);\
|
||||
int ms = W_VerifyNMUSlumps(musicpath); \
|
||||
if (ms == 1) \
|
||||
D_AddFile(musicpath); \
|
||||
D_AddFile(musicpath, startupwadfiles); \
|
||||
else if (ms == 0) \
|
||||
I_Error("File "str" has been modified with non-music/sound lumps"); \
|
||||
}
|
||||
|
@ -1006,9 +1012,12 @@ static inline void D_MakeTitleString(char *s)
|
|||
//
|
||||
void D_SRB2Main(void)
|
||||
{
|
||||
INT32 p;
|
||||
INT32 p, i;
|
||||
char srb2[82]; // srb2 title banner
|
||||
char title[82];
|
||||
lumpinfo_t *lumpinfo;
|
||||
UINT16 wadnum;
|
||||
char *name;
|
||||
|
||||
INT32 pstartmap = 1;
|
||||
boolean autostart = false;
|
||||
|
@ -1160,11 +1169,7 @@ void D_SRB2Main(void)
|
|||
const char *s = M_GetNextParm();
|
||||
|
||||
if (s) // Check for NULL?
|
||||
{
|
||||
if (!W_VerifyNMUSlumps(s))
|
||||
G_SetGameModified(true, false);
|
||||
D_AddFile(s);
|
||||
}
|
||||
D_AddFile(s, startuppwads);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1214,13 +1219,13 @@ void D_SRB2Main(void)
|
|||
|
||||
// load wad, including the main wad file
|
||||
CONS_Printf("W_InitMultipleFiles(): Adding IWAD and main PWADs.\n");
|
||||
if (!W_InitMultipleFiles(startupwadfiles))
|
||||
if (!W_InitMultipleFiles(startupwadfiles, false))
|
||||
#ifdef _DEBUG
|
||||
CONS_Error("A WAD file was not found or not valid.\nCheck the log to see which ones.\n");
|
||||
#else
|
||||
I_Error("A WAD file was not found or not valid.\nCheck the log to see which ones.\n");
|
||||
#endif
|
||||
D_CleanFile();
|
||||
D_CleanFile(startupwadfiles);
|
||||
|
||||
mainwads = 0;
|
||||
|
||||
|
@ -1234,7 +1239,7 @@ void D_SRB2Main(void)
|
|||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_GFX_KART); // gfx.kart
|
||||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_TEXTURES_KART); // textures.kart
|
||||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_CHARS_KART); // chars.kart
|
||||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_MAPS_KART); // maps.kart
|
||||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_MAPS_KART); // maps.kart -- 4 - If you touch this, make sure to touch up the majormods stuff below.
|
||||
#ifdef USE_PATCH_KART
|
||||
mainwads++; W_VerifyFileMD5(mainwads, ASSET_HASH_PATCH_KART); // patch.kart
|
||||
#endif
|
||||
|
@ -1254,6 +1259,66 @@ void D_SRB2Main(void)
|
|||
|
||||
mainwadstally = packetsizetally;
|
||||
|
||||
//
|
||||
// search for maps
|
||||
//
|
||||
for (wadnum = 4; wadnum < 6; wadnum++) // fucking arbitrary numbers
|
||||
{
|
||||
lumpinfo = wadfiles[wadnum]->lumpinfo;
|
||||
for (i = 0; i < wadfiles[wadnum]->numlumps; i++, lumpinfo++)
|
||||
{
|
||||
name = lumpinfo->name;
|
||||
|
||||
if (name[0] == 'M' && name[1] == 'A' && name[2] == 'P') // Ignore the headers
|
||||
{
|
||||
INT16 num;
|
||||
if (name[5] != '\0')
|
||||
continue;
|
||||
num = (INT16)M_MapNumber(name[3], name[4]);
|
||||
|
||||
// we want to record whether this map exists. if it doesn't have a header, we can assume it's not relephant
|
||||
if (num <= NUMMAPS && mapheaderinfo[num - 1])
|
||||
{
|
||||
mapheaderinfo[num - 1]->menuflags |= LF2_EXISTSHACK;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!W_InitMultipleFiles(startuppwads, true))
|
||||
CONS_Error("A PWAD file was not found or not valid.\nCheck the log to see which ones.\n");
|
||||
D_CleanFile(startuppwads);
|
||||
|
||||
//
|
||||
// search for maps... again.
|
||||
//
|
||||
for (wadnum = mainwads+1; wadnum < numwadfiles; wadnum++)
|
||||
{
|
||||
lumpinfo = wadfiles[wadnum]->lumpinfo;
|
||||
for (i = 0; i < wadfiles[wadnum]->numlumps; i++, lumpinfo++)
|
||||
{
|
||||
name = lumpinfo->name;
|
||||
|
||||
if (name[0] == 'M' && name[1] == 'A' && name[2] == 'P') // Ignore the headers
|
||||
{
|
||||
INT16 num;
|
||||
if (name[5] != '\0')
|
||||
continue;
|
||||
num = (INT16)M_MapNumber(name[3], name[4]);
|
||||
|
||||
// we want to record whether this map exists. if it doesn't have a header, we can assume it's not relephant
|
||||
if (num <= NUMMAPS && mapheaderinfo[num - 1])
|
||||
{
|
||||
if (mapheaderinfo[num - 1]->menuflags & LF2_EXISTSHACK)
|
||||
G_SetGameModified(multiplayer, true); // oops, double-defined - no record attack privileges for you
|
||||
mapheaderinfo[num - 1]->menuflags |= LF2_EXISTSHACK;
|
||||
}
|
||||
|
||||
CONS_Printf("%s\n", name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
cht_Init();
|
||||
|
||||
//---------------------------------------------------- READY SCREEN
|
||||
|
|
15
src/d_net.c
15
src/d_net.c
|
@ -821,10 +821,6 @@ static const char *packettypename[NUMPACKETTYPE] =
|
|||
"CLIENTMIS",
|
||||
"CLIENT2CMD",
|
||||
"CLIENT2MIS",
|
||||
"CLIENT3CMD",
|
||||
"CLIENT3MIS",
|
||||
"CLIENT4CMD",
|
||||
"CLIENT4MIS",
|
||||
"NODEKEEPALIVE",
|
||||
"NODEKEEPALIVEMIS",
|
||||
"SERVERTICS",
|
||||
|
@ -841,6 +837,15 @@ static const char *packettypename[NUMPACKETTYPE] =
|
|||
"RESYNCHEND",
|
||||
"RESYNCHGET",
|
||||
|
||||
"CLIENT3CMD",
|
||||
"CLIENT3MIS",
|
||||
"CLIENT4CMD",
|
||||
"CLIENT4MIS",
|
||||
"BASICKEEPALIVE",
|
||||
|
||||
"JOINCHALLENGE",
|
||||
"DOWNLOADFILESOKAY",
|
||||
|
||||
"FILEFRAGMENT",
|
||||
"TEXTCMD",
|
||||
"TEXTCMD2",
|
||||
|
@ -868,7 +873,7 @@ static void DebugPrintpacket(const char *header)
|
|||
break;
|
||||
case PT_CLIENTJOIN:
|
||||
fprintf(debugfile, " number %d mode %d\n", netbuffer->u.clientcfg.localplayers,
|
||||
netbuffer->u.clientcfg.mode);
|
||||
netbuffer->u.clientcfg.needsdownload);
|
||||
break;
|
||||
case PT_SERVERTICS:
|
||||
{
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
#define __D_NET__
|
||||
|
||||
// Max computers in a game
|
||||
#define MAXNETNODES 16
|
||||
#define MAXNETNODES (MAXPLAYERS+4)
|
||||
#define BROADCASTADDR MAXNETNODES
|
||||
#define MAXSPLITSCREENPLAYERS 4 // Max number of players on a single computer
|
||||
#define NETSPLITSCREEN // Kart's splitscreen netgame feature
|
||||
|
|
158
src/d_netcmd.c
158
src/d_netcmd.c
|
@ -169,6 +169,7 @@ static void Got_Verification(UINT8 **cp, INT32 playernum);
|
|||
static void Got_Removal(UINT8 **cp, INT32 playernum);
|
||||
static void Command_Verify_f(void);
|
||||
static void Command_RemoveAdmin_f(void);
|
||||
static void Command_ChangeJoinPassword_f(void);
|
||||
static void Command_MotD_f(void);
|
||||
static void Got_MotD_f(UINT8 **cp, INT32 playernum);
|
||||
|
||||
|
@ -378,6 +379,7 @@ consvar_t cv_kartdebughuddrop = {"kartdebughuddrop", "Off", CV_NETVAR|CV_CHEAT|C
|
|||
|
||||
consvar_t cv_kartdebugcheckpoint = {"kartdebugcheckpoint", "Off", CV_NOSHOWHELP, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_kartdebugnodes = {"kartdebugnodes", "Off", CV_NOSHOWHELP, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_kartdebugcolorize = {"kartdebugcolorize", "Off", CV_NOSHOWHELP, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
static CV_PossibleValue_t votetime_cons_t[] = {{10, "MIN"}, {3600, "MAX"}, {0, NULL}};
|
||||
consvar_t cv_votetime = {"votetime", "20", CV_NETVAR, votetime_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
@ -435,6 +437,14 @@ consvar_t cv_jointimeout = {"jointimeout", "105", CV_CALL|CV_SAVE, nettimeout_co
|
|||
#ifdef NEWPING
|
||||
static CV_PossibleValue_t maxping_cons_t[] = {{0, "MIN"}, {1000, "MAX"}, {0, NULL}};
|
||||
consvar_t cv_maxping = {"maxping", "800", CV_SAVE, maxping_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
static CV_PossibleValue_t pingtimeout_cons_t[] = {{8, "MIN"}, {120, "MAX"}, {0, NULL}};
|
||||
consvar_t cv_pingtimeout = {"pingtimeout", "10", CV_SAVE, pingtimeout_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
// show your ping on the HUD next to framerate. Defaults to warning only (shows up if your ping is > maxping)
|
||||
static CV_PossibleValue_t showping_cons_t[] = {{0, "Off"}, {1, "Always"}, {2, "Warning"}, {0, NULL}};
|
||||
consvar_t cv_showping = {"showping", "Always", CV_SAVE, showping_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
#endif
|
||||
// Intermission time Tails 04-19-2002
|
||||
static CV_PossibleValue_t inttime_cons_t[] = {{0, "MIN"}, {3600, "MAX"}, {0, NULL}};
|
||||
|
@ -525,6 +535,8 @@ void D_RegisterServerCommands(void)
|
|||
RegisterNetXCmd(XD_PICKVOTE, Got_PickVotecmd);
|
||||
|
||||
// Remote Administration
|
||||
CV_RegisterVar(&cv_dummyjoinpassword);
|
||||
COM_AddCommand("joinpassword", Command_ChangeJoinPassword_f);
|
||||
COM_AddCommand("password", Command_Changepassword_f);
|
||||
RegisterNetXCmd(XD_LOGIN, Got_Login);
|
||||
COM_AddCommand("login", Command_Login_f); // useful in dedicated to kick off remote admin
|
||||
|
@ -664,6 +676,8 @@ void D_RegisterServerCommands(void)
|
|||
CV_RegisterVar(&cv_sleep);
|
||||
#ifdef NEWPING
|
||||
CV_RegisterVar(&cv_maxping);
|
||||
CV_RegisterVar(&cv_pingtimeout);
|
||||
CV_RegisterVar(&cv_showping);
|
||||
#endif
|
||||
|
||||
#ifdef SEENAMES
|
||||
|
@ -807,6 +821,8 @@ void D_RegisterClientCommands(void)
|
|||
//CV_RegisterVar(&cv_alwaysfreelook2);
|
||||
//CV_RegisterVar(&cv_chasefreelook);
|
||||
//CV_RegisterVar(&cv_chasefreelook2);
|
||||
CV_RegisterVar(&cv_showfocuslost);
|
||||
CV_RegisterVar(&cv_pauseifunfocused);
|
||||
|
||||
// g_input.c
|
||||
CV_RegisterVar(&cv_turnaxis);
|
||||
|
@ -3504,6 +3520,7 @@ static void D_MD5PasswordPass(const UINT8 *buffer, size_t len, const char *salt,
|
|||
|
||||
if (len > 256-sl)
|
||||
len = 256-sl;
|
||||
|
||||
memcpy(tmpbuf, buffer, len);
|
||||
memmove(&tmpbuf[len], salt, sl);
|
||||
//strcpy(&tmpbuf[len], salt);
|
||||
|
@ -3517,7 +3534,7 @@ static void D_MD5PasswordPass(const UINT8 *buffer, size_t len, const char *salt,
|
|||
}
|
||||
|
||||
#define BASESALT "basepasswordstorage"
|
||||
static UINT8 adminpassmd5[16];
|
||||
static UINT8 adminpassmd5[MD5_LEN];
|
||||
static boolean adminpasswordset = false;
|
||||
|
||||
void D_SetPassword(const char *pw)
|
||||
|
@ -3556,7 +3573,7 @@ static void Command_Login_f(void)
|
|||
// If we have no MD5 support then completely disable XD_LOGIN responses for security.
|
||||
CONS_Alert(CONS_NOTICE, "Remote administration commands are not supported in this build.\n");
|
||||
#else
|
||||
XBOXSTATIC UINT8 finalmd5[16];
|
||||
XBOXSTATIC UINT8 finalmd5[MD5_LEN];
|
||||
const char *pw;
|
||||
|
||||
if (!netgame)
|
||||
|
@ -3579,11 +3596,11 @@ static void Command_Login_f(void)
|
|||
D_MD5PasswordPass((const UINT8 *)pw, strlen(pw), BASESALT, &finalmd5);
|
||||
|
||||
// Do the final pass to get the comparison the server will come up with
|
||||
D_MD5PasswordPass(finalmd5, 16, va("PNUM%02d", consoleplayer), &finalmd5);
|
||||
D_MD5PasswordPass(finalmd5, MD5_LEN, va("PNUM%02d", consoleplayer), &finalmd5);
|
||||
|
||||
CONS_Printf(M_GetText("Sending login... (Notice only given if password is correct.)\n"));
|
||||
|
||||
SendNetXCmd(XD_LOGIN, finalmd5, 16);
|
||||
SendNetXCmd(XD_LOGIN, finalmd5, MD5_LEN);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -3594,9 +3611,9 @@ static void Got_Login(UINT8 **cp, INT32 playernum)
|
|||
(void)cp;
|
||||
(void)playernum;
|
||||
#else
|
||||
UINT8 sentmd5[16], finalmd5[16];
|
||||
UINT8 sentmd5[MD5_LEN], finalmd5[MD5_LEN];
|
||||
|
||||
READMEM(*cp, sentmd5, 16);
|
||||
READMEM(*cp, sentmd5, MD5_LEN);
|
||||
|
||||
if (client)
|
||||
return;
|
||||
|
@ -3608,9 +3625,9 @@ static void Got_Login(UINT8 **cp, INT32 playernum)
|
|||
}
|
||||
|
||||
// Do the final pass to compare with the sent md5
|
||||
D_MD5PasswordPass(adminpassmd5, 16, va("PNUM%02d", playernum), &finalmd5);
|
||||
D_MD5PasswordPass(adminpassmd5, MD5_LEN, va("PNUM%02d", playernum), &finalmd5);
|
||||
|
||||
if (!memcmp(sentmd5, finalmd5, 16))
|
||||
if (!memcmp(sentmd5, finalmd5, MD5_LEN))
|
||||
{
|
||||
CONS_Printf(M_GetText("%s passed authentication.\n"), player_names[playernum]);
|
||||
COM_BufInsertText(va("promote %d\n", playernum)); // do this immediately
|
||||
|
@ -3779,6 +3796,131 @@ static void Got_Removal(UINT8 **cp, INT32 playernum)
|
|||
CONS_Printf(M_GetText("You are no longer a server administrator.\n"));
|
||||
}
|
||||
|
||||
// Join password stuff
|
||||
consvar_t cv_dummyjoinpassword = {"dummyjoinpassword", "", CV_HIDEN|CV_NOSHOWHELP|CV_PASSWORD, NULL, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
#define NUMJOINCHALLENGES 32
|
||||
static UINT8 joinpassmd5[MD5_LEN+1];
|
||||
boolean joinpasswordset = false;
|
||||
static UINT8 joinpasschallenges[NUMJOINCHALLENGES][MD5_LEN];
|
||||
static tic_t joinpasschallengeson[NUMJOINCHALLENGES];
|
||||
|
||||
boolean D_IsJoinPasswordOn(void)
|
||||
{
|
||||
return joinpasswordset;
|
||||
}
|
||||
|
||||
static inline void GetChallengeAnswer(UINT8 *question, UINT8 *passwordmd5, UINT8 *answer)
|
||||
{
|
||||
D_MD5PasswordPass(question, MD5_LEN, (char *) passwordmd5, answer);
|
||||
}
|
||||
|
||||
void D_ComputeChallengeAnswer(UINT8 *question, const char *pw, UINT8 *answer)
|
||||
{
|
||||
static UINT8 passwordmd5[MD5_LEN+1];
|
||||
|
||||
memset(passwordmd5, 0x00, MD5_LEN+1);
|
||||
D_MD5PasswordPass((const UINT8 *)pw, strlen(pw), BASESALT, &passwordmd5);
|
||||
GetChallengeAnswer(question, passwordmd5, answer);
|
||||
}
|
||||
|
||||
void D_SetJoinPassword(const char *pw)
|
||||
{
|
||||
memset(joinpassmd5, 0x00, MD5_LEN+1);
|
||||
D_MD5PasswordPass((const UINT8 *)pw, strlen(pw), BASESALT, &joinpassmd5);
|
||||
joinpasswordset = true;
|
||||
}
|
||||
|
||||
boolean D_VerifyJoinPasswordChallenge(UINT8 num, UINT8 *answer)
|
||||
{
|
||||
boolean passed = false;
|
||||
|
||||
num %= NUMJOINCHALLENGES;
|
||||
|
||||
//@TODO use a constant-time memcmp....
|
||||
if (joinpasschallengeson[num] > 0 && memcmp(answer, joinpasschallenges[num], MD5_LEN) == 0)
|
||||
passed = true;
|
||||
|
||||
// Wipe and reset the challenge so that it can't be tried against again, as a small measure against brute-force attacks.
|
||||
memset(joinpasschallenges[num], 0x00, MD5_LEN);
|
||||
joinpasschallengeson[num] = 0;
|
||||
|
||||
return passed;
|
||||
}
|
||||
|
||||
void D_MakeJoinPasswordChallenge(UINT8 *num, UINT8 *question)
|
||||
{
|
||||
size_t i;
|
||||
|
||||
for (i = 0; i < NUMJOINCHALLENGES; i++)
|
||||
{
|
||||
(*num) = M_RandomKey(NUMJOINCHALLENGES);
|
||||
|
||||
if (joinpasschallengeson[(*num)] == 0)
|
||||
break;
|
||||
}
|
||||
|
||||
if (joinpasschallengeson[(*num)] > 0)
|
||||
{
|
||||
// Ugh, all challenges are (probably) taken. Let's find the oldest one and overwrite it.
|
||||
tic_t oldesttic = INT32_MAX;
|
||||
|
||||
for (i = 0; i < NUMJOINCHALLENGES; i++)
|
||||
{
|
||||
if (joinpasschallengeson[i] < oldesttic)
|
||||
{
|
||||
(*num) = i;
|
||||
oldesttic = joinpasschallengeson[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
joinpasschallengeson[(*num)] = I_GetTime();
|
||||
|
||||
memset(question, 0x00, MD5_LEN);
|
||||
for (i = 0; i < MD5_LEN; i++)
|
||||
question[i] = M_RandomByte();
|
||||
|
||||
// Store the answer in memory. What was the question again?
|
||||
GetChallengeAnswer(question, joinpassmd5, joinpasschallenges[(*num)]);
|
||||
|
||||
// This ensures that num is always non-zero and will be valid when used for the answer
|
||||
if ((*num) == 0)
|
||||
(*num) = NUMJOINCHALLENGES;
|
||||
}
|
||||
|
||||
// Remote Administration
|
||||
static void Command_ChangeJoinPassword_f(void)
|
||||
{
|
||||
#ifdef NOMD5
|
||||
// If we have no MD5 support then completely disable XD_LOGIN responses for security.
|
||||
CONS_Alert(CONS_NOTICE, "Remote administration commands are not supported in this build.\n");
|
||||
#else
|
||||
if (client) // cannot change remotely
|
||||
{
|
||||
CONS_Printf(M_GetText("Only the server can use this.\n"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (COM_Argc() != 2)
|
||||
{
|
||||
CONS_Printf(M_GetText("joinpassword <password>: set a password to join the server\nUse -remove to disable the password.\n"));
|
||||
return;
|
||||
}
|
||||
|
||||
if (strcmp(COM_Argv(1), "-remove") == 0)
|
||||
{
|
||||
joinpasswordset = false;
|
||||
CONS_Printf(M_GetText("Join password removed.\n"));
|
||||
}
|
||||
else
|
||||
{
|
||||
D_SetJoinPassword(COM_Argv(1));
|
||||
CONS_Printf(M_GetText("Join password set.\n"));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void Command_MotD_f(void)
|
||||
{
|
||||
size_t i, j;
|
||||
|
|
|
@ -126,7 +126,7 @@ extern consvar_t cv_karteliminatelast;
|
|||
extern consvar_t cv_votetime;
|
||||
|
||||
extern consvar_t cv_kartdebugitem, cv_kartdebugamount, cv_kartdebugshrink, cv_kartdebugdistribution, cv_kartdebughuddrop;
|
||||
extern consvar_t cv_kartdebugcheckpoint, cv_kartdebugnodes;
|
||||
extern consvar_t cv_kartdebugcheckpoint, cv_kartdebugnodes, cv_kartdebugcolorize;
|
||||
|
||||
extern consvar_t cv_itemfinder;
|
||||
|
||||
|
@ -145,6 +145,8 @@ extern consvar_t cv_specialrings, cv_powerstones, cv_matchboxes, cv_competitionb
|
|||
|
||||
#ifdef NEWPING
|
||||
extern consvar_t cv_maxping;
|
||||
extern consvar_t cv_pingtimeout;
|
||||
extern consvar_t cv_showping;
|
||||
#endif
|
||||
|
||||
extern consvar_t cv_skipmapcheck;
|
||||
|
@ -246,6 +248,14 @@ void RemoveAdminPlayer(INT32 playernum);
|
|||
void ItemFinder_OnChange(void);
|
||||
void D_SetPassword(const char *pw);
|
||||
|
||||
extern consvar_t cv_dummyjoinpassword;
|
||||
extern boolean joinpasswordset;
|
||||
boolean D_IsJoinPasswordOn(void);
|
||||
void D_ComputeChallengeAnswer(UINT8 *question, const char *pw, UINT8 *answer);
|
||||
void D_SetJoinPassword(const char *pw);
|
||||
boolean D_VerifyJoinPasswordChallenge(UINT8 num, UINT8 *answer);
|
||||
void D_MakeJoinPasswordChallenge(UINT8 *num, UINT8 *question);
|
||||
|
||||
// used for the player setup menu
|
||||
UINT8 CanChangeSkin(INT32 playernum);
|
||||
|
||||
|
|
|
@ -32,13 +32,7 @@
|
|||
// Extra abilities/settings for skins (combinable stuff)
|
||||
typedef enum
|
||||
{
|
||||
SF_SUPER = 1, // Can turn super in singleplayer/co-op mode.
|
||||
SF_SUPERANIMS = 1<<1, // If super, use the super sonic animations
|
||||
SF_SUPERSPIN = 1<<2, // Should spin frames be played while super?
|
||||
SF_HIRES = 1<<3, // Draw the sprite 2x as small?
|
||||
SF_NOSKID = 1<<4, // No skid particles etc
|
||||
SF_NOSPEEDADJUST = 1<<5, // Skin-specific version of disablespeedadjust
|
||||
SF_RUNONWATER = 1<<6, // Run on top of water FOFs?
|
||||
SF_HIRES = 1, // Draw the sprite 2x as small?
|
||||
} skinflags_t;
|
||||
|
||||
//Primary and secondary skin abilities
|
||||
|
@ -275,6 +269,7 @@ typedef enum
|
|||
k_nextcheck, // Next checkpoint distance; for p_user.c (was "pw_ncd")
|
||||
k_waypoint, // Waypoints.
|
||||
k_starpostwp, // Temporarily stores player waypoint for... some reason. Used when respawning and finishing.
|
||||
k_starpostflip, // the last starpost we hit requires flipping?
|
||||
k_respawn, // Timer for the DEZ laser respawn effect
|
||||
k_dropdash, // Charge up for respawn Drop Dash
|
||||
|
||||
|
@ -354,6 +349,7 @@ typedef enum
|
|||
k_getsparks, // Disable drift sparks at low speed, JUST enough to give acceleration the actual headstart above speed
|
||||
k_jawztargetdelay, // Delay for Jawz target switching, to make it less twitchy
|
||||
k_spectatewait, // How long have you been waiting as a spectator
|
||||
k_growcancel, // Hold the item button down to cancel Grow
|
||||
|
||||
NUMKARTSTUFF
|
||||
} kartstufftype_t;
|
||||
|
@ -571,6 +567,8 @@ typedef struct player_s
|
|||
UINT8 bot;
|
||||
|
||||
tic_t jointime; // Timer when player joins game to change skin/color
|
||||
|
||||
UINT8 splitscreenindex;
|
||||
#ifdef HWRENDER
|
||||
fixed_t fovadd; // adjust FOV for hw rendering
|
||||
#endif
|
||||
|
|
280
src/dehacked.c
280
src/dehacked.c
|
@ -3108,11 +3108,6 @@ static void readmaincfg(MYFILE *f)
|
|||
if (creditscutscene > 128)
|
||||
creditscutscene = 128;
|
||||
}
|
||||
else if (fastcmp(word, "DISABLESPEEDADJUST"))
|
||||
{
|
||||
DEH_WriteUndoline(word, va("%d", disableSpeedAdjust), UNDO_NONE);
|
||||
disableSpeedAdjust = (value || word2[0] == 'T' || word2[0] == 'Y');
|
||||
}
|
||||
else if (fastcmp(word, "NUMDEMOS"))
|
||||
{
|
||||
DEH_WriteUndoline(word, va("%d", numDemos), UNDO_NONE);
|
||||
|
@ -7155,6 +7150,13 @@ static const char *const STATE_LIST[] = { // array length left dynamic for sanit
|
|||
"S_KARMAFIREWORK4",
|
||||
"S_KARMAFIREWORKTRAIL",
|
||||
|
||||
// Opaque smoke version, to prevent lag
|
||||
"S_OPAQUESMOKE1",
|
||||
"S_OPAQUESMOKE2",
|
||||
"S_OPAQUESMOKE3",
|
||||
"S_OPAQUESMOKE4",
|
||||
"S_OPAQUESMOKE5",
|
||||
|
||||
#ifdef SEENAMES
|
||||
"S_NAMECHECK",
|
||||
#endif
|
||||
|
@ -8139,89 +8141,164 @@ static const char *const ML_LIST[16] = {
|
|||
// This DOES differ from r_draw's Color_Names, unfortunately.
|
||||
// Also includes Super colors
|
||||
static const char *COLOR_ENUMS[] = { // Rejigged for Kart.
|
||||
"NONE", // 00 // SKINCOLOR_NONE
|
||||
"WHITE", // 01 // SKINCOLOR_WHITE
|
||||
"SILVER", // 02 // SKINCOLOR_SILVER
|
||||
"GREY", // 03 // SKINCOLOR_GREY
|
||||
"NICKEL", // 04 // SKINCOLOR_NICKEL
|
||||
"BLACK", // 05 // SKINCOLOR_BLACK
|
||||
"SEPIA", // 06 // SKINCOLOR_SEPIA
|
||||
"BEIGE", // 07 // SKINCOLOR_BEIGE
|
||||
"BROWN", // 08 // SKINCOLOR_BROWN
|
||||
"LEATHER", // 09 // SKINCOLOR_LEATHER
|
||||
"SALMON", // 10 // SKINCOLOR_SALMON
|
||||
"PINK", // 11 // SKINCOLOR_PINK
|
||||
"ROSE", // 12 // SKINCOLOR_ROSE
|
||||
"RUBY", // 13 // SKINCOLOR_RUBY
|
||||
"RASPBERRY", // 14 // SKINCOLOR_RASPBERRY
|
||||
"RED", // 15 // SKINCOLOR_RED
|
||||
"CRIMSON", // 16 // SKINCOLOR_CRIMSON
|
||||
"KETCHUP", // 17 // SKINCOLOR_KETCHUP
|
||||
"DAWN", // 18 // SKINCOLOR_DAWN
|
||||
"CREAMSICLE", // 19 // SKINCOLOR_CREAMSICLE
|
||||
"ORANGE", // 20 // SKINCOLOR_ORANGE
|
||||
"PUMPKIN", // 21 // SKINCOLOR_PUMPKIN
|
||||
"ROSEWOOD", // 22 // SKINCOLOR_ROSEWOOD
|
||||
"BURGUNDY", // 23 // SKINCOLOR_BURGUNDY
|
||||
"TANGERINE", // 24 // SKINCOLOR_TANGERINE
|
||||
"PEACH", // 25 // SKINCOLOR_PEACH
|
||||
"CARAMEL", // 26 // SKINCOLOR_CARAMEL
|
||||
"GOLD", // 27 // SKINCOLOR_GOLD
|
||||
"BRONZE", // 28 // SKINCOLOR_BRONZE
|
||||
"YELLOW", // 29 // SKINCOLOR_YELLOW
|
||||
"MUSTARD", // 30 // SKINCOLOR_MUSTARD
|
||||
"OLIVE", // 31 // SKINCOLOR_OLIVE
|
||||
"VOMIT", // 32 // SKINCOLOR_VOMIT
|
||||
"GARDEN", // 33 // SKINCOLOR_GARDEN
|
||||
"LIME", // 34 // SKINCOLOR_LIME
|
||||
"TEA", // 35 // SKINCOLOR_TEA
|
||||
"PISTACHIO", // 36 // SKINCOLOR_PISTACHIO
|
||||
"ROBOHOOD", // 37 // SKINCOLOR_ROBOHOOD
|
||||
"MOSS", // 38 // SKINCOLOR_MOSS
|
||||
"MINT", // 39 // SKINCOLOR_MINT
|
||||
"GREEN", // 40 // SKINCOLOR_GREEN
|
||||
"PINETREE", // 41 // SKINCOLOR_PINETREE
|
||||
"EMERALD", // 42 // SKINCOLOR_EMERALD
|
||||
"SWAMP", // 43 // SKINCOLOR_SWAMP
|
||||
"DREAM", // 44 // SKINCOLOR_DREAM
|
||||
"AQUA", // 45 // SKINCOLOR_AQUA
|
||||
"TEAL", // 46 // SKINCOLOR_TEAL
|
||||
"CYAN", // 47 // SKINCOLOR_CYAN
|
||||
"JAWZ", // 48 // SKINCOLOR_JAWZ
|
||||
"CERULEAN", // 49 // SKINCOLOR_CERULEAN
|
||||
"NAVY", // 50 // SKINCOLOR_NAVY
|
||||
"SLATE", // 51 // SKINCOLOR_SLATE
|
||||
"STEEL", // 52 // SKINCOLOR_STEEL
|
||||
"JET", // 53 // SKINCOLOR_JET
|
||||
"SAPPHIRE", // 54 // SKINCOLOR_SAPPHIRE
|
||||
"PERIWINKLE", // 55 // SKINCOLOR_PERIWINKLE
|
||||
"BLUE", // 56 // SKINCOLOR_BLUE
|
||||
"BLUEBERRY", // 57 // SKINCOLOR_BLUEBERRY
|
||||
"DUSK", // 58 // SKINCOLOR_DUSK
|
||||
"PURPLE", // 59 // SKINCOLOR_PURPLE
|
||||
"LAVENDER", // 60 // SKINCOLOR_LAVENDER
|
||||
"BYZANTIUM", // 61 // SKINCOLOR_BYZANTIUM
|
||||
"POMEGRANATE", // 62 // SKINCOLOR_POMEGRANATE
|
||||
"LILAC", // 63 // SKINCOLOR_LILAC
|
||||
"NONE", // SKINCOLOR_NONE
|
||||
"WHITE", // SKINCOLOR_WHITE
|
||||
"SILVER", // SKINCOLOR_SILVER
|
||||
"GREY", // SKINCOLOR_GREY
|
||||
"NICKEL", // SKINCOLOR_NICKEL
|
||||
"BLACK", // SKINCOLOR_BLACK
|
||||
"FAIRY", // SKINCOLOR_FAIRY
|
||||
"POPCORN", // SKINCOLOR_POPCORN
|
||||
"SEPIA", // SKINCOLOR_SEPIA
|
||||
"BEIGE", // SKINCOLOR_BEIGE
|
||||
"BROWN", // SKINCOLOR_BROWN
|
||||
"LEATHER", // SKINCOLOR_LEATHER
|
||||
"SALMON", // SKINCOLOR_SALMON
|
||||
"PINK", // SKINCOLOR_PINK
|
||||
"ROSE", // SKINCOLOR_ROSE
|
||||
"BRICK", // SKINCOLOR_BRICK
|
||||
"RUBY", // SKINCOLOR_RUBY
|
||||
"RASPBERRY", // SKINCOLOR_RASPBERRY
|
||||
"CHERRY", // SKINCOLOR_CHERRY
|
||||
"RED", // SKINCOLOR_RED
|
||||
"CRIMSON", // SKINCOLOR_CRIMSON
|
||||
"MAROON", // SKINCOLOR_MAROON
|
||||
"FLAME", // SKINCOLOR_FLAME
|
||||
"SCARLET", // SKINCOLOR_SCARLET
|
||||
"KETCHUP", // SKINCOLOR_KETCHUP
|
||||
"DAWN", // SKINCOLOR_DAWN
|
||||
"SUNSET", // SKINCOLOR_SUNSET
|
||||
"CREAMSICLE", // SKINCOLOR_CREAMSICLE
|
||||
"ORANGE", // SKINCOLOR_ORANGE
|
||||
"PUMPKIN", // SKINCOLOR_PUMPKIN
|
||||
"ROSEWOOD", // SKINCOLOR_ROSEWOOD
|
||||
"BURGUNDY", // SKINCOLOR_BURGUNDY
|
||||
"TANGERINE", // SKINCOLOR_TANGERINE
|
||||
"PEACH", // SKINCOLOR_PEACH
|
||||
"CARAMEL", // SKINCOLOR_CARAMEL
|
||||
"CREAM", // SKINCOLOR_CREAM
|
||||
"GOLD", // SKINCOLOR_GOLD
|
||||
"ROYAL", // SKINCOLOR_ROYAL
|
||||
"BRONZE", // SKINCOLOR_BRONZE
|
||||
"COPPER", // SKINCOLOR_COPPER
|
||||
"YELLOW", // SKINCOLOR_YELLOW
|
||||
"MUSTARD", // SKINCOLOR_MUSTARD
|
||||
"OLIVE", // SKINCOLOR_OLIVE
|
||||
"VOMIT", // SKINCOLOR_VOMIT
|
||||
"GARDEN", // SKINCOLOR_GARDEN
|
||||
"LIME", // SKINCOLOR_LIME
|
||||
"HANDHELD", // SKINCOLOR_HANDHELD
|
||||
"TEA", // SKINCOLOR_TEA
|
||||
"PISTACHIO", // SKINCOLOR_PISTACHIO
|
||||
"MOSS", // SKINCOLOR_MOSS
|
||||
"CAMOUFLAGE", // SKINCOLOR_CAMOUFLAGE
|
||||
"ROBOHOOD", // SKINCOLOR_ROBOHOOD
|
||||
"MINT", // SKINCOLOR_MINT
|
||||
"GREEN", // SKINCOLOR_GREEN
|
||||
"PINETREE", // SKINCOLOR_PINETREE
|
||||
"EMERALD", // SKINCOLOR_EMERALD
|
||||
"SWAMP", // SKINCOLOR_SWAMP
|
||||
"DREAM", // SKINCOLOR_DREAM
|
||||
"PLAGUE", // SKINCOLOR_PLAGUE
|
||||
"ALGAE", // SKINCOLOR_ALGAE
|
||||
"CARIBBEAN", // SKINCOLOR_CARIBBEAN
|
||||
"AQUA", // SKINCOLOR_AQUA
|
||||
"TEAL", // SKINCOLOR_TEAL
|
||||
"CYAN", // SKINCOLOR_CYAN
|
||||
"JAWZ", // SKINCOLOR_JAWZ
|
||||
"CERULEAN", // SKINCOLOR_CERULEAN
|
||||
"NAVY", // SKINCOLOR_NAVY
|
||||
"PLATINUM", // SKINCOLOR_PLATINUM
|
||||
"SLATE", // SKINCOLOR_SLATE
|
||||
"STEEL", // SKINCOLOR_STEEL
|
||||
"RUST", // SKINCOLOR_RUST
|
||||
"JET", // SKINCOLOR_JET
|
||||
"SAPPHIRE", // SKINCOLOR_SAPPHIRE
|
||||
"PERIWINKLE", // SKINCOLOR_PERIWINKLE
|
||||
"BLUE", // SKINCOLOR_BLUE
|
||||
"BLUEBERRY", // SKINCOLOR_BLUEBERRY
|
||||
"NOVA", // SKINCOLOR_NOVA
|
||||
"PASTEL", // SKINCOLOR_PASTEL
|
||||
"MOONSLAM", // SKINCOLOR_MOONSLAM
|
||||
"ULTRAVIOLET", // SKINCOLOR_ULTRAVIOLET
|
||||
"DUSK", // SKINCOLOR_DUSK
|
||||
"BUBBLEGUM", // SKINCOLOR_BUBBLEGUM
|
||||
"PURPLE", // SKINCOLOR_PURPLE
|
||||
"FUCHSIA", // SKINCOLOR_FUCHSIA
|
||||
"TOXIC", // SKINCOLOR_TOXIC
|
||||
"MAUVE", // SKINCOLOR_MAUVE
|
||||
"LAVENDER", // SKINCOLOR_LAVENDER
|
||||
"BYZANTIUM", // SKINCOLOR_BYZANTIUM
|
||||
"POMEGRANATE", // SKINCOLOR_POMEGRANATE
|
||||
"LILAC", // SKINCOLOR_LILAC
|
||||
|
||||
// Super special awesome Super flashing colors!
|
||||
"SUPER1", // SKINCOLOR_SUPER1
|
||||
"SUPER2", // SKINCOLOR_SUPER2,
|
||||
"SUPER3", // SKINCOLOR_SUPER3,
|
||||
"SUPER4", // SKINCOLOR_SUPER4,
|
||||
"SUPER5", // SKINCOLOR_SUPER5,
|
||||
// Super Tails
|
||||
"TSUPER1", // SKINCOLOR_TSUPER1,
|
||||
"TSUPER2", // SKINCOLOR_TSUPER2,
|
||||
"TSUPER3", // SKINCOLOR_TSUPER3,
|
||||
"TSUPER4", // SKINCOLOR_TSUPER4,
|
||||
"TSUPER5", // SKINCOLOR_TSUPER5,
|
||||
// Super Knuckles
|
||||
"KSUPER1", // SKINCOLOR_KSUPER1,
|
||||
"KSUPER2", // SKINCOLOR_KSUPER2,
|
||||
"KSUPER3", // SKINCOLOR_KSUPER3,
|
||||
"KSUPER4", // SKINCOLOR_KSUPER4,
|
||||
"KSUPER5" // SKINCOLOR_KSUPER5,
|
||||
|
||||
|
||||
|
||||
|
||||
// Special super colors
|
||||
// Super Sonic Yellow
|
||||
"SUPER1", // SKINCOLOR_SUPER1
|
||||
"SUPER2", // SKINCOLOR_SUPER2,
|
||||
"SUPER3", // SKINCOLOR_SUPER3,
|
||||
"SUPER4", // SKINCOLOR_SUPER4,
|
||||
"SUPER5", // SKINCOLOR_SUPER5,
|
||||
|
||||
// Super Tails Orange
|
||||
"TSUPER1", // SKINCOLOR_TSUPER1,
|
||||
"TSUPER2", // SKINCOLOR_TSUPER2,
|
||||
"TSUPER3", // SKINCOLOR_TSUPER3,
|
||||
"TSUPER4", // SKINCOLOR_TSUPER4,
|
||||
"TSUPER5", // SKINCOLOR_TSUPER5,
|
||||
|
||||
// Super Knuckles Red
|
||||
"KSUPER1", // SKINCOLOR_KSUPER1,
|
||||
"KSUPER2", // SKINCOLOR_KSUPER2,
|
||||
"KSUPER3", // SKINCOLOR_KSUPER3,
|
||||
"KSUPER4", // SKINCOLOR_KSUPER4,
|
||||
"KSUPER5", // SKINCOLOR_KSUPER5,
|
||||
|
||||
// Hyper Sonic Pink
|
||||
"PSUPER1", // SKINCOLOR_PSUPER1,
|
||||
"PSUPER2", // SKINCOLOR_PSUPER2,
|
||||
"PSUPER3", // SKINCOLOR_PSUPER3,
|
||||
"PSUPER4", // SKINCOLOR_PSUPER4,
|
||||
"PSUPER5", // SKINCOLOR_PSUPER5,
|
||||
|
||||
// Hyper Sonic Blue
|
||||
"BSUPER1", // SKINCOLOR_BSUPER1,
|
||||
"BSUPER2", // SKINCOLOR_BSUPER2,
|
||||
"BSUPER3", // SKINCOLOR_BSUPER3,
|
||||
"BSUPER4", // SKINCOLOR_BSUPER4,
|
||||
"BSUPER5", // SKINCOLOR_BSUPER5,
|
||||
|
||||
// Aqua Super
|
||||
"ASUPER1", // SKINCOLOR_ASUPER1,
|
||||
"ASUPER2", // SKINCOLOR_ASUPER2,
|
||||
"ASUPER3", // SKINCOLOR_ASUPER3,
|
||||
"ASUPER4", // SKINCOLOR_ASUPER4,
|
||||
"ASUPER5", // SKINCOLOR_ASUPER5,
|
||||
|
||||
// Hyper Sonic Green
|
||||
"GSUPER1", // SKINCOLOR_GSUPER1,
|
||||
"GSUPER2", // SKINCOLOR_GSUPER2,
|
||||
"GSUPER3", // SKINCOLOR_GSUPER3,
|
||||
"GSUPER4", // SKINCOLOR_GSUPER4,
|
||||
"GSUPER5", // SKINCOLOR_GSUPER5,
|
||||
|
||||
// Hyper Sonic White
|
||||
"WSUPER1", // SKINCOLOR_WSUPER1,
|
||||
"WSUPER2", // SKINCOLOR_WSUPER2,
|
||||
"WSUPER3", // SKINCOLOR_WSUPER3,
|
||||
"WSUPER4", // SKINCOLOR_WSUPER4,
|
||||
"WSUPER5", // SKINCOLOR_WSUPER5,
|
||||
|
||||
// Creamy Super (Shadow?)
|
||||
"CSUPER1", // SKINCOLOR_CSUPER1,
|
||||
"CSUPER2", // SKINCOLOR_CSUPER2,
|
||||
"CSUPER3", // SKINCOLOR_CSUPER3,
|
||||
"CSUPER4", // SKINCOLOR_CSUPER4,
|
||||
"CSUPER5" // SKINCOLOR_CSUPER5,
|
||||
};
|
||||
|
||||
static const char *const POWERS_LIST[] = {
|
||||
|
@ -8259,6 +8336,7 @@ static const char *const POWERS_LIST[] = {
|
|||
"INGOOP" // In goop
|
||||
};
|
||||
|
||||
#ifdef HAVE_BLUA
|
||||
static const char *const KARTSTUFF_LIST[] = {
|
||||
"POSITION",
|
||||
"OLDPOSITION",
|
||||
|
@ -8267,6 +8345,7 @@ static const char *const KARTSTUFF_LIST[] = {
|
|||
"NEXTCHECK",
|
||||
"WAYPOINT",
|
||||
"STARPOSTWP",
|
||||
"STARPOSTFLIP",
|
||||
"RESPAWN",
|
||||
"DROPDASH",
|
||||
|
||||
|
@ -8340,8 +8419,10 @@ static const char *const KARTSTUFF_LIST[] = {
|
|||
"ITEMBLINKMODE",
|
||||
"GETSPARKS",
|
||||
"JAWZTARGETDELAY",
|
||||
"SPECTATEWAIT"
|
||||
"SPECTATEWAIT",
|
||||
"GROWCANCEL"
|
||||
};
|
||||
#endif
|
||||
|
||||
static const char *const HUDITEMS_LIST[] = {
|
||||
"LIVESNAME",
|
||||
|
@ -8564,13 +8645,7 @@ struct {
|
|||
{"RW_RAIL",RW_RAIL},
|
||||
|
||||
// Character flags (skinflags_t)
|
||||
{"SF_SUPER",SF_SUPER},
|
||||
{"SF_SUPERANIMS",SF_SUPERANIMS},
|
||||
{"SF_SUPERSPIN",SF_SUPERSPIN},
|
||||
{"SF_HIRES",SF_HIRES},
|
||||
{"SF_NOSKID",SF_NOSKID},
|
||||
{"SF_NOSPEEDADJUST",SF_NOSPEEDADJUST},
|
||||
{"SF_RUNONWATER",SF_RUNONWATER},
|
||||
|
||||
// Character abilities!
|
||||
// Primary
|
||||
|
@ -9047,20 +9122,6 @@ static powertype_t get_power(const char *word)
|
|||
return pw_invulnerability;
|
||||
}
|
||||
|
||||
static kartstufftype_t get_kartstuff(const char *word)
|
||||
{ // Returns the vlaue of k_ enumerations
|
||||
kartstufftype_t i;
|
||||
if (*word >= '0' && *word <= '9')
|
||||
return atoi(word);
|
||||
if (fastncmp("K_",word,2))
|
||||
word += 2; // take off the k_
|
||||
for (i = 0; i < NUMKARTSTUFF; i++)
|
||||
if (fastcmp(word, KARTSTUFF_LIST[i]))
|
||||
return i;
|
||||
deh_warning("Couldn't find power named 'k_%s'",word);
|
||||
return k_position;
|
||||
}
|
||||
|
||||
/// \todo Make ANY of this completely over-the-top math craziness obey the order of operations.
|
||||
static fixed_t op_mul(fixed_t a, fixed_t b) { return a*b; }
|
||||
static fixed_t op_div(fixed_t a, fixed_t b) { return a/b; }
|
||||
|
@ -9857,6 +9918,9 @@ static inline int lib_getenum(lua_State *L)
|
|||
} else if (fastcmp(word,"indirectitemcooldown")) {
|
||||
lua_pushinteger(L, indirectitemcooldown);
|
||||
return 1;
|
||||
} else if (fastcmp(word,"hyubgone")) {
|
||||
lua_pushinteger(L, hyubgone);
|
||||
return 1;
|
||||
} else if (fastcmp(word,"thwompsactive")) {
|
||||
lua_pushboolean(L, thwompsactive);
|
||||
return 1;
|
||||
|
|
|
@ -94,6 +94,9 @@ void I_FinishUpdate (void)
|
|||
if (cv_ticrate.value)
|
||||
SCR_DisplayTicRate();
|
||||
|
||||
if (cv_showping.value && netgame && consoleplayer != serverplayer)
|
||||
SCR_DisplayLocalPing();
|
||||
|
||||
//blast it to the screen
|
||||
// this code sucks
|
||||
//memcpy(dascreen,screens[0],screenwidth*screenheight);
|
||||
|
|
|
@ -150,9 +150,9 @@ extern FILE *logstream;
|
|||
// we use comprevision and compbranch instead.
|
||||
#else
|
||||
#define VERSION 100 // Game version
|
||||
#define SUBVERSION 3 // more precise version number
|
||||
#define VERSIONSTRING "v1.0.3"
|
||||
#define VERSIONSTRINGW L"v1.0.3"
|
||||
#define SUBVERSION 4 // more precise version number
|
||||
#define VERSIONSTRING "v1.0.4"
|
||||
#define VERSIONSTRINGW L"v1.0.4"
|
||||
// Hey! If you change this, add 1 to the MODVERSION below!
|
||||
// Otherwise we can't force updates!
|
||||
#endif
|
||||
|
@ -221,7 +221,7 @@ extern FILE *logstream;
|
|||
// it's only for detection of the version the player is using so the MS can alert them of an update.
|
||||
// Only set it higher, not lower, obviously.
|
||||
// Note that we use this to help keep internal testing in check; this is why v2.1.0 is not version "1".
|
||||
#define MODVERSION 3
|
||||
#define MODVERSION 4
|
||||
|
||||
// Filter consvars by version
|
||||
// To version config.cfg, MAJOREXECVERSION is set equal to MODVERSION automatically.
|
||||
|
@ -244,7 +244,7 @@ extern FILE *logstream;
|
|||
// NOTE: it needs more than this to increase the number of players...
|
||||
|
||||
#define MAXPLAYERS 16
|
||||
#define MAXSKINS 64
|
||||
#define MAXSKINS 128
|
||||
#define PLAYERSMASK (MAXPLAYERS-1)
|
||||
#define MAXPLAYERNAME 21
|
||||
|
||||
|
@ -256,6 +256,8 @@ typedef enum
|
|||
SKINCOLOR_GREY,
|
||||
SKINCOLOR_NICKEL,
|
||||
SKINCOLOR_BLACK,
|
||||
SKINCOLOR_FAIRY,
|
||||
SKINCOLOR_POPCORN,
|
||||
SKINCOLOR_SEPIA,
|
||||
SKINCOLOR_BEIGE,
|
||||
SKINCOLOR_BROWN,
|
||||
|
@ -263,12 +265,18 @@ typedef enum
|
|||
SKINCOLOR_SALMON,
|
||||
SKINCOLOR_PINK,
|
||||
SKINCOLOR_ROSE,
|
||||
SKINCOLOR_BRICK,
|
||||
SKINCOLOR_RUBY,
|
||||
SKINCOLOR_RASPBERRY,
|
||||
SKINCOLOR_CHERRY,
|
||||
SKINCOLOR_RED,
|
||||
SKINCOLOR_CRIMSON,
|
||||
SKINCOLOR_MAROON,
|
||||
SKINCOLOR_FLAME,
|
||||
SKINCOLOR_SCARLET,
|
||||
SKINCOLOR_KETCHUP,
|
||||
SKINCOLOR_DAWN,
|
||||
SKINCOLOR_SUNSET,
|
||||
SKINCOLOR_CREAMSICLE,
|
||||
SKINCOLOR_ORANGE,
|
||||
SKINCOLOR_PUMPKIN,
|
||||
|
@ -277,68 +285,130 @@ typedef enum
|
|||
SKINCOLOR_TANGERINE,
|
||||
SKINCOLOR_PEACH,
|
||||
SKINCOLOR_CARAMEL,
|
||||
SKINCOLOR_CREAM,
|
||||
SKINCOLOR_GOLD,
|
||||
SKINCOLOR_ROYAL,
|
||||
SKINCOLOR_BRONZE,
|
||||
SKINCOLOR_COPPER,
|
||||
SKINCOLOR_YELLOW,
|
||||
SKINCOLOR_MUSTARD,
|
||||
SKINCOLOR_OLIVE,
|
||||
SKINCOLOR_VOMIT,
|
||||
SKINCOLOR_GARDEN,
|
||||
SKINCOLOR_LIME,
|
||||
SKINCOLOR_HANDHELD,
|
||||
SKINCOLOR_TEA,
|
||||
SKINCOLOR_PISTACHIO,
|
||||
SKINCOLOR_ROBOHOOD,
|
||||
SKINCOLOR_MOSS,
|
||||
SKINCOLOR_CAMOUFLAGE,
|
||||
SKINCOLOR_ROBOHOOD,
|
||||
SKINCOLOR_MINT,
|
||||
SKINCOLOR_GREEN,
|
||||
SKINCOLOR_PINETREE,
|
||||
SKINCOLOR_EMERALD,
|
||||
SKINCOLOR_SWAMP,
|
||||
SKINCOLOR_DREAM,
|
||||
SKINCOLOR_PLAGUE,
|
||||
SKINCOLOR_ALGAE,
|
||||
SKINCOLOR_CARIBBEAN,
|
||||
SKINCOLOR_AQUA,
|
||||
SKINCOLOR_TEAL,
|
||||
SKINCOLOR_CYAN,
|
||||
SKINCOLOR_JAWZ, // Oni's torment
|
||||
SKINCOLOR_CERULEAN,
|
||||
SKINCOLOR_NAVY,
|
||||
SKINCOLOR_PLATINUM,
|
||||
SKINCOLOR_SLATE,
|
||||
SKINCOLOR_STEEL,
|
||||
SKINCOLOR_RUST,
|
||||
SKINCOLOR_JET,
|
||||
SKINCOLOR_SAPPHIRE, // sweet mother, i cannot weave - slender aphrodite has overcome me with longing for a girl
|
||||
SKINCOLOR_PERIWINKLE,
|
||||
SKINCOLOR_BLUE,
|
||||
SKINCOLOR_BLUEBERRY,
|
||||
SKINCOLOR_NOVA,
|
||||
SKINCOLOR_PASTEL,
|
||||
SKINCOLOR_MOONSLAM,
|
||||
SKINCOLOR_ULTRAVIOLET,
|
||||
SKINCOLOR_DUSK,
|
||||
SKINCOLOR_BUBBLEGUM,
|
||||
SKINCOLOR_PURPLE,
|
||||
SKINCOLOR_FUCHSIA,
|
||||
SKINCOLOR_TOXIC,
|
||||
SKINCOLOR_MAUVE,
|
||||
SKINCOLOR_LAVENDER,
|
||||
SKINCOLOR_BYZANTIUM,
|
||||
SKINCOLOR_POMEGRANATE,
|
||||
SKINCOLOR_LILAC,
|
||||
|
||||
// Careful! MAXSKINCOLORS cannot be greater than 0x40 -- Which it is now.
|
||||
// "Careful! MAXSKINCOLORS cannot be greater than 0x40 -- Which it is now."
|
||||
// (This comment is a dirty liar! This is only limited by the integer type, so 255 for UINT8.)
|
||||
MAXSKINCOLORS,
|
||||
|
||||
// Super special awesome Super flashing colors!
|
||||
// Super Sonic Yellow
|
||||
SKINCOLOR_SUPER1 = MAXSKINCOLORS,
|
||||
SKINCOLOR_SUPER2,
|
||||
SKINCOLOR_SUPER3,
|
||||
SKINCOLOR_SUPER4,
|
||||
SKINCOLOR_SUPER5,
|
||||
|
||||
// Super Tails
|
||||
// Super Tails Orange
|
||||
SKINCOLOR_TSUPER1,
|
||||
SKINCOLOR_TSUPER2,
|
||||
SKINCOLOR_TSUPER3,
|
||||
SKINCOLOR_TSUPER4,
|
||||
SKINCOLOR_TSUPER5,
|
||||
|
||||
// Super Knuckles
|
||||
// Super Knuckles Red
|
||||
SKINCOLOR_KSUPER1,
|
||||
SKINCOLOR_KSUPER2,
|
||||
SKINCOLOR_KSUPER3,
|
||||
SKINCOLOR_KSUPER4,
|
||||
SKINCOLOR_KSUPER5,
|
||||
|
||||
// Hyper Sonic Pink
|
||||
SKINCOLOR_PSUPER1,
|
||||
SKINCOLOR_PSUPER2,
|
||||
SKINCOLOR_PSUPER3,
|
||||
SKINCOLOR_PSUPER4,
|
||||
SKINCOLOR_PSUPER5,
|
||||
|
||||
// Hyper Sonic Blue
|
||||
SKINCOLOR_BSUPER1,
|
||||
SKINCOLOR_BSUPER2,
|
||||
SKINCOLOR_BSUPER3,
|
||||
SKINCOLOR_BSUPER4,
|
||||
SKINCOLOR_BSUPER5,
|
||||
|
||||
// Aqua Super
|
||||
SKINCOLOR_ASUPER1,
|
||||
SKINCOLOR_ASUPER2,
|
||||
SKINCOLOR_ASUPER3,
|
||||
SKINCOLOR_ASUPER4,
|
||||
SKINCOLOR_ASUPER5,
|
||||
|
||||
// Hyper Sonic Green
|
||||
SKINCOLOR_GSUPER1,
|
||||
SKINCOLOR_GSUPER2,
|
||||
SKINCOLOR_GSUPER3,
|
||||
SKINCOLOR_GSUPER4,
|
||||
SKINCOLOR_GSUPER5,
|
||||
|
||||
// Hyper Sonic White
|
||||
SKINCOLOR_WSUPER1,
|
||||
SKINCOLOR_WSUPER2,
|
||||
SKINCOLOR_WSUPER3,
|
||||
SKINCOLOR_WSUPER4,
|
||||
SKINCOLOR_WSUPER5,
|
||||
|
||||
// Creamy Super (Shadow?)
|
||||
SKINCOLOR_CSUPER1,
|
||||
SKINCOLOR_CSUPER2,
|
||||
SKINCOLOR_CSUPER3,
|
||||
SKINCOLOR_CSUPER4,
|
||||
SKINCOLOR_CSUPER5,
|
||||
|
||||
MAXTRANSLATIONS
|
||||
} skincolors_t;
|
||||
|
||||
|
@ -472,13 +542,17 @@ INT32 I_GetKey(void);
|
|||
#define max(x, y) (((x) > (y)) ? (x) : (y))
|
||||
#endif
|
||||
|
||||
#ifndef M_PIl
|
||||
#define M_PIl 3.1415926535897932384626433832795029L
|
||||
#endif
|
||||
|
||||
// Floating point comparison epsilons from float.h
|
||||
#ifndef FLT_EPSILON
|
||||
#define FLT_EPSILON 1.1920928955078125e-7f
|
||||
#endif
|
||||
|
||||
#ifndef DBL_EPSILON
|
||||
#define DBL_EPSILON 2.2204460492503131e-16
|
||||
#define DBL_EPSILON 2.2204460492503131e-16l
|
||||
#endif
|
||||
|
||||
// An assert-type mechanism.
|
||||
|
|
|
@ -57,7 +57,6 @@ extern boolean modifiedgame;
|
|||
extern boolean majormods;
|
||||
extern UINT16 mainwads;
|
||||
extern boolean savemoddata; // This mod saves time/emblem data.
|
||||
extern boolean disableSpeedAdjust; // Don't alter the duration of player states if true
|
||||
extern boolean imcontinuing; // Temporary flag while continuing
|
||||
extern boolean metalrecording;
|
||||
|
||||
|
@ -469,6 +468,7 @@ extern boolean comeback;
|
|||
extern SINT8 battlewanted[4];
|
||||
extern tic_t wantedcalcdelay;
|
||||
extern tic_t indirectitemcooldown;
|
||||
extern tic_t hyubgone;
|
||||
extern tic_t mapreset;
|
||||
extern UINT8 nospectategrief;
|
||||
extern boolean thwompsactive;
|
||||
|
|
|
@ -611,7 +611,7 @@ void F_CreditDrawer(void)
|
|||
|
||||
if (credits_pics[i].colorize != SKINCOLOR_NONE)
|
||||
{
|
||||
colormap = R_GetTranslationColormap(TC_RAINBOW, credits_pics[i].colorize, 0);
|
||||
colormap = R_GetTranslationColormap(TC_RAINBOW, credits_pics[i].colorize, GTC_MENUCACHE);
|
||||
sc = FRACUNIT; // quick hack so I don't have to add another field to credits_pics
|
||||
}
|
||||
|
||||
|
@ -643,16 +643,34 @@ void F_CreditDrawer(void)
|
|||
if (((y>>FRACBITS) * vid.dupy) > vid.height)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void F_CreditTicker(void)
|
||||
{
|
||||
// "Simulate" the drawing of the credits so that dedicated mode doesn't get stuck
|
||||
UINT16 i;
|
||||
fixed_t y = (80<<FRACBITS) - 5*(animtimer<<FRACBITS)/8;
|
||||
|
||||
// Draw credits text on top
|
||||
for (i = 0; credits[i]; i++)
|
||||
{
|
||||
switch(credits[i][0])
|
||||
{
|
||||
case 0: y += 80<<FRACBITS; break;
|
||||
case 1: y += 30<<FRACBITS; break;
|
||||
default: y += 12<<FRACBITS; break;
|
||||
}
|
||||
if (FixedMul(y,vid.dupy) > vid.height)
|
||||
break;
|
||||
}
|
||||
|
||||
// Do this here rather than in the drawer you doofus! (this is why dedicated mode broke at credits)
|
||||
if (!credits[i] && y <= 120<<FRACBITS && !finalecount)
|
||||
{
|
||||
timetonext = 5*TICRATE+1;
|
||||
finalecount = 5*TICRATE;
|
||||
}
|
||||
}
|
||||
|
||||
void F_CreditTicker(void)
|
||||
{
|
||||
if (timetonext)
|
||||
timetonext--;
|
||||
else
|
||||
|
@ -1103,6 +1121,10 @@ void F_StartWaitingPlayers(void)
|
|||
finalecount = 0;
|
||||
|
||||
randskin = M_RandomKey(numskins);
|
||||
|
||||
if (waitcolormap)
|
||||
Z_Free(waitcolormap);
|
||||
|
||||
waitcolormap = R_GetTranslationColormap(randskin, skins[randskin].prefcolor, 0);
|
||||
|
||||
for (i = 0; i < 2; i++)
|
||||
|
|
196
src/g_game.c
196
src/g_game.c
|
@ -92,7 +92,6 @@ boolean majormods = false; // Set if Lua/Gameplay SOC/replacement map has been a
|
|||
boolean savemoddata = false;
|
||||
UINT8 paused;
|
||||
UINT8 modeattacking = ATTACKING_NONE;
|
||||
boolean disableSpeedAdjust = true;
|
||||
boolean imcontinuing = false;
|
||||
boolean runemeraldmanager = false;
|
||||
|
||||
|
@ -267,6 +266,7 @@ SINT8 pickedvote; // What vote the host rolls
|
|||
SINT8 battlewanted[4]; // WANTED players in battle, worth x2 points
|
||||
tic_t wantedcalcdelay; // Time before it recalculates WANTED
|
||||
tic_t indirectitemcooldown; // Cooldown before any more Shrink, SPB, or any other item that works indirectly is awarded
|
||||
tic_t hyubgone; // Cooldown before hyudoro is allowed to be rerolled
|
||||
tic_t mapreset; // Map reset delay when enough players have joined an empty game
|
||||
UINT8 nospectategrief; // How many players need to be in-game to eliminate last; for preventing spectate griefing
|
||||
boolean thwompsactive; // Thwomps activate on lap 2
|
||||
|
@ -437,6 +437,9 @@ consvar_t cv_chatbacktint = {"chatbacktint", "On", CV_SAVE, CV_OnOff, NULL, 0, N
|
|||
static CV_PossibleValue_t consolechat_cons_t[] = {{0, "Window"}, {1, "Console"}, {2, "Window (Hidden)"}, {0, NULL}};
|
||||
consvar_t cv_consolechat = {"chatmode", "Window", CV_SAVE, consolechat_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
// Pause game upon window losing focus
|
||||
consvar_t cv_pauseifunfocused = {"pauseifunfocused", "Yes", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
// Display song credits
|
||||
consvar_t cv_songcredits = {"songcredits", "On", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
|
@ -1820,80 +1823,6 @@ static INT32 spectatedelay, spectatedelay2, spectatedelay3, spectatedelay4 = 0;
|
|||
//
|
||||
boolean G_Responder(event_t *ev)
|
||||
{
|
||||
// allow spy mode changes even during the demo
|
||||
if (gamestate == GS_LEVEL && ev->type == ev_keydown
|
||||
&& (ev->data1 == KEY_F12 || ev->data1 == gamecontrol[gc_viewpoint][0] || ev->data1 == gamecontrol[gc_viewpoint][1]))
|
||||
{
|
||||
if (splitscreen || !netgame)
|
||||
displayplayer = consoleplayer;
|
||||
else
|
||||
{
|
||||
UINT8 i = 0; // spy mode
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
{
|
||||
displayplayer++;
|
||||
if (displayplayer == MAXPLAYERS)
|
||||
displayplayer = 0;
|
||||
|
||||
if (displayplayer == consoleplayer)
|
||||
break; // End loop
|
||||
|
||||
if (!playeringame[displayplayer])
|
||||
continue;
|
||||
|
||||
if (players[displayplayer].spectator)
|
||||
continue;
|
||||
|
||||
// SRB2Kart: Only go through players who are actually playing
|
||||
if (players[displayplayer].exiting)
|
||||
continue;
|
||||
|
||||
if (players[displayplayer].pflags & PF_TIMEOVER)
|
||||
continue;
|
||||
|
||||
// I don't know if we want this actually, but I'll humor the suggestion anyway
|
||||
if (G_BattleGametype())
|
||||
{
|
||||
if (players[displayplayer].kartstuff[k_bumper] <= 0)
|
||||
continue;
|
||||
}
|
||||
|
||||
// SRB2Kart: we have no team-based modes, YET...
|
||||
/*if (G_GametypeHasTeams())
|
||||
{
|
||||
if (players[consoleplayer].ctfteam
|
||||
&& players[displayplayer].ctfteam != players[consoleplayer].ctfteam)
|
||||
continue;
|
||||
}
|
||||
else if (gametype == GT_HIDEANDSEEK)
|
||||
{
|
||||
if (players[consoleplayer].pflags & PF_TAGIT)
|
||||
continue;
|
||||
}
|
||||
// Other Tag-based gametypes?
|
||||
else if (G_TagGametype())
|
||||
{
|
||||
if (!players[consoleplayer].spectator
|
||||
&& (players[consoleplayer].pflags & PF_TAGIT) != (players[displayplayer].pflags & PF_TAGIT))
|
||||
continue;
|
||||
}
|
||||
else if (G_GametypeHasSpectators() && G_BattleGametype())
|
||||
{
|
||||
if (!players[consoleplayer].spectator)
|
||||
continue;
|
||||
}*/
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
// change statusbar also if playing back demo
|
||||
if (singledemo)
|
||||
ST_changeDemoView();
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
// any other key pops up menu if in demos
|
||||
if (gameaction == ga_nothing && !singledemo &&
|
||||
((demoplayback && !modeattacking && !titledemo) || gamestate == GS_TITLESCREEN))
|
||||
|
@ -1971,6 +1900,80 @@ boolean G_Responder(event_t *ev)
|
|||
if (HU_Responder(ev))
|
||||
return true; // chat ate the event
|
||||
|
||||
// allow spy mode changes even during the demo
|
||||
if (gamestate == GS_LEVEL && ev->type == ev_keydown
|
||||
&& (ev->data1 == KEY_F12 || ev->data1 == gamecontrol[gc_viewpoint][0] || ev->data1 == gamecontrol[gc_viewpoint][1]))
|
||||
{
|
||||
if (splitscreen || !netgame)
|
||||
displayplayer = consoleplayer;
|
||||
else
|
||||
{
|
||||
UINT8 i = 0; // spy mode
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
{
|
||||
displayplayer++;
|
||||
if (displayplayer == MAXPLAYERS)
|
||||
displayplayer = 0;
|
||||
|
||||
if (displayplayer == consoleplayer)
|
||||
break; // End loop
|
||||
|
||||
if (!playeringame[displayplayer])
|
||||
continue;
|
||||
|
||||
if (players[displayplayer].spectator)
|
||||
continue;
|
||||
|
||||
// SRB2Kart: Only go through players who are actually playing
|
||||
if (players[displayplayer].exiting)
|
||||
continue;
|
||||
|
||||
if (players[displayplayer].pflags & PF_TIMEOVER)
|
||||
continue;
|
||||
|
||||
// I don't know if we want this actually, but I'll humor the suggestion anyway
|
||||
if (G_BattleGametype())
|
||||
{
|
||||
if (players[displayplayer].kartstuff[k_bumper] <= 0)
|
||||
continue;
|
||||
}
|
||||
|
||||
// SRB2Kart: we have no team-based modes, YET...
|
||||
/*if (G_GametypeHasTeams())
|
||||
{
|
||||
if (players[consoleplayer].ctfteam
|
||||
&& players[displayplayer].ctfteam != players[consoleplayer].ctfteam)
|
||||
continue;
|
||||
}
|
||||
else if (gametype == GT_HIDEANDSEEK)
|
||||
{
|
||||
if (players[consoleplayer].pflags & PF_TAGIT)
|
||||
continue;
|
||||
}
|
||||
// Other Tag-based gametypes?
|
||||
else if (G_TagGametype())
|
||||
{
|
||||
if (!players[consoleplayer].spectator
|
||||
&& (players[consoleplayer].pflags & PF_TAGIT) != (players[displayplayer].pflags & PF_TAGIT))
|
||||
continue;
|
||||
}
|
||||
else if (G_GametypeHasSpectators() && G_BattleGametype())
|
||||
{
|
||||
if (!players[consoleplayer].spectator)
|
||||
continue;
|
||||
}*/
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
// change statusbar also if playing back demo
|
||||
if (singledemo)
|
||||
ST_changeDemoView();
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
// update keys current state
|
||||
G_MapEventsToControls(ev);
|
||||
|
||||
|
@ -2162,7 +2165,7 @@ void G_Ticker(boolean run)
|
|||
G_CopyTiccmd(cmd, &netcmds[buf][i], 1);
|
||||
|
||||
// Use the leveltime sent in the player's ticcmd to determine control lag
|
||||
cmd->latency = modeattacking ? 0 : min((leveltime & 0xFF) - cmd->latency, MAXPREDICTTICS-1); //@TODO add a cvar to allow setting this max
|
||||
cmd->latency = modeattacking ? 0 : min(((leveltime & 0xFF) - cmd->latency) & 0xFF, MAXPREDICTTICS-1); //@TODO add a cvar to allow setting this max
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2357,6 +2360,7 @@ void G_PlayerReborn(INT32 player)
|
|||
UINT8 skincolor;
|
||||
INT32 skin;
|
||||
tic_t jointime;
|
||||
UINT8 splitscreenindex;
|
||||
boolean spectator;
|
||||
INT16 bot;
|
||||
SINT8 pity;
|
||||
|
@ -2371,6 +2375,7 @@ void G_PlayerReborn(INT32 player)
|
|||
INT32 bumper;
|
||||
INT32 comebackpoints;
|
||||
INT32 wanted;
|
||||
INT32 respawnflip;
|
||||
boolean songcredit = false;
|
||||
|
||||
score = players[player].score;
|
||||
|
@ -2380,6 +2385,7 @@ void G_PlayerReborn(INT32 player)
|
|||
ctfteam = players[player].ctfteam;
|
||||
exiting = players[player].exiting;
|
||||
jointime = players[player].jointime;
|
||||
splitscreenindex = players[player].splitscreenindex;
|
||||
spectator = players[player].spectator;
|
||||
pflags = (players[player].pflags & (PF_TIMEOVER|PF_FLIPCAM|PF_TAGIT|PF_TAGGED|PF_ANALOGMODE|PF_WANTSTOJOIN));
|
||||
|
||||
|
@ -2411,6 +2417,7 @@ void G_PlayerReborn(INT32 player)
|
|||
starposty = players[player].starposty;
|
||||
starpostz = players[player].starpostz;
|
||||
starpostnum = players[player].starpostnum;
|
||||
respawnflip = players[player].kartstuff[k_starpostflip]; //SRB2KART
|
||||
starpostangle = players[player].starpostangle;
|
||||
jumpfactor = players[player].jumpfactor;
|
||||
thokitem = players[player].thokitem;
|
||||
|
@ -2476,6 +2483,7 @@ void G_PlayerReborn(INT32 player)
|
|||
p->pflags = pflags;
|
||||
p->ctfteam = ctfteam;
|
||||
p->jointime = jointime;
|
||||
p->splitscreenindex = splitscreenindex;
|
||||
p->spectator = spectator;
|
||||
|
||||
// save player config truth reborn
|
||||
|
@ -2530,6 +2538,7 @@ void G_PlayerReborn(INT32 player)
|
|||
p->kartstuff[k_comebacktimer] = comebacktime;
|
||||
p->kartstuff[k_wanted] = wanted;
|
||||
p->kartstuff[k_eggmanblame] = -1;
|
||||
p->kartstuff[k_starpostflip] = respawnflip;
|
||||
|
||||
// Don't do anything immediately
|
||||
p->pflags |= PF_USEDOWN;
|
||||
|
@ -4947,7 +4956,8 @@ void G_WriteGhostTic(mobj_t *ghost)
|
|||
// GZT_XYZ is only useful if you've moved 256 FRACUNITS or more in a single tic.
|
||||
if (abs(ghost->x-oldghost.x) > MAXMOM
|
||||
|| abs(ghost->y-oldghost.y) > MAXMOM
|
||||
|| abs(ghost->z-oldghost.z) > MAXMOM)
|
||||
|| abs(ghost->z-oldghost.z) > MAXMOM
|
||||
|| (leveltime & 255) == 1) // Hack to enable slightly nicer resyncing
|
||||
{
|
||||
oldghost.x = ghost->x;
|
||||
oldghost.y = ghost->y;
|
||||
|
@ -4961,8 +4971,8 @@ void G_WriteGhostTic(mobj_t *ghost)
|
|||
{
|
||||
// For moving normally:
|
||||
// Store one full byte of movement, plus one byte of fractional movement.
|
||||
INT16 momx = (INT16)((ghost->x-oldghost.x)>>8);
|
||||
INT16 momy = (INT16)((ghost->y-oldghost.y)>>8);
|
||||
INT16 momx = (INT16)((ghost->x-oldghost.x + (1<<4))>>8);
|
||||
INT16 momy = (INT16)((ghost->y-oldghost.y + (1<<4))>>8);
|
||||
if (momx != oldghost.momx
|
||||
|| momy != oldghost.momy)
|
||||
{
|
||||
|
@ -4972,7 +4982,7 @@ void G_WriteGhostTic(mobj_t *ghost)
|
|||
WRITEINT16(demo_p,momx);
|
||||
WRITEINT16(demo_p,momy);
|
||||
}
|
||||
momx = (INT16)((ghost->z-oldghost.z)>>8);
|
||||
momx = (INT16)((ghost->z-oldghost.z + (1<<4))>>8);
|
||||
if (momx != oldghost.momz)
|
||||
{
|
||||
oldghost.momz = momx;
|
||||
|
@ -5076,8 +5086,9 @@ void G_WriteGhostTic(mobj_t *ghost)
|
|||
void G_ConsGhostTic(void)
|
||||
{
|
||||
UINT8 ziptic;
|
||||
UINT16 px,py,pz,gx,gy,gz;
|
||||
fixed_t px,py,pz,gx,gy,gz;
|
||||
mobj_t *testmo;
|
||||
fixed_t syncleeway;
|
||||
boolean nightsfail = false;
|
||||
|
||||
if (!demo_p || !demo_start)
|
||||
|
@ -5094,6 +5105,7 @@ void G_ConsGhostTic(void)
|
|||
oldghost.x = READFIXED(demo_p);
|
||||
oldghost.y = READFIXED(demo_p);
|
||||
oldghost.z = READFIXED(demo_p);
|
||||
syncleeway = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5107,6 +5119,7 @@ void G_ConsGhostTic(void)
|
|||
oldghost.x += oldghost.momx;
|
||||
oldghost.y += oldghost.momy;
|
||||
oldghost.z += oldghost.momz;
|
||||
syncleeway = FRACUNIT;
|
||||
}
|
||||
if (ziptic & GZT_ANGLE)
|
||||
demo_p++;
|
||||
|
@ -5172,14 +5185,14 @@ void G_ConsGhostTic(void)
|
|||
}
|
||||
|
||||
// Re-synchronise
|
||||
px = testmo->x>>FRACBITS;
|
||||
py = testmo->y>>FRACBITS;
|
||||
pz = testmo->z>>FRACBITS;
|
||||
gx = oldghost.x>>FRACBITS;
|
||||
gy = oldghost.y>>FRACBITS;
|
||||
gz = oldghost.z>>FRACBITS;
|
||||
px = testmo->x;
|
||||
py = testmo->y;
|
||||
pz = testmo->z;
|
||||
gx = oldghost.x;
|
||||
gy = oldghost.y;
|
||||
gz = oldghost.z;
|
||||
|
||||
if (nightsfail || px != gx || py != gy || pz != gz)
|
||||
if (nightsfail || abs(px-gx) > syncleeway || abs(py-gy) > syncleeway || abs(pz-gz) > syncleeway)
|
||||
{
|
||||
if (demosynced)
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Demo playback has desynced!\n"));
|
||||
|
@ -5290,17 +5303,16 @@ void G_GhostTicker(void)
|
|||
INT32 type = -1;
|
||||
if (g->mo->skin)
|
||||
{
|
||||
skin_t *skin = (skin_t *)g->mo->skin;
|
||||
switch (ziptic & EZT_THOKMASK)
|
||||
{
|
||||
case EZT_THOK:
|
||||
type = skin->thokitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].painchance : (UINT32)skin->thokitem;
|
||||
type = (UINT32)mobjinfo[MT_PLAYER].painchance;
|
||||
break;
|
||||
case EZT_SPIN:
|
||||
type = skin->spinitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].damage : (UINT32)skin->spinitem;
|
||||
type = (UINT32)mobjinfo[MT_PLAYER].damage;
|
||||
break;
|
||||
case EZT_REV:
|
||||
type = skin->revitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].raisestate : (UINT32)skin->revitem;
|
||||
type = (UINT32)mobjinfo[MT_PLAYER].raisestate;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -56,6 +56,7 @@ extern INT16 rw_maximums[NUM_WEAPONS];
|
|||
// used in game menu
|
||||
extern consvar_t cv_chatwidth, cv_chatnotifications, cv_chatheight, cv_chattime, cv_consolechat, cv_chatbacktint, cv_chatspamprotection/*, cv_compactscoreboard*/;
|
||||
extern consvar_t cv_songcredits;
|
||||
extern consvar_t cv_pauseifunfocused;
|
||||
//extern consvar_t cv_crosshair, cv_crosshair2, cv_crosshair3, cv_crosshair4;
|
||||
extern consvar_t cv_invertmouse/*, cv_alwaysfreelook, cv_chasefreelook, cv_mousemove*/;
|
||||
extern consvar_t cv_invertmouse2/*, cv_alwaysfreelook2, cv_chasefreelook2, cv_mousemove2*/;
|
||||
|
|
|
@ -1239,6 +1239,8 @@ void G_ClearAllControlKeys(void)
|
|||
{
|
||||
G_ClearControlKeys(gamecontrol, i);
|
||||
G_ClearControlKeys(gamecontrolbis, i);
|
||||
G_ClearControlKeys(gamecontrol3, i);
|
||||
G_ClearControlKeys(gamecontrol4, i);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -201,7 +201,7 @@ static polyvertex_t *fracdivline(fdivline_t *bsp, polyvertex_t *v1,
|
|||
// (do not accept hit with the extensions)
|
||||
num = (v2x - v1x)*v2dy + (v1y - v2y)*v2dx;
|
||||
frac = num / den;
|
||||
if (frac < 0.0 || frac > 1.0)
|
||||
if (frac < 0.0l || frac > 1.0l)
|
||||
return NULL;
|
||||
|
||||
// now get the frac along the BSP line
|
||||
|
|
|
@ -72,6 +72,7 @@
|
|||
#include "../v_video.h"
|
||||
#include "hw_clip.h"
|
||||
#include "hw_glob.h"
|
||||
#include "../r_main.h"
|
||||
#include "../r_state.h"
|
||||
#include "../tables.h"
|
||||
#include "r_opengl/r_opengl.h"
|
||||
|
@ -328,7 +329,7 @@ angle_t gld_FrustumAngle(void)
|
|||
|
||||
// NEWCLIP TODO: SRB2CBTODO: make a global render_fov for this function
|
||||
|
||||
float render_fov = FIXED_TO_FLOAT(cv_grfov.value);
|
||||
float render_fov = FIXED_TO_FLOAT(cv_fov.value);
|
||||
float render_fovratio = (float)BASEVIDWIDTH / (float)BASEVIDHEIGHT; // SRB2CBTODO: NEWCLIPTODO: Is this right?
|
||||
float render_multiplier = 64.0f / render_fovratio / RMUL;
|
||||
|
||||
|
|
|
@ -61,9 +61,6 @@ typedef void (*I_Error_t) (const char *error, ...) FUNCIERROR;
|
|||
// ==========================================================================
|
||||
|
||||
// Constants
|
||||
#ifndef M_PIl
|
||||
#define M_PIl 3.1415926535897932384626433832795029L
|
||||
#endif
|
||||
#define DEGREE (0.017453292519943295769236907684883l) // 2*PI/360
|
||||
|
||||
void DBG_Printf(const char *lpFmt, ...) /*FUNCPRINTF*/;
|
||||
|
|
|
@ -86,12 +86,10 @@ static UINT32 atohex(const char *s);
|
|||
static void CV_filtermode_ONChange(void);
|
||||
static void CV_anisotropic_ONChange(void);
|
||||
static void CV_FogDensity_ONChange(void);
|
||||
static void CV_grFov_OnChange(void);
|
||||
// ==========================================================================
|
||||
// 3D ENGINE COMMANDS & CONSOLE VARS
|
||||
// ==========================================================================
|
||||
|
||||
static CV_PossibleValue_t grfov_cons_t[] = {{0, "MIN"}, {179*FRACUNIT, "MAX"}, {0, NULL}};
|
||||
static CV_PossibleValue_t grfiltermode_cons_t[]= {{HWD_SET_TEXTUREFILTER_POINTSAMPLED, "Nearest"},
|
||||
{HWD_SET_TEXTUREFILTER_BILINEAR, "Bilinear"}, {HWD_SET_TEXTUREFILTER_TRILINEAR, "Trilinear"},
|
||||
{HWD_SET_TEXTUREFILTER_MIXED1, "Linear_Nearest"},
|
||||
|
@ -112,7 +110,6 @@ static consvar_t cv_grbeta = {"gr_beta", "0", 0, CV_Unsigned, NULL, 0, NULL, NUL
|
|||
|
||||
static float HWRWipeCounter = 1.0f;
|
||||
consvar_t cv_grrounddown = {"gr_rounddown", "Off", 0, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_grfov = {"gr_fov", "90", CV_FLOAT|CV_CALL, grfov_cons_t, CV_grFov_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_grfogdensity = {"gr_fogdensity", "150", CV_CALL|CV_NOINIT, CV_Unsigned,
|
||||
CV_FogDensity_ONChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
|
@ -5907,7 +5904,7 @@ void HWR_SetViewSize(void)
|
|||
// ==========================================================================
|
||||
void HWR_RenderSkyboxView(INT32 viewnumber, player_t *player)
|
||||
{
|
||||
const float fpov = FIXED_TO_FLOAT(cv_grfov.value+player->fovadd);
|
||||
const float fpov = FIXED_TO_FLOAT(cv_fov.value+player->fovadd);
|
||||
postimg_t *type;
|
||||
UINT8 ssplayer = 0;
|
||||
|
||||
|
@ -6073,7 +6070,7 @@ if (0)
|
|||
viewangle = localaiming4;
|
||||
|
||||
// Handle stuff when you are looking farther up or down.
|
||||
if ((aimingangle || cv_grfov.value+player->fovadd > 90*FRACUNIT))
|
||||
if ((aimingangle || cv_fov.value+player->fovadd > 90*FRACUNIT))
|
||||
{
|
||||
dup_viewangle += ANGLE_90;
|
||||
HWR_ClearClipSegs();
|
||||
|
@ -6151,7 +6148,7 @@ if (0)
|
|||
// ==========================================================================
|
||||
void HWR_RenderPlayerView(INT32 viewnumber, player_t *player)
|
||||
{
|
||||
const float fpov = FIXED_TO_FLOAT(cv_grfov.value+player->fovadd);
|
||||
const float fpov = FIXED_TO_FLOAT(cv_fov.value+player->fovadd);
|
||||
postimg_t *type;
|
||||
UINT8 ssplayer = 0;
|
||||
|
||||
|
@ -6332,7 +6329,7 @@ if (0)
|
|||
viewangle = localaiming4;
|
||||
|
||||
// Handle stuff when you are looking farther up or down.
|
||||
if ((aimingangle || cv_grfov.value+player->fovadd > 90*FRACUNIT))
|
||||
if ((aimingangle || cv_fov.value+player->fovadd > 90*FRACUNIT))
|
||||
{
|
||||
dup_viewangle += ANGLE_90;
|
||||
HWR_ClearClipSegs();
|
||||
|
@ -6455,11 +6452,6 @@ static void HWR_FoggingOn(void)
|
|||
// ==========================================================================
|
||||
|
||||
|
||||
static void CV_grFov_OnChange(void)
|
||||
{
|
||||
if ((netgame || multiplayer) && !cv_debug && cv_grfov.value != 90*FRACUNIT)
|
||||
CV_Set(&cv_grfov, cv_grfov.defaultvalue);
|
||||
}
|
||||
|
||||
static void Command_GrStats_f(void)
|
||||
{
|
||||
|
@ -6482,7 +6474,6 @@ static void Command_GrStats_f(void)
|
|||
void HWR_AddCommands(void)
|
||||
{
|
||||
CV_RegisterVar(&cv_grrounddown);
|
||||
CV_RegisterVar(&cv_grfov);
|
||||
CV_RegisterVar(&cv_grfogdensity);
|
||||
CV_RegisterVar(&cv_grfiltermode);
|
||||
CV_RegisterVar(&cv_granisotropicmode);
|
||||
|
|
|
@ -80,7 +80,6 @@ extern consvar_t cv_grstaticlighting;
|
|||
extern consvar_t cv_grcoronas;
|
||||
extern consvar_t cv_grcoronasize;
|
||||
#endif
|
||||
extern consvar_t cv_grfov;
|
||||
extern consvar_t cv_grmd2;
|
||||
extern consvar_t cv_grfog;
|
||||
extern consvar_t cv_grfogcolor;
|
||||
|
|
|
@ -2056,10 +2056,11 @@ EXPORT void HWRAPI(DrawMD2) (INT32 *gl_cmd_buffer, md2_frame_t *frame, FTransfor
|
|||
EXPORT void HWRAPI(SetTransform) (FTransform *stransform)
|
||||
{
|
||||
static boolean special_splitscreen;
|
||||
GLdouble used_fov;
|
||||
pglLoadIdentity();
|
||||
if (stransform)
|
||||
{
|
||||
boolean fovx90;
|
||||
used_fov = stransform->fovxangle;
|
||||
// keep a trace of the transformation for md2
|
||||
memcpy(&md2_transform, stransform, sizeof (md2_transform));
|
||||
|
||||
|
@ -2074,36 +2075,29 @@ EXPORT void HWRAPI(SetTransform) (FTransform *stransform)
|
|||
pglRotatef(stransform->angley+270.0f, 0.0f, 1.0f, 0.0f);
|
||||
pglTranslatef(-stransform->x, -stransform->z, -stransform->y);
|
||||
|
||||
pglMatrixMode(GL_PROJECTION);
|
||||
pglLoadIdentity();
|
||||
fovx90 = stransform->fovxangle > 0.0f && fabsf(stransform->fovxangle - 90.0f) < 0.5f;
|
||||
special_splitscreen = (stransform->splitscreen == 1 && fovx90);
|
||||
if (special_splitscreen)
|
||||
GLPerspective(53.13l, 2*ASPECT_RATIO); // 53.13 = 2*atan(0.5)
|
||||
else
|
||||
GLPerspective(stransform->fovxangle, ASPECT_RATIO);
|
||||
#ifndef MINI_GL_COMPATIBILITY
|
||||
pglGetDoublev(GL_PROJECTION_MATRIX, projMatrix); // added for new coronas' code (without depth buffer)
|
||||
#endif
|
||||
pglMatrixMode(GL_MODELVIEW);
|
||||
special_splitscreen = (stransform->splitscreen == 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
//Hurdler: is "fov" correct?
|
||||
used_fov = fov;
|
||||
pglScalef(1.0f, 1.0f, -1.0f);
|
||||
|
||||
pglMatrixMode(GL_PROJECTION);
|
||||
pglLoadIdentity();
|
||||
if (special_splitscreen)
|
||||
GLPerspective(53.13l, 2*ASPECT_RATIO); // 53.13 = 2*atan(0.5)
|
||||
else
|
||||
//Hurdler: is "fov" correct?
|
||||
GLPerspective(fov, ASPECT_RATIO);
|
||||
#ifndef MINI_GL_COMPATIBILITY
|
||||
pglGetDoublev(GL_PROJECTION_MATRIX, projMatrix); // added for new coronas' code (without depth buffer)
|
||||
#endif
|
||||
pglMatrixMode(GL_MODELVIEW);
|
||||
}
|
||||
|
||||
pglMatrixMode(GL_PROJECTION);
|
||||
pglLoadIdentity();
|
||||
if (special_splitscreen)
|
||||
{
|
||||
used_fov = atan(tan(used_fov*M_PIl/360.0l)*0.8l)*360/M_PIl;
|
||||
GLPerspective(used_fov, 2*ASPECT_RATIO);
|
||||
}
|
||||
else
|
||||
GLPerspective(used_fov, ASPECT_RATIO);
|
||||
#ifndef MINI_GL_COMPATIBILITY
|
||||
pglGetDoublev(GL_PROJECTION_MATRIX, projMatrix); // added for new coronas' code (without depth buffer)
|
||||
#endif
|
||||
pglMatrixMode(GL_MODELVIEW);
|
||||
|
||||
#ifndef MINI_GL_COMPATIBILITY
|
||||
pglGetDoublev(GL_MODELVIEW_MATRIX, modelMatrix); // added for new coronas' code (without depth buffer)
|
||||
#endif
|
||||
|
|
260
src/hu_stuff.c
260
src/hu_stuff.c
|
@ -74,6 +74,14 @@ patch_t *nightsnum[10]; // 0-9
|
|||
patch_t *lt_font[LT_FONTSIZE];
|
||||
patch_t *cred_font[CRED_FONTSIZE];
|
||||
|
||||
// ping font
|
||||
// Note: I'd like to adress that at this point we might *REALLY* want to work towards a common drawString function that can take any font we want because this is really turning into a MESS. :V -Lat'
|
||||
patch_t *pingnum[10];
|
||||
patch_t *pinggfx[5]; // small ping graphic
|
||||
|
||||
patch_t *framecounter;
|
||||
patch_t *frameslash; // framerate stuff. Used in screen.c
|
||||
|
||||
static player_t *plr;
|
||||
boolean chat_on; // entering a chat message?
|
||||
static char w_chat[HU_MAXMSGLEN];
|
||||
|
@ -263,6 +271,8 @@ void HU_LoadGraphics(void)
|
|||
tallnum[i] = (patch_t *)W_CachePatchName(buffer, PU_HUDGFX);
|
||||
sprintf(buffer, "NGTNUM%d", i);
|
||||
nightsnum[i] = (patch_t *) W_CachePatchName(buffer, PU_HUDGFX);
|
||||
sprintf(buffer, "PINGN%d", i);
|
||||
pingnum[i] = (patch_t *) W_CachePatchName(buffer, PU_HUDGFX);
|
||||
}
|
||||
|
||||
// minus for negative tallnums
|
||||
|
@ -295,6 +305,17 @@ void HU_LoadGraphics(void)
|
|||
tinyemeraldpics[6] = W_CachePatchName("TEMER7", PU_HUDGFX);
|
||||
|
||||
songcreditbg = W_CachePatchName("K_SONGCR", PU_HUDGFX);
|
||||
|
||||
// cache ping gfx:
|
||||
for (i = 0; i < 5; i++)
|
||||
{
|
||||
sprintf(buffer, "PINGGFX%d", i+1);
|
||||
pinggfx[i] = (patch_t *)W_CachePatchName(buffer, PU_HUDGFX);
|
||||
}
|
||||
|
||||
// fps stuff
|
||||
framecounter = W_CachePatchName("FRAMER", PU_HUDGFX);
|
||||
frameslash = W_CachePatchName("FRAMESL", PU_HUDGFX);;
|
||||
}
|
||||
|
||||
// Initialise Heads up
|
||||
|
@ -757,44 +778,139 @@ static void Got_Saycmd(UINT8 **p, INT32 playernum)
|
|||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
{
|
||||
const UINT8 color = players[playernum].skincolor;
|
||||
|
||||
cstart = "\x83";
|
||||
|
||||
if (color <= SKINCOLOR_SILVER || color == SKINCOLOR_SLATE)
|
||||
cstart = "\x80"; // white
|
||||
else if (color <= SKINCOLOR_BLACK || color == SKINCOLOR_JET)
|
||||
cstart = "\x86"; // V_GRAYMAP
|
||||
else if (color <= SKINCOLOR_LEATHER)
|
||||
cstart = "\x8e"; // V_BROWNMAP
|
||||
else if (color <= SKINCOLOR_ROSE || color == SKINCOLOR_LILAC)
|
||||
cstart = "\x8d"; // V_PINKMAP
|
||||
else if (color <= SKINCOLOR_KETCHUP)
|
||||
cstart = "\x85"; // V_REDMAP
|
||||
else if (color <= SKINCOLOR_TANGERINE)
|
||||
cstart = "\x87"; // V_ORANGEMAP
|
||||
else if (color <= SKINCOLOR_CARAMEL)
|
||||
cstart = "\x8f"; // V_PEACHMAP
|
||||
else if (color <= SKINCOLOR_BRONZE)
|
||||
cstart = "\x8A"; // V_GOLDMAP
|
||||
else if (color <= SKINCOLOR_OLIVE)
|
||||
cstart = "\x82"; // V_YELLOWMAP
|
||||
else if (color <= SKINCOLOR_PISTACHIO)
|
||||
cstart = "\x8b"; // V_TEAMAP
|
||||
else if (color <= SKINCOLOR_DREAM || color == SKINCOLOR_LIME)
|
||||
cstart = "\x83"; // V_GREENMAP
|
||||
else if (color <= SKINCOLOR_NAVY || color == SKINCOLOR_SAPPHIRE)
|
||||
cstart = "\x88"; // V_SKYMAP
|
||||
else if (color <= SKINCOLOR_STEEL)
|
||||
cstart = "\x8c"; // V_STEELMAP
|
||||
else if (color <= SKINCOLOR_BLUEBERRY)
|
||||
cstart = "\x84"; // V_BLUEMAP
|
||||
else if (color == SKINCOLOR_PURPLE)
|
||||
cstart = "\x81"; // V_PURPLEMAP
|
||||
else //if (color <= SKINCOLOR_POMEGRANATE)
|
||||
cstart = "\x89"; // V_LAVENDERMAP
|
||||
}
|
||||
switch (color)
|
||||
{
|
||||
case SKINCOLOR_WHITE:
|
||||
case SKINCOLOR_SILVER:
|
||||
case SKINCOLOR_SLATE:
|
||||
cstart = "\x80"; // White
|
||||
break;
|
||||
case SKINCOLOR_GREY:
|
||||
case SKINCOLOR_NICKEL:
|
||||
case SKINCOLOR_BLACK:
|
||||
case SKINCOLOR_JET:
|
||||
cstart = "\x86"; // V_GRAYMAP
|
||||
break;
|
||||
case SKINCOLOR_SEPIA:
|
||||
case SKINCOLOR_BEIGE:
|
||||
case SKINCOLOR_BROWN:
|
||||
case SKINCOLOR_LEATHER:
|
||||
case SKINCOLOR_RUST:
|
||||
cstart = "\x8e"; // V_BROWNMAP
|
||||
break;
|
||||
case SKINCOLOR_FAIRY:
|
||||
case SKINCOLOR_SALMON:
|
||||
case SKINCOLOR_PINK:
|
||||
case SKINCOLOR_ROSE:
|
||||
case SKINCOLOR_BRICK:
|
||||
case SKINCOLOR_BUBBLEGUM:
|
||||
case SKINCOLOR_LILAC:
|
||||
cstart = "\x8d"; // V_PINKMAP
|
||||
break;
|
||||
case SKINCOLOR_RUBY:
|
||||
case SKINCOLOR_RASPBERRY:
|
||||
case SKINCOLOR_CHERRY:
|
||||
case SKINCOLOR_RED:
|
||||
case SKINCOLOR_CRIMSON:
|
||||
case SKINCOLOR_MAROON:
|
||||
case SKINCOLOR_FLAME:
|
||||
case SKINCOLOR_SCARLET:
|
||||
case SKINCOLOR_KETCHUP:
|
||||
cstart = "\x85"; // V_REDMAP
|
||||
break;
|
||||
case SKINCOLOR_DAWN:
|
||||
case SKINCOLOR_SUNSET:
|
||||
case SKINCOLOR_CREAMSICLE:
|
||||
case SKINCOLOR_ORANGE:
|
||||
case SKINCOLOR_PUMPKIN:
|
||||
case SKINCOLOR_ROSEWOOD:
|
||||
case SKINCOLOR_BURGUNDY:
|
||||
case SKINCOLOR_TANGERINE:
|
||||
cstart = "\x87"; // V_ORANGEMAP
|
||||
break;
|
||||
case SKINCOLOR_PEACH:
|
||||
case SKINCOLOR_CARAMEL:
|
||||
case SKINCOLOR_CREAM:
|
||||
cstart = "\x8f"; // V_PEACHMAP
|
||||
break;
|
||||
case SKINCOLOR_GOLD:
|
||||
case SKINCOLOR_ROYAL:
|
||||
case SKINCOLOR_BRONZE:
|
||||
case SKINCOLOR_COPPER:
|
||||
cstart = "\x8A"; // V_GOLDMAP
|
||||
break;
|
||||
case SKINCOLOR_POPCORN:
|
||||
case SKINCOLOR_YELLOW:
|
||||
case SKINCOLOR_MUSTARD:
|
||||
case SKINCOLOR_OLIVE:
|
||||
cstart = "\x82"; // V_YELLOWMAP
|
||||
break;
|
||||
case SKINCOLOR_VOMIT:
|
||||
case SKINCOLOR_GARDEN:
|
||||
case SKINCOLOR_TEA:
|
||||
case SKINCOLOR_PISTACHIO:
|
||||
cstart = "\x8b"; // V_TEAMAP
|
||||
break;
|
||||
case SKINCOLOR_LIME:
|
||||
case SKINCOLOR_HANDHELD:
|
||||
case SKINCOLOR_MOSS:
|
||||
case SKINCOLOR_CAMOUFLAGE:
|
||||
case SKINCOLOR_ROBOHOOD:
|
||||
case SKINCOLOR_MINT:
|
||||
case SKINCOLOR_GREEN:
|
||||
case SKINCOLOR_PINETREE:
|
||||
case SKINCOLOR_EMERALD:
|
||||
case SKINCOLOR_SWAMP:
|
||||
case SKINCOLOR_DREAM:
|
||||
case SKINCOLOR_PLAGUE:
|
||||
case SKINCOLOR_ALGAE:
|
||||
cstart = "\x83"; // V_GREENMAP
|
||||
break;
|
||||
case SKINCOLOR_CARIBBEAN:
|
||||
case SKINCOLOR_AQUA:
|
||||
case SKINCOLOR_TEAL:
|
||||
case SKINCOLOR_CYAN:
|
||||
case SKINCOLOR_JAWZ:
|
||||
case SKINCOLOR_CERULEAN:
|
||||
case SKINCOLOR_NAVY:
|
||||
case SKINCOLOR_SAPPHIRE:
|
||||
cstart = "\x88"; // V_SKYMAP
|
||||
break;
|
||||
case SKINCOLOR_PLATINUM:
|
||||
case SKINCOLOR_STEEL:
|
||||
cstart = "\x8c"; // V_STEELMAP
|
||||
break;
|
||||
case SKINCOLOR_PERIWINKLE:
|
||||
case SKINCOLOR_BLUE:
|
||||
case SKINCOLOR_BLUEBERRY:
|
||||
case SKINCOLOR_NOVA:
|
||||
cstart = "\x84"; // V_BLUEMAP
|
||||
break;
|
||||
case SKINCOLOR_ULTRAVIOLET:
|
||||
case SKINCOLOR_PURPLE:
|
||||
case SKINCOLOR_FUCHSIA:
|
||||
cstart = "\x81"; // V_PURPLEMAP
|
||||
break;
|
||||
case SKINCOLOR_PASTEL:
|
||||
case SKINCOLOR_MOONSLAM:
|
||||
case SKINCOLOR_DUSK:
|
||||
case SKINCOLOR_TOXIC:
|
||||
case SKINCOLOR_MAUVE:
|
||||
case SKINCOLOR_LAVENDER:
|
||||
case SKINCOLOR_BYZANTIUM:
|
||||
case SKINCOLOR_POMEGRANATE:
|
||||
cstart = "\x89"; // V_LAVENDERMAP
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
prefix = cstart;
|
||||
|
||||
// Give admins and remote admins their symbols.
|
||||
|
@ -1109,8 +1225,6 @@ static INT16 typelines = 1; // number of drawfill lines we need when drawing the
|
|||
//
|
||||
boolean HU_Responder(event_t *ev)
|
||||
{
|
||||
INT32 c=0;
|
||||
|
||||
if (ev->type != ev_keydown)
|
||||
return false;
|
||||
|
||||
|
@ -1136,18 +1250,6 @@ boolean HU_Responder(event_t *ev)
|
|||
return false;
|
||||
}
|
||||
|
||||
c = (INT32)ev->data1;
|
||||
|
||||
// capslock (now handled outside of chat on so that it works everytime......)
|
||||
if (c && c == KEY_CAPSLOCK) // it's a toggle.
|
||||
{
|
||||
if (capslock)
|
||||
capslock = false;
|
||||
else
|
||||
capslock = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
#ifndef NONET
|
||||
if (!chat_on)
|
||||
{
|
||||
|
@ -1175,6 +1277,7 @@ boolean HU_Responder(event_t *ev)
|
|||
}
|
||||
else // if chat_on
|
||||
{
|
||||
INT32 c = (INT32)ev->data1;
|
||||
|
||||
// Ignore modifier keys
|
||||
// Note that we do this here so users can still set
|
||||
|
@ -1190,20 +1293,7 @@ boolean HU_Responder(event_t *ev)
|
|||
&& ev->data1 != gamecontrol[gc_talkkey][1]))
|
||||
return false;
|
||||
|
||||
c = (INT32)ev->data1;
|
||||
|
||||
// I know this looks very messy but this works. If it ain't broke, don't fix it!
|
||||
// shift LETTERS to uppercase if we have capslock or are holding shift
|
||||
if ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z'))
|
||||
{
|
||||
if (shiftdown ^ capslock)
|
||||
c = shiftxform[c];
|
||||
}
|
||||
else // if we're holding shift we should still shift non letter symbols
|
||||
{
|
||||
if (shiftdown)
|
||||
c = shiftxform[c];
|
||||
}
|
||||
c = CON_ShiftChar(c);
|
||||
|
||||
// pasting. pasting is cool. chat is a bit limited, though :(
|
||||
if (((c == 'v' || c == 'V') && ctrldown) && !CHAT_MUTE)
|
||||
|
@ -1612,9 +1702,9 @@ static void HU_drawChatLog(INT32 offset)
|
|||
|
||||
// draw arrows to indicate that we can (or not) scroll.
|
||||
if (chat_scroll > 0)
|
||||
V_DrawThinString(chatx-9, ((justscrolledup) ? (chat_topy-1) : (chat_topy)), V_SNAPTOBOTTOM | V_SNAPTOLEFT | highlight, "\x1A"); // up arrow
|
||||
V_DrawCharacter(chatx-9, ((justscrolledup) ? (chat_topy-1) : (chat_topy)), V_SNAPTOBOTTOM | V_SNAPTOLEFT | highlight | '\x1A', false); // up arrow
|
||||
if (chat_scroll < chat_maxscroll)
|
||||
V_DrawThinString(chatx-9, chat_bottomy-((justscrolleddown) ? 5 : 6), V_SNAPTOBOTTOM | V_SNAPTOLEFT | highlight, "\x1B"); // down arrow
|
||||
V_DrawCharacter(chatx-9, chat_bottomy-((justscrolleddown) ? 5 : 6), V_SNAPTOBOTTOM | V_SNAPTOLEFT | highlight | '\x1B', false); // down arrow
|
||||
|
||||
justscrolleddown = false;
|
||||
justscrolledup = false;
|
||||
|
@ -2178,6 +2268,7 @@ static void HU_DrawSongCredits(void)
|
|||
V_DrawRightAlignedThinString(cursongcredit.x, y, V_ALLOWLOWERCASE|V_6WIDTHSPACE|V_SNAPTOLEFT|(cursongcredit.trans<<V_ALPHASHIFT), str);
|
||||
}
|
||||
|
||||
|
||||
// Heads up displays drawer, call each frame
|
||||
//
|
||||
void HU_Drawer(void)
|
||||
|
@ -2369,36 +2460,25 @@ void HU_Erase(void)
|
|||
//
|
||||
// HU_drawPing
|
||||
//
|
||||
void HU_drawPing(INT32 x, INT32 y, INT32 ping, boolean notext)
|
||||
void HU_drawPing(INT32 x, INT32 y, UINT32 ping, INT32 flags)
|
||||
{
|
||||
UINT8 numbars = 1; // how many ping bars do we draw?
|
||||
UINT8 barcolor = 128; // color we use for the bars (green, yellow or red)
|
||||
SINT8 i = 0;
|
||||
SINT8 yoffset = 6;
|
||||
INT32 dx = x+1 - (V_SmallStringWidth(va("%dms", ping), V_ALLOWLOWERCASE)/2);
|
||||
INT32 gfxnum = 4; // gfx to draw
|
||||
UINT8 const *colormap = R_GetTranslationColormap(TC_RAINBOW, SKINCOLOR_SALMON, GTC_CACHE);
|
||||
|
||||
if (ping < 128)
|
||||
{
|
||||
numbars = 3;
|
||||
barcolor = 184;
|
||||
}
|
||||
if (ping < 76)
|
||||
gfxnum = 0;
|
||||
else if (ping < 137)
|
||||
gfxnum = 1;
|
||||
else if (ping < 256)
|
||||
{
|
||||
numbars = 2; // Apparently ternaries w/ multiple statements don't look good in C so I decided against it.
|
||||
barcolor = 103;
|
||||
}
|
||||
gfxnum = 2;
|
||||
else if (ping < 500)
|
||||
gfxnum = 3;
|
||||
|
||||
if (!notext || vid.width >= 640) // how sad, we're using a shit resolution.
|
||||
V_DrawSmallString(dx, y+4, V_ALLOWLOWERCASE, va("%dms", ping));
|
||||
|
||||
for (i=0; (i<3); i++) // Draw the ping bar
|
||||
{
|
||||
V_DrawFill(x+2 *(i-1), y+yoffset-4, 2, 8-yoffset, 31);
|
||||
if (i < numbars)
|
||||
V_DrawFill(x+2 *(i-1), y+yoffset-3, 1, 8-yoffset-1, barcolor);
|
||||
|
||||
yoffset -= 2;
|
||||
}
|
||||
V_DrawScaledPatch(x, y, flags, pinggfx[gfxnum]);
|
||||
if (servermaxping && ping > servermaxping && hu_tick < 4) // flash ping red if too high
|
||||
V_DrawPingNum(x, y+9, flags, ping, colormap);
|
||||
else
|
||||
V_DrawPingNum(x, y+9, flags, ping, NULL);
|
||||
}
|
||||
|
||||
//
|
||||
|
|
|
@ -80,7 +80,11 @@ extern boolean chat_on;
|
|||
|
||||
extern patch_t *hu_font[HU_FONTSIZE], *kart_font[KART_FONTSIZE], *tny_font[HU_FONTSIZE]; // SRB2kart
|
||||
extern patch_t *tallnum[10];
|
||||
extern patch_t *pingnum[10];
|
||||
extern patch_t *pinggfx[5];
|
||||
extern patch_t *nightsnum[10];
|
||||
extern patch_t *framecounter;
|
||||
extern patch_t *frameslash;
|
||||
extern patch_t *lt_font[LT_FONTSIZE];
|
||||
extern patch_t *cred_font[CRED_FONTSIZE];
|
||||
extern patch_t *emeraldpics[7];
|
||||
|
@ -109,7 +113,7 @@ void HU_Drawer(void);
|
|||
char HU_dequeueChatChar(void);
|
||||
void HU_Erase(void);
|
||||
void HU_clearChatChars(void);
|
||||
void HU_drawPing(INT32 x, INT32 y, INT32 ping, boolean notext); // Lat': Ping drawer for scoreboard.
|
||||
void HU_drawPing(INT32 x, INT32 y, UINT32 ping, INT32 flags); // Lat': Ping drawer for scoreboard.
|
||||
//void HU_DrawTeamTabRankings(playersort_t *tab, INT32 whiteplayer);
|
||||
//void HU_DrawDualTabRankings(INT32 x, INT32 y, playersort_t *tab, INT32 scorelines, INT32 whiteplayer);
|
||||
void HU_DrawTabRankings(INT32 x, INT32 y, playersort_t *tab, INT32 scorelines, INT32 whiteplayer, INT32 hilicol);
|
||||
|
|
10
src/i_tcp.c
10
src/i_tcp.c
|
@ -612,7 +612,7 @@ static boolean SOCK_Get(void)
|
|||
if (c != ERRSOCKET)
|
||||
{
|
||||
// find remote node number
|
||||
for (j = 0; j <= MAXNETNODES; j++) //include LAN
|
||||
for (j = 1; j <= MAXNETNODES; j++) //include LAN
|
||||
{
|
||||
if (SOCK_cmpaddr(&fromaddress, &clientaddress[j], 0))
|
||||
{
|
||||
|
@ -1340,8 +1340,12 @@ static SINT8 SOCK_NetMakeNodewPort(const char *address, const char *port)
|
|||
while (runp != NULL)
|
||||
{
|
||||
// find ip of the server
|
||||
memcpy(&clientaddress[newnode], runp->ai_addr, runp->ai_addrlen);
|
||||
runp = NULL;
|
||||
if (sendto(mysockets[0], NULL, 0, 0, runp->ai_addr, runp->ai_addrlen) == 0)
|
||||
{
|
||||
memcpy(&clientaddress[newnode], runp->ai_addr, runp->ai_addrlen);
|
||||
break;
|
||||
}
|
||||
runp = runp->ai_next;
|
||||
}
|
||||
I_freeaddrinfo(ai);
|
||||
return newnode;
|
||||
|
|
23
src/info.c
23
src/info.c
|
@ -3140,11 +3140,11 @@ state_t states[NUMSTATES] =
|
|||
{SPR_NULL, 0, 1, {A_FZBoomSmoke}, 1, 0, S_FZEROBOOM12}, // S_FZEROBOOM11
|
||||
{SPR_NULL, 0, 1, {A_FZBoomSmoke}, 0, 0, S_NULL}, // S_FZEROBOOM12
|
||||
|
||||
{SPR_SMOK, FF_TRANS30, 30, {NULL}, 0, 0, S_FZSLOWSMOKE2}, // S_FZSLOWSMOKE1
|
||||
{SPR_SMOK, FF_TRANS30|1, 30, {NULL}, 0, 0, S_FZSLOWSMOKE3}, // S_FZSLOWSMOKE2
|
||||
{SPR_SMOK, FF_TRANS30|2, 30, {NULL}, 0, 0, S_FZSLOWSMOKE4}, // S_FZSLOWSMOKE3
|
||||
{SPR_SMOK, FF_TRANS30|3, 30, {NULL}, 0, 0, S_FZSLOWSMOKE5}, // S_FZSLOWSMOKE4
|
||||
{SPR_SMOK, FF_TRANS30|4, 30, {NULL}, 0, 0, S_NULL}, // S_FZSLOWSMOKE5
|
||||
{SPR_SMOK, 0, 30, {NULL}, 0, 0, S_FZSLOWSMOKE2}, // S_FZSLOWSMOKE1
|
||||
{SPR_SMOK, 1, 30, {NULL}, 0, 0, S_FZSLOWSMOKE3}, // S_FZSLOWSMOKE2
|
||||
{SPR_SMOK, 2, 30, {NULL}, 0, 0, S_FZSLOWSMOKE4}, // S_FZSLOWSMOKE3
|
||||
{SPR_SMOK, 3, 30, {NULL}, 0, 0, S_FZSLOWSMOKE5}, // S_FZSLOWSMOKE4
|
||||
{SPR_SMOK, 4, 30, {NULL}, 0, 0, S_NULL}, // S_FZSLOWSMOKE5
|
||||
|
||||
// Various plants
|
||||
{SPR_SBUS, 0, -1, {NULL}, 0, 0, S_NULL}, // S_SONICBUSH
|
||||
|
@ -3394,6 +3394,13 @@ state_t states[NUMSTATES] =
|
|||
{SPR_FWRK, 3|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_KARMAFIREWORK1}, // S_KARMAFIREWORK4
|
||||
{SPR_FWRK, 4|FF_FULLBRIGHT, TICRATE, {NULL}, 0, 0, S_NULL}, // S_KARMAFIREWORKTRAIL
|
||||
|
||||
// Opaque smoke
|
||||
{SPR_SMOK, 0, 4, {NULL}, 0, 0, S_OPAQUESMOKE2}, // S_OPAQUESMOKE1
|
||||
{SPR_SMOK, 1, 5, {NULL}, 0, 0, S_OPAQUESMOKE3}, // S_OPAQUESMOKE2
|
||||
{SPR_SMOK, 2, 6, {NULL}, 0, 0, S_OPAQUESMOKE4}, // S_OPAQUESMOKE3
|
||||
{SPR_SMOK, 3, 7, {NULL}, 0, 0, S_OPAQUESMOKE5}, // S_OPAQUESMOKE4
|
||||
{SPR_SMOK, 4, 8, {NULL}, 0, 0, S_NULL}, // S_OPAQUESMOKE5
|
||||
|
||||
#ifdef SEENAMES
|
||||
{SPR_NULL, 0, 1, {NULL}, 0, 0, S_NULL}, // S_NAMECHECK
|
||||
#endif
|
||||
|
@ -15018,8 +15025,8 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
|
|||
S_NULL, // xdeathstate
|
||||
sfx_None, // deathsound
|
||||
8, // speed
|
||||
8*FRACUNIT, // radius
|
||||
8*FRACUNIT, // height
|
||||
32*FRACUNIT, // radius
|
||||
64*FRACUNIT, // height
|
||||
1, // display offset
|
||||
100, // mass
|
||||
0, // damage
|
||||
|
@ -15574,7 +15581,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
|
|||
1, // spawnhealth
|
||||
S_NULL, // seestate
|
||||
sfx_tossed, // seesound
|
||||
6*TICRATE, // reactiontime
|
||||
0, // reactiontime
|
||||
sfx_None, // attacksound
|
||||
S_NULL, // painstate
|
||||
192*FRACUNIT, // painchance
|
||||
|
|
|
@ -4052,6 +4052,12 @@ typedef enum state
|
|||
S_KARMAFIREWORK4,
|
||||
S_KARMAFIREWORKTRAIL,
|
||||
|
||||
S_OPAQUESMOKE1,
|
||||
S_OPAQUESMOKE2,
|
||||
S_OPAQUESMOKE3,
|
||||
S_OPAQUESMOKE4,
|
||||
S_OPAQUESMOKE5,
|
||||
|
||||
#ifdef SEENAMES
|
||||
S_NAMECHECK,
|
||||
#endif
|
||||
|
|
1028
src/k_kart.c
1028
src/k_kart.c
File diff suppressed because it is too large
Load diff
|
@ -11,7 +11,7 @@
|
|||
|
||||
#define KART_FULLTURN 800
|
||||
|
||||
UINT8 colortranslations[MAXSKINCOLORS][16];
|
||||
UINT8 colortranslations[MAXTRANSLATIONS][16];
|
||||
extern const char *KartColor_Names[MAXSKINCOLORS];
|
||||
extern const UINT8 KartColor_Opposite[MAXSKINCOLORS*2];
|
||||
void K_RainbowColormap(UINT8 *dest_colormap, UINT8 skincolor);
|
||||
|
@ -23,6 +23,7 @@ void K_RegisterKartStuff(void);
|
|||
boolean K_IsPlayerLosing(player_t *player);
|
||||
boolean K_IsPlayerWanted(player_t *player);
|
||||
void K_KartBouncing(mobj_t *mobj1, mobj_t *mobj2, boolean bounce, boolean solid);
|
||||
void K_FlipFromObject(mobj_t *mo, mobj_t *master);
|
||||
void K_MatchGenericExtraFlags(mobj_t *mo, mobj_t *master);
|
||||
void K_RespawnChecker(player_t *player);
|
||||
void K_KartMoveAnimation(player_t *player);
|
||||
|
@ -41,6 +42,7 @@ void K_SpawnBoostTrail(player_t *player);
|
|||
void K_SpawnSparkleTrail(mobj_t *mo);
|
||||
void K_SpawnWipeoutTrail(mobj_t *mo, boolean translucent);
|
||||
void K_DriftDustHandling(mobj_t *spawner);
|
||||
void K_PuntMine(mobj_t *mine, mobj_t *punter);
|
||||
void K_DoSneaker(player_t *player, INT32 type);
|
||||
void K_DoPogoSpring(mobj_t *mo, fixed_t vertispeed, UINT8 sound);
|
||||
void K_KillBananaChain(mobj_t *banana, mobj_t *inflictor, mobj_t *source);
|
||||
|
|
|
@ -632,19 +632,6 @@ static int lib_pCheckSolidLava(lua_State *L)
|
|||
return 1;
|
||||
}
|
||||
|
||||
static int lib_pCanRunOnWater(lua_State *L)
|
||||
{
|
||||
player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER));
|
||||
ffloor_t *rover = *((ffloor_t **)luaL_checkudata(L, 2, META_FFLOOR));
|
||||
//HUDSAFE
|
||||
if (!player)
|
||||
return LUA_ErrInvalid(L, "player_t");
|
||||
if (!rover)
|
||||
return LUA_ErrInvalid(L, "ffloor_t");
|
||||
lua_pushboolean(L, P_CanRunOnWater(player, rover));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int lib_pSpawnShadowMobj(lua_State *L)
|
||||
{
|
||||
mobj_t *caster = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ));
|
||||
|
@ -2627,7 +2614,6 @@ static luaL_Reg lib[] = {
|
|||
{"P_InsideANonSolidFFloor",lib_pInsideANonSolidFFloor},
|
||||
{"P_CheckDeathPitCollide",lib_pCheckDeathPitCollide},
|
||||
{"P_CheckSolidLava",lib_pCheckSolidLava},
|
||||
{"P_CanRunOnWater",lib_pCanRunOnWater},
|
||||
{"P_SpawnShadowMobj",lib_pSpawnShadowMobj},
|
||||
|
||||
// p_user
|
||||
|
|
|
@ -410,6 +410,24 @@ static int libd_drawPaddedNum(lua_State *L)
|
|||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int libd_drawPingNum(lua_State *L)
|
||||
{
|
||||
INT32 x, y, flags, num;
|
||||
const UINT8 *colormap = NULL;
|
||||
HUDONLY
|
||||
x = luaL_checkinteger(L, 1);
|
||||
y = luaL_checkinteger(L, 2);
|
||||
num = luaL_checkinteger(L, 3);
|
||||
flags = luaL_optinteger(L, 4, 0);
|
||||
flags &= ~V_PARAMMASK; // Don't let crashes happen.
|
||||
if (!lua_isnoneornil(L, 5))
|
||||
colormap = *((UINT8 **)luaL_checkudata(L, 5, META_COLORMAP));
|
||||
|
||||
V_DrawPingNum(x, y, flags, num, colormap);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int libd_drawFill(lua_State *L)
|
||||
{
|
||||
INT32 x = luaL_optinteger(L, 1, 0);
|
||||
|
@ -613,6 +631,7 @@ static luaL_Reg lib_draw[] = {
|
|||
{"drawScaled", libd_drawScaled},
|
||||
{"drawNum", libd_drawNum},
|
||||
{"drawPaddedNum", libd_drawPaddedNum},
|
||||
{"drawPingNum", libd_drawPingNum},
|
||||
{"drawFill", libd_drawFill},
|
||||
{"fadeScreen", libd_fadeScreen},
|
||||
{"drawString", libd_drawString},
|
||||
|
|
|
@ -325,6 +325,8 @@ static int player_get(lua_State *L)
|
|||
lua_pushinteger(L, plr->bot);
|
||||
else if (fastcmp(field,"jointime"))
|
||||
lua_pushinteger(L, plr->jointime);
|
||||
else if (fastcmp(field,"splitscreenindex"))
|
||||
lua_pushinteger(L, plr->splitscreenindex);
|
||||
#ifdef HWRENDER
|
||||
else if (fastcmp(field,"fovadd"))
|
||||
lua_pushfixed(L, plr->fovadd);
|
||||
|
@ -613,6 +615,8 @@ static int player_set(lua_State *L)
|
|||
return NOSET;
|
||||
else if (fastcmp(field,"jointime"))
|
||||
plr->jointime = (tic_t)luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"splitscreenindex"))
|
||||
return NOSET;
|
||||
#ifdef HWRENDER
|
||||
else if (fastcmp(field,"fovadd"))
|
||||
plr->fovadd = luaL_checkfixed(L, 3);
|
||||
|
@ -739,6 +743,8 @@ static int ticcmd_get(lua_State *L)
|
|||
lua_pushinteger(L, cmd->buttons);
|
||||
else if (fastcmp(field,"driftturn"))
|
||||
lua_pushinteger(L, cmd->driftturn);
|
||||
else if (fastcmp(field,"latency"))
|
||||
lua_pushinteger(L, cmd->latency);
|
||||
else
|
||||
return NOFIELD;
|
||||
|
||||
|
|
|
@ -1020,7 +1020,7 @@ void LUA_Archive(void)
|
|||
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
{
|
||||
if (!playeringame[i])
|
||||
if (!playeringame[i] && i > 0) // NEVER skip player 0, this is for dedi servs.
|
||||
continue;
|
||||
// all players in game will be archived, even if they just add a 0.
|
||||
ArchiveExtVars(&players[i], "player");
|
||||
|
@ -1056,7 +1056,7 @@ void LUA_UnArchive(void)
|
|||
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
{
|
||||
if (!playeringame[i])
|
||||
if (!playeringame[i] && i > 0) // same here, this is to synch dediservs properly.
|
||||
continue;
|
||||
UnArchiveExtVars(&players[i]);
|
||||
}
|
||||
|
|
|
@ -30,24 +30,10 @@ enum skin {
|
|||
skin_facerank,
|
||||
skin_facewant,
|
||||
skin_facemmap,
|
||||
skin_ability,
|
||||
skin_ability2,
|
||||
skin_thokitem,
|
||||
skin_spinitem,
|
||||
skin_revitem,
|
||||
skin_actionspd,
|
||||
skin_mindash,
|
||||
skin_maxdash,
|
||||
// SRB2kart
|
||||
skin_kartspeed,
|
||||
skin_kartweight,
|
||||
//
|
||||
skin_normalspeed,
|
||||
skin_runspeed,
|
||||
skin_thrustfactor,
|
||||
skin_accelstart,
|
||||
skin_acceleration,
|
||||
skin_jumpfactor,
|
||||
skin_starttranscolor,
|
||||
skin_prefcolor,
|
||||
skin_highresscale,
|
||||
|
@ -64,24 +50,10 @@ static const char *const skin_opt[] = {
|
|||
"facerank",
|
||||
"facewant",
|
||||
"facemmap",
|
||||
"ability",
|
||||
"ability2",
|
||||
"thokitem",
|
||||
"spinitem",
|
||||
"revitem",
|
||||
"actionspd",
|
||||
"mindash",
|
||||
"maxdash",
|
||||
// SRB2kart
|
||||
"kartspeed",
|
||||
"kartweight",
|
||||
//
|
||||
"normalspeed",
|
||||
"runspeed",
|
||||
"thrustfactor",
|
||||
"accelstart",
|
||||
"acceleration",
|
||||
"jumpfactor",
|
||||
"starttranscolor",
|
||||
"prefcolor",
|
||||
"highresscale",
|
||||
|
@ -139,30 +111,6 @@ static int skin_get(lua_State *L)
|
|||
break;
|
||||
lua_pushlstring(L, skin->facemmap, i);
|
||||
break;
|
||||
case skin_ability:
|
||||
lua_pushinteger(L, skin->ability);
|
||||
break;
|
||||
case skin_ability2:
|
||||
lua_pushinteger(L, skin->ability2);
|
||||
break;
|
||||
case skin_thokitem:
|
||||
lua_pushinteger(L, skin->thokitem);
|
||||
break;
|
||||
case skin_spinitem:
|
||||
lua_pushinteger(L, skin->spinitem);
|
||||
break;
|
||||
case skin_revitem:
|
||||
lua_pushinteger(L, skin->revitem);
|
||||
break;
|
||||
case skin_actionspd:
|
||||
lua_pushfixed(L, skin->actionspd);
|
||||
break;
|
||||
case skin_mindash:
|
||||
lua_pushfixed(L, skin->mindash);
|
||||
break;
|
||||
case skin_maxdash:
|
||||
lua_pushfixed(L, skin->maxdash);
|
||||
break;
|
||||
// SRB2kart
|
||||
case skin_kartspeed:
|
||||
lua_pushinteger(L, skin->kartspeed);
|
||||
|
@ -171,24 +119,6 @@ static int skin_get(lua_State *L)
|
|||
lua_pushinteger(L, skin->kartweight);
|
||||
break;
|
||||
//
|
||||
case skin_normalspeed:
|
||||
lua_pushfixed(L, skin->normalspeed);
|
||||
break;
|
||||
case skin_runspeed:
|
||||
lua_pushfixed(L, skin->runspeed);
|
||||
break;
|
||||
case skin_thrustfactor:
|
||||
lua_pushinteger(L, skin->thrustfactor);
|
||||
break;
|
||||
case skin_accelstart:
|
||||
lua_pushinteger(L, skin->accelstart);
|
||||
break;
|
||||
case skin_acceleration:
|
||||
lua_pushinteger(L, skin->acceleration);
|
||||
break;
|
||||
case skin_jumpfactor:
|
||||
lua_pushfixed(L, skin->jumpfactor);
|
||||
break;
|
||||
case skin_starttranscolor:
|
||||
lua_pushinteger(L, skin->starttranscolor);
|
||||
break;
|
||||
|
|
122
src/m_menu.c
122
src/m_menu.c
|
@ -399,6 +399,8 @@ static void Dummystaff_OnChange(void);
|
|||
// CONSOLE VARIABLES AND THEIR POSSIBLE VALUES GO HERE.
|
||||
// ==========================================================================
|
||||
|
||||
consvar_t cv_showfocuslost = {"showfocuslost", "Yes", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL };
|
||||
|
||||
static CV_PossibleValue_t map_cons_t[] = {
|
||||
{0,"MIN"},
|
||||
{NUMMAPS, "MAX"},
|
||||
|
@ -948,14 +950,15 @@ static menuitem_t MP_MainMenu[] =
|
|||
|
||||
static menuitem_t MP_ServerMenu[] =
|
||||
{
|
||||
{IT_STRING|IT_CVAR, NULL, "Max. Player Count", &cv_maxplayers, 10},
|
||||
{IT_STRING|IT_CALL, NULL, "Room...", M_RoomMenu, 20},
|
||||
{IT_STRING|IT_CVAR|IT_CV_STRING, NULL, "Server Name", &cv_servername, 30},
|
||||
{IT_STRING|IT_CVAR, NULL, "Max. Player Count", &cv_maxplayers, 0},
|
||||
{IT_STRING|IT_CALL, NULL, "Room...", M_RoomMenu, 10},
|
||||
{IT_STRING|IT_CVAR|IT_CV_STRING, NULL, "Server Name", &cv_servername, 20},
|
||||
{IT_STRING|IT_CVAR|IT_CV_PASSWORD, NULL, "Password", &cv_dummyjoinpassword, 44},
|
||||
|
||||
{IT_STRING|IT_CVAR, NULL, "Game Type", &cv_newgametype, 68},
|
||||
{IT_STRING|IT_CVAR, NULL, "Level", &cv_nextmap, 78},
|
||||
{IT_STRING|IT_CVAR, NULL, "Game Type", &cv_newgametype, 68},
|
||||
{IT_STRING|IT_CVAR, NULL, "Level", &cv_nextmap, 78},
|
||||
|
||||
{IT_WHITESTRING|IT_CALL, NULL, "Start", M_StartServer, 130},
|
||||
{IT_WHITESTRING|IT_CALL, NULL, "Start", M_StartServer, 130},
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1249,7 +1252,7 @@ static menuitem_t OP_OpenGLOptionsMenu[] =
|
|||
{IT_SUBMENU|IT_STRING, NULL, "Fog...", &OP_OpenGLFogDef, 10},
|
||||
{IT_SUBMENU|IT_STRING, NULL, "Gamma...", &OP_OpenGLColorDef, 20},
|
||||
|
||||
{IT_STRING|IT_CVAR, NULL, "Field of View", &cv_grfov, 35},
|
||||
{IT_STRING|IT_CVAR, NULL, "Field of View", &cv_fov, 35},
|
||||
{IT_STRING|IT_CVAR, NULL, "Quality", &cv_scr_depth, 45},
|
||||
{IT_STRING|IT_CVAR, NULL, "Texture Filter", &cv_grfiltermode, 55},
|
||||
{IT_STRING|IT_CVAR, NULL, "Anisotropic", &cv_granisotropicmode, 65},
|
||||
|
@ -1316,6 +1319,9 @@ static menuitem_t OP_SoundOptionsMenu[] =
|
|||
{IT_STRING|IT_CVAR, NULL, "Powerup Warning", &cv_kartinvinsfx, 95},
|
||||
|
||||
{IT_KEYHANDLER|IT_STRING, NULL, "Sound Test", M_HandleSoundTest, 110},
|
||||
|
||||
{IT_STRING|IT_CVAR, NULL, "Play Music While Unfocused", &cv_playmusicifunfocused, 125},
|
||||
{IT_STRING|IT_CVAR, NULL, "Play SFX While Unfocused", &cv_playsoundifunfocused, 135},
|
||||
};
|
||||
|
||||
/*static menuitem_t OP_DataOptionsMenu[] =
|
||||
|
@ -1390,7 +1396,7 @@ static menuitem_t OP_HUDOptionsMenu[] =
|
|||
{IT_STRING | IT_CVAR | IT_CV_SLIDER,
|
||||
NULL, "HUD Visibility", &cv_translucenthud, 20},
|
||||
|
||||
{IT_STRING | IT_SUBMENU, NULL, "Online chat options...",&OP_ChatOptionsDef, 35},
|
||||
{IT_STRING | IT_SUBMENU, NULL, "Online HUD options...",&OP_ChatOptionsDef, 35},
|
||||
{IT_STRING | IT_CVAR, NULL, "Background Glass", &cons_backcolor, 45},
|
||||
|
||||
{IT_STRING | IT_CVAR | IT_CV_SLIDER,
|
||||
|
@ -1402,8 +1408,11 @@ static menuitem_t OP_HUDOptionsMenu[] =
|
|||
// highlight info - (GOOD HIGHLIGHT, WARNING HIGHLIGHT) - 105 (see M_DrawHUDOptions)
|
||||
|
||||
{IT_STRING | IT_CVAR, NULL, "Console Text Size", &cv_constextsize, 120},
|
||||
|
||||
{IT_STRING | IT_CVAR, NULL, "Show \"FOCUS LOST\"", &cv_showfocuslost, 135},
|
||||
};
|
||||
|
||||
// Ok it's still called chatoptions but we'll put ping display in here to be clean
|
||||
static menuitem_t OP_ChatOptionsMenu[] =
|
||||
{
|
||||
// will ANYONE who doesn't know how to use the console want to touch this one?
|
||||
|
@ -1417,6 +1426,8 @@ static menuitem_t OP_ChatOptionsMenu[] =
|
|||
{IT_STRING | IT_CVAR, NULL, "Chat Background Tint", &cv_chatbacktint, 50},
|
||||
{IT_STRING | IT_CVAR, NULL, "Message Fadeout Time", &cv_chattime, 60},
|
||||
{IT_STRING | IT_CVAR, NULL, "Spam Protection", &cv_chatspamprotection, 70},
|
||||
|
||||
{IT_STRING | IT_CVAR, NULL, "Local ping display", &cv_showping, 90}, // shows ping next to framerate if we want to.
|
||||
};
|
||||
|
||||
static menuitem_t OP_GameOptionsMenu[] =
|
||||
|
@ -1469,15 +1480,16 @@ static menuitem_t OP_AdvServerOptionsMenu[] =
|
|||
|
||||
{IT_STRING | IT_CVAR, NULL, "Attempts to resynchronise", &cv_resynchattempts, 40},
|
||||
{IT_STRING | IT_CVAR, NULL, "Ping limit (ms)", &cv_maxping, 50},
|
||||
{IT_STRING | IT_CVAR, NULL, "Connection timeout (tics)", &cv_nettimeout, 60},
|
||||
{IT_STRING | IT_CVAR, NULL, "Join timeout (tics)", &cv_jointimeout, 70},
|
||||
{IT_STRING | IT_CVAR, NULL, "Ping timeout (s)", &cv_pingtimeout, 60},
|
||||
{IT_STRING | IT_CVAR, NULL, "Connection timeout (tics)", &cv_nettimeout, 70},
|
||||
{IT_STRING | IT_CVAR, NULL, "Join timeout (tics)", &cv_jointimeout, 80},
|
||||
|
||||
{IT_STRING | IT_CVAR, NULL, "Max. file transfer send (KB)", &cv_maxsend, 90},
|
||||
{IT_STRING | IT_CVAR, NULL, "File transfer packet rate", &cv_downloadspeed, 100},
|
||||
{IT_STRING | IT_CVAR, NULL, "Max. file transfer send (KB)", &cv_maxsend, 100},
|
||||
{IT_STRING | IT_CVAR, NULL, "File transfer packet rate", &cv_downloadspeed, 110},
|
||||
|
||||
{IT_STRING | IT_CVAR, NULL, "Log join addresses", &cv_showjoinaddress, 120},
|
||||
{IT_STRING | IT_CVAR, NULL, "Log resyncs", &cv_blamecfail, 130},
|
||||
{IT_STRING | IT_CVAR, NULL, "Log file transfers", &cv_noticedownload, 140},
|
||||
{IT_STRING | IT_CVAR, NULL, "Log join addresses", &cv_showjoinaddress, 130},
|
||||
{IT_STRING | IT_CVAR, NULL, "Log resyncs", &cv_blamecfail, 140},
|
||||
{IT_STRING | IT_CVAR, NULL, "Log file transfers", &cv_noticedownload, 150},
|
||||
};
|
||||
#endif
|
||||
|
||||
|
@ -2379,6 +2391,9 @@ static void M_NextOpt(void)
|
|||
{
|
||||
INT16 oldItemOn = itemOn; // prevent infinite loop
|
||||
|
||||
if ((currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_PASSWORD)
|
||||
((consvar_t *)currentMenu->menuitems[itemOn].itemaction)->value = 0;
|
||||
|
||||
do
|
||||
{
|
||||
if (itemOn + 1 > currentMenu->numitems - 1)
|
||||
|
@ -2392,6 +2407,9 @@ static void M_PrevOpt(void)
|
|||
{
|
||||
INT16 oldItemOn = itemOn; // prevent infinite loop
|
||||
|
||||
if ((currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_PASSWORD)
|
||||
((consvar_t *)currentMenu->menuitems[itemOn].itemaction)->value = 0;
|
||||
|
||||
do
|
||||
{
|
||||
if (!itemOn)
|
||||
|
@ -2678,8 +2696,11 @@ boolean M_Responder(event_t *ev)
|
|||
// BP: one of the more big hack i have never made
|
||||
if (routine && (currentMenu->menuitems[itemOn].status & IT_TYPE) == IT_CVAR)
|
||||
{
|
||||
if ((currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_STRING)
|
||||
if ((currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_STRING || (currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_PASSWORD)
|
||||
{
|
||||
if (ch == KEY_TAB && (currentMenu->menuitems[itemOn].status & IT_CVARTYPE) == IT_CV_PASSWORD)
|
||||
((consvar_t *)currentMenu->menuitems[itemOn].itemaction)->value ^= 1;
|
||||
|
||||
if (shiftdown && ch >= 32 && ch <= 127)
|
||||
ch = shiftxform[ch];
|
||||
if (M_ChangeStringCvar(ch))
|
||||
|
@ -2880,7 +2901,7 @@ void M_Drawer(void)
|
|||
}
|
||||
|
||||
// focus lost notification goes on top of everything, even the former everything
|
||||
if (window_notinfocus)
|
||||
if (window_notinfocus && cv_showfocuslost.value)
|
||||
{
|
||||
M_DrawTextBox((BASEVIDWIDTH/2) - (60), (BASEVIDHEIGHT/2) - (16), 13, 2);
|
||||
if (gamestate == GS_LEVEL && (P_AutoPause() || paused))
|
||||
|
@ -3453,7 +3474,7 @@ static void M_DrawMapEmblems(INT32 mapnum, INT32 x, INT32 y)
|
|||
|
||||
if (emblem->collected)
|
||||
V_DrawSmallMappedPatch(x, y, 0, W_CachePatchName(M_GetEmblemPatch(emblem), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_MENUCACHE));
|
||||
else
|
||||
V_DrawSmallScaledPatch(x, y, 0, W_CachePatchName("NEEDIT", PU_CACHE));
|
||||
|
||||
|
@ -3553,6 +3574,8 @@ static void M_DrawGenericMenu(void)
|
|||
case IT_CVAR:
|
||||
{
|
||||
consvar_t *cv = (consvar_t *)currentMenu->menuitems[i].itemaction;
|
||||
char asterisks[MAXSTRINGLENGTH+1];
|
||||
size_t sl;
|
||||
switch (currentMenu->menuitems[i].status & IT_CVARTYPE)
|
||||
{
|
||||
case IT_CV_SLIDER:
|
||||
|
@ -3560,6 +3583,27 @@ static void M_DrawGenericMenu(void)
|
|||
case IT_CV_NOPRINT: // color use this
|
||||
case IT_CV_INVISSLIDER: // monitor toggles use this
|
||||
break;
|
||||
case IT_CV_PASSWORD:
|
||||
if (i == itemOn)
|
||||
{
|
||||
V_DrawRightAlignedThinString(x + MAXSTRINGLENGTH*8 + 10, y, V_ALLOWLOWERCASE, va(M_GetText("Tab: %s password"), cv->value ? "hide" : "show"));
|
||||
}
|
||||
|
||||
if (!cv->value || i != itemOn)
|
||||
{
|
||||
sl = strlen(cv->string);
|
||||
memset(asterisks, '*', sl);
|
||||
memset(asterisks + sl, 0, MAXSTRINGLENGTH+1-sl);
|
||||
|
||||
M_DrawTextBox(x, y + 4, MAXSTRINGLENGTH, 1);
|
||||
V_DrawString(x + 8, y + 12, V_ALLOWLOWERCASE, asterisks);
|
||||
if (skullAnimCounter < 4 && i == itemOn)
|
||||
V_DrawCharacter(x + 8 + V_StringWidth(asterisks, 0), y + 12,
|
||||
'_' | 0x80, false);
|
||||
y += 16;
|
||||
break;
|
||||
}
|
||||
/* fallthru */
|
||||
case IT_CV_STRING:
|
||||
M_DrawTextBox(x, y + 4, MAXSTRINGLENGTH, 1);
|
||||
V_DrawString(x + 8, y + 12, V_ALLOWLOWERCASE, cv->string);
|
||||
|
@ -3767,7 +3811,7 @@ static void M_DrawPauseMenu(void)
|
|||
|
||||
if (emblem->collected)
|
||||
V_DrawSmallMappedPatch(40, 44 + (i*8), 0, W_CachePatchName(M_GetEmblemPatch(emblem), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_MENUCACHE));
|
||||
else
|
||||
V_DrawSmallScaledPatch(40, 44 + (i*8), 0, W_CachePatchName("NEEDIT", PU_CACHE));
|
||||
|
||||
|
@ -5315,7 +5359,7 @@ static void M_DrawEmblemHints(void)
|
|||
{
|
||||
collected = recommendedflags;
|
||||
V_DrawMappedPatch(12, 12+(28*j), 0, W_CachePatchName(M_GetEmblemPatch(emblem), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(emblem), GTC_MENUCACHE));
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5658,7 +5702,7 @@ static void M_DrawLoadGameData(void)
|
|||
V_DrawScaledPatch(SP_LoadDef.x,144+8,0,W_CachePatchName(skins[savegameinfo[saveSlotSelected].skinnum].face, PU_CACHE));
|
||||
else
|
||||
{
|
||||
UINT8 *colormap = R_GetTranslationColormap(savegameinfo[saveSlotSelected].skinnum, savegameinfo[saveSlotSelected].skincolor, 0);
|
||||
UINT8 *colormap = R_GetTranslationColormap(savegameinfo[saveSlotSelected].skinnum, savegameinfo[saveSlotSelected].skincolor, GTC_MENUCACHE);
|
||||
V_DrawMappedPatch(SP_LoadDef.x,144+8,0,W_CachePatchName(skins[savegameinfo[saveSlotSelected].skinnum].face, PU_CACHE), colormap);
|
||||
}
|
||||
|
||||
|
@ -6348,7 +6392,7 @@ static void M_DrawStatsMaps(int location)
|
|||
|
||||
if (exemblem->collected)
|
||||
V_DrawSmallMappedPatch(295, y, 0, W_CachePatchName(M_GetExtraEmblemPatch(exemblem), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetExtraEmblemColor(exemblem), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetExtraEmblemColor(exemblem), GTC_MENUCACHE));
|
||||
else
|
||||
V_DrawSmallScaledPatch(295, y, 0, W_CachePatchName("NEEDIT", PU_CACHE));
|
||||
|
||||
|
@ -6483,7 +6527,7 @@ void M_DrawTimeAttackMenu(void)
|
|||
// Character face!
|
||||
if (W_CheckNumForName(skins[cv_chooseskin.value-1].facewant) != LUMPERROR)
|
||||
{
|
||||
UINT8 *colormap = R_GetTranslationColormap(cv_chooseskin.value-1, cv_playercolor.value, 0);
|
||||
UINT8 *colormap = R_GetTranslationColormap(cv_chooseskin.value-1, cv_playercolor.value, GTC_MENUCACHE);
|
||||
V_DrawMappedPatch(BASEVIDWIDTH-x - SHORT(facewantprefix[cv_chooseskin.value-1]->width), y, 0, facewantprefix[cv_chooseskin.value-1], colormap);
|
||||
}
|
||||
|
||||
|
@ -6608,7 +6652,7 @@ void M_DrawTimeAttackMenu(void)
|
|||
|
||||
if (em->collected)
|
||||
V_DrawMappedPatch(BASEVIDWIDTH - 64 - 24, y+48, 0, W_CachePatchName(M_GetEmblemPatch(em), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(em), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(em), GTC_MENUCACHE));
|
||||
else
|
||||
V_DrawScaledPatch(BASEVIDWIDTH - 64 - 24, y+48, 0, W_CachePatchName("NEEDIT", PU_CACHE));
|
||||
|
||||
|
@ -6768,7 +6812,7 @@ static boolean M_QuitTimeAttackMenu(void)
|
|||
|
||||
if (em->collected)
|
||||
V_DrawSmallMappedPatch(160+88, yHeight, 0, W_CachePatchName(M_GetEmblemPatch(em), PU_CACHE),
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(em), GTC_CACHE));
|
||||
R_GetTranslationColormap(TC_DEFAULT, M_GetEmblemColor(em), GTC_MENUCACHE));
|
||||
else
|
||||
V_DrawSmallScaledPatch(160+88, yHeight, 0, W_CachePatchName("NEEDIT", PU_CACHE));
|
||||
|
||||
|
@ -7237,6 +7281,7 @@ static void M_DrawConnectMenu(void)
|
|||
{
|
||||
UINT16 i, j;
|
||||
const char *gt = "Unknown";
|
||||
const char *spd = "";
|
||||
INT32 numPages = (serverlistcount+(SERVERS_PER_PAGE-1))/SERVERS_PER_PAGE;
|
||||
|
||||
for (i = FIRSTSERVERLINE; i < min(localservercount, SERVERS_PER_PAGE)+FIRSTSERVERLINE; i++)
|
||||
|
@ -7290,7 +7335,17 @@ static void M_DrawConnectMenu(void)
|
|||
V_DrawSmallString(currentMenu->x+46,S_LINEY(i)+8, globalflags,
|
||||
va("Players: %02d/%02d", serverlist[slindex].info.numberofplayer, serverlist[slindex].info.maxplayer));
|
||||
|
||||
V_DrawSmallString(currentMenu->x+112, S_LINEY(i)+8, globalflags, va("Gametype: %s", gt));
|
||||
V_DrawSmallString(currentMenu->x+112, S_LINEY(i)+8, globalflags, gt);
|
||||
|
||||
if (serverlist[slindex].info.gametype == GT_RACE)
|
||||
{
|
||||
spd = kartspeed_cons_t[serverlist[slindex].info.kartvars & SV_SPEEDMASK].strvalue;
|
||||
|
||||
V_DrawSmallString(currentMenu->x+132, S_LINEY(i)+8, globalflags, va("(%s Speed)", spd));
|
||||
}
|
||||
|
||||
if (serverlist[slindex].info.kartvars & SV_PASSWORD)
|
||||
V_DrawFixedPatch((currentMenu->x - 9) << FRACBITS, (S_LINEY(i)) << FRACBITS, FRACUNIT, globalflags & (~V_ALLOWLOWERCASE), W_CachePatchName("SERVLOCK", PU_CACHE), NULL);
|
||||
|
||||
MP_ConnectMenu[i+FIRSTSERVERLINE].status = IT_STRING | IT_CALL;
|
||||
}
|
||||
|
@ -7525,6 +7580,11 @@ static void M_StartServer(INT32 choice)
|
|||
// Still need to reset devmode
|
||||
cv_debug = 0;
|
||||
|
||||
if (strlen(cv_dummyjoinpassword.string) > 0)
|
||||
D_SetJoinPassword(cv_dummyjoinpassword.string);
|
||||
else
|
||||
joinpasswordset = false;
|
||||
|
||||
if (demoplayback)
|
||||
G_StopDemo();
|
||||
if (metalrecording)
|
||||
|
@ -7826,7 +7886,7 @@ Update the maxplayers label...
|
|||
if (!trans && i > cv_splitplayers.value)
|
||||
trans = V_TRANSLUCENT;
|
||||
|
||||
colmap = R_GetTranslationColormap(pskin, pcol, 0);
|
||||
colmap = R_GetTranslationColormap(pskin, pcol, GTC_MENUCACHE);
|
||||
|
||||
V_DrawFixedPatch(x<<FRACBITS, y<<FRACBITS, FRACUNIT, trans, facewantprefix[pskin], colmap);
|
||||
|
||||
|
@ -8137,7 +8197,7 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
|
||||
statdot = W_CachePatchName("K_SDOT2", PU_CACHE); // coloured center
|
||||
if (setupm_fakecolor)
|
||||
V_DrawFixedPatch(((BASEVIDWIDTH - mx - 80) + ((speed-1)*8))<<FRACBITS, ((my+76) + ((weight-1)*8))<<FRACBITS, FRACUNIT, 0, statdot, R_GetTranslationColormap(0, setupm_fakecolor, 0));
|
||||
V_DrawFixedPatch(((BASEVIDWIDTH - mx - 80) + ((speed-1)*8))<<FRACBITS, ((my+76) + ((weight-1)*8))<<FRACBITS, FRACUNIT, 0, statdot, R_GetTranslationColormap(0, setupm_fakecolor, GTC_MENUCACHE));
|
||||
|
||||
// 2.2 color bar backported with permission
|
||||
#define charw 72
|
||||
|
@ -8207,7 +8267,7 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
offx = 8;
|
||||
offy = 8;
|
||||
}
|
||||
colmap = R_GetTranslationColormap(col, setupm_fakecolor, 0);
|
||||
colmap = R_GetTranslationColormap(col, setupm_fakecolor, GTC_MENUCACHE);
|
||||
V_DrawFixedPatch((x+offx)<<FRACBITS, (my+28+offy)<<FRACBITS, FRACUNIT, 0, face, colmap);
|
||||
if (scale == FRACUNIT) // bit of a hack
|
||||
V_DrawFixedPatch((x+offx)<<FRACBITS, (my+28+offy)<<FRACBITS, FRACUNIT, 0, cursor, colmap);
|
||||
|
@ -8253,7 +8313,7 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
// draw player sprite
|
||||
if (setupm_fakecolor) // inverse should never happen
|
||||
{
|
||||
UINT8 *colormap = R_GetTranslationColormap(setupm_fakeskin, setupm_fakecolor, 0);
|
||||
UINT8 *colormap = R_GetTranslationColormap(setupm_fakeskin, setupm_fakecolor, GTC_MENUCACHE);
|
||||
|
||||
if (skins[setupm_fakeskin].flags & SF_HIRES)
|
||||
{
|
||||
|
@ -8264,8 +8324,6 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
}
|
||||
else
|
||||
V_DrawMappedPatch(mx+43, my+131, flags, patch, colormap);
|
||||
|
||||
Z_Free(colormap);
|
||||
}
|
||||
#undef charw
|
||||
}
|
||||
|
|
|
@ -104,6 +104,7 @@ boolean M_CanShowLevelInList(INT32 mapnum, INT32 gt);
|
|||
#define IT_CV_NOPRINT 1536
|
||||
#define IT_CV_NOMOD 2048
|
||||
#define IT_CV_INVISSLIDER 2560
|
||||
#define IT_CV_PASSWORD 3072
|
||||
|
||||
//call/submenu specific
|
||||
// There used to be a lot more here but ...
|
||||
|
@ -211,6 +212,7 @@ typedef struct
|
|||
|
||||
extern description_t description[32];
|
||||
|
||||
extern consvar_t cv_showfocuslost;
|
||||
extern consvar_t cv_newgametype, cv_nextmap, cv_chooseskin, cv_serversort;
|
||||
extern CV_PossibleValue_t gametype_cons_t[];
|
||||
|
||||
|
|
|
@ -22,6 +22,8 @@
|
|||
# include <limits.h>
|
||||
#endif
|
||||
|
||||
#define MD5_LEN 16
|
||||
|
||||
/* The following contortions are an attempt to use the C preprocessor
|
||||
to determine an unsigned integral type that is 32 bits wide. An
|
||||
alternative approach is to use autoconf's AC_CHECK_SIZEOF macro, but
|
||||
|
|
|
@ -8640,6 +8640,7 @@ void A_LightningFollowPlayer(mobj_t *actor)
|
|||
else // else just teleport to player directly
|
||||
P_TeleportMove(actor, actor->target->x, actor->target->y, actor->target->z);
|
||||
|
||||
K_MatchGenericExtraFlags(actor, actor->target); // copy our target for graviflip
|
||||
actor->momx = actor->target->momx;
|
||||
actor->momy = actor->target->momy;
|
||||
actor->momz = actor->target->momz; // Give momentum since we don't teleport to our player literally every frame.
|
||||
|
|
|
@ -141,6 +141,9 @@ boolean P_CanPickupItem(player_t *player, UINT8 weapon)
|
|||
|| (weapon != 3 && player->kartstuff[k_itemamount])
|
||||
|| player->kartstuff[k_itemheld])
|
||||
return false;
|
||||
|
||||
if (weapon == 3 && player->kartstuff[k_itemtype] == KITEM_THUNDERSHIELD)
|
||||
return false; // No stacking thunder shields!
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -411,6 +414,12 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck)
|
|||
player->kartstuff[k_roulettetype] = 2;
|
||||
}
|
||||
|
||||
#if 0
|
||||
// Eggbox snipe!
|
||||
if (special->type == MT_EGGMANITEM && special->health > 1)
|
||||
S_StartSound(toucher, sfx_bsnipe);
|
||||
#endif
|
||||
|
||||
{
|
||||
mobj_t *poof = P_SpawnMobj(special->x, special->y, special->z, MT_EXPLODE);
|
||||
S_StartSound(poof, special->info->deathsound);
|
||||
|
@ -1468,6 +1477,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck)
|
|||
player->starpostz = special->z>>FRACBITS;
|
||||
player->starpostangle = special->angle;
|
||||
player->starpostnum = special->health;
|
||||
player->kartstuff[k_starpostflip] = special->spawnpoint->options & MTF_OBJECTFLIP; // store flipping
|
||||
|
||||
//S_StartSound(toucher, special->info->painsound);
|
||||
return;
|
||||
|
@ -2952,66 +2962,6 @@ static void P_KillPlayer(player_t *player, mobj_t *source, INT32 damage)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
static inline void P_SuperDamage(player_t *player, mobj_t *inflictor, mobj_t *source, INT32 damage) // SRB2kart - unused.
|
||||
{
|
||||
fixed_t fallbackspeed;
|
||||
angle_t ang;
|
||||
|
||||
P_ForceFeed(player, 40, 10, TICRATE, 40 + min(damage, 100)*2);
|
||||
|
||||
if (player->mo->eflags & MFE_VERTICALFLIP)
|
||||
player->mo->z--;
|
||||
else
|
||||
player->mo->z++;
|
||||
|
||||
if (player->mo->eflags & MFE_UNDERWATER)
|
||||
P_SetObjectMomZ(player->mo, FixedDiv(10511*FRACUNIT,2600*FRACUNIT), false);
|
||||
else
|
||||
P_SetObjectMomZ(player->mo, FixedDiv(69*FRACUNIT,10*FRACUNIT), false);
|
||||
|
||||
ang = R_PointToAngle2(inflictor->x, inflictor->y, player->mo->x, player->mo->y);
|
||||
|
||||
// explosion and rail rings send you farther back, making it more difficult
|
||||
// to recover
|
||||
if (inflictor->flags2 & MF2_SCATTER && source)
|
||||
{
|
||||
fixed_t dist = P_AproxDistance(P_AproxDistance(source->x-player->mo->x, source->y-player->mo->y), source->z-player->mo->z);
|
||||
|
||||
dist = FixedMul(128*FRACUNIT, inflictor->scale) - dist/4;
|
||||
|
||||
if (dist < FixedMul(4*FRACUNIT, inflictor->scale))
|
||||
dist = FixedMul(4*FRACUNIT, inflictor->scale);
|
||||
|
||||
fallbackspeed = dist;
|
||||
}
|
||||
else if (inflictor->flags2 & MF2_EXPLOSION)
|
||||
{
|
||||
if (inflictor->flags2 & MF2_RAILRING)
|
||||
fallbackspeed = FixedMul(28*FRACUNIT, inflictor->scale); // 7x
|
||||
else
|
||||
fallbackspeed = FixedMul(20*FRACUNIT, inflictor->scale); // 5x
|
||||
}
|
||||
else if (inflictor->flags2 & MF2_RAILRING)
|
||||
fallbackspeed = FixedMul(16*FRACUNIT, inflictor->scale); // 4x
|
||||
else
|
||||
fallbackspeed = FixedMul(4*FRACUNIT, inflictor->scale); // the usual amount of force
|
||||
|
||||
P_InstaThrust(player->mo, ang, fallbackspeed);
|
||||
|
||||
// SRB2kart - This shouldn't be reachable, but this frame is invalid.
|
||||
//if (player->charflags & SF_SUPERANIMS)
|
||||
// P_SetPlayerMobjState(player->mo, S_PLAY_SUPERHIT);
|
||||
//else
|
||||
P_SetPlayerMobjState(player->mo, player->mo->info->painstate);
|
||||
|
||||
P_ResetPlayer(player);
|
||||
|
||||
if (player->timeshit != UINT8_MAX)
|
||||
++player->timeshit;
|
||||
}
|
||||
*/
|
||||
|
||||
void P_RemoveShield(player_t *player)
|
||||
{
|
||||
if (player->powers[pw_shield] & SH_FORCE)
|
||||
|
|
|
@ -274,8 +274,6 @@ boolean P_CameraThinker(player_t *player, camera_t *thiscam, boolean resetcalled
|
|||
void P_Attract(mobj_t *source, mobj_t *enemy, boolean nightsgrab);
|
||||
mobj_t *P_GetClosestAxis(mobj_t *source);
|
||||
|
||||
boolean P_CanRunOnWater(player_t *player, ffloor_t *rover);
|
||||
|
||||
void P_FlashPal(player_t *pl, UINT16 type, UINT16 duration);
|
||||
#define PAL_WHITE 1
|
||||
#define PAL_MIXUP 2
|
||||
|
|
38
src/p_map.c
38
src/p_map.c
|
@ -747,6 +747,9 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
&& !(tmthing->type == MT_ORBINAUT || tmthing->type == MT_JAWZ || tmthing->type == MT_JAWZ_DUD))
|
||||
return true;
|
||||
|
||||
if (thing->player && thing->player->kartstuff[k_hyudorotimer])
|
||||
return true; // no interaction
|
||||
|
||||
if (thing->type == MT_PLAYER)
|
||||
{
|
||||
// Player Damage
|
||||
|
@ -850,7 +853,7 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
|
||||
if (thing->type == MT_PLAYER)
|
||||
{
|
||||
S_StartSound(NULL, sfx_cgot); //let all players hear it.
|
||||
S_StartSound(NULL, sfx_bsnipe); //let all players hear it.
|
||||
HU_SetCEchoFlags(0);
|
||||
HU_SetCEchoDuration(5);
|
||||
HU_DoCEcho(va("%s\\was hit by a kitchen sink.\\\\\\\\", player_names[thing->player-players]));
|
||||
|
@ -912,6 +915,10 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
|
||||
if (thing->type == MT_PLAYER)
|
||||
{
|
||||
// Banana snipe!
|
||||
if (tmthing->type == MT_BANANA && tmthing->health > 1)
|
||||
S_StartSound(thing, sfx_bsnipe);
|
||||
|
||||
// Player Damage
|
||||
K_SpinPlayer(thing->player, tmthing->target, 0, tmthing, (tmthing->type == MT_BANANA || tmthing->type == MT_BANANA_SHIELD));
|
||||
|
||||
|
@ -980,7 +987,12 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
|
||||
if (thing->type == MT_PLAYER)
|
||||
{
|
||||
P_KillMobj(tmthing, thing, thing);
|
||||
// Bomb punting
|
||||
if ((tmthing->state >= &states[S_SSMINE1] && tmthing->state <= &states[S_SSMINE4])
|
||||
|| (tmthing->state >= &states[S_SSMINE_DEPLOY8] && tmthing->state <= &states[S_SSMINE_DEPLOY13]))
|
||||
P_KillMobj(tmthing, thing, thing);
|
||||
else
|
||||
K_PuntMine(tmthing, thing);
|
||||
}
|
||||
else if (thing->type == MT_ORBINAUT || thing->type == MT_JAWZ || thing->type == MT_JAWZ_DUD
|
||||
|| thing->type == MT_ORBINAUT_SHIELD || thing->type == MT_JAWZ_SHIELD)
|
||||
|
@ -1021,6 +1033,9 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
&& !(thing->type == MT_ORBINAUT || thing->type == MT_JAWZ || thing->type == MT_JAWZ_DUD))
|
||||
return true;
|
||||
|
||||
if (tmthing->player && tmthing->player->kartstuff[k_hyudorotimer]) // I thought about doing this for just the objects below but figured it should apply to everything.
|
||||
return true; // no interaction
|
||||
|
||||
if (thing->type == MT_ORBINAUT_SHIELD || thing->type == MT_JAWZ_SHIELD
|
||||
|| thing->type == MT_ORBINAUT || thing->type == MT_JAWZ || thing->type == MT_JAWZ_DUD)
|
||||
{
|
||||
|
@ -1056,6 +1071,10 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
if (tmthing->health <= 0 || thing->health <= 0)
|
||||
return true;
|
||||
|
||||
// Banana snipe!
|
||||
if (thing->type == MT_BANANA && thing->health > 1)
|
||||
S_StartSound(tmthing, sfx_bsnipe);
|
||||
|
||||
// Player Damage
|
||||
K_SpinPlayer(tmthing->player, thing->target, 0, tmthing, (thing->type == MT_BANANA || thing->type == MT_BANANA_SHIELD));
|
||||
|
||||
|
@ -1079,7 +1098,12 @@ static boolean PIT_CheckThing(mobj_t *thing)
|
|||
if (tmthing->health <= 0 || thing->health <= 0)
|
||||
return true;
|
||||
|
||||
P_KillMobj(thing, tmthing, tmthing);
|
||||
// Bomb punting
|
||||
if ((thing->state >= &states[S_SSMINE1] && thing->state <= &states[S_SSMINE4])
|
||||
|| (thing->state >= &states[S_SSMINE_DEPLOY8] && thing->state <= &states[S_SSMINE_DEPLOY13]))
|
||||
P_KillMobj(thing, tmthing, tmthing);
|
||||
else
|
||||
K_PuntMine(thing, tmthing);
|
||||
}
|
||||
else if (thing->type == MT_MINEEXPLOSION && tmthing->player)
|
||||
{
|
||||
|
@ -2090,7 +2114,7 @@ boolean P_CheckPosition(mobj_t *thing, fixed_t x, fixed_t y)
|
|||
continue;
|
||||
}
|
||||
|
||||
if (thing->player && (P_CheckSolidLava(thing, rover) || P_CanRunOnWater(thing->player, rover)))
|
||||
if (thing->player && P_CheckSolidLava(thing, rover))
|
||||
;
|
||||
else if (thing->type == MT_SKIM && (rover->flags & FF_SWIMMABLE))
|
||||
;
|
||||
|
@ -2763,8 +2787,7 @@ boolean P_TryMove(mobj_t *thing, fixed_t x, fixed_t y, boolean allowdropoff)
|
|||
thing->eflags |= MFE_JUSTSTEPPEDDOWN;
|
||||
}
|
||||
#ifdef ESLOPE
|
||||
// HACK TO FIX DSZ2: apply only if slopes are involved
|
||||
else if (tmceilingslope && tmceilingz < thingtop && thingtop - tmceilingz <= maxstep)
|
||||
else if (tmceilingz < thingtop && thingtop - tmceilingz <= maxstep)
|
||||
{
|
||||
thing->z = (thing->ceilingz = thingtop = tmceilingz) - thing->height;
|
||||
thing->eflags |= MFE_JUSTSTEPPEDDOWN;
|
||||
|
@ -2777,8 +2800,7 @@ boolean P_TryMove(mobj_t *thing, fixed_t x, fixed_t y, boolean allowdropoff)
|
|||
thing->eflags |= MFE_JUSTSTEPPEDDOWN;
|
||||
}
|
||||
#ifdef ESLOPE
|
||||
// HACK TO FIX DSZ2: apply only if slopes are involved
|
||||
else if (tmfloorslope && tmfloorz > thing->z && tmfloorz - thing->z <= maxstep)
|
||||
else if (tmfloorz > thing->z && tmfloorz - thing->z <= maxstep)
|
||||
{
|
||||
thing->z = thing->floorz = tmfloorz;
|
||||
thing->eflags |= MFE_JUSTSTEPPEDDOWN;
|
||||
|
|
|
@ -649,7 +649,7 @@ void P_LineOpening(line_t *linedef, mobj_t *mobj)
|
|||
if (!(rover->flags & FF_EXISTS))
|
||||
continue;
|
||||
|
||||
if (mobj->player && (P_CheckSolidLava(mobj, rover) || P_CanRunOnWater(mobj->player, rover)))
|
||||
if (mobj->player && P_CheckSolidLava(mobj, rover))
|
||||
;
|
||||
else if (!((rover->flags & FF_BLOCKPLAYER && mobj->player)
|
||||
|| (rover->flags & FF_BLOCKOTHERS && !mobj->player)))
|
||||
|
@ -693,7 +693,7 @@ void P_LineOpening(line_t *linedef, mobj_t *mobj)
|
|||
if (!(rover->flags & FF_EXISTS))
|
||||
continue;
|
||||
|
||||
if (mobj->player && (P_CheckSolidLava(mobj, rover) || P_CanRunOnWater(mobj->player, rover)))
|
||||
if (mobj->player && P_CheckSolidLava(mobj, rover))
|
||||
;
|
||||
else if (!((rover->flags & FF_BLOCKPLAYER && mobj->player)
|
||||
|| (rover->flags & FF_BLOCKOTHERS && !mobj->player)))
|
||||
|
|
201
src/p_mobj.c
201
src/p_mobj.c
|
@ -167,58 +167,8 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
|
|||
I_Error("P_SetPlayerMobjState used for non-player mobj. Use P_SetMobjState instead!\n(Mobj type: %d, State: %d)", mobj->type, state);
|
||||
#endif
|
||||
|
||||
// Catch state changes for Super Sonic
|
||||
/* // SRB2kart - don't need
|
||||
if (player->powers[pw_super] && (player->charflags & SF_SUPERANIMS))
|
||||
{
|
||||
switch (state)
|
||||
{
|
||||
case S_PLAY_STND:
|
||||
case S_PLAY_TAP1:
|
||||
case S_PLAY_TAP2:
|
||||
case S_PLAY_GASP:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERSTAND);
|
||||
return true;
|
||||
case S_PLAY_FALL1:
|
||||
case S_PLAY_SPRING:
|
||||
case S_PLAY_RUN1:
|
||||
case S_PLAY_RUN2:
|
||||
case S_PLAY_RUN3:
|
||||
case S_PLAY_RUN4:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERWALK1);
|
||||
return true;
|
||||
case S_PLAY_FALL2:
|
||||
case S_PLAY_RUN5:
|
||||
case S_PLAY_RUN6:
|
||||
case S_PLAY_RUN7:
|
||||
case S_PLAY_RUN8:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERWALK2);
|
||||
return true;
|
||||
case S_PLAY_SPD1:
|
||||
case S_PLAY_SPD2:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERFLY1);
|
||||
return true;
|
||||
case S_PLAY_SPD3:
|
||||
case S_PLAY_SPD4:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERFLY2);
|
||||
return true;
|
||||
case S_PLAY_TEETER1:
|
||||
case S_PLAY_TEETER2:
|
||||
P_SetPlayerMobjState(mobj, S_PLAY_SUPERTEETER);
|
||||
return true;
|
||||
case S_PLAY_ATK1:
|
||||
case S_PLAY_ATK2:
|
||||
case S_PLAY_ATK3:
|
||||
case S_PLAY_ATK4:
|
||||
if (!(player->charflags & SF_SUPERSPIN))
|
||||
return true;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
// You were in pain state after taking a hit, and you're moving out of pain state now?
|
||||
else */if (mobj->state == &states[mobj->info->painstate] && player->powers[pw_flashing] == K_GetKartFlashing(player) && state != mobj->info->painstate)
|
||||
if (mobj->state == &states[mobj->info->painstate] && player->powers[pw_flashing] == K_GetKartFlashing(player) && state != mobj->info->painstate)
|
||||
{
|
||||
// Start flashing, since you've landed.
|
||||
player->powers[pw_flashing] = K_GetKartFlashing(player)-1;
|
||||
|
@ -260,51 +210,6 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
|
|||
st = &states[state];
|
||||
mobj->state = st;
|
||||
mobj->tics = st->tics;
|
||||
|
||||
// Adjust the player's animation speed to match their velocity.
|
||||
if (!(disableSpeedAdjust || player->charflags & SF_NOSPEEDADJUST))
|
||||
{
|
||||
fixed_t speed = FixedDiv(player->speed, FixedMul(mobj->scale, player->mo->movefactor)); // fixed_t speed = FixedDiv(player->speed, mobj->scale);
|
||||
if (player->panim == PA_ROLL)
|
||||
{
|
||||
if (speed > 16<<FRACBITS)
|
||||
mobj->tics = 1;
|
||||
else
|
||||
mobj->tics = 2;
|
||||
}
|
||||
else if (player->panim == PA_FALL)
|
||||
{
|
||||
speed = FixedDiv(abs(mobj->momz), mobj->scale);
|
||||
if (speed < 10<<FRACBITS)
|
||||
mobj->tics = 4;
|
||||
else if (speed < 20<<FRACBITS)
|
||||
mobj->tics = 3;
|
||||
else if (speed < 30<<FRACBITS)
|
||||
mobj->tics = 2;
|
||||
else
|
||||
mobj->tics = 1;
|
||||
}
|
||||
else if (P_IsObjectOnGround(mobj) || player->powers[pw_super]) // Only if on the ground or superflying.
|
||||
{
|
||||
if (player->panim == PA_WALK)
|
||||
{
|
||||
if (speed > 12<<FRACBITS)
|
||||
mobj->tics = 2;
|
||||
else if (speed > 6<<FRACBITS)
|
||||
mobj->tics = 3;
|
||||
else
|
||||
mobj->tics = 4;
|
||||
}
|
||||
else if (player->panim == PA_RUN)
|
||||
{
|
||||
if (speed > 52<<FRACBITS)
|
||||
mobj->tics = 1;
|
||||
else
|
||||
mobj->tics = 2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
mobj->sprite = st->sprite;
|
||||
mobj->frame = st->frame;
|
||||
mobj->anim_duration = (UINT16)st->var2; // only used if FF_ANIMATE is set
|
||||
|
@ -1404,11 +1309,14 @@ fixed_t P_GetMobjGravity(mobj_t *mo)
|
|||
break;
|
||||
case MT_BANANA:
|
||||
case MT_EGGMANITEM:
|
||||
case MT_SSMINE:
|
||||
case MT_SINK:
|
||||
if (mo->extravalue2 > 0)
|
||||
gravityadd *= mo->extravalue2;
|
||||
/* FALLTHRU */
|
||||
case MT_ORBINAUT:
|
||||
case MT_JAWZ:
|
||||
case MT_JAWZ_DUD:
|
||||
case MT_SSMINE:
|
||||
case MT_SINK:
|
||||
gravityadd = (5*gravityadd)/2;
|
||||
break;
|
||||
case MT_SIGN:
|
||||
|
@ -2099,7 +2007,7 @@ static void P_AdjustMobjFloorZ_FFloors(mobj_t *mo, sector_t *sector, UINT8 motyp
|
|||
topheight = P_GetFOFTopZ(mo, sector, rover, mo->x, mo->y, NULL);
|
||||
bottomheight = P_GetFOFBottomZ(mo, sector, rover, mo->x, mo->y, NULL);
|
||||
|
||||
if (mo->player && (P_CheckSolidLava(mo, rover) || P_CanRunOnWater(mo->player, rover))) // only the player should be affected
|
||||
if (mo->player && P_CheckSolidLava(mo, rover)) // only the player should be affected
|
||||
;
|
||||
else if (motype != 0 && rover->flags & FF_SWIMMABLE) // "scenery" only
|
||||
continue;
|
||||
|
@ -3222,27 +3130,6 @@ static boolean P_SceneryZMovement(mobj_t *mo)
|
|||
return true;
|
||||
}
|
||||
|
||||
// P_CanRunOnWater
|
||||
//
|
||||
// Returns true if player can waterrun on the 3D floor
|
||||
//
|
||||
boolean P_CanRunOnWater(player_t *player, ffloor_t *rover)
|
||||
{
|
||||
fixed_t topheight =
|
||||
#ifdef ESLOPE
|
||||
*rover->t_slope ? P_GetZAt(*rover->t_slope, player->mo->x, player->mo->y) :
|
||||
#endif
|
||||
*rover->topheight;
|
||||
|
||||
if (((player->charflags & SF_RUNONWATER) && player->mo->ceilingz-topheight >= player->mo->height)
|
||||
&& (rover->flags & FF_SWIMMABLE) && !(player->pflags & PF_SPINNING) && player->speed > FixedMul(player->runspeed, player->mo->scale)
|
||||
&& !(player->pflags & PF_SLIDING)
|
||||
&& abs(player->mo->z - topheight) < FixedMul(30*FRACUNIT, player->mo->scale))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
//
|
||||
// P_MobjCheckWater
|
||||
//
|
||||
|
@ -3399,8 +3286,8 @@ void P_MobjCheckWater(mobj_t *mobj)
|
|||
|
||||
// skipping stone!
|
||||
if (p && p->kartstuff[k_waterskip] < 2
|
||||
&& ((p->speed/2 > abs(mobj->momz)) // Going more forward than horizontal, so you can skip across the water.
|
||||
|| (p->speed > K_GetKartSpeed(p,false)/4 && p->kartstuff[k_waterskip])) // Already skipped once, so you can skip once more!
|
||||
&& ((p->speed/3 > abs(mobj->momz)) // Going more forward than horizontal, so you can skip across the water.
|
||||
|| (p->speed > K_GetKartSpeed(p,false)/3 && p->kartstuff[k_waterskip])) // Already skipped once, so you can skip once more!
|
||||
&& ((!(mobj->eflags & MFE_VERTICALFLIP) && thingtop - mobj->momz > mobj->watertop)
|
||||
|| ((mobj->eflags & MFE_VERTICALFLIP) && mobj->z - mobj->momz < mobj->waterbottom)))
|
||||
{
|
||||
|
@ -6637,7 +6524,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
case MT_SINK_SHIELD:
|
||||
if ((mobj->health > 0
|
||||
&& (!mobj->target || !mobj->target->player || mobj->target->player->health <= 0 || mobj->target->player->spectator))
|
||||
|| (mobj->health <= 0 && mobj->z <= mobj->floorz)
|
||||
|| (mobj->health <= 0 && P_IsObjectOnGround(mobj))
|
||||
|| P_CheckDeathPitCollide(mobj)) // When in death state
|
||||
{
|
||||
P_RemoveMobj(mobj);
|
||||
|
@ -6651,19 +6538,22 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
fixed_t y = P_RandomRange(-35, 35)*mobj->scale;
|
||||
fixed_t z = P_RandomRange(0, 70)*mobj->scale;
|
||||
mobj_t *smoke = P_SpawnMobj(mobj->x + x, mobj->y + y, mobj->z + z, MT_SMOKE);
|
||||
P_SetMobjState(smoke, S_OPAQUESMOKE1);
|
||||
K_MatchGenericExtraFlags(smoke, mobj);
|
||||
smoke->scale = mobj->scale * 2;
|
||||
smoke->destscale = mobj->scale * 6;
|
||||
smoke->momz = P_RandomRange(4, 9)*FRACUNIT;
|
||||
smoke->momz = P_RandomRange(4, 9)*FRACUNIT*P_MobjFlip(smoke);
|
||||
}
|
||||
break;
|
||||
case MT_BOOMPARTICLE:
|
||||
{
|
||||
fixed_t x = P_RandomRange(-16, 16)*mobj->scale;
|
||||
fixed_t y = P_RandomRange(-16, 16)*mobj->scale;
|
||||
fixed_t z = P_RandomRange(0, 32)*mobj->scale;
|
||||
fixed_t z = P_RandomRange(0, 32)*mobj->scale*P_MobjFlip(mobj);
|
||||
if (leveltime % 2 == 0)
|
||||
{
|
||||
mobj_t *smoke = P_SpawnMobj(mobj->x + x, mobj->y + y, mobj->z + z, MT_BOSSEXPLODE);
|
||||
K_MatchGenericExtraFlags(smoke, mobj);
|
||||
P_SetMobjState(smoke, S_QUICKBOOM1);
|
||||
smoke->scale = mobj->scale/2;
|
||||
smoke->destscale = mobj->scale;
|
||||
|
@ -6672,6 +6562,8 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
else
|
||||
{
|
||||
mobj_t *smoke = P_SpawnMobj(mobj->x + x, mobj->y + y, mobj->z + z, MT_SMOKE);
|
||||
P_SetMobjState(smoke, S_OPAQUESMOKE1);
|
||||
K_MatchGenericExtraFlags(smoke, mobj);
|
||||
smoke->scale = mobj->scale;
|
||||
smoke->destscale = mobj->scale*2;
|
||||
}
|
||||
|
@ -6777,7 +6669,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
}
|
||||
else if ((mobj->health > 0
|
||||
&& (!mobj->target || !mobj->target->player || !mobj->target->player->mo || mobj->target->player->health <= 0 || mobj->target->player->spectator))
|
||||
|| (mobj->health <= 0 && mobj->z <= mobj->floorz)
|
||||
|| (mobj->health <= 0 && P_IsObjectOnGround(mobj))
|
||||
|| P_CheckDeathPitCollide(mobj)) // When in death state
|
||||
{
|
||||
P_RemoveMobj(mobj);
|
||||
|
@ -7225,6 +7117,9 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
y = mobj->target->y;
|
||||
z = mobj->target->z + (80*mapobjectscale);
|
||||
}
|
||||
if (mobj->target->eflags & MFE_VERTICALFLIP)
|
||||
z += mobj->target->height - FixedMul(mobj->target->scale, mobj->height);
|
||||
|
||||
P_TeleportMove(mobj, x, y, z);
|
||||
}
|
||||
break;
|
||||
|
@ -7420,7 +7315,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
case MT_BANANA:
|
||||
case MT_EGGMANITEM:
|
||||
case MT_SPB:
|
||||
if (mobj->z <= mobj->floorz)
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
{
|
||||
P_RemoveMobj(mobj);
|
||||
return;
|
||||
|
@ -7433,7 +7328,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
break;
|
||||
case MT_JAWZ:
|
||||
case MT_JAWZ_DUD:
|
||||
if (mobj->z <= mobj->floorz)
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
P_SetMobjState(mobj, mobj->info->xdeathstate);
|
||||
// fallthru
|
||||
case MT_JAWZ_SHIELD:
|
||||
|
@ -7467,7 +7362,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
/* FALLTHRU */
|
||||
case MT_SMK_MOLE:
|
||||
mobj->flags2 ^= MF2_DONTDRAW;
|
||||
if (mobj->z <= mobj->floorz)
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
{
|
||||
P_RemoveMobj(mobj);
|
||||
return;
|
||||
|
@ -7488,7 +7383,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
}
|
||||
|
||||
mobj->flags2 ^= MF2_DONTDRAW;
|
||||
if (mobj->z <= mobj->floorz)
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
{
|
||||
P_RemoveMobj(mobj);
|
||||
return;
|
||||
|
@ -8157,7 +8052,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
mobj->friction = ORIG_FRICTION/4;
|
||||
if (mobj->momx || mobj->momy)
|
||||
P_SpawnGhostMobj(mobj);
|
||||
if (mobj->z <= mobj->floorz && mobj->health > 1)
|
||||
if (P_IsObjectOnGround(mobj) && mobj->health > 1)
|
||||
{
|
||||
S_StartSound(mobj, mobj->info->activesound);
|
||||
mobj->momx = mobj->momy = 0;
|
||||
|
@ -8177,7 +8072,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
case MT_SINK:
|
||||
if (mobj->momx || mobj->momy)
|
||||
P_SpawnGhostMobj(mobj);
|
||||
if (mobj->z <= mobj->floorz)
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
{
|
||||
S_StartSound(mobj, mobj->info->deathsound);
|
||||
P_SetMobjState(mobj, S_NULL);
|
||||
|
@ -8190,28 +8085,26 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
mobj->color = mobj->target->player->skincolor;
|
||||
else
|
||||
mobj->color = SKINCOLOR_KETCHUP;
|
||||
|
||||
if (mobj->momx || mobj->momy)
|
||||
P_SpawnGhostMobj(mobj);
|
||||
if (P_IsObjectOnGround(mobj))
|
||||
|
||||
if (P_IsObjectOnGround(mobj) && (mobj->state == &states[S_SSMINE_AIR1] || mobj->state == &states[S_SSMINE_AIR2]))
|
||||
{
|
||||
if (mobj->state == &states[S_SSMINE_AIR1] || mobj->state == &states[S_SSMINE_AIR2])
|
||||
P_SetMobjState(mobj, S_SSMINE_DEPLOY1);
|
||||
if (mobj->reactiontime >= mobj->info->reactiontime)
|
||||
if (mobj->extravalue1 > 0)
|
||||
mobj->extravalue1--;
|
||||
else
|
||||
{
|
||||
mobj->momx = mobj->momy = 0;
|
||||
S_StartSound(mobj, mobj->info->activesound);
|
||||
mobj->reactiontime--;
|
||||
P_SetMobjState(mobj, S_SSMINE_DEPLOY1);
|
||||
}
|
||||
}
|
||||
if (mobj->reactiontime && mobj->reactiontime < mobj->info->reactiontime)
|
||||
{
|
||||
mobj->reactiontime--;
|
||||
if (!mobj->reactiontime)
|
||||
P_KillMobj(mobj, NULL, NULL);
|
||||
}
|
||||
|
||||
if ((mobj->state >= &states[S_SSMINE1] && mobj->state <= &states[S_SSMINE4])
|
||||
|| (mobj->state >= &states[S_SSMINE_DEPLOY8] && mobj->state <= &states[S_SSMINE_DEPLOY13]))
|
||||
A_GrenadeRing(mobj);
|
||||
|
||||
if (mobj->threshold > 0)
|
||||
mobj->threshold--;
|
||||
break;
|
||||
|
@ -8355,6 +8248,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
break;
|
||||
case MT_INSTASHIELDB:
|
||||
mobj->flags2 ^= MF2_DONTDRAW;
|
||||
K_MatchGenericExtraFlags(mobj, mobj->target);
|
||||
/* FALLTHRU */
|
||||
case MT_INSTASHIELDA:
|
||||
if (!mobj->target || !mobj->target->health || (mobj->target->player && !mobj->target->player->kartstuff[k_instashield]))
|
||||
|
@ -8363,6 +8257,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
return;
|
||||
}
|
||||
P_TeleportMove(mobj, mobj->target->x, mobj->target->y, mobj->target->z);
|
||||
K_MatchGenericExtraFlags(mobj, mobj->target);
|
||||
break;
|
||||
case MT_BATTLEPOINT:
|
||||
if (!mobj->target || P_MobjWasRemoved(mobj->target))
|
||||
|
@ -8383,7 +8278,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
if (mobj->movefactor < mobj->target->height)
|
||||
mobj->movefactor = mobj->target->height;
|
||||
}
|
||||
|
||||
K_MatchGenericExtraFlags(mobj, mobj->target);
|
||||
P_TeleportMove(mobj, mobj->target->x, mobj->target->y, mobj->target->z + (mobj->target->height/2) + mobj->movefactor);
|
||||
break;
|
||||
case MT_THUNDERSHIELD:
|
||||
|
@ -8508,6 +8403,10 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
mobj->flags2 &= ~MF2_DONTDRAW;
|
||||
}
|
||||
|
||||
// Update mobj antigravity status:
|
||||
mobj->eflags = (mobj->eflags & ~MFE_VERTICALFLIP)|(mobj->target->eflags & MFE_VERTICALFLIP);
|
||||
mobj->flags2 = (mobj->flags2 & ~MF2_OBJECTFLIP)|(mobj->target->flags2 & MF2_OBJECTFLIP);
|
||||
|
||||
// Now for the wheels
|
||||
{
|
||||
const fixed_t rad = FixedMul(mobjinfo[MT_PLAYER].radius, mobj->target->scale);
|
||||
|
@ -8529,6 +8428,7 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
P_SetScale(cur, mobj->target->scale);
|
||||
cur->color = mobj->target->color;
|
||||
cur->colorized = true;
|
||||
K_FlipFromObject(cur, mobj->target);
|
||||
|
||||
if (mobj->flags2 & MF2_DONTDRAW)
|
||||
cur->flags2 |= MF2_DONTDRAW;
|
||||
|
@ -11124,7 +11024,7 @@ void P_MovePlayerToSpawn(INT32 playernum, mapthing_t *mthing)
|
|||
if (mthing->options >> ZSHIFT)
|
||||
z -= ((mthing->options >> ZSHIFT) << FRACBITS);
|
||||
if (p->kartstuff[k_respawn])
|
||||
z -= 128*FRACUNIT; // Too late for v1, but for later: 128*mapobjectscale;
|
||||
z -= 128*mapobjectscale;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -11132,7 +11032,7 @@ void P_MovePlayerToSpawn(INT32 playernum, mapthing_t *mthing)
|
|||
if (mthing->options >> ZSHIFT)
|
||||
z += ((mthing->options >> ZSHIFT) << FRACBITS);
|
||||
if (p->kartstuff[k_respawn])
|
||||
z += 128*FRACUNIT; // Too late for v1, but for later: 128*mapobjectscale;
|
||||
z += 128*mapobjectscale;
|
||||
}
|
||||
|
||||
if (mthing->options & MTF_OBJECTFLIP) // flip the player!
|
||||
|
@ -11193,7 +11093,14 @@ void P_MovePlayerToStarpost(INT32 playernum)
|
|||
#endif
|
||||
sector->ceilingheight;
|
||||
|
||||
z = (p->starpostz + 128) << FRACBITS; // Respawn off the ground
|
||||
if (mobj->player->kartstuff[k_starpostflip])
|
||||
z = (p->starpostz<<FRACBITS) - FixedMul(128<<FRACBITS, mapobjectscale) - mobj->height;
|
||||
else
|
||||
z = (p->starpostz<<FRACBITS) + FixedMul(128<<FRACBITS, mapobjectscale);
|
||||
|
||||
//z = (p->starpostz + 128) << FRACBITS; // reverse gravity exists, pls
|
||||
mobj->player->kartstuff[k_starpostflip] = 0;
|
||||
|
||||
if (z < floor)
|
||||
z = floor;
|
||||
else if (z > ceiling - mobjinfo[MT_PLAYER].height)
|
||||
|
|
|
@ -249,6 +249,8 @@ static void P_NetArchivePlayers(void)
|
|||
|
||||
WRITEUINT32(save_p, players[i].jointime);
|
||||
|
||||
WRITEUINT8(save_p, players[i].splitscreenindex);
|
||||
|
||||
WRITEUINT16(save_p, flags);
|
||||
|
||||
if (flags & CAPSULE)
|
||||
|
@ -426,6 +428,8 @@ static void P_NetUnArchivePlayers(void)
|
|||
|
||||
players[i].jointime = READUINT32(save_p);
|
||||
|
||||
players[i].splitscreenindex = READUINT8(save_p);
|
||||
|
||||
flags = READUINT16(save_p);
|
||||
|
||||
if (flags & CAPSULE)
|
||||
|
@ -675,8 +679,6 @@ static void P_NetArchiveWorld(void)
|
|||
|
||||
WRITEUINT16(put, 0xffff);
|
||||
|
||||
mld = W_CacheLumpNum(lastloadedmaplumpnum+ML_LINEDEFS, PU_CACHE);
|
||||
msd = W_CacheLumpNum(lastloadedmaplumpnum+ML_SIDEDEFS, PU_CACHE);
|
||||
// do lines
|
||||
for (i = 0; i < numlines; i++, mld++, li++)
|
||||
{
|
||||
|
@ -695,13 +697,13 @@ static void P_NetArchiveWorld(void)
|
|||
diff |= LD_S1TEXOFF;
|
||||
//SoM: 4/1/2000: Some textures are colormaps. Don't worry about invalid textures.
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[0]].toptexture) != -1
|
||||
&& si->toptexture != R_TextureNumForName(msd[li->sidenum[0]].toptexture))
|
||||
&& si->toptexture != R_TextureNumForName(msd[li->sidenum[0]].toptexture))
|
||||
diff |= LD_S1TOPTEX;
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[0]].bottomtexture) != -1
|
||||
&& si->bottomtexture != R_TextureNumForName(msd[li->sidenum[0]].bottomtexture))
|
||||
&& si->bottomtexture != R_TextureNumForName(msd[li->sidenum[0]].bottomtexture))
|
||||
diff |= LD_S1BOTTEX;
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[0]].midtexture) != -1
|
||||
&& si->midtexture != R_TextureNumForName(msd[li->sidenum[0]].midtexture))
|
||||
&& si->midtexture != R_TextureNumForName(msd[li->sidenum[0]].midtexture))
|
||||
diff |= LD_S1MIDTEX;
|
||||
}
|
||||
if (li->sidenum[1] != 0xffff)
|
||||
|
@ -710,13 +712,13 @@ static void P_NetArchiveWorld(void)
|
|||
if (si->textureoffset != SHORT(msd[li->sidenum[1]].textureoffset)<<FRACBITS)
|
||||
diff2 |= LD_S2TEXOFF;
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[1]].toptexture) != -1
|
||||
&& si->toptexture != R_TextureNumForName(msd[li->sidenum[1]].toptexture))
|
||||
&& si->toptexture != R_TextureNumForName(msd[li->sidenum[1]].toptexture))
|
||||
diff2 |= LD_S2TOPTEX;
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[1]].bottomtexture) != -1
|
||||
&& si->bottomtexture != R_TextureNumForName(msd[li->sidenum[1]].bottomtexture))
|
||||
&& si->bottomtexture != R_TextureNumForName(msd[li->sidenum[1]].bottomtexture))
|
||||
diff2 |= LD_S2BOTTEX;
|
||||
if (R_CheckTextureNumForName(msd[li->sidenum[1]].midtexture) != -1
|
||||
&& si->midtexture != R_TextureNumForName(msd[li->sidenum[1]].midtexture))
|
||||
&& si->midtexture != R_TextureNumForName(msd[li->sidenum[1]].midtexture))
|
||||
diff2 |= LD_S2MIDTEX;
|
||||
if (diff2)
|
||||
diff |= LD_DIFF2;
|
||||
|
@ -3313,6 +3315,7 @@ static void P_NetArchiveMisc(void)
|
|||
|
||||
WRITEUINT32(save_p, wantedcalcdelay);
|
||||
WRITEUINT32(save_p, indirectitemcooldown);
|
||||
WRITEUINT32(save_p, hyubgone);
|
||||
WRITEUINT32(save_p, mapreset);
|
||||
WRITEUINT8(save_p, nospectategrief);
|
||||
WRITEUINT8(save_p, thwompsactive);
|
||||
|
@ -3421,6 +3424,7 @@ static inline boolean P_NetUnArchiveMisc(void)
|
|||
|
||||
wantedcalcdelay = READUINT32(save_p);
|
||||
indirectitemcooldown = READUINT32(save_p);
|
||||
hyubgone = READUINT32(save_p);
|
||||
mapreset = READUINT32(save_p);
|
||||
nospectategrief = READUINT8(save_p);
|
||||
thwompsactive = (boolean)READUINT8(save_p);
|
||||
|
|
|
@ -3216,10 +3216,9 @@ boolean P_SetupLevel(boolean skipprecip)
|
|||
if (!cv_analog4.changed)
|
||||
CV_SetValue(&cv_analog4, 0);*/
|
||||
|
||||
#ifdef HWRENDER
|
||||
if (rendermode != render_soft && rendermode != render_none)
|
||||
CV_Set(&cv_grfov, cv_grfov.defaultvalue);
|
||||
#endif
|
||||
// Shouldn't be necessary with render parity?
|
||||
/*if (rendermode != render_none)
|
||||
CV_Set(&cv_fov, cv_fov.defaultvalue);*/
|
||||
|
||||
displayplayer = consoleplayer; // Start with your OWN view, please!
|
||||
}
|
||||
|
@ -3246,6 +3245,7 @@ boolean P_SetupLevel(boolean skipprecip)
|
|||
|
||||
wantedcalcdelay = wantedfrequency*2;
|
||||
indirectitemcooldown = 0;
|
||||
hyubgone = 0;
|
||||
mapreset = 0;
|
||||
nospectategrief = 0;
|
||||
thwompsactive = false;
|
||||
|
|
|
@ -4247,13 +4247,14 @@ DoneSection2:
|
|||
player->starpostx = player->mo->x>>FRACBITS;
|
||||
player->starposty = player->mo->y>>FRACBITS;
|
||||
player->starpostz = player->mo->floorz>>FRACBITS;
|
||||
player->kartstuff[k_starpostflip] = player->mo->flags2 & MF2_OBJECTFLIP; // store flipping
|
||||
player->starpostangle = player->mo->angle; //R_PointToAngle2(0, 0, player->mo->momx, player->mo->momy); torn; a momentum-based guess is less likely to be wrong in general, but when it IS wrong, it fucks you over entirely...
|
||||
}
|
||||
else
|
||||
{
|
||||
// SRB2kart 200117
|
||||
// Reset starposts (checkpoints) info
|
||||
player->starpostangle = player->starpostx = player->starposty = player->starpostz = 0;
|
||||
player->starpostangle = player->starpostx = player->starposty = player->starpostz = player->kartstuff[k_starpostflip] = 0;
|
||||
}
|
||||
|
||||
if (P_IsLocalPlayer(player))
|
||||
|
|
|
@ -680,6 +680,8 @@ void P_Ticker(boolean run)
|
|||
|
||||
if (indirectitemcooldown)
|
||||
indirectitemcooldown--;
|
||||
if (hyubgone)
|
||||
hyubgone--;
|
||||
|
||||
if (G_BattleGametype())
|
||||
{
|
||||
|
|
275
src/p_user.c
275
src/p_user.c
|
@ -172,7 +172,7 @@ boolean P_AutoPause(void)
|
|||
if (netgame || modeattacking)
|
||||
return false;
|
||||
|
||||
return (menuactive || window_notinfocus);
|
||||
return (menuactive || ( window_notinfocus && cv_pauseifunfocused.value ));
|
||||
}
|
||||
|
||||
//
|
||||
|
@ -3634,165 +3634,6 @@ static void P_DoFiring(player_t *player, ticcmd_t *cmd) // SRB2kart - unused.
|
|||
}
|
||||
*/
|
||||
|
||||
#if 0
|
||||
//
|
||||
// P_DoSuperStuff()
|
||||
//
|
||||
// Handle related superform functionality.
|
||||
//
|
||||
static void P_DoSuperStuff(player_t *player)
|
||||
{
|
||||
mobj_t *spark;
|
||||
ticcmd_t *cmd = &player->cmd;
|
||||
//if (player->mo->state >= &states[S_PLAY_SUPERTRANS1] && player->mo->state <= &states[S_PLAY_SUPERTRANS9])
|
||||
// return; // don't do anything right now, we're in the middle of transforming!
|
||||
|
||||
if (player->pflags & PF_NIGHTSMODE)
|
||||
return; // NiGHTS Super doesn't mix with normal super
|
||||
|
||||
// Does player have all emeralds? If so, flag the "Ready For Super!"
|
||||
/*if ((ALL7EMERALDS(emeralds) || ALL7EMERALDS(player->powers[pw_emeralds])) && player->health > 50)
|
||||
player->pflags |= PF_SUPERREADY;
|
||||
else
|
||||
player->pflags &= ~PF_SUPERREADY;*/
|
||||
|
||||
if (player->powers[pw_super])
|
||||
{
|
||||
// If you're super and not Sonic, de-superize!
|
||||
if (!((ALL7EMERALDS(emeralds)) && (player->charflags & SF_SUPER)) && !(ALL7EMERALDS(player->powers[pw_emeralds])))
|
||||
{
|
||||
player->powers[pw_super] = 0;
|
||||
P_SetPlayerMobjState(player->mo, S_KART_STND1);
|
||||
P_RestoreMusic(player);
|
||||
P_SpawnShieldOrb(player);
|
||||
|
||||
// Restore color
|
||||
if (player->powers[pw_shield] & SH_FIREFLOWER)
|
||||
{
|
||||
player->mo->color = SKINCOLOR_WHITE;
|
||||
G_GhostAddColor(GHC_FIREFLOWER);
|
||||
}
|
||||
else
|
||||
{
|
||||
player->mo->color = player->skincolor;
|
||||
G_GhostAddColor(GHC_NORMAL);
|
||||
}
|
||||
|
||||
if (gametype != GT_COOP)
|
||||
{
|
||||
HU_SetCEchoFlags(0);
|
||||
HU_SetCEchoDuration(5);
|
||||
HU_DoCEcho(va("%s\\is no longer super.\\\\\\\\", player_names[player-players]));
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
// Deplete one ring every second while super
|
||||
if ((leveltime % TICRATE == 0) && !(player->exiting))
|
||||
{
|
||||
player->health--;
|
||||
player->mo->health--;
|
||||
}
|
||||
|
||||
// future todo: a skin option for this, and possibly more colors
|
||||
switch (player->skin)
|
||||
{
|
||||
case 1: /* Tails */ player->mo->color = SKINCOLOR_TSUPER1; break;
|
||||
case 2: /* Knux */ player->mo->color = SKINCOLOR_KSUPER1; break;
|
||||
default: /* everyone */ player->mo->color = SKINCOLOR_SUPER1; break;
|
||||
}
|
||||
player->mo->color += abs( ( (signed)( (unsigned)leveltime >> 1 ) % 9) - 4);
|
||||
|
||||
if ((cmd->forwardmove != 0 || cmd->sidemove != 0 || player->pflags & (PF_CARRIED|PF_ROPEHANG|PF_ITEMHANG|PF_MACESPIN))
|
||||
&& !(leveltime % TICRATE) && (player->mo->momx || player->mo->momy))
|
||||
{
|
||||
spark = P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z, MT_SUPERSPARK);
|
||||
spark->destscale = player->mo->scale;
|
||||
P_SetScale(spark, player->mo->scale);
|
||||
}
|
||||
|
||||
G_GhostAddColor(GHC_SUPER);
|
||||
|
||||
// Ran out of rings while super!
|
||||
if (player->health <= 1 || player->exiting)
|
||||
{
|
||||
player->powers[pw_emeralds] = 0; // lost the power stones
|
||||
P_SpawnGhostMobj(player->mo);
|
||||
|
||||
player->powers[pw_super] = 0;
|
||||
|
||||
// Restore color
|
||||
if (player->powers[pw_shield] & SH_FIREFLOWER)
|
||||
{
|
||||
player->mo->color = SKINCOLOR_WHITE;
|
||||
G_GhostAddColor(GHC_FIREFLOWER);
|
||||
}
|
||||
else
|
||||
{
|
||||
player->mo->color = player->skincolor;
|
||||
G_GhostAddColor(GHC_NORMAL);
|
||||
}
|
||||
|
||||
if (gametype != GT_COOP)
|
||||
player->powers[pw_flashing] = K_GetKartFlashing(player)-1;
|
||||
|
||||
/*
|
||||
if (player->mo->health > 0)
|
||||
{
|
||||
if ((player->pflags & PF_JUMPED) || (player->pflags & PF_SPINNING))
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_ATK1);
|
||||
else if (player->panim == PA_RUN)
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_SPD1);
|
||||
else if (player->panim == PA_WALK)
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_RUN1);
|
||||
else
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_STND);
|
||||
|
||||
if (!player->exiting)
|
||||
{
|
||||
player->health = 1;
|
||||
player->mo->health = 1;
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
// Inform the netgame that the champion has fallen in the heat of battle.
|
||||
if (gametype != GT_COOP)
|
||||
{
|
||||
S_StartSound(NULL, sfx_s3k66); //let all players hear it.
|
||||
HU_SetCEchoFlags(0);
|
||||
HU_SetCEchoDuration(5);
|
||||
HU_DoCEcho(va("%s\\is no longer super.\\\\\\\\", player_names[player-players]));
|
||||
}
|
||||
|
||||
// Resume normal music if you're the console player
|
||||
P_RestoreMusic(player);
|
||||
|
||||
// If you had a shield, restore its visual significance.
|
||||
P_SpawnShieldOrb(player);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
//
|
||||
// P_SuperReady
|
||||
//
|
||||
// Returns true if player is ready to turn super, duh
|
||||
//
|
||||
/*boolean P_SuperReady(player_t *player)
|
||||
{
|
||||
if ((player->pflags & PF_SUPERREADY) && !player->powers[pw_super] && !player->powers[pw_tailsfly]
|
||||
&& !(player->powers[pw_shield] & SH_NOSTACK)
|
||||
&& !player->powers[pw_invulnerability]
|
||||
&& !(maptol & TOL_NIGHTS) // don't turn 'regular super' in nights levels
|
||||
&& player->pflags & PF_JUMPED
|
||||
&& ((player->charflags & SF_SUPER) || ALL7EMERALDS(player->powers[pw_emeralds])))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}*/
|
||||
|
||||
//
|
||||
// P_DoJump
|
||||
//
|
||||
|
@ -6382,99 +6223,6 @@ void P_ElementalFireTrail(player_t *player)
|
|||
}
|
||||
}
|
||||
|
||||
/*static void P_SkidStuff(player_t *player)
|
||||
{
|
||||
fixed_t pmx = player->rmomx + player->cmomx;
|
||||
fixed_t pmy = player->rmomy + player->cmomy;
|
||||
|
||||
// Knuckles glides into the dirt.
|
||||
// SRB2kart - don't need
|
||||
if (player->pflags & PF_GLIDING && player->skidtime)
|
||||
{
|
||||
// Fell off a ledge...
|
||||
if (!onground)
|
||||
{
|
||||
player->skidtime = 0;
|
||||
player->pflags &= ~(PF_GLIDING|PF_JUMPED);
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_FALL1);
|
||||
}
|
||||
// Get up and brush yourself off, idiot.
|
||||
else if (player->glidetime > 15)
|
||||
{
|
||||
P_ResetPlayer(player);
|
||||
P_SetPlayerMobjState(player->mo, S_PLAY_STND);
|
||||
player->mo->momx = player->cmomx;
|
||||
player->mo->momy = player->cmomy;
|
||||
}
|
||||
// Didn't stop yet? Skid FOREVER!
|
||||
else if (player->skidtime == 1)
|
||||
player->skidtime = 3*TICRATE+1;
|
||||
// Spawn a particle every 3 tics.
|
||||
else if (!(player->skidtime % 3))
|
||||
{
|
||||
mobj_t *particle = P_SpawnMobj(player->mo->x + P_RandomRange(-player->mo->radius, player->mo->radius), player->mo->y + P_RandomRange(-player->mo->radius, player->mo->radius),
|
||||
player->mo->z + (player->mo->eflags & MFE_VERTICALFLIP ? player->mo->height - mobjinfo[MT_PARTICLE].height : 0),
|
||||
MT_PARTICLE);
|
||||
particle->tics = 10;
|
||||
|
||||
particle->eflags |= player->mo->eflags & MFE_VERTICALFLIP;
|
||||
P_SetScale(particle, player->mo->scale >> 2);
|
||||
particle->destscale = player->mo->scale << 2;
|
||||
particle->scalespeed = FixedMul(particle->scalespeed, player->mo->scale); // scale the scaling speed!
|
||||
P_SetObjectMomZ(particle, FRACUNIT, false);
|
||||
S_StartSound(player->mo, sfx_s3k7e); // the proper "Knuckles eats dirt" sfx.
|
||||
}
|
||||
}
|
||||
// Skidding!
|
||||
elseif (onground && !(player->mo->eflags & MFE_GOOWATER) && !(player->pflags & (PF_JUMPED|PF_SPINNING|PF_SLIDING)) && !(player->charflags & SF_NOSKID))
|
||||
{
|
||||
if (player->skidtime)
|
||||
{
|
||||
// Spawn a particle every 3 tics.
|
||||
if (!(player->skidtime % 3))
|
||||
{
|
||||
mobj_t *particle = P_SpawnMobj(player->mo->x, player->mo->y,
|
||||
player->mo->z + (player->mo->eflags & MFE_VERTICALFLIP ? player->mo->height - mobjinfo[MT_PARTICLE].height : 0),
|
||||
MT_PARTICLE);
|
||||
particle->tics = 10;
|
||||
|
||||
particle->eflags |= player->mo->eflags & MFE_VERTICALFLIP;
|
||||
P_SetScale(particle, player->mo->scale >> 2);
|
||||
particle->destscale = player->mo->scale << 2;
|
||||
particle->scalespeed = FixedMul(particle->scalespeed, player->mo->scale); // scale the scaling speed!
|
||||
P_SetObjectMomZ(particle, FRACUNIT, false);
|
||||
}
|
||||
}
|
||||
else if (P_AproxDistance(pmx, pmy) >= FixedMul(player->runspeed/2, player->mo->scale) // if you were moving faster than half your run speed last frame
|
||||
&& (player->mo->momx != pmx || player->mo->momy != pmy) // and you are moving differently this frame
|
||||
&& P_GetPlayerControlDirection(player) == 2) // and your controls are pointing in the opposite direction to your movement
|
||||
{ // check for skidding
|
||||
angle_t mang = R_PointToAngle2(0,0,pmx,pmy); // movement angle
|
||||
angle_t pang = R_PointToAngle2(pmx,pmy,player->mo->momx,player->mo->momy); // push angle
|
||||
angle_t dang = mang - pang; // delta angle
|
||||
|
||||
if (dang > ANGLE_180) // Make delta angle always positive, invert it if it's negative.
|
||||
dang = InvAngle(dang);
|
||||
|
||||
// If your push angle is more than this close to a full 180 degrees, trigger a skid.
|
||||
if (dang > ANGLE_157h)
|
||||
{
|
||||
player->skidtime = (player->mo->movefactor == FRACUNIT) ? TICRATE/2 : (FixedDiv(35<<(FRACBITS-1), FixedSqrt(player->mo->movefactor)))>>FRACBITS; //player->skidtime = TICRATE/2;
|
||||
S_StartSound(player->mo, sfx_skid);
|
||||
if (player->panim != PA_WALK)
|
||||
P_SetPlayerMobjState(player->mo, S_KART_WALK2); // SRB2kart - was S_PLAY_RUN4
|
||||
player->mo->tics = player->skidtime;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (player->skidtime) {
|
||||
player->skidtime = 0;
|
||||
S_StopSound(player->mo);
|
||||
}
|
||||
}
|
||||
}*/
|
||||
|
||||
//
|
||||
// P_MovePlayer
|
||||
static void P_MovePlayer(player_t *player)
|
||||
|
@ -6662,7 +6410,7 @@ static void P_MovePlayer(player_t *player)
|
|||
//CONS_Printf("leftover turn (%s): %5d or %4d%%\n",
|
||||
// player_names[player-players],
|
||||
// (INT16) (cmd->angleturn - (player->mo->angle>>16)),
|
||||
// (INT16) (cmd->angleturn - (player->mo->angle>>16)) * 100 / (angle_diff ?: 1));
|
||||
// (INT16) (cmd->angleturn - (player->mo->angle>>16)) * 100 / (angle_diff ? angle_diff : 1));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -7654,12 +7402,14 @@ static void P_NukeAllPlayers(player_t *player)
|
|||
//
|
||||
void P_NukeEnemies(mobj_t *inflictor, mobj_t *source, fixed_t radius)
|
||||
{
|
||||
const fixed_t ns = 60 << FRACBITS;
|
||||
const fixed_t ns = 60 * mapobjectscale;
|
||||
mobj_t *mo;
|
||||
angle_t fa;
|
||||
thinker_t *think;
|
||||
INT32 i;
|
||||
|
||||
radius = FixedMul(radius, mapobjectscale);
|
||||
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
fa = (i*(FINEANGLES/16));
|
||||
|
@ -8295,9 +8045,6 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall
|
|||
if (mo->eflags & MFE_VERTICALFLIP)
|
||||
camheight += thiscam->height;
|
||||
|
||||
if (splitscreen == 1)
|
||||
camspeed = (3*camspeed)/4;
|
||||
|
||||
if (camspeed > FRACUNIT)
|
||||
camspeed = FRACUNIT;
|
||||
|
||||
|
@ -8351,13 +8098,6 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall
|
|||
height -= FixedMul(height, player->kartstuff[k_boostcam]);
|
||||
}
|
||||
|
||||
// in splitscreen modes, mess with the camera distances to make it feel proportional to how it feels normally
|
||||
if (splitscreen == 1) // widescreen splits should get x1.5 distance
|
||||
{
|
||||
dist = FixedMul(dist, 3*FRACUNIT/2);
|
||||
height = FixedMul(height, 3*FRACUNIT/2);
|
||||
}
|
||||
|
||||
x = mo->x - FixedMul(FINECOSINE((angle>>ANGLETOFINESHIFT) & FINEMASK), dist);
|
||||
y = mo->y - FixedMul(FINESINE((angle>>ANGLETOFINESHIFT) & FINEMASK), dist);
|
||||
|
||||
|
@ -8623,10 +8363,7 @@ boolean P_MoveChaseCamera(player_t *player, camera_t *thiscam, boolean resetcall
|
|||
{
|
||||
thiscam->momx = x - thiscam->x;
|
||||
thiscam->momy = y - thiscam->y;
|
||||
if (splitscreen == 1) // Wide-screen needs to follow faster, due to a smaller vertical:horizontal ratio of screen space
|
||||
thiscam->momz = FixedMul(z - thiscam->z, (3*camspeed)/4);
|
||||
else
|
||||
thiscam->momz = FixedMul(z - thiscam->z, camspeed/2);
|
||||
thiscam->momz = FixedMul(z - thiscam->z, camspeed/2);
|
||||
}
|
||||
|
||||
thiscam->pan = pan;
|
||||
|
|
|
@ -102,6 +102,8 @@ extern lumpnum_t viewborderlump[8];
|
|||
// ------------------------------------------------
|
||||
|
||||
#define GTC_CACHE 1
|
||||
#define GTC_MENUCACHE GTC_CACHE
|
||||
//@TODO Add a separate caching mechanism for menu colormaps distinct from in-level GTC_CACHE. For now this is still preferable to memory leaks...
|
||||
|
||||
#define TC_DEFAULT -1
|
||||
#define TC_BOSS -2
|
||||
|
|
30
src/r_main.c
30
src/r_main.c
|
@ -56,6 +56,7 @@ INT32 centerx, centery;
|
|||
fixed_t centerxfrac, centeryfrac;
|
||||
fixed_t projection;
|
||||
fixed_t projectiony; // aspect ratio
|
||||
fixed_t fovtan; // field of view
|
||||
|
||||
// just for profiling purposes
|
||||
size_t framecount;
|
||||
|
@ -134,11 +135,14 @@ static CV_PossibleValue_t drawdist_precip_cons_t[] = {
|
|||
{1024, "1024"}, {1536, "1536"}, {2048, "2048"},
|
||||
{0, "None"}, {0, NULL}};
|
||||
|
||||
static CV_PossibleValue_t fov_cons_t[] = {{0, "MIN"}, {179*FRACUNIT, "MAX"}, {0, NULL}};
|
||||
|
||||
//static CV_PossibleValue_t precipdensity_cons_t[] = {{0, "None"}, {1, "Light"}, {2, "Moderate"}, {4, "Heavy"}, {6, "Thick"}, {8, "V.Thick"}, {0, NULL}};
|
||||
static CV_PossibleValue_t translucenthud_cons_t[] = {{0, "MIN"}, {10, "MAX"}, {0, NULL}};
|
||||
static CV_PossibleValue_t maxportals_cons_t[] = {{0, "MIN"}, {12, "MAX"}, {0, NULL}}; // lmao rendering 32 portals, you're a card
|
||||
static CV_PossibleValue_t homremoval_cons_t[] = {{0, "No"}, {1, "Yes"}, {2, "Flash"}, {0, NULL}};
|
||||
|
||||
static void Fov_OnChange(void);
|
||||
static void ChaseCam_OnChange(void);
|
||||
static void ChaseCam2_OnChange(void);
|
||||
static void ChaseCam3_OnChange(void);
|
||||
|
@ -175,6 +179,7 @@ consvar_t cv_drawdist = {"drawdist", "Infinite", CV_SAVE, drawdist_cons_t, NULL,
|
|||
//consvar_t cv_drawdist_nights = {"drawdist_nights", "2048", CV_SAVE, drawdist_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_drawdist_precip = {"drawdist_precip", "1024", CV_SAVE, drawdist_precip_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
//consvar_t cv_precipdensity = {"precipdensity", "Moderate", CV_SAVE, precipdensity_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_fov = {"fov", "90", CV_FLOAT|CV_CALL, fov_cons_t, Fov_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
// Okay, whoever said homremoval causes a performance hit should be shot.
|
||||
consvar_t cv_homremoval = {"homremoval", "Yes", CV_SAVE, homremoval_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
@ -227,6 +232,14 @@ void SplitScreen_OnChange(void)
|
|||
}
|
||||
}
|
||||
}
|
||||
static void Fov_OnChange(void)
|
||||
{
|
||||
// Shouldn't be needed with render parity?
|
||||
//if ((netgame || multiplayer) && !cv_debug && cv_fov.value != 90*FRACUNIT)
|
||||
// CV_Set(&cv_fov, cv_fov.defaultvalue);
|
||||
|
||||
R_SetViewSize();
|
||||
}
|
||||
|
||||
static void ChaseCam_OnChange(void)
|
||||
{
|
||||
|
@ -517,7 +530,7 @@ static void R_InitTextureMapping(void)
|
|||
//
|
||||
// Calc focallength
|
||||
// so FIELDOFVIEW angles covers SCREENWIDTH.
|
||||
focallength = FixedDiv(centerxfrac,
|
||||
focallength = FixedDiv(projection,
|
||||
FINETANGENT(FINEANGLES/4+/*cv_fov.value*/ FIELDOFVIEW/2));
|
||||
|
||||
#ifdef ESLOPE
|
||||
|
@ -632,6 +645,7 @@ void R_ExecuteSetViewSize(void)
|
|||
INT32 j;
|
||||
INT32 level;
|
||||
INT32 startmapl;
|
||||
angle_t fov;
|
||||
|
||||
setsizeneeded = false;
|
||||
|
||||
|
@ -660,9 +674,12 @@ void R_ExecuteSetViewSize(void)
|
|||
centerxfrac = centerx<<FRACBITS;
|
||||
centeryfrac = centery<<FRACBITS;
|
||||
|
||||
projection = centerxfrac;
|
||||
//projectiony = (((vid.height*centerx*BASEVIDWIDTH)/BASEVIDHEIGHT)/vid.width)<<FRACBITS;
|
||||
projectiony = centerxfrac;
|
||||
fov = FixedAngle(cv_fov.value/2) + ANGLE_90;
|
||||
fovtan = FINETANGENT(fov >> ANGLETOFINESHIFT);
|
||||
if (splitscreen == 1) // Splitscreen FOV should be adjusted to maintain expected vertical view
|
||||
fovtan = 17*fovtan/10;
|
||||
|
||||
projection = projectiony = FixedDiv(centerxfrac, fovtan);
|
||||
|
||||
R_InitViewBuffer(scaledviewwidth, viewheight);
|
||||
|
||||
|
@ -688,7 +705,7 @@ void R_ExecuteSetViewSize(void)
|
|||
for (i = 0; i < j; i++)
|
||||
{
|
||||
dy = ((i - viewheight*8)<<FRACBITS) + FRACUNIT/2;
|
||||
dy = abs(dy);
|
||||
dy = FixedMul(abs(dy), fovtan);
|
||||
yslopetab[i] = FixedDiv(centerx*FRACUNIT, dy);
|
||||
}
|
||||
}
|
||||
|
@ -803,7 +820,7 @@ subsector_t *R_IsPointInSubsector(fixed_t x, fixed_t y)
|
|||
static mobj_t *viewmobj;
|
||||
|
||||
// WARNING: a should be unsigned but to add with 2048, it isn't!
|
||||
#define AIMINGTODY(a) ((FINETANGENT((2048+(((INT32)a)>>ANGLETOFINESHIFT)) & FINEMASK)*160)>>FRACBITS)
|
||||
#define AIMINGTODY(a) FixedDiv((FINETANGENT((2048+(((INT32)a)>>ANGLETOFINESHIFT)) & FINEMASK)*160)>>FRACBITS, fovtan)
|
||||
|
||||
// recalc necessary stuff for mouseaiming
|
||||
// slopes are already calculated for the full possible view (which is 4*viewheight).
|
||||
|
@ -1490,6 +1507,7 @@ void R_RegisterEngineStuff(void)
|
|||
CV_RegisterVar(&cv_drawdist);
|
||||
//CV_RegisterVar(&cv_drawdist_nights);
|
||||
CV_RegisterVar(&cv_drawdist_precip);
|
||||
CV_RegisterVar(&cv_fov);
|
||||
|
||||
CV_RegisterVar(&cv_chasecam);
|
||||
CV_RegisterVar(&cv_chasecam2);
|
||||
|
|
|
@ -79,6 +79,7 @@ extern consvar_t cv_flipcam, cv_flipcam2, cv_flipcam3, cv_flipcam4;
|
|||
extern consvar_t cv_shadow, cv_shadowoffs;
|
||||
extern consvar_t cv_translucency;
|
||||
extern consvar_t /*cv_precipdensity,*/ cv_drawdist, /*cv_drawdist_nights,*/ cv_drawdist_precip;
|
||||
extern consvar_t cv_fov;
|
||||
extern consvar_t cv_skybox;
|
||||
extern consvar_t cv_tailspickup;
|
||||
|
||||
|
|
|
@ -1051,7 +1051,7 @@ void R_DrawSinglePlane(visplane_t *pl)
|
|||
temp = P_GetZAt(pl->slope, pl->viewx, pl->viewy);
|
||||
zeroheight = FIXED_TO_FLOAT(temp);
|
||||
|
||||
#define ANG2RAD(angle) ((float)((angle)*M_PI)/ANGLE_180)
|
||||
#define ANG2RAD(angle) ((float)((angle)*M_PIl)/ANGLE_180)
|
||||
|
||||
// p is the texture origin in view space
|
||||
// Don't add in the offsets at this stage, because doing so can result in
|
||||
|
|
37
src/r_segs.c
37
src/r_segs.c
|
@ -870,16 +870,18 @@ void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pfloor)
|
|||
leftheight -= viewz;
|
||||
rightheight -= viewz;
|
||||
|
||||
#define OVERFLOWTEST(height, scale) \
|
||||
overflow_test = (INT64)centeryfrac - (((INT64)height*scale)>>FRACBITS); \
|
||||
if (overflow_test < 0) overflow_test = -overflow_test; \
|
||||
if ((UINT64)overflow_test&0xFFFFFFFF80000000ULL) continue;
|
||||
#define CLAMPMAX INT32_MAX
|
||||
#define CLAMPMIN (-INT32_MAX) // This is not INT32_MIN on purpose! INT32_MIN makes the drawers freak out.
|
||||
// Monster Iestyn (25/03/18): do not skip these lights if they fail overflow test, just clamp them instead so they behave.
|
||||
overflow_test = (INT64)centeryfrac - (((INT64)leftheight*ds->scale1)>>FRACBITS);
|
||||
if (overflow_test > (INT64)CLAMPMAX) rlight->height = CLAMPMAX;
|
||||
else if (overflow_test > (INT64)CLAMPMIN) rlight->height = (fixed_t)overflow_test;
|
||||
else rlight->height = CLAMPMIN;
|
||||
|
||||
OVERFLOWTEST(leftheight, ds->scale1)
|
||||
OVERFLOWTEST(rightheight, ds->scale2)
|
||||
|
||||
rlight->height = (centeryfrac) - FixedMul(leftheight, ds->scale1);
|
||||
rlight->heightstep = (centeryfrac) - FixedMul(rightheight, ds->scale2);
|
||||
overflow_test = (INT64)centeryfrac - (((INT64)rightheight*ds->scale2)>>FRACBITS);
|
||||
if (overflow_test > (INT64)CLAMPMAX) rlight->heightstep = CLAMPMAX;
|
||||
else if (overflow_test > (INT64)CLAMPMIN) rlight->heightstep = (fixed_t)overflow_test;
|
||||
else rlight->heightstep = CLAMPMIN;
|
||||
rlight->heightstep = (rlight->heightstep-rlight->height)/(range);
|
||||
#else
|
||||
if (light->height < *pfloor->bottomheight)
|
||||
|
@ -901,12 +903,16 @@ void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pfloor)
|
|||
leftheight -= viewz;
|
||||
rightheight -= viewz;
|
||||
|
||||
OVERFLOWTEST(leftheight, ds->scale1)
|
||||
OVERFLOWTEST(rightheight, ds->scale2)
|
||||
#undef OVERFLOWTEST
|
||||
// Monster Iestyn (25/03/18): do not skip these lights if they fail overflow test, just clamp them instead so they behave.
|
||||
overflow_test = (INT64)centeryfrac - (((INT64)leftheight*ds->scale1)>>FRACBITS);
|
||||
if (overflow_test > (INT64)CLAMPMAX) rlight->botheight = CLAMPMAX;
|
||||
else if (overflow_test > (INT64)CLAMPMIN) rlight->botheight = (fixed_t)overflow_test;
|
||||
else rlight->botheight = CLAMPMIN;
|
||||
|
||||
rlight->botheight = (centeryfrac) - FixedMul(leftheight, ds->scale1);
|
||||
rlight->botheightstep = (centeryfrac) - FixedMul(rightheight, ds->scale2);
|
||||
overflow_test = (INT64)centeryfrac - (((INT64)rightheight*ds->scale2)>>FRACBITS);
|
||||
if (overflow_test > (INT64)CLAMPMAX) rlight->botheightstep = CLAMPMAX;
|
||||
else if (overflow_test > (INT64)CLAMPMIN) rlight->botheightstep = (fixed_t)overflow_test;
|
||||
else rlight->botheightstep = CLAMPMIN;
|
||||
rlight->botheightstep = (rlight->botheightstep-rlight->botheight)/(range);
|
||||
#else
|
||||
lheight = *light->caster->bottomheight;// > *pfloor->topheight ? *pfloor->topheight + FRACUNIT : *light->caster->bottomheight;
|
||||
|
@ -1079,9 +1085,6 @@ void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pfloor)
|
|||
}
|
||||
#endif
|
||||
|
||||
#define CLAMPMAX INT32_MAX
|
||||
#define CLAMPMIN (-INT32_MAX) // This is not INT32_MIN on purpose! INT32_MIN makes the drawers freak out.
|
||||
|
||||
// draw the columns
|
||||
for (dc_x = x1; dc_x <= x2; dc_x++)
|
||||
{
|
||||
|
|
|
@ -1315,6 +1315,7 @@ static void R_ProjectSprite(mobj_t *thing)
|
|||
return;
|
||||
|
||||
scalestep = (yscale2 - yscale)/(x2 - x1);
|
||||
scalestep = scalestep ? scalestep : 1;
|
||||
|
||||
// The following two are alternate sorting methods which might be more applicable in some circumstances. TODO - maybe enable via MF2?
|
||||
// sortscale = max(yscale, yscale2);
|
||||
|
@ -1795,7 +1796,7 @@ void R_AddSprites(sector_t *sec, INT32 lightlevel, UINT8 viewnumber)
|
|||
}
|
||||
}
|
||||
|
||||
// Someone seriously wants infinite draw distance for precipitation?
|
||||
// no, no infinite draw distance for precipitation. this option at zero is supposed to turn it off
|
||||
if ((limit_dist = (fixed_t)cv_drawdist_precip.value << FRACBITS))
|
||||
{
|
||||
for (precipthing = sec->preciplist; precipthing; precipthing = precipthing->snext)
|
||||
|
@ -1811,13 +1812,6 @@ void R_AddSprites(sector_t *sec, INT32 lightlevel, UINT8 viewnumber)
|
|||
R_ProjectPrecipitationSprite(precipthing);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Draw everything in sector, no checks
|
||||
for (precipthing = sec->preciplist; precipthing; precipthing = precipthing->snext)
|
||||
if (!(precipthing->precipflags & PCF_INVISIBLE))
|
||||
R_ProjectPrecipitationSprite(precipthing);
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
|
@ -2536,23 +2530,6 @@ static void Sk_SetDefaultValue(skin_t *skin)
|
|||
skin->kartweight = 5;
|
||||
//
|
||||
|
||||
skin->normalspeed = 36<<FRACBITS;
|
||||
skin->runspeed = 28<<FRACBITS;
|
||||
skin->thrustfactor = 5;
|
||||
skin->accelstart = 96;
|
||||
skin->acceleration = 40;
|
||||
|
||||
skin->ability = CA_NONE;
|
||||
skin->ability2 = CA2_SPINDASH;
|
||||
skin->jumpfactor = FRACUNIT;
|
||||
skin->actionspd = 30<<FRACBITS;
|
||||
skin->mindash = 15<<FRACBITS;
|
||||
skin->maxdash = 90<<FRACBITS;
|
||||
|
||||
skin->thokitem = -1;
|
||||
skin->spinitem = -1;
|
||||
skin->revitem = -1;
|
||||
|
||||
skin->highresscale = FRACUNIT>>1;
|
||||
|
||||
for (i = 0; i < sfx_skinsoundslot0; i++)
|
||||
|
@ -2586,7 +2563,7 @@ void R_InitSkins(void)
|
|||
#ifdef SKINVALUES
|
||||
skin_cons_t[0].strvalue = skins[0].name;
|
||||
#endif
|
||||
skin->flags = SF_SUPER|SF_SUPERANIMS|SF_SUPERSPIN;
|
||||
skin->flags = 0;
|
||||
strcpy(skin->realname, "Sonic");
|
||||
strcpy(skin->hudname, "SONIC");
|
||||
|
||||
|
@ -2595,20 +2572,11 @@ void R_InitSkins(void)
|
|||
strncpy(skin->facemmap, "PLAYMMAP", 9);
|
||||
skin->prefcolor = SKINCOLOR_BLUE;
|
||||
|
||||
skin->ability = CA_THOK;
|
||||
skin->actionspd = 60<<FRACBITS;
|
||||
|
||||
// SRB2kart
|
||||
skin->kartspeed = 8;
|
||||
skin->kartweight = 2;
|
||||
//
|
||||
|
||||
skin->normalspeed = 36<<FRACBITS;
|
||||
skin->runspeed = 28<<FRACBITS;
|
||||
skin->thrustfactor = 5;
|
||||
skin->accelstart = 96;
|
||||
skin->acceleration = 40;
|
||||
|
||||
skin->spritedef.numframes = sprites[SPR_PLAY].numframes;
|
||||
skin->spritedef.spriteframes = sprites[SPR_PLAY].spriteframes;
|
||||
ST_LoadFaceGraphics(skin->facerank, skin->facewant, skin->facemmap, 0);
|
||||
|
@ -2672,31 +2640,12 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
|
|||
if (player->mo)
|
||||
player->mo->skin = skin;
|
||||
|
||||
player->charability = (UINT8)skin->ability;
|
||||
player->charability2 = (UINT8)skin->ability2;
|
||||
|
||||
player->charflags = (UINT32)skin->flags;
|
||||
|
||||
player->thokitem = skin->thokitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].painchance : (UINT32)skin->thokitem;
|
||||
player->spinitem = skin->spinitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].damage : (UINT32)skin->spinitem;
|
||||
player->revitem = skin->revitem < 0 ? (mobjtype_t)mobjinfo[MT_PLAYER].raisestate : (UINT32)skin->revitem;
|
||||
|
||||
player->actionspd = skin->actionspd;
|
||||
player->mindash = skin->mindash;
|
||||
player->maxdash = skin->maxdash;
|
||||
|
||||
// SRB2kart
|
||||
player->kartspeed = skin->kartspeed;
|
||||
player->kartweight = skin->kartweight;
|
||||
|
||||
player->normalspeed = skin->normalspeed;
|
||||
player->runspeed = skin->runspeed;
|
||||
player->thrustfactor = skin->thrustfactor;
|
||||
player->accelstart = skin->accelstart;
|
||||
player->acceleration = skin->acceleration;
|
||||
|
||||
player->jumpfactor = skin->jumpfactor;
|
||||
|
||||
/*if (!(cv_debug || devparm) && !(netgame || multiplayer || demoplayback || modeattacking))
|
||||
{
|
||||
if (playernum == consoleplayer)
|
||||
|
@ -2895,28 +2844,8 @@ void R_AddSkins(UINT16 wadnum)
|
|||
#define FULLPROCESS(field) else if (!stricmp(stoken, #field)) skin->field = get_number(value);
|
||||
// character type identification
|
||||
FULLPROCESS(flags)
|
||||
//FULLPROCESS(ability)
|
||||
//FULLPROCESS(ability2)
|
||||
|
||||
//FULLPROCESS(thokitem)
|
||||
//FULLPROCESS(spinitem)
|
||||
//FULLPROCESS(revitem)
|
||||
#undef FULLPROCESS
|
||||
|
||||
#define GETSPEED(field) else if (!stricmp(stoken, #field)) skin->field = atoi(value)<<FRACBITS;
|
||||
//GETSPEED(normalspeed)
|
||||
GETSPEED(runspeed)
|
||||
//GETSPEED(mindash)
|
||||
//GETSPEED(maxdash)
|
||||
//GETSPEED(actionspd)
|
||||
#undef GETSPEED
|
||||
|
||||
/*#define GETINT(field) else if (!stricmp(stoken, #field)) skin->field = atoi(value);
|
||||
GETINT(thrustfactor)
|
||||
GETINT(accelstart)
|
||||
GETINT(acceleration)
|
||||
#undef GETINT*/
|
||||
|
||||
#define GETKARTSTAT(field) \
|
||||
else if (!stricmp(stoken, #field)) \
|
||||
{ \
|
||||
|
@ -2934,8 +2863,6 @@ void R_AddSkins(UINT16 wadnum)
|
|||
|
||||
else if (!stricmp(stoken, "prefcolor"))
|
||||
skin->prefcolor = K_GetKartColorByName(value);
|
||||
//else if (!stricmp(stoken, "jumpfactor"))
|
||||
//skin->jumpfactor = FLOAT_TO_FIXED(atof(value));
|
||||
else if (!stricmp(stoken, "highresscale"))
|
||||
skin->highresscale = FLOAT_TO_FIXED(atof(value));
|
||||
else
|
||||
|
@ -3045,9 +2972,6 @@ next_token:
|
|||
HWR_AddPlayerMD2(numskins);
|
||||
#endif
|
||||
|
||||
if (skin->flags & SF_RUNONWATER) // this is literally the only way a skin can be a major mod... this might be a bit heavy handed
|
||||
G_SetGameModified(multiplayer, true);
|
||||
|
||||
numskins++;
|
||||
}
|
||||
return;
|
||||
|
|
|
@ -83,29 +83,11 @@ typedef struct
|
|||
char hudname[SKINNAMESIZE+1]; // HUD name to display (officially exactly 5 characters long)
|
||||
char facerank[9], facewant[9], facemmap[9]; // Arbitrarily named patch lumps
|
||||
|
||||
UINT8 ability; // ability definition
|
||||
UINT8 ability2; // secondary ability definition
|
||||
INT32 thokitem;
|
||||
INT32 spinitem;
|
||||
INT32 revitem;
|
||||
fixed_t actionspd;
|
||||
fixed_t mindash;
|
||||
fixed_t maxdash;
|
||||
|
||||
// SRB2kart
|
||||
UINT8 kartspeed;
|
||||
UINT8 kartweight;
|
||||
//
|
||||
|
||||
fixed_t normalspeed; // Normal ground
|
||||
fixed_t runspeed; // Speed that you break into your run animation
|
||||
|
||||
UINT8 thrustfactor; // Thrust = thrustfactor * acceleration
|
||||
UINT8 accelstart; // Acceleration if speed = 0
|
||||
UINT8 acceleration; // Acceleration
|
||||
|
||||
fixed_t jumpfactor; // multiple of standard jump height
|
||||
|
||||
// Definable color translation table
|
||||
UINT8 starttranscolor;
|
||||
UINT8 prefcolor;
|
||||
|
|
|
@ -57,6 +57,9 @@ static void GameMIDIMusic_OnChange(void);
|
|||
static void GameSounds_OnChange(void);
|
||||
static void GameDigiMusic_OnChange(void);
|
||||
|
||||
static void PlayMusicIfUnfocused_OnChange(void);
|
||||
static void PlaySoundIfUnfocused_OnChange(void);
|
||||
|
||||
// commands for music and sound servers
|
||||
#ifdef MUSSERV
|
||||
consvar_t musserver_cmd = {"musserver_cmd", "musserver", CV_SAVE, NULL, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
@ -110,6 +113,9 @@ consvar_t cv_gamemidimusic = {"midimusic", "On", CV_SAVE|CV_CALL|CV_NOINIT, CV_O
|
|||
#endif
|
||||
consvar_t cv_gamesounds = {"sounds", "On", CV_SAVE|CV_CALL|CV_NOINIT, CV_OnOff, GameSounds_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
consvar_t cv_playmusicifunfocused = {"playmusicifunfocused", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, PlayMusicIfUnfocused_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_playsoundifunfocused = {"playsoundsifunfocused", "No", CV_SAVE|CV_CALL|CV_NOINIT, CV_YesNo, PlaySoundIfUnfocused_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
#define S_MAX_VOLUME 127
|
||||
|
||||
// when to clip out sounds
|
||||
|
@ -270,6 +276,9 @@ void S_RegisterSoundStuff(void)
|
|||
CV_RegisterVar(&cv_gamemidimusic);
|
||||
#endif
|
||||
|
||||
CV_RegisterVar(&cv_playmusicifunfocused);
|
||||
CV_RegisterVar(&cv_playsoundifunfocused);
|
||||
|
||||
COM_AddCommand("tunes", Command_Tunes_f);
|
||||
COM_AddCommand("restartaudio", Command_RestartAudio_f);
|
||||
|
||||
|
@ -1897,6 +1906,10 @@ static boolean S_PlayMusic(boolean looping)
|
|||
}
|
||||
|
||||
S_InitMusicVolume(); // switch between digi and sequence volume
|
||||
|
||||
if (window_notinfocus && !cv_playmusicifunfocused.value)
|
||||
I_PauseSong();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -1978,6 +1991,24 @@ void S_ResumeAudio(void)
|
|||
I_ResumeCD();
|
||||
}
|
||||
|
||||
void S_DisableSound(void)
|
||||
{
|
||||
if (sound_started && !sound_disabled)
|
||||
{
|
||||
sound_disabled = true;
|
||||
S_StopSounds();
|
||||
}
|
||||
}
|
||||
|
||||
void S_EnableSound(void)
|
||||
{
|
||||
if (sound_started && sound_disabled)
|
||||
{
|
||||
sound_disabled = false;
|
||||
S_InitSfxChannels(cv_soundvolume.value);
|
||||
}
|
||||
}
|
||||
|
||||
void S_SetMusicVolume(INT32 digvolume, INT32 seqvolume)
|
||||
{
|
||||
if (digvolume < 0)
|
||||
|
@ -2156,15 +2187,11 @@ void GameSounds_OnChange(void)
|
|||
|
||||
if (sound_disabled)
|
||||
{
|
||||
sound_disabled = false;
|
||||
S_InitSfxChannels(cv_soundvolume.value);
|
||||
S_StartSound(NULL, sfx_strpst);
|
||||
if (!( cv_playsoundifunfocused.value && window_notinfocus ))
|
||||
S_EnableSound();
|
||||
}
|
||||
else
|
||||
{
|
||||
sound_disabled = true;
|
||||
S_StopSounds();
|
||||
}
|
||||
S_DisableSound();
|
||||
}
|
||||
|
||||
void GameDigiMusic_OnChange(void)
|
||||
|
@ -2251,3 +2278,28 @@ void GameMIDIMusic_OnChange(void)
|
|||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
static void PlayMusicIfUnfocused_OnChange(void)
|
||||
{
|
||||
if (window_notinfocus)
|
||||
{
|
||||
if (cv_playmusicifunfocused.value)
|
||||
I_PauseSong();
|
||||
else
|
||||
I_ResumeSong();
|
||||
}
|
||||
}
|
||||
|
||||
static void PlaySoundIfUnfocused_OnChange(void)
|
||||
{
|
||||
if (!cv_gamesounds.value)
|
||||
return;
|
||||
|
||||
if (window_notinfocus)
|
||||
{
|
||||
if (cv_playsoundifunfocused.value)
|
||||
S_DisableSound();
|
||||
else
|
||||
S_EnableSound();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,6 +33,8 @@ extern consvar_t cv_gamedigimusic;
|
|||
extern consvar_t cv_gamemidimusic;
|
||||
#endif
|
||||
extern consvar_t cv_gamesounds;
|
||||
extern consvar_t cv_playmusicifunfocused;
|
||||
extern consvar_t cv_playsoundifunfocused;
|
||||
|
||||
#ifdef SNDSERV
|
||||
extern consvar_t sndserver_cmd, sndserver_arg;
|
||||
|
@ -169,6 +171,10 @@ void S_StopMusic(void);
|
|||
void S_PauseAudio(void);
|
||||
void S_ResumeAudio(void);
|
||||
|
||||
// Enable and disable sound effects
|
||||
void S_EnableSound(void);
|
||||
void S_DisableSound(void);
|
||||
|
||||
//
|
||||
// Updates music & sounds
|
||||
//
|
||||
|
|
33
src/screen.c
33
src/screen.c
|
@ -403,7 +403,7 @@ void SCR_DisplayTicRate(void)
|
|||
tic_t i;
|
||||
tic_t ontic = I_GetTime();
|
||||
tic_t totaltics = 0;
|
||||
INT32 ticcntcolor = 0;
|
||||
const UINT8 *ticcntcolor = NULL;
|
||||
|
||||
for (i = lasttic + 1; i < TICRATE+lasttic && i < ontic; ++i)
|
||||
fpsgraph[i % TICRATE] = false;
|
||||
|
@ -414,13 +414,36 @@ void SCR_DisplayTicRate(void)
|
|||
if (fpsgraph[i])
|
||||
++totaltics;
|
||||
|
||||
if (totaltics <= TICRATE/2) ticcntcolor = V_REDMAP;
|
||||
else if (totaltics == TICRATE) ticcntcolor = V_GREENMAP;
|
||||
if (totaltics <= TICRATE/2) ticcntcolor = R_GetTranslationColormap(TC_RAINBOW, SKINCOLOR_SALMON, GTC_CACHE);
|
||||
else if (totaltics == TICRATE) ticcntcolor = R_GetTranslationColormap(TC_RAINBOW, SKINCOLOR_MINT, GTC_CACHE);
|
||||
|
||||
V_DrawString(vid.width-(24*vid.dupx), vid.height-(16*vid.dupy),
|
||||
/*V_DrawString(vid.width-(24*vid.dupx), vid.height-(16*vid.dupy),
|
||||
V_YELLOWMAP|V_NOSCALESTART, "FPS");
|
||||
V_DrawString(vid.width-(40*vid.dupx), vid.height-( 8*vid.dupy),
|
||||
ticcntcolor|V_NOSCALESTART, va("%02d/%02u", totaltics, TICRATE));
|
||||
ticcntcolor|V_NOSCALESTART, va("%02d/%02u", totaltics, TICRATE));*/
|
||||
|
||||
// draw "FPS"
|
||||
V_DrawFixedPatch(306<<FRACBITS, 183<<FRACBITS, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTORIGHT, framecounter, R_GetTranslationColormap(TC_RAINBOW, SKINCOLOR_YELLOW, GTC_CACHE));
|
||||
// draw total frame:
|
||||
V_DrawPingNum(318, 190, V_SNAPTOBOTTOM|V_SNAPTORIGHT, TICRATE, ticcntcolor);
|
||||
// draw "/"
|
||||
V_DrawFixedPatch(306<<FRACBITS, 190<<FRACBITS, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTORIGHT, frameslash, ticcntcolor);
|
||||
// draw our actual framerate
|
||||
V_DrawPingNum(306, 190, V_SNAPTOBOTTOM|V_SNAPTORIGHT, totaltics, ticcntcolor);
|
||||
|
||||
|
||||
lasttic = ontic;
|
||||
}
|
||||
|
||||
// SCR_DisplayLocalPing
|
||||
// Used to draw the user's local ping next to the framerate for a quick check without having to hold TAB for instance. By default, it only shows up if your ping is too high and risks getting you kicked.
|
||||
|
||||
void SCR_DisplayLocalPing(void)
|
||||
{
|
||||
UINT32 ping = playerpingtable[consoleplayer]; // consoleplayer's ping is everyone's ping in a splitnetgame :P
|
||||
if (cv_showping.value == 1 || (cv_showping.value == 2 && ping > servermaxping)) // only show 2 (warning) if our ping is at a bad level
|
||||
{
|
||||
INT32 dispy = cv_ticrate.value ? 160 : 181;
|
||||
HU_drawPing(307, dispy, ping, V_SNAPTORIGHT | V_SNAPTOBOTTOM);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -180,5 +180,6 @@ FUNCMATH boolean SCR_IsAspectCorrect(INT32 width, INT32 height);
|
|||
|
||||
// move out to main code for consistency
|
||||
void SCR_DisplayTicRate(void);
|
||||
void SCR_DisplayLocalPing(void);
|
||||
#undef DNWH
|
||||
#endif //__SCREEN_H__
|
||||
|
|
|
@ -2974,8 +2974,8 @@ static void I_ShutdownTimer(void)
|
|||
//
|
||||
tic_t I_GetTime (void)
|
||||
{
|
||||
static Uint32 basetime = 0;
|
||||
Uint32 ticks = SDL_GetTicks();
|
||||
static Uint64 basetime = 0;
|
||||
Uint64 ticks = SDL_GetTicks();
|
||||
|
||||
if (!basetime)
|
||||
basetime = ticks;
|
||||
|
|
|
@ -64,7 +64,7 @@
|
|||
#include "../m_menu.h"
|
||||
#include "../d_main.h"
|
||||
#include "../s_sound.h"
|
||||
#include "../i_sound.h" // midi pause/unpause
|
||||
#include "../i_sound.h" // midi pause/unpause
|
||||
#include "../i_joy.h"
|
||||
#include "../st_stuff.h"
|
||||
#include "../g_game.h"
|
||||
|
@ -615,9 +615,13 @@ static void Impl_HandleWindowEvent(SDL_WindowEvent evt)
|
|||
{
|
||||
// Tell game we got focus back, resume music if necessary
|
||||
window_notinfocus = false;
|
||||
|
||||
if (!paused)
|
||||
I_ResumeSong(); //resume it
|
||||
|
||||
if (cv_gamesounds.value)
|
||||
S_EnableSound();
|
||||
|
||||
if (!firsttimeonmouse)
|
||||
{
|
||||
if (cv_usemouse.value) I_StartupMouse();
|
||||
|
@ -630,7 +634,10 @@ static void Impl_HandleWindowEvent(SDL_WindowEvent evt)
|
|||
{
|
||||
// Tell game we lost focus, pause music
|
||||
window_notinfocus = true;
|
||||
I_PauseSong();
|
||||
if (!cv_playmusicifunfocused.value)
|
||||
I_PauseSong();
|
||||
if (!cv_playsoundifunfocused.value)
|
||||
S_DisableSound();
|
||||
|
||||
if (!disable_mouse)
|
||||
{
|
||||
|
@ -1327,6 +1334,7 @@ void I_UpdateNoBlit(void)
|
|||
// from PrBoom's src/SDL/i_video.c
|
||||
static inline boolean I_SkipFrame(void)
|
||||
{
|
||||
#if 0
|
||||
static boolean skip = false;
|
||||
|
||||
if (rendermode != render_soft)
|
||||
|
@ -1345,6 +1353,8 @@ static inline boolean I_SkipFrame(void)
|
|||
default:
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
//
|
||||
|
@ -1361,6 +1371,9 @@ void I_FinishUpdate(void)
|
|||
if (cv_ticrate.value)
|
||||
SCR_DisplayTicRate();
|
||||
|
||||
if (cv_showping.value && netgame && consoleplayer != serverplayer)
|
||||
SCR_DisplayLocalPing();
|
||||
|
||||
if (rendermode == render_soft && screens[0])
|
||||
{
|
||||
SDL_Rect rect;
|
||||
|
|
BIN
src/sdl/srb2icon.png
Normal file
BIN
src/sdl/srb2icon.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 3 KiB |
|
@ -1343,6 +1343,9 @@ void I_FinishUpdate(void)
|
|||
if (cv_ticrate.value)
|
||||
SCR_DisplayTicRate();
|
||||
|
||||
if (cv_showping.value && netgame && consoleplayer != serverplayer)
|
||||
SCR_DisplayLocalPing();
|
||||
|
||||
if (render_soft == rendermode && screens[0])
|
||||
{
|
||||
SDL_Rect *dstrect = NULL;
|
||||
|
|
|
@ -815,6 +815,7 @@ sfxinfo_t S_sfx[NUMSFX] =
|
|||
{"chain", false, 255, 8, -1, NULL, 0, -1, -1, LUMPERROR}, // Mementos Reaper
|
||||
{"mkuma", false, 96, 8, -1, NULL, 0, -1, -1, LUMPERROR}, // Trigger Happy Havoc Monokuma
|
||||
{"toada", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR}, // Arid Sands Toad scream
|
||||
{"bsnipe", false, 96, 8, -1, NULL, 0, -1, -1, LUMPERROR}, // Banana sniping
|
||||
{"itfree", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR}, // :shitsfree:
|
||||
{"dbgsal", false, 255, 8, -1, NULL, 0, -1, -1, LUMPERROR}, // Debug notification
|
||||
|
||||
|
|
|
@ -890,6 +890,7 @@ typedef enum
|
|||
sfx_chain,
|
||||
sfx_mkuma,
|
||||
sfx_toada,
|
||||
sfx_bsnipe,
|
||||
sfx_itfree,
|
||||
sfx_dbgsal,
|
||||
|
||||
|
|
|
@ -1342,8 +1342,8 @@ void V_DrawCharacter(INT32 x, INT32 y, INT32 c, boolean lowercaseallowed)
|
|||
V_DrawScaledPatch(x, y, flags, hu_font[c]);
|
||||
}
|
||||
|
||||
// Writes a single character for the chat. (draw WHITE if bit 7 set)
|
||||
// Essentially the same as the above but it's small or big depending on what resolution you've chosen to huge..
|
||||
// Writes a single character for the chat (half scaled). (draw WHITE if bit 7 set)
|
||||
// 16/02/19: Scratch the scaling thing, chat doesn't work anymore under 2x res -Lat'
|
||||
//
|
||||
void V_DrawChatCharacter(INT32 x, INT32 y, INT32 c, boolean lowercaseallowed, UINT8 *colormap)
|
||||
{
|
||||
|
@ -1359,13 +1359,11 @@ void V_DrawChatCharacter(INT32 x, INT32 y, INT32 c, boolean lowercaseallowed, UI
|
|||
if (c < 0 || c >= HU_FONTSIZE || !hu_font[c])
|
||||
return;
|
||||
|
||||
w = (vid.width < 640 ) ? (SHORT(hu_font[c]->width)/2) : (SHORT(hu_font[c]->width)); // use normal sized characters if we're using a terribly low resolution.
|
||||
w = SHORT(hu_font[c]->width)/2;
|
||||
if (x + w > vid.width)
|
||||
return;
|
||||
|
||||
V_DrawFixedPatch(x*FRACUNIT, y*FRACUNIT, (vid.width < 640) ? (FRACUNIT) : (FRACUNIT/2), flags, hu_font[c], colormap);
|
||||
|
||||
|
||||
V_DrawFixedPatch(x*FRACUNIT, y*FRACUNIT, FRACUNIT/2, flags, hu_font[c], colormap);
|
||||
}
|
||||
|
||||
// Precompile a wordwrapped string to any given width.
|
||||
|
@ -2015,6 +2013,28 @@ void V_DrawPaddedTallNum(INT32 x, INT32 y, INT32 flags, INT32 num, INT32 digits)
|
|||
} while (--digits);
|
||||
}
|
||||
|
||||
// Draws a number using the PING font thingy.
|
||||
// TODO: Merge number drawing functions into one with "font name" selection.
|
||||
|
||||
void V_DrawPingNum(INT32 x, INT32 y, INT32 flags, INT32 num, const UINT8 *colormap)
|
||||
{
|
||||
INT32 w = SHORT(pingnum[0]->width); // this SHOULD always be 5 but I guess custom graphics exist.
|
||||
|
||||
if (flags & V_NOSCALESTART)
|
||||
w *= vid.dupx;
|
||||
|
||||
if (num < 0)
|
||||
num = -num;
|
||||
|
||||
// draw the number
|
||||
do
|
||||
{
|
||||
x -= (w-1); // Oni wanted their outline to intersect.
|
||||
V_DrawFixedPatch(x<<FRACBITS, y<<FRACBITS, FRACUNIT, flags, pingnum[num%10], colormap);
|
||||
num /= 10;
|
||||
} while (num);
|
||||
}
|
||||
|
||||
// Write a string using the credit font
|
||||
// NOTE: the text is centered for screens larger than the base width
|
||||
//
|
||||
|
|
|
@ -190,6 +190,10 @@ void V_DrawStringAtFixed(fixed_t x, fixed_t y, INT32 option, const char *string)
|
|||
void V_DrawTallNum(INT32 x, INT32 y, INT32 flags, INT32 num);
|
||||
void V_DrawPaddedTallNum(INT32 x, INT32 y, INT32 flags, INT32 num, INT32 digits);
|
||||
|
||||
// Draw ping numbers. Used by the scoreboard and that one ping option. :P
|
||||
// This is a separate function because IMO lua should have access to it as well.
|
||||
void V_DrawPingNum(INT32 x, INT32 y, INT32 flags, INT32 num, const UINT8 *colormap);
|
||||
|
||||
// Find string width from lt_font chars
|
||||
INT32 V_LevelNameWidth(const char *string);
|
||||
INT32 V_LevelNameHeight(const char *string);
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue