mirror of
https://github.com/vcmi/vcmi.git
synced 2025-04-17 11:56:46 +02:00
Implemented semi-transparent spell effects
This commit is contained in:
parent
fd1a31253b
commit
dfe6e04464
@ -881,9 +881,10 @@ uint32_t CastAnimation::getAttackClimaxFrame() const
|
|||||||
return maxFrames / 2;
|
return maxFrames / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, int effects, float transparencyFactor, bool reversed):
|
||||||
BattleAnimation(owner),
|
BattleAnimation(owner),
|
||||||
animation(GH.renderHandler().loadAnimation(animationName, EImageBlitMode::SIMPLE)),
|
animation(GH.renderHandler().loadAnimation(animationName, EImageBlitMode::SIMPLE)),
|
||||||
|
transparencyFactor(transparencyFactor),
|
||||||
effectFlags(effects),
|
effectFlags(effects),
|
||||||
effectFinished(false),
|
effectFinished(false),
|
||||||
reversed(reversed)
|
reversed(reversed)
|
||||||
@ -892,32 +893,32 @@ EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath &
|
|||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<BattleHex> hex, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<BattleHex> hex, int effects, bool reversed):
|
||||||
EffectAnimation(owner, animationName, effects, reversed)
|
EffectAnimation(owner, animationName, effects, 1.0f, reversed)
|
||||||
{
|
{
|
||||||
battlehexes = hex;
|
battlehexes = hex;
|
||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, BattleHex hex, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, BattleHex hex, int effects, float transparencyFactor, bool reversed):
|
||||||
EffectAnimation(owner, animationName, effects, reversed)
|
EffectAnimation(owner, animationName, effects, transparencyFactor, reversed)
|
||||||
{
|
{
|
||||||
assert(hex.isValid());
|
assert(hex.isValid());
|
||||||
battlehexes.push_back(hex);
|
battlehexes.push_back(hex);
|
||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<Point> pos, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<Point> pos, int effects, bool reversed):
|
||||||
EffectAnimation(owner, animationName, effects, reversed)
|
EffectAnimation(owner, animationName, effects, 1.0f, reversed)
|
||||||
{
|
{
|
||||||
positions = pos;
|
positions = pos;
|
||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, int effects, bool reversed):
|
||||||
EffectAnimation(owner, animationName, effects, reversed)
|
EffectAnimation(owner, animationName, effects, 1.0f, reversed)
|
||||||
{
|
{
|
||||||
positions.push_back(pos);
|
positions.push_back(pos);
|
||||||
}
|
}
|
||||||
|
|
||||||
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, BattleHex hex, int effects, bool reversed):
|
EffectAnimation::EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, BattleHex hex, int effects, bool reversed):
|
||||||
EffectAnimation(owner, animationName, effects, reversed)
|
EffectAnimation(owner, animationName, effects, 1.0f, reversed)
|
||||||
{
|
{
|
||||||
assert(hex.isValid());
|
assert(hex.isValid());
|
||||||
battlehexes.push_back(hex);
|
battlehexes.push_back(hex);
|
||||||
@ -951,6 +952,7 @@ bool EffectAnimation::init()
|
|||||||
be.effectID = ID;
|
be.effectID = ID;
|
||||||
be.animation = animation;
|
be.animation = animation;
|
||||||
be.currentFrame = 0;
|
be.currentFrame = 0;
|
||||||
|
be.transparencyFactor = transparencyFactor;
|
||||||
be.type = reversed ? BattleEffect::AnimType::REVERSE : BattleEffect::AnimType::DEFAULT;
|
be.type = reversed ? BattleEffect::AnimType::REVERSE : BattleEffect::AnimType::DEFAULT;
|
||||||
|
|
||||||
for (size_t i = 0; i < std::max(battlehexes.size(), positions.size()); ++i)
|
for (size_t i = 0; i < std::max(battlehexes.size(), positions.size()); ++i)
|
||||||
|
@ -309,9 +309,10 @@ public:
|
|||||||
class EffectAnimation : public BattleAnimation
|
class EffectAnimation : public BattleAnimation
|
||||||
{
|
{
|
||||||
std::string soundName;
|
std::string soundName;
|
||||||
|
int effectFlags;
|
||||||
|
float transparencyFactor;
|
||||||
bool effectFinished;
|
bool effectFinished;
|
||||||
bool reversed;
|
bool reversed;
|
||||||
int effectFlags;
|
|
||||||
|
|
||||||
std::shared_ptr<CAnimation> animation;
|
std::shared_ptr<CAnimation> animation;
|
||||||
std::vector<Point> positions;
|
std::vector<Point> positions;
|
||||||
@ -335,14 +336,14 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
/// Create animation with screen-wide effect
|
/// Create animation with screen-wide effect
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, int effects = 0, float transparencyFactor = 1.f, bool reversed = false);
|
||||||
|
|
||||||
/// Create animation positioned at point(s). Note that positions must be are absolute, including battleint position offset
|
/// Create animation positioned at point(s). Note that positions must be are absolute, including battleint position offset
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos , int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos , int effects = 0, bool reversed = false);
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<Point> pos , int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<Point> pos , int effects = 0, bool reversed = false);
|
||||||
|
|
||||||
/// Create animation positioned at certain hex(es)
|
/// Create animation positioned at certain hex(es)
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, BattleHex hex , int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, BattleHex hex , int effects = 0, float transparencyFactor = 1.0f, bool reversed = false);
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<BattleHex> hex, int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, std::vector<BattleHex> hex, int effects = 0, bool reversed = false);
|
||||||
|
|
||||||
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, BattleHex hex, int effects = 0, bool reversed = false);
|
EffectAnimation(BattleInterface & owner, const AnimationPath & animationName, Point pos, BattleHex hex, int effects = 0, bool reversed = false);
|
||||||
|
@ -44,7 +44,7 @@ void BattleEffectsController::displayEffect(EBattleEffect effect, const BattleHe
|
|||||||
displayEffect(effect, AudioPath(), destTile);
|
displayEffect(effect, AudioPath(), destTile);
|
||||||
}
|
}
|
||||||
|
|
||||||
void BattleEffectsController::displayEffect(EBattleEffect effect, const AudioPath & soundFile, const BattleHex & destTile)
|
void BattleEffectsController::displayEffect(EBattleEffect effect, const AudioPath & soundFile, const BattleHex & destTile, float transparencyFactor)
|
||||||
{
|
{
|
||||||
size_t effectID = static_cast<size_t>(effect);
|
size_t effectID = static_cast<size_t>(effect);
|
||||||
|
|
||||||
@ -52,7 +52,7 @@ void BattleEffectsController::displayEffect(EBattleEffect effect, const AudioPat
|
|||||||
|
|
||||||
CCS->soundh->playSound( soundFile );
|
CCS->soundh->playSound( soundFile );
|
||||||
|
|
||||||
owner.stacksController->addNewAnim(new EffectAnimation(owner, customAnim, destTile));
|
owner.stacksController->addNewAnim(new EffectAnimation(owner, customAnim, destTile, 0, transparencyFactor));
|
||||||
}
|
}
|
||||||
|
|
||||||
void BattleEffectsController::battleTriggerEffect(const BattleTriggerEffect & bte)
|
void BattleEffectsController::battleTriggerEffect(const BattleTriggerEffect & bte)
|
||||||
@ -69,7 +69,7 @@ void BattleEffectsController::battleTriggerEffect(const BattleTriggerEffect & bt
|
|||||||
switch(static_cast<BonusType>(bte.effect))
|
switch(static_cast<BonusType>(bte.effect))
|
||||||
{
|
{
|
||||||
case BonusType::HP_REGENERATION:
|
case BonusType::HP_REGENERATION:
|
||||||
displayEffect(EBattleEffect::REGENERATION, AudioPath::builtin("REGENER"), stack->getPosition());
|
displayEffect(EBattleEffect::REGENERATION, AudioPath::builtin("REGENER"), stack->getPosition(), 0.5);
|
||||||
break;
|
break;
|
||||||
case BonusType::MANA_DRAIN:
|
case BonusType::MANA_DRAIN:
|
||||||
displayEffect(EBattleEffect::MANA_DRAIN, AudioPath::builtin("MANADRAI"), stack->getPosition());
|
displayEffect(EBattleEffect::MANA_DRAIN, AudioPath::builtin("MANADRAI"), stack->getPosition());
|
||||||
@ -78,7 +78,7 @@ void BattleEffectsController::battleTriggerEffect(const BattleTriggerEffect & bt
|
|||||||
displayEffect(EBattleEffect::POISON, AudioPath::builtin("POISON"), stack->getPosition());
|
displayEffect(EBattleEffect::POISON, AudioPath::builtin("POISON"), stack->getPosition());
|
||||||
break;
|
break;
|
||||||
case BonusType::FEAR:
|
case BonusType::FEAR:
|
||||||
displayEffect(EBattleEffect::FEAR, AudioPath::builtin("FEAR"), stack->getPosition());
|
displayEffect(EBattleEffect::FEAR, AudioPath::builtin("FEAR"), stack->getPosition(), 0.5);
|
||||||
break;
|
break;
|
||||||
case BonusType::MORALE:
|
case BonusType::MORALE:
|
||||||
{
|
{
|
||||||
@ -124,6 +124,7 @@ void BattleEffectsController::collectRenderableObjects(BattleRenderer & renderer
|
|||||||
currentFrame %= elem.animation->size();
|
currentFrame %= elem.animation->size();
|
||||||
|
|
||||||
auto img = elem.animation->getImage(currentFrame, static_cast<size_t>(elem.type));
|
auto img = elem.animation->getImage(currentFrame, static_cast<size_t>(elem.type));
|
||||||
|
img->setAlpha(255 * elem.transparencyFactor);
|
||||||
|
|
||||||
canvas.draw(img, elem.pos);
|
canvas.draw(img, elem.pos);
|
||||||
});
|
});
|
||||||
|
@ -39,7 +39,8 @@ struct BattleEffect
|
|||||||
|
|
||||||
AnimType type;
|
AnimType type;
|
||||||
Point pos; //position on the screen
|
Point pos; //position on the screen
|
||||||
float currentFrame;
|
float currentFrame = 0.0;
|
||||||
|
float transparencyFactor = 1.0;
|
||||||
std::shared_ptr<CAnimation> animation;
|
std::shared_ptr<CAnimation> animation;
|
||||||
int effectID; //uniqueID equal ot ID of appropriate CSpellEffectAnim
|
int effectID; //uniqueID equal ot ID of appropriate CSpellEffectAnim
|
||||||
BattleHex tile; //Indicates if effect which hex the effect is drawn on
|
BattleHex tile; //Indicates if effect which hex the effect is drawn on
|
||||||
@ -65,7 +66,7 @@ public:
|
|||||||
|
|
||||||
//displays custom effect on the battlefield
|
//displays custom effect on the battlefield
|
||||||
void displayEffect(EBattleEffect effect, const BattleHex & destTile);
|
void displayEffect(EBattleEffect effect, const BattleHex & destTile);
|
||||||
void displayEffect(EBattleEffect effect, const AudioPath & soundFile, const BattleHex & destTile);
|
void displayEffect(EBattleEffect effect, const AudioPath & soundFile, const BattleHex & destTile, float transparencyFactor = 1.f);
|
||||||
|
|
||||||
void battleTriggerEffect(const BattleTriggerEffect & bte);
|
void battleTriggerEffect(const BattleTriggerEffect & bte);
|
||||||
|
|
||||||
|
@ -535,9 +535,9 @@ void BattleInterface::displaySpellAnimationQueue(const CSpell * spell, const CSp
|
|||||||
flags |= EffectAnimation::SCREEN_FILL;
|
flags |= EffectAnimation::SCREEN_FILL;
|
||||||
|
|
||||||
if (!destinationTile.isValid())
|
if (!destinationTile.isValid())
|
||||||
stacksController->addNewAnim(new EffectAnimation(*this, animation.resourceName, flags));
|
stacksController->addNewAnim(new EffectAnimation(*this, animation.resourceName, flags, animation.transparency));
|
||||||
else
|
else
|
||||||
stacksController->addNewAnim(new EffectAnimation(*this, animation.resourceName, destinationTile, flags));
|
stacksController->addNewAnim(new EffectAnimation(*this, animation.resourceName, destinationTile, flags, animation.transparency));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -636,7 +636,7 @@ void BattleStacksController::stackAttacking( const StackAttackInfo & info )
|
|||||||
{
|
{
|
||||||
owner.addToAnimationStage(EAnimationEvents::AFTER_HIT, [=]()
|
owner.addToAnimationStage(EAnimationEvents::AFTER_HIT, [=]()
|
||||||
{
|
{
|
||||||
owner.effectsController->displayEffect(EBattleEffect::DRAIN_LIFE, AudioPath::builtin("DRAINLIF"), attacker->getPosition());
|
owner.effectsController->displayEffect(EBattleEffect::DRAIN_LIFE, AudioPath::builtin("DRAINLIF"), attacker->getPosition(), 0.5);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -22,7 +22,8 @@
|
|||||||
"properties" : {
|
"properties" : {
|
||||||
"verticalPosition" : {"type" : "string", "enum" :["top","bottom"]},
|
"verticalPosition" : {"type" : "string", "enum" :["top","bottom"]},
|
||||||
"defName" : {"type" : "string", "format" : "animationFile"},
|
"defName" : {"type" : "string", "format" : "animationFile"},
|
||||||
"effectName" : { "type" : "string" }
|
"effectName" : { "type" : "string" },
|
||||||
|
"transparency" : {"type" : "number", "minimum" : 0, "maximum" : 1}
|
||||||
},
|
},
|
||||||
"additionalProperties" : false
|
"additionalProperties" : false
|
||||||
}
|
}
|
||||||
|
@ -252,7 +252,7 @@
|
|||||||
"targetType": "NO_TARGET",
|
"targetType": "NO_TARGET",
|
||||||
|
|
||||||
"animation":{
|
"animation":{
|
||||||
"hit":["SP04_"]
|
"hit":[{ "defName" : "SP04_", "transparency" : 0.5}]
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
"cast": "DEATHCLD"
|
"cast": "DEATHCLD"
|
||||||
|
@ -44,7 +44,7 @@
|
|||||||
{"minimumAngle": 1.20 ,"defName":"C08SPW1"},
|
{"minimumAngle": 1.20 ,"defName":"C08SPW1"},
|
||||||
{"minimumAngle": 1.50 ,"defName":"C08SPW0"}
|
{"minimumAngle": 1.50 ,"defName":"C08SPW0"}
|
||||||
],
|
],
|
||||||
"hit":["C08SPW5"]
|
"hit":[ {"defName" : "C08SPW5", "transparency" : 0.5 }]
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
"cast": "ICERAY"
|
"cast": "ICERAY"
|
||||||
@ -309,7 +309,7 @@
|
|||||||
"targetType" : "CREATURE",
|
"targetType" : "CREATURE",
|
||||||
|
|
||||||
"animation":{
|
"animation":{
|
||||||
"affect":["C14SPA0"]
|
"affect":[{"defName" : "C14SPA0", "transparency" : 0.5}]
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
"cast": "SACBRETH"
|
"cast": "SACBRETH"
|
||||||
|
@ -483,7 +483,7 @@
|
|||||||
"targetType" : "CREATURE",
|
"targetType" : "CREATURE",
|
||||||
|
|
||||||
"animation":{
|
"animation":{
|
||||||
"affect":["C01SPE0"]
|
"affect":[{ "defName" : "C01SPE0", "transparency" : 0.5}]
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
"cast": "RESURECT"
|
"cast": "RESURECT"
|
||||||
|
@ -652,7 +652,7 @@
|
|||||||
"targetType" : "CREATURE",
|
"targetType" : "CREATURE",
|
||||||
|
|
||||||
"animation":{
|
"animation":{
|
||||||
"affect":["C07SPA1"],
|
"affect":[{"defName" : "C07SPA1", "transparency" : 0.5}],
|
||||||
"projectile":[{"defName":"C07SPA0"}]//???
|
"projectile":[{"defName":"C07SPA0"}]//???
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
@ -696,7 +696,7 @@
|
|||||||
"targetType" : "CREATURE",
|
"targetType" : "CREATURE",
|
||||||
|
|
||||||
"animation":{
|
"animation":{
|
||||||
"affect":[{"defName":"C10SPW", "verticalPosition":"bottom"}]
|
"affect":[{"defName":"C10SPW", "verticalPosition":"bottom", "transparency" : 0.5}]
|
||||||
},
|
},
|
||||||
"sounds": {
|
"sounds": {
|
||||||
"cast": "PRAYER"
|
"cast": "PRAYER"
|
||||||
|
@ -544,7 +544,8 @@ void CSpell::serializeJson(JsonSerializeFormat & handler)
|
|||||||
///CSpell::AnimationInfo
|
///CSpell::AnimationInfo
|
||||||
CSpell::AnimationItem::AnimationItem() :
|
CSpell::AnimationItem::AnimationItem() :
|
||||||
verticalPosition(VerticalPosition::TOP),
|
verticalPosition(VerticalPosition::TOP),
|
||||||
pause(0)
|
pause(0),
|
||||||
|
transparency(1)
|
||||||
{
|
{
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -965,10 +966,15 @@ std::shared_ptr<CSpell> CSpellHandler::loadFromJson(const std::string & scope, c
|
|||||||
auto vPosStr = item["verticalPosition"].String();
|
auto vPosStr = item["verticalPosition"].String();
|
||||||
if("bottom" == vPosStr)
|
if("bottom" == vPosStr)
|
||||||
newItem.verticalPosition = VerticalPosition::BOTTOM;
|
newItem.verticalPosition = VerticalPosition::BOTTOM;
|
||||||
|
|
||||||
|
if (item["transparency"].isNumber())
|
||||||
|
newItem.transparency = item["transparency"].Float();
|
||||||
|
else
|
||||||
|
newItem.transparency = 1.0;
|
||||||
}
|
}
|
||||||
else if(item.isNumber())
|
else if(item.isNumber())
|
||||||
{
|
{
|
||||||
newItem.pause = static_cast<int>(item.Float());
|
newItem.pause = item.Integer();
|
||||||
}
|
}
|
||||||
|
|
||||||
q.push_back(newItem);
|
q.push_back(newItem);
|
||||||
|
@ -74,6 +74,7 @@ public:
|
|||||||
AnimationPath resourceName;
|
AnimationPath resourceName;
|
||||||
std::string effectName;
|
std::string effectName;
|
||||||
VerticalPosition verticalPosition;
|
VerticalPosition verticalPosition;
|
||||||
|
float transparency;
|
||||||
int pause;
|
int pause;
|
||||||
|
|
||||||
AnimationItem();
|
AnimationItem();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user