(v3.0b) Enhanced Vanilla Project (EVP) - My first Doom mod

Projects that alter game functions but do not include new maps belong here.
Forum rules
The Projects forums are only for projects. If you are asking questions about a project, either find that project's thread, or start a thread in the General section instead.

Got a cool project idea but nothing else? Put it in the project ideas thread instead!

Projects for any Doom-based engine (especially 3DGE) are perfectly acceptable here too.

Please read the full rules for more details.
User avatar
Mere_Duke
Posts: 215
Joined: Sun Aug 28, 2016 3:35 pm
Location: Russia

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by Mere_Duke »

A_D_M_E_R_A_L wrote:2. I'd LOVE to do that (grin face while Invul is active) but I don't know HOW. If there is a way to do it, I want to know how to do it ASAP.
You need a "zscriptified" status bars. ZScript is a thing but a very low-documented one, so you will need to experiment. Basically what you need is to override functions that draw things, then call the original ones to draw all, and after that add something on top of it (e.g. draw special mugshot if player have Invuln sphere).

As an example I've found this post by AFADoomer a few years back:






Here's a (very ugly) status bar that is stripped down to bare minimals and heavily commented... Not sure if that will help or not.

I didn't include keys on here, since there's no key bar equivalent in ZScript - you have to manually check for the keys and draw them yourself (see ugliness here), but this at least mostly documents the core functions that Vaecrius mentioned in the previous post, plus some.

Code: Select all

version "2.5"

class NewStatusBar : BaseStatusBar
{
    // Unlike SBARINFO, fonts can't be directly referenced by name.
    //  You'll need to declare them here, then initialize them in Init() below
    HUDFont mHUDFont;
    HUDFont mIndexFont;
    HUDFont mAmountFont;

    // This is necessary if you want to use the Inventory Bar
    InventoryBarState diparms;

    // You need a DynamicValueInterpolator for any value that you want to have interpolated
    //  This includes both bar values and any numbers that you want to "count to" 
    //  instead of having the value immediately change over
    DynamicValueInterpolator mHealthInterpolator;

    // Declare any other variables you might end up needing here
    
    // What happens when this bar is initialized?
    override void Init()
    {
        // Run the parent status bar's Init() function
        //   It's generally a good idea to call the super class's function whenever you 
        //   are overriding a function, in case some critical code is executed by the 
        //   parent class - unless you know specifically that you want to completely
        //   replace the parent class's function instead
        Super.Init();

        SetSize(32, 320, 200); // This sets the pixel height of the status bar and the base resolution

        // Initialize the fonts - there's actually a wiki page on this part: 
        //    https://zdoom.org/wiki/Classes:HUDFont
        Font fnt = "HUDFONT_DOOM";
        mHUDFont = HUDFont.Create(fnt, fnt.GetCharWidth("0"), true, 1, 1);

        fnt = "INDEXFONT_DOOM";
        mIndexFont = HUDFont.Create(fnt, fnt.GetCharWidth("0"), true);

        mAmountFont = HUDFont.Create("INDEXFONT");

        // Initialize the inventory bar
        diparms = InventoryBarState.Create();

        // Initialize the interpolation variables
        //  Parameters:
        //    Starting Value
        //    Change Factor (I'm not 100% sure what this does)
        //    Minimum change step size (don't increment by less than this amount each Update() call)
        //    Maximum change step size (don't increment by more than this amount each Update() call)
        //
        //  These are the values used by:
        //    Hexen's health bar: 0, 0.25, 1, 8
        //    Hexen's chain health bar: 0, 0.25, 1, 6
        mHealthInterpolator = DynamicValueInterpolator.Create(0, 0.25, 1, 8);
    }

    // What happens when a new game begins
    override void NewGame ()
    {
        // Run the parent status bar's NewGame() function
        Super.NewGame();

        // Reset any interpolators that you declared
        //  void Reset(int value)
        //  Parameter: Desired value that you want to set the value to immediately
        mHealthInterpolator.Reset(0); // Reset sets the current value directly, so this sets the value to 0
    }

    // What needs to run every tick
    override void Tick()
    {
        // Run the parent status bar's Tick() function
        Super.Tick();

        // Update the value of the interpolators
        //  void Update(int destvalue)
        //  Parameter: Desired end-state value of the interpolator
        //   This is what sets the interpolator's value.  It uses the min/max step size variables that we created 
        //   interpolator with in Init(), so must be called repeatedly to set the correct value (so, if we start
        //   at 0, and Update to 100, and max step size is 8, each Update call will increment the value up by 8
        //   until the value reaches 100...  8, 16, 24, 32, ... 96, 100)
        mHealthInterpolator.Update(CPlayer.health); // Set the interpolator's value to this player's health
    }

    // Draw the status bar
    //   The default status bars use some logic here to call different functions based on whether the bar is normal
    //   or full-screen.  Since you don't actually want to use anything but a fullscreen HUD, you can get rid of the 
    //   checks here and jsut do the drawing here instead of calling another function
    override void Draw (int state, double TicFrac)
    {
        // Run the parent status bar's Draw() function
        Super.Draw (state, TicFrac); 

        BeginHUD(); // You'd use BeginStatusBar(); if you wanted a traditional bar instead of fullscreen

        // Draw the hud elements
        //   The x, y coordinates are all in Vector2 format, which for editing purposes means that they are enclosed
        //   in their own set of parenthesis...  Screen coordinates of x=5, y=10 is written as "(5, 10)"
        //
        //   Positioning flags are mostly self-explanatory; a list can be seen here: https://github.com/coelckers/gzdoom/blob/master/wadsrc/static/zscript/statusbar/statusbar.txt#L159
        //    Flags that start with DI_SCREEN set the relative position of the coordinates you pass - so (0, -15) and 
        //    DI_SCREEN_CENTER_BOTTOM will position your element at screen center, 15 pixels from the bottom
        //
        //    Flags that start with DI_ITEM set the positioning point of the element, essentially by overriding the 
        //    sprite/graphic's image offsets.  DI_ITEM_LEFT_TOP will position the item with it's top left corner at 
        //    the coordinates you provide, and DI_ITEM_OFFSETS will use the item's offset values

        // Only draw if there's no automap active
        if (!automapactive)
        {
            // Draw an image
            //  native void DrawImage(String texture, Vector2 pos, int flags = 0, double Alpha = 1., Vector2 box = (-1, -1), Vector2 scale = (1, 1));
            //  Parameters:
            //   Texture name as a string
            //   The desired coordinates of the image
            //   Positioning flags (DI_*)
            //   Alpha of the image (0.0 - 1.0)
            //   Vector2 box = (-1, -1) (Don't know what this does...)
            //   Scale as a Vector2 (so, half sized would be: (0.5, 0.5) )
            //
            //  NOTES: 
            //  There is also a DrawTexture function that uses the exact same parameters, except it takes an texture ID 
            //  instead of the string name of the texture - it's used when drawing the MugShot below
            //
            //  There is also a DrawInventoryIcon function with the same parameters except that it takes an inventory item
            //  instead of the texture name - used for ammo and inventory icon drawing below 
            DrawImage("STBAR", (0, 168), DI_ITEM_OFFSETS, 1.0, (-1, -1), (1, 1));

            // Draw a text string
            //  native void DrawString(HUDFont font, String string, Vector2 pos, int flags = 0, int translation = Font.CR_UNTRANSLATED, double Alpha = 1., int wrapwidth = -1, int linespacing = 4);
            //  Parameters:
            //   Font variable name, as declared in Init()
            //   The string you want to print.  To print a variable that is a number value (like DrawNumber in SBARINFO), use FormatNumber(yourvariable)
            //   Position where you want the string printed
            //   Positioning flags
            //   The font color translation that you want to use
            //   Alpha of the string
            //   Width that the string can be before it begins to wrap
            //   Spacing between the lines in the string when it wraps or has a newline character in it
            DrawString(mHUDFont, FormatNumber(CPlayer.health, 3), (90, 171), DI_TEXT_ALIGN_RIGHT|DI_NOSHADOW);
            DrawString(mHUDFont, "This is a normal string...", (221, 171), DI_TEXT_ALIGN_RIGHT|DI_NOSHADOW);

            // Draw a bar
            //  void DrawBar(String ongfx, String offgfx, double curval, double maxval, Vector2 position, int border, int vertical, int flags = 0)
            //  Parameters:
            //   The top layer graphic of the bar that is incrementally drawn based on the variable value
            //   The bottom/background graphic of the bar
            //   The current value of the bar - usually your interpolated variable
            //   The maximum value of the bar
            //   Bar position
            //   "Border" - I think only really used by Hexen?
            //   Bar direction flags - SHADER_HORZ, SHADER_VERT, or SHADER_REVERSE - https://github.com/coelckers/gzdoom/blob/master/wadsrc/static/zscript/statusbar/statusbar.txt#L261
            //   Positioning Flags
            //
            //  Note the use of GetValue() on the health interpolator here.
            DrawBar("SOULA0", "PINVA0", mHealthInterpolator.GetValue(), CPlayer.mo.GetMaxHealth(true), (36, 160), 0, SHADER_HORZ, DI_ITEM_OFFSETS);

            // Draw current ammo amounts
            Ammo ammo1, ammo2;
            int ammocount1, ammocount2;
            [ammo1, ammo2, ammocount1, ammocount2] = GetCurrentAmmo();
            if (ammo1) { DrawString(mAmountFont, FormatNumber(ammocount1, 3), (225, 171), DI_TEXT_ALIGN_RIGHT); }
            if (ammo2) { DrawString(mAmountFont, FormatNumber(ammocount2, 3), (225, 185), DI_TEXT_ALIGN_RIGHT); }

            //Ammo Icons
            DrawInventoryIcon(ammo1, (231, 170), DI_ITEM_OFFSETS);
            DrawInventoryIcon(ammo2, (231, 184), DI_ITEM_OFFSETS);

            // Draw armor amount
            let armor = CPlayer.mo.FindInventory("BasicArmor");
            if (armor != null && armor.Amount > 0)
            {
                DrawInventoryIcon(armor, (4, 184), DI_ITEM_OFFSETS);
                DrawString(mHUDFont, FormatNumber(GetArmorAmount(), 3), (52, 185), DI_TEXT_ALIGN_RIGHT);
                DrawString(mHUDFont, "%", (65, 185), DI_TEXT_ALIGN_RIGHT);
            }

            // Draw the mugshot
            //  Uses DrawTexture to draw the mugshot image, as retrieved by GetMugShot
            //  native TextureID GetMugshot(int accuracy, int stateflags=MugShot.STANDARD, String default_face = "STF");
            //   (I haven't looked into these parameters at all - I assume the "STF" one changes the mugshot image base, though)
            DrawTexture(GetMugShot(5), (143, 168), DI_ITEM_OFFSETS);

            // Draw the currently selected inventory item
            //  void DrawInventoryIcon(Inventory item, Vector2 pos, int flags = 0, double alpha = 1.0, Vector2 boxsize = (-1, -1), Vector2 scale = (1.,1.))
            //  Parameters:
            //   Inventory item name - CPlayer.mo.InvSel is the current inventroy selected by the player
            //   All other parameters are the same as DrawImage
            //
            //  A major difference from SBARINFO is that you have to manually draw the inventory amount
            if (CPlayer.mo.InvSel != null) // If there's an inventory item selected...
            {
                double x = 160;
                double y = 198;
                DrawInventoryIcon(CPlayer.mo.InvSel, (x, y));
                if (CPlayer.mo.InvSel.Amount > 1) // If you have more than one, draw the amount number as a string
                {
                    DrawString(mAmountFont, FormatNumber(CPlayer.mo.InvSel.Amount), (x + 15, y-mIndexFont.mFont.GetHeight()), DI_TEXT_ALIGN_RIGHT, Font.CR_GOLD);
                }
            }
    
            // Draw the inventory bar
            if (isInventoryBarVisible()) // If it should be visible...
            {
                // void DrawInventoryBar(InventoryBarState parms, Vector2 position, int numfields, int flags = 0, double bgalpha = 1.)
                // Parameters:
                //  The InventoryBarState variable that you declared and initialized above
                //  The desired coordinates of the bar
                //  The number of inventory items to show in the bar at one time
                //  Positioning flags
                //  Alpha of the background for the inventory bar (0.0 to 1.0)
                DrawInventoryBar(diparms, (0, 0), 7, DI_SCREEN_CENTER_BOTTOM, 0.5);
            }

            // Other useful functions:
            //  bool CheckInventory(class<Inventory> item, int amount = 1)
            //  bool CheckHealth(int Amount, bool percentage = false)
            //  bool isInvulnerable()
            //  bool isInventoryBarVisible()
            //  bool CheckWeaponSelected(class<Weapon> weap, bool checksister = true)
            //  bool CheckDisplayName(String displayname)
            //  String FormatNumber(int number, int minsize = 0, int maxsize = 0, int format = 0, String prefix = "")
        }
    }
}




