@@ -1562,46 +1562,27 @@ void ovinaxs_mercurial_egg( special_effect_t& effect )
1562
1562
{
1563
1563
double cap_mul;
1564
1564
int cap;
1565
- double original_amount;
1566
1565
1567
1566
ovinax_stat_buff_t ( player_t * p, std::string_view n, const spell_data_t * s, const spell_data_t * data )
1568
1567
: stat_buff_t ( p, n, s ),
1569
1568
cap_mul ( 1.0 - data->effectN ( 4 ).percent() ),
1570
1569
cap( as<int >( data->effectN ( 5 ).base_value() ) )
1571
1570
{}
1572
1571
1573
- void reset () override
1574
- {
1575
- stat_buff_t::reset ();
1576
- stats[ 0 ].amount = original_amount;
1577
- }
1578
-
1579
- void _initialize ()
1580
- {
1581
- // assume each buff has a single stat. refactor if this changes.
1582
- assert ( stats.size () == 1 );
1583
- original_amount = stats[ 0 ].amount ;
1584
- }
1585
-
1586
1572
// values can be off by a +/-2 due to unknown rounding being performed by the in-game script
1587
- void recalculate_stat_amount ( int stacks = 0 )
1573
+ double buff_stat_stack_amount ( const buff_stat_t & stat, int s ) const override
1588
1574
{
1589
- auto s = stacks ? stacks : check ();
1590
- if ( !s )
1591
- return ;
1592
-
1593
- if ( s <= cap )
1594
- stats[ 0 ].amount = original_amount;
1595
- else
1596
- stats[ 0 ].amount = original_amount * ( cap + ( s - cap ) * cap_mul ) / s;
1575
+ double val = std::max ( 1.0 , std::fabs ( stat.amount ) );
1576
+ double stack = s <= cap ? s : cap + ( s - cap ) * cap_mul;
1577
+ // TODO: confirm truncation happens on final amount, and not per stack amount
1578
+ return std::copysign ( std::trunc ( stack * val + 1e-3 ), stat.amount );
1597
1579
}
1598
1580
};
1599
1581
1600
1582
// setup stat buffs
1601
1583
auto primary = create_buff<ovinax_stat_buff_t >( effect.player, effect.player->find_spell ( 449578 ), data );
1602
1584
primary->set_stat_from_effect_type ( A_MOD_STAT, data->effectN ( 1 ).average( effect ) )
1603
1585
->set_constant_behavior( buff_constant_behavior::NEVER_CONSTANT );
1604
- primary->_initialize ();
1605
1586
1606
1587
static constexpr std::array<unsigned , 4 > buff_ids = { 449595 , 449594 , 449581 , 449593 };
1607
1588
@@ -1617,7 +1598,6 @@ void ovinaxs_mercurial_egg( special_effect_t& effect )
1617
1598
buff->set_stat_from_effect_type ( A_MOD_RATING, data->effectN ( 2 ).average ( effect ) )
1618
1599
->set_name_reporting ( stat_str )
1619
1600
->set_constant_behavior ( buff_constant_behavior::NEVER_CONSTANT );
1620
- buff->_initialize ();
1621
1601
1622
1602
secondaries[ secondary_ratings[ i ] ] = buff;
1623
1603
}
@@ -1633,12 +1613,6 @@ void ovinaxs_mercurial_egg( special_effect_t& effect )
1633
1613
if ( halt->check () )
1634
1614
return ;
1635
1615
1636
- // recalculate stat amounts first before making stack adjustments. because recalculation changes the basic
1637
- // per-stack amount of the buff, this results in different post-adjustment total amounts depending if the stack is
1638
- // increasing or decreasing until the next tick.
1639
- primary->recalculate_stat_amount ();
1640
- range::for_each ( secondaries, []( const auto & b ) { b.second ->recalculate_stat_amount (); } );
1641
-
1642
1616
// if player is moving decrement stack. if player is above desired primary stack and not casting, assume player
1643
1617
// will sidestep to try to decrement.
1644
1618
auto desired = p->thewarwithin_opts .ovinaxs_mercurial_egg_desired_primary_stacks ;
@@ -1686,14 +1660,12 @@ void ovinaxs_mercurial_egg( special_effect_t& effect )
1686
1660
1687
1661
if ( p_stacks )
1688
1662
{
1689
- primary->recalculate_stat_amount ( p_stacks );
1690
1663
primary->trigger ( p_stacks );
1691
1664
}
1692
1665
1693
1666
if ( s_stacks )
1694
1667
{
1695
1668
auto buff = secondaries.at ( util::highest_stat ( p, secondary_ratings ) );
1696
- buff->recalculate_stat_amount ( s_stacks );
1697
1669
buff->trigger ( s_stacks );
1698
1670
}
1699
1671
0 commit comments