27 changed files with 2572 additions and 2572 deletions
@ -1,154 +1,154 @@ |
|||||||
/**
|
/**
|
||||||
* @file animationinfo.cpp |
* @file animationinfo.cpp |
||||||
* |
* |
||||||
* Contains the core animation information and related logic |
* Contains the core animation information and related logic |
||||||
*/ |
*/ |
||||||
|
|
||||||
#include "animationinfo.h" |
#include "animationinfo.h" |
||||||
#include "appfat.h" |
#include "appfat.h" |
||||||
#include "nthread.h" |
#include "nthread.h" |
||||||
#include "utils/log.hpp" |
#include "utils/log.hpp" |
||||||
|
|
||||||
namespace devilution { |
namespace devilution { |
||||||
|
|
||||||
int AnimationInfo::GetFrameToUseForRendering() const |
int AnimationInfo::GetFrameToUseForRendering() const |
||||||
{ |
{ |
||||||
// Normal logic is used,
|
// Normal logic is used,
|
||||||
// - if no frame-skipping is required and so we have exactly one Animationframe per game tick
|
// - if no frame-skipping is required and so we have exactly one Animationframe per game tick
|
||||||
// or
|
// or
|
||||||
// - if we load from a savegame where the new variables are not stored (we don't want to break savegame compatiblity because of smoother rendering of one animation)
|
// - if we load from a savegame where the new variables are not stored (we don't want to break savegame compatiblity because of smoother rendering of one animation)
|
||||||
if (RelevantFramesForDistributing <= 0) |
if (RelevantFramesForDistributing <= 0) |
||||||
return CurrentFrame; |
return CurrentFrame; |
||||||
|
|
||||||
if (CurrentFrame > RelevantFramesForDistributing) |
if (CurrentFrame > RelevantFramesForDistributing) |
||||||
return CurrentFrame; |
return CurrentFrame; |
||||||
|
|
||||||
assert(TicksSinceSequenceStarted >= 0); |
assert(TicksSinceSequenceStarted >= 0); |
||||||
|
|
||||||
// we don't use the processed game ticks alone but also the fragtion of the next game tick (if a rendering happens between game ticks). This helps to smooth the animations.
|
// we don't use the processed game ticks alone but also the fragtion of the next game tick (if a rendering happens between game ticks). This helps to smooth the animations.
|
||||||
float totalTicksForCurrentAnimationSequence = gfProgressToNextGameTick + (float)TicksSinceSequenceStarted; |
float totalTicksForCurrentAnimationSequence = gfProgressToNextGameTick + (float)TicksSinceSequenceStarted; |
||||||
|
|
||||||
// 1 added for rounding reasons. float to int cast always truncate.
|
// 1 added for rounding reasons. float to int cast always truncate.
|
||||||
int absoluteAnimationFrame = 1 + (int)(totalTicksForCurrentAnimationSequence * TickModifier); |
int absoluteAnimationFrame = 1 + (int)(totalTicksForCurrentAnimationSequence * TickModifier); |
||||||
if (SkippedFramesFromPreviousAnimation > 0) { |
if (SkippedFramesFromPreviousAnimation > 0) { |
||||||
// absoluteAnimationFrames contains also the Frames from the previous Animation, so if we want to get the current Frame we have to remove them
|
// absoluteAnimationFrames contains also the Frames from the previous Animation, so if we want to get the current Frame we have to remove them
|
||||||
absoluteAnimationFrame -= SkippedFramesFromPreviousAnimation; |
absoluteAnimationFrame -= SkippedFramesFromPreviousAnimation; |
||||||
if (absoluteAnimationFrame <= 0) { |
if (absoluteAnimationFrame <= 0) { |
||||||
// We still display the remains of the previous Animation
|
// We still display the remains of the previous Animation
|
||||||
absoluteAnimationFrame = NumberOfFrames + absoluteAnimationFrame; |
absoluteAnimationFrame = NumberOfFrames + absoluteAnimationFrame; |
||||||
} |
} |
||||||
} else if (absoluteAnimationFrame > RelevantFramesForDistributing) { |
} else if (absoluteAnimationFrame > RelevantFramesForDistributing) { |
||||||
// this can happen if we are at the last frame and the next game tick is due (gfProgressToNextGameTick >= 1.0f)
|
// this can happen if we are at the last frame and the next game tick is due (gfProgressToNextGameTick >= 1.0f)
|
||||||
if (absoluteAnimationFrame > (RelevantFramesForDistributing + 1)) { |
if (absoluteAnimationFrame > (RelevantFramesForDistributing + 1)) { |
||||||
// we should never have +2 frames even if next game tick is due
|
// we should never have +2 frames even if next game tick is due
|
||||||
Log("GetFrameToUseForRendering: Calculated an invalid Animation Frame (Calculated {} MaxFrame {})", absoluteAnimationFrame, RelevantFramesForDistributing); |
Log("GetFrameToUseForRendering: Calculated an invalid Animation Frame (Calculated {} MaxFrame {})", absoluteAnimationFrame, RelevantFramesForDistributing); |
||||||
} |
} |
||||||
return RelevantFramesForDistributing; |
return RelevantFramesForDistributing; |
||||||
} |
} |
||||||
if (absoluteAnimationFrame <= 0) { |
if (absoluteAnimationFrame <= 0) { |
||||||
Log("GetFrameToUseForRendering: Calculated an invalid Animation Frame (Calculated {})", absoluteAnimationFrame); |
Log("GetFrameToUseForRendering: Calculated an invalid Animation Frame (Calculated {})", absoluteAnimationFrame); |
||||||
return 1; |
return 1; |
||||||
} |
} |
||||||
return absoluteAnimationFrame; |
return absoluteAnimationFrame; |
||||||
} |
} |
||||||
|
|
||||||
void AnimationInfo::SetNewAnimation(byte *pData, int numberOfFrames, int delayLen, AnimationDistributionFlags flags /*= AnimationDistributionFlags::None*/, int numSkippedFrames /*= 0*/, int distributeFramesBeforeFrame /*= 0*/) |
void AnimationInfo::SetNewAnimation(byte *pData, int numberOfFrames, int delayLen, AnimationDistributionFlags flags /*= AnimationDistributionFlags::None*/, int numSkippedFrames /*= 0*/, int distributeFramesBeforeFrame /*= 0*/) |
||||||
{ |
{ |
||||||
if ((flags & AnimationDistributionFlags::RepeatedAction) == AnimationDistributionFlags::RepeatedAction && distributeFramesBeforeFrame != 0 && NumberOfFrames == numberOfFrames && CurrentFrame >= distributeFramesBeforeFrame && CurrentFrame != NumberOfFrames) { |
if ((flags & AnimationDistributionFlags::RepeatedAction) == AnimationDistributionFlags::RepeatedAction && distributeFramesBeforeFrame != 0 && NumberOfFrames == numberOfFrames && CurrentFrame >= distributeFramesBeforeFrame && CurrentFrame != NumberOfFrames) { |
||||||
// We showed the same Animation (for example a melee attack) before but truncated the Animation.
|
// We showed the same Animation (for example a melee attack) before but truncated the Animation.
|
||||||
// So now we should add them back to the new Animation. This increases the speed of the current Animation but the game logic/ticks isn't affected.
|
// So now we should add them back to the new Animation. This increases the speed of the current Animation but the game logic/ticks isn't affected.
|
||||||
SkippedFramesFromPreviousAnimation = NumberOfFrames - CurrentFrame; |
SkippedFramesFromPreviousAnimation = NumberOfFrames - CurrentFrame; |
||||||
} else { |
} else { |
||||||
SkippedFramesFromPreviousAnimation = 0; |
SkippedFramesFromPreviousAnimation = 0; |
||||||
} |
} |
||||||
|
|
||||||
this->pData = pData; |
this->pData = pData; |
||||||
NumberOfFrames = numberOfFrames; |
NumberOfFrames = numberOfFrames; |
||||||
CurrentFrame = 1; |
CurrentFrame = 1; |
||||||
DelayCounter = 0; |
DelayCounter = 0; |
||||||
DelayLen = delayLen; |
DelayLen = delayLen; |
||||||
TicksSinceSequenceStarted = 0; |
TicksSinceSequenceStarted = 0; |
||||||
RelevantFramesForDistributing = 0; |
RelevantFramesForDistributing = 0; |
||||||
TickModifier = 0.0f; |
TickModifier = 0.0f; |
||||||
|
|
||||||
if (numSkippedFrames != 0 || flags != AnimationDistributionFlags::None) { |
if (numSkippedFrames != 0 || flags != AnimationDistributionFlags::None) { |
||||||
// Animation Frames that will be adjusted for the skipped Frames/game ticks
|
// Animation Frames that will be adjusted for the skipped Frames/game ticks
|
||||||
int relevantAnimationFramesForDistributing = numberOfFrames; |
int relevantAnimationFramesForDistributing = numberOfFrames; |
||||||
if (distributeFramesBeforeFrame != 0) { |
if (distributeFramesBeforeFrame != 0) { |
||||||
// After an attack hits (_pAFNum or _pSFNum) it can be canceled or another attack can be queued and this means the animation is canceled.
|
// After an attack hits (_pAFNum or _pSFNum) it can be canceled or another attack can be queued and this means the animation is canceled.
|
||||||
// In normal attacks frame skipping always happens before the attack actual hit.
|
// In normal attacks frame skipping always happens before the attack actual hit.
|
||||||
// This has the advantage that the sword or bow always points to the enemy when the hit happens (_pAFNum or _pSFNum).
|
// This has the advantage that the sword or bow always points to the enemy when the hit happens (_pAFNum or _pSFNum).
|
||||||
// Our distribution logic must also regard this behaviour, so we are not allowed to distribute the skipped animations after the actual hit (_pAnimStopDistributingAfterFrame).
|
// Our distribution logic must also regard this behaviour, so we are not allowed to distribute the skipped animations after the actual hit (_pAnimStopDistributingAfterFrame).
|
||||||
relevantAnimationFramesForDistributing = distributeFramesBeforeFrame - 1; |
relevantAnimationFramesForDistributing = distributeFramesBeforeFrame - 1; |
||||||
} |
} |
||||||
|
|
||||||
// How many game ticks are needed to advance one Animation Frame
|
// How many game ticks are needed to advance one Animation Frame
|
||||||
int ticksPerFrame = (delayLen + 1); |
int ticksPerFrame = (delayLen + 1); |
||||||
|
|
||||||
// Game ticks that will be adjusted for the skipped Frames/game ticks
|
// Game ticks that will be adjusted for the skipped Frames/game ticks
|
||||||
int relevantAnimationTicksForDistribution = relevantAnimationFramesForDistributing * ticksPerFrame; |
int relevantAnimationTicksForDistribution = relevantAnimationFramesForDistributing * ticksPerFrame; |
||||||
|
|
||||||
// How many game ticks will the Animation be really shown (skipped Frames and game ticks removed)
|
// How many game ticks will the Animation be really shown (skipped Frames and game ticks removed)
|
||||||
int relevantAnimationTicksWithSkipping = relevantAnimationTicksForDistribution - (numSkippedFrames * ticksPerFrame); |
int relevantAnimationTicksWithSkipping = relevantAnimationTicksForDistribution - (numSkippedFrames * ticksPerFrame); |
||||||
|
|
||||||
if ((flags & AnimationDistributionFlags::ProcessAnimationPending) == AnimationDistributionFlags::ProcessAnimationPending) { |
if ((flags & AnimationDistributionFlags::ProcessAnimationPending) == AnimationDistributionFlags::ProcessAnimationPending) { |
||||||
// If ProcessAnimation will be called after SetNewAnimation (in same game tick as SetNewAnimation), we increment the Animation-Counter.
|
// If ProcessAnimation will be called after SetNewAnimation (in same game tick as SetNewAnimation), we increment the Animation-Counter.
|
||||||
// If no delay is specified, this will result in complete skipped frame (see ProcessAnimation).
|
// If no delay is specified, this will result in complete skipped frame (see ProcessAnimation).
|
||||||
// But if we have a delay specified, this would only result in a reduced time the first frame is shown (one skipped delay).
|
// But if we have a delay specified, this would only result in a reduced time the first frame is shown (one skipped delay).
|
||||||
// Because of that, we only the remove one game tick from the time the Animation is shown
|
// Because of that, we only the remove one game tick from the time the Animation is shown
|
||||||
relevantAnimationTicksWithSkipping -= 1; |
relevantAnimationTicksWithSkipping -= 1; |
||||||
// The Animation Distribution Logic needs to account how many game ticks passed since the Animation started.
|
// The Animation Distribution Logic needs to account how many game ticks passed since the Animation started.
|
||||||
// Because ProcessAnimation will increase this later (in same game tick as SetNewAnimation), we correct this upfront.
|
// Because ProcessAnimation will increase this later (in same game tick as SetNewAnimation), we correct this upfront.
|
||||||
// This also means Rendering should never hapen with TicksSinceSequenceStarted < 0.
|
// This also means Rendering should never hapen with TicksSinceSequenceStarted < 0.
|
||||||
TicksSinceSequenceStarted = -1; |
TicksSinceSequenceStarted = -1; |
||||||
} |
} |
||||||
|
|
||||||
if ((flags & AnimationDistributionFlags::SkipsDelayOfLastFrame) == AnimationDistributionFlags::SkipsDelayOfLastFrame) { |
if ((flags & AnimationDistributionFlags::SkipsDelayOfLastFrame) == AnimationDistributionFlags::SkipsDelayOfLastFrame) { |
||||||
// The logic for player/monster/... (not ProcessAnimation) only checks the frame not the delay.
|
// The logic for player/monster/... (not ProcessAnimation) only checks the frame not the delay.
|
||||||
// That means if a delay is specified, the last-frame is shown less then the other frames
|
// That means if a delay is specified, the last-frame is shown less then the other frames
|
||||||
// Example:
|
// Example:
|
||||||
// If we have a animation with 3 frames and with a delay of 1 (ticksPerFrame = 2).
|
// If we have a animation with 3 frames and with a delay of 1 (ticksPerFrame = 2).
|
||||||
// The logic checks "if (frame == 3) { start_new_animation(); }"
|
// The logic checks "if (frame == 3) { start_new_animation(); }"
|
||||||
// This will result that frame 4 is the last shown Animation Frame.
|
// This will result that frame 4 is the last shown Animation Frame.
|
||||||
// GameTick Frame Cnt
|
// GameTick Frame Cnt
|
||||||
// 1 1 0
|
// 1 1 0
|
||||||
// 2 1 1
|
// 2 1 1
|
||||||
// 3 2 0
|
// 3 2 0
|
||||||
// 3 2 1
|
// 3 2 1
|
||||||
// 4 3 0
|
// 4 3 0
|
||||||
// 5 - -
|
// 5 - -
|
||||||
// in game tick 5 ProcessPlayer sees Frame = 3 and stops the animation.
|
// in game tick 5 ProcessPlayer sees Frame = 3 and stops the animation.
|
||||||
// But Frame 3 is only shown 1 game tick and all other Frames are shown 2 game ticks.
|
// But Frame 3 is only shown 1 game tick and all other Frames are shown 2 game ticks.
|
||||||
// Thats why we need to remove the Delay of the last Frame from the time (game ticks) the Animation is shown
|
// Thats why we need to remove the Delay of the last Frame from the time (game ticks) the Animation is shown
|
||||||
relevantAnimationTicksWithSkipping -= delayLen; |
relevantAnimationTicksWithSkipping -= delayLen; |
||||||
} |
} |
||||||
|
|
||||||
// The truncated Frames from previous Animation will also be shown, so we also have to distribute them for the given time (game ticks)
|
// The truncated Frames from previous Animation will also be shown, so we also have to distribute them for the given time (game ticks)
|
||||||
relevantAnimationTicksForDistribution += (SkippedFramesFromPreviousAnimation * ticksPerFrame); |
relevantAnimationTicksForDistribution += (SkippedFramesFromPreviousAnimation * ticksPerFrame); |
||||||
|
|
||||||
// if we skipped Frames we need to expand the game ticks to make one game tick for this Animation "faster"
|
// if we skipped Frames we need to expand the game ticks to make one game tick for this Animation "faster"
|
||||||
float tickModifier = (float)relevantAnimationTicksForDistribution / (float)relevantAnimationTicksWithSkipping; |
float tickModifier = (float)relevantAnimationTicksForDistribution / (float)relevantAnimationTicksWithSkipping; |
||||||
|
|
||||||
// tickModifier specifies the Animation fraction per game tick, so we have to remove the delay from the variable
|
// tickModifier specifies the Animation fraction per game tick, so we have to remove the delay from the variable
|
||||||
tickModifier /= ticksPerFrame; |
tickModifier /= ticksPerFrame; |
||||||
|
|
||||||
RelevantFramesForDistributing = relevantAnimationFramesForDistributing; |
RelevantFramesForDistributing = relevantAnimationFramesForDistributing; |
||||||
TickModifier = tickModifier; |
TickModifier = tickModifier; |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
void AnimationInfo::ProcessAnimation() |
void AnimationInfo::ProcessAnimation() |
||||||
{ |
{ |
||||||
DelayCounter++; |
DelayCounter++; |
||||||
TicksSinceSequenceStarted++; |
TicksSinceSequenceStarted++; |
||||||
if (DelayCounter > DelayLen) { |
if (DelayCounter > DelayLen) { |
||||||
DelayCounter = 0; |
DelayCounter = 0; |
||||||
CurrentFrame++; |
CurrentFrame++; |
||||||
if (CurrentFrame > NumberOfFrames) { |
if (CurrentFrame > NumberOfFrames) { |
||||||
CurrentFrame = 1; |
CurrentFrame = 1; |
||||||
TicksSinceSequenceStarted = 0; |
TicksSinceSequenceStarted = 0; |
||||||
} |
} |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
} // namespace devilution
|
} // namespace devilution
|
||||||
|
|||||||
@ -1,101 +1,101 @@ |
|||||||
/**
|
/**
|
||||||
* @file animationinfo.h |
* @file animationinfo.h |
||||||
* |
* |
||||||
* Contains the core animation information and related logic |
* Contains the core animation information and related logic |
||||||
*/ |
*/ |
||||||
#pragma once |
#pragma once |
||||||
|
|
||||||
#include <stdint.h> |
#include <stdint.h> |
||||||
#include <type_traits> |
#include <type_traits> |
||||||
|
|
||||||
#include "engine.h" |
#include "engine.h" |
||||||
|
|
||||||
namespace devilution { |
namespace devilution { |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Specifies what special logics are applied for a Animation |
* @brief Specifies what special logics are applied for a Animation |
||||||
*/ |
*/ |
||||||
enum AnimationDistributionFlags : uint8_t { |
enum AnimationDistributionFlags : uint8_t { |
||||||
None = 0, |
None = 0, |
||||||
/**
|
/**
|
||||||
* @brief ProcessAnimation will be called after SetNewAnimation (in same game tick as NewPlrAnim) |
* @brief ProcessAnimation will be called after SetNewAnimation (in same game tick as NewPlrAnim) |
||||||
*/ |
*/ |
||||||
ProcessAnimationPending = 1 << 0, |
ProcessAnimationPending = 1 << 0, |
||||||
/**
|
/**
|
||||||
* @brief Delay of last Frame is ignored (for example, because only Frame and not delay is checked in game_logic) |
* @brief Delay of last Frame is ignored (for example, because only Frame and not delay is checked in game_logic) |
||||||
*/ |
*/ |
||||||
SkipsDelayOfLastFrame = 1 << 1, |
SkipsDelayOfLastFrame = 1 << 1, |
||||||
/**
|
/**
|
||||||
* @brief Repeated Animation (for example same player melee attack, that can be repeated directly after hit frame and doesn't need to show all animation frames) |
* @brief Repeated Animation (for example same player melee attack, that can be repeated directly after hit frame and doesn't need to show all animation frames) |
||||||
*/ |
*/ |
||||||
RepeatedAction = 1 << 2, |
RepeatedAction = 1 << 2, |
||||||
}; |
}; |
||||||
|
|
||||||
/*
|
/*
|
||||||
* @brief Contains the core animation information and related logic |
* @brief Contains the core animation information and related logic |
||||||
*/ |
*/ |
||||||
class AnimationInfo { |
class AnimationInfo { |
||||||
public: |
public: |
||||||
/**
|
/**
|
||||||
* @brief Pointer to Animation Data |
* @brief Pointer to Animation Data |
||||||
*/ |
*/ |
||||||
byte *pData; |
byte *pData; |
||||||
/**
|
/**
|
||||||
* @brief Additional delay of each animation in the current animation |
* @brief Additional delay of each animation in the current animation |
||||||
*/ |
*/ |
||||||
int DelayLen; |
int DelayLen; |
||||||
/**
|
/**
|
||||||
* @brief Increases by one each game tick, counting how close we are to DelayLen |
* @brief Increases by one each game tick, counting how close we are to DelayLen |
||||||
*/ |
*/ |
||||||
int DelayCounter; |
int DelayCounter; |
||||||
/**
|
/**
|
||||||
* @brief Number of frames in current animation |
* @brief Number of frames in current animation |
||||||
*/ |
*/ |
||||||
int NumberOfFrames; |
int NumberOfFrames; |
||||||
/**
|
/**
|
||||||
* @brief Current frame of animation |
* @brief Current frame of animation |
||||||
*/ |
*/ |
||||||
int CurrentFrame; |
int CurrentFrame; |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Calculates the Frame to use for the Animation rendering |
* @brief Calculates the Frame to use for the Animation rendering |
||||||
* @return The Frame to use for rendering |
* @return The Frame to use for rendering |
||||||
*/ |
*/ |
||||||
int GetFrameToUseForRendering() const; |
int GetFrameToUseForRendering() const; |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Sets the new Animation with all relevant information for rendering |
* @brief Sets the new Animation with all relevant information for rendering |
||||||
* @param pData Pointer to Animation Data |
* @param pData Pointer to Animation Data |
||||||
* @param numberOfFrames Number of Frames in Animation |
* @param numberOfFrames Number of Frames in Animation |
||||||
* @param delayLen Delay after each Animation sequence |
* @param delayLen Delay after each Animation sequence |
||||||
* @param flags Specifies what special logics are applied to this Animation |
* @param flags Specifies what special logics are applied to this Animation |
||||||
* @param numSkippedFrames Number of Frames that will be skipped (for example with modifier "faster attack") |
* @param numSkippedFrames Number of Frames that will be skipped (for example with modifier "faster attack") |
||||||
* @param distributeFramesBeforeFrame Distribute the numSkippedFrames only before this frame |
* @param distributeFramesBeforeFrame Distribute the numSkippedFrames only before this frame |
||||||
*/ |
*/ |
||||||
void SetNewAnimation(byte *pData, int numberOfFrames, int delayLen, AnimationDistributionFlags flags = AnimationDistributionFlags::None, int numSkippedFrames = 0, int distributeFramesBeforeFrame = 0); |
void SetNewAnimation(byte *pData, int numberOfFrames, int delayLen, AnimationDistributionFlags flags = AnimationDistributionFlags::None, int numSkippedFrames = 0, int distributeFramesBeforeFrame = 0); |
||||||
|
|
||||||
/*
|
/*
|
||||||
* @brief Process the Animation for a game tick (for example advances the frame) |
* @brief Process the Animation for a game tick (for example advances the frame) |
||||||
*/ |
*/ |
||||||
void ProcessAnimation(); |
void ProcessAnimation(); |
||||||
|
|
||||||
private: |
private: |
||||||
/**
|
/**
|
||||||
* @brief Specifies how many animations-fractions are displayed between two game ticks. this can be > 0, if animations are skipped or < 0 if the same animation is shown in multiple times (delay specified). |
* @brief Specifies how many animations-fractions are displayed between two game ticks. this can be > 0, if animations are skipped or < 0 if the same animation is shown in multiple times (delay specified). |
||||||
*/ |
*/ |
||||||
float TickModifier; |
float TickModifier; |
||||||
/**
|
/**
|
||||||
* @brief Number of game ticks after the current animation sequence started |
* @brief Number of game ticks after the current animation sequence started |
||||||
*/ |
*/ |
||||||
int TicksSinceSequenceStarted; |
int TicksSinceSequenceStarted; |
||||||
/**
|
/**
|
||||||
* @brief Animation Frames that will be adjusted for the skipped Frames/game ticks |
* @brief Animation Frames that will be adjusted for the skipped Frames/game ticks |
||||||
*/ |
*/ |
||||||
int RelevantFramesForDistributing; |
int RelevantFramesForDistributing; |
||||||
/**
|
/**
|
||||||
* @brief Animation Frames that wasn't shown from previous Animation |
* @brief Animation Frames that wasn't shown from previous Animation |
||||||
*/ |
*/ |
||||||
int SkippedFramesFromPreviousAnimation; |
int SkippedFramesFromPreviousAnimation; |
||||||
}; |
}; |
||||||
|
|
||||||
} // namespace devilution
|
} // namespace devilution
|
||||||
|
|||||||
@ -1,5 +1,5 @@ |
|||||||
#pragma once |
#pragma once |
||||||
|
|
||||||
void DvlNet_SendInfoRequest(); |
void DvlNet_SendInfoRequest(); |
||||||
std::vector<std::string> DvlNet_GetGamelist(); |
std::vector<std::string> DvlNet_GetGamelist(); |
||||||
void DvlNet_SetPassword(std::string pw); |
void DvlNet_SetPassword(std::string pw); |
||||||
|
|||||||
@ -1,73 +1,73 @@ |
|||||||
/**
|
/**
|
||||||
* @file math.h |
* @file math.h |
||||||
* |
* |
||||||
* Math utility functions |
* Math utility functions |
||||||
*/ |
*/ |
||||||
#pragma once |
#pragma once |
||||||
|
|
||||||
namespace devilution { |
namespace devilution { |
||||||
namespace math { |
namespace math { |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Compute sign of t |
* @brief Compute sign of t |
||||||
* @tparam T Any arithmetic type |
* @tparam T Any arithmetic type |
||||||
* @param t Value to compute sign of |
* @param t Value to compute sign of |
||||||
* @return -1 if t < 0, 1 if t > 0, 0 if t == 0 |
* @return -1 if t < 0, 1 if t > 0, 0 if t == 0 |
||||||
*/ |
*/ |
||||||
template <typename T> |
template <typename T> |
||||||
int Sign(T t) |
int Sign(T t) |
||||||
{ |
{ |
||||||
return (t > T(0)) - (t < T(0)); |
return (t > T(0)) - (t < T(0)); |
||||||
} |
} |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Linearly interpolate from a towards b using mixing value t |
* @brief Linearly interpolate from a towards b using mixing value t |
||||||
* @tparam V Any arithmetic type, used for interpolants and return value |
* @tparam V Any arithmetic type, used for interpolants and return value |
||||||
* @tparam T Any arithmetic type, used for interpolator |
* @tparam T Any arithmetic type, used for interpolator |
||||||
* @param a Low interpolation value (returned when t == 0) |
* @param a Low interpolation value (returned when t == 0) |
||||||
* @param b High interpolation value (returned when t == 1) |
* @param b High interpolation value (returned when t == 1) |
||||||
* @param t Interpolator, commonly in range [0..1], values outside this range will extrapolate |
* @param t Interpolator, commonly in range [0..1], values outside this range will extrapolate |
||||||
* @return a + (b - a) * t |
* @return a + (b - a) * t |
||||||
*/ |
*/ |
||||||
template <typename V, typename T> |
template <typename V, typename T> |
||||||
V Lerp(V a, V b, T t) |
V Lerp(V a, V b, T t) |
||||||
{ |
{ |
||||||
return a + (b - a) * t; |
return a + (b - a) * t; |
||||||
} |
} |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Inverse lerp, given two key values a and b, and a free value v, determine mixing factor t so that v = Lerp(a, b, t) |
* @brief Inverse lerp, given two key values a and b, and a free value v, determine mixing factor t so that v = Lerp(a, b, t) |
||||||
* @tparam T Any arithmetic type |
* @tparam T Any arithmetic type |
||||||
* @param a Low key value (function returns 0 if v == a) |
* @param a Low key value (function returns 0 if v == a) |
||||||
* @param b High key value (function returns 1 if v == b) |
* @param b High key value (function returns 1 if v == b) |
||||||
* @param v Mixing factor, commonly in range [a..b] to get a return [0..1] |
* @param v Mixing factor, commonly in range [a..b] to get a return [0..1] |
||||||
* @return Value t so that v = Lerp(a, b, t); or 0 if b == a |
* @return Value t so that v = Lerp(a, b, t); or 0 if b == a |
||||||
*/ |
*/ |
||||||
template <typename T> |
template <typename T> |
||||||
T InvLerp(T a, T b, T v) |
T InvLerp(T a, T b, T v) |
||||||
{ |
{ |
||||||
if (b == a) |
if (b == a) |
||||||
return T(0); |
return T(0); |
||||||
|
|
||||||
return (v - a) / (b - a); |
return (v - a) / (b - a); |
||||||
} |
} |
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Remaps value v from range [inMin, inMax] to [outMin, outMax] |
* @brief Remaps value v from range [inMin, inMax] to [outMin, outMax] |
||||||
* @tparam T Any arithmetic type |
* @tparam T Any arithmetic type |
||||||
* @param inMin First bound of input range |
* @param inMin First bound of input range |
||||||
* @param inMax Second bound of input range |
* @param inMax Second bound of input range |
||||||
* @param outMin First bound of output range |
* @param outMin First bound of output range |
||||||
* @param outMax Second bound of output range |
* @param outMax Second bound of output range |
||||||
* @param v Value to remap |
* @param v Value to remap |
||||||
* @return Transformed value so that InvLerp(inMin, inMax, v) == InvLerp(outMin, outMax, return) |
* @return Transformed value so that InvLerp(inMin, inMax, v) == InvLerp(outMin, outMax, return) |
||||||
*/ |
*/ |
||||||
template <typename T> |
template <typename T> |
||||||
T Remap(T inMin, T inMax, T outMin, T outMax, T v) |
T Remap(T inMin, T inMax, T outMin, T outMax, T v) |
||||||
{ |
{ |
||||||
auto t = InvLerp(inMin, inMax, v); |
auto t = InvLerp(inMin, inMax, v); |
||||||
return Lerp(outMin, outMax, t); |
return Lerp(outMin, outMax, t); |
||||||
} |
} |
||||||
|
|
||||||
} // namespace math
|
} // namespace math
|
||||||
} // namespace devilution
|
} // namespace devilution
|
||||||
|
|||||||
@ -1,19 +1,19 @@ |
|||||||
#pragma once |
#pragma once |
||||||
|
|
||||||
#ifdef __has_include |
#ifdef __has_include |
||||||
#if defined(__cplusplus) && __cplusplus >= 201703L && __has_include(<string_view>) // should be 201606L, but STL headers disagree
|
#if defined(__cplusplus) && __cplusplus >= 201703L && __has_include(<string_view>) // should be 201606L, but STL headers disagree
|
||||||
#include <string_view> // IWYU pragma: export |
#include <string_view> // IWYU pragma: export |
||||||
namespace devilution { |
namespace devilution { |
||||||
using string_view = std::string_view; |
using string_view = std::string_view; |
||||||
} |
} |
||||||
#elif __has_include(<experimental/string_view>) |
#elif __has_include(<experimental/string_view>) |
||||||
#include <experimental/string_view> // IWYU pragma: export |
#include <experimental/string_view> // IWYU pragma: export |
||||||
namespace devilution { |
namespace devilution { |
||||||
using string_view = std::experimental::string_view; |
using string_view = std::experimental::string_view; |
||||||
} |
} |
||||||
#else |
#else |
||||||
#error "Missing support for <string_view> or <experimental/string_view>" |
#error "Missing support for <string_view> or <experimental/string_view>" |
||||||
#endif |
#endif |
||||||
#else |
#else |
||||||
#error "__has_include unavailable" |
#error "__has_include unavailable" |
||||||
#endif |
#endif |
||||||
|
|||||||
@ -1,31 +1,31 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "appfat.h" |
#include "appfat.h" |
||||||
#include "diablo.h" |
#include "diablo.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Appfat, app_fatal) |
TEST(Appfat, app_fatal) |
||||||
{ |
{ |
||||||
EXPECT_EXIT(app_fatal("test"), ::testing::ExitedWithCode(1), "test"); |
EXPECT_EXIT(app_fatal("test"), ::testing::ExitedWithCode(1), "test"); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Appfat, ErrDlg) |
TEST(Appfat, ErrDlg) |
||||||
{ |
{ |
||||||
EXPECT_EXIT(ErrDlg("Title", "Unknown error", "appfat.cpp", 7), ::testing::ExitedWithCode(1), "Unknown error\n\nThe error occurred at: appfat.cpp line 7"); |
EXPECT_EXIT(ErrDlg("Title", "Unknown error", "appfat.cpp", 7), ::testing::ExitedWithCode(1), "Unknown error\n\nThe error occurred at: appfat.cpp line 7"); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Appfat, FileErrDlg) |
TEST(Appfat, FileErrDlg) |
||||||
{ |
{ |
||||||
EXPECT_EXIT(FileErrDlg("devilution/image.cl2"), ::testing::ExitedWithCode(1), "devilution/image.cl2"); |
EXPECT_EXIT(FileErrDlg("devilution/image.cl2"), ::testing::ExitedWithCode(1), "devilution/image.cl2"); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Appfat, InsertCDDlg) |
TEST(Appfat, InsertCDDlg) |
||||||
{ |
{ |
||||||
EXPECT_EXIT(InsertCDDlg(), ::testing::ExitedWithCode(1), "diabdat.mpq"); |
EXPECT_EXIT(InsertCDDlg(), ::testing::ExitedWithCode(1), "diabdat.mpq"); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Appfat, DirErrorDlg) |
TEST(Appfat, DirErrorDlg) |
||||||
{ |
{ |
||||||
EXPECT_EXIT(DirErrorDlg("/"), ::testing::ExitedWithCode(1), "Unable to write to location:\n/"); |
EXPECT_EXIT(DirErrorDlg("/"), ::testing::ExitedWithCode(1), "Unable to write to location:\n/"); |
||||||
} |
} |
||||||
|
|||||||
@ -1,127 +1,127 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "automap.h" |
#include "automap.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Automap, InitAutomap) |
TEST(Automap, InitAutomap) |
||||||
{ |
{ |
||||||
InitAutomapOnce(); |
InitAutomapOnce(); |
||||||
EXPECT_EQ(AutomapActive, false); |
EXPECT_EQ(AutomapActive, false); |
||||||
EXPECT_EQ(AutoMapScale, 50); |
EXPECT_EQ(AutoMapScale, 50); |
||||||
EXPECT_EQ(AmLine64, 32); |
EXPECT_EQ(AmLine64, 32); |
||||||
EXPECT_EQ(AmLine32, 16); |
EXPECT_EQ(AmLine32, 16); |
||||||
EXPECT_EQ(AmLine16, 8); |
EXPECT_EQ(AmLine16, 8); |
||||||
EXPECT_EQ(AmLine8, 4); |
EXPECT_EQ(AmLine8, 4); |
||||||
EXPECT_EQ(AmLine4, 2); |
EXPECT_EQ(AmLine4, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, StartAutomap) |
TEST(Automap, StartAutomap) |
||||||
{ |
{ |
||||||
StartAutomap(); |
StartAutomap(); |
||||||
EXPECT_EQ(AutomapOffset.x, 0); |
EXPECT_EQ(AutomapOffset.x, 0); |
||||||
EXPECT_EQ(AutomapOffset.y, 0); |
EXPECT_EQ(AutomapOffset.y, 0); |
||||||
EXPECT_EQ(AutomapActive, true); |
EXPECT_EQ(AutomapActive, true); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapUp) |
TEST(Automap, AutomapUp) |
||||||
{ |
{ |
||||||
AutomapOffset.x = 1; |
AutomapOffset.x = 1; |
||||||
AutomapOffset.y = 1; |
AutomapOffset.y = 1; |
||||||
AutomapUp(); |
AutomapUp(); |
||||||
EXPECT_EQ(AutomapOffset.x, 0); |
EXPECT_EQ(AutomapOffset.x, 0); |
||||||
EXPECT_EQ(AutomapOffset.y, 0); |
EXPECT_EQ(AutomapOffset.y, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapDown) |
TEST(Automap, AutomapDown) |
||||||
{ |
{ |
||||||
AutomapOffset.x = 1; |
AutomapOffset.x = 1; |
||||||
AutomapOffset.y = 1; |
AutomapOffset.y = 1; |
||||||
AutomapDown(); |
AutomapDown(); |
||||||
EXPECT_EQ(AutomapOffset.x, 2); |
EXPECT_EQ(AutomapOffset.x, 2); |
||||||
EXPECT_EQ(AutomapOffset.y, 2); |
EXPECT_EQ(AutomapOffset.y, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapLeft) |
TEST(Automap, AutomapLeft) |
||||||
{ |
{ |
||||||
AutomapOffset.x = 1; |
AutomapOffset.x = 1; |
||||||
AutomapOffset.y = 1; |
AutomapOffset.y = 1; |
||||||
AutomapLeft(); |
AutomapLeft(); |
||||||
EXPECT_EQ(AutomapOffset.x, 0); |
EXPECT_EQ(AutomapOffset.x, 0); |
||||||
EXPECT_EQ(AutomapOffset.y, 2); |
EXPECT_EQ(AutomapOffset.y, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapRight) |
TEST(Automap, AutomapRight) |
||||||
{ |
{ |
||||||
AutomapOffset.x = 1; |
AutomapOffset.x = 1; |
||||||
AutomapOffset.y = 1; |
AutomapOffset.y = 1; |
||||||
AutomapRight(); |
AutomapRight(); |
||||||
EXPECT_EQ(AutomapOffset.x, 2); |
EXPECT_EQ(AutomapOffset.x, 2); |
||||||
EXPECT_EQ(AutomapOffset.y, 0); |
EXPECT_EQ(AutomapOffset.y, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapZoomIn) |
TEST(Automap, AutomapZoomIn) |
||||||
{ |
{ |
||||||
AutoMapScale = 50; |
AutoMapScale = 50; |
||||||
AutomapZoomIn(); |
AutomapZoomIn(); |
||||||
EXPECT_EQ(AutoMapScale, 55); |
EXPECT_EQ(AutoMapScale, 55); |
||||||
EXPECT_EQ(AmLine64, 35); |
EXPECT_EQ(AmLine64, 35); |
||||||
EXPECT_EQ(AmLine32, 17); |
EXPECT_EQ(AmLine32, 17); |
||||||
EXPECT_EQ(AmLine16, 8); |
EXPECT_EQ(AmLine16, 8); |
||||||
EXPECT_EQ(AmLine8, 4); |
EXPECT_EQ(AmLine8, 4); |
||||||
EXPECT_EQ(AmLine4, 2); |
EXPECT_EQ(AmLine4, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapZoomIn_Max) |
TEST(Automap, AutomapZoomIn_Max) |
||||||
{ |
{ |
||||||
AutoMapScale = 195; |
AutoMapScale = 195; |
||||||
AutomapZoomIn(); |
AutomapZoomIn(); |
||||||
AutomapZoomIn(); |
AutomapZoomIn(); |
||||||
EXPECT_EQ(AutoMapScale, 200); |
EXPECT_EQ(AutoMapScale, 200); |
||||||
EXPECT_EQ(AmLine64, 128); |
EXPECT_EQ(AmLine64, 128); |
||||||
EXPECT_EQ(AmLine32, 64); |
EXPECT_EQ(AmLine32, 64); |
||||||
EXPECT_EQ(AmLine16, 32); |
EXPECT_EQ(AmLine16, 32); |
||||||
EXPECT_EQ(AmLine8, 16); |
EXPECT_EQ(AmLine8, 16); |
||||||
EXPECT_EQ(AmLine4, 8); |
EXPECT_EQ(AmLine4, 8); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapZoomOut) |
TEST(Automap, AutomapZoomOut) |
||||||
{ |
{ |
||||||
AutoMapScale = 200; |
AutoMapScale = 200; |
||||||
AutomapZoomOut(); |
AutomapZoomOut(); |
||||||
EXPECT_EQ(AutoMapScale, 195); |
EXPECT_EQ(AutoMapScale, 195); |
||||||
EXPECT_EQ(AmLine64, 124); |
EXPECT_EQ(AmLine64, 124); |
||||||
EXPECT_EQ(AmLine32, 62); |
EXPECT_EQ(AmLine32, 62); |
||||||
EXPECT_EQ(AmLine16, 31); |
EXPECT_EQ(AmLine16, 31); |
||||||
EXPECT_EQ(AmLine8, 15); |
EXPECT_EQ(AmLine8, 15); |
||||||
EXPECT_EQ(AmLine4, 7); |
EXPECT_EQ(AmLine4, 7); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapZoomOut_Min) |
TEST(Automap, AutomapZoomOut_Min) |
||||||
{ |
{ |
||||||
AutoMapScale = 55; |
AutoMapScale = 55; |
||||||
AutomapZoomOut(); |
AutomapZoomOut(); |
||||||
AutomapZoomOut(); |
AutomapZoomOut(); |
||||||
EXPECT_EQ(AutoMapScale, 50); |
EXPECT_EQ(AutoMapScale, 50); |
||||||
EXPECT_EQ(AmLine64, 32); |
EXPECT_EQ(AmLine64, 32); |
||||||
EXPECT_EQ(AmLine32, 16); |
EXPECT_EQ(AmLine32, 16); |
||||||
EXPECT_EQ(AmLine16, 8); |
EXPECT_EQ(AmLine16, 8); |
||||||
EXPECT_EQ(AmLine8, 4); |
EXPECT_EQ(AmLine8, 4); |
||||||
EXPECT_EQ(AmLine4, 2); |
EXPECT_EQ(AmLine4, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Automap, AutomapZoomReset) |
TEST(Automap, AutomapZoomReset) |
||||||
{ |
{ |
||||||
AutoMapScale = 50; |
AutoMapScale = 50; |
||||||
AutomapOffset.x = 1; |
AutomapOffset.x = 1; |
||||||
AutomapOffset.y = 1; |
AutomapOffset.y = 1; |
||||||
AutomapZoomReset(); |
AutomapZoomReset(); |
||||||
EXPECT_EQ(AutomapOffset.x, 0); |
EXPECT_EQ(AutomapOffset.x, 0); |
||||||
EXPECT_EQ(AutomapOffset.y, 0); |
EXPECT_EQ(AutomapOffset.y, 0); |
||||||
EXPECT_EQ(AutoMapScale, 50); |
EXPECT_EQ(AutoMapScale, 50); |
||||||
EXPECT_EQ(AmLine64, 32); |
EXPECT_EQ(AmLine64, 32); |
||||||
EXPECT_EQ(AmLine32, 16); |
EXPECT_EQ(AmLine32, 16); |
||||||
EXPECT_EQ(AmLine16, 8); |
EXPECT_EQ(AmLine16, 8); |
||||||
EXPECT_EQ(AmLine8, 4); |
EXPECT_EQ(AmLine8, 4); |
||||||
EXPECT_EQ(AmLine4, 2); |
EXPECT_EQ(AmLine4, 2); |
||||||
} |
} |
||||||
|
|||||||
@ -1,15 +1,15 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "codec.h" |
#include "codec.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Codec, codec_get_encoded_len) |
TEST(Codec, codec_get_encoded_len) |
||||||
{ |
{ |
||||||
EXPECT_EQ(codec_get_encoded_len(50), 72); |
EXPECT_EQ(codec_get_encoded_len(50), 72); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Codec, codec_get_encoded_len_eq) |
TEST(Codec, codec_get_encoded_len_eq) |
||||||
{ |
{ |
||||||
EXPECT_EQ(codec_get_encoded_len(128), 136); |
EXPECT_EQ(codec_get_encoded_len(128), 136); |
||||||
} |
} |
||||||
|
|||||||
@ -1,29 +1,29 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "control.h" |
#include "control.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Control, SetSpell) |
TEST(Control, SetSpell) |
||||||
{ |
{ |
||||||
pnumlines = 1; |
pnumlines = 1; |
||||||
pinfoflag = true; |
pinfoflag = true; |
||||||
pSpell = SPL_FIREBOLT; |
pSpell = SPL_FIREBOLT; |
||||||
pSplType = RSPLTYPE_CHARGES; |
pSplType = RSPLTYPE_CHARGES; |
||||||
SetSpell(); |
SetSpell(); |
||||||
EXPECT_EQ(spselflag, false); |
EXPECT_EQ(spselflag, false); |
||||||
EXPECT_EQ(plr[myplr]._pRSpell, SPL_FIREBOLT); |
EXPECT_EQ(plr[myplr]._pRSpell, SPL_FIREBOLT); |
||||||
EXPECT_EQ(plr[myplr]._pRSplType, RSPLTYPE_CHARGES); |
EXPECT_EQ(plr[myplr]._pRSplType, RSPLTYPE_CHARGES); |
||||||
EXPECT_EQ(pnumlines, 0); |
EXPECT_EQ(pnumlines, 0); |
||||||
EXPECT_EQ(pinfoflag, false); |
EXPECT_EQ(pinfoflag, false); |
||||||
EXPECT_EQ(force_redraw, 255); |
EXPECT_EQ(force_redraw, 255); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Control, ClearPanel) |
TEST(Control, ClearPanel) |
||||||
{ |
{ |
||||||
pnumlines = 1; |
pnumlines = 1; |
||||||
pinfoflag = true; |
pinfoflag = true; |
||||||
ClearPanel(); |
ClearPanel(); |
||||||
EXPECT_EQ(pnumlines, 0); |
EXPECT_EQ(pnumlines, 0); |
||||||
EXPECT_EQ(pinfoflag, false); |
EXPECT_EQ(pinfoflag, false); |
||||||
} |
} |
||||||
|
|||||||
@ -1,19 +1,19 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "cursor.h" |
#include "cursor.h" |
||||||
#include "itemdat.h" |
#include "itemdat.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Cursor, SetCursor) |
TEST(Cursor, SetCursor) |
||||||
{ |
{ |
||||||
int i = ICURS_SPIKED_CLUB + CURSOR_FIRSTITEM; |
int i = ICURS_SPIKED_CLUB + CURSOR_FIRSTITEM; |
||||||
NewCursor(i); |
NewCursor(i); |
||||||
EXPECT_EQ(pcurs, i); |
EXPECT_EQ(pcurs, i); |
||||||
EXPECT_EQ(cursW, 1 * 28); |
EXPECT_EQ(cursW, 1 * 28); |
||||||
EXPECT_EQ(cursH, 3 * 28); |
EXPECT_EQ(cursH, 3 * 28); |
||||||
EXPECT_EQ(icursW, 1 * 28); |
EXPECT_EQ(icursW, 1 * 28); |
||||||
EXPECT_EQ(icursH, 3 * 28); |
EXPECT_EQ(icursH, 3 * 28); |
||||||
EXPECT_EQ(icursW28, 1); |
EXPECT_EQ(icursW28, 1); |
||||||
EXPECT_EQ(icursH28, 3); |
EXPECT_EQ(icursH28, 3); |
||||||
} |
} |
||||||
|
|||||||
@ -1,19 +1,19 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "dead.h" |
#include "dead.h" |
||||||
#include "engine.h" |
#include "engine.h" |
||||||
#include "gendung.h" |
#include "gendung.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Dead, AddDead) |
TEST(Dead, AddDead) |
||||||
{ |
{ |
||||||
AddDead({21, 48}, 8, DIR_W); |
AddDead({21, 48}, 8, DIR_W); |
||||||
EXPECT_EQ(dDead[21][48], 8 + (DIR_W << 5)); |
EXPECT_EQ(dDead[21][48], 8 + (DIR_W << 5)); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Dead, AddDead_OOB) |
TEST(Dead, AddDead_OOB) |
||||||
{ |
{ |
||||||
AddDead({21, 48}, MaxDead + 1, DIR_W); |
AddDead({21, 48}, MaxDead + 1, DIR_W); |
||||||
EXPECT_EQ(dDead[21][48], 0 + (DIR_W << 5)); |
EXPECT_EQ(dDead[21][48], 0 + (DIR_W << 5)); |
||||||
} |
} |
||||||
|
|||||||
@ -1,14 +1,14 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "diablo.h" |
#include "diablo.h" |
||||||
#include "multi.h" |
#include "multi.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Diablo, diablo_pause_game_unpause) |
TEST(Diablo, diablo_pause_game_unpause) |
||||||
{ |
{ |
||||||
gbIsMultiplayer = false; |
gbIsMultiplayer = false; |
||||||
PauseMode = 1; |
PauseMode = 1; |
||||||
diablo_pause_game(); |
diablo_pause_game(); |
||||||
EXPECT_EQ(PauseMode, 0); |
EXPECT_EQ(PauseMode, 0); |
||||||
} |
} |
||||||
|
|||||||
@ -1,17 +1,17 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "doom.h" |
#include "doom.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Doom, doom_get_frame_from_time) |
TEST(Doom, doom_get_frame_from_time) |
||||||
{ |
{ |
||||||
DoomQuestState = 1200 * 8 + 548; |
DoomQuestState = 1200 * 8 + 548; |
||||||
EXPECT_EQ(doom_get_frame_from_time(), 8); |
EXPECT_EQ(doom_get_frame_from_time(), 8); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Doom, doom_get_frame_from_time_max) |
TEST(Doom, doom_get_frame_from_time_max) |
||||||
{ |
{ |
||||||
DoomQuestState = 1200 * 30 + 1; |
DoomQuestState = 1200 * 30 + 1; |
||||||
EXPECT_EQ(doom_get_frame_from_time(), 31); |
EXPECT_EQ(doom_get_frame_from_time(), 31); |
||||||
} |
} |
||||||
|
|||||||
@ -1,21 +1,21 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "diablo.h" |
#include "diablo.h" |
||||||
#include "drlg_l1.h" |
#include "drlg_l1.h" |
||||||
#include "lighting.h" |
#include "lighting.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Drlg_l1, DRLG_Init_Globals_noflag) |
TEST(Drlg_l1, DRLG_Init_Globals_noflag) |
||||||
{ |
{ |
||||||
lightflag = false; |
lightflag = false; |
||||||
DRLG_Init_Globals(); |
DRLG_Init_Globals(); |
||||||
EXPECT_EQ(dLight[0][0], 15); |
EXPECT_EQ(dLight[0][0], 15); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Drlg_l1, DRLG_Init_Globals) |
TEST(Drlg_l1, DRLG_Init_Globals) |
||||||
{ |
{ |
||||||
lightflag = true; |
lightflag = true; |
||||||
DRLG_Init_Globals(); |
DRLG_Init_Globals(); |
||||||
EXPECT_EQ(dLight[0][0], 0); |
EXPECT_EQ(dLight[0][0], 0); |
||||||
} |
} |
||||||
|
|||||||
@ -1,12 +1,12 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "drlg_l2.h" |
#include "drlg_l2.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Drlg_l2, InitDungeon) |
TEST(Drlg_l2, InitDungeon) |
||||||
{ |
{ |
||||||
InitDungeon(); |
InitDungeon(); |
||||||
EXPECT_EQ(predungeon[0][0], 32); |
EXPECT_EQ(predungeon[0][0], 32); |
||||||
EXPECT_EQ(dflags[0][0], 0); |
EXPECT_EQ(dflags[0][0], 0); |
||||||
} |
} |
||||||
|
|||||||
@ -1,35 +1,35 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "drlg_l3.h" |
#include "drlg_l3.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Drlg_l3, AddFenceDoors_x) |
TEST(Drlg_l3, AddFenceDoors_x) |
||||||
{ |
{ |
||||||
memset(dungeon, 0, sizeof(dungeon)); |
memset(dungeon, 0, sizeof(dungeon)); |
||||||
dungeon[5][5] = 7; |
dungeon[5][5] = 7; |
||||||
dungeon[5 - 1][5] = 130; |
dungeon[5 - 1][5] = 130; |
||||||
dungeon[5 + 1][5] = 152; |
dungeon[5 + 1][5] = 152; |
||||||
AddFenceDoors(); |
AddFenceDoors(); |
||||||
EXPECT_EQ(dungeon[5][5], 146); |
EXPECT_EQ(dungeon[5][5], 146); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Drlg_l3, AddFenceDoors_y) |
TEST(Drlg_l3, AddFenceDoors_y) |
||||||
{ |
{ |
||||||
memset(dungeon, 0, sizeof(dungeon)); |
memset(dungeon, 0, sizeof(dungeon)); |
||||||
dungeon[5][5] = 7; |
dungeon[5][5] = 7; |
||||||
dungeon[5][5 - 1] = 130; |
dungeon[5][5 - 1] = 130; |
||||||
dungeon[5][5 + 1] = 152; |
dungeon[5][5 + 1] = 152; |
||||||
AddFenceDoors(); |
AddFenceDoors(); |
||||||
EXPECT_EQ(dungeon[5][5], 147); |
EXPECT_EQ(dungeon[5][5], 147); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Drlg_l3, AddFenceDoors_no) |
TEST(Drlg_l3, AddFenceDoors_no) |
||||||
{ |
{ |
||||||
memset(dungeon, 0, sizeof(dungeon)); |
memset(dungeon, 0, sizeof(dungeon)); |
||||||
dungeon[5][5] = 7; |
dungeon[5][5] = 7; |
||||||
dungeon[5 - 1][5] = 130; |
dungeon[5 - 1][5] = 130; |
||||||
dungeon[5 + 1][5] = 153; |
dungeon[5 + 1][5] = 153; |
||||||
AddFenceDoors(); |
AddFenceDoors(); |
||||||
EXPECT_EQ(dungeon[5][5], 7); |
EXPECT_EQ(dungeon[5][5], 7); |
||||||
} |
} |
||||||
|
|||||||
@ -1,21 +1,21 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "drlg_l4.h" |
#include "drlg_l4.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Drlg_l4, IsDURWall) |
TEST(Drlg_l4, IsDURWall) |
||||||
{ |
{ |
||||||
EXPECT_EQ(IsDURWall(25), true); |
EXPECT_EQ(IsDURWall(25), true); |
||||||
EXPECT_EQ(IsDURWall(28), true); |
EXPECT_EQ(IsDURWall(28), true); |
||||||
EXPECT_EQ(IsDURWall(23), true); |
EXPECT_EQ(IsDURWall(23), true); |
||||||
EXPECT_EQ(IsDURWall(20), false); |
EXPECT_EQ(IsDURWall(20), false); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Drlg_l4, IsDLLWall) |
TEST(Drlg_l4, IsDLLWall) |
||||||
{ |
{ |
||||||
EXPECT_EQ(IsDLLWall(27), true); |
EXPECT_EQ(IsDLLWall(27), true); |
||||||
EXPECT_EQ(IsDLLWall(26), true); |
EXPECT_EQ(IsDLLWall(26), true); |
||||||
EXPECT_EQ(IsDLLWall(22), true); |
EXPECT_EQ(IsDLLWall(22), true); |
||||||
EXPECT_EQ(IsDLLWall(20), false); |
EXPECT_EQ(IsDLLWall(20), false); |
||||||
} |
} |
||||||
|
|||||||
@ -1,56 +1,56 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "effects.h" |
#include "effects.h" |
||||||
#include "player.h" |
#include "player.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Effects, calc_snd_position_center) |
TEST(Effects, calc_snd_position_center) |
||||||
{ |
{ |
||||||
plr[myplr].position.tile = { 50, 50 }; |
plr[myplr].position.tile = { 50, 50 }; |
||||||
int plVolume = 0; |
int plVolume = 0; |
||||||
int plPan = 0; |
int plPan = 0; |
||||||
EXPECT_EQ(calc_snd_position(50, 50, &plVolume, &plPan), true); |
EXPECT_EQ(calc_snd_position(50, 50, &plVolume, &plPan), true); |
||||||
EXPECT_EQ(plVolume, 0); |
EXPECT_EQ(plVolume, 0); |
||||||
EXPECT_EQ(plPan, 0); |
EXPECT_EQ(plPan, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Effects, calc_snd_position_near) |
TEST(Effects, calc_snd_position_near) |
||||||
{ |
{ |
||||||
plr[myplr].position.tile = { 50, 50 }; |
plr[myplr].position.tile = { 50, 50 }; |
||||||
int plVolume = 0; |
int plVolume = 0; |
||||||
int plPan = 0; |
int plPan = 0; |
||||||
EXPECT_EQ(calc_snd_position(55, 50, &plVolume, &plPan), true); |
EXPECT_EQ(calc_snd_position(55, 50, &plVolume, &plPan), true); |
||||||
EXPECT_EQ(plVolume, -320); |
EXPECT_EQ(plVolume, -320); |
||||||
EXPECT_EQ(plPan, 1280); |
EXPECT_EQ(plPan, 1280); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Effects, calc_snd_position_out_of_range) |
TEST(Effects, calc_snd_position_out_of_range) |
||||||
{ |
{ |
||||||
plr[myplr].position.tile = { 12, 12 }; |
plr[myplr].position.tile = { 12, 12 }; |
||||||
int plVolume = 1234; |
int plVolume = 1234; |
||||||
int plPan = 0; |
int plPan = 0; |
||||||
EXPECT_EQ(calc_snd_position(112, 112, &plVolume, &plPan), false); |
EXPECT_EQ(calc_snd_position(112, 112, &plVolume, &plPan), false); |
||||||
EXPECT_EQ(plVolume, 1234); |
EXPECT_EQ(plVolume, 1234); |
||||||
EXPECT_EQ(plPan, 0); |
EXPECT_EQ(plPan, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Effects, calc_snd_position_extreme_right) |
TEST(Effects, calc_snd_position_extreme_right) |
||||||
{ |
{ |
||||||
plr[myplr].position.tile = { 50, 50 }; |
plr[myplr].position.tile = { 50, 50 }; |
||||||
int plVolume = 0; |
int plVolume = 0; |
||||||
int plPan = 0; |
int plPan = 0; |
||||||
EXPECT_EQ(calc_snd_position(75, 25, &plVolume, &plPan), true); |
EXPECT_EQ(calc_snd_position(75, 25, &plVolume, &plPan), true); |
||||||
EXPECT_EQ(plVolume, -2176); |
EXPECT_EQ(plVolume, -2176); |
||||||
EXPECT_EQ(plPan, 6400); |
EXPECT_EQ(plPan, 6400); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Effects, calc_snd_position_extreme_left) |
TEST(Effects, calc_snd_position_extreme_left) |
||||||
{ |
{ |
||||||
plr[myplr].position.tile = { 50, 50 }; |
plr[myplr].position.tile = { 50, 50 }; |
||||||
int plVolume = 0; |
int plVolume = 0; |
||||||
int plPan = 0; |
int plPan = 0; |
||||||
EXPECT_EQ(calc_snd_position(25, 75, &plVolume, &plPan), true); |
EXPECT_EQ(calc_snd_position(25, 75, &plVolume, &plPan), true); |
||||||
EXPECT_EQ(plVolume, -2176); |
EXPECT_EQ(plVolume, -2176); |
||||||
EXPECT_EQ(plPan, -6400); |
EXPECT_EQ(plPan, -6400); |
||||||
} |
} |
||||||
|
|||||||
@ -1,226 +1,226 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "cursor.h" |
#include "cursor.h" |
||||||
#include "inv.h" |
#include "inv.h" |
||||||
#include "player.h" |
#include "player.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
/* Set up a given item as a spell scroll, allowing for its usage. */ |
/* Set up a given item as a spell scroll, allowing for its usage. */ |
||||||
void set_up_scroll(ItemStruct &item, spell_id spell) |
void set_up_scroll(ItemStruct &item, spell_id spell) |
||||||
{ |
{ |
||||||
pcurs = CURSOR_HAND; |
pcurs = CURSOR_HAND; |
||||||
leveltype = DTYPE_CATACOMBS; |
leveltype = DTYPE_CATACOMBS; |
||||||
plr[myplr]._pRSpell = static_cast<spell_id>(spell); |
plr[myplr]._pRSpell = static_cast<spell_id>(spell); |
||||||
item._itype = ITYPE_MISC; |
item._itype = ITYPE_MISC; |
||||||
item._iMiscId = IMISC_SCROLL; |
item._iMiscId = IMISC_SCROLL; |
||||||
item._iSpell = spell; |
item._iSpell = spell; |
||||||
} |
} |
||||||
|
|
||||||
/* Clear the inventory of myplr. */ |
/* Clear the inventory of myplr. */ |
||||||
void clear_inventory() |
void clear_inventory() |
||||||
{ |
{ |
||||||
for (int i = 0; i < NUM_INV_GRID_ELEM; i++) { |
for (int i = 0; i < NUM_INV_GRID_ELEM; i++) { |
||||||
memset(&plr[myplr].InvList[i], 0, sizeof(ItemStruct)); |
memset(&plr[myplr].InvList[i], 0, sizeof(ItemStruct)); |
||||||
plr[myplr].InvGrid[i] = 0; |
plr[myplr].InvGrid[i] = 0; |
||||||
} |
} |
||||||
plr[myplr]._pNumInv = 0; |
plr[myplr]._pNumInv = 0; |
||||||
} |
} |
||||||
|
|
||||||
// Test that the scroll is used in the inventory in correct conditions
|
// Test that the scroll is used in the inventory in correct conditions
|
||||||
TEST(Inv, UseScroll_from_inventory) |
TEST(Inv, UseScroll_from_inventory) |
||||||
{ |
{ |
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
plr[myplr]._pNumInv = 5; |
plr[myplr]._pNumInv = 5; |
||||||
EXPECT_TRUE(UseScroll()); |
EXPECT_TRUE(UseScroll()); |
||||||
} |
} |
||||||
|
|
||||||
// Test that the scroll is used in the belt in correct conditions
|
// Test that the scroll is used in the belt in correct conditions
|
||||||
TEST(Inv, UseScroll_from_belt) |
TEST(Inv, UseScroll_from_belt) |
||||||
{ |
{ |
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
EXPECT_TRUE(UseScroll()); |
EXPECT_TRUE(UseScroll()); |
||||||
} |
} |
||||||
|
|
||||||
// Test that the scroll is not used in the inventory for each invalid condition
|
// Test that the scroll is not used in the inventory for each invalid condition
|
||||||
TEST(Inv, UseScroll_from_inventory_invalid_conditions) |
TEST(Inv, UseScroll_from_inventory_invalid_conditions) |
||||||
{ |
{ |
||||||
// Empty the belt to prevent using a scroll from the belt
|
// Empty the belt to prevent using a scroll from the belt
|
||||||
for (int i = 0; i < MAXBELTITEMS; i++) { |
for (int i = 0; i < MAXBELTITEMS; i++) { |
||||||
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
||||||
} |
} |
||||||
|
|
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
pcurs = CURSOR_IDENTIFY; |
pcurs = CURSOR_IDENTIFY; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
leveltype = DTYPE_TOWN; |
leveltype = DTYPE_TOWN; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_HEAL); |
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_HEAL); |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
plr[myplr].InvList[2]._iMiscId = IMISC_STAFF; |
plr[myplr].InvList[2]._iMiscId = IMISC_STAFF; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].InvList[2], SPL_FIREBOLT); |
||||||
plr[myplr].InvList[2]._itype = ITYPE_NONE; |
plr[myplr].InvList[2]._itype = ITYPE_NONE; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
} |
} |
||||||
|
|
||||||
// Test that the scroll is not used in the belt for each invalid condition
|
// Test that the scroll is not used in the belt for each invalid condition
|
||||||
TEST(Inv, UseScroll_from_belt_invalid_conditions) |
TEST(Inv, UseScroll_from_belt_invalid_conditions) |
||||||
{ |
{ |
||||||
// Disable the inventory to prevent using a scroll from the inventory
|
// Disable the inventory to prevent using a scroll from the inventory
|
||||||
plr[myplr]._pNumInv = 0; |
plr[myplr]._pNumInv = 0; |
||||||
|
|
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
pcurs = CURSOR_IDENTIFY; |
pcurs = CURSOR_IDENTIFY; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
leveltype = DTYPE_TOWN; |
leveltype = DTYPE_TOWN; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_HEAL); |
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_HEAL); |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
plr[myplr].SpdList[2]._iMiscId = IMISC_STAFF; |
plr[myplr].SpdList[2]._iMiscId = IMISC_STAFF; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
|
|
||||||
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
set_up_scroll(plr[myplr].SpdList[2], SPL_FIREBOLT); |
||||||
plr[myplr].SpdList[2]._itype = ITYPE_NONE; |
plr[myplr].SpdList[2]._itype = ITYPE_NONE; |
||||||
EXPECT_FALSE(UseScroll()); |
EXPECT_FALSE(UseScroll()); |
||||||
} |
} |
||||||
|
|
||||||
// Test gold calculation
|
// Test gold calculation
|
||||||
TEST(Inv, CalculateGold) |
TEST(Inv, CalculateGold) |
||||||
{ |
{ |
||||||
plr[myplr]._pNumInv = 10; |
plr[myplr]._pNumInv = 10; |
||||||
// Set up two slots of gold both in the belt and inventory
|
// Set up two slots of gold both in the belt and inventory
|
||||||
plr[myplr].SpdList[1]._itype = ITYPE_GOLD; |
plr[myplr].SpdList[1]._itype = ITYPE_GOLD; |
||||||
plr[myplr].SpdList[5]._itype = ITYPE_GOLD; |
plr[myplr].SpdList[5]._itype = ITYPE_GOLD; |
||||||
plr[myplr].InvList[2]._itype = ITYPE_GOLD; |
plr[myplr].InvList[2]._itype = ITYPE_GOLD; |
||||||
plr[myplr].InvList[3]._itype = ITYPE_GOLD; |
plr[myplr].InvList[3]._itype = ITYPE_GOLD; |
||||||
// Set the gold amount to arbitrary values
|
// Set the gold amount to arbitrary values
|
||||||
plr[myplr].SpdList[1]._ivalue = 100; |
plr[myplr].SpdList[1]._ivalue = 100; |
||||||
plr[myplr].SpdList[5]._ivalue = 200; |
plr[myplr].SpdList[5]._ivalue = 200; |
||||||
plr[myplr].InvList[2]._ivalue = 3; |
plr[myplr].InvList[2]._ivalue = 3; |
||||||
plr[myplr].InvList[3]._ivalue = 30; |
plr[myplr].InvList[3]._ivalue = 30; |
||||||
|
|
||||||
EXPECT_EQ(CalculateGold(myplr), 333); |
EXPECT_EQ(CalculateGold(myplr), 333); |
||||||
} |
} |
||||||
|
|
||||||
// Test automatic gold placing
|
// Test automatic gold placing
|
||||||
TEST(Inv, GoldAutoPlace) |
TEST(Inv, GoldAutoPlace) |
||||||
{ |
{ |
||||||
// Empty the inventory
|
// Empty the inventory
|
||||||
clear_inventory(); |
clear_inventory(); |
||||||
|
|
||||||
// Put gold into the inventory:
|
// Put gold into the inventory:
|
||||||
// | 1000 | ... | ...
|
// | 1000 | ... | ...
|
||||||
plr[myplr].InvList[0]._itype = ITYPE_GOLD; |
plr[myplr].InvList[0]._itype = ITYPE_GOLD; |
||||||
plr[myplr].InvList[0]._ivalue = 1000; |
plr[myplr].InvList[0]._ivalue = 1000; |
||||||
plr[myplr]._pNumInv = 1; |
plr[myplr]._pNumInv = 1; |
||||||
// Put (max gold - 100) gold, which is 4900, into the player's hand
|
// Put (max gold - 100) gold, which is 4900, into the player's hand
|
||||||
plr[myplr].HoldItem._itype = ITYPE_GOLD; |
plr[myplr].HoldItem._itype = ITYPE_GOLD; |
||||||
plr[myplr].HoldItem._ivalue = GOLD_MAX_LIMIT - 100; |
plr[myplr].HoldItem._ivalue = GOLD_MAX_LIMIT - 100; |
||||||
|
|
||||||
GoldAutoPlace(myplr); |
GoldAutoPlace(myplr); |
||||||
// We expect the inventory:
|
// We expect the inventory:
|
||||||
// | 5000 | 900 | ...
|
// | 5000 | 900 | ...
|
||||||
EXPECT_EQ(plr[myplr].InvList[0]._ivalue, GOLD_MAX_LIMIT); |
EXPECT_EQ(plr[myplr].InvList[0]._ivalue, GOLD_MAX_LIMIT); |
||||||
EXPECT_EQ(plr[myplr].InvList[1]._ivalue, 900); |
EXPECT_EQ(plr[myplr].InvList[1]._ivalue, 900); |
||||||
} |
} |
||||||
|
|
||||||
// Test removing an item from inventory with no other items.
|
// Test removing an item from inventory with no other items.
|
||||||
TEST(Inv, RemoveInvItem) |
TEST(Inv, RemoveInvItem) |
||||||
{ |
{ |
||||||
clear_inventory(); |
clear_inventory(); |
||||||
// Put a two-slot misc item into the inventory:
|
// Put a two-slot misc item into the inventory:
|
||||||
// | (item) | (item) | ... | ...
|
// | (item) | (item) | ... | ...
|
||||||
plr[myplr]._pNumInv = 1; |
plr[myplr]._pNumInv = 1; |
||||||
plr[myplr].InvGrid[0] = 1; |
plr[myplr].InvGrid[0] = 1; |
||||||
plr[myplr].InvGrid[1] = -1; |
plr[myplr].InvGrid[1] = -1; |
||||||
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
||||||
|
|
||||||
plr[myplr].RemoveInvItem(0); |
plr[myplr].RemoveInvItem(0); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[1], 0); |
EXPECT_EQ(plr[myplr].InvGrid[1], 0); |
||||||
EXPECT_EQ(plr[myplr]._pNumInv, 0); |
EXPECT_EQ(plr[myplr]._pNumInv, 0); |
||||||
} |
} |
||||||
|
|
||||||
// Test removing an item from inventory with other items in it.
|
// Test removing an item from inventory with other items in it.
|
||||||
TEST(Inv, RemoveInvItem_other_item) |
TEST(Inv, RemoveInvItem_other_item) |
||||||
{ |
{ |
||||||
clear_inventory(); |
clear_inventory(); |
||||||
// Put a two-slot misc item and a ring into the inventory:
|
// Put a two-slot misc item and a ring into the inventory:
|
||||||
// | (item) | (item) | (ring) | ...
|
// | (item) | (item) | (ring) | ...
|
||||||
plr[myplr]._pNumInv = 2; |
plr[myplr]._pNumInv = 2; |
||||||
plr[myplr].InvGrid[0] = 1; |
plr[myplr].InvGrid[0] = 1; |
||||||
plr[myplr].InvGrid[1] = -1; |
plr[myplr].InvGrid[1] = -1; |
||||||
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
||||||
|
|
||||||
plr[myplr].InvGrid[2] = 2; |
plr[myplr].InvGrid[2] = 2; |
||||||
plr[myplr].InvList[1]._itype = ITYPE_RING; |
plr[myplr].InvList[1]._itype = ITYPE_RING; |
||||||
|
|
||||||
plr[myplr].RemoveInvItem(0); |
plr[myplr].RemoveInvItem(0); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[1], 0); |
EXPECT_EQ(plr[myplr].InvGrid[1], 0); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[2], 1); |
EXPECT_EQ(plr[myplr].InvGrid[2], 1); |
||||||
EXPECT_EQ(plr[myplr].InvList[0]._itype, ITYPE_RING); |
EXPECT_EQ(plr[myplr].InvList[0]._itype, ITYPE_RING); |
||||||
EXPECT_EQ(plr[myplr]._pNumInv, 1); |
EXPECT_EQ(plr[myplr]._pNumInv, 1); |
||||||
} |
} |
||||||
|
|
||||||
// Test removing an item from the belt
|
// Test removing an item from the belt
|
||||||
TEST(Inv, RemoveSpdBarItem) |
TEST(Inv, RemoveSpdBarItem) |
||||||
{ |
{ |
||||||
// Clear the belt
|
// Clear the belt
|
||||||
for (int i = 0; i < MAXBELTITEMS; i++) { |
for (int i = 0; i < MAXBELTITEMS; i++) { |
||||||
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
||||||
} |
} |
||||||
// Put an item in the belt: | x | x | item | x | x | x | x | x |
|
// Put an item in the belt: | x | x | item | x | x | x | x | x |
|
||||||
plr[myplr].SpdList[3]._itype = ITYPE_MISC; |
plr[myplr].SpdList[3]._itype = ITYPE_MISC; |
||||||
|
|
||||||
RemoveSpdBarItem(myplr, 3); |
RemoveSpdBarItem(myplr, 3); |
||||||
EXPECT_EQ(plr[myplr].SpdList[3]._itype, ITYPE_NONE); |
EXPECT_EQ(plr[myplr].SpdList[3]._itype, ITYPE_NONE); |
||||||
} |
} |
||||||
|
|
||||||
// Test removing a scroll from the inventory
|
// Test removing a scroll from the inventory
|
||||||
TEST(Inv, RemoveScroll_inventory) |
TEST(Inv, RemoveScroll_inventory) |
||||||
{ |
{ |
||||||
clear_inventory(); |
clear_inventory(); |
||||||
|
|
||||||
// Put a firebolt scroll into the inventory
|
// Put a firebolt scroll into the inventory
|
||||||
plr[myplr]._pNumInv = 1; |
plr[myplr]._pNumInv = 1; |
||||||
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_FIREBOLT); |
plr[myplr]._pRSpell = static_cast<spell_id>(SPL_FIREBOLT); |
||||||
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
plr[myplr].InvList[0]._itype = ITYPE_MISC; |
||||||
plr[myplr].InvList[0]._iMiscId = IMISC_SCROLL; |
plr[myplr].InvList[0]._iMiscId = IMISC_SCROLL; |
||||||
plr[myplr].InvList[0]._iSpell = SPL_FIREBOLT; |
plr[myplr].InvList[0]._iSpell = SPL_FIREBOLT; |
||||||
|
|
||||||
RemoveScroll(myplr); |
RemoveScroll(myplr); |
||||||
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
EXPECT_EQ(plr[myplr].InvGrid[0], 0); |
||||||
EXPECT_EQ(plr[myplr]._pNumInv, 0); |
EXPECT_EQ(plr[myplr]._pNumInv, 0); |
||||||
} |
} |
||||||
|
|
||||||
// Test removing a scroll from the belt
|
// Test removing a scroll from the belt
|
||||||
TEST(Inv, RemoveScroll_belt) |
TEST(Inv, RemoveScroll_belt) |
||||||
{ |
{ |
||||||
// Clear the belt
|
// Clear the belt
|
||||||
for (int i = 0; i < MAXBELTITEMS; i++) { |
for (int i = 0; i < MAXBELTITEMS; i++) { |
||||||
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
plr[myplr].SpdList[i]._itype = ITYPE_NONE; |
||||||
} |
} |
||||||
// Put a firebolt scroll into the belt
|
// Put a firebolt scroll into the belt
|
||||||
plr[myplr]._pSpell = static_cast<spell_id>(SPL_FIREBOLT); |
plr[myplr]._pSpell = static_cast<spell_id>(SPL_FIREBOLT); |
||||||
plr[myplr].SpdList[3]._itype = ITYPE_MISC; |
plr[myplr].SpdList[3]._itype = ITYPE_MISC; |
||||||
plr[myplr].SpdList[3]._iMiscId = IMISC_SCROLL; |
plr[myplr].SpdList[3]._iMiscId = IMISC_SCROLL; |
||||||
plr[myplr].SpdList[3]._iSpell = SPL_FIREBOLT; |
plr[myplr].SpdList[3]._iSpell = SPL_FIREBOLT; |
||||||
|
|
||||||
RemoveScroll(myplr); |
RemoveScroll(myplr); |
||||||
EXPECT_EQ(plr[myplr].SpdList[3]._itype, ITYPE_NONE); |
EXPECT_EQ(plr[myplr].SpdList[3]._itype, ITYPE_NONE); |
||||||
} |
} |
||||||
|
|||||||
@ -1,38 +1,38 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "control.h" |
#include "control.h" |
||||||
#include "lighting.h" |
#include "lighting.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Lighting, CrawlTables) |
TEST(Lighting, CrawlTables) |
||||||
{ |
{ |
||||||
int CrawlNum[19] = { 0, 3, 12, 45, 94, 159, 240, 337, 450, 579, 724, 885, 1062, 1255, 1464, 1689, 1930, 2187, 2460 }; |
int CrawlNum[19] = { 0, 3, 12, 45, 94, 159, 240, 337, 450, 579, 724, 885, 1062, 1255, 1464, 1689, 1930, 2187, 2460 }; |
||||||
|
|
||||||
bool added[40][40]; |
bool added[40][40]; |
||||||
memset(added, 0, sizeof(added)); |
memset(added, 0, sizeof(added)); |
||||||
|
|
||||||
for (int j = 0; j < 19; j++) { |
for (int j = 0; j < 19; j++) { |
||||||
int x = 20; |
int x = 20; |
||||||
int y = 20; |
int y = 20; |
||||||
int cr = CrawlNum[j] + 1; |
int cr = CrawlNum[j] + 1; |
||||||
for (unsigned i = (uint8_t)CrawlTable[cr - 1]; i > 0; i--, cr += 2) { |
for (unsigned i = (uint8_t)CrawlTable[cr - 1]; i > 0; i--, cr += 2) { |
||||||
int dx = x + CrawlTable[cr]; |
int dx = x + CrawlTable[cr]; |
||||||
int dy = y + CrawlTable[cr + 1]; |
int dy = y + CrawlTable[cr + 1]; |
||||||
sprintf(tempstr, "location %d:%d added twice.", dx - 20, dy - 20); |
sprintf(tempstr, "location %d:%d added twice.", dx - 20, dy - 20); |
||||||
EXPECT_EQ(added[dx][dy], false) << tempstr; |
EXPECT_EQ(added[dx][dy], false) << tempstr; |
||||||
added[dx][dy] = true; |
added[dx][dy] = true; |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
for (int i = -18; i <= 18; i++) { |
for (int i = -18; i <= 18; i++) { |
||||||
for (int j = -18; j <= 18; j++) { |
for (int j = -18; j <= 18; j++) { |
||||||
if (added[i + 20][j + 20]) |
if (added[i + 20][j + 20]) |
||||||
continue; |
continue; |
||||||
if ((i == -18 && j == -18) || (i == -18 && j == 18) || (i == 18 && j == -18) || (i == 18 && j == 18)) |
if ((i == -18 && j == -18) || (i == -18 && j == 18) || (i == 18 && j == -18) || (i == 18 && j == 18)) |
||||||
continue; // Limit of the crawl table rage
|
continue; // Limit of the crawl table rage
|
||||||
sprintf(tempstr, "while checking location %d:%d.", i, j); |
sprintf(tempstr, "while checking location %d:%d.", i, j); |
||||||
EXPECT_EQ(false, true) << tempstr; |
EXPECT_EQ(false, true) << tempstr; |
||||||
} |
} |
||||||
} |
} |
||||||
} |
} |
||||||
|
|||||||
@ -1,87 +1,87 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "missiles.h" |
#include "missiles.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
TEST(Missiles, GetDirection8) |
TEST(Missiles, GetDirection8) |
||||||
{ |
{ |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 15 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 15 })); |
||||||
EXPECT_EQ(1, GetDirection({ 0, 0 }, { 0, 15 })); |
EXPECT_EQ(1, GetDirection({ 0, 0 }, { 0, 15 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 15 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 15 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 8 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 8 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 8 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 8 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 7 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 15, 7 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 11, 7 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 11, 7 })); |
||||||
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 11 })); |
EXPECT_EQ(0, GetDirection({ 0, 0 }, { 8, 11 })); |
||||||
EXPECT_EQ(4, GetDirection({ 15, 15 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 15, 15 }, { 0, 0 })); |
||||||
EXPECT_EQ(5, GetDirection({ 0, 15 }, { 0, 0 })); |
EXPECT_EQ(5, GetDirection({ 0, 15 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 8, 15 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 8, 15 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 8, 8 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 8, 8 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 15, 8 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 15, 8 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 15, 7 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 15, 7 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 11, 7 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 11, 7 }, { 0, 0 })); |
||||||
EXPECT_EQ(4, GetDirection({ 8, 11 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 8, 11 }, { 0, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 15, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 15, 0 })); |
||||||
EXPECT_EQ(7, GetDirection({ 0, 0 }, { 15, 0 })); |
EXPECT_EQ(7, GetDirection({ 0, 0 }, { 15, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 15, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 15, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 8, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 8, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 8, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 8, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 7, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 15 }, { 7, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 11 }, { 7, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 11 }, { 7, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 11, 0 })); |
EXPECT_EQ(6, GetDirection({ 0, 8 }, { 11, 0 })); |
||||||
|
|
||||||
EXPECT_EQ(0, GetDirection({ 1, 1 }, { 2, 2 })); |
EXPECT_EQ(0, GetDirection({ 1, 1 }, { 2, 2 })); |
||||||
EXPECT_EQ(1, GetDirection({ 1, 1 }, { 1, 2 })); |
EXPECT_EQ(1, GetDirection({ 1, 1 }, { 1, 2 })); |
||||||
EXPECT_EQ(2, GetDirection({ 1, 1 }, { 0, 2 })); |
EXPECT_EQ(2, GetDirection({ 1, 1 }, { 0, 2 })); |
||||||
EXPECT_EQ(3, GetDirection({ 1, 1 }, { 0, 1 })); |
EXPECT_EQ(3, GetDirection({ 1, 1 }, { 0, 1 })); |
||||||
EXPECT_EQ(4, GetDirection({ 1, 1 }, { 0, 0 })); |
EXPECT_EQ(4, GetDirection({ 1, 1 }, { 0, 0 })); |
||||||
EXPECT_EQ(5, GetDirection({ 1, 1 }, { 1, 0 })); |
EXPECT_EQ(5, GetDirection({ 1, 1 }, { 1, 0 })); |
||||||
EXPECT_EQ(6, GetDirection({ 1, 1 }, { 2, 0 })); |
EXPECT_EQ(6, GetDirection({ 1, 1 }, { 2, 0 })); |
||||||
EXPECT_EQ(7, GetDirection({ 1, 1 }, { 2, 1 })); |
EXPECT_EQ(7, GetDirection({ 1, 1 }, { 2, 1 })); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Missiles, GetDirection16) |
TEST(Missiles, GetDirection16) |
||||||
{ |
{ |
||||||
EXPECT_EQ(0, GetDirection16(0, 0, 15, 15)); |
EXPECT_EQ(0, GetDirection16(0, 0, 15, 15)); |
||||||
EXPECT_EQ(2, GetDirection16(0, 0, 0, 15)); |
EXPECT_EQ(2, GetDirection16(0, 0, 0, 15)); |
||||||
EXPECT_EQ(1, GetDirection16(0, 0, 8, 15)); |
EXPECT_EQ(1, GetDirection16(0, 0, 8, 15)); |
||||||
EXPECT_EQ(0, GetDirection16(0, 0, 8, 8)); |
EXPECT_EQ(0, GetDirection16(0, 0, 8, 8)); |
||||||
EXPECT_EQ(15, GetDirection16(0, 0, 15, 8)); |
EXPECT_EQ(15, GetDirection16(0, 0, 15, 8)); |
||||||
EXPECT_EQ(15, GetDirection16(0, 0, 15, 7)); |
EXPECT_EQ(15, GetDirection16(0, 0, 15, 7)); |
||||||
EXPECT_EQ(15, GetDirection16(0, 0, 11, 7)); |
EXPECT_EQ(15, GetDirection16(0, 0, 11, 7)); |
||||||
EXPECT_EQ(0, GetDirection16(0, 0, 8, 11)); |
EXPECT_EQ(0, GetDirection16(0, 0, 8, 11)); |
||||||
EXPECT_EQ(8, GetDirection16(15, 15, 0, 0)); |
EXPECT_EQ(8, GetDirection16(15, 15, 0, 0)); |
||||||
EXPECT_EQ(10, GetDirection16(0, 15, 0, 0)); |
EXPECT_EQ(10, GetDirection16(0, 15, 0, 0)); |
||||||
EXPECT_EQ(9, GetDirection16(8, 15, 0, 0)); |
EXPECT_EQ(9, GetDirection16(8, 15, 0, 0)); |
||||||
EXPECT_EQ(8, GetDirection16(8, 8, 0, 0)); |
EXPECT_EQ(8, GetDirection16(8, 8, 0, 0)); |
||||||
EXPECT_EQ(7, GetDirection16(15, 8, 0, 0)); |
EXPECT_EQ(7, GetDirection16(15, 8, 0, 0)); |
||||||
EXPECT_EQ(7, GetDirection16(15, 7, 0, 0)); |
EXPECT_EQ(7, GetDirection16(15, 7, 0, 0)); |
||||||
EXPECT_EQ(7, GetDirection16(11, 7, 0, 0)); |
EXPECT_EQ(7, GetDirection16(11, 7, 0, 0)); |
||||||
EXPECT_EQ(8, GetDirection16(8, 11, 0, 0)); |
EXPECT_EQ(8, GetDirection16(8, 11, 0, 0)); |
||||||
EXPECT_EQ(12, GetDirection16(0, 15, 15, 0)); |
EXPECT_EQ(12, GetDirection16(0, 15, 15, 0)); |
||||||
EXPECT_EQ(14, GetDirection16(0, 0, 15, 0)); |
EXPECT_EQ(14, GetDirection16(0, 0, 15, 0)); |
||||||
EXPECT_EQ(13, GetDirection16(0, 8, 15, 0)); |
EXPECT_EQ(13, GetDirection16(0, 8, 15, 0)); |
||||||
EXPECT_EQ(12, GetDirection16(0, 8, 8, 0)); |
EXPECT_EQ(12, GetDirection16(0, 8, 8, 0)); |
||||||
EXPECT_EQ(11, GetDirection16(0, 15, 8, 0)); |
EXPECT_EQ(11, GetDirection16(0, 15, 8, 0)); |
||||||
EXPECT_EQ(11, GetDirection16(0, 15, 7, 0)); |
EXPECT_EQ(11, GetDirection16(0, 15, 7, 0)); |
||||||
EXPECT_EQ(11, GetDirection16(0, 11, 7, 0)); |
EXPECT_EQ(11, GetDirection16(0, 11, 7, 0)); |
||||||
EXPECT_EQ(12, GetDirection16(0, 8, 11, 0)); |
EXPECT_EQ(12, GetDirection16(0, 8, 11, 0)); |
||||||
|
|
||||||
EXPECT_EQ(0, GetDirection16(2, 2, 3, 3)); |
EXPECT_EQ(0, GetDirection16(2, 2, 3, 3)); |
||||||
EXPECT_EQ(1, GetDirection16(2, 2, 3, 4)); |
EXPECT_EQ(1, GetDirection16(2, 2, 3, 4)); |
||||||
EXPECT_EQ(2, GetDirection16(2, 2, 2, 4)); |
EXPECT_EQ(2, GetDirection16(2, 2, 2, 4)); |
||||||
EXPECT_EQ(3, GetDirection16(2, 2, 1, 4)); |
EXPECT_EQ(3, GetDirection16(2, 2, 1, 4)); |
||||||
EXPECT_EQ(4, GetDirection16(2, 2, 1, 3)); |
EXPECT_EQ(4, GetDirection16(2, 2, 1, 3)); |
||||||
EXPECT_EQ(5, GetDirection16(2, 2, 0, 3)); |
EXPECT_EQ(5, GetDirection16(2, 2, 0, 3)); |
||||||
EXPECT_EQ(6, GetDirection16(2, 2, 0, 2)); |
EXPECT_EQ(6, GetDirection16(2, 2, 0, 2)); |
||||||
EXPECT_EQ(7, GetDirection16(2, 2, 0, 1)); |
EXPECT_EQ(7, GetDirection16(2, 2, 0, 1)); |
||||||
EXPECT_EQ(8, GetDirection16(2, 2, 1, 1)); |
EXPECT_EQ(8, GetDirection16(2, 2, 1, 1)); |
||||||
EXPECT_EQ(9, GetDirection16(2, 2, 1, 0)); |
EXPECT_EQ(9, GetDirection16(2, 2, 1, 0)); |
||||||
EXPECT_EQ(10, GetDirection16(2, 2, 2, 0)); |
EXPECT_EQ(10, GetDirection16(2, 2, 2, 0)); |
||||||
EXPECT_EQ(11, GetDirection16(2, 2, 3, 0)); |
EXPECT_EQ(11, GetDirection16(2, 2, 3, 0)); |
||||||
EXPECT_EQ(12, GetDirection16(2, 2, 3, 1)); |
EXPECT_EQ(12, GetDirection16(2, 2, 3, 1)); |
||||||
EXPECT_EQ(13, GetDirection16(2, 2, 4, 1)); |
EXPECT_EQ(13, GetDirection16(2, 2, 4, 1)); |
||||||
EXPECT_EQ(14, GetDirection16(2, 2, 4, 2)); |
EXPECT_EQ(14, GetDirection16(2, 2, 4, 2)); |
||||||
EXPECT_EQ(15, GetDirection16(2, 2, 4, 3)); |
EXPECT_EQ(15, GetDirection16(2, 2, 4, 3)); |
||||||
} |
} |
||||||
|
|||||||
@ -1,83 +1,83 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "player.h" |
#include "player.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
namespace devilution { |
namespace devilution { |
||||||
extern bool PM_DoGotHit(int pnum); |
extern bool PM_DoGotHit(int pnum); |
||||||
} |
} |
||||||
|
|
||||||
int RunBlockTest(int frames, int flags) |
int RunBlockTest(int frames, int flags) |
||||||
{ |
{ |
||||||
int pnum = 0; |
int pnum = 0; |
||||||
plr[pnum].AnimInfo.CurrentFrame = 1; |
plr[pnum].AnimInfo.CurrentFrame = 1; |
||||||
plr[pnum]._pHFrames = frames; |
plr[pnum]._pHFrames = frames; |
||||||
plr[pnum].actionFrame = 1; |
plr[pnum].actionFrame = 1; |
||||||
plr[pnum]._pIFlags = flags; |
plr[pnum]._pIFlags = flags; |
||||||
plr[pnum]._pmode = PM_GOTHIT; |
plr[pnum]._pmode = PM_GOTHIT; |
||||||
plr[pnum]._pGFXLoad = -1; |
plr[pnum]._pGFXLoad = -1; |
||||||
|
|
||||||
int i = 1; |
int i = 1; |
||||||
for (; i < 100; i++) { |
for (; i < 100; i++) { |
||||||
PM_DoGotHit(pnum); |
PM_DoGotHit(pnum); |
||||||
if (plr[pnum]._pmode != PM_GOTHIT) |
if (plr[pnum]._pmode != PM_GOTHIT) |
||||||
break; |
break; |
||||||
plr[pnum].AnimInfo.CurrentFrame++; |
plr[pnum].AnimInfo.CurrentFrame++; |
||||||
} |
} |
||||||
|
|
||||||
return i; |
return i; |
||||||
} |
} |
||||||
|
|
||||||
#define NORM 0 |
#define NORM 0 |
||||||
#define BAL ISPL_FASTRECOVER |
#define BAL ISPL_FASTRECOVER |
||||||
#define STA ISPL_FASTERRECOVER |
#define STA ISPL_FASTERRECOVER |
||||||
#define HAR ISPL_FASTESTRECOVER |
#define HAR ISPL_FASTESTRECOVER |
||||||
#define BALSTA (ISPL_FASTRECOVER | ISPL_FASTERRECOVER) |
#define BALSTA (ISPL_FASTRECOVER | ISPL_FASTERRECOVER) |
||||||
#define BALHAR (ISPL_FASTRECOVER | ISPL_FASTESTRECOVER) |
#define BALHAR (ISPL_FASTRECOVER | ISPL_FASTESTRECOVER) |
||||||
#define STAHAR (ISPL_FASTERRECOVER | ISPL_FASTESTRECOVER) |
#define STAHAR (ISPL_FASTERRECOVER | ISPL_FASTESTRECOVER) |
||||||
#define ZEN (ISPL_FASTRECOVER | ISPL_FASTERRECOVER | ISPL_FASTESTRECOVER) |
#define ZEN (ISPL_FASTRECOVER | ISPL_FASTERRECOVER | ISPL_FASTESTRECOVER) |
||||||
#define WAR 6 |
#define WAR 6 |
||||||
#define ROU 7 |
#define ROU 7 |
||||||
#define SRC 8 |
#define SRC 8 |
||||||
|
|
||||||
int BlockData[][3] = { |
int BlockData[][3] = { |
||||||
{ 6, WAR, NORM }, |
{ 6, WAR, NORM }, |
||||||
{ 7, ROU, NORM }, |
{ 7, ROU, NORM }, |
||||||
{ 8, SRC, NORM }, |
{ 8, SRC, NORM }, |
||||||
|
|
||||||
{ 5, WAR, BAL }, |
{ 5, WAR, BAL }, |
||||||
{ 6, ROU, BAL }, |
{ 6, ROU, BAL }, |
||||||
{ 7, SRC, BAL }, |
{ 7, SRC, BAL }, |
||||||
|
|
||||||
{ 4, WAR, STA }, |
{ 4, WAR, STA }, |
||||||
{ 5, ROU, STA }, |
{ 5, ROU, STA }, |
||||||
{ 6, SRC, STA }, |
{ 6, SRC, STA }, |
||||||
|
|
||||||
{ 3, WAR, HAR }, |
{ 3, WAR, HAR }, |
||||||
{ 4, ROU, HAR }, |
{ 4, ROU, HAR }, |
||||||
{ 5, SRC, HAR }, |
{ 5, SRC, HAR }, |
||||||
|
|
||||||
{ 4, WAR, BALSTA }, |
{ 4, WAR, BALSTA }, |
||||||
{ 5, ROU, BALSTA }, |
{ 5, ROU, BALSTA }, |
||||||
{ 6, SRC, BALSTA }, |
{ 6, SRC, BALSTA }, |
||||||
|
|
||||||
{ 3, WAR, BALHAR }, |
{ 3, WAR, BALHAR }, |
||||||
{ 4, ROU, BALHAR }, |
{ 4, ROU, BALHAR }, |
||||||
{ 5, SRC, BALHAR }, |
{ 5, SRC, BALHAR }, |
||||||
|
|
||||||
{ 3, WAR, STAHAR }, |
{ 3, WAR, STAHAR }, |
||||||
{ 4, ROU, STAHAR }, |
{ 4, ROU, STAHAR }, |
||||||
{ 5, SRC, STAHAR }, |
{ 5, SRC, STAHAR }, |
||||||
|
|
||||||
{ 2, WAR, ZEN }, |
{ 2, WAR, ZEN }, |
||||||
{ 3, ROU, ZEN }, |
{ 3, ROU, ZEN }, |
||||||
{ 4, SRC, ZEN }, |
{ 4, SRC, ZEN }, |
||||||
}; |
}; |
||||||
|
|
||||||
TEST(Player, PM_DoGotHit) |
TEST(Player, PM_DoGotHit) |
||||||
{ |
{ |
||||||
for (size_t i = 0; i < sizeof(BlockData) / sizeof(*BlockData); i++) { |
for (size_t i = 0; i < sizeof(BlockData) / sizeof(*BlockData); i++) { |
||||||
EXPECT_EQ(BlockData[i][0], RunBlockTest(BlockData[i][1], BlockData[i][2])); |
EXPECT_EQ(BlockData[i][0], RunBlockTest(BlockData[i][1], BlockData[i][2])); |
||||||
} |
} |
||||||
} |
} |
||||||
|
|||||||
@ -1,164 +1,164 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "diablo.h" |
#include "diablo.h" |
||||||
#include "scrollrt.h" |
#include "scrollrt.h" |
||||||
#include "utils/ui_fwd.h" |
#include "utils/ui_fwd.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
// TilesInView
|
// TilesInView
|
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_in_view_original) |
TEST(Scrool_rt, calc_tiles_in_view_original) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight - 128; |
gnViewportHeight = gnScreenHeight - 128; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int columns = 0; |
int columns = 0; |
||||||
int rows = 0; |
int rows = 0; |
||||||
TilesInView(&columns, &rows); |
TilesInView(&columns, &rows); |
||||||
EXPECT_EQ(columns, 10); |
EXPECT_EQ(columns, 10); |
||||||
EXPECT_EQ(rows, 11); |
EXPECT_EQ(rows, 11); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_in_view_original_zoom) |
TEST(Scrool_rt, calc_tiles_in_view_original_zoom) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight - 128; |
gnViewportHeight = gnScreenHeight - 128; |
||||||
zoomflag = false; |
zoomflag = false; |
||||||
int columns = 0; |
int columns = 0; |
||||||
int rows = 0; |
int rows = 0; |
||||||
TilesInView(&columns, &rows); |
TilesInView(&columns, &rows); |
||||||
EXPECT_EQ(columns, 5); |
EXPECT_EQ(columns, 5); |
||||||
EXPECT_EQ(rows, 6); |
EXPECT_EQ(rows, 6); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_in_view_960_540) |
TEST(Scrool_rt, calc_tiles_in_view_960_540) |
||||||
{ |
{ |
||||||
gnScreenWidth = 960; |
gnScreenWidth = 960; |
||||||
gnScreenHeight = 540; |
gnScreenHeight = 540; |
||||||
gnViewportHeight = gnScreenHeight; |
gnViewportHeight = gnScreenHeight; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int columns = 0; |
int columns = 0; |
||||||
int rows = 0; |
int rows = 0; |
||||||
TilesInView(&columns, &rows); |
TilesInView(&columns, &rows); |
||||||
EXPECT_EQ(columns, 15); |
EXPECT_EQ(columns, 15); |
||||||
EXPECT_EQ(rows, 17); |
EXPECT_EQ(rows, 17); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_in_view_640_512) |
TEST(Scrool_rt, calc_tiles_in_view_640_512) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
gnScreenHeight = 512; |
gnScreenHeight = 512; |
||||||
gnViewportHeight = gnScreenHeight - 128; |
gnViewportHeight = gnScreenHeight - 128; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int columns = 0; |
int columns = 0; |
||||||
int rows = 0; |
int rows = 0; |
||||||
TilesInView(&columns, &rows); |
TilesInView(&columns, &rows); |
||||||
EXPECT_EQ(columns, 10); |
EXPECT_EQ(columns, 10); |
||||||
EXPECT_EQ(rows, 12); |
EXPECT_EQ(rows, 12); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_in_view_768_480_zoom) |
TEST(Scrool_rt, calc_tiles_in_view_768_480_zoom) |
||||||
{ |
{ |
||||||
gnScreenWidth = 768; |
gnScreenWidth = 768; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight; |
gnViewportHeight = gnScreenHeight; |
||||||
zoomflag = false; |
zoomflag = false; |
||||||
int columns = 0; |
int columns = 0; |
||||||
int rows = 0; |
int rows = 0; |
||||||
TilesInView(&columns, &rows); |
TilesInView(&columns, &rows); |
||||||
EXPECT_EQ(columns, 6); |
EXPECT_EQ(columns, 6); |
||||||
EXPECT_EQ(rows, 8); |
EXPECT_EQ(rows, 8); |
||||||
} |
} |
||||||
|
|
||||||
// CalcTileOffset
|
// CalcTileOffset
|
||||||
|
|
||||||
TEST(Scrool_rt, calc_tile_offset_original) |
TEST(Scrool_rt, calc_tile_offset_original) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight - 128; |
gnViewportHeight = gnScreenHeight - 128; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int x = 0; |
int x = 0; |
||||||
int y = 0; |
int y = 0; |
||||||
CalcTileOffset(&x, &y); |
CalcTileOffset(&x, &y); |
||||||
EXPECT_EQ(x, 0); |
EXPECT_EQ(x, 0); |
||||||
EXPECT_EQ(y, 0); |
EXPECT_EQ(y, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tile_offset_original_zoom) |
TEST(Scrool_rt, calc_tile_offset_original_zoom) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight - 128; |
gnViewportHeight = gnScreenHeight - 128; |
||||||
zoomflag = false; |
zoomflag = false; |
||||||
int x = 0; |
int x = 0; |
||||||
int y = 0; |
int y = 0; |
||||||
CalcTileOffset(&x, &y); |
CalcTileOffset(&x, &y); |
||||||
EXPECT_EQ(x, 0); |
EXPECT_EQ(x, 0); |
||||||
EXPECT_EQ(y, 8); |
EXPECT_EQ(y, 8); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tile_offset_960_540) |
TEST(Scrool_rt, calc_tile_offset_960_540) |
||||||
{ |
{ |
||||||
gnScreenWidth = 960; |
gnScreenWidth = 960; |
||||||
gnScreenHeight = 540; |
gnScreenHeight = 540; |
||||||
gnViewportHeight = gnScreenHeight; |
gnViewportHeight = gnScreenHeight; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int x = 0; |
int x = 0; |
||||||
int y = 0; |
int y = 0; |
||||||
CalcTileOffset(&x, &y); |
CalcTileOffset(&x, &y); |
||||||
EXPECT_EQ(x, 0); |
EXPECT_EQ(x, 0); |
||||||
EXPECT_EQ(y, 2); |
EXPECT_EQ(y, 2); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tile_offset_853_480) |
TEST(Scrool_rt, calc_tile_offset_853_480) |
||||||
{ |
{ |
||||||
gnScreenWidth = 853; |
gnScreenWidth = 853; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight; |
gnViewportHeight = gnScreenHeight; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
int x = 0; |
int x = 0; |
||||||
int y = 0; |
int y = 0; |
||||||
CalcTileOffset(&x, &y); |
CalcTileOffset(&x, &y); |
||||||
EXPECT_EQ(x, 21); |
EXPECT_EQ(x, 21); |
||||||
EXPECT_EQ(y, 0); |
EXPECT_EQ(y, 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tile_offset_768_480_zoom) |
TEST(Scrool_rt, calc_tile_offset_768_480_zoom) |
||||||
{ |
{ |
||||||
gnScreenWidth = 768; |
gnScreenWidth = 768; |
||||||
gnScreenHeight = 480; |
gnScreenHeight = 480; |
||||||
gnViewportHeight = gnScreenHeight; |
gnViewportHeight = gnScreenHeight; |
||||||
zoomflag = false; |
zoomflag = false; |
||||||
int x = 0; |
int x = 0; |
||||||
int y = 0; |
int y = 0; |
||||||
CalcTileOffset(&x, &y); |
CalcTileOffset(&x, &y); |
||||||
EXPECT_EQ(x, 0); |
EXPECT_EQ(x, 0); |
||||||
EXPECT_EQ(y, 8); |
EXPECT_EQ(y, 8); |
||||||
} |
} |
||||||
|
|
||||||
// RowsCoveredByPanel
|
// RowsCoveredByPanel
|
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_covered_by_panel_original) |
TEST(Scrool_rt, calc_tiles_covered_by_panel_original) |
||||||
{ |
{ |
||||||
gnScreenWidth = 640; |
gnScreenWidth = 640; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
EXPECT_EQ(RowsCoveredByPanel(), 0); |
EXPECT_EQ(RowsCoveredByPanel(), 0); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_covered_by_panel_960) |
TEST(Scrool_rt, calc_tiles_covered_by_panel_960) |
||||||
{ |
{ |
||||||
gnScreenWidth = 960; |
gnScreenWidth = 960; |
||||||
zoomflag = true; |
zoomflag = true; |
||||||
EXPECT_EQ(RowsCoveredByPanel(), 4); |
EXPECT_EQ(RowsCoveredByPanel(), 4); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Scrool_rt, calc_tiles_covered_by_panel_960_zoom) |
TEST(Scrool_rt, calc_tiles_covered_by_panel_960_zoom) |
||||||
{ |
{ |
||||||
gnScreenWidth = 960; |
gnScreenWidth = 960; |
||||||
zoomflag = false; |
zoomflag = false; |
||||||
EXPECT_EQ(RowsCoveredByPanel(), 2); |
EXPECT_EQ(RowsCoveredByPanel(), 2); |
||||||
} |
} |
||||||
|
|||||||
@ -1,74 +1,74 @@ |
|||||||
#include <gtest/gtest.h> |
#include <gtest/gtest.h> |
||||||
|
|
||||||
#include "stores.h" |
#include "stores.h" |
||||||
|
|
||||||
using namespace devilution; |
using namespace devilution; |
||||||
|
|
||||||
namespace { |
namespace { |
||||||
|
|
||||||
TEST(Stores, AddStoreHoldRepair_magic) |
TEST(Stores, AddStoreHoldRepair_magic) |
||||||
{ |
{ |
||||||
ItemStruct *item; |
ItemStruct *item; |
||||||
|
|
||||||
item = &storehold[0]; |
item = &storehold[0]; |
||||||
|
|
||||||
item->_iMaxDur = 60; |
item->_iMaxDur = 60; |
||||||
item->_iDurability = item->_iMaxDur; |
item->_iDurability = item->_iMaxDur; |
||||||
item->_iMagical = ITEM_QUALITY_MAGIC; |
item->_iMagical = ITEM_QUALITY_MAGIC; |
||||||
item->_iIdentified = true; |
item->_iIdentified = true; |
||||||
item->_ivalue = 2000; |
item->_ivalue = 2000; |
||||||
item->_iIvalue = 19000; |
item->_iIvalue = 19000; |
||||||
|
|
||||||
for (int i = 1; i < item->_iMaxDur; i++) { |
for (int i = 1; i < item->_iMaxDur; i++) { |
||||||
item->_ivalue = 2000; |
item->_ivalue = 2000; |
||||||
item->_iIvalue = 19000; |
item->_iIvalue = 19000; |
||||||
item->_iDurability = i; |
item->_iDurability = i; |
||||||
storenumh = 0; |
storenumh = 0; |
||||||
AddStoreHoldRepair(item, 0); |
AddStoreHoldRepair(item, 0); |
||||||
EXPECT_EQ(1, storenumh); |
EXPECT_EQ(1, storenumh); |
||||||
EXPECT_EQ(95 * (item->_iMaxDur - i) / 2, item->_ivalue); |
EXPECT_EQ(95 * (item->_iMaxDur - i) / 2, item->_ivalue); |
||||||
} |
} |
||||||
|
|
||||||
item->_iDurability = 59; |
item->_iDurability = 59; |
||||||
storenumh = 0; |
storenumh = 0; |
||||||
item->_ivalue = 500; |
item->_ivalue = 500; |
||||||
item->_iIvalue = 30; // To cheap to repair
|
item->_iIvalue = 30; // To cheap to repair
|
||||||
AddStoreHoldRepair(item, 0); |
AddStoreHoldRepair(item, 0); |
||||||
EXPECT_EQ(0, storenumh); |
EXPECT_EQ(0, storenumh); |
||||||
EXPECT_EQ(30, item->_iIvalue); |
EXPECT_EQ(30, item->_iIvalue); |
||||||
EXPECT_EQ(500, item->_ivalue); |
EXPECT_EQ(500, item->_ivalue); |
||||||
} |
} |
||||||
|
|
||||||
TEST(Stores, AddStoreHoldRepair_normal) |
TEST(Stores, AddStoreHoldRepair_normal) |
||||||
{ |
{ |
||||||
ItemStruct *item; |
ItemStruct *item; |
||||||
|
|
||||||
item = &storehold[0]; |
item = &storehold[0]; |
||||||
|
|
||||||
item->_iMaxDur = 20; |
item->_iMaxDur = 20; |
||||||
item->_iDurability = item->_iMaxDur; |
item->_iDurability = item->_iMaxDur; |
||||||
item->_iMagical = ITEM_QUALITY_NORMAL; |
item->_iMagical = ITEM_QUALITY_NORMAL; |
||||||
item->_iIdentified = true; |
item->_iIdentified = true; |
||||||
item->_ivalue = 2000; |
item->_ivalue = 2000; |
||||||
item->_iIvalue = item->_ivalue; |
item->_iIvalue = item->_ivalue; |
||||||
|
|
||||||
for (int i = 1; i < item->_iMaxDur; i++) { |
for (int i = 1; i < item->_iMaxDur; i++) { |
||||||
item->_ivalue = 2000; |
item->_ivalue = 2000; |
||||||
item->_iIvalue = item->_ivalue; |
item->_iIvalue = item->_ivalue; |
||||||
item->_iDurability = i; |
item->_iDurability = i; |
||||||
storenumh = 0; |
storenumh = 0; |
||||||
AddStoreHoldRepair(item, 0); |
AddStoreHoldRepair(item, 0); |
||||||
EXPECT_EQ(1, storenumh); |
EXPECT_EQ(1, storenumh); |
||||||
EXPECT_EQ(50 * (item->_iMaxDur - i), item->_ivalue); |
EXPECT_EQ(50 * (item->_iMaxDur - i), item->_ivalue); |
||||||
} |
} |
||||||
|
|
||||||
item->_iDurability = 19; |
item->_iDurability = 19; |
||||||
storenumh = 0; |
storenumh = 0; |
||||||
item->_ivalue = 10; // less then 1 per dur
|
item->_ivalue = 10; // less then 1 per dur
|
||||||
item->_iIvalue = item->_ivalue; |
item->_iIvalue = item->_ivalue; |
||||||
AddStoreHoldRepair(item, 0); |
AddStoreHoldRepair(item, 0); |
||||||
EXPECT_EQ(1, storenumh); |
EXPECT_EQ(1, storenumh); |
||||||
EXPECT_EQ(1, item->_ivalue); |
EXPECT_EQ(1, item->_ivalue); |
||||||
EXPECT_EQ(1, item->_iIvalue); |
EXPECT_EQ(1, item->_iIvalue); |
||||||
} |
} |
||||||
} // namespace
|
} // namespace
|
||||||
|
|||||||
Loading…
Reference in new issue