Hope this will help at least a little.
User avatar
Mere_Duke
Posts: 215
Joined: Sun Aug 28, 2016 3:35 pm
Location: Russia

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by Mere_Duke »

A few more bits info for you.

Here is the default Status Bar class:
https://zdoom.org/wiki/Classes:BaseStatusBar
(You can look there to know what members that class have and to which data you'll have access by deriving your own class. It's useful. For example, the current player declared there as CPlayer.)
You can also find this definitions inside of gzdoom.pk3 file.



The mugshot can be defined differently. Change

Code: Select all

	DrawTexture(GetMugShot(5), (143, 168), DI_ITEM_OFFSETS);
to

Code: Select all

			if (isInvulnerable())
			{
				DrawTexture(GetMugShot(5, MugShot.CUSTOM, "SFF"), (143, 168), DI_ITEM_OFFSETS);
			}
			else
			{
				DrawTexture(GetMugShot(5), (143, 168), DI_ITEM_OFFSETS); // ... else draw default Doomboy
			}
This draws a custom mugshot in case player is invulnerable via a powerup. Note that you should have a bunch of new sprites to fill all mugshot variants. And in that function all you need is to define its prefix.
I include here a test example based off the AFADoomer's post & female mugshot sprites from Hideous Destructor by Matt. Load it, pick Invulnerability Sphere and see what happens. (The overall status bar is still crappy-looking, but anyway.)
http://www.mediafire.com/file/e79eh9kst185lb4/test.7z

