First!
This commit is contained in:
commit
22dac448ea
918 changed files with 2378 additions and 0 deletions
165
zscript/LGPL3.txt
Normal file
165
zscript/LGPL3.txt
Normal file
|
|
@ -0,0 +1,165 @@
|
|||
GNU LESSER GENERAL PUBLIC LICENSE
|
||||
Version 3, 29 June 2007
|
||||
|
||||
Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
|
||||
This version of the GNU Lesser General Public License incorporates
|
||||
the terms and conditions of version 3 of the GNU General Public
|
||||
License, supplemented by the additional permissions listed below.
|
||||
|
||||
0. Additional Definitions.
|
||||
|
||||
As used herein, "this License" refers to version 3 of the GNU Lesser
|
||||
General Public License, and the "GNU GPL" refers to version 3 of the GNU
|
||||
General Public License.
|
||||
|
||||
"The Library" refers to a covered work governed by this License,
|
||||
other than an Application or a Combined Work as defined below.
|
||||
|
||||
An "Application" is any work that makes use of an interface provided
|
||||
by the Library, but which is not otherwise based on the Library.
|
||||
Defining a subclass of a class defined by the Library is deemed a mode
|
||||
of using an interface provided by the Library.
|
||||
|
||||
A "Combined Work" is a work produced by combining or linking an
|
||||
Application with the Library. The particular version of the Library
|
||||
with which the Combined Work was made is also called the "Linked
|
||||
Version".
|
||||
|
||||
The "Minimal Corresponding Source" for a Combined Work means the
|
||||
Corresponding Source for the Combined Work, excluding any source code
|
||||
for portions of the Combined Work that, considered in isolation, are
|
||||
based on the Application, and not on the Linked Version.
|
||||
|
||||
The "Corresponding Application Code" for a Combined Work means the
|
||||
object code and/or source code for the Application, including any data
|
||||
and utility programs needed for reproducing the Combined Work from the
|
||||
Application, but excluding the System Libraries of the Combined Work.
|
||||
|
||||
1. Exception to Section 3 of the GNU GPL.
|
||||
|
||||
You may convey a covered work under sections 3 and 4 of this License
|
||||
without being bound by section 3 of the GNU GPL.
|
||||
|
||||
2. Conveying Modified Versions.
|
||||
|
||||
If you modify a copy of the Library, and, in your modifications, a
|
||||
facility refers to a function or data to be supplied by an Application
|
||||
that uses the facility (other than as an argument passed when the
|
||||
facility is invoked), then you may convey a copy of the modified
|
||||
version:
|
||||
|
||||
a) under this License, provided that you make a good faith effort to
|
||||
ensure that, in the event an Application does not supply the
|
||||
function or data, the facility still operates, and performs
|
||||
whatever part of its purpose remains meaningful, or
|
||||
|
||||
b) under the GNU GPL, with none of the additional permissions of
|
||||
this License applicable to that copy.
|
||||
|
||||
3. Object Code Incorporating Material from Library Header Files.
|
||||
|
||||
The object code form of an Application may incorporate material from
|
||||
a header file that is part of the Library. You may convey such object
|
||||
code under terms of your choice, provided that, if the incorporated
|
||||
material is not limited to numerical parameters, data structure
|
||||
layouts and accessors, or small macros, inline functions and templates
|
||||
(ten or fewer lines in length), you do both of the following:
|
||||
|
||||
a) Give prominent notice with each copy of the object code that the
|
||||
Library is used in it and that the Library and its use are
|
||||
covered by this License.
|
||||
|
||||
b) Accompany the object code with a copy of the GNU GPL and this license
|
||||
document.
|
||||
|
||||
4. Combined Works.
|
||||
|
||||
You may convey a Combined Work under terms of your choice that,
|
||||
taken together, effectively do not restrict modification of the
|
||||
portions of the Library contained in the Combined Work and reverse
|
||||
engineering for debugging such modifications, if you also do each of
|
||||
the following:
|
||||
|
||||
a) Give prominent notice with each copy of the Combined Work that
|
||||
the Library is used in it and that the Library and its use are
|
||||
covered by this License.
|
||||
|
||||
b) Accompany the Combined Work with a copy of the GNU GPL and this license
|
||||
document.
|
||||
|
||||
c) For a Combined Work that displays copyright notices during
|
||||
execution, include the copyright notice for the Library among
|
||||
these notices, as well as a reference directing the user to the
|
||||
copies of the GNU GPL and this license document.
|
||||
|
||||
d) Do one of the following:
|
||||
|
||||
0) Convey the Minimal Corresponding Source under the terms of this
|
||||
License, and the Corresponding Application Code in a form
|
||||
suitable for, and under terms that permit, the user to
|
||||
recombine or relink the Application with a modified version of
|
||||
the Linked Version to produce a modified Combined Work, in the
|
||||
manner specified by section 6 of the GNU GPL for conveying
|
||||
Corresponding Source.
|
||||
|
||||
1) Use a suitable shared library mechanism for linking with the
|
||||
Library. A suitable mechanism is one that (a) uses at run time
|
||||
a copy of the Library already present on the user's computer
|
||||
system, and (b) will operate properly with a modified version
|
||||
of the Library that is interface-compatible with the Linked
|
||||
Version.
|
||||
|
||||
e) Provide Installation Information, but only if you would otherwise
|
||||
be required to provide such information under section 6 of the
|
||||
GNU GPL, and only to the extent that such information is
|
||||
necessary to install and execute a modified version of the
|
||||
Combined Work produced by recombining or relinking the
|
||||
Application with a modified version of the Linked Version. (If
|
||||
you use option 4d0, the Installation Information must accompany
|
||||
the Minimal Corresponding Source and Corresponding Application
|
||||
Code. If you use option 4d1, you must provide the Installation
|
||||
Information in the manner specified by section 6 of the GNU GPL
|
||||
for conveying Corresponding Source.)
|
||||
|
||||
5. Combined Libraries.
|
||||
|
||||
You may place library facilities that are a work based on the
|
||||
Library side by side in a single library together with other library
|
||||
facilities that are not Applications and are not covered by this
|
||||
License, and convey such a combined library under terms of your
|
||||
choice, if you do both of the following:
|
||||
|
||||
a) Accompany the combined library with a copy of the same work based
|
||||
on the Library, uncombined with any other library facilities,
|
||||
conveyed under the terms of this License.
|
||||
|
||||
b) Give prominent notice with the combined library that part of it
|
||||
is a work based on the Library, and explaining where to find the
|
||||
accompanying uncombined form of the same work.
|
||||
|
||||
6. Revised Versions of the GNU Lesser General Public License.
|
||||
|
||||
The Free Software Foundation may publish revised and/or new versions
|
||||
of the GNU Lesser General Public License from time to time. Such new
|
||||
versions will be similar in spirit to the present version, but may
|
||||
differ in detail to address new problems or concerns.
|
||||
|
||||
Each version is given a distinguishing version number. If the
|
||||
Library as you received it specifies that a certain numbered version
|
||||
of the GNU Lesser General Public License "or any later version"
|
||||
applies to it, you have the option of following the terms and
|
||||
conditions either of that published version or of any later version
|
||||
published by the Free Software Foundation. If the Library as you
|
||||
received it does not specify a version number of the GNU Lesser
|
||||
General Public License, you may choose any version of the GNU Lesser
|
||||
General Public License ever published by the Free Software Foundation.
|
||||
|
||||
If the Library as you received it specifies that a proxy can decide
|
||||
whether future versions of the GNU Lesser General Public License shall
|
||||
apply, that proxy's public statement of acceptance of any version is
|
||||
permanent authorization for you to choose that version for the
|
||||
Library.
|
||||
0
zscript/armoritems.zsc
Normal file
0
zscript/armoritems.zsc
Normal file
0
zscript/asmd.zsc
Normal file
0
zscript/asmd.zsc
Normal file
0
zscript/automag.zsc
Normal file
0
zscript/automag.zsc
Normal file
0
zscript/betamag.zsc
Normal file
0
zscript/betamag.zsc
Normal file
0
zscript/biorifle.zsc
Normal file
0
zscript/biorifle.zsc
Normal file
0
zscript/dispersionpistol.zsc
Normal file
0
zscript/dispersionpistol.zsc
Normal file
0
zscript/eightball.zsc
Normal file
0
zscript/eightball.zsc
Normal file
0
zscript/flakcannon.zsc
Normal file
0
zscript/flakcannon.zsc
Normal file
0
zscript/gatling.zsc
Normal file
0
zscript/gatling.zsc
Normal file
0
zscript/healitems.zsc
Normal file
0
zscript/healitems.zsc
Normal file
0
zscript/impaler.zsc
Normal file
0
zscript/impaler.zsc
Normal file
0
zscript/minigun.zsc
Normal file
0
zscript/minigun.zsc
Normal file
151
zscript/miscitems.zsc
Normal file
151
zscript/miscitems.zsc
Normal file
|
|
@ -0,0 +1,151 @@
|
|||
// Backpack that only gives ammo for valid weapons
|
||||
Class UnrealBackpack : BackpackItem replaces Backpack
|
||||
{
|
||||
override Inventory CreateCopy( Actor other )
|
||||
{
|
||||
// Find every unique type of ammoitem. Give it to the player if
|
||||
// he doesn't have it already, and double its maximum capacity.
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
let type = (class<Ammo>)(AllActorClasses[i]);
|
||||
if ( !type || (type.GetParentClass() != 'Ammo') ) continue;
|
||||
// check that it's for a valid weapon
|
||||
bool isvalid = false;
|
||||
for ( int j=0; j<AllActorClasses.Size(); j++ )
|
||||
{
|
||||
let type2 = (class<Weapon>)(AllActorClasses[j]);
|
||||
if ( !type2 ) continue;
|
||||
let rep = GetReplacement(type2);
|
||||
if ( (rep != type2) && !(rep is "DehackedPickup") ) continue;
|
||||
readonly<Weapon> weap = GetDefaultByType(type2);
|
||||
if ( !other.player || !other.player.weapons.LocateWeapon(type2) || weap.bCheatNotWeapon ) continue;
|
||||
if ( (weap.AmmoType1 == type) || (weap.AmmoType2 == type) )
|
||||
{
|
||||
isvalid = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( !isvalid ) continue;
|
||||
let ammoitem = Ammo(other.FindInventory(type));
|
||||
int amount = GetDefaultByType(type).BackpackAmount;
|
||||
// extra ammo in baby mode and nightmare mode
|
||||
if ( !bIgnoreSkill ) amount = int(amount*G_SkillPropertyFloat(SKILLP_AmmoFactor));
|
||||
if ( amount < 0 ) amount = 0;
|
||||
if ( !ammoitem )
|
||||
{
|
||||
// The player did not have the ammoitem. Add it.
|
||||
ammoitem = Ammo(Spawn(type));
|
||||
ammoitem.Amount = bDepleted?0:amount;
|
||||
if ( ammoitem.BackpackMaxAmount > ammoitem.MaxAmount )
|
||||
ammoitem.MaxAmount = ammoitem.BackpackMaxAmount;
|
||||
if ( ammoitem.Amount > ammoitem.MaxAmount )
|
||||
ammoitem.Amount = ammoitem.MaxAmount;
|
||||
ammoitem.AttachToOwner(other);
|
||||
}
|
||||
else
|
||||
{
|
||||
// The player had the ammoitem. Give some more.
|
||||
if ( ammoitem.MaxAmount < ammoitem.BackpackMaxAmount )
|
||||
ammoitem.MaxAmount = ammoitem.BackpackMaxAmount;
|
||||
if ( !bDepleted && (ammoitem.Amount < ammoitem.MaxAmount) )
|
||||
{
|
||||
ammoitem.Amount += amount;
|
||||
if ( ammoitem.Amount > ammoitem.MaxAmount )
|
||||
ammoitem.Amount = ammoitem.MaxAmount;
|
||||
}
|
||||
}
|
||||
}
|
||||
return Inventory.CreateCopy(other);
|
||||
}
|
||||
override bool HandlePickup (Inventory item)
|
||||
{
|
||||
// Since you already have a backpack, that means you already have every
|
||||
// kind of ammo in your inventory, so we don't need to look at the
|
||||
// entire PClass list to discover what kinds of ammo exist, and we don't
|
||||
// have to alter the MaxAmount either.
|
||||
if ( item is 'BackpackItem' )
|
||||
{
|
||||
for ( let probe = Owner.Inv; probe; probe = probe.Inv )
|
||||
{
|
||||
if ( probe.GetParentClass() != 'Ammo' ) continue;
|
||||
if ( probe.Amount >= probe.MaxAmount && !sv_unlimited_pickup ) continue;
|
||||
int amount = Ammo(probe).Default.BackpackAmount;
|
||||
// extra ammo in baby mode and nightmare mode
|
||||
if ( !bIgnoreSkill )
|
||||
amount = int(amount*G_SkillPropertyFloat(SKILLP_AmmoFactor));
|
||||
probe.Amount += amount;
|
||||
if ( (probe.Amount > probe.MaxAmount) && !sv_unlimited_pickup )
|
||||
probe.Amount = probe.MaxAmount;
|
||||
}
|
||||
// The pickup always succeeds, even if you didn't get anything
|
||||
item.bPickupGood = true;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
Default
|
||||
{
|
||||
Tag "Backpack";
|
||||
Inventory.PickupMessage "You got a Backpack.";
|
||||
Inventory.RespawnTics 2100;
|
||||
}
|
||||
States
|
||||
{
|
||||
Spawn:
|
||||
BPAK A -1;
|
||||
Stop;
|
||||
}
|
||||
}
|
||||
|
||||
Class UTranslator : UnrealInventory
|
||||
{
|
||||
bool bCurrentlyActivated, bNewMessage, bNotNewMessage, bShowHint;
|
||||
string NewMessage, Hint;
|
||||
ui TextureID thud;
|
||||
ui Font tfnt;
|
||||
|
||||
ui void DrawTranslator( Vector2 scalev, double ClipX, double ClipY )
|
||||
{
|
||||
if ( thud.IsNull() ) thud = TexMan.CheckForTexture("TranHUD3",TexMan.Type_Any);
|
||||
if ( !tfnt ) tfnt = Font.FindFont('UTahoma10');
|
||||
double CurX, CurY;
|
||||
CurX = ClipX/2-128;
|
||||
CurY = ClipY/2-68;
|
||||
Screen.DrawTexture(thud,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
String ttxt;
|
||||
if ( bShowHint && (Hint.length() > 0) ) ttxt = String.Format("Hint: %s",Hint);
|
||||
else if ( NewMessage.length() > 0 ) ttxt = NewMessage;
|
||||
else ttxt = "I'd just like to interject for a moment. What you're referring to as Linux, is in fact, GNU/Linux, or as I've recently taken to calling it, GNU plus Linux. Linux is not an operating system unto itself, but rather another free component of a fully functioning GNU system made useful by the GNU corelibs, shell utilities and vital system components comprising a full OS as defined by POSIX.";
|
||||
BrokenLines lines = tfnt.BreakLines(ttxt,220);
|
||||
int th = tfnt.GetHeight();
|
||||
CurX += 20;
|
||||
CurY += 18;
|
||||
for ( int i=0; i<lines.Count() && i<(110/th); i++ )
|
||||
{
|
||||
Screen.DrawText(tfnt,Font.CR_GREEN,CurX,CurY,lines.StringAt(i),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurY += th-1;
|
||||
}
|
||||
}
|
||||
|
||||
override void Travelled()
|
||||
{
|
||||
Super.Travelled();
|
||||
NewMessage = Hint = "";
|
||||
}
|
||||
|
||||
override bool Use( bool pickup )
|
||||
{
|
||||
if ( pickup ) return false;
|
||||
bActive = bCurrentlyActivated = !bCurrentlyActivated;
|
||||
if ( !bActive ) bShowHint = bNewMessage = bNotNewmessage = false;
|
||||
return false;
|
||||
}
|
||||
|
||||
Default
|
||||
{
|
||||
Tag "Universal Translator";
|
||||
Inventory.PickupMessage "You got the Universal Translator.";
|
||||
Inventory.Icon "I_Tran";
|
||||
Inventory.MaxAmount 1;
|
||||
}
|
||||
}
|
||||
72
zscript/mk_coordutil.zsc
Normal file
72
zscript/mk_coordutil.zsc
Normal file
|
|
@ -0,0 +1,72 @@
|
|||
/*
|
||||
Coordinate Utility helper class.
|
||||
(C)2018 Marisa Kirisame, UnSX Team.
|
||||
Released under the GNU Lesser General Public License version 3 (or later).
|
||||
See https://www.gnu.org/licenses/lgpl-3.0.txt for its terms.
|
||||
*/
|
||||
|
||||
Class mkCoordUtil
|
||||
{
|
||||
// projects a world point onto screen
|
||||
// view matrix setup mostly pulled from gutawer's code
|
||||
static Vector3 WorldToScreen( Vector3 vect, Vector3 eye, double pitch, double yaw, double roll, double vfov )
|
||||
{
|
||||
double ar = Screen.getWidth()/double(Screen.getHeight());
|
||||
double fovr = (ar>=1.3)?1.333333:ar;
|
||||
double fov = 2*atan(tan(clamp(vfov,5,170)*0.5)/fovr);
|
||||
float pr = level.pixelstretch;
|
||||
double angx = cos(pitch);
|
||||
double angy = sin(pitch)*pr;
|
||||
double alen = sqrt(angx*angx+angy*angy);
|
||||
double apitch = asin(angy/alen);
|
||||
double ayaw = yaw-90;
|
||||
// rotations
|
||||
Matrix4 mRoll = Matrix4.rotate((0,0,1),roll);
|
||||
Matrix4 mPitch = Matrix4.rotate((1,0,0),apitch);
|
||||
Matrix4 mYaw = Matrix4.rotate((0,-1,0),ayaw);
|
||||
// scaling
|
||||
Matrix4 mScale = Matrix4.identity();
|
||||
mScale.set(1,1,pr);
|
||||
// YZ swap
|
||||
Matrix4 mYZ = Matrix4.create();
|
||||
mYZ.set(0,0,1);
|
||||
mYZ.set(2,1,1);
|
||||
mYZ.set(1,2,-1);
|
||||
mYZ.set(3,3,1);
|
||||
// translation
|
||||
Matrix4 mMove = Matrix4.identity();
|
||||
mMove.set(3,0,-eye.x);
|
||||
mMove.set(3,1,-eye.y);
|
||||
mMove.set(3,2,-eye.z);
|
||||
// perspective
|
||||
Matrix4 mPerspective = Matrix4.perspective(fov,ar,5,65535);
|
||||
// full matrix
|
||||
Matrix4 mView = mRoll.mul(mPitch);
|
||||
mView = mView.mul(mYaw);
|
||||
mView = mView.mul(mScale);
|
||||
mView = mView.mul(mYZ);
|
||||
mView = mView.mul(mMove);
|
||||
Matrix4 mWorldToScreen = mPerspective.mul(mView);
|
||||
return mWorldToScreen.vmat(vect);
|
||||
}
|
||||
|
||||
// converts a projected screen position to 2D canvas coords
|
||||
// thanks once again to gutawer for making this thing screenblocks-aware
|
||||
// [NEW] added second return value: true if the point has valid depth (i.e.: it's not behind view)
|
||||
// [TODO] handle forced aspect ratio (e.g.: 320x200 scaling)
|
||||
static Vector2, bool ToViewport( Vector3 screenpos, bool scrblocks = true )
|
||||
{
|
||||
if ( scrblocks )
|
||||
{
|
||||
int winx, winy, winw, winh;
|
||||
[winx,winy,winw,winh] = Screen.getViewWindow();
|
||||
int sh = Screen.getHeight();
|
||||
int ht = sh;
|
||||
int screenblocks = CVar.GetCVar("screenblocks",players[consoleplayer]).getInt();
|
||||
if ( screenblocks < 10 ) ht = (screenblocks*sh/10)&~7;
|
||||
int bt = sh-(ht+winy-((ht-winh)/2));
|
||||
return (winx,sh-bt-ht)+((screenpos.x+1)*winw,(-screenpos.y+1)*ht)*0.5, (screenpos.z<=1.0);
|
||||
}
|
||||
else return ((screenpos.x+1)*Screen.getWidth(),(-screenpos.y+1)*Screen.getHeight())*0.5, (screenpos.z<=1.0);
|
||||
}
|
||||
}
|
||||
123
zscript/mk_matrix.zsc
Normal file
123
zscript/mk_matrix.zsc
Normal file
|
|
@ -0,0 +1,123 @@
|
|||
/*
|
||||
Matrix Math helper class.
|
||||
(C)2018 Marisa Kirisame, UnSX Team.
|
||||
Released under the GNU Lesser General Public License version 3 (or later).
|
||||
See https://www.gnu.org/licenses/lgpl-3.0.txt for its terms.
|
||||
*/
|
||||
|
||||
Class Matrix4
|
||||
{
|
||||
private double m[16];
|
||||
|
||||
Matrix4 init()
|
||||
{
|
||||
int i;
|
||||
for ( i=0; i<16; i++ ) m[i] = 0;
|
||||
return self;
|
||||
}
|
||||
|
||||
static Matrix4 create()
|
||||
{
|
||||
return new("Matrix4").init();
|
||||
}
|
||||
|
||||
static Matrix4 identity()
|
||||
{
|
||||
Matrix4 o = Matrix4.create();
|
||||
for ( int i=0; i<4; i++ ) o.set(i,i,1);
|
||||
return o;
|
||||
}
|
||||
|
||||
double get( int c, int r )
|
||||
{
|
||||
return m[r*4+c];
|
||||
}
|
||||
|
||||
void set( int c, int r, double v )
|
||||
{
|
||||
m[r*4+c] = v;
|
||||
}
|
||||
|
||||
Matrix4 add( Matrix4 o )
|
||||
{
|
||||
Matrix4 r = Matrix4.create();
|
||||
int i, j;
|
||||
for ( i=0; i<4; i++ ) for ( j=0; j<4; j++ )
|
||||
r.set(j,i,get(j,i)+o.get(j,i));
|
||||
return r;
|
||||
}
|
||||
|
||||
Matrix4 scale( double s )
|
||||
{
|
||||
Matrix4 r = Matrix4.create();
|
||||
int i, j;
|
||||
for ( i=0; i<4; i++ ) for ( j=0; j<4; j++ )
|
||||
r.set(j,i,get(j,i)*s);
|
||||
return r;
|
||||
}
|
||||
|
||||
Matrix4 mul( Matrix4 o )
|
||||
{
|
||||
Matrix4 r = Matrix4.create();
|
||||
int i, j;
|
||||
for ( i=0; i<4; i++ ) for ( j=0; j<4; j++ )
|
||||
r.set(j,i,get(0,i)*o.get(j,0)+get(1,i)*o.get(j,1)+get(2,i)*o.get(j,2)+get(3,i)*o.get(j,3));
|
||||
return r;
|
||||
}
|
||||
|
||||
Vector3 vmat( Vector3 o )
|
||||
{
|
||||
double x, y, z, w;
|
||||
x = get(0,0)*o.x+get(1,0)*o.y+get(2,0)*o.z+get(3,0);
|
||||
y = get(0,1)*o.x+get(1,1)*o.y+get(2,1)*o.z+get(3,1);
|
||||
z = get(0,2)*o.x+get(1,2)*o.y+get(2,2)*o.z+get(3,2);
|
||||
w = get(0,3)*o.x+get(1,3)*o.y+get(2,3)*o.z+get(3,3);
|
||||
return (x,y,z)/w;
|
||||
}
|
||||
|
||||
static Matrix4 rotate( Vector3 axis, double theta )
|
||||
{
|
||||
Matrix4 r = Matrix4.identity();
|
||||
double s, c, oc;
|
||||
s = sin(theta);
|
||||
c = cos(theta);
|
||||
oc = 1.0-c;
|
||||
r.set(0,0,oc*axis.x*axis.x+c);
|
||||
r.set(1,0,oc*axis.x*axis.y-axis.z*s);
|
||||
r.set(2,0,oc*axis.x*axis.z+axis.y*s);
|
||||
r.set(0,1,oc*axis.y*axis.x+axis.z*s);
|
||||
r.set(1,1,oc*axis.y*axis.y+c);
|
||||
r.set(2,1,oc*axis.y*axis.z-axis.x*s);
|
||||
r.set(0,2,oc*axis.z*axis.x-axis.y*s);
|
||||
r.set(1,2,oc*axis.z*axis.y+axis.x*s);
|
||||
r.set(2,2,oc*axis.z*axis.z+c);
|
||||
return r;
|
||||
}
|
||||
|
||||
static Matrix4 perspective( double fov, double ar, double znear, double zfar )
|
||||
{
|
||||
Matrix4 r = Matrix4.create();
|
||||
double f = 1/tan(fov*0.5);
|
||||
r.set(0,0,f/ar);
|
||||
r.set(1,1,f);
|
||||
r.set(2,2,(zfar+znear)/(znear-zfar));
|
||||
r.set(3,2,(2*zfar*znear)/(znear-zfar));
|
||||
r.set(2,3,-1);
|
||||
return r;
|
||||
}
|
||||
|
||||
// UE-like axes from rotation
|
||||
static Vector3, Vector3, Vector3 getaxes( double pitch, double yaw, double roll )
|
||||
{
|
||||
Vector3 x = (1,0,0), y = (0,-1,0), z = (0,0,1); // y inverted for left-handed result
|
||||
Matrix4 mRoll = Matrix4.rotate((1,0,0),roll);
|
||||
Matrix4 mPitch = Matrix4.rotate((0,1,0),pitch);
|
||||
Matrix4 mYaw = Matrix4.rotate((0,0,1),yaw);
|
||||
Matrix4 mRot = mRoll.mul(mYaw);
|
||||
mRot = mRot.mul(mPitch);
|
||||
x = mRot.vmat(x);
|
||||
y = mRot.vmat(y);
|
||||
z = mRot.vmat(z);
|
||||
return x, y, z;
|
||||
}
|
||||
}
|
||||
0
zscript/napalm.zsc
Normal file
0
zscript/napalm.zsc
Normal file
0
zscript/peacemaker.zsc
Normal file
0
zscript/peacemaker.zsc
Normal file
0
zscript/powerups.zsc
Normal file
0
zscript/powerups.zsc
Normal file
0
zscript/quadshot.zsc
Normal file
0
zscript/quadshot.zsc
Normal file
0
zscript/razorjack.zsc
Normal file
0
zscript/razorjack.zsc
Normal file
0
zscript/rifle.zsc
Normal file
0
zscript/rifle.zsc
Normal file
192
zscript/spawners.zsc
Normal file
192
zscript/spawners.zsc
Normal file
|
|
@ -0,0 +1,192 @@
|
|||
// Tier 1 (chainsaw)
|
||||
Class Tier1Weapon : RandomSpawner2 replaces Chainsaw
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Stunner", 255;
|
||||
DropItem "UnrealTranslocator", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Tier 2 (pistol, clip)
|
||||
Class Tier2Weapon : RandomSpawner2 replaces Pistol
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Automag", 255;
|
||||
DropItem "OldAutomag", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class Tier2Ammo : RandomSpawner2 replaces Clip
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "UClip", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Tier 3 (shotgun, shells)
|
||||
Class Tier3Weapon : RandomSpawner2 replaces Shotgun
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Stinger", 255;
|
||||
DropItem "ASMD", 255;
|
||||
DropItem "Quadshot", 255;
|
||||
DropItem "Impaler", 255;
|
||||
}
|
||||
}
|
||||
Class Tier3Weapon2 : Tier3Weapon replaces SuperShotgun {}
|
||||
Class Tier3Ammo : RandomSpawner2 replaces Shell
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "StingerAmmo", 255;
|
||||
DropItem "ASMDAmmo", 255;
|
||||
DropItem "QShells", 255;
|
||||
}
|
||||
}
|
||||
Class Tier3Ammo2 : Tier3Ammo replaces ShellBox {}
|
||||
|
||||
// Tier 4 (chaingun, ammo box)
|
||||
Class Tier4Weapon : RandomSpawner2 replaces Chaingun
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Razorjack", 255;
|
||||
DropItem "UMinigun", 255;
|
||||
}
|
||||
}
|
||||
Class Tier4Ammo : RandomSpawner2 replaces ClipBox
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "RazorAmmo", 255;
|
||||
DropItem "UMiniAmmo", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Tier 5 (rocket launcher, rocket ammo)
|
||||
Class Tier5Weapon : RandomSpawner2 replaces RocketLauncher
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Eightball", 255;
|
||||
DropItem "UFlakCannon", 255;
|
||||
}
|
||||
}
|
||||
Class Tier5Ammo : RandomSpawner2 replaces RocketAmmo
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "RocketCan", 255;
|
||||
DropItem "UFlakAmmo", 255;
|
||||
}
|
||||
}
|
||||
Class Tier5Ammo2 : RandomSpawner2 replaces RocketBox
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "RocketCan", 255;
|
||||
DropItem "UFlakBox", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Tier 6 (plasma rifle, cell)
|
||||
Class Tier6Weapon : RandomSpawner2 replaces PlasmaRifle
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "GESBioRifle", 255;
|
||||
DropItem "Rifle", 255;
|
||||
DropItem "Flamethrower", 255;
|
||||
}
|
||||
}
|
||||
Class Tier6Ammo : RandomSpawner2 replaces Cell
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "BioSludge", 255;
|
||||
DropItem "URifleShell", 255;
|
||||
DropItem "NapalmCan", 255;
|
||||
}
|
||||
}
|
||||
Class Tier6Ammo2 : RandomSpawner2 replaces CellPack
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "BioSludge", 255;
|
||||
DropItem "URifleAmmo", 255;
|
||||
DropItem "NapalmCan", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Tier 7 (bfg9000)
|
||||
Class Tier7Weapon : RandomSpawner2 replaces BFG9000
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "GatlingGun", 255;
|
||||
}
|
||||
}
|
||||
|
||||
// Misc.
|
||||
Class BerserkSpawner : RandomSpawner2 replaces Berserk
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Amplifier", 255;
|
||||
DropItem "WeaponPowerup", 255;
|
||||
DropItem "UPowerup", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class LightSpawner : RandomSpawner2 replaces Infrared
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Flashlight", 255;
|
||||
DropItem "USearchlight", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class RadsuitSpawner : RandomSpawner2 replaces Radsuit
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "UJumpBoots", 255;
|
||||
DropItem "ToxinSuit", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class BackpackSpawner : RandomSpawner2 replaces Backpack
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "AsbestosSuit", 255;
|
||||
DropItem "VoiceBox", 255;
|
||||
DropItem "ForceField", 255;
|
||||
DropItem "UnrealBackpack", 255;
|
||||
DropItem "MinigunSentry", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class BlursphereSpawner : RandomSpawner2 replaces Blursphere
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "UInvisibility", 255;
|
||||
DropItem "Dampener", 255;
|
||||
DropItem "ChameleonHeart", 255;
|
||||
}
|
||||
}
|
||||
|
||||
Class StimpakSpawner : RandomSpawner2 replaces Stimpack
|
||||
{
|
||||
Default
|
||||
{
|
||||
DropItem "Bandages", 255;
|
||||
DropItem "NaliFruit", 255;
|
||||
}
|
||||
}
|
||||
185
zscript/stinger.zsc
Normal file
185
zscript/stinger.zsc
Normal file
|
|
@ -0,0 +1,185 @@
|
|||
Class StingerAmmo : Ammo
|
||||
{
|
||||
Default
|
||||
{
|
||||
Tag "Tarydium Shards";
|
||||
Inventory.Icon "I_Stingr";
|
||||
Inventory.PickupMessage "You picked up 40 Tarydium Shards.";
|
||||
Inventory.Amount 40;
|
||||
Inventory.MaxAmount 200;
|
||||
Ammo.BackpackAmount 80;
|
||||
Ammo.BackpackMaxAmount 400;
|
||||
Ammo.DropAmount 10;
|
||||
}
|
||||
States
|
||||
{
|
||||
Spawn:
|
||||
SAMO A -1;
|
||||
Stop;
|
||||
}
|
||||
}
|
||||
|
||||
Class StingerProjectile : Actor
|
||||
{
|
||||
Default
|
||||
{
|
||||
Obituary "%o was perforated by %k's Stinger.";
|
||||
DamageType 'shot';
|
||||
DamageFunction Random[Stinger](15,25);
|
||||
Speed 40;
|
||||
Radius 2;
|
||||
Height 2;
|
||||
PROJECTILE;
|
||||
+SKYEXPLODE;
|
||||
+BLOODSPLATTER;
|
||||
}
|
||||
States
|
||||
{
|
||||
Spawn:
|
||||
TPRJ A -1 Bright;
|
||||
Stop;
|
||||
Death:
|
||||
TNT1 A 0
|
||||
{
|
||||
if ( !Random[Stinger](0,2) ) A_PlaySound("stinger/hit2",CHAN_BODY,0.5);
|
||||
else A_PlaySound("stinger/hit",CHAN_BODY,0.6);
|
||||
}
|
||||
TPRJ BCDEFG 2 Bright;
|
||||
Stop;
|
||||
XDeath:
|
||||
TNT1 A 1 A_PlaySound("stinger/flesh");
|
||||
Stop;
|
||||
}
|
||||
}
|
||||
|
||||
Class Stinger : UnrealWeapon
|
||||
{
|
||||
Default
|
||||
{
|
||||
Tag "Stinger";
|
||||
Inventory.PickupMessage "You picked up the Stinger.";
|
||||
Weapon.UpSound "stinger/select";
|
||||
Weapon.SlotNumber 3;
|
||||
Weapon.SelectionOrder 7;
|
||||
Weapon.AmmoType "StingerAmmo";
|
||||
Weapon.AmmoUse 1;
|
||||
Weapon.AmmoType2 "StingerAmmo";
|
||||
Weapon.AmmoUse2 1;
|
||||
Weapon.AmmoGive 40;
|
||||
}
|
||||
action void A_StingerFire()
|
||||
{
|
||||
Weapon weap = Weapon(invoker);
|
||||
if ( !weap ) return;
|
||||
if ( weap.Ammo1.Amount <= 0 ) return;
|
||||
if ( !weap.DepleteAmmo(weap.bAltFire,true,1) ) return;
|
||||
UnrealMainHandler.DoFlash(self,Color(16,0,64,255),1);
|
||||
A_AlertMonsters();
|
||||
A_QuakeEx(1,1,1,4,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.1);
|
||||
Vector3 x, y, z;
|
||||
[x, y, z] = Matrix4.GetAxes(pitch,angle,roll);
|
||||
Vector3 origin = (pos.x,pos.y,player.viewz)+10.0*x+8.0*y-9.0*z;
|
||||
Actor p = Spawn("StingerProjectile",origin);
|
||||
p.angle = angle;
|
||||
p.pitch = BulletSlope();
|
||||
p.vel = (cos(p.angle)*cos(p.pitch),sin(p.angle)*cos(p.pitch),-sin(p.pitch))*p.speed;
|
||||
p.target = self;
|
||||
}
|
||||
action void A_StingerAltFire()
|
||||
{
|
||||
Weapon weap = Weapon(invoker);
|
||||
if ( !weap ) return;
|
||||
if ( weap.Ammo1.Amount <= 0 ) return;
|
||||
UnrealMainHandler.DoFlash(self,Color(16,0,64,255),1);
|
||||
A_AlertMonsters();
|
||||
A_QuakeEx(1,1,1,4,0,1,"",QF_RELATIVE|QF_SCALEDOWN,rollIntensity:0.1);
|
||||
Vector3 x, y, z;
|
||||
[x, y, z] = Matrix4.GetAxes(pitch,angle,roll);
|
||||
Vector3 origin = (pos.x,pos.y,player.viewz)+10.0*x+8.0*y-9.0*z;
|
||||
[x, y, z] = Matrix4.GetAxes(BulletSlope(),angle,roll);
|
||||
A_PlaySound("stinger/altfire",CHAN_WEAPON);
|
||||
Actor p;
|
||||
double a, s;
|
||||
Vector3 dir;
|
||||
for ( int i=0; i<4; i++ )
|
||||
{
|
||||
if ( weap.Ammo1.Amount <= 0 ) return;
|
||||
if ( !weap.DepleteAmmo(weap.bAltFire,true,1) ) return;
|
||||
a = FRandom[Stinger](0,360);
|
||||
s = FRandom[Stinger](0,0.08);
|
||||
dir = (x+y*cos(a)*s+z*sin(a)*s).unit();
|
||||
p = Spawn("StingerProjectile",origin);
|
||||
p.angle = atan2(dir.y,dir.x);
|
||||
p.pitch = asin(-dir.z);
|
||||
p.vel = (cos(p.angle)*cos(p.pitch),sin(p.angle)*cos(p.pitch),-sin(p.pitch))*p.speed;
|
||||
p.target = self;
|
||||
}
|
||||
}
|
||||
States
|
||||
{
|
||||
Spawn:
|
||||
STNP A -1;
|
||||
Stop;
|
||||
STNP B -1;
|
||||
Stop;
|
||||
Select:
|
||||
STNS A 1 A_Raise(int.max);
|
||||
Wait;
|
||||
Ready:
|
||||
STNS ABCDEFGHIJKLMNOPQRSTU 1 A_WeaponReady(WRF_NOFIRE);
|
||||
Idle:
|
||||
STNI A 1
|
||||
{
|
||||
A_CheckReload();
|
||||
A_WeaponReady();
|
||||
}
|
||||
Wait;
|
||||
Fire:
|
||||
STNF A 2
|
||||
{
|
||||
A_PlaySound("stinger/fire",CHAN_WEAPON);
|
||||
A_StingerFire();
|
||||
A_Overlay(PSP_FLASH,"MFlash");
|
||||
A_OverlayFlags(PSP_FLASH,PSPF_RenderStyle,true);
|
||||
A_OverlayRenderstyle(PSP_FLASH,STYLE_Add);
|
||||
}
|
||||
STNF BC 2;
|
||||
STNI A 3;
|
||||
STNI A 0 A_Refire(1);
|
||||
Goto Idle;
|
||||
STNI A 0 A_PlaySound("stinger/hold",CHAN_WEAPON,1.0,true);
|
||||
Hold:
|
||||
STNH A 1
|
||||
{
|
||||
A_StingerFire();
|
||||
A_Overlay(PSP_FLASH,"MFlashHold");
|
||||
A_OverlayFlags(PSP_FLASH,PSPF_RenderStyle,true);
|
||||
A_OverlayRenderstyle(PSP_FLASH,STYLE_Add);
|
||||
}
|
||||
STNH BCDEFG 1;
|
||||
STNH A 0 A_Refire();
|
||||
STNH A 2 A_PlaySound("stinger/release",CHAN_WEAPON);
|
||||
Goto Idle;
|
||||
AltFire:
|
||||
STNF A 2
|
||||
{
|
||||
A_StingerAltFire();
|
||||
A_Overlay(PSP_FLASH,"MFlash");
|
||||
A_OverlayFlags(PSP_FLASH,PSPF_RenderStyle,true);
|
||||
A_OverlayRenderstyle(PSP_FLASH,STYLE_Add);
|
||||
}
|
||||
STNF BC 2;
|
||||
STNI A 35; // yes, 1 second cooldown
|
||||
Goto Idle;
|
||||
Deselect:
|
||||
STND ABCDEFGHIJK 1;
|
||||
STND K 1 A_Lower(int.max);
|
||||
Wait;
|
||||
MFlash:
|
||||
STFF ABC 2 Bright;
|
||||
Stop;
|
||||
MFlashHold:
|
||||
STFH ABCDEFG 1 Bright;
|
||||
Stop;
|
||||
}
|
||||
}
|
||||
0
zscript/stunner.zsc
Normal file
0
zscript/stunner.zsc
Normal file
0
zscript/translocator.zsc
Normal file
0
zscript/translocator.zsc
Normal file
388
zscript/unrealcommon.zsc
Normal file
388
zscript/unrealcommon.zsc
Normal file
|
|
@ -0,0 +1,388 @@
|
|||
Class UnrealPlayer : DoomPlayer
|
||||
{
|
||||
bool lastground;
|
||||
double lastvelz, prevvelz;
|
||||
transient CVar footsteps;
|
||||
|
||||
Default
|
||||
{
|
||||
Player.StartItem "Automag";
|
||||
Player.StartItem "DispersionPistol";
|
||||
Player.StartItem "UMiniAmmo", 30;
|
||||
Player.DamageScreenColor "FF 00 00", 1.0;
|
||||
Player.ViewHeight 46;
|
||||
}
|
||||
|
||||
// Have to modify the give cheat to handle UT armor
|
||||
override void CheatGive( String name, int amount )
|
||||
{
|
||||
if ( PlayerNumber() != consoleplayer )
|
||||
A_Log(String.Format("%s is a cheater: give %s\n",player.GetUserName(),name));
|
||||
if ( !player.mo || (player.health <= 0) ) return;
|
||||
int giveall = ALL_NO;
|
||||
if ( name ~== "all" ) giveall = ALL_YES;
|
||||
else if (name ~== "everything") giveall = ALL_YESYES;
|
||||
if ( name ~== "health" )
|
||||
{
|
||||
if ( amount > 0 )
|
||||
{
|
||||
health += amount;
|
||||
player.health = health;
|
||||
}
|
||||
else player.health = health = GetMaxHealth(true);
|
||||
}
|
||||
if ( giveall || (name ~== "backpack") )
|
||||
{
|
||||
// Select the correct type of backpack based on the game
|
||||
let type = (class<Inventory>)(gameinfo.backpacktype);
|
||||
if ( type ) GiveInventory(type,1,true);
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "ammo") )
|
||||
{
|
||||
// Find every unique type of ammo. Give it to the player if
|
||||
// he doesn't have it already, and set each to its maximum.
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
let type = (class<Ammo>)(AllActorClasses[i]);
|
||||
if ( !type || (type.GetParentClass() != "Ammo") )
|
||||
continue;
|
||||
// Only give if it's for a valid weapon, unless using "give everything"
|
||||
bool isvalid = false;
|
||||
for ( int j=0; j<AllActorClasses.Size(); j++ )
|
||||
{
|
||||
let type2 = (class<Weapon>)(AllActorClasses[j]);
|
||||
if ( !type2 ) continue;
|
||||
let rep = GetReplacement(type2);
|
||||
if ( (rep != type2) && !(rep is "DehackedPickup") ) continue;
|
||||
readonly<Weapon> weap = GetDefaultByType(type2);
|
||||
if ( !player.weapons.LocateWeapon(type2) || (weap.bCheatNotWeapon && (giveall != ALL_YESYES)) ) continue;
|
||||
if ( (weap.AmmoType1 == type) || (weap.AmmoType2 == type) )
|
||||
{
|
||||
isvalid = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( !isvalid ) continue;
|
||||
let ammoitem = FindInventory(type);
|
||||
if ( !ammoitem )
|
||||
{
|
||||
ammoitem = Inventory(Spawn(type));
|
||||
ammoitem.AttachToOwner(self);
|
||||
ammoitem.Amount = ammoitem.MaxAmount;
|
||||
}
|
||||
else if ( ammoitem.Amount < ammoitem.MaxAmount )
|
||||
ammoitem.Amount = ammoitem.MaxAmount;
|
||||
}
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "armor") )
|
||||
{
|
||||
// Doomreal gives the player all subclasses of UnrealArmor
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
if ( !(AllActorClasses[i] is "UnrealArmor") ) continue;
|
||||
let item = Inventory(Spawn(AllActorClasses[i]));
|
||||
if ( !item.CallTryPickup(self) ) item.Destroy();
|
||||
}
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "keys") )
|
||||
{
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
if ( !(AllActorClasses[i] is "Key") ) continue;
|
||||
let keyitem = GetDefaultByType(AllActorClasses[i]);
|
||||
if ( keyitem.special1 )
|
||||
{
|
||||
let item = Inventory(Spawn(AllActorClasses[i]));
|
||||
if ( !item.CallTryPickup(self) ) item.Destroy();
|
||||
}
|
||||
}
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "weapons") )
|
||||
{
|
||||
let savedpending = player.PendingWeapon;
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
let type = (class<Weapon>)(AllActorClasses[i]);
|
||||
if ( !type || (type == "Weapon") ) continue;
|
||||
// Don't give replaced weapons unless the replacement was done by Dehacked.
|
||||
let rep = GetReplacement(type);
|
||||
if ( (rep == type) || (rep is "DehackedPickup") )
|
||||
{
|
||||
// Give the weapon only if it is set in a weapon slot.
|
||||
if ( !player.weapons.LocateWeapon(type) ) continue;
|
||||
readonly<Weapon> def = GetDefaultByType(type);
|
||||
if ( (giveall == ALL_YESYES) || !def.bCheatNotWeapon )
|
||||
GiveInventory(type,1,true);
|
||||
}
|
||||
}
|
||||
player.PendingWeapon = savedpending;
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "artifacts") )
|
||||
{
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
let type = (class<Inventory>)(AllActorClasses[i]);
|
||||
if ( !type ) continue;
|
||||
let def = GetDefaultByType (type);
|
||||
if ( def.Icon.isValid() && (def.MaxAmount > 1) &&
|
||||
!(type is "PuzzleItem") && !(type is "Powerup") && !(type is "Ammo") && !(type is "Armor"))
|
||||
{
|
||||
// Do not give replaced items unless using "give everything"
|
||||
if ( (giveall == ALL_YESYES) || (GetReplacement(type) == type) )
|
||||
GiveInventory(type,(amount<=0)?def.MaxAmount:amount,true);
|
||||
}
|
||||
}
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall || (name ~== "puzzlepieces") )
|
||||
{
|
||||
for ( int i=0; i<AllActorClasses.Size(); i++ )
|
||||
{
|
||||
let type = (class<PuzzleItem>)(AllActorClasses[i]);
|
||||
if ( !type ) continue;
|
||||
let def = GetDefaultByType(type);
|
||||
if ( !def.Icon.isValid() ) continue;
|
||||
// Do not give replaced items unless using "give everything"
|
||||
if ( (giveall == ALL_YESYES) || (GetReplacement(type) == type) )
|
||||
GiveInventory(type,(amount<=0)?def.MaxAmount:amount,true);
|
||||
}
|
||||
if ( !giveall ) return;
|
||||
}
|
||||
if ( giveall ) return;
|
||||
let type = name;
|
||||
if ( !type )
|
||||
{
|
||||
if ( PlayerNumber() == consoleplayer )
|
||||
A_Log(String.Format("Unknown item \"%s\"\n",name));
|
||||
}
|
||||
else GiveInventory(type,amount,true);
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !player ) return;
|
||||
if ( !footsteps ) footsteps = CVar.GetCVar('stinger_footsteps',players[consoleplayer]);
|
||||
if ( !footsteps.GetBool() ) return;
|
||||
double ang = level.time/(20*TICRATE/35.)*360.;
|
||||
if ( (abs(sin(ang)) >= 1.0) && player.onground && (player.cmd.forwardmove || player.cmd.sidemove) )
|
||||
{
|
||||
if ( (waterlevel > 0) || GetFloorTerrain().IsLiquid ) A_PlaySound("u1/playerfootstepwet",CHAN_5,abs(vel.xy.length())*0.03);
|
||||
else A_PlaySound("u1/playerfootstep",CHAN_5,abs(vel.xy.length())*0.03);
|
||||
}
|
||||
if ( player.onground && !bNoGravity && !lastground && (lastvelz < -4) && (lastvelz >= -8) )
|
||||
{
|
||||
if ( (waterlevel > 0) || GetFloorTerrain().IsLiquid ) A_PlaySound("u1/wetsplash",CHAN_AUTO,abs(lastvelz*0.0625));
|
||||
else A_PlaySound("*land",CHAN_AUTO,abs(lastvelz*0.03));
|
||||
}
|
||||
lastground = player.onground;
|
||||
lastvelz = prevvelz;
|
||||
prevvelz = vel.z;
|
||||
}
|
||||
}
|
||||
|
||||
// Random Spawner that passes through dropped status to items
|
||||
Class RandomSpawner2 : RandomSpawner
|
||||
{
|
||||
override void PostSpawn( Actor spawned )
|
||||
{
|
||||
if ( !bDROPPED ) return;
|
||||
if ( spawned is 'Inventory' ) Inventory(spawned).bTOSSED = bDROPPED;
|
||||
if ( spawned is 'UnrealWeapon' )
|
||||
{
|
||||
spawned.SetState(spawned.ResolveState("Spawn")+1);
|
||||
Inventory(spawned).bALWAYSPICKUP = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Class UnrealWeapon : Weapon
|
||||
{
|
||||
// Drawstuffs under HUD
|
||||
virtual ui void PreRender( double lbottom ) {}
|
||||
// Drawstuffs over HUD
|
||||
virtual ui void PostRender( double lbottom ) {}
|
||||
|
||||
override Inventory CreateTossable( int amt )
|
||||
{
|
||||
if ( Ammo1 && (Ammo1.Amount <= 0) ) return null;
|
||||
Inventory d = Super.CreateTossable(amt);
|
||||
if ( d && (d.GetClass() == GetClass()) )
|
||||
{
|
||||
d.SetState(d.ResolveState("Spawn")+1);
|
||||
d.bALWAYSPICKUP = true;
|
||||
}
|
||||
return d;
|
||||
}
|
||||
|
||||
override bool SpecialDropAction( Actor dropper )
|
||||
{
|
||||
SetState(ResolveState("Spawn")+1);
|
||||
bALWAYSPICKUP = true;
|
||||
return false;
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
if ( !Owner || !Owner.player || (Owner.player.ReadyWeapon != self) ) return;
|
||||
Owner.player.WeaponState |= WF_WEAPONBOBBING; // U1 weapons always bob
|
||||
}
|
||||
|
||||
override void OwnerDied()
|
||||
{
|
||||
Super.OwnerDied();
|
||||
A_ClearRefire();
|
||||
}
|
||||
|
||||
Default
|
||||
{
|
||||
Weapon.BobStyle "Smooth";
|
||||
Weapon.BobSpeed 1.5;
|
||||
Weapon.BobRangeX 0.2;
|
||||
Weapon.BobRangeY 0.4;
|
||||
+WEAPON.NOALERT;
|
||||
}
|
||||
}
|
||||
|
||||
Class UnrealInventory : Inventory
|
||||
{
|
||||
bool bActive; // is currently activated
|
||||
int Charge; // for timed items
|
||||
int DefaultCharge;
|
||||
|
||||
Property Charge : DefaultCharge;
|
||||
|
||||
// Drawstuffs under HUD
|
||||
virtual ui void PreRender( double lbottom ) {}
|
||||
// Drawstuffs over HUD
|
||||
virtual ui void PostRender( double lbottom ) {}
|
||||
|
||||
Default
|
||||
{
|
||||
+INVENTORY.INVBAR;
|
||||
UnrealInventory.Charge 0;
|
||||
}
|
||||
}
|
||||
|
||||
Class UnrealArmor : Armor
|
||||
{
|
||||
int absorb;
|
||||
|
||||
Property ArmorAbsorption : absorb;
|
||||
|
||||
Default
|
||||
{
|
||||
+INVENTORY.AUTOACTIVATE;
|
||||
+INVENTORY.UNTOSSABLE;
|
||||
Inventory.MaxAmount 0;
|
||||
}
|
||||
override void AbsorbDamage( int damage, Name damageType, out int newdamage )
|
||||
{
|
||||
int saved;
|
||||
if ( (amount > 0) && !DamageTypeDefinition.IgnoreArmor(damageType) )
|
||||
{
|
||||
saved = damage*absorb/100.;
|
||||
if ( amount <= saved ) saved = amount;
|
||||
newdamage -= saved;
|
||||
amount -= saved;
|
||||
damage = newdamage;
|
||||
}
|
||||
if ( damage > 0 ) newdamage = ApplyDamageFactors(GetClass(),damageType,damage,damage);
|
||||
if ( amount <= 0 ) Destroy();
|
||||
}
|
||||
}
|
||||
|
||||
Class GenericFlash : HUDMessageBase
|
||||
{
|
||||
Color col;
|
||||
int duration;
|
||||
double alpha;
|
||||
Actor cam;
|
||||
GenericFlash Setup( Actor camera, Color c, int d )
|
||||
{
|
||||
alpha = 1.0;
|
||||
col = c;
|
||||
duration = d;
|
||||
cam = camera;
|
||||
return self;
|
||||
}
|
||||
override bool Tick()
|
||||
{
|
||||
alpha -= 1./duration;
|
||||
return (alpha<=0);
|
||||
}
|
||||
override void Draw( int bottom, int visibility )
|
||||
{
|
||||
if ( automapactive || (visibility != BaseStatusBar.HUDMSGLayer_UnderHUD) ) return;
|
||||
if ( cam && (players[consoleplayer].camera != cam) ) return;
|
||||
Screen.Dim(col,(col.a/255.)*alpha,0,0,Screen.GetWidth(),Screen.GetHeight());
|
||||
}
|
||||
}
|
||||
|
||||
Class QueuedFlash
|
||||
{
|
||||
Color c;
|
||||
int duration;
|
||||
int tic;
|
||||
Actor cam;
|
||||
}
|
||||
|
||||
Class UnrealMainHandler : StaticEventHandler
|
||||
{
|
||||
Array<QueuedFlash> flashes;
|
||||
|
||||
override void WorldLoaded( WorldEvent e )
|
||||
{
|
||||
if ( gamestate != GS_LEVEL || e.IsSaveGame ) return;
|
||||
// prettify Kinsie's test map for a more Unreal feel
|
||||
if ( level.levelname ~== "Modder Test Map" )
|
||||
{
|
||||
TexMan.ReplaceTextures("-noflat-","-kinsie-",0);
|
||||
TextureID skytx = TexMan.CheckForTexture("BlueSky",TexMan.Type_Any);
|
||||
level.ChangeSky(skytx,skytx);
|
||||
// TODO handplace some dynamic lights and add Unreal/UT ambient sounds
|
||||
}
|
||||
}
|
||||
|
||||
override void WorldThingSpawned( WorldEvent e )
|
||||
{
|
||||
if ( e.Thing.bBOSS ) e.Thing.bNOTELEFRAG = true;
|
||||
}
|
||||
|
||||
override void WorldTick()
|
||||
{
|
||||
for ( int i=0; i<flashes.size(); i++ )
|
||||
{
|
||||
if ( flashes[i].tic >= gametic ) continue;
|
||||
flashes.Delete(i);
|
||||
i--;
|
||||
}
|
||||
}
|
||||
|
||||
override void PostUiTick()
|
||||
{
|
||||
for ( int i=0; i<flashes.size(); i++ )
|
||||
{
|
||||
if ( flashes[i].tic < gametic ) continue;
|
||||
GenericFlash gf = new("GenericFlash").Setup(flashes[i].cam,flashes[i].c,flashes[i].duration);
|
||||
StatusBar.AttachMessage(gf,0,BaseStatusBar.HUDMSGLayer_UnderHUD);
|
||||
}
|
||||
}
|
||||
|
||||
static void DoFlash( Actor camera, Color c, int duration )
|
||||
{
|
||||
QueuedFlash qf = new("QueuedFlash");
|
||||
qf.duration = duration;
|
||||
qf.c = c;
|
||||
qf.tic = gametic;
|
||||
qf.cam = camera;
|
||||
let hnd = UnrealMainHandler(StaticEventHandler.Find("UnrealMainHandler"));
|
||||
hnd.flashes.push(qf);
|
||||
}
|
||||
}
|
||||
455
zscript/unrealhud.zsc
Normal file
455
zscript/unrealhud.zsc
Normal file
|
|
@ -0,0 +1,455 @@
|
|||
// An almost 1:1 recreation of the Unreal 1 HUD
|
||||
Class ViewTracer : LineTracer
|
||||
{
|
||||
Actor ignore;
|
||||
|
||||
override ETraceStatus TraceCallback()
|
||||
{
|
||||
if ( Results.HitType == TRACE_HitActor )
|
||||
{
|
||||
if ( (Results.HitActor == ignore) || !Results.HitActor.player || !Results.HitActor.bSHOOTABLE || Results.HitActor.bINVISIBLE ) return TRACE_Skip;
|
||||
return TRACE_Stop;
|
||||
}
|
||||
else if ( (Results.HitType == TRACE_HitWall) && (Results.Tier == TIER_Middle) )
|
||||
{
|
||||
if ( !Results.HitLine.sidedef[1] ) return TRACE_Stop;
|
||||
return TRACE_Skip;
|
||||
}
|
||||
return TRACE_Stop;
|
||||
}
|
||||
}
|
||||
|
||||
Class UnrealHUD : BaseStatusBar
|
||||
{
|
||||
double FracTic;
|
||||
|
||||
// Unreal HUD variables
|
||||
Color RedColor, GreenColor, BlackColor;
|
||||
int HudMode;
|
||||
|
||||
// Helpers
|
||||
Vector2 scalev;
|
||||
double CurX, CurY, ClipX, ClipY;
|
||||
Color DrawColor;
|
||||
ViewTracer vtracer;
|
||||
Actor lastseen;
|
||||
int lastseentic, Count;
|
||||
|
||||
// Fonts
|
||||
Font LargeFont, LargeRedFont, MedFont, WhiteFont, TinyFont,
|
||||
TinyWhiteFont, TinyRedFont;
|
||||
|
||||
// Common Textures
|
||||
TextureID HalfHud, HudLine, HudAmmo, IconHeal, IconSkul, IconSel,
|
||||
IconBase;
|
||||
|
||||
// Translations
|
||||
int RedIcon;
|
||||
|
||||
override void Init()
|
||||
{
|
||||
Super.Init();
|
||||
SetSize(0,320,200);
|
||||
// Initialize
|
||||
Count = 0;
|
||||
vtracer = new("ViewTracer");
|
||||
RedColor = "FF 00 00";
|
||||
GreenColor = "00 FF 00";
|
||||
BlackColor = "00 00 00";
|
||||
DrawColor = "FF FF FF";
|
||||
LargeFont = Font.FindFont('ULargeFont');
|
||||
LargeRedFont = Font.FindFont('ULargeRedFont');
|
||||
MedFont = Font.FindFont('UMedFont');
|
||||
WhiteFont = Font.FindFont('UWhiteFont');
|
||||
TinyFont = Font.FindFont('UTinyFont');
|
||||
TinyWhiteFont = Font.FindFont('UTinyWhiteFont');
|
||||
TinyRedFont = Font.FindFont('UTinyRedFont');
|
||||
HalfHud = TexMan.CheckForTexture("HalfHud",TexMan.Type_Any);
|
||||
HudLine = TexMan.CheckForTexture("HudLine",TexMan.Type_Any);
|
||||
HudAmmo = TexMan.CheckForTexture("HudAmmo",TexMan.Type_Any);
|
||||
IconHeal = TexMan.CheckForTexture("IconHeal",TexMan.Type_Any);
|
||||
IconSkul = TexMan.CheckForTexture("IconSkul",TexMan.Type_Any);
|
||||
IconSel = TexMan.CheckForTexture("IconSel",TexMan.Type_Any);
|
||||
IconBase = TexMan.CheckForTexture("IconBase",TexMan.Type_Any);
|
||||
RedIcon = Translation.GetID('RedIcon');
|
||||
}
|
||||
|
||||
override void Draw( int state, double TicFrac )
|
||||
{
|
||||
Super.Draw(state,TicFrac);
|
||||
HudMode = CVar.GetCVar('stinger_hudmode',players[consoleplayer]).GetInt();
|
||||
scalev.x = scalev.y = Max(1,CVar.GetCVar('stinger_hudscale',players[consoleplayer]).GetInt());
|
||||
ClipX = Screen.GetWidth()/scalev.x;
|
||||
ClipY = Screen.GetHeight()/scalev.y;
|
||||
CurX = 0;
|
||||
CurY = 0;
|
||||
double lbottom = Screen.GetHeight()-32*scalev.y; // TODO properly calculate
|
||||
for ( Inventory i=CPlayer.mo.inv; i; i=i.inv )
|
||||
if ( i is 'UnrealInventory' )
|
||||
UnrealInventory(i).PreRender(lbottom);
|
||||
if ( CPlayer.ReadyWeapon is 'UnrealWeapon' )
|
||||
UnrealWeapon(CPlayer.ReadyWeapon).PreRender(lbottom);
|
||||
if ( (state == HUD_StatusBar) || (state == HUD_Fullscreen) )
|
||||
{
|
||||
BeginHUD();
|
||||
FracTic = TicFrac;
|
||||
DrawUnrealHUD();
|
||||
}
|
||||
for ( Inventory i=CPlayer.mo.inv; i; i=i.inv )
|
||||
if ( i is 'UnrealInventory' )
|
||||
UnrealInventory(i).PostRender(lbottom);
|
||||
if ( CPlayer.ReadyWeapon is 'UnrealWeapon' )
|
||||
UnrealWeapon(CPlayer.ReadyWeapon).PostRender(lbottom);
|
||||
}
|
||||
|
||||
private void DrawNumberOf( int n, double x, double y )
|
||||
{
|
||||
if ( n <= 0 ) return;
|
||||
CurX = X-4;
|
||||
CurY = Y+20;
|
||||
n++;
|
||||
string itxt = String.Format("%d",n);
|
||||
CurX -= TinyRedFont.StringWidth(itxt);
|
||||
Screen.DrawText(TinyRedFont,Font.CR_UNTRANSLATED,CurX,CurY,itxt,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
|
||||
private void DrawIconValue( int n )
|
||||
{
|
||||
if ( !HudMode || (HudMode == 3) ) return;
|
||||
double TempX = CurX, TempY = CurY;
|
||||
string itxt = String.Format("%d",n);
|
||||
CurX -= 2;
|
||||
CurY -= 6;
|
||||
CurX -= TinyFont.StringWidth(itxt);
|
||||
Screen.DrawText(TinyFont,Font.CR_UNTRANSLATED,CurX,CurY,itxt,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurX = TempX;
|
||||
CurY = TempY;
|
||||
}
|
||||
|
||||
private void DrawHudIcon( double x, double y, Inventory i, bool bRed )
|
||||
{
|
||||
if ( i.Icon.IsNull() ) return;
|
||||
double width = CurX;
|
||||
CurX = x;
|
||||
CurY = y;
|
||||
if ( bRed ) Screen.DrawTexture(i.Icon,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_TranslationIndex,RedIcon);
|
||||
else Screen.DrawTexture(i.Icon,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
|
||||
private void DrawFragCount( double x, double y )
|
||||
{
|
||||
CurX = X;
|
||||
CurY = Y;
|
||||
Screen.DrawTexture(IconSkul,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurX += 30;
|
||||
CurY += 23;
|
||||
string score = String.Format("%d",(deathmatch||teamplay)?CPlayer.fragcount:CPlayer.killcount);
|
||||
CurX -= TinyWhiteFont.StringWidth(score);
|
||||
Screen.DrawText(TinyWhiteFont,Font.CR_UNTRANSLATED,CurX,CurY,score,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
|
||||
private void DrawInventory( double x, double y, bool bDrawOne )
|
||||
{
|
||||
bool bGotNext, bGotPrev, bGotSelected, bRed, bFlashTranslator;
|
||||
Inventory Inv, Prev, Next, SelectedItem;
|
||||
UTranslator translator;
|
||||
double HalfHUDX, HalfHUDY;
|
||||
double AmmoBarSize;
|
||||
if ( HudMode < 4 ) // then draw HalfHUD
|
||||
{
|
||||
HalfHUDX = ClipX-64;
|
||||
HalfHUDY = ClipY-32;
|
||||
Screen.DrawTexture(HalfHUD,false,HalfHUDX,HalfHUDY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
if ( !CPlayer.mo.Inv ) return; // can this even happen?
|
||||
bFlashTranslator = false;
|
||||
bGotSelected = false;
|
||||
bGotNext = false;
|
||||
bGotPrev = false;
|
||||
Prev = null;
|
||||
Next = null;
|
||||
SelectedItem = CPlayer.mo.InvSel;
|
||||
for ( Inv=CPlayer.mo.Inv; Inv; Inv=Inv.Inv )
|
||||
{
|
||||
if ( bDrawOne ) break;
|
||||
// if drawing more than one inventory, find next and previous items
|
||||
if ( Inv == SelectedItem ) bGotSelected = true;
|
||||
else if ( Inv.bINVBAR )
|
||||
{
|
||||
if ( bGotSelected )
|
||||
{
|
||||
if ( !bGotNext )
|
||||
{
|
||||
Next = Inv;
|
||||
bGotNext = true;
|
||||
}
|
||||
else if ( !bGotPrev ) Prev = Inv;
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( !Next ) Next = Prev;
|
||||
Prev = Inv;
|
||||
bGotPrev = true;
|
||||
}
|
||||
}
|
||||
if ( Inv is 'UTranslator' ) translator = UTranslator(Inv);
|
||||
}
|
||||
// drawing weapon slots differently than Unreal 1 because we have better methods here
|
||||
let cw = CPlayer.ReadyWeapon;
|
||||
int cwslot = -1;
|
||||
if ( cw && (cw.SlotNumber != -1) ) cwslot = cw.SlotNumber?(cw.SlotNumber-1):9;
|
||||
let pw = CPlayer.PendingWeapon;
|
||||
int pwslot = -1;
|
||||
if ( pw && (pw.SlotNumber != -1) ) pwslot = pw.SlotNumber?(pw.SlotNumber-1):9;
|
||||
Weapon wslots[10];
|
||||
// first run, populate the full array of weapons
|
||||
for ( int i=0; i<10; i++ )
|
||||
{
|
||||
int sslot = (i<9)?(i+1):0;
|
||||
for ( Inv = CPlayer.mo.Inv; Inv; Inv=Inv.Inv )
|
||||
{
|
||||
if ( !(Inv is 'Weapon') ) continue;
|
||||
let w = Weapon(Inv);
|
||||
if ( w.SlotNumber != sslot ) continue;
|
||||
int slot = w.SlotNumber?(w.SlotNumber-1):9;
|
||||
if ( !wslots[slot] )
|
||||
{
|
||||
wslots[slot] = w;
|
||||
continue;
|
||||
}
|
||||
if ( (wslots[slot] == pw) || (wslots[slot] == cw) ) continue;
|
||||
if ( (w == pw) || (w == cw) )
|
||||
{
|
||||
wslots[slot] = w;
|
||||
continue;
|
||||
}
|
||||
if ( (w.SelectionOrder < wslots[slot].SelectionOrder) && (!w.Ammo1 || (w.Ammo1.Amount > 0)) )
|
||||
wslots[slot] = w;
|
||||
else if ( (w.SelectionOrder >= wslots[slot].SelectionOrder) && wslots[slot].Ammo1 && (wslots[slot].Ammo1.Amount <= 0) )
|
||||
wslots[slot] = w;
|
||||
}
|
||||
}
|
||||
// draw the slots
|
||||
if ( HudMode < 4 )
|
||||
{
|
||||
for ( int i=0; i<10; i++ )
|
||||
{
|
||||
if ( !wslots[i] ) continue;
|
||||
Font cfont = TinyFont;
|
||||
if ( cwslot == i ) cfont = TinyWhiteFont;
|
||||
int realslot = (i<9)?(i+1):i;
|
||||
CurX = HalfHUDX-3+realslot*6;
|
||||
CurY = HalfHUDY+4;
|
||||
Screen.DrawText(cfont,Font.CR_UNTRANSLATED,CurX,CurY,String.Format("%d",realslot),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
// Draw ammo bar
|
||||
let amo = wslots[i].Ammo1;
|
||||
if ( !amo ) continue;
|
||||
CurY = HalfHUDY+11;
|
||||
AmmoBarSize = 16*min(1.0,amo.Amount/double(amo.MaxAmount));
|
||||
CurY = HalfHUDY+29-AmmoBarSize;
|
||||
if ( (AmmoBarSize < 8) && (amo.Amount < 10) && (amo.Amount > 0) )
|
||||
{
|
||||
CurY -= 9;
|
||||
Screen.DrawText(TinyRedFont,Font.CR_UNTRANSLATED,CurX,CurY,String.Format("%d",amo.Amount),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurY += 9;
|
||||
}
|
||||
DrawColor = "00 FF 00";
|
||||
if ( AmmoBarSize < 8 ) DrawColor = Color(255-int(AmmoBarSize)*30,int(AmmoBarSize)*30+40,0);
|
||||
if ( amo.Amount > 0 )
|
||||
{
|
||||
Screen.DrawTexture(HudAmmo,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_FillColor,BlackColor,DTA_DestWidth,4,DTA_DestHeightF,AmmoBarSize);
|
||||
Screen.DrawTexture(HudAmmo,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_AlphaChannel,true,DTA_FillColor,DrawColor,DTA_DestWidth,4,DTA_DestHeightF,AmmoBarSize);
|
||||
}
|
||||
}
|
||||
}
|
||||
// TODO draw translator
|
||||
if ( translator )
|
||||
{
|
||||
if ( translator.bCurrentlyActivated ) translator.DrawTranslator(scalev,ClipX,ClipY);
|
||||
else bFlashTranslator = (translator.bNewMessage || translator.bNotNewMessage);
|
||||
}
|
||||
// draw the inventory bar
|
||||
if ( (HUDMode == 5) || !SelectedItem ) return;
|
||||
Count++;
|
||||
if ( Count > 20 ) Count = 0;
|
||||
if ( Prev )
|
||||
{
|
||||
bRed = ((Prev is 'UnrealInventory') && UnrealInventory(Prev).bActive) || (Prev is 'Powerup') || ((Prev is 'UTranslator') && bFlashTranslator);
|
||||
DrawHudIcon(x,y,Prev,bRed);
|
||||
if ( Prev.MaxAmount > 1 ) DrawNumberOf(Prev.Amount,x,y);
|
||||
}
|
||||
bRed = ((SelectedItem is 'UnrealInventory') && UnrealInventory(SelectedItem).bActive) || (SelectedItem is 'Powerup') || ((SelectedItem is 'UTranslator') && bFlashTranslator);
|
||||
if ( !Next && !Prev && !bDrawOne ) DrawHudIcon(x+64,y,SelectedItem,bRed);
|
||||
else DrawHudIcon(x+32,y,SelectedItem,bRed);
|
||||
CurX = x+32;
|
||||
if ( !Next && !Prev && !bDrawOne ) CurX = x+64;
|
||||
CurY = y;
|
||||
Screen.DrawTexture(IconSel,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
if ( SelectedItem.MaxAmount > 1 ) DrawNumberOf(SelectedItem.Amount,CurX,y);
|
||||
if ( Next )
|
||||
{
|
||||
bRed = ((Next is 'UnrealInventory') && UnrealInventory(Next).bActive) || (Next is 'Powerup') || ((Next is 'UTranslator') && bFlashTranslator);
|
||||
DrawHudIcon(x+64,y,Next,bRed);
|
||||
if ( Next.MaxAmount > 1 ) DrawNumberOf(Next.Amount,x+64,y);
|
||||
}
|
||||
}
|
||||
|
||||
private void DrawArmor( double x, double y, bool bDrawOne )
|
||||
{
|
||||
int ArmorAmount = 0, CurAbs = 0;
|
||||
Inventory Inv, BestArmor;
|
||||
double XL, YL;
|
||||
CurX = x;
|
||||
CurY = y;
|
||||
for ( Inv=CPlayer.mo.Inv; Inv; Inv=Inv.Inv )
|
||||
{
|
||||
if ( !(Inv is 'UnrealArmor') ) continue;
|
||||
ArmorAmount += Inv.Amount;
|
||||
if ( (Inv.Amount <= 0) || Inv.Icon.IsNull() ) continue;
|
||||
if ( !bDrawOne )
|
||||
{
|
||||
DrawHudIcon(CurX,y,Inv,false);
|
||||
DrawIconValue(Inv.Amount);
|
||||
CurX += 32;
|
||||
}
|
||||
else if ( UnrealArmor(Inv).absorb > CurAbs )
|
||||
{
|
||||
CurAbs = UnrealArmor(Inv).absorb;
|
||||
BestArmor = Inv;
|
||||
}
|
||||
}
|
||||
if ( bDrawOne && BestArmor )
|
||||
{
|
||||
DrawHudIcon(CurX,Y,BestArmor,false);
|
||||
DrawIconValue(BestArmor.Amount);
|
||||
CurX += 32;
|
||||
}
|
||||
if ( (ArmorAmount > 0) && !HudMode )
|
||||
Screen.DrawText(LargeFont,Font.CR_UNTRANSLATED,CurX,Y,String.Format("%d",ArmorAmount),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
|
||||
private void DrawAmmo( double x, double y )
|
||||
{
|
||||
CurX = x;
|
||||
CurY = y;
|
||||
if ( !CPlayer.ReadyWeapon || !CPlayer.ReadyWeapon.Ammo1 )
|
||||
{
|
||||
Screen.DrawTexture(IconBase,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
return;
|
||||
}
|
||||
Font cfont = LargeFont;
|
||||
if ( CPlayer.ReadyWeapon.Ammo1.Amount < 10 ) cfont = LargeRedFont;
|
||||
if ( !HudMode )
|
||||
{
|
||||
CurX -= cfont.StringWidth(String.Format("%d",CPlayer.ReadyWeapon.Ammo1.Amount));
|
||||
Screen.DrawText(cfont,Font.CR_UNTRANSLATED,CurX,CurY,String.Format("%d",CPlayer.ReadyWeapon.Ammo1.Amount),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
}
|
||||
CurX = x;
|
||||
Screen.DrawTexture(IconBase,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
// TODO downscale icons in cases where they're bigger than a 32x32 box
|
||||
TextureID icon = CPlayer.ReadyWeapon.Icon.IsNull()?CPlayer.ReadyWeapon.Ammo1.Icon:CPlayer.ReadyWeapon.Icon;
|
||||
Screen.DrawTexture(icon,false,CurX+16,CurY+16,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_CenterOffset,true);
|
||||
CurX += 32;
|
||||
CurY += 29;
|
||||
DrawIconValue(CPlayer.ReadyWeapon.Ammo1.Amount);
|
||||
CurX = X+2;
|
||||
CurY = Y+29;
|
||||
if ( (HudMode != 1) && (HudMode != 2) && (HudMode != 4) )
|
||||
Screen.DrawTexture(HudLine,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_WindowRightF,Min(27.*(CPlayer.ReadyWeapon.Ammo1.Amount/double(CPlayer.ReadyWeapon.Ammo1.MaxAmount)),27.));
|
||||
}
|
||||
|
||||
private void DrawHealth( double x, double y )
|
||||
{
|
||||
CurX = X;
|
||||
CurY = Y;
|
||||
Font cfont = LargeFont;
|
||||
if ( CPlayer.mo.Health < 25 ) cfont = LargeRedFont;
|
||||
Screen.DrawTexture(IconHeal,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurX += 32;
|
||||
CurY += 29;
|
||||
DrawIconValue(Max(0,CPlayer.mo.Health));
|
||||
CurY -= 29;
|
||||
if ( !HudMode ) Screen.DrawText(cfont,Font.CR_UNTRANSLATED,CurX,CurY,String.Format("%d",Max(0,CPlayer.mo.Health)),DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true);
|
||||
CurX = X+2;
|
||||
CurY = Y+29;
|
||||
if ( (HudMode != 1) && (HudMode != 2) && (HudMode != 4) )
|
||||
Screen.DrawTexture(HudLine,false,CurX,CurY,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_WindowRightF,Min(27.*(CPlayer.mo.Health/double(CPlayer.mo.SpawnHealth())),27.));
|
||||
}
|
||||
|
||||
private void DrawIdentifyInfo()
|
||||
{
|
||||
double lalpha = 2.0-((gametic+fractic)-lastseentic)/Thinker.TICRATE;
|
||||
if ( !lastseen || (lalpha <= 0) ) return;
|
||||
String cl1 = "DarkGreen", cl2 = "Green";
|
||||
if ( deathmatch && (lastseen.player.GetTeam() < teams.size()) )
|
||||
{
|
||||
cl2 = teams[lastseen.player.GetTeam()].mName;
|
||||
cl1 = String.Format("Dark%s",cl2);
|
||||
}
|
||||
String tname = String.Format("\c[%s]Name:\c[%s] %s",cl1,cl2,lastseen.player.GetUserName());
|
||||
CurX = (ClipX-WhiteFont.StringWidth(tname))/2;
|
||||
CurY = ClipY-54;
|
||||
Screen.DrawText(WhiteFont,Font.CR_UNTRANSLATED,CurX,CurY,tname,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_Alpha,lalpha/2.);
|
||||
if ( !deathmatch || (lastseen.IsTeammate(CPlayer.mo)) )
|
||||
{
|
||||
CurY += 1.2*WhiteFont.GetHeight();
|
||||
tname = String.Format("\c[%s]Health:\c[%s] %d",cl1,cl2,lastseen.Health);
|
||||
Screen.DrawText(WhiteFont,Font.CR_UNTRANSLATED,CurX,CurY,tname,DTA_VirtualWidthF,ClipX,DTA_VirtualHeightF,ClipY,DTA_KeepRatio,true,DTA_Alpha,lalpha/2.);
|
||||
}
|
||||
}
|
||||
|
||||
private void DrawKeys( double x, double y )
|
||||
{
|
||||
// TODO
|
||||
}
|
||||
|
||||
private void DrawUnrealHUD()
|
||||
{
|
||||
if ( HudMode == 5 )
|
||||
{
|
||||
DrawInventory(ClipX-96,0,false);
|
||||
return;
|
||||
}
|
||||
if ( ClipX < 320 ) HudMode = 4;
|
||||
// Draw Armor
|
||||
if ( HudMode < 2 ) DrawArmor(0,0,false);
|
||||
else if ( (HudMode == 3) || (HudMode == 2) ) DrawArmor(0,ClipY-32,false);
|
||||
else if ( HudMode == 4 ) DrawArmor(ClipX-64,ClipY-64,true);
|
||||
// Draw Ammo
|
||||
if ( HudMode != 4 ) DrawAmmo(ClipX-96,ClipY-32);
|
||||
else DrawAmmo(ClipX-32,ClipY-32);
|
||||
// Draw Health
|
||||
if ( HudMode < 2 ) DrawHealth(0,ClipY-32);
|
||||
else if ( (HudMode == 3) || (HudMode == 2) ) DrawHealth(ClipX-128,ClipY-32);
|
||||
else if ( HudMode == 4 ) DrawHealth(ClipX-64,ClipY-32);
|
||||
// Display Inventory
|
||||
if ( HudMode < 2 ) DrawInventory(ClipX-96,0,false);
|
||||
else if ( HudMode == 3 ) DrawInventory(ClipX-96,ClipY-64,false);
|
||||
else if ( HudMode == 4 ) DrawInventory(ClipX-64,ClipY-64,true);
|
||||
else if ( HudMode == 2 ) DrawInventory(ClipX/2-64,ClipY-32,false);
|
||||
// Display Frag count
|
||||
if ( HudMode < 3 ) DrawFragCount(ClipX-32,ClipY-64);
|
||||
else if ( HudMode == 3 ) DrawFragCount(0,ClipY-64);
|
||||
else if ( HudMode == 4 ) DrawFragCount(0,ClipY-32);
|
||||
// Display Keys
|
||||
if ( HudMode < 3 ) DrawKeys(ClipX,ClipY-64);
|
||||
else if ( HudMode < 6 ) DrawKeys(ClipX,ClipY);
|
||||
// Display Identification Info
|
||||
DrawIdentifyInfo();
|
||||
}
|
||||
|
||||
override void Tick()
|
||||
{
|
||||
Super.Tick();
|
||||
vtracer.ignore = CPlayer.mo;
|
||||
vtracer.trace(CPlayer.mo.Vec2OffsetZ(0,0,CPlayer.viewz),CPlayer.mo.CurSector,(cos(CPlayer.mo.angle)*cos(CPlayer.mo.pitch),sin(CPlayer.mo.angle)*cos(CPlayer.mo.pitch),-sin(CPlayer.mo.pitch)),1000,0);
|
||||
if ( vtracer.Results.HitType != TRACE_HitActor ) return;
|
||||
lastseen = vtracer.Results.HitActor;
|
||||
lastseentic = gametic;
|
||||
CPlayer.inventorytics = 0;
|
||||
}
|
||||
|
||||
override void DrawAutomapHUD( double TicFrac )
|
||||
{
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue