This commit is contained in:
Christoph Oelckers 2016-12-11 14:45:42 +01:00
commit 71fd949f26
50 changed files with 329 additions and 707 deletions

View file

@ -193,7 +193,7 @@ void DBot::Dofire (ticcmd_t *cmd)
else
{
//*4 is for atmosphere, the chainsaws sounding and all..
no_fire = (Dist > MELEERANGE*4);
no_fire = (Dist > DEFMELEERANGE*4);
}
}
else if (player->ReadyWeapon->WeaponFlags & WIF_BOT_BFG)

View file

@ -1,121 +0,0 @@
// "Build Engine & Tools" Copyright (c) 1993-1997 Ken Silverman
// Ken Silverman's official web site: "http://www.advsys.net/ken"
// See the included license file "BUILDLIC.TXT" for license info.
//
// This file is based on pragmas.h from Ken Silverman's original Build
// source code release but is meant for use with any compiler and does not
// rely on any inline assembly.
//
#if _MSC_VER
#pragma once
#endif
#if defined(__GNUC__) && !defined(__forceinline)
#define __forceinline __inline__ __attribute__((always_inline))
#endif
static __forceinline SDWORD Scale (SDWORD a, SDWORD b, SDWORD c)
{
return (SDWORD)(((SQWORD)a*b)/c);
}
static __forceinline SDWORD MulScale1 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 1); }
static __forceinline SDWORD MulScale2 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 2); }
static __forceinline SDWORD MulScale3 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 3); }
static __forceinline SDWORD MulScale4 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 4); }
static __forceinline SDWORD MulScale5 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 5); }
static __forceinline SDWORD MulScale6 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 6); }
static __forceinline SDWORD MulScale7 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 7); }
static __forceinline SDWORD MulScale8 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 8); }
static __forceinline SDWORD MulScale9 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 9); }
static __forceinline SDWORD MulScale10 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 10); }
static __forceinline SDWORD MulScale11 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 11); }
static __forceinline SDWORD MulScale12 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 12); }
static __forceinline SDWORD MulScale13 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 13); }
static __forceinline SDWORD MulScale14 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 14); }
static __forceinline SDWORD MulScale15 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 15); }
static __forceinline SDWORD MulScale16 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 16); }
static __forceinline SDWORD MulScale17 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 17); }
static __forceinline SDWORD MulScale18 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 18); }
static __forceinline SDWORD MulScale19 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 19); }
static __forceinline SDWORD MulScale20 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 20); }
static __forceinline SDWORD MulScale21 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 21); }
static __forceinline SDWORD MulScale22 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 22); }
static __forceinline SDWORD MulScale23 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 23); }
static __forceinline SDWORD MulScale24 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 24); }
static __forceinline SDWORD MulScale25 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 25); }
static __forceinline SDWORD MulScale26 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 26); }
static __forceinline SDWORD MulScale27 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 27); }
static __forceinline SDWORD MulScale28 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 28); }
static __forceinline SDWORD MulScale29 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 29); }
static __forceinline SDWORD MulScale30 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 30); }
static __forceinline SDWORD MulScale31 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 31); }
static __forceinline SDWORD MulScale32 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a * b) >> 32); }
static __forceinline DWORD UMulScale16 (DWORD a, DWORD b) { return (DWORD)(((QWORD)a * b) >> 16); }
static __forceinline SDWORD DMulScale1 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 1); }
static __forceinline SDWORD DMulScale2 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 2); }
static __forceinline SDWORD DMulScale3 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 3); }
static __forceinline SDWORD DMulScale4 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 4); }
static __forceinline SDWORD DMulScale5 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 5); }
static __forceinline SDWORD DMulScale6 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 6); }
static __forceinline SDWORD DMulScale7 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 7); }
static __forceinline SDWORD DMulScale8 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 8); }
static __forceinline SDWORD DMulScale9 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 9); }
static __forceinline SDWORD DMulScale10 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 10); }
static __forceinline SDWORD DMulScale11 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 11); }
static __forceinline SDWORD DMulScale12 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 12); }
static __forceinline SDWORD DMulScale13 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 13); }
static __forceinline SDWORD DMulScale14 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 14); }
static __forceinline SDWORD DMulScale15 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 15); }
static __forceinline SDWORD DMulScale16 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 16); }
static __forceinline SDWORD DMulScale17 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 17); }
static __forceinline SDWORD DMulScale18 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 18); }
static __forceinline SDWORD DMulScale19 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 19); }
static __forceinline SDWORD DMulScale20 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 20); }
static __forceinline SDWORD DMulScale21 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 21); }
static __forceinline SDWORD DMulScale22 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 22); }
static __forceinline SDWORD DMulScale23 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 23); }
static __forceinline SDWORD DMulScale24 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 24); }
static __forceinline SDWORD DMulScale25 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 25); }
static __forceinline SDWORD DMulScale26 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 26); }
static __forceinline SDWORD DMulScale27 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 27); }
static __forceinline SDWORD DMulScale28 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 28); }
static __forceinline SDWORD DMulScale29 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 29); }
static __forceinline SDWORD DMulScale30 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 30); }
static __forceinline SDWORD DMulScale31 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 31); }
static __forceinline SDWORD DMulScale32 (SDWORD a, SDWORD b, SDWORD c, SDWORD d) { return (SDWORD)(((SQWORD)a*b + (SQWORD)c*d) >> 32); }
static inline SDWORD DivScale2 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 2) / b); }
static inline SDWORD DivScale3 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 3) / b); }
static inline SDWORD DivScale4 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 4) / b); }
static inline SDWORD DivScale5 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 5) / b); }
static inline SDWORD DivScale6 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 6) / b); }
static inline SDWORD DivScale7 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 7) / b); }
static inline SDWORD DivScale8 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 8) / b); }
static inline SDWORD DivScale9 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 9) / b); }
static inline SDWORD DivScale10 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 10) / b); }
static inline SDWORD DivScale11 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 11) / b); }
static inline SDWORD DivScale12 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 12) / b); }
static inline SDWORD DivScale13 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 13) / b); }
static inline SDWORD DivScale14 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 14) / b); }
static inline SDWORD DivScale15 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 15) / b); }
static inline SDWORD DivScale16 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 16) / b); }
static inline SDWORD DivScale17 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 17) / b); }
static inline SDWORD DivScale18 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 18) / b); }
static inline SDWORD DivScale19 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 19) / b); }
static inline SDWORD DivScale20 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 20) / b); }
static inline SDWORD DivScale21 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 21) / b); }
static inline SDWORD DivScale22 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 22) / b); }
static inline SDWORD DivScale23 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 23) / b); }
static inline SDWORD DivScale24 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 24) / b); }
static inline SDWORD DivScale25 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 25) / b); }
static inline SDWORD DivScale26 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 26) / b); }
static inline SDWORD DivScale27 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 27) / b); }
static inline SDWORD DivScale28 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 28) / b); }
static inline SDWORD DivScale29 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 29) / b); }
static inline SDWORD DivScale30 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 30) / b); }
static inline SDWORD DivScale31 (SDWORD a, SDWORD b) { return (SDWORD)(((SQWORD)a << 31) / b); }

View file

@ -374,7 +374,7 @@ public:
static FileWriter *Open(const char *filename);
virtual size_t Write(const void *buffer, size_t len);
size_t Printf(const char *fmt, ...);
size_t Printf(const char *fmt, ...) GCCPRINTF(2,3);
protected:

View file

@ -718,7 +718,7 @@ public:
#include "t_fs.h"
void script_error(const char *s, ...);
void script_error(const char *s, ...) GCCPRINTF(1,2);
void FS_EmulateCmd(char * string);
extern AActor *trigger_obj;

View file