Probably there instead of drawing the entire mugshot you want to draw just a single sprite (with DrawImage for example). Or somehow call all "super" funcs in the new Status Bar class to code _only_ new mugshot. It's up to you.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

https://discord.gg/CuqpyK7
I made a Discord server for the mod. Come on in.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

v26 (24/01/19)
Changed the color on the difficulty text
Added shortcuts to the "Mod options" submenu
New barrel explosion animation
New ricochet sounds
New footstep sounds for Imp, Mancubus and Chaingunner
New active sounds for Shotgunner, Chaingunner, Imp and Cyberdemon
New attack animation for Arch-Vile (seems faster, but it's the same in terms if tics)
New firing sound for the Pump Shotgun and SSG
New Baron sprite - Archon Lord (from CDI - Complex Doom Invasion, recolored by me)
Custom invul mugshots
Beezle
Posts: 139
Joined: Thu Aug 16, 2018 6:48 pm

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by Beezle »

After a little more testing with blood addons I found that its the colored blood that causes the sprite conflict in Hell Knight's death animation. So it actually works with EVP, but for Bolognese you can't load bbgore_colored_blood_for_cacodemons_and_bruisers_vanilla.pk3, and for Nash Gore VE you can't load cblood.pk3.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

Beezle wrote:After a little more testing with blood addons I found that its the colored blood that causes the sprite conflict in Hell Knight's death animation. So it actually works with EVP, but for Bolognese you can't load bbgore_colored_blood_for_cacodemons_and_bruisers_vanilla.pk3, and for Nash Gore VE you can't load cblood.pk3.
I didn't aimed for the compatibility with the gore mods at all.
User avatar
BROS_ETT_311
Posts: 218
Joined: Fri Nov 03, 2017 6:05 pm

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by BROS_ETT_311 »

Beezle wrote:After a little more testing with blood addons I found that its the colored blood that causes the sprite conflict in Hell Knight's death animation. So it actually works with EVP, but for Bolognese you can't load bbgore_colored_blood_for_cacodemons_and_bruisers_vanilla.pk3, and for Nash Gore VE you can't load cblood.pk3.
Both addons for their respective gore mod replace the actors. Each uses the original/vanilla sprites for death animations, which is why they aren't compatible with EVP (or any mod that uses different sprite sets from the original Doom). I'd think any compatibility patch would have to be either user generated, or by the original authors of each gore mod.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

v27 (6/02/19)
Added a set of shaders - ACES Tonemap
New kickback animation for the BFG
Edited the sprites of a Demon (looks very much like R667's Cyber Fiend)
Fixed offsets on Baron's movement frames
Added the logo for the menu and changed the UAC icon's color so it doesn't clash
New pump shotgun and pistol sprites, courtesy of TypicalSonicFan
Edited Cyberdemon's sprites to include the heart thing on his chest
Added Agathodemon's teeth for the Cacodemon
New muzzle flash and select animations for the RL
New sound for the plasma rifle (same for Arachno's plasma cannon)
New select animation for the PR
New SSG animations
Edited Chaingun sprites (by TypicalSonicFan)
Beezle
Posts: 139
Joined: Thu Aug 16, 2018 6:48 pm

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by Beezle »

Really love this new set of shaders you added. Goes really well with the enemy sprites.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

Beezle wrote:Really love this new set of shaders you added. Goes really well with the enemy sprites.
It is customizable aswell.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

v27a hotfix (7/02/19)
Changed a select animation for the BFG (hard to notice, but it's there)
The red dot sights on the shotgun during select/deselect animation now use A_Overlay instead of A_GunFlash (brightmaps don't work for them for some reason)
User avatar
NullWire
Posts: 270
Joined: Fri Dec 18, 2015 4:48 pm

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by NullWire »

The weapons sprites are beautiful, perfect, what else I can say?
Good work! :D

But as suggestion, do you think you could polish more the Chaingun, Plasma rifle and BFG-9000 sprites?
Like you did with the shotguns, they could look even better!

Also a railgun can be a good addition to the arsenal tbh.
User avatar
Sgt. Shivers
Posts: 1743
Joined: Fri Jun 22, 2012 5:39 am

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by Sgt. Shivers »

I really like the blend of brightmaps and darkdoom in this mod, it gives everything a nice neon look. The pistol feels a bit strange to use at the moment, clicking rapidly fires slower than just holding the button, is this intentional? Also, the fist animation looks a bit unnatural. Maybe have the arm returning to rest position animation be a bit slower? I enjoyed playing this mod quite a bit and I look forwards to seeing where you go with it!
User avatar
StroggVorbis
Posts: 866
Joined: Wed Nov 08, 2017 4:23 pm
Graphics Processor: nVidia with Vulkan support
Location: Germany

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by StroggVorbis »

@Sgt. Shivers
Isn't this the case with the vanilla pistol also? Holding the fire button down before the fire state passes A_Refire makes it go immediately to the top of the fire state again, otherwise you have to start over from the ready state which basically acts as a prefire delay.

Could also be that the tic duration is longer in EVP than vanilla.
User avatar
A_D_M_E_R_A_L
Posts: 284
Joined: Sun Apr 16, 2017 2:55 am
Preferred Pronouns: He/Him

Re: Enhanced Vanilla Project (EVP) - My first Doom mod

Post by A_D_M_E_R_A_L »

DabbingSquidward wrote:@Sgt. Shivers
Isn't this the case with the vanilla pistol also? Holding the fire button down before the fire state passes A_Refire makes it go immediately to the top of the fire state again, otherwise you have to start over from the ready state which basically acts as a prefire delay.

Could also be that the tic duration is longer in EVP than vanilla.
The tic duration is EXACTLY the same in pretty much all the weapons and those people that complain about not being able to rapid fire a pistol are just very used to pistols from other mods where you can spam-click and not used to the vanilla pistol's behavior.
NullWire wrote:Also a railgun can be a good addition to the arsenal tbh.
No extra weapons, I'm sticking to the default arsenal.
Post Reply

Return to “Gameplay Mods”