- fixed: The compatibility parser applied the last map's settings to all

maps in the compatibility list.
- Added compatibility settings for a few more levels in some classic WADs.
- Added spechit overflow workaround for Strain MAP07. This is highly map
  specific because the original behavior cannot be restored.
- Added a check for Doom's IWAD levels that forces COMPAT_SHORTTEX for them.
  MD5 cannot be used well here because there's many different IWADs with 
  slightly different levels. This is only done for Doom format levels to
  ensure that custom IWADs for ZDoom are not affected.
- fixed: level.flags2 was not reset at level start.
- Fixed: Morph powerups can change the actor picking up the item so 
  AInventory::CallTryPickup must be able to return the new actor.
- Fixed: ACS's GiveInventory may not assume that a PlayerPawn is still
  attached to the player data after an item has been given.
- Added a missing NULL pointer check to DBaseStatusBar::Blendview.


SVN r1405 (trunk)
This commit is contained in:
Christoph Oelckers 2009-02-06 00:16:57 +00:00
parent 70aa9cb92a
commit cccdfd6336
12 changed files with 116 additions and 17 deletions

View file

@ -1,9 +1,26 @@
February 5, 2009 (Changes by Graf Zahl)
- fixed: The compatibility parser applied the last map's settings to all
maps in the compatibility list.
- Added compatibility settings for a few more levels in some classic WADs.
- Added spechit overflow workaround for Strain MAP07. This is highly map
specific because the original behavior cannot be restored.
- Added a check for Doom's IWAD levels that forces COMPAT_SHORTTEX for them.
MD5 cannot be used well here because there's many different IWADs with
slightly different levels. This is only done for Doom format levels to
ensure that custom IWADs for ZDoom are not affected.
- fixed: level.flags2 was not reset at level start.
- Fixed: Morph powerups can change the actor picking up the item so
AInventory::CallTryPickup must be able to return the new actor.
- Fixed: ACS's GiveInventory may not assume that a PlayerPawn is still
attached to the player data after an item has been given.
- Added a missing NULL pointer check to DBaseStatusBar::Blendview.
February 4, 2009 February 4, 2009
- Added a compatibility lump because I think it's a shame that Void doesn't - Added a compatibility lump because I think it's a shame that Void doesn't
work properly on new ZDooms after all the collaboration I had with Cyb on work properly on new ZDooms after all the collaboration I had with Cyb on
that map. (Works with other maps, too.) that map. (Works with other maps, too.)
February 5, 2009 (Changes by Graf Zahl) February 4, 2009 (Changes by Graf Zahl)
- Made improvements so that the FOptionalMapinfoData class is easier to use. - Made improvements so that the FOptionalMapinfoData class is easier to use.
February 3, 2009 February 3, 2009

View file

@ -45,6 +45,8 @@
#include "doomdef.h" #include "doomdef.h"
#include "doomstat.h" #include "doomstat.h"
#include "c_dispatch.h" #include "c_dispatch.h"
#include "gi.h"
#include "g_level.h"
// MACROS ------------------------------------------------------------------ // MACROS ------------------------------------------------------------------
@ -75,6 +77,7 @@ static FCompatOption Options[] =
{ {
{ "setslopeoverflow", 0, BCOMPATF_SETSLOPEOVERFLOW }, { "setslopeoverflow", 0, BCOMPATF_SETSLOPEOVERFLOW },
{ "resetplayerspeed", 0, BCOMPATF_RESETPLAYERSPEED }, { "resetplayerspeed", 0, BCOMPATF_RESETPLAYERSPEED },
{ "spechitoverflow", 0, BCOMPATF_SPECHITOVERFLOW },
// list copied from g_mapinfo.cpp // list copied from g_mapinfo.cpp
{ "shorttex", COMPATF_SHORTTEX, 0 }, { "shorttex", COMPATF_SHORTTEX, 0 },
@ -169,6 +172,7 @@ void ParseCompatibility()
{ {
BCompatMap[md5array[j]] = flags; BCompatMap[md5array[j]] = flags;
} }
md5array.Clear();
} }
} }
@ -183,20 +187,42 @@ void CheckCompatibility(MapData *map)
FMD5Holder md5; FMD5Holder md5;
FCompatValues *flags; FCompatValues *flags;
map->GetChecksum(md5.Bytes); // When playing Doom IWAD levels force COMPAT_SHORTTEX.
flags = BCompatMap.CheckKey(md5); if (Wads.GetLumpFile(map->lumpnum) == 1 && gameinfo.gametype == GAME_Doom && !(level.flags & LEVEL_HEXENFORMAT))
if (flags != NULL)
{ {
ii_compatflags = flags->CompatFlags; ii_compatflags = COMPATF_SHORTTEX;
ib_compatflags = flags->BCompatFlags; ib_compatflags = 0;
} }
else else
{ {
ii_compatflags = 0; map->GetChecksum(md5.Bytes);
ib_compatflags = 0;
flags = BCompatMap.CheckKey(md5);
if (developer)
{
Printf("MD5 = ");
for (size_t j = 0; j < sizeof(md5.Bytes); ++j)
{
Printf("%02X", md5.Bytes[j]);
}
if (flags != NULL) Printf(", cflags = %08x, bflags = %08x\n", flags->CompatFlags, flags->BCompatFlags);
else Printf("\n");
}
if (flags != NULL)
{
ii_compatflags = flags->CompatFlags;
ib_compatflags = flags->BCompatFlags;
}
else
{
ii_compatflags = 0;
ib_compatflags = 0;
}
} }
// Reset i_compatflags // Reset i_compatflags
compatflags = compatflags; compatflags.Callback();
} }
//========================================================================== //==========================================================================

View file

@ -288,6 +288,7 @@ enum
{ {
BCOMPATF_SETSLOPEOVERFLOW = 1 << 0, // SetSlope things can overflow BCOMPATF_SETSLOPEOVERFLOW = 1 << 0, // SetSlope things can overflow
BCOMPATF_RESETPLAYERSPEED = 1 << 1, // Set player speed to 1.0 when changing maps BCOMPATF_RESETPLAYERSPEED = 1 << 1, // Set player speed to 1.0 when changing maps
BCOMPATF_SPECHITOVERFLOW = 1 << 2, // Emulate spechit overflow (e.g. Strain MAP07)
}; };
// phares 3/20/98: // phares 3/20/98:

View file

@ -1216,6 +1216,7 @@ void G_InitLevelLocals ()
level.aircontrol = (fixed_t)(sv_aircontrol * 65536.f); level.aircontrol = (fixed_t)(sv_aircontrol * 65536.f);
level.teamdamage = teamdamage; level.teamdamage = teamdamage;
level.flags = 0; level.flags = 0;
level.flags2 = 0;
info = FindLevelInfo (level.mapname); info = FindLevelInfo (level.mapname);

View file

@ -876,9 +876,9 @@ void AInventory::Touch (AActor *toucher)
toucher = toucher->player->mo; toucher = toucher->player->mo;
} }
// This is the only situation when a pickup flash should ever play. if (!CallTryPickup (toucher, &toucher)) return;
if (!CallTryPickup (toucher)) return;
// This is the only situation when a pickup flash should ever play.
if (PickupFlash != NULL && !ShouldStay()) if (PickupFlash != NULL && !ShouldStay())
{ {
Spawn(PickupFlash, x, y, z, ALLOW_REPLACE); Spawn(PickupFlash, x, y, z, ALLOW_REPLACE);
@ -1258,10 +1258,13 @@ bool AInventory::TryPickup (AActor *&toucher)
// //
//=========================================================================== //===========================================================================
bool AInventory::CallTryPickup (AActor *toucher) bool AInventory::CallTryPickup (AActor *toucher, AActor **toucher_return)
{ {
bool res = TryPickup(toucher); bool res = TryPickup(toucher);
// Morph items can change the toucher so we need an option to return this info.
if (toucher_return != NULL) *toucher_return = toucher;
if (!res && (ItemFlags & IF_ALWAYSPICKUP) && !ShouldStay()) if (!res && (ItemFlags & IF_ALWAYSPICKUP) && !ShouldStay())
{ {
res = true; res = true;

View file

@ -117,7 +117,7 @@ public:
virtual bool ShouldRespawn (); virtual bool ShouldRespawn ();
virtual bool ShouldStay (); virtual bool ShouldStay ();
virtual void Hide (); virtual void Hide ();
bool CallTryPickup (AActor *toucher); bool CallTryPickup (AActor *toucher, AActor **toucher_return = NULL);
virtual void DoPickupSpecial (AActor *toucher); virtual void DoPickupSpecial (AActor *toucher);
virtual bool SpecialDropAction (AActor *dropper); virtual bool SpecialDropAction (AActor *dropper);
virtual bool DrawPowerup (int x, int y); virtual bool DrawPowerup (int x, int y);

View file

@ -1502,7 +1502,7 @@ void DBaseStatusBar::BlendView (float blend[4])
if (screen->Accel2D || (CPlayer->camera != NULL && menuactive == MENU_Off && ConsoleState == c_up)) if (screen->Accel2D || (CPlayer->camera != NULL && menuactive == MENU_Off && ConsoleState == c_up))
{ {
player_t *player = (CPlayer->camera->player != NULL) ? CPlayer->camera->player : CPlayer; player_t *player = (CPlayer->camera != NULL && CPlayer->camera->player != NULL) ? CPlayer->camera->player : CPlayer;
AddBlend (player->BlendR, player->BlendG, player->BlendB, player->BlendA, blend); AddBlend (player->BlendR, player->BlendG, player->BlendB, player->BlendA, blend);
} }

View file

@ -65,6 +65,8 @@ public:
int BoxOnLineSide (const line_t *ld) const; int BoxOnLineSide (const line_t *ld) const;
void Set(int index, fixed_t value) {m_Box[index] = value;}
protected: protected:
fixed_t m_Box[4]; fixed_t m_Box[4];
}; };

View file

@ -451,7 +451,7 @@ static void DoGiveInv (AActor *actor, const PClass *info, int amount)
} }
// If the item was a weapon, don't bring it up automatically // If the item was a weapon, don't bring it up automatically
// unless the player was not already using a weapon. // unless the player was not already using a weapon.
if (savedPendingWeap != NULL && hadweap) if (savedPendingWeap != NULL && hadweap && actor->player != NULL)
{ {
actor->player->PendingWeapon = savedPendingWeap; actor->player->PendingWeapon = savedPendingWeap;
} }

View file

@ -3423,6 +3423,16 @@ void P_SetupLevel (char *lumpname, int position)
P_LoadThings (map); P_LoadThings (map);
else else
P_LoadThings2 (map); // [RH] Load Hexen-style things P_LoadThings2 (map); // [RH] Load Hexen-style things
if (ib_compatflags & BCOMPATF_SPECHITOVERFLOW)
{
// restoring the original behavior doesn't work so we have to patch the levels in other ways.
// Fortunately the only known level depending on this bug is Strain's MAP07 and that's easy to fix.
if (numlines == 1022)
{
lines[1021].flags &= ~ML_BLOCKING;
}
}
} }
else else
{ {

View file

@ -978,6 +978,8 @@ void APlayerPawn::ThrowPoisonBag ()
void APlayerPawn::GiveDefaultInventory () void APlayerPawn::GiveDefaultInventory ()
{ {
if (player == NULL) return;
// [GRB] Give inventory specified in DECORATE // [GRB] Give inventory specified in DECORATE
player->health = GetDefault ()->health; player->health = GetDefault ()->health;
@ -1033,13 +1035,20 @@ void APlayerPawn::GiveDefaultInventory ()
static_cast<AWeapon*>(item)->AmmoGive1 = static_cast<AWeapon*>(item)->AmmoGive1 =
static_cast<AWeapon*>(item)->AmmoGive2 = 0; static_cast<AWeapon*>(item)->AmmoGive2 = 0;
} }
if (!item->CallTryPickup(this)) AActor *check;
if (!item->CallTryPickup(this, &check))
{ {
if (check != this)
{
// Player was morphed. This is illegal at game start.
// This problem is only detectable when it's too late to do something about it...
I_Error("Cannot give morph items when starting a game");
}
item->Destroy (); item->Destroy ();
item = NULL; item = NULL;
} }
} }
if (item != NULL && item->IsKindOf (RUNTIME_CLASS (AWeapon)) && if (item != NULL && item->IsKindOf (RUNTIME_CLASS (AWeapon)) &&
static_cast<AWeapon*>(item)->CheckAmmo(AWeapon::EitherFire, false)) static_cast<AWeapon*>(item)->CheckAmmo(AWeapon::EitherFire, false))
{ {
player->ReadyWeapon = player->PendingWeapon = static_cast<AWeapon *> (item); player->ReadyWeapon = player->PendingWeapon = static_cast<AWeapon *> (item);

View file

@ -29,4 +29,34 @@ A80E7EE40E0D0C76A6FBD242BE29FE27 // map15
// What's really sad is that I got a separate bug report for this map // What's really sad is that I got a separate bug report for this map
// years ago, but nobody made mention of this problem back then. // years ago, but nobody made mention of this problem back then.
trace trace
useblocking
}
// mostly cosmetic (except AV MAP07 and MM2 MAP25)
0EECBF37B328C9CAAF20DED4949A4157 // Sudtic e2m6
4ACE0644883BDA0CBA254FA02C9ACF83 // Teutic e3m4
9F2BE080A33F775294BD78822456924E // Nukemine e1m4
CD31793D3A4B00231B124C0C23649644 // Strain map02
19094AEB53D12EFC8E0568424F659F11 // Strain map31
60733BDD1AA3F4B2262ADC79B2E1B5AB // Memento Mori map29
F84AB4557464A383E93F37CD3A82AC48 // MM2 map03
1497894956B3C8EBE8A240B7FDD99C6A // MM2 map25
941E4CB56EE4184E0B1ED43486AB0BBF // AV map07
{
shorttex
}
2FE901F659A16E58D7BCD7C30021C238 // AV map15
{
trace
}
9D50EBE17CEC78938C7A668DB0768611 // Strain map07: Make the exit accessible
{
spechitoverflow
}
96368EB950E33AF62EA6423434E3CEF7 // Hacx map17: There's some switches behind shootable covers in this level
{
useblocking
} }