@ -1,176 +0,0 @@
// "Build Engine & Tools" Copyright (c) 1993-1997 Ken Silverman
// Ken Silverman's official web site: "http://www.advsys.net/ken"
// See the included license file "BUILDLIC.TXT" for license info.
//
// This file is based on pragmas.h from Ken Silverman's original Build
// source code release but is meant for use with GCC instead of Watcom C.
//
// Some of the inline assembly has been turned into C code, because
// modern compilers are smart enough to produce code at least as good as
// Ken's inline assembly.
//
// I can come up with several different operand constraints for the
// following that work just fine when used all by themselves, but
// when I concatenate them together so that the compiler can choose
// between them, I get the following (but only if enough parameters
// are passed as the result of some operations instead of as
// variables/constants--e.g. DMulScale16 (a*2, b*2, c*2, d*2) instead of
// DMulScale16 (a, b, c, d)):
//
// `asm' operand requires impossible reload
//
// Why?
#include <stdlib.h>
#ifndef alloca
// MinGW does not seem to come with alloca defined.
#define alloca __builtin_alloca
#endif
static inline SDWORD Scale (SDWORD a, SDWORD b, SDWORD c)
{
SDWORD result, dummy;
asm volatile
("imull %3\n\t"
"idivl %4"
: "=a,a,a,a,a,a" (result),
"=&d,&d,&d,&d,d,d" (dummy)
: "a,a,a,a,a,a" (a),
"m,r,m,r,d,d" (b),
"r,r,m,m,r,m" (c)
: "cc"
);
return result;
}
#define MAKECONSTMulScale(s) \
static inline SDWORD MulScale##s (SDWORD a, SDWORD b) { return ((SQWORD)a * b) >> s; }
MAKECONSTMulScale(1)
MAKECONSTMulScale(2)
MAKECONSTMulScale(3)
MAKECONSTMulScale(4)
MAKECONSTMulScale(5)
MAKECONSTMulScale(6)
MAKECONSTMulScale(7)
MAKECONSTMulScale(8)
MAKECONSTMulScale(9)
MAKECONSTMulScale(10)
MAKECONSTMulScale(11)
MAKECONSTMulScale(12)
MAKECONSTMulScale(13)
MAKECONSTMulScale(14)
MAKECONSTMulScale(15)
MAKECONSTMulScale(16)
MAKECONSTMulScale(17)
MAKECONSTMulScale(18)
MAKECONSTMulScale(19)
MAKECONSTMulScale(20)
MAKECONSTMulScale(21)
MAKECONSTMulScale(22)
MAKECONSTMulScale(23)
MAKECONSTMulScale(24)
MAKECONSTMulScale(25)
MAKECONSTMulScale(26)
MAKECONSTMulScale(27)
MAKECONSTMulScale(28)
MAKECONSTMulScale(29)
MAKECONSTMulScale(30)
MAKECONSTMulScale(31)
MAKECONSTMulScale(32)
#undef MAKECONSTMulScale
static inline DWORD UMulScale16(DWORD a, DWORD b) { return ((QWORD)a * b) >> 16; }
#define MAKECONSTDMulScale(s) \
static inline SDWORD DMulScale##s (SDWORD a, SDWORD b, SDWORD c, SDWORD d) \
{ \
return (((SQWORD)a * b) + ((SQWORD)c * d)) >> s; \
}
MAKECONSTDMulScale(1)
MAKECONSTDMulScale(2)
MAKECONSTDMulScale(3)
MAKECONSTDMulScale(4)
MAKECONSTDMulScale(5)
MAKECONSTDMulScale(6)
MAKECONSTDMulScale(7)
MAKECONSTDMulScale(8)
MAKECONSTDMulScale(9)
MAKECONSTDMulScale(10)
MAKECONSTDMulScale(11)
MAKECONSTDMulScale(12)
MAKECONSTDMulScale(13)
MAKECONSTDMulScale(14)
MAKECONSTDMulScale(15)
MAKECONSTDMulScale(16)
MAKECONSTDMulScale(17)
MAKECONSTDMulScale(18)
MAKECONSTDMulScale(19)
MAKECONSTDMulScale(20)
MAKECONSTDMulScale(21)
MAKECONSTDMulScale(22)
MAKECONSTDMulScale(23)
MAKECONSTDMulScale(24)
MAKECONSTDMulScale(25)
MAKECONSTDMulScale(26)
MAKECONSTDMulScale(27)
MAKECONSTDMulScale(28)
MAKECONSTDMulScale(29)
MAKECONSTDMulScale(30)
MAKECONSTDMulScale(31)
MAKECONSTDMulScale(32)
#undef MAKECONSTDMulScale
#define MAKECONSTDivScale(s) \
static inline SDWORD DivScale##s (SDWORD a, SDWORD b) \
{ \
SDWORD result, dummy; \
asm volatile \
("idivl %4" \
:"=a,a" (result), \
"=d,d" (dummy) \
: "a,a" (a<<s), \
"d,d" (a>>(32-s)), \
"r,m" (b) \
: "cc"); \
return result; \
}
MAKECONSTDivScale(2)
MAKECONSTDivScale(3)
MAKECONSTDivScale(4)
MAKECONSTDivScale(5)
MAKECONSTDivScale(6)
MAKECONSTDivScale(7)
MAKECONSTDivScale(8)
MAKECONSTDivScale(9)
MAKECONSTDivScale(10)
MAKECONSTDivScale(11)
MAKECONSTDivScale(12)
MAKECONSTDivScale(13)
MAKECONSTDivScale(14)
MAKECONSTDivScale(15)
MAKECONSTDivScale(16)
MAKECONSTDivScale(17)
MAKECONSTDivScale(18)
MAKECONSTDivScale(19)
MAKECONSTDivScale(20)
MAKECONSTDivScale(21)
MAKECONSTDivScale(22)
MAKECONSTDivScale(23)
MAKECONSTDivScale(24)
MAKECONSTDivScale(25)
MAKECONSTDivScale(26)
MAKECONSTDivScale(27)
MAKECONSTDivScale(28)
MAKECONSTDivScale(29)
MAKECONSTDivScale(30)
MAKECONSTDivScale(31)
#undef MAKECONSTDivScale

View file

