Fixed HP/SP bar limits

This commit is contained in:
Daegaladh 2024-09-09 18:22:45 +02:00
parent d160413cf5
commit 29010fa544
5 changed files with 49 additions and 12 deletions

View File

@ -671,8 +671,8 @@ CREATE TABLE IF NOT EXISTS `homunculus` (
`luk` smallint(4) unsigned NOT NULL default '0',
`hp` int(11) unsigned NOT NULL default '0',
`max_hp` int(11) unsigned NOT NULL default '0',
`sp` int(11) NOT NULL default '0',
`max_sp` int(11) NOT NULL default '0',
`sp` int(11) unsigned NOT NULL default '0',
`max_sp` int(11) unsigned NOT NULL default '0',
`skill_point` smallint(4) unsigned NOT NULL default '0',
`alive` tinyint(2) NOT NULL default '1',
`rename_flag` tinyint(2) NOT NULL default '0',

View File

@ -0,0 +1,3 @@
ALTER TABLE `homunculus`
CHANGE COLUMN `sp` `sp` INT(11) UNSIGNED NOT NULL DEFAULT '0' AFTER `max_hp`,
CHANGE COLUMN `max_sp` `max_sp` INT(11) UNSIGNED NOT NULL DEFAULT '0' AFTER `sp`;

View File

@ -189,10 +189,10 @@ bool mapif_homunculus_load(int homun_id, struct s_homunculus* hd)
Sql_GetData(sql_handle, 12, &data, nullptr); hd->int_ = atoi(data);
Sql_GetData(sql_handle, 13, &data, nullptr); hd->dex = atoi(data);
Sql_GetData(sql_handle, 14, &data, nullptr); hd->luk = atoi(data);
Sql_GetData(sql_handle, 15, &data, nullptr); hd->hp = atoi(data);
Sql_GetData(sql_handle, 16, &data, nullptr); hd->max_hp = atoi(data);
Sql_GetData(sql_handle, 17, &data, nullptr); hd->sp = atoi(data);
Sql_GetData(sql_handle, 18, &data, nullptr); hd->max_sp = atoi(data);
Sql_GetData(sql_handle, 15, &data, nullptr); hd->hp = static_cast<unsigned int>(strtoul(data, nullptr, 10));
Sql_GetData(sql_handle, 16, &data, nullptr); hd->max_hp = static_cast<unsigned int>(strtoul(data, nullptr, 10));
Sql_GetData(sql_handle, 17, &data, nullptr); hd->sp = static_cast<unsigned int>(strtoul(data, nullptr, 10));
Sql_GetData(sql_handle, 18, &data, nullptr); hd->max_sp = static_cast<unsigned int>(strtoul(data, nullptr, 10));
Sql_GetData(sql_handle, 19, &data, nullptr); hd->skillpts = atoi(data);
Sql_GetData(sql_handle, 20, &data, nullptr); hd->rename_flag = atoi(data);
Sql_GetData(sql_handle, 21, &data, nullptr); hd->vaporize = atoi(data);

View File

@ -497,7 +497,7 @@ struct s_homunculus { //[orn]
uint32 char_id;
short class_;
short prev_class;
int hp,max_hp,sp,max_sp;
uint32 hp,max_hp,sp,max_sp;
unsigned int intimacy; //[orn]
short hunger;
struct s_skill hskill[MAX_HOMUNSKILL]; //albator

View File

@ -1768,13 +1768,30 @@ void clif_homunculus_updatestatus(map_session_data& sd, _sp type) {
p.value = static_cast<decltype(p.value)>( std::min<decltype(sd.hd->homunculus.exp)>( sd.hd->homunculus.exp, std::numeric_limits<decltype(PACKET_ZC_PROPERTY_HOMUN::exp)>::max() ) );
break;
case SP_HP:
if (status->max_hp > (std::is_same<decltype(PACKET_ZC_PROPERTY_HOMUN::hp), uint16>::value ? INT16_MAX : INT32_MAX / 100))
// Homunculus HP and SP bars will screw up if the percentage calculation exceeds signed values
// Any value above will screw up the bars
#if PACKETVER_MAIN_NUM >= 20200819 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20190626
// Tested maximum: 2147483647 (INT32_MAX)
if (status->max_hp > INT32_MAX)
#elif PACKETVER_MAIN_NUM >= 20131230 || PACKETVER_RE_NUM >= 20131230 || defined(PACKETVER_ZERO)
// Tested maximum: 21474836 (INT32_MAX / 100)
if (status->max_hp > INT32_MAX / 100)
#else
// Tested maximum: 32767 (INT16_MAX)
if (status->max_hp > INT16_MAX)
#endif
p.value = status->hp / (status->max_hp / 100);
else
p.value = static_cast<decltype(p.value)>(status->hp);
break;
case SP_SP:
if (status->max_sp > (std::is_same<decltype(PACKET_ZC_PROPERTY_HOMUN::sp), uint16>::value ? INT16_MAX : INT32_MAX / 100))
#if PACKETVER_MAIN_NUM >= 20200819 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20190626
// Tested maximum: 2147483647 (INT32_MAX)
if (status->max_sp > INT32_MAX)
#else
// Tested maximum: 32767 (INT16_MAX)
if (status->max_sp > INT16_MAX)
#endif
p.value = status->sp / (status->max_sp / 100);
else
p.value = static_cast<decltype(p.value)>(status->sp);
@ -1827,15 +1844,32 @@ void clif_hominfo( map_session_data *sd, struct homun_data *hd, int flag ){
p.flee = status->flee;
p.amotion = (flag) ? 0 : status->amotion;
// Homunculus HP and SP bars will screw up if the percentage calculation exceeds signed values
// Tested maximum: 21474836(=INT32_MAX/100), any value above will screw up the bars
if( status->max_hp > ( std::is_same<decltype(p.hp), uint16>::value ? INT16_MAX : INT32_MAX / 100 ) ){
// Any value above will screw up the bars
#if PACKETVER_MAIN_NUM >= 20200819 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20190626
// Tested maximum: 2147483647 (INT32_MAX)
if (status->max_hp > INT32_MAX)
#elif PACKETVER_MAIN_NUM >= 20131230 || PACKETVER_RE_NUM >= 20131230 || defined(PACKETVER_ZERO)
// Tested maximum: 21474836 (INT32_MAX / 100)
if (status->max_hp > INT32_MAX / 100)
#else
// Tested maximum: 32767 (INT16_MAX)
if (status->max_hp > INT16_MAX)
#endif
{
p.hp = status->hp / ( status->max_hp / 100 );
p.maxHp = 100;
}else{
p.hp = static_cast<decltype(p.hp)>(status->hp);
p.maxHp = static_cast<decltype(p.maxHp)>(status->max_hp);
}
if( status->max_sp > ( std::is_same<decltype(p.sp), uint16>::value ? INT16_MAX : INT32_MAX / 100 ) ){
#if PACKETVER_MAIN_NUM >= 20200819 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20190626
// Tested maximum: 2147483647 (INT32_MAX)
if (status->max_sp > INT32_MAX)
#else
// Tested maximum: 32767 (INT16_MAX)
if (status->max_sp > INT16_MAX)
#endif
{
p.sp = status->sp / ( status->max_sp / 100 );
p.maxSp = 100;
}else{