@ -4,14 +4,72 @@
#include <stdlib.h>
#include "doomtype.h"
// Unfortunately, the Scale function still gets badly handled on 32 bit x86 platforms so it's the last remaining piece of inline assembly
// GCC inlines
#if defined(__GNUC__) && defined(__i386__) && !defined(__clang__)
#include "gccinlines.h"
#elif defined(_MSC_VER) && defined(_M_IX86)
#include "mscinlines.h"
#else
#include "basicinlines.h"
#ifndef alloca
// MinGW does not seem to come with alloca defined.
#define alloca __builtin_alloca
#endif
static inline int32_t Scale(int32_t a, int32_t b, int32_t c)
{
int32_t result, dummy;
asm volatile
("imull %3\n\t"
"idivl %4"
: "=a,a,a,a,a,a" (result),
"=&d,&d,&d,&d,d,d" (dummy)
: "a,a,a,a,a,a" (a),
"m,r,m,r,d,d" (b),
"r,r,m,m,r,m" (c)
: "cc"
);
return result;
}
// MSVC inlines
#elif defined(_MSC_VER) && defined(_M_IX86)
#pragma warning (disable: 4035)
__forceinline int32_t Scale(int32_t a, int32_t b, int32_t c)
{
__asm mov eax, a
__asm imul b
__asm idiv c
}
#pragma warning (default: 4035)
#else
static __forceinline int32_t Scale(int32_t a, int32_t b, int32_t c)
{
return (int32_t)(((int64_t)a*b) / c);
}
#endif
// Modern compilers are smart enough to do these multiplications intelligently.
__forceinline int32_t MulScale14(int32_t a, int32_t b) { return (int32_t)(((int64_t)a * b) >> 14); } // only used by R_DrawVoxel
__forceinline int32_t MulScale30(int32_t a, int32_t b) { return (int32_t)(((int64_t)a * b) >> 30); } // only used once in the node builder
__forceinline int32_t MulScale32(int32_t a, int32_t b) { return (int32_t)(((int64_t)a * b) >> 32); } // only used by R_DrawVoxel
__forceinline uint32_t UMulScale16(uint32_t a, uint32_t b) { return (uint32_t)(((uint64_t)a * b) >> 16); } // used for sky drawing
__forceinline int32_t DMulScale3(int32_t a, int32_t b, int32_t c, int32_t d) { return (int32_t)(((int64_t)a*b + (int64_t)c*d) >> 3); } // used for setting up slopes for Build maps
__forceinline int32_t DMulScale6(int32_t a, int32_t b, int32_t c, int32_t d) { return (int32_t)(((int64_t)a*b + (int64_t)c*d) >> 6); } // only used by R_DrawVoxel
__forceinline int32_t DMulScale10(int32_t a, int32_t b, int32_t c, int32_t d) { return (int32_t)(((int64_t)a*b + (int64_t)c*d) >> 10); } // only used by R_DrawVoxel
__forceinline int32_t DMulScale18(int32_t a, int32_t b, int32_t c, int32_t d) { return (int32_t)(((int64_t)a*b + (int64_t)c*d) >> 18); } // only used by R_DrawVoxel
__forceinline int32_t DMulScale32(int32_t a, int32_t b, int32_t c, int32_t d) { return (int32_t)(((int64_t)a*b + (int64_t)c*d) >> 32); } // used by R_PointOnSide.
// Sadly, for divisions this is not true but these are so infrequently used that the C versions are just fine, despite not being fully optimal.
__forceinline int32_t DivScale6(int32_t a, int32_t b) { return (int32_t)(((int64_t)a << 6) / b); } // only used by R_DrawVoxel
__forceinline int32_t DivScale21(int32_t a, int32_t b) { return (int32_t)(((int64_t)a << 21) / b); } // only used by R_DrawVoxel
__forceinline int32_t DivScale30(int32_t a, int32_t b) { return (int32_t)(((int64_t)a << 30) / b); } // only used once in the node builder
__forceinline void fillshort(void *buff, unsigned int count, WORD clear)
{
SWORD *b2 = (SWORD *)buff;
@ -23,14 +81,18 @@ __forceinline void fillshort(void *buff, unsigned int count, WORD clear)
#include "xs_Float.h"
inline SDWORD FixedDiv (SDWORD a, SDWORD b)
inline int32_t FixedDiv (int32_t a, int32_t b)
{
if ((DWORD)abs(a) >> (31-16) >= (DWORD)abs (b))
if ((uint32_t)abs(a) >> (31-16) >= (uint32_t)abs (b))
return (a^b)<0 ? FIXED_MIN : FIXED_MAX;
return DivScale16 (a, b);
return (int32_t)(((int64_t)a << 16) / b);
}
#define FixedMul MulScale16
__forceinline int32_t FixedMul(int32_t a, int32_t b)
{
return (int32_t)(((int64_t)a * b) >> 16);
}
inline fixed_t FloatToFixed(double f)
{

View file

@ -1,186 +0,0 @@
// "Build Engine & Tools" Copyright (c) 1993-1997 Ken Silverman
// Ken Silverman's official web site: "http://www.advsys.net/ken"
// See the included license file "BUILDLIC.TXT" for license info.
//
// This file is based on pragmas.h from Ken Silverman's original Build
// source code release but is meant for use with Visual C++ instead of
// Watcom C.
//
// Some of the inline assembly has been turned into C code, because VC++
// is smart enough to produce code at least as good as Ken's inlines.
// The more used functions are still inline assembly, because they do
// things that can't really be done in C. (I consider this a bad thing,
// because VC++ has considerably poorer support for inline assembly than
// Watcom, so it's better to rely on its C optimizer to produce fast code.)
//
#include <string.h>
#include <stddef.h>
#pragma warning (disable: 4035)
__forceinline SDWORD Scale (SDWORD a, SDWORD b, SDWORD c)
{
__asm mov eax,a
__asm imul b
__asm idiv c
}
#define MAKECONSTMulScale(s) \
__forceinline SDWORD MulScale##s (SDWORD a, SDWORD b) \
{ \
__asm mov eax,a \
__asm imul b \
__asm shrd eax,edx,s \
}
MAKECONSTMulScale(1)
MAKECONSTMulScale(2)
MAKECONSTMulScale(3)
MAKECONSTMulScale(4)
MAKECONSTMulScale(5)
MAKECONSTMulScale(6)
MAKECONSTMulScale(7)
MAKECONSTMulScale(8)
MAKECONSTMulScale(9)
MAKECONSTMulScale(10)
MAKECONSTMulScale(11)
MAKECONSTMulScale(12)
MAKECONSTMulScale(13)
MAKECONSTMulScale(14)
MAKECONSTMulScale(15)
MAKECONSTMulScale(16)
MAKECONSTMulScale(17)
MAKECONSTMulScale(18)
MAKECONSTMulScale(19)
MAKECONSTMulScale(20)
MAKECONSTMulScale(21)
MAKECONSTMulScale(22)
MAKECONSTMulScale(23)
MAKECONSTMulScale(24)
MAKECONSTMulScale(25)
MAKECONSTMulScale(26)
MAKECONSTMulScale(27)
MAKECONSTMulScale(28)
MAKECONSTMulScale(29)
MAKECONSTMulScale(30)
MAKECONSTMulScale(31)
#undef MAKECONSTMulScale
__forceinline SDWORD MulScale32 (SDWORD a, SDWORD b)
{
__asm mov eax,a
__asm imul b
__asm mov eax,edx
}
__forceinline DWORD UMulScale16(DWORD a, DWORD b)
{
__asm mov eax,a
__asm mul b
__asm shrd eax,edx,16
}
#define MAKECONSTDMulScale(s) \
__forceinline SDWORD DMulScale##s (SDWORD a, SDWORD b, SDWORD c, SDWORD d) \
{ \
__asm mov eax,a \
__asm imul b \
__asm mov ebx,eax \
__asm mov eax,c \
__asm mov esi,edx \
__asm imul d \
__asm add eax,ebx \
__asm adc edx,esi \
__asm shrd eax,edx,s \
}
MAKECONSTDMulScale(1)
MAKECONSTDMulScale(2)
MAKECONSTDMulScale(3)
MAKECONSTDMulScale(4)
MAKECONSTDMulScale(5)
MAKECONSTDMulScale(6)
MAKECONSTDMulScale(7)
MAKECONSTDMulScale(8)
MAKECONSTDMulScale(9)
MAKECONSTDMulScale(10)
MAKECONSTDMulScale(11)
MAKECONSTDMulScale(12)
MAKECONSTDMulScale(13)
MAKECONSTDMulScale(14)
MAKECONSTDMulScale(15)
MAKECONSTDMulScale(16)
MAKECONSTDMulScale(17)
MAKECONSTDMulScale(18)
MAKECONSTDMulScale(19)
MAKECONSTDMulScale(20)
MAKECONSTDMulScale(21)
MAKECONSTDMulScale(22)
MAKECONSTDMulScale(23)
MAKECONSTDMulScale(24)
MAKECONSTDMulScale(25)
MAKECONSTDMulScale(26)
MAKECONSTDMulScale(27)
MAKECONSTDMulScale(28)
MAKECONSTDMulScale(29)
MAKECONSTDMulScale(30)
MAKECONSTDMulScale(31)
#undef MAKCONSTDMulScale
__forceinline SDWORD DMulScale32 (SDWORD a, SDWORD b, SDWORD c, SDWORD d)
{
__asm mov eax,a
__asm imul b
__asm mov ebx,eax
__asm mov eax,c
__asm mov esi,edx
__asm imul d
__asm add eax,ebx
__asm adc edx,esi
__asm mov eax,edx
}
#define MAKECONSTDivScale(s) \
__forceinline SDWORD DivScale##s (SDWORD a, SDWORD b) \
{ \
__asm mov edx,a \
__asm sar edx,32-s \
__asm mov eax,a \
__asm shl eax,s \
__asm idiv b \
}
MAKECONSTDivScale(2)
MAKECONSTDivScale(3)
MAKECONSTDivScale(4)
MAKECONSTDivScale(5)
MAKECONSTDivScale(6)
MAKECONSTDivScale(7)
MAKECONSTDivScale(8)
MAKECONSTDivScale(9)
MAKECONSTDivScale(10)
MAKECONSTDivScale(11)
MAKECONSTDivScale(12)
MAKECONSTDivScale(13)
MAKECONSTDivScale(14)
MAKECONSTDivScale(15)
MAKECONSTDivScale(16)
MAKECONSTDivScale(17)
MAKECONSTDivScale(18)
MAKECONSTDivScale(19)
MAKECONSTDivScale(20)
MAKECONSTDivScale(21)
MAKECONSTDivScale(22)
MAKECONSTDivScale(23)
MAKECONSTDivScale(24)
MAKECONSTDivScale(25)
MAKECONSTDivScale(26)
MAKECONSTDivScale(27)
MAKECONSTDivScale(28)
MAKECONSTDivScale(29)
MAKECONSTDivScale(30)
MAKECONSTDivScale(31)
#undef MAKECONSTDivScale
#pragma warning (default: 4035)

View file

@ -2093,7 +2093,7 @@ DEFINE_ACTION_FUNCTION(AStateProvider, A_CustomPunch)
damage *= pr_cwpunch() % 8 + 1;
angle = self->Angles.Yaw + pr_cwpunch.Random2() * (5.625 / 256);
if (range == 0) range = MELEERANGE;
if (range == 0) range = DEFMELEERANGE;
pitch = P_AimLineAttack (self, angle, range, &t);
// only use ammo when actually hitting something!

View file

@ -262,7 +262,7 @@ void P_NoiseAlert (AActor *target, AActor *emitter, bool splash, double maxdist)
}
}
DEFINE_ACTION_FUNCTION(AActor, NoiseAlert)
DEFINE_ACTION_FUNCTION(AActor, SoundAlert)
{
PARAM_SELF_PROLOGUE(AActor);
PARAM_OBJECT(target, AActor);

View file

@ -62,7 +62,7 @@ extern int bmapnegy;
#define TALKRANGE (128.)
#define USERANGE (64.)
#define MELEERANGE (64.)
#define DEFMELEERANGE (64.)
#define SAWRANGE (64.+(1./65536.)) // use meleerange + 1 so the puff doesn't skip the flash (i.e. plays all states)
#define MISSILERANGE (32*64.)
#define PLAYERMISSILERANGE (8192.) // [RH] New MISSILERANGE for players

View file

@ -2001,8 +2001,8 @@ int P_VanillaPointOnLineSide(double x, double y, const line_t* line)
auto dx = FloatToFixed(x - line->v1->fX());
auto dy = FloatToFixed(y - line->v1->fY());
auto left = MulScale16( int(delta.Y * 256) , dx );
auto right = MulScale16( dy , int(delta.X * 256) );
auto left = FixedMul( int(delta.Y * 256) , dx );
auto right = FixedMul( dy , int(delta.X * 256) );
if (right < left)
return 0; // front side

View file

@ -639,12 +639,12 @@ void R_AddLine (seg_t *line)
if (rw_frontcz1 > rw_backcz1 || rw_frontcz2 > rw_backcz2)
{
rw_havehigh = true;
WallMost (wallupper, backsector->ceilingplane, &WallC);
R_CreateWallSegmentYSloped (wallupper, backsector->ceilingplane, &WallC);
}
if (rw_frontfz1 < rw_backfz1 || rw_frontfz2 < rw_backfz2)
{
rw_havelow = true;
WallMost (walllower, backsector->floorplane, &WallC);
R_CreateWallSegmentYSloped (walllower, backsector->floorplane, &WallC);
}
// Portal
@ -745,8 +745,8 @@ void R_AddLine (seg_t *line)
}
else
{
rw_ceilstat = WallMost (walltop, frontsector->ceilingplane, &WallC);
rw_floorstat = WallMost (wallbottom, frontsector->floorplane, &WallC);
rw_ceilstat = R_CreateWallSegmentYSloped (walltop, frontsector->ceilingplane, &WallC);
rw_floorstat = R_CreateWallSegmentYSloped (wallbottom, frontsector->floorplane, &WallC);
// [RH] treat off-screen walls as solid
#if 0 // Maybe later...

View file

@ -456,7 +456,7 @@ static bool VOX_ReadSpriteNames(FScanner &sc, TArray<DWORD> &vsprites)
}
else if (sc.StringLen == 5 && (sc.String[4] = toupper(sc.String[4]), sc.String[4] < 'A' || sc.String[4] >= 'A' + MAX_SPRITE_FRAMES))
{
sc.ScriptMessage("Sprite frame %s is invalid.\n", sc.String[4]);
sc.ScriptMessage("Sprite frame %c is invalid.\n", sc.String[4]);
}
else
{

View file

@ -103,8 +103,7 @@ namespace swrenderer
bool R_GetTransMaskDrawers(fixed_t(**tmvline1)(), void(**tmvline4)());
const uint8_t *R_GetColumn(FTexture *tex, int col);
void wallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const uint8_t *(*getcol)(FTexture *tex, int col) = R_GetColumn);
void rt_initcols(uint8_t *buffer = nullptr);
void rt_span_coverage(int x, int start, int stop);
void rt_draw4cols(int sx);

View file

@ -1053,8 +1053,8 @@ CCMD (clearwallcycles)
bestwallcycles = HUGE_VAL;
}
#if 1
// To use these, also uncomment the clock/unclock in wallscan
#if 0
// The replacement code for Build's wallscan doesn't have any timing calls so this does not work anymore.
static double bestscancycles = HUGE_VAL;
ADD_STAT (scancycles)

View file

@ -150,6 +150,7 @@ static double xstepscale, ystepscale;
static double basexfrac, baseyfrac;
void R_DrawSinglePlane (visplane_t *, fixed_t alpha, bool additive, bool masked);
void R_DrawSkySegment(visplane_t *vis, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const uint8_t *(*getcol)(FTexture *tex, int col));
//==========================================================================
//
@ -624,7 +625,7 @@ extern FTexture *rw_pic;
// Allow for layer skies up to 512 pixels tall. This is overkill,
// since the most anyone can ever see of the sky is 500 pixels.
// We need 4 skybufs because wallscan can draw up to 4 columns at a time.
// We need 4 skybufs because R_DrawSkySegment can draw up to 4 columns at a time.
static BYTE skybuf[4][512];
static DWORD lastskycol[4];
static int skycolplace;
@ -891,7 +892,7 @@ static void R_DrawSky (visplane_t *pl)
{
lastskycol[x] = 0xffffffff;
}
wallscan (pl->left, pl->right, (short *)pl->top, (short *)pl->bottom, swall, lwall,
R_DrawSkySegment (pl, (short *)pl->top, (short *)pl->bottom, swall, lwall,
frontyScale, backskytex == NULL ? R_GetOneSkyColumn : R_GetTwoSkyColumns);
}
else
@ -928,7 +929,7 @@ static void R_DrawSkyStriped (visplane_t *pl)
{
lastskycol[x] = 0xffffffff;
}
wallscan (pl->left, pl->right, top, bot, swall, lwall, rw_pic->Scale.Y,
R_DrawSkySegment (pl, top, bot, swall, lwall, rw_pic->Scale.Y,
backskytex == NULL ? R_GetOneSkyColumn : R_GetTwoSkyColumns);
yl = yh;
yh += drawheight;

View file

@ -17,12 +17,6 @@
// DESCRIPTION:
// All the clipping: columns, horizontal spans, sky columns.
//
// This file contains some code from the Build Engine.
//
// "Build Engine & Tools" Copyright (c) 1993-1997 Ken Silverman
// Ken Silverman's official web site: "http://www.advsys.net/ken"
// See the included license file "BUILDLIC.TXT" for license info.
//
//-----------------------------------------------------------------------------
#include <stdlib.h>
@ -64,9 +58,8 @@ namespace swrenderer
{
using namespace drawerargs;
void call_wallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, bool mask);
void wallscan_np2(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, double top, double bot, bool mask);
void wallscan_np2_ds(drawseg_t *ds, int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat);
void R_DrawWallSegment(FTexture *rw_pic, int x1, int x2, short *walltop, short *wallbottom, float *swall, fixed_t *lwall, double yscale, double top, double bottom, bool mask);
void R_DrawDrawSeg(drawseg_t *ds, int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat);
#define HEIGHTBITS 12
#define HEIGHTSHIFT (FRACBITS-HEIGHTBITS)
@ -193,13 +186,13 @@ void ClipMidtex(int x1, int x2)
{
short most[MAXWIDTH];
WallMost(most, curline->frontsector->ceilingplane, &WallC);
R_CreateWallSegmentYSloped(most, curline->frontsector->ceilingplane, &WallC);
for (int i = x1; i < x2; ++i)
{
if (wallupper[i] < most[i])
wallupper[i] = most[i];
}
WallMost(most, curline->frontsector->floorplane, &WallC);
R_CreateWallSegmentYSloped(most, curline->frontsector->floorplane, &WallC);
for (int i = x1; i < x2; ++i)
{
if (walllower[i] > most[i])
@ -381,19 +374,19 @@ void R_RenderMaskedSegRange (drawseg_t *ds, int x1, int x2)
if (fake3D & FAKE3D_CLIPTOP)
{
OWallMost(wallupper, textop < sclipTop - ViewPos.Z ? textop : sclipTop - ViewPos.Z, &WallC);
R_CreateWallSegmentY(wallupper, textop < sclipTop - ViewPos.Z ? textop : sclipTop - ViewPos.Z, &WallC);
}
else
{
OWallMost(wallupper, textop, &WallC);
R_CreateWallSegmentY(wallupper, textop, &WallC);
}
if (fake3D & FAKE3D_CLIPBOTTOM)
{
OWallMost(walllower, textop - texheight > sclipBottom - ViewPos.Z ? textop - texheight : sclipBottom - ViewPos.Z, &WallC);
R_CreateWallSegmentY(walllower, textop - texheight > sclipBottom - ViewPos.Z ? textop - texheight : sclipBottom - ViewPos.Z, &WallC);
}
else
{
OWallMost(walllower, textop - texheight, &WallC);
R_CreateWallSegmentY(walllower, textop - texheight, &WallC);
}
for (i = x1; i < x2; i++)
@ -496,7 +489,7 @@ void R_RenderMaskedSegRange (drawseg_t *ds, int x1, int x2)
if (fake3D & FAKE3D_CLIPTOP)
{
OWallMost(wallupper, sclipTop - ViewPos.Z, &WallC);
R_CreateWallSegmentY(wallupper, sclipTop - ViewPos.Z, &WallC);
for (i = x1; i < x2; i++)
{
if (wallupper[i] < mceilingclip[i])
@ -506,7 +499,7 @@ void R_RenderMaskedSegRange (drawseg_t *ds, int x1, int x2)
}
if (fake3D & FAKE3D_CLIPBOTTOM)
{
OWallMost(walllower, sclipBottom - ViewPos.Z, &WallC);
R_CreateWallSegmentY(walllower, sclipBottom - ViewPos.Z, &WallC);
for (i = x1; i < x2; i++)
{
if (walllower[i] > mfloorclip[i])
@ -517,7 +510,7 @@ void R_RenderMaskedSegRange (drawseg_t *ds, int x1, int x2)
rw_offset = 0;
rw_pic = tex;
wallscan_np2_ds(ds, x1, x2, mceilingclip, mfloorclip, MaskedSWall, maskedtexturecol, ds->yscale);
R_DrawDrawSeg(ds, x1, x2, mceilingclip, mfloorclip, MaskedSWall, maskedtexturecol, ds->yscale);
}
clearfog:
@ -630,8 +623,8 @@ void R_RenderFakeWall(drawseg_t *ds, int x1, int x2, F3DFloor *rover)
WallC.tright.Y = ds->cy + ds->cdy;
WallT = ds->tmapvals;
OWallMost(wallupper, sclipTop - ViewPos.Z, &WallC);
OWallMost(walllower, sclipBottom - ViewPos.Z, &WallC);
R_CreateWallSegmentY(wallupper, sclipTop - ViewPos.Z, &WallC);
R_CreateWallSegmentY(walllower, sclipBottom - ViewPos.Z, &WallC);
for (i = x1; i < x2; i++)
{
@ -645,7 +638,7 @@ void R_RenderFakeWall(drawseg_t *ds, int x1, int x2, F3DFloor *rover)
}
PrepLWall (lwall, curline->sidedef->TexelLength*xscale, ds->sx1, ds->sx2);
wallscan_np2_ds(ds, x1, x2, wallupper, walllower, MaskedSWall, lwall, yscale);
R_DrawDrawSeg(ds, x1, x2, wallupper, walllower, MaskedSWall, lwall, yscale);
R_FinishSetPatchStyle();
}
@ -1057,9 +1050,6 @@ void R_RenderFakeWallRange (drawseg_t *ds, int x1, int x2)
// Can draw or mark the starting pixel of floor and ceiling textures.
// CALLED: CORE LOOPING ROUTINE.
//
// [RH] Rewrote this to use Build's wallscan, so it's quite far
// removed from the original Doom routine.
//
void R_RenderSegLoop ()
{
@ -1175,14 +1165,7 @@ void R_RenderSegLoop ()
{
rw_offset = -rw_offset;
}
if (rw_pic->GetHeight() != 1 << rw_pic->HeightBits)
{
wallscan_np2(x1, x2, walltop, wallbottom, swall, lwall, yscale, MAX(rw_frontcz1, rw_frontcz2), MIN(rw_frontfz1, rw_frontfz2), false);
}
else
{
call_wallscan(x1, x2, walltop, wallbottom, swall, lwall, yscale, false);
}
R_DrawWallSegment(rw_pic, x1, x2, walltop, wallbottom, swall, lwall, yscale, MAX(rw_frontcz1, rw_frontcz2), MIN(rw_frontfz1, rw_frontfz2), false);
}
fillshort (ceilingclip+x1, x2-x1, viewheight);
fillshort (floorclip+x1, x2-x1, 0xffff);
@ -1218,14 +1201,7 @@ void R_RenderSegLoop ()
{
rw_offset = -rw_offset;
}
if (rw_pic->GetHeight() != 1 << rw_pic->HeightBits)
{
wallscan_np2(x1, x2, walltop, wallupper, swall, lwall, yscale, MAX(rw_frontcz1, rw_frontcz2), MIN(rw_backcz1, rw_backcz2), false);
}
else
{
call_wallscan(x1, x2, walltop, wallupper, swall, lwall, yscale, false);
}
R_DrawWallSegment(rw_pic, x1, x2, walltop, wallupper, swall, lwall, yscale, MAX(rw_frontcz1, rw_frontcz2), MIN(rw_backcz1, rw_backcz2), false);
}
memcpy (ceilingclip+x1, wallupper+x1, (x2-x1)*sizeof(short));
}
@ -1264,14 +1240,7 @@ void R_RenderSegLoop ()
{
rw_offset = -rw_offset;
}
if (rw_pic->GetHeight() != 1 << rw_pic->HeightBits)
{
wallscan_np2(x1, x2, walllower, wallbottom, swall, lwall, yscale, MAX(rw_backfz1, rw_backfz2), MIN(rw_frontfz1, rw_frontfz2), false);
}
else
{
call_wallscan(x1, x2, walllower, wallbottom, swall, lwall, yscale, false);
}
R_DrawWallSegment(rw_pic, x1, x2, walllower, wallbottom, swall, lwall, yscale, MAX(rw_backfz1, rw_backfz2), MIN(rw_frontfz1, rw_frontfz2), false);
}
memcpy (floorclip+x1, walllower+x1, (x2-x1)*sizeof(short));
}
@ -1382,7 +1351,7 @@ void R_NewWall (bool needlights)
// wall but nothing to draw for it.
// Recalculate walltop so that the wall is clipped by the back sector's
// ceiling instead of the front sector's ceiling.
WallMost (walltop, backsector->ceilingplane, &WallC);
R_CreateWallSegmentYSloped (walltop, backsector->ceilingplane, &WallC);
}
// Putting sky ceilings on the front and back of a line alters the way unpegged
// positioning works.
@ -1957,19 +1926,19 @@ void R_StoreWallRange (int start, int stop)
ds_p++;
}
int WallMostAny(short *mostbuf, double z1, double z2, const FWallCoords *wallc)
int R_CreateWallSegmentY(short *outbuf, double z1, double z2, const FWallCoords *wallc)
{
float y1 = (float)(CenterY - z1 * InvZtoScale / wallc->sz1);
float y2 = (float)(CenterY - z2 * InvZtoScale / wallc->sz2);
if (y1 < 0 && y2 < 0) // entire line is above screen
{
memset(&mostbuf[wallc->sx1], 0, (wallc->sx2 - wallc->sx1) * sizeof(mostbuf[0]));
memset(&outbuf[wallc->sx1], 0, (wallc->sx2 - wallc->sx1) * sizeof(outbuf[0]));
return 3;
}
else if (y1 > viewheight && y2 > viewheight) // entire line is below screen
{
fillshort(&mostbuf[wallc->sx1], wallc->sx2 - wallc->sx1, viewheight);
fillshort(&outbuf[wallc->sx1], wallc->sx2 - wallc->sx1, viewheight);
return 12;
}
@ -1983,7 +1952,7 @@ int WallMostAny(short *mostbuf, double z1, double z2, const FWallCoords *wallc)
{
float t = (x - wallc->sx1) * rcp_delta;
float y = y1 * (1.0f - t) + y2 * t;
mostbuf[x] = (short)xs_RoundToInt(y);
outbuf[x] = (short)xs_RoundToInt(y);
}
}
else
@ -1992,23 +1961,18 @@ int WallMostAny(short *mostbuf, double z1, double z2, const FWallCoords *wallc)
{
float t = (x - wallc->sx1) * rcp_delta;
float y = y1 * (1.0f - t) + y2 * t;
mostbuf[x] = (short)clamp(xs_RoundToInt(y), 0, viewheight);
outbuf[x] = (short)clamp(xs_RoundToInt(y), 0, viewheight);
}
}
return 0;
}
int OWallMost(short *mostbuf, double z, const FWallCoords *wallc)
{
return WallMostAny(mostbuf, z, z, wallc);
}
int WallMost(short *mostbuf, const secplane_t &plane, const FWallCoords *wallc)
int R_CreateWallSegmentYSloped(short *outbuf, const secplane_t &plane, const FWallCoords *wallc)
{
if (!plane.isSlope())
{
return OWallMost(mostbuf, plane.Zat0() - ViewPos.Z, wallc);
return R_CreateWallSegmentY(outbuf, plane.Zat0() - ViewPos.Z, wallc);
}
else
{
@ -2073,7 +2037,7 @@ int WallMost(short *mostbuf, const secplane_t &plane, const FWallCoords *wallc)
}
}
return WallMostAny(mostbuf, z1, z2, wallc);
return R_CreateWallSegmentY(outbuf, z1, z2, wallc);
}
}

View file

@ -34,8 +34,13 @@ extern short *openings;
extern ptrdiff_t lastopening;
extern size_t maxopenings;
int OWallMost (short *mostbuf, double z, const FWallCoords *wallc);
int WallMost (short *mostbuf, const secplane_t &plane, const FWallCoords *wallc);
int R_CreateWallSegmentY (short *outbuf, double z1, double z2, const FWallCoords *wallc);
int R_CreateWallSegmentYSloped (short *outbuf, const secplane_t &plane, const FWallCoords *wallc);
inline int R_CreateWallSegmentY(short *outbuf, double z, const FWallCoords *wallc)
{
return R_CreateWallSegmentY(outbuf, z, z, wallc);
}
void PrepWall (float *swall, fixed_t *lwall, double walxrepeat, int x1, int x2);
void PrepLWall (fixed_t *lwall, double walxrepeat, int x1, int x2);

View file

@ -1624,7 +1624,7 @@ void R_DrawPlayerSprites ()
else
{
wx = weapon->oldx + (weapon->x - weapon->oldx) * r_TicFracF;
wy = weapon->oldy + (weapon->y - weapon->oldy) * r_TicFracF + WEAPON_FUDGE_Y;
wy = weapon->oldy + (weapon->y - weapon->oldy) * r_TicFracF;
}
}
else

View file

@ -42,6 +42,12 @@ void R_EndDrawerCommands();
class DrawerThread
{
public:
DrawerThread()
{
dc_temp = dc_temp_buff;
dc_temp_rgba = dc_temp_rgbabuff_rgba;
}
std::thread thread;
// Thread line index of this thread

View file

@ -50,10 +50,10 @@ namespace swrenderer
extern FTexture *rw_pic;
extern int wallshade;
struct WallscanSampler
struct WallSampler
{
WallscanSampler() { }
WallscanSampler(int y1, float swal, double yrepeat, fixed_t xoffset, FTexture *texture, const BYTE*(*getcol)(FTexture *texture, int x));
WallSampler() { }
WallSampler(int y1, float swal, double yrepeat, fixed_t xoffset, FTexture *texture, const BYTE*(*getcol)(FTexture *texture, int x));
uint32_t uv_pos;
uint32_t uv_step;
@ -63,7 +63,7 @@ struct WallscanSampler
uint32_t height;
};
WallscanSampler::WallscanSampler(int y1, float swal, double yrepeat, fixed_t xoffset, FTexture *texture, const BYTE*(*getcol)(FTexture *texture, int x))
WallSampler::WallSampler(int y1, float swal, double yrepeat, fixed_t xoffset, FTexture *texture, const BYTE*(*getcol)(FTexture *texture, int x))
{
height = texture->GetHeight();
@ -96,7 +96,7 @@ WallscanSampler::WallscanSampler(int y1, float swal, double yrepeat, fixed_t xof
}
// Draw a column with support for non-power-of-two ranges
void wallscan_drawcol1(int x, int y1, int y2, WallscanSampler &sampler, DWORD(*draw1column)())
static void Draw1Column(int x, int y1, int y2, WallSampler &sampler, DWORD(*draw1column)())
{
if (sampler.uv_max == 0 || sampler.uv_step == 0) // power of two
{
@ -144,7 +144,7 @@ void wallscan_drawcol1(int x, int y1, int y2, WallscanSampler &sampler, DWORD(*d
}
// Draw four columns with support for non-power-of-two ranges
void wallscan_drawcol4(int x, int y1, int y2, WallscanSampler *sampler, void(*draw4columns)())
static void Draw4Columns(int x, int y1, int y2, WallSampler *sampler, void(*draw4columns)())
{
if (sampler[0].uv_max == 0 || sampler[0].uv_step == 0) // power of two, no wrap handling needed
{
@ -210,17 +210,16 @@ void wallscan_drawcol4(int x, int y1, int y2, WallscanSampler *sampler, void(*dr
typedef DWORD(*Draw1ColumnFuncPtr)();
typedef void(*Draw4ColumnsFuncPtr)();
void wallscan_any(
static void ProcessWallWorker(
int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat,
const BYTE *(*getcol)(FTexture *tex, int x),
void(setupwallscan(int bits, Draw1ColumnFuncPtr &draw1, Draw4ColumnsFuncPtr &draw2)))
void(setupProcessNormalWall(int bits, Draw1ColumnFuncPtr &draw1, Draw4ColumnsFuncPtr &draw2)))
{
if (rw_pic->UseType == FTexture::TEX_Null)
return;
fixed_t xoffset = rw_offset;
rw_pic->GetHeight(); // To ensure that rw_pic->HeightBits has been set
int fracbits = 32 - rw_pic->HeightBits;
if (fracbits == 32)
{ // Hack for one pixel tall textures
@ -231,7 +230,7 @@ void wallscan_any(
DWORD(*draw1column)();
void(*draw4columns)();
setupwallscan(fracbits, draw1column, draw4columns);
setupProcessNormalWall(fracbits, draw1column, draw4columns);
bool fixed = (fixedcolormap != NULL || fixedlightlev >= 0);
if (fixed)
@ -264,8 +263,8 @@ void wallscan_any(
if (!fixed)
dc_colormap = basecolormap->Maps + (GETPALOOKUP(light, wallshade) << COLORMAPSHIFT);
WallscanSampler sampler(y1, swal[x], yrepeat, lwal[x] + xoffset, rw_pic, getcol);
wallscan_drawcol1(x, y1, y2, sampler, draw1column);
WallSampler sampler(y1, swal[x], yrepeat, lwal[x] + xoffset, rw_pic, getcol);
Draw1Column(x, y1, y2, sampler, draw1column);
}
// The aligned columns
@ -282,9 +281,9 @@ void wallscan_any(
light += rw_lightstep;
}
WallscanSampler sampler[4];
WallSampler sampler[4];
for (int i = 0; i < 4; i++)
sampler[i] = WallscanSampler(y1[i], swal[x + i], yrepeat, lwal[x + i] + xoffset, rw_pic, getcol);
sampler[i] = WallSampler(y1[i], swal[x + i], yrepeat, lwal[x + i] + xoffset, rw_pic, getcol);
// Figure out where we vertically can start and stop drawing 4 columns in one go
int middle_y1 = y1[0];
@ -312,7 +311,7 @@ void wallscan_any(
if (!fixed)
dc_colormap = basecolormap->Maps + (GETPALOOKUP(lights[i], wallshade) << COLORMAPSHIFT);
wallscan_drawcol1(x + i, y1[i], y2[i], sampler[i], draw1column);
Draw1Column(x + i, y1[i], y2[i], sampler[i], draw1column);
}
continue;
}
@ -324,7 +323,7 @@ void wallscan_any(
dc_colormap = basecolormap->Maps + (GETPALOOKUP(lights[i], wallshade) << COLORMAPSHIFT);
if (y1[i] < middle_y1)
wallscan_drawcol1(x + i, y1[i], middle_y1, sampler[i], draw1column);
Draw1Column(x + i, y1[i], middle_y1, sampler[i], draw1column);
}
// Draw the area where all 4 columns are active
@ -335,7 +334,7 @@ void wallscan_any(
palookupoffse[i] = basecolormap->Maps + (GETPALOOKUP(lights[i], wallshade) << COLORMAPSHIFT);
}
}
wallscan_drawcol4(x, middle_y1, middle_y2, sampler, draw4columns);
Draw4Columns(x, middle_y1, middle_y2, sampler, draw4columns);
// Draw the last rows where not all 4 columns are active
for (int i = 0; i < 4; i++)
@ -344,7 +343,7 @@ void wallscan_any(
dc_colormap = basecolormap->Maps + (GETPALOOKUP(lights[i], wallshade) << COLORMAPSHIFT);
if (middle_y2 < y2[i])
wallscan_drawcol1(x + i, middle_y2, y2[i], sampler[i], draw1column);
Draw1Column(x + i, middle_y2, y2[i], sampler[i], draw1column);
}
}
@ -359,16 +358,16 @@ void wallscan_any(
if (!fixed)
dc_colormap = basecolormap->Maps + (GETPALOOKUP(light, wallshade) << COLORMAPSHIFT);
WallscanSampler sampler(y1, swal[x], yrepeat, lwal[x] + xoffset, rw_pic, getcol);
wallscan_drawcol1(x, y1, y2, sampler, draw1column);
WallSampler sampler(y1, swal[x], yrepeat, lwal[x] + xoffset, rw_pic, getcol);
Draw1Column(x, y1, y2, sampler, draw1column);
}
NetUpdate();
}
void wallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x))
static void ProcessNormalWall(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x) = R_GetColumn)
{
wallscan_any(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
ProcessWallWorker(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
{
setupvline(bits);
line1 = dovline1;
@ -376,15 +375,15 @@ void wallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lw
});
}
void maskwallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x) = R_GetColumn)
static void ProcessMaskedWall(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x) = R_GetColumn)
{
if (!rw_pic->bMasked) // Textures that aren't masked can use the faster wallscan.
if (!rw_pic->bMasked) // Textures that aren't masked can use the faster ProcessNormalWall.
{
wallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol);
ProcessNormalWall(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol);
}
else
{
wallscan_any(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
ProcessWallWorker(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
{
setupmvline(bits);
line1 = domvline1;
@ -393,18 +392,18 @@ void maskwallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t
}
}
void transmaskwallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x) = R_GetColumn)
static void ProcessTranslucentWall(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x) = R_GetColumn)
{
static fixed_t(*tmvline1)();
static void(*tmvline4)();
if (!R_GetTransMaskDrawers(&tmvline1, &tmvline4))
{
// The current translucency is unsupported, so draw with regular maskwallscan instead.
maskwallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol);
// The current translucency is unsupported, so draw with regular ProcessMaskedWall instead.
ProcessMaskedWall(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol);
}
else
{
wallscan_any(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
ProcessWallWorker(x1, x2, uwal, dwal, swal, lwal, yrepeat, getcol, [](int bits, Draw1ColumnFuncPtr &line1, Draw4ColumnsFuncPtr &line4)
{
setuptmvline(bits);
line1 = reinterpret_cast<DWORD(*)()>(tmvline1);
@ -413,7 +412,7 @@ void transmaskwallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fi
}
}
void wallscan_striped (int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat)
static void ProcessStripedWall(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat)
{
FDynamicColormap *startcolormap = basecolormap;
int startshade = wallshade;
@ -431,14 +430,14 @@ void wallscan_striped (int x1, int x2, short *uwal, short *dwal, float *swal, fi
// kg3D - fake floors instead of zdoom light list
for (unsigned int i = 0; i < frontsector->e->XFloor.lightlist.Size(); i++)
{
int j = WallMost (most3, frontsector->e->XFloor.lightlist[i].plane, &WallC);
int j = R_CreateWallSegmentYSloped (most3, frontsector->e->XFloor.lightlist[i].plane, &WallC);
if (j != 3)
{
for (int j = x1; j < x2; ++j)
{
down[j] = clamp (most3[j], up[j], dwal[j]);
}
wallscan (x1, x2, up, down, swal, lwal, yrepeat);
ProcessNormalWall (x1, x2, up, down, swal, lwal, yrepeat);
up = down;
down = (down == most1) ? most2 : most1;
}
@ -449,49 +448,49 @@ void wallscan_striped (int x1, int x2, short *uwal, short *dwal, float *swal, fi
*lit->p_lightlevel, lit->lightsource != NULL) + r_actualextralight);
}
wallscan (x1, x2, up, dwal, swal, lwal, yrepeat);
ProcessNormalWall (x1, x2, up, dwal, swal, lwal, yrepeat);
basecolormap = startcolormap;
wallshade = startshade;
}
void call_wallscan(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, bool mask)
static void ProcessWall(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, bool mask)
{
if (mask)
{
if (colfunc == basecolfunc)
{
maskwallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat);
ProcessMaskedWall(x1, x2, uwal, dwal, swal, lwal, yrepeat);
}
else
{
transmaskwallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat);
ProcessTranslucentWall(x1, x2, uwal, dwal, swal, lwal, yrepeat);
}
}
else
{
if (fixedcolormap != NULL || fixedlightlev >= 0 || !(frontsector->e && frontsector->e->XFloor.lightlist.Size()))
{
wallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat);
ProcessNormalWall(x1, x2, uwal, dwal, swal, lwal, yrepeat);
}
else
{
wallscan_striped(x1, x2, uwal, dwal, swal, lwal, yrepeat);
ProcessStripedWall(x1, x2, uwal, dwal, swal, lwal, yrepeat);
}
}
}
//=============================================================================
//
// wallscan_np2
// ProcessWallNP2
//
// This is a wrapper around wallscan that helps it tile textures whose heights
// This is a wrapper around ProcessWall that helps it tile textures whose heights
// are not powers of 2. It divides the wall into texture-sized strips and calls
// wallscan for each of those. Since only one repetition of the texture fits
// in each strip, wallscan will not tile.
// ProcessNormalWall for each of those. Since only one repetition of the texture fits
// in each strip, ProcessWall will not tile.
//
//=============================================================================
void wallscan_np2(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, double top, double bot, bool mask)
static void ProcessWallNP2(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, double top, double bot, bool mask)
{
short most1[MAXWIDTH], most2[MAXWIDTH], most3[MAXWIDTH];
short *up, *down;
@ -511,21 +510,21 @@ void wallscan_np2(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t
dc_texturemid = (partition - ViewPos.Z) * yrepeat + texheight;
while (partition > bot)
{
int j = OWallMost(most3, partition - ViewPos.Z, &WallC);
int j = R_CreateWallSegmentY(most3, partition - ViewPos.Z, &WallC);
if (j != 3)
{
for (int j = x1; j < x2; ++j)
{
down[j] = clamp(most3[j], up[j], dwal[j]);
}
call_wallscan(x1, x2, up, down, swal, lwal, yrepeat, mask);
ProcessWall(x1, x2, up, down, swal, lwal, yrepeat, mask);
up = down;
down = (down == most1) ? most2 : most1;
}
partition -= scaledtexheight;
dc_texturemid -= texheight;
}
call_wallscan(x1, x2, up, dwal, swal, lwal, yrepeat, mask);
ProcessWall(x1, x2, up, dwal, swal, lwal, yrepeat, mask);
}
else
{ // upside down: draw strips from bottom to top
@ -535,25 +534,25 @@ void wallscan_np2(int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t
dc_texturemid = (partition - ViewPos.Z) * yrepeat + texheight;
while (partition < top)
{
int j = OWallMost(most3, partition - ViewPos.Z, &WallC);
int j = R_CreateWallSegmentY(most3, partition - ViewPos.Z, &WallC);
if (j != 12)
{
for (int j = x1; j < x2; ++j)
{
up[j] = clamp(most3[j], uwal[j], down[j]);
}
call_wallscan(x1, x2, up, down, swal, lwal, yrepeat, mask);
ProcessWall(x1, x2, up, down, swal, lwal, yrepeat, mask);
down = up;
up = (up == most1) ? most2 : most1;
}
partition -= scaledtexheight;
dc_texturemid -= texheight;
}
call_wallscan(x1, x2, uwal, down, swal, lwal, yrepeat, mask);
ProcessWall(x1, x2, uwal, down, swal, lwal, yrepeat, mask);
}
}
void wallscan_np2_ds(drawseg_t *ds, int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat)
void R_DrawDrawSeg(drawseg_t *ds, int x1, int x2, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat)
{
if (rw_pic->GetHeight() != 1 << rw_pic->HeightBits)
{
@ -571,13 +570,32 @@ void wallscan_np2_ds(drawseg_t *ds, int x1, int x2, short *uwal, short *dwal, fl
{
bot = MAX(bot, sclipBottom);
}
wallscan_np2(x1, x2, uwal, dwal, swal, lwal, yrepeat, top, bot, true);
ProcessWallNP2(x1, x2, uwal, dwal, swal, lwal, yrepeat, top, bot, true);
}
else
{
call_wallscan(x1, x2, uwal, dwal, swal, lwal, yrepeat, true);
ProcessWall(x1, x2, uwal, dwal, swal, lwal, yrepeat, true);
}
}
void R_DrawWallSegment(FTexture *rw_pic, int x1, int x2, short *walltop, short *wallbottom, float *swall, fixed_t *lwall, double yscale, double top, double bottom, bool mask)
{
if (rw_pic->GetHeight() != 1 << rw_pic->HeightBits)
{
ProcessWallNP2(x1, x2, walltop, wallbottom, swall, lwall, yscale, top, bottom, false);
}
else
{
ProcessWall(x1, x2, walltop, wallbottom, swall, lwall, yscale, false);
}
}
void R_DrawSkySegment(visplane_t *pl, short *uwal, short *dwal, float *swal, fixed_t *lwal, double yrepeat, const BYTE *(*getcol)(FTexture *tex, int x))
{
ProcessNormalWall(pl->left, pl->right, uwal, dwal, swal, lwal, yrepeat, getcol);
}
}

View file

@ -61,8 +61,8 @@ public:
int MustMatchString(const char * const *strings, size_t stride = sizeof(char*));
int GetMessageLine();
void ScriptError(const char *message, ...);
void ScriptMessage(const char *message, ...);
void ScriptError(const char *message, ...) GCCPRINTF(2,3);
void ScriptMessage(const char *message, ...) GCCPRINTF(2,3);
bool isText();
@ -155,7 +155,7 @@ struct FScriptPosition
FScriptPosition(FString fname, int line);
FScriptPosition(FScanner &sc);
FScriptPosition &operator=(const FScriptPosition &other);
void Message(int severity, const char *message,...) const;
void Message(int severity, const char *message,...) const GCCPRINTF(3,4);
static void ResetErrorCounter()
{
WarnCounter = 0;

View file

@ -1,10 +1,10 @@
/*
** thingdef_expression.cpp
** codegen.cpp
**
** Expression evaluation
** Compiler backend / code generation for ZScript and DECORATE
**
**---------------------------------------------------------------------------
** Copyright 2008 Christoph Oelckers
** Copyright 2008-2016 Christoph Oelckers
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
@ -3371,6 +3371,17 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx)
{
Promote(ctx);
}
// allows comparing state labels with null pointers.
else if (left->ValueType == TypeStateLabel && right->ValueType == TypeNullPtr)
{
right = new FxTypeCast(right, TypeStateLabel, false);
SAFE_RESOLVE(right, ctx);
}
else if (right->ValueType == TypeStateLabel && left->ValueType == TypeNullPtr)
{
left = new FxTypeCast(left, TypeStateLabel, false);
SAFE_RESOLVE(left, ctx);
}
else if (left->ValueType->GetRegType() == REGT_POINTER && right->ValueType->GetRegType() == REGT_POINTER)
{
if (left->ValueType != right->ValueType && right->ValueType != TypeNullPtr && left->ValueType != TypeNullPtr &&
@ -6586,8 +6597,7 @@ ExpEmit FxStructMember::Emit(VMFunctionBuilder *build)
//==========================================================================
//
// not really needed at the moment but may become useful with meta properties
// and some other class-specific extensions.
//
//
//==========================================================================

View file

@ -74,7 +74,7 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode)
}
if (cls == nullptr)
{
Error(cnode, "Class %s cannot be found in the current translation unit.");
Error(cnode, "Class %s cannot be found in the current translation unit.", FName(cnode->NodeName).GetChars());
return;
}
}
@ -1583,12 +1583,19 @@ PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt)
PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym)
{
// The duplicate Simplify call is necessary because if the head node gets replaced there is no way to detect the end of the list otherwise.
arraysize = Simplify(arraysize, sym, true);
ZCC_Expression *val;
TArray<ZCC_Expression *> indices;
// Simplify is too broken to resolve this inside the ring list so unravel the list into an array before starting to simplify its components.
auto node = arraysize;
do
{
val = Simplify(arraysize, sym, true);
indices.Push(node);
node = static_cast<ZCC_Expression*>(node->SiblingNext);
} while (node != arraysize);
for (auto node : indices)
{
auto val = Simplify(node, sym, true);
if (val->Operation != PEX_ConstValue || !val->Type->IsA(RUNTIME_CLASS(PInt)))
{
Error(arraysize, "Array index must be an integer constant");
@ -1601,8 +1608,7 @@ PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize,
return TypeError;
}
baseType = NewArray(baseType, size);
val = static_cast<ZCC_Expression *>(val->SiblingNext);
} while (val != arraysize);
}
return baseType;
}

View file

@ -135,8 +135,8 @@ private:
ZCC_ExprTypeRef *NodeFromSymbolType(PSymbolType *sym, ZCC_Expression *idnode);
void Warn(ZCC_TreeNode *node, const char *msg, ...);
void Error(ZCC_TreeNode *node, const char *msg, ...);
void Warn(ZCC_TreeNode *node, const char *msg, ...) GCCPRINTF(3,4);
void Error(ZCC_TreeNode *node, const char *msg, ...) GCCPRINTF(3,4);
void MessageV(ZCC_TreeNode *node, const char *txtcolor, const char *msg, va_list argptr);
FxExpression *ConvertAST(PStruct *cclass, ZCC_TreeNode *ast);

View file

@ -190,7 +190,7 @@ enum
VERB_DEBUG
};
void cmsg(int type, int verbosity_level, const char *fmt, ...);
void cmsg(int type, int verbosity_level, const char *fmt, ...) GCCPRINTF(3,4);
/*

View file

@ -680,17 +680,23 @@ void I_SetWndProc()
void RestoreConView()
{
HDC screenDC = GetDC(0);
int dpi = GetDeviceCaps(screenDC, LOGPIXELSX);
ReleaseDC(0, screenDC);
int width = (512 * dpi + 96 / 2) / 96;
int height = (384 * dpi + 96 / 2) / 96;
// Make sure the window has a frame in case it was fullscreened.
SetWindowLongPtr (Window, GWL_STYLE, WS_VISIBLE|WS_OVERLAPPEDWINDOW);
if (GetWindowLong (Window, GWL_EXSTYLE) & WS_EX_TOPMOST)
{
SetWindowPos (Window, HWND_BOTTOM, 0, 0, 512, 384,
SetWindowPos (Window, HWND_BOTTOM, 0, 0, width, height,
SWP_DRAWFRAME | SWP_NOCOPYBITS | SWP_NOMOVE);
SetWindowPos (Window, HWND_TOP, 0, 0, 0, 0, SWP_NOCOPYBITS | SWP_NOMOVE | SWP_NOSIZE);
}
else
{
SetWindowPos (Window, NULL, 0, 0, 512, 384,
SetWindowPos (Window, NULL, 0, 0, width, height,
SWP_DRAWFRAME | SWP_NOCOPYBITS | SWP_NOMOVE | SWP_NOZORDER);
}
@ -935,8 +941,11 @@ void DoMain (HINSTANCE hInstance)
progdir.Truncate((long)strlen(program));
progdir.UnlockBuffer();
width = 512;
height = 384;
HDC screenDC = GetDC(0);
int dpi = GetDeviceCaps(screenDC, LOGPIXELSX);
ReleaseDC(0, screenDC);
width = (512 * dpi + 96 / 2) / 96;
height = (384 * dpi + 96 / 2) / 96;
// Many Windows structures that specify their size do so with the first
// element. DEVMODE is not one of those structures.

View file

@ -1375,10 +1375,16 @@ static HCURSOR CreateAlphaCursor(FTexture *cursorpic)
HBITMAP color, mono;
void *bits;
// Find closest integer scale factor for the monitor DPI
HDC screenDC = GetDC(0);
int dpi = GetDeviceCaps(screenDC, LOGPIXELSX);
int scale = MAX((dpi + 96 / 2 - 1) / 96, 1);
ReleaseDC(0, screenDC);
memset(&bi, 0, sizeof(bi));
bi.bV5Size = sizeof(bi);
bi.bV5Width = 32;
bi.bV5Height = 32;
bi.bV5Width = 32 * scale;
bi.bV5Height = 32 * scale;
bi.bV5Planes = 1;
bi.bV5BitCount = 32;
bi.bV5Compression = BI_BITFIELDS;
@ -1403,7 +1409,7 @@ static HCURSOR CreateAlphaCursor(FTexture *cursorpic)
}
// Create an empty mask bitmap, since CreateIconIndirect requires this.
mono = CreateBitmap(32, 32, 1, 1, NULL);
mono = CreateBitmap(32 * scale, 32 * scale, 1, 1, NULL);
if (mono == NULL)
{
DeleteObject(color);
@ -1413,10 +1419,28 @@ static HCURSOR CreateAlphaCursor(FTexture *cursorpic)
// Copy cursor to the color bitmap. Note that GDI bitmaps are upside down compared
// to normal conventions, so we create the FBitmap pointing at the last row and use
// a negative pitch so that CopyTrueColorPixels will use GDI's orientation.
FBitmap bmp((BYTE *)bits + 31*32*4, -32*4, 32, 32);
cursorpic->CopyTrueColorPixels(&bmp, 0, 0);
if (scale == 1)
{
FBitmap bmp((BYTE *)bits + 31 * 32 * 4, -32 * 4, 32, 32);
cursorpic->CopyTrueColorPixels(&bmp, 0, 0);
}
else
{
TArray<uint32_t> unscaled;
unscaled.Resize(32 * 32);
FBitmap bmp((BYTE *)&unscaled[0] + 31 * 32 * 4, -32 * 4, 32, 32);
cursorpic->CopyTrueColorPixels(&bmp, 0, 0);
uint32_t *scaled = (uint32_t*)bits;
for (int y = 0; y < 32 * scale; y++)
{
for (int x = 0; x < 32 * scale; x++)
{
scaled[x + y * 32 * scale] = unscaled[x / scale + y / scale * 32];
}
}
}
return CreateBitmapCursor(cursorpic->LeftOffset, cursorpic->TopOffset, mono, color);
return CreateBitmapCursor(cursorpic->LeftOffset * scale, cursorpic->TopOffset * scale, mono, color);
}
//==========================================================================

View file

@ -14,7 +14,7 @@
</trustInfo>
<asmv3:application xmlns:asmv3="urn:schemas-microsoft-com:asm.v3">
<asmv3:windowsSettings xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">
<dpiAware>true</dpiAware>
<dpiAware>true/pm</dpiAware>
</asmv3:windowsSettings>
</asmv3:application>
<compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
@ -31,4 +31,4 @@
<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}"/>
</application>
</compatibility>
</assembly>
</assembly>

View file

@ -300,7 +300,7 @@ class Actor : Thinker native
native bool isTeammate(Actor other);
native int PlayerNumber();
native void SetFriendPlayer(PlayerInfo player);
native void NoiseAlert(Actor target, bool splash = false, double maxdist = 0);
native void SoundAlert(Actor target, bool splash = false, double maxdist = 0);
native void DaggerAlert(Actor target);
native void ClearBounce();
native TerrainDef GetFloorTerrain();

View file

@ -871,7 +871,7 @@ enum ELineAttackFlags
LAF_NOINTERACT = 8,
}
const MELEERANGE = 64;
const DEFMELEERANGE = 64;
const SAWRANGE = (64.+(1./65536.)); // use meleerange + 1 so the puff doesn't skip the flash (i.e. plays all states)
const MISSILERANGE = (32*64);
const PLAYERMISSILERANGE = 8192; // [RH] New MISSILERANGE for players

View file

@ -282,7 +282,7 @@ class ScriptedMarine : Actor
//
//============================================================================
void A_M_Refire (bool ignoremissile, statelabel jumpto)
void A_M_Refire (bool ignoremissile, statelabel jumpto = null)
{
if (target == null || target.health <= 0)
{
@ -293,13 +293,15 @@ class ScriptedMarine : Actor
return;
}
}
SetStateLabel (jumpto);
if (jumpto != null) SetStateLabel (jumpto);
else SetState(CurState + 1);
return;
}
if (((ignoremissile || MissileState == null) && !CheckMeleeRange ()) ||
!CheckSight (target) || random[SMarineRefire]() < 4) // Small chance of stopping even when target not dead
{
SetStateLabel (jumpto);
if (jumpto != null) SetStateLabel (jumpto);
else SetState(CurState + 1);
}
}
@ -372,8 +374,8 @@ class ScriptedMarine : Actor
A_FaceTarget ();
double ang = angle + random2[SMarinePunch]() * (5.625 / 256);
double pitch = AimLineAttack (ang, MELEERANGE);
LineAttack (ang, MELEERANGE, pitch, damage, 'Melee', "BulletPuff", true, t);
double pitch = AimLineAttack (ang, DEFMELEERANGE);
LineAttack (ang, DEFMELEERANGE, pitch, damage, 'Melee', "BulletPuff", true, t);
// turn to face target
if (t.linetarget)

View file

@ -65,9 +65,9 @@ extend class Actor
damage *= 10;
double ang = angle + Random2[Punch]() * (5.625 / 256);
double pitch = AimLineAttack (ang, MELEERANGE);
double pitch = AimLineAttack (ang, DEFMELEERANGE);
LineAttack (ang, MELEERANGE, pitch, damage, 'Melee', "BulletPuff", LAF_ISMELEEATTACK, t);
LineAttack (ang, DEFMELEERANGE, pitch, damage, 'Melee', "BulletPuff", LAF_ISMELEEATTACK, t);
// turn to face target
if (t.linetarget)

View file

@ -77,8 +77,8 @@ class Beak : Weapon
int damage = random[BeakAtk](1,3);
double ang = angle;
double slope = AimLineAttack (ang, MELEERANGE);
LineAttack (ang, MELEERANGE, slope, damage, 'Melee', "BeakPuff", true, t);
double slope = AimLineAttack (ang, DEFMELEERANGE);
LineAttack (ang, DEFMELEERANGE, slope, damage, 'Melee', "BeakPuff", true, t);
if (t.linetarget)
{
angle = t.angleFromSource;
@ -125,8 +125,8 @@ class BeakPowered : Beak
int damage = random[BeakAtk](1,8) * 4;
double ang = angle;
double slope = AimLineAttack (ang, MELEERANGE);
LineAttack (ang, MELEERANGE, slope, damage, 'Melee', "BeakPuff", true, t);
double slope = AimLineAttack (ang, DEFMELEERANGE);
LineAttack (ang, DEFMELEERANGE, slope, damage, 'Melee', "BeakPuff", true, t);
if (t.linetarget)
{
angle = t.angleFromSource;

View file

@ -74,7 +74,7 @@ class Gauntlets : Weapon
if (power)
{
damage = random[GauntletAtk](1, 8) * 2;
dist = 4*MELEERANGE;
dist = 4*DEFMELEERANGE;
ang += random2[GauntletAtk]() * (2.8125 / 256);
pufftype = "GauntletPuff2";
}

View file

@ -54,8 +54,8 @@ class Staff : HereticWeapon
return;
}
double ang = angle + Random2[StaffAtk]() * (5.625 / 256);
double slope = AimLineAttack (ang, MELEERANGE);
LineAttack (ang, MELEERANGE, slope, damage, 'Melee', puff, true, t);
double slope = AimLineAttack (ang, DEFMELEERANGE);
LineAttack (ang, DEFMELEERANGE, slope, damage, 'Melee', puff, true, t);
if (t.linetarget)
{
//S_StartSound(player.mo, sfx_stfhit);

View file

@ -103,10 +103,9 @@ extend class Actor
action void A_Blast(int blastflags = 0, double strength = 255, double radius = 255, double speed = 20, class<Actor> blasteffect = "BlastEffect", sound blastsound = "BlastRadius")
{
Weapon weapon = player.ReadyWeapon;
if (player && (blastflags & BF_USEAMMO) && invoker == weapon && stateinfo != null && stateinfo.mStateType == STATE_Psprite)
if (player && (blastflags & BF_USEAMMO) && invoker == player.ReadyWeapon && stateinfo != null && stateinfo.mStateType == STATE_Psprite)
{
Weapon weapon = player.ReadyWeapon;
if (weapon != null && !weapon.DepleteAmmo(weapon.bAltFire))
{
return;
@ -117,7 +116,7 @@ extend class Actor
if (!(blastflags & BF_DONTWARN))
{
NoiseAlert (self);
SoundAlert (self);
}
ThinkerIterator it = ThinkerIterator.Create("Actor");
Actor mo;

View file

@ -66,10 +66,10 @@ class CWeapMace : ClericWeapon
for (int j = 1; j >= -1; j -= 2)
{
double ang = angle + j*i*(45. / 16);
double slope = AimLineAttack(ang, 2 * MELEERANGE, t);
double slope = AimLineAttack(ang, 2 * DEFMELEERANGE, t);
if (t.linetarget)
{
LineAttack(ang, 2 * MELEERANGE, slope, damage, 'Melee', "HammerPuff", true, t);
LineAttack(ang, 2 * DEFMELEERANGE, slope, damage, 'Melee', "HammerPuff", true, t);
if (t.linetarget != null)
{
AdjustPlayerAngle(t);
@ -81,7 +81,7 @@ class CWeapMace : ClericWeapon
// didn't find any creatures, so try to strike any walls
weaponspecial = 0;
double slope = AimLineAttack (angle, MELEERANGE);
LineAttack (angle, MELEERANGE, slope, damage, 'Melee', "HammerPuff");
double slope = AimLineAttack (angle, DEFMELEERANGE);
LineAttack (angle, DEFMELEERANGE, slope, damage, 'Melee', "HammerPuff");
}
}

View file

@ -74,10 +74,10 @@ class CWeapStaff : ClericWeapon
for (int j = 1; j >= -1; j -= 2)
{
double ang = angle + j*i*(45. / 16);
double slope = AimLineAttack(ang, 1.5 * MELEERANGE, t, 0., ALF_CHECK3D);
double slope = AimLineAttack(ang, 1.5 * DEFMELEERANGE, t, 0., ALF_CHECK3D);
if (t.linetarget)
{
LineAttack(ang, 1.5 * MELEERANGE, slope, damage, 'Melee', "CStaffPuff", false, t);
LineAttack(ang, 1.5 * DEFMELEERANGE, slope, damage, 'Melee', "CStaffPuff", false, t);
if (t.linetarget != null)
{
angle = t.angleFromSource;

View file

@ -3,7 +3,7 @@
class FWeapAxe : FighterWeapon
{
const AXERANGE = (2.25 * MELEERANGE);
const AXERANGE = (2.25 * DEFMELEERANGE);
Default
{
@ -273,8 +273,8 @@ class FWeapAxe : FighterWeapon
// didn't find any creatures, so try to strike any walls
self.weaponspecial = 0;
double slope = AimLineAttack (angle, MELEERANGE);
LineAttack (angle, MELEERANGE, slope, damage, 'Melee', pufftype, true);
double slope = AimLineAttack (angle, DEFMELEERANGE);
LineAttack (angle, DEFMELEERANGE, slope, damage, 'Melee', pufftype, true);
}
}

View file

@ -56,7 +56,7 @@ class FWeapFist : FighterWeapon
Class<Actor> pufftype;
FTranslatedLineTarget t;
double slope = AimLineAttack (angle, 2*MELEERANGE, t);
double slope = AimLineAttack (angle, 2*DEFMELEERANGE, t);
if (t.linetarget != null)
{
if (++weaponspecial >= 3)
@ -69,7 +69,7 @@ class FWeapFist : FighterWeapon
{
pufftype = "PunchPuff";
}
LineAttack (angle, 2*MELEERANGE, slope, damage, 'Melee', pufftype, true, t);
LineAttack (angle, 2*DEFMELEERANGE, slope, damage, 'Melee', pufftype, true, t);
if (t.linetarget != null)
{
// The mass threshold has been changed to CommanderKeen's value which has been used most often for 'unmovable' stuff.
@ -117,8 +117,8 @@ class FWeapFist : FighterWeapon
// didn't find any creatures, so try to strike any walls
weaponspecial = 0;
double slope = AimLineAttack (angle, MELEERANGE);
LineAttack (angle, MELEERANGE, slope, damage, 'Melee', "PunchPuff", true);
double slope = AimLineAttack (angle, DEFMELEERANGE);
LineAttack (angle, DEFMELEERANGE, slope, damage, 'Melee', "PunchPuff", true);
}
}

View file

@ -3,7 +3,7 @@
class FWeapHammer : FighterWeapon
{
const HAMMER_RANGE = 1.5 * MELEERANGE;
const HAMMER_RANGE = 1.5 * DEFMELEERANGE;
Default
{

View file

@ -72,7 +72,7 @@ class MWeapFrost : MageWeapon
for (int i = 0; i < 16; i++)
{
double ang = angle + i*(45./16);
double slope = AimLineAttack (ang, MELEERANGE, t, 0., ALF_CHECK3D);
double slope = AimLineAttack (ang, DEFMELEERANGE, t, 0., ALF_CHECK3D);
if (t.linetarget)
{
t.linetarget.DamageMobj (self, self, damage, 'Ice', DMG_USEANGLE, t.angleFromSource);

View file

@ -70,8 +70,8 @@ class Snout : Weapon
int damage = random[SnoutAttack](3, 6);
double ang = angle;
double slope = AimLineAttack(ang, MELEERANGE);
Actor puff = LineAttack(ang, MELEERANGE, slope, damage, 'Melee', "SnoutPuff", true, t);
double slope = AimLineAttack(ang, DEFMELEERANGE);
Actor puff = LineAttack(ang, DEFMELEERANGE, slope, damage, 'Melee', "SnoutPuff", true, t);
A_PlaySound("PigActive", CHAN_VOICE);
if(t.linetarget)
{

View file

@ -302,7 +302,7 @@ class AcolyteToBe : Acolyte
Door_Close(999, 64);
if (target != null && target.player != null)
{
NoiseAlert (target);
SoundAlert (target);
}
}
}

View file

@ -114,7 +114,7 @@ extend class Actor
if (reactiontime == 2)
{
// [RH] Unalert monsters near the alarm and not just those in the same sector as it.
NoiseAlert (NULL, false);
SoundAlert (NULL, false);
}
else if (reactiontime > 50)
{

View file

@ -67,7 +67,7 @@ class Stalker : Actor
STLK QRST 4;
STLK U 4 A_NoBlocking;
STLK VW 4;
STLK "XYZ[" 4 Bright;
STLK XYZ[ 4 Bright;
Stop;
}
@ -86,7 +86,7 @@ class Stalker : Actor
void A_StalkerLookInit ()
{
State st;
if (!bNoGravity)
if (bNoGravity)
{
st = FindState("LookCeiling");
}
@ -94,7 +94,7 @@ class Stalker : Actor
{
st = FindState("LookFloor");
}
if (st.NextState != st)
if (st != CurState.NextState)
{
SetState (st);
}

View file

@ -173,7 +173,7 @@ extend class Actor
if (target != null && emitter != null)
{
emitter.NoiseAlert(target, false, maxdist);
emitter.SoundAlert(target, false, maxdist);
}
}

View file

@ -610,7 +610,7 @@ class RaiseAlarm : DummyStrifeItem
override bool TryPickup (in out Actor toucher)
{
toucher.NoiseAlert (toucher);
toucher.SoundAlert (toucher);
ThinkerIterator it = ThinkerIterator.Create("AlienSpectre3");
Actor spectre = Actor(it.Next());
@ -629,7 +629,7 @@ class RaiseAlarm : DummyStrifeItem
{
if (dropper.target != null)
{
dropper.target.NoiseAlert(dropper.target);
dropper.target.SoundAlert(dropper.target);
if (dropper.target.CheckLocalView(consoleplayer))
{
A_Log("You Fool! You've set off the alarm.");
@ -674,7 +674,7 @@ class CloseDoor222 : DummyStrifeItem
{
A_Log("You're dead! You set off the alarm.");
}
dropper.target.NoiseAlert(dropper.target);
dropper.target.SoundAlert(dropper.target);
}
Destroy ();
return true;

View file

@ -1857,7 +1857,7 @@ class PowerCoupling : Actor
// [RH] In case the player broke it with the dagger, alert the guards now.
if (LastHeard != source)
{
NoiseAlert (source);
SoundAlert (source);
}
Door_Close(225, 16);
Floor_LowerToHighestEE(44, 8);