Poison React now activates when character is damaged only - Fixes bugreport:109
Cloaking fixed to official behaviour (Thanks helvetica for the hour of testing) - Concerning bugreport:171 Fixed instancing long map names causing crashes - Cannot save or memo on instance maps (Lemongrass) - Map channels are no longer activated on instance maps (Lemongrass) - Fixed a character save issue with instance maps (Lemongrass) - Map local channels are disabled by default, this is custom (Lemongrass) - Just thank Lemongrass overall, I gave him a hard time with this issue ~ Hercules Merge ~ Update Bloody Lust and Maelstrom to official behaviour (Credits: malufett) git-svn-id: https://svn.code.sf.net/p/rathena/svn/trunk@17408 54d463be-8e91-2dee-dedb-b68131a5f0ec
This commit is contained in:
parent
1ed6911a71
commit
81e3b03ace
@ -30,7 +30,7 @@ chsys: (
|
|||||||
allow_user_channel_creation: true
|
allow_user_channel_creation: true
|
||||||
|
|
||||||
/* "map_local_channel" is an instanced channel unique to each map. */
|
/* "map_local_channel" is an instanced channel unique to each map. */
|
||||||
map_local_channel: true
|
map_local_channel: false
|
||||||
map_local_channel_name: "map"
|
map_local_channel_name: "map"
|
||||||
map_local_channel_color: "Yellow"
|
map_local_channel_color: "Yellow"
|
||||||
map_local_channel_autojoin: true /* Disable autojoin in specific maps through mapflag 'nomapchannelautojoin'. */
|
map_local_channel_autojoin: true /* Disable autojoin in specific maps through mapflag 'nomapchannelautojoin'. */
|
||||||
|
@ -399,7 +399,9 @@
|
|||||||
380: Item Failed. [%s] is cooling down. Wait %d seconds.
|
380: Item Failed. [%s] is cooling down. Wait %d seconds.
|
||||||
381: Skill Failed. [%s] requires %dx %s.
|
381: Skill Failed. [%s] requires %dx %s.
|
||||||
382: You're too close to a stone or emperium to use this skill.
|
382: You're too close to a stone or emperium to use this skill.
|
||||||
//383-389 free
|
383: You cannot create a savepoint in an instance.
|
||||||
|
384: You cannot create a memo in an instance.
|
||||||
|
//385-389 free
|
||||||
//NoAsk
|
//NoAsk
|
||||||
390: Autorejecting is activated.
|
390: Autorejecting is activated.
|
||||||
391: Autorejecting is deactivated.
|
391: Autorejecting is deactivated.
|
||||||
|
@ -874,7 +874,7 @@
|
|||||||
2300,7,6,2,0,0x1,0,3,1,yes,0,0,1,none,0, SC_DIMENSIONDOOR,Dimension Door
|
2300,7,6,2,0,0x1,0,3,1,yes,0,0,1,none,0, SC_DIMENSIONDOOR,Dimension Door
|
||||||
2301,7,6,2,0,0x1,0,3,1,yes,0,0,0,none,0, SC_CHAOSPANIC,Chaos Panic
|
2301,7,6,2,0,0x1,0,3,1,yes,0,0,0,none,0, SC_CHAOSPANIC,Chaos Panic
|
||||||
2302,7,6,2,0,0x1,0,3,1,yes,0,0,0,none,0, SC_MAELSTROM,Maelstrom
|
2302,7,6,2,0,0x1,0,3,1,yes,0,0,0,none,0, SC_MAELSTROM,Maelstrom
|
||||||
2303,7,6,2,0,0x1,0,3,1,yes,0,0,0,none,0, SC_BLOODYLUST,Bloody Lust
|
2303,7,6,2,0,0x1,3,3,1,yes,0,0,1,none,0, SC_BLOODYLUST,Bloody Lust
|
||||||
2304,0,6,4,-1,0,0,3,1,no,0,0,0,weapon,0, SC_FEINTBOMB,Feint Bomb
|
2304,0,6,4,-1,0,0,3,1,no,0,0,0,weapon,0, SC_FEINTBOMB,Feint Bomb
|
||||||
|
|
||||||
//****
|
//****
|
||||||
|
@ -729,6 +729,11 @@ ACMD_FUNC(save)
|
|||||||
{
|
{
|
||||||
nullpo_retr(-1, sd);
|
nullpo_retr(-1, sd);
|
||||||
|
|
||||||
|
if( map[sd->bl.m].instance_id ) {
|
||||||
|
clif_displaymessage(fd, msg_txt(sd,383)); // You cannot create a savepoint in an instance.
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
pc_setsavepoint(sd, sd->mapindex, sd->bl.x, sd->bl.y);
|
pc_setsavepoint(sd, sd->mapindex, sd->bl.x, sd->bl.y);
|
||||||
if (sd->status.pet_id > 0 && sd->pd)
|
if (sd->status.pet_id > 0 && sd->pd)
|
||||||
intif_save_petdata(sd->status.account_id, &sd->pd->pet);
|
intif_save_petdata(sd->status.account_id, &sd->pd->pet);
|
||||||
@ -2221,8 +2226,7 @@ ACMD_FUNC(memo)
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
pc_memo(sd, position);
|
return !pc_memo( sd, position );
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
|
@ -745,6 +745,10 @@ int battle_calc_damage(struct block_list *src,struct block_list *bl,struct Damag
|
|||||||
if( battle_config.ksprotection && mob_ksprotected(src, bl) )
|
if( battle_config.ksprotection && mob_ksprotected(src, bl) )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
if( map_getcell(bl->m, bl->x, bl->y, CELL_CHKMAELSTROM) && skill_get_type(skill_id) != BF_MISC
|
||||||
|
&& skill_get_casttype(skill_id) == CAST_GROUND )
|
||||||
|
return 0;
|
||||||
|
|
||||||
if (bl->type == BL_PC) {
|
if (bl->type == BL_PC) {
|
||||||
sd=(struct map_session_data *)bl;
|
sd=(struct map_session_data *)bl;
|
||||||
//Special no damage states
|
//Special no damage states
|
||||||
@ -2739,7 +2743,7 @@ static int battle_calc_attack_skill_ratio(struct Damage wd, struct block_list *s
|
|||||||
skillratio += sc->data[SC_OVERTHRUST]->val3;
|
skillratio += sc->data[SC_OVERTHRUST]->val3;
|
||||||
if(sc->data[SC_MAXOVERTHRUST])
|
if(sc->data[SC_MAXOVERTHRUST])
|
||||||
skillratio += sc->data[SC_MAXOVERTHRUST]->val2;
|
skillratio += sc->data[SC_MAXOVERTHRUST]->val2;
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC__BLOODYLUST])
|
if (sc->data[SC_BERSERK] || sc->data[SC_SATURDAYNIGHTFEVER])
|
||||||
skillratio += 100;
|
skillratio += 100;
|
||||||
if(sc->data[SC_ZENKAI] && sstatus->rhw.ele == sc->data[SC_ZENKAI]->val2 )
|
if(sc->data[SC_ZENKAI] && sstatus->rhw.ele == sc->data[SC_ZENKAI]->val2 )
|
||||||
skillratio += sc->data[SC_ZENKAI]->val1 * 2;
|
skillratio += sc->data[SC_ZENKAI]->val1 * 2;
|
||||||
@ -6008,7 +6012,7 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (tsc) {
|
if (tsc) {
|
||||||
if (tsc->data[SC_POISONREACT] &&
|
if (damage > 0 && tsc->data[SC_POISONREACT] &&
|
||||||
(rnd()%100 < tsc->data[SC_POISONREACT]->val3
|
(rnd()%100 < tsc->data[SC_POISONREACT]->val3
|
||||||
|| sstatus->def_ele == ELE_POISON) &&
|
|| sstatus->def_ele == ELE_POISON) &&
|
||||||
// check_distance_bl(src, target, tstatus->rhw.range+1) && Doesn't checks range! o.O;
|
// check_distance_bl(src, target, tstatus->rhw.range+1) && Doesn't checks range! o.O;
|
||||||
|
@ -304,7 +304,22 @@ int chrif_save(struct map_session_data *sd, int flag) {
|
|||||||
WFIFOL(char_fd,4) = sd->status.account_id;
|
WFIFOL(char_fd,4) = sd->status.account_id;
|
||||||
WFIFOL(char_fd,8) = sd->status.char_id;
|
WFIFOL(char_fd,8) = sd->status.char_id;
|
||||||
WFIFOB(char_fd,12) = (flag==1)?1:0; //Flag to tell char-server this character is quitting.
|
WFIFOB(char_fd,12) = (flag==1)?1:0; //Flag to tell char-server this character is quitting.
|
||||||
memcpy(WFIFOP(char_fd,13), &sd->status, sizeof(sd->status));
|
|
||||||
|
// If the user is on a instance map, we have to fake his current position
|
||||||
|
if( map[sd->bl.m].instance_id ){
|
||||||
|
struct mmo_charstatus status;
|
||||||
|
|
||||||
|
// Copy the whole status
|
||||||
|
memcpy( &status, &sd->status, sizeof( struct mmo_charstatus ) );
|
||||||
|
// Change his current position to his savepoint
|
||||||
|
memcpy( &status.last_point, &status.save_point, sizeof( struct point ) );
|
||||||
|
// Copy the copied status into the packet
|
||||||
|
memcpy( WFIFOP( char_fd, 13 ), &status, sizeof( struct mmo_charstatus ) );
|
||||||
|
} else {
|
||||||
|
// Copy the whole status into the packet
|
||||||
|
memcpy( WFIFOP( char_fd, 13 ), &sd->status, sizeof( struct mmo_charstatus ) );
|
||||||
|
}
|
||||||
|
|
||||||
WFIFOSET(char_fd, WFIFOW(char_fd,2));
|
WFIFOSET(char_fd, WFIFOW(char_fd,2));
|
||||||
|
|
||||||
if( sd->status.pet_id > 0 && sd->pd )
|
if( sd->status.pet_id > 0 && sd->pd )
|
||||||
|
@ -1660,7 +1660,7 @@ void clif_quitsave(int fd,struct map_session_data *sd) {
|
|||||||
|
|
||||||
/// Notifies the client of a position change to coordinates on given map (ZC_NPCACK_MAPMOVE).
|
/// Notifies the client of a position change to coordinates on given map (ZC_NPCACK_MAPMOVE).
|
||||||
/// 0091 <map name>.16B <x>.W <y>.W
|
/// 0091 <map name>.16B <x>.W <y>.W
|
||||||
void clif_changemap(struct map_session_data *sd, short map, int x, int y)
|
void clif_changemap(struct map_session_data *sd, short m, int x, int y)
|
||||||
{
|
{
|
||||||
int fd;
|
int fd;
|
||||||
nullpo_retv(sd);
|
nullpo_retv(sd);
|
||||||
@ -1668,7 +1668,18 @@ void clif_changemap(struct map_session_data *sd, short map, int x, int y)
|
|||||||
|
|
||||||
WFIFOHEAD(fd,packet_len(0x91));
|
WFIFOHEAD(fd,packet_len(0x91));
|
||||||
WFIFOW(fd,0) = 0x91;
|
WFIFOW(fd,0) = 0x91;
|
||||||
mapindex_getmapname_ext(mapindex_id2name(map), (char*)WFIFOP(fd,2));
|
if(map[m].instance_id) { // Instance map check to send client source map name so we don't crash player
|
||||||
|
struct instance_data *im = &instance_data[map[m].instance_id];
|
||||||
|
int i;
|
||||||
|
if(!im) // This shouldn't happen but if it does give them the map we intended to give
|
||||||
|
mapindex_getmapname_ext(map[m].name, (char*)WFIFOP(fd,2));
|
||||||
|
for(i = 0; i < MAX_MAP_PER_INSTANCE; i++) // Loop to find the src map we want
|
||||||
|
if(im->map[i].m == m) {
|
||||||
|
mapindex_getmapname_ext(map[im->map[i].src_m].name, (char*)WFIFOP(fd,2));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
mapindex_getmapname_ext(map[m].name, (char*)WFIFOP(fd,2));
|
||||||
WFIFOW(fd,18) = x;
|
WFIFOW(fd,18) = x;
|
||||||
WFIFOW(fd,20) = y;
|
WFIFOW(fd,20) = y;
|
||||||
WFIFOSET(fd,packet_len(0x91));
|
WFIFOSET(fd,packet_len(0x91));
|
||||||
@ -8286,7 +8297,7 @@ void clif_refresh(struct map_session_data *sd)
|
|||||||
int i;
|
int i;
|
||||||
nullpo_retv(sd);
|
nullpo_retv(sd);
|
||||||
|
|
||||||
clif_changemap(sd,sd->mapindex,sd->bl.x,sd->bl.y);
|
clif_changemap(sd,sd->bl.m,sd->bl.x,sd->bl.y);
|
||||||
clif_inventorylist(sd);
|
clif_inventorylist(sd);
|
||||||
if(pc_iscarton(sd)) {
|
if(pc_iscarton(sd)) {
|
||||||
clif_cartlist(sd);
|
clif_cartlist(sd);
|
||||||
@ -9139,7 +9150,7 @@ void clif_parse_LoadEndAck(int fd,struct map_session_data *sd)
|
|||||||
|
|
||||||
if (sd->state.rewarp) { //Rewarp player.
|
if (sd->state.rewarp) { //Rewarp player.
|
||||||
sd->state.rewarp = 0;
|
sd->state.rewarp = 0;
|
||||||
clif_changemap(sd, sd->mapindex, sd->bl.x, sd->bl.y);
|
clif_changemap(sd, sd->bl.m, sd->bl.x, sd->bl.y);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -9379,7 +9390,8 @@ void clif_parse_LoadEndAck(int fd,struct map_session_data *sd)
|
|||||||
status_calc_pc(sd, false); // Some conditions are map-dependent so we must recalculate
|
status_calc_pc(sd, false); // Some conditions are map-dependent so we must recalculate
|
||||||
sd->state.changemap = false;
|
sd->state.changemap = false;
|
||||||
|
|
||||||
if( Channel_Config.map_enable && Channel_Config.map_autojoin && !map[sd->bl.m].flag.chmautojoin) {
|
// Instances do not need their own channels
|
||||||
|
if( Channel_Config.map_enable && Channel_Config.map_autojoin && !map[sd->bl.m].flag.chmautojoin && !map[sd->bl.m].instance_id ) {
|
||||||
channel_mjoin(sd); //join new map
|
channel_mjoin(sd); //join new map
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -9567,6 +9579,11 @@ void clif_parse_WalkToXY(int fd, struct map_session_data *sd)
|
|||||||
if(sd->sc.data[SC_RUN] || sd->sc.data[SC_WUGDASH])
|
if(sd->sc.data[SC_RUN] || sd->sc.data[SC_WUGDASH])
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
// Cloaking wall check is actually updated when you click to process next movement
|
||||||
|
// not when you move each cell. This is official behaviour.
|
||||||
|
if (sd->sc.data[SC_CLOAKING])
|
||||||
|
skill_check_cloaking(&sd->bl, sd->sc.data[SC_CLOAKING]);
|
||||||
|
|
||||||
pc_delinvincibletimer(sd);
|
pc_delinvincibletimer(sd);
|
||||||
|
|
||||||
RFIFOPOS(fd, packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0], &x, &y, NULL);
|
RFIFOPOS(fd, packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0], &x, &y, NULL);
|
||||||
|
@ -345,7 +345,7 @@ void clif_clearunit_delayed(struct block_list* bl, clr_type type, unsigned int t
|
|||||||
int clif_spawn(struct block_list *bl); //area
|
int clif_spawn(struct block_list *bl); //area
|
||||||
void clif_walkok(struct map_session_data *sd); // self
|
void clif_walkok(struct map_session_data *sd); // self
|
||||||
void clif_move(struct unit_data *ud); //area
|
void clif_move(struct unit_data *ud); //area
|
||||||
void clif_changemap(struct map_session_data *sd, short map, int x, int y); //self
|
void clif_changemap(struct map_session_data *sd, short m, int x, int y); //self
|
||||||
void clif_changemapserver(struct map_session_data* sd, unsigned short map_index, int x, int y, uint32 ip, uint16 port); //self
|
void clif_changemapserver(struct map_session_data* sd, unsigned short map_index, int x, int y, uint32 ip, uint16 port); //self
|
||||||
void clif_blown(struct block_list *bl); // area
|
void clif_blown(struct block_list *bl); // area
|
||||||
void clif_slide(struct block_list *bl, int x, int y); // area
|
void clif_slide(struct block_list *bl, int x, int y); // area
|
||||||
|
@ -369,7 +369,7 @@ int instance_mapname2mapid(const char *name, short instance_id)
|
|||||||
{
|
{
|
||||||
struct instance_data *im;
|
struct instance_data *im;
|
||||||
int m = map_mapname2mapid(name);
|
int m = map_mapname2mapid(name);
|
||||||
char iname[12];
|
char iname[MAP_NAME_LENGTH];
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
if(m < 0) {
|
if(m < 0) {
|
||||||
@ -377,6 +377,8 @@ int instance_mapname2mapid(const char *name, short instance_id)
|
|||||||
return m;
|
return m;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
strcpy(iname,name);
|
||||||
|
|
||||||
if(instance_id <= 0 || instance_id > MAX_INSTANCE_DATA)
|
if(instance_id <= 0 || instance_id > MAX_INSTANCE_DATA)
|
||||||
return m;
|
return m;
|
||||||
|
|
||||||
@ -386,8 +388,13 @@ int instance_mapname2mapid(const char *name, short instance_id)
|
|||||||
|
|
||||||
for(i = 0; i < MAX_MAP_PER_INSTANCE; i++)
|
for(i = 0; i < MAX_MAP_PER_INSTANCE; i++)
|
||||||
if(im->map[i].src_m == m) {
|
if(im->map[i].src_m == m) {
|
||||||
snprintf(iname, sizeof(iname), ((strchr(name,'@') == NULL)?"%.3d#%s":"%.3d%s"), instance_id, name);
|
char alt_name[MAP_NAME_LENGTH];
|
||||||
return mapindex_name2id(iname);
|
if((strchr(iname,'@') == NULL) && strlen(iname) > 8) {
|
||||||
|
memmove(iname, iname+(strlen(iname)-9), strlen(iname));
|
||||||
|
snprintf(alt_name, sizeof(alt_name),"%d#%s", instance_id, iname);
|
||||||
|
} else
|
||||||
|
snprintf(alt_name, sizeof(alt_name),"%.3d%s", instance_id, iname);
|
||||||
|
return map_mapname2mapid(alt_name);
|
||||||
}
|
}
|
||||||
|
|
||||||
return m;
|
return m;
|
||||||
@ -515,7 +522,7 @@ int instance_enter(struct map_session_data *sd, const char *name)
|
|||||||
if((m = instance_mapname2mapid(db->enter.mapname, p->instance_id)) < 0)
|
if((m = instance_mapname2mapid(db->enter.mapname, p->instance_id)) < 0)
|
||||||
return 3;
|
return 3;
|
||||||
|
|
||||||
if(pc_setpos(sd, m, db->enter.x, db->enter.y, 0))
|
if(pc_setpos(sd, map_id2index(m), db->enter.x, db->enter.y, 0))
|
||||||
return 3;
|
return 3;
|
||||||
|
|
||||||
// If there was an idle timer, let's stop it
|
// If there was an idle timer, let's stop it
|
||||||
|
@ -425,8 +425,6 @@ int map_moveblock(struct block_list *bl, int x1, int y1, unsigned int tick)
|
|||||||
if (sc->data[SC_DANCING])
|
if (sc->data[SC_DANCING])
|
||||||
skill_unit_move_unit_group(skill_id2group(sc->data[SC_DANCING]->val2), bl->m, x1-x0, y1-y0);
|
skill_unit_move_unit_group(skill_id2group(sc->data[SC_DANCING]->val2), bl->m, x1-x0, y1-y0);
|
||||||
else {
|
else {
|
||||||
if (sc->data[SC_CLOAKING])
|
|
||||||
skill_check_cloaking(bl, sc->data[SC_CLOAKING]);
|
|
||||||
if (sc->data[SC_WARM])
|
if (sc->data[SC_WARM])
|
||||||
skill_unit_move_unit_group(skill_id2group(sc->data[SC_WARM]->val4), bl->m, x1-x0, y1-y0);
|
skill_unit_move_unit_group(skill_id2group(sc->data[SC_WARM]->val4), bl->m, x1-x0, y1-y0);
|
||||||
if (sc->data[SC_BANDING])
|
if (sc->data[SC_BANDING])
|
||||||
@ -2181,6 +2179,7 @@ int map_addinstancemap(const char *name, int id)
|
|||||||
{
|
{
|
||||||
int src_m = map_mapname2mapid(name);
|
int src_m = map_mapname2mapid(name);
|
||||||
int dst_m = -1, i;
|
int dst_m = -1, i;
|
||||||
|
char iname[MAP_NAME_LENGTH];
|
||||||
size_t size;
|
size_t size;
|
||||||
|
|
||||||
if(src_m < 0)
|
if(src_m < 0)
|
||||||
@ -2209,8 +2208,16 @@ int map_addinstancemap(const char *name, int id)
|
|||||||
// Copy the map
|
// Copy the map
|
||||||
memcpy(&map[dst_m], &map[src_m], sizeof(struct map_data));
|
memcpy(&map[dst_m], &map[src_m], sizeof(struct map_data));
|
||||||
|
|
||||||
|
strcpy(iname,name);
|
||||||
|
|
||||||
// Alter the name
|
// Alter the name
|
||||||
snprintf(map[dst_m].name, sizeof(map[dst_m].name), ((strchr(name,'@') == NULL)?"%.3d#%s":"%.3d%s"), id, name);
|
// Due to this being custom we only worry about preserving as many characters as necessary for accurate map distinguishing
|
||||||
|
// This also allows us to maintain complete independence with main map functions
|
||||||
|
if((strchr(iname,'@') == NULL) && strlen(iname) > 8) {
|
||||||
|
memmove(iname, iname+(strlen(iname)-9), strlen(iname));
|
||||||
|
snprintf(map[dst_m].name, sizeof(map[dst_m].name),"%d#%s", id, iname);
|
||||||
|
} else
|
||||||
|
snprintf(map[dst_m].name, sizeof(map[dst_m].name),"%.3d%s", id, iname);
|
||||||
map[dst_m].name[MAP_NAME_LENGTH-1] = '\0';
|
map[dst_m].name[MAP_NAME_LENGTH-1] = '\0';
|
||||||
|
|
||||||
map[dst_m].m = dst_m;
|
map[dst_m].m = dst_m;
|
||||||
@ -2225,6 +2232,7 @@ int map_addinstancemap(const char *name, int id)
|
|||||||
map[dst_m].block_mob = (struct block_list **)aCalloc(1,size);
|
map[dst_m].block_mob = (struct block_list **)aCalloc(1,size);
|
||||||
|
|
||||||
map[dst_m].index = mapindex_addmap(-1, map[dst_m].name);
|
map[dst_m].index = mapindex_addmap(-1, map[dst_m].name);
|
||||||
|
map[dst_m].channel = NULL;
|
||||||
|
|
||||||
map_addmap2db(&map[dst_m]);
|
map_addmap2db(&map[dst_m]);
|
||||||
|
|
||||||
|
28
src/map/pc.c
28
src/map/pc.c
@ -1091,7 +1091,7 @@ bool pc_authok(struct map_session_data *sd, int login_id2, time_t expiration_tim
|
|||||||
/**
|
/**
|
||||||
* Fixes login-without-aura glitch (the screen won't blink at this point, don't worry :P)
|
* Fixes login-without-aura glitch (the screen won't blink at this point, don't worry :P)
|
||||||
**/
|
**/
|
||||||
clif_changemap(sd,sd->mapindex,sd->bl.x,sd->bl.y);
|
clif_changemap(sd,sd->bl.m,sd->bl.x,sd->bl.y);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -4211,7 +4211,7 @@ int pc_isUseitem(struct map_session_data *sd,int n)
|
|||||||
case 12243: // Mercenary's Berserk Potion
|
case 12243: // Mercenary's Berserk Potion
|
||||||
if( sd->md == NULL || sd->md->db == NULL )
|
if( sd->md == NULL || sd->md->db == NULL )
|
||||||
return 0;
|
return 0;
|
||||||
if (sd->md->sc.data[SC_BERSERK] || sd->md->sc.data[SC_SATURDAYNIGHTFEVER] || sd->md->sc.data[SC__BLOODYLUST])
|
if (sd->md->sc.data[SC_BERSERK] || sd->md->sc.data[SC_SATURDAYNIGHTFEVER])
|
||||||
return 0;
|
return 0;
|
||||||
if( nameid == 12242 && sd->md->db->lv < 40 )
|
if( nameid == 12242 && sd->md->db->lv < 40 )
|
||||||
return 0;
|
return 0;
|
||||||
@ -4308,7 +4308,7 @@ int pc_useitem(struct map_session_data *sd,int n)
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (sd->sc.count && (
|
if (sd->sc.count && (
|
||||||
sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_SATURDAYNIGHTFEVER] ||
|
sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAYNIGHTFEVER] ||
|
||||||
(sd->sc.data[SC_GRAVITATION] && sd->sc.data[SC_GRAVITATION]->val3 == BCT_SELF) ||
|
(sd->sc.data[SC_GRAVITATION] && sd->sc.data[SC_GRAVITATION]->val3 == BCT_SELF) ||
|
||||||
sd->sc.data[SC_TRICKDEAD] ||
|
sd->sc.data[SC_TRICKDEAD] ||
|
||||||
sd->sc.data[SC_HIDING] ||
|
sd->sc.data[SC_HIDING] ||
|
||||||
@ -4879,7 +4879,7 @@ int pc_setpos(struct map_session_data* sd, unsigned short mapindex, int x, int y
|
|||||||
|
|
||||||
if(sd->bl.prev != NULL){
|
if(sd->bl.prev != NULL){
|
||||||
unit_remove_map_pc(sd,clrtype);
|
unit_remove_map_pc(sd,clrtype);
|
||||||
clif_changemap(sd,map[m].index,x,y); // [MouseJstr]
|
clif_changemap(sd,m,x,y); // [MouseJstr]
|
||||||
} else if(sd->state.active) //Tag player for rewarping after map-loading is done. [Skotlex]
|
} else if(sd->state.active) //Tag player for rewarping after map-loading is done. [Skotlex]
|
||||||
sd->state.rewarp = 1;
|
sd->state.rewarp = 1;
|
||||||
|
|
||||||
@ -4992,6 +4992,11 @@ int pc_memo(struct map_session_data* sd, int pos)
|
|||||||
pos = 0;
|
pos = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if( map[sd->bl.m].instance_id ) {
|
||||||
|
clif_displaymessage( sd->fd, msg_txt(sd,384) ); // You cannot create a memo in an instance.
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
sd->status.memo_point[pos].map = map_id2index(sd->bl.m);
|
sd->status.memo_point[pos].map = map_id2index(sd->bl.m);
|
||||||
sd->status.memo_point[pos].x = sd->bl.x;
|
sd->status.memo_point[pos].x = sd->bl.x;
|
||||||
sd->status.memo_point[pos].y = sd->bl.y;
|
sd->status.memo_point[pos].y = sd->bl.y;
|
||||||
@ -8553,8 +8558,7 @@ int pc_equipitem(struct map_session_data *sd,int n,int req_pos)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( DIFF_TICK(sd->canequip_tick,gettick()) > 0 )
|
if( DIFF_TICK(sd->canequip_tick,gettick()) > 0 ) {
|
||||||
{
|
|
||||||
clif_equipitemack(sd,n,0,0);
|
clif_equipitemack(sd,n,0,0);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -8570,8 +8574,7 @@ int pc_equipitem(struct map_session_data *sd,int n,int req_pos)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAYNIGHTFEVER] || sd->sc.data[SC__BLOODYLUST])
|
if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAYNIGHTFEVER]) {
|
||||||
{
|
|
||||||
clif_equipitemack(sd,n,0,0); // fail
|
clif_equipitemack(sd,n,0,0); // fail
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -8582,15 +8585,14 @@ int pc_equipitem(struct map_session_data *sd,int n,int req_pos)
|
|||||||
pos = sd->equip_index[EQI_ACC_R] >= 0 ? EQP_ACC_L : EQP_ACC_R;
|
pos = sd->equip_index[EQI_ACC_R] >= 0 ? EQP_ACC_L : EQP_ACC_R;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(pos == EQP_ARMS && id->equip == EQP_HAND_R)
|
if(pos == EQP_ARMS && id->equip == EQP_HAND_R) { //Dual wield capable weapon.
|
||||||
{ //Dual wield capable weapon.
|
|
||||||
pos = (req_pos&EQP_ARMS);
|
pos = (req_pos&EQP_ARMS);
|
||||||
if (pos == EQP_ARMS) //User specified both slots, pick one for them.
|
if (pos == EQP_ARMS) //User specified both slots, pick one for them.
|
||||||
pos = sd->equip_index[EQI_HAND_R] >= 0 ? EQP_HAND_L : EQP_HAND_R;
|
pos = sd->equip_index[EQI_HAND_R] >= 0 ? EQP_HAND_L : EQP_HAND_R;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pos&EQP_HAND_R && battle_config.use_weapon_skill_range&BL_PC)
|
if (pos&EQP_HAND_R && battle_config.use_weapon_skill_range&BL_PC) {
|
||||||
{ //Update skill-block range database when weapon range changes. [Skotlex]
|
//Update skill-block range database when weapon range changes. [Skotlex]
|
||||||
i = sd->equip_index[EQI_HAND_R];
|
i = sd->equip_index[EQI_HAND_R];
|
||||||
if (i < 0 || !sd->inventory_data[i]) //No data, or no weapon equipped
|
if (i < 0 || !sd->inventory_data[i]) //No data, or no weapon equipped
|
||||||
flag = 1;
|
flag = 1;
|
||||||
@ -8607,7 +8609,7 @@ int pc_equipitem(struct map_session_data *sd,int n,int req_pos)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(pos==EQP_AMMO){
|
if(pos==EQP_AMMO) {
|
||||||
clif_arrowequip(sd,n);
|
clif_arrowequip(sd,n);
|
||||||
clif_arrow_fail(sd,3);
|
clif_arrow_fail(sd,3);
|
||||||
}
|
}
|
||||||
|
@ -250,7 +250,6 @@ struct map_session_data {
|
|||||||
unsigned int canskill_tick; // used to prevent abuse from no-delay ACT files
|
unsigned int canskill_tick; // used to prevent abuse from no-delay ACT files
|
||||||
unsigned int cansendmail_tick; // [Mail System Flood Protection]
|
unsigned int cansendmail_tick; // [Mail System Flood Protection]
|
||||||
unsigned int ks_floodprotect_tick; // [Kill Steal Protection]
|
unsigned int ks_floodprotect_tick; // [Kill Steal Protection]
|
||||||
unsigned int bloodylust_tick; // bloodylust player timer [out/in re full-heal protection]
|
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
short nameid;
|
short nameid;
|
||||||
|
@ -16561,21 +16561,18 @@ BUILDIN_FUNC(instance_npcname)
|
|||||||
BUILDIN_FUNC(instance_mapname)
|
BUILDIN_FUNC(instance_mapname)
|
||||||
{
|
{
|
||||||
const char *str;
|
const char *str;
|
||||||
char iname[12];
|
|
||||||
int16 m;
|
int16 m;
|
||||||
short instance_id = 0;
|
short instance_id = 0;
|
||||||
|
|
||||||
str = script_getstr(st,2);
|
str = script_getstr(st,2);
|
||||||
|
|
||||||
if( script_hasdata(st,3) )
|
if( script_hasdata(st,3) )
|
||||||
instance_id = script_getnum(st,3);
|
instance_id = script_getnum(st,3);
|
||||||
else
|
else
|
||||||
instance_id = script_instancegetid(st);
|
instance_id = script_instancegetid(st);
|
||||||
|
|
||||||
// Build the instance mapname
|
|
||||||
snprintf(iname, sizeof(iname), ((strchr(str,'@') == NULL)?"%.3d#%s":"%.3d%s"), instance_id, str);
|
|
||||||
|
|
||||||
// Check that instance mapname is a valid map
|
// Check that instance mapname is a valid map
|
||||||
if( !instance_id || (m = map_mapname2mapid(iname)) < 0 )
|
if(!instance_id || (m = instance_mapname2mapid(str,instance_id)) < 0)
|
||||||
script_pushconststr(st, "");
|
script_pushconststr(st, "");
|
||||||
else
|
else
|
||||||
script_pushconststr(st, map[m].name);
|
script_pushconststr(st, map[m].name);
|
||||||
@ -16616,7 +16613,6 @@ BUILDIN_FUNC(instance_warpall)
|
|||||||
short instance_id;
|
short instance_id;
|
||||||
const char *mapn;
|
const char *mapn;
|
||||||
int x, y;
|
int x, y;
|
||||||
unsigned short mapindex;
|
|
||||||
|
|
||||||
mapn = script_getstr(st,2);
|
mapn = script_getstr(st,2);
|
||||||
x = script_getnum(st,3);
|
x = script_getnum(st,3);
|
||||||
@ -16632,9 +16628,8 @@ BUILDIN_FUNC(instance_warpall)
|
|||||||
if( !(p = party_search(instance_data[instance_id].party_id)) )
|
if( !(p = party_search(instance_data[instance_id].party_id)) )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
mapindex = map_id2index(m);
|
|
||||||
for( i = 0; i < MAX_PARTY; i++ )
|
for( i = 0; i < MAX_PARTY; i++ )
|
||||||
if( (pl_sd = p->data[i].sd) && map[pl_sd->bl.m].instance_id == instance_id ) pc_setpos(pl_sd,mapindex,x,y,CLR_TELEPORT);
|
if( (pl_sd = p->data[i].sd) && map[pl_sd->bl.m].instance_id == instance_id ) pc_setpos(pl_sd,map_id2index(m),x,y,CLR_TELEPORT);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
103
src/map/skill.c
103
src/map/skill.c
@ -5028,7 +5028,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
dstsd = sd;
|
dstsd = sd;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (tsc->data[SC_BERSERK] || tsc->data[SC_SATURDAYNIGHTFEVER] || tsc->data[SC__BLOODYLUST])
|
else if (tsc->data[SC_BERSERK] || tsc->data[SC_SATURDAYNIGHTFEVER])
|
||||||
heal = 0; //Needed so that it actually displays 0 when healing.
|
heal = 0; //Needed so that it actually displays 0 when healing.
|
||||||
}
|
}
|
||||||
clif_skill_nodamage (src, bl, skill_id, heal, 1);
|
clif_skill_nodamage (src, bl, skill_id, heal, 1);
|
||||||
@ -10081,6 +10081,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
case SC_DIMENSIONDOOR:
|
case SC_DIMENSIONDOOR:
|
||||||
case SC_CHAOSPANIC:
|
case SC_CHAOSPANIC:
|
||||||
case SC_MAELSTROM:
|
case SC_MAELSTROM:
|
||||||
|
case SC_BLOODYLUST:
|
||||||
case WM_REVERBERATION:
|
case WM_REVERBERATION:
|
||||||
case WM_SEVERE_RAINSTORM:
|
case WM_SEVERE_RAINSTORM:
|
||||||
case WM_POEMOFNETHERWORLD:
|
case WM_POEMOFNETHERWORLD:
|
||||||
@ -10565,11 +10566,6 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
sc_start2(src,src, type, 100, skill_id, skill_lv, skill_get_time(skill_id, skill_lv)));
|
sc_start2(src,src, type, 100, skill_id, skill_lv, skill_get_time(skill_id, skill_lv)));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case SC_BLOODYLUST: //set in another group so instance will move if recasted
|
|
||||||
flag |= 33;
|
|
||||||
skill_unitsetting(src, skill_id, skill_lv, x, y, 0);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case KO_MAKIBISHI:
|
case KO_MAKIBISHI:
|
||||||
for( i = 0; i < (skill_lv+2); i++ ) {
|
for( i = 0; i < (skill_lv+2); i++ ) {
|
||||||
x = src->x - 1 + rnd()%3;
|
x = src->x - 1 + rnd()%3;
|
||||||
@ -10629,7 +10625,7 @@ int skill_castend_map (struct map_session_data *sd, uint16 skill_id, const char
|
|||||||
sd->sc.data[SC_AUTOCOUNTER] ||
|
sd->sc.data[SC_AUTOCOUNTER] ||
|
||||||
sd->sc.data[SC_STEELBODY] ||
|
sd->sc.data[SC_STEELBODY] ||
|
||||||
(sd->sc.data[SC_DANCING] && skill_id < RK_ENCHANTBLADE && !pc_checkskill(sd, WM_LESSON)) ||
|
(sd->sc.data[SC_DANCING] && skill_id < RK_ENCHANTBLADE && !pc_checkskill(sd, WM_LESSON)) ||
|
||||||
sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] ||
|
sd->sc.data[SC_BERSERK] ||
|
||||||
sd->sc.data[SC_BASILICA] ||
|
sd->sc.data[SC_BASILICA] ||
|
||||||
sd->sc.data[SC_MARIONETTE] ||
|
sd->sc.data[SC_MARIONETTE] ||
|
||||||
sd->sc.data[SC_WHITEIMPRISON] ||
|
sd->sc.data[SC_WHITEIMPRISON] ||
|
||||||
@ -11163,9 +11159,6 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill
|
|||||||
case SO_VACUUM_EXTREME:
|
case SO_VACUUM_EXTREME:
|
||||||
range++;
|
range++;
|
||||||
|
|
||||||
break;
|
|
||||||
case SC_BLOODYLUST:
|
|
||||||
skill_clear_group(src, 32);
|
|
||||||
break;
|
break;
|
||||||
case GN_WALLOFTHORN:
|
case GN_WALLOFTHORN:
|
||||||
if( flag&1 )
|
if( flag&1 )
|
||||||
@ -11299,6 +11292,9 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill
|
|||||||
if (unit_flag&UF_RANGEDSINGLEUNIT && i == (layout->count / 2))
|
if (unit_flag&UF_RANGEDSINGLEUNIT && i == (layout->count / 2))
|
||||||
val2 |= UF_RANGEDSINGLEUNIT; // center.
|
val2 |= UF_RANGEDSINGLEUNIT; // center.
|
||||||
|
|
||||||
|
if( sd && map_getcell(src->m, ux, uy, CELL_CHKMAELSTROM) ) //Does not recover SP from monster skills
|
||||||
|
map_foreachincell(skill_maelstrom_suction,src->m,ux,uy,BL_SKILL,skill_id,skill_lv);
|
||||||
|
|
||||||
if( range <= 0 )
|
if( range <= 0 )
|
||||||
map_foreachincell(skill_cell_overlap,src->m,ux,uy,BL_SKILL,skill_id, &alive, src);
|
map_foreachincell(skill_cell_overlap,src->m,ux,uy,BL_SKILL,skill_id, &alive, src);
|
||||||
if( !alive )
|
if( !alive )
|
||||||
@ -11360,7 +11356,8 @@ static int skill_unit_onplace (struct skill_unit *src, struct block_list *bl, un
|
|||||||
nullpo_ret(sg=src->group);
|
nullpo_ret(sg=src->group);
|
||||||
nullpo_ret(ss=map_id2bl(sg->src_id));
|
nullpo_ret(ss=map_id2bl(sg->src_id));
|
||||||
|
|
||||||
if( skill_get_type(sg->skill_id) == BF_MAGIC && map_getcell(bl->m, bl->x, bl->y, CELL_CHKLANDPROTECTOR) && sg->skill_id != SA_LANDPROTECTOR )
|
if( (skill_get_type(sg->skill_id) == BF_MAGIC && map_getcell(bl->m, bl->x, bl->y, CELL_CHKLANDPROTECTOR) && sg->skill_id != SA_LANDPROTECTOR) ||
|
||||||
|
map_getcell(bl->m, bl->x, bl->y, CELL_CHKMAELSTROM) )
|
||||||
return 0; //AoE skills are ineffective. [Skotlex]
|
return 0; //AoE skills are ineffective. [Skotlex]
|
||||||
|
|
||||||
if( skill_get_inf2(sg->skill_id)&(INF2_SONG_DANCE|INF2_ENSEMBLE_SKILL) && map_getcell(bl->m, bl->x, bl->y, CELL_CHKBASILICA) )
|
if( skill_get_inf2(sg->skill_id)&(INF2_SONG_DANCE|INF2_ENSEMBLE_SKILL) && map_getcell(bl->m, bl->x, bl->y, CELL_CHKBASILICA) )
|
||||||
@ -11400,26 +11397,17 @@ static int skill_unit_onplace (struct skill_unit *src, struct block_list *bl, un
|
|||||||
sc_start4(ss, bl,type,100,sg->skill_lv,sg->skill_id,sg->group_id,0,sg->limit);
|
sc_start4(ss, bl,type,100,sg->skill_lv,sg->skill_id,sg->group_id,0,sg->limit);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_PNEUMA:
|
|
||||||
case UNT_CHAOSPANIC:
|
|
||||||
case UNT_MAELSTROM:
|
|
||||||
if (!sce)
|
|
||||||
sc_start4(ss, bl,type,100,sg->skill_lv,sg->group_id,0,0,sg->limit);
|
|
||||||
break;
|
|
||||||
case UNT_BLOODYLUST:
|
case UNT_BLOODYLUST:
|
||||||
if (sg->src_id == bl->id)
|
if (sg->src_id == bl->id)
|
||||||
break; //Does not affect the caster.
|
break; //Does not affect the caster.
|
||||||
if (!sce) {
|
if( !sce && sc_start4(ss, bl,type,100,sg->skill_lv,0,SC__BLOODYLUST,0,sg->limit) )
|
||||||
TBL_PC *sd = BL_CAST(BL_PC, bl); //prevent fullheal exploit
|
sc_start(ss, bl,SC__BLOODYLUST,100,sg->skill_lv,sg->limit);
|
||||||
if (sd && sd->bloodylust_tick && DIFF_TICK(gettick(), sd->bloodylust_tick) < skill_get_time2(SC_BLOODYLUST, 1))
|
break;
|
||||||
clif_skill_nodamage(&src->bl,bl,sg->skill_id,sg->skill_lv,
|
|
||||||
sc_start4(ss, bl, type, 100, sg->skill_lv, 1, 0, 0, skill_get_time(LK_BERSERK, sg->skill_lv)));
|
case UNT_PNEUMA:
|
||||||
else {
|
case UNT_CHAOSPANIC:
|
||||||
if (sd) sd->bloodylust_tick = gettick();
|
if (!sce)
|
||||||
clif_skill_nodamage(&src->bl,bl,sg->skill_id,sg->skill_lv,
|
sc_start4(ss, bl,type,100,sg->skill_lv,sg->group_id,0,0,sg->limit);
|
||||||
sc_start4(ss, bl, type, 100, sg->skill_lv, 0, 0, 0, skill_get_time(LK_BERSERK, sg->skill_lv)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_WARP_WAITING: {
|
case UNT_WARP_WAITING: {
|
||||||
@ -12413,15 +12401,10 @@ int skill_unit_onleft (uint16 skill_id, struct block_list *bl, unsigned int tick
|
|||||||
case SO_WATER_INSIGNIA:
|
case SO_WATER_INSIGNIA:
|
||||||
case SO_WIND_INSIGNIA:
|
case SO_WIND_INSIGNIA:
|
||||||
case SO_EARTH_INSIGNIA:
|
case SO_EARTH_INSIGNIA:
|
||||||
|
case SC_BLOODYLUST:
|
||||||
if (sce)
|
if (sce)
|
||||||
status_change_end(bl, type, INVALID_TIMER);
|
status_change_end(bl, type, INVALID_TIMER);
|
||||||
break;
|
break;
|
||||||
case SC_BLOODYLUST:
|
|
||||||
if (sce) {
|
|
||||||
status_change_end(bl, type, INVALID_TIMER);
|
|
||||||
status_set_sp(bl, 0, 0); //set sp to 0 when quitting zone
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case BA_DISSONANCE:
|
case BA_DISSONANCE:
|
||||||
case DC_UGLYDANCE: //Used for updating song timers in overlap instances
|
case DC_UGLYDANCE: //Used for updating song timers in overlap instances
|
||||||
{
|
{
|
||||||
@ -12908,6 +12891,22 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case AS_CLOAKING:
|
||||||
|
{
|
||||||
|
static int dx[] = { 0, 1, 0, -1, -1, 1, 1, -1};
|
||||||
|
static int dy[] = {-1, 0, 1, 0, -1, -1, 1, 1};
|
||||||
|
|
||||||
|
if( (sd->bl.type == BL_PC && battle_config.pc_cloak_check_type&1)
|
||||||
|
|| (sd->bl.type != BL_PC && battle_config.monster_cloak_check_type&1) ) { //Check for walls.
|
||||||
|
int i;
|
||||||
|
ARR_FIND( 0, 8, i, map_getcell(sd->bl.m, sd->bl.x+dx[i], sd->bl.y+dy[i], CELL_CHKNOPASS) != 0 );
|
||||||
|
if( i == 8 ) {
|
||||||
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
case AL_WARP:
|
case AL_WARP:
|
||||||
if(!battle_config.duel_allow_teleport && sd->duel_group) { // duel restriction [LuzZza]
|
if(!battle_config.duel_allow_teleport && sd->duel_group) { // duel restriction [LuzZza]
|
||||||
char output[128]; sprintf(output, msg_txt(sd,365), skill_get_name(AL_WARP));
|
char output[128]; sprintf(output, msg_txt(sd,365), skill_get_name(AL_WARP));
|
||||||
@ -15002,10 +15001,6 @@ int skill_clear_group (struct block_list *bl, int flag)
|
|||||||
if( flag&8 )
|
if( flag&8 )
|
||||||
group[count++]= ud->skillunit[i];
|
group[count++]= ud->skillunit[i];
|
||||||
break;
|
break;
|
||||||
case SC_BLOODYLUST:
|
|
||||||
if (flag & 32)
|
|
||||||
group[count++] = ud->skillunit[i];
|
|
||||||
break;
|
|
||||||
default:
|
default:
|
||||||
if (flag&2 && skill_get_inf2(ud->skillunit[i]->skill_id)&INF2_TRAP)
|
if (flag&2 && skill_get_inf2(ud->skillunit[i]->skill_id)&INF2_TRAP)
|
||||||
group[count++]= ud->skillunit[i];
|
group[count++]= ud->skillunit[i];
|
||||||
@ -15036,7 +15031,6 @@ struct skill_unit_group *skill_locate_element_field(struct block_list *bl)
|
|||||||
case SA_LANDPROTECTOR:
|
case SA_LANDPROTECTOR:
|
||||||
case NJ_SUITON:
|
case NJ_SUITON:
|
||||||
case SO_WARMER:
|
case SO_WARMER:
|
||||||
case SC_BLOODYLUST:
|
|
||||||
return ud->skillunit[i];
|
return ud->skillunit[i];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -15317,6 +15311,34 @@ static int skill_trap_splash (struct block_list *bl, va_list ap)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int skill_maelstrom_suction(struct block_list *bl, va_list ap)
|
||||||
|
{
|
||||||
|
uint16 skill_id, skill_lv;
|
||||||
|
struct skill_unit *unit;
|
||||||
|
|
||||||
|
skill_id = va_arg(ap,int);
|
||||||
|
skill_lv = va_arg(ap,int);
|
||||||
|
unit = (struct skill_unit *)bl;
|
||||||
|
|
||||||
|
if( unit == NULL || unit->group == NULL )
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if( skill_get_inf2(skill_id)&INF2_TRAP )
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if( unit->group->skill_id == SC_MAELSTROM ){
|
||||||
|
struct block_list *src;
|
||||||
|
if( (src = map_id2bl(unit->group->src_id)) ){
|
||||||
|
int sp = unit->group->skill_lv * skill_lv;
|
||||||
|
if( src->type == BL_PC )
|
||||||
|
sp += ((TBL_PC*)src)->status.job_level / 5;
|
||||||
|
status_heal(src, 0, sp/2, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
*
|
*
|
||||||
*------------------------------------------*/
|
*------------------------------------------*/
|
||||||
@ -15405,6 +15427,9 @@ struct skill_unit *skill_initunit (struct skill_unit_group *group, int idx, int
|
|||||||
nullpo_retr(NULL, group->unit); // crash-protection against poor coding
|
nullpo_retr(NULL, group->unit); // crash-protection against poor coding
|
||||||
nullpo_retr(NULL, unit=&group->unit[idx]);
|
nullpo_retr(NULL, unit=&group->unit[idx]);
|
||||||
|
|
||||||
|
if( map_getcell(map_id2bl(group->src_id)->m, x, y, CELL_CHKMAELSTROM) )
|
||||||
|
return unit;
|
||||||
|
|
||||||
if(!unit->alive)
|
if(!unit->alive)
|
||||||
group->alive_count++;
|
group->alive_count++;
|
||||||
|
|
||||||
|
@ -1865,6 +1865,7 @@ struct s_skill_magicmushroom_db {
|
|||||||
uint16 skill_id;
|
uint16 skill_id;
|
||||||
};
|
};
|
||||||
extern struct s_skill_magicmushroom_db skill_magicmushroom_db[MAX_SKILL_MAGICMUSHROOM_DB];
|
extern struct s_skill_magicmushroom_db skill_magicmushroom_db[MAX_SKILL_MAGICMUSHROOM_DB];
|
||||||
|
int skill_maelstrom_suction(struct block_list *bl, va_list ap);
|
||||||
/**
|
/**
|
||||||
* Ranger
|
* Ranger
|
||||||
**/
|
**/
|
||||||
|
@ -496,10 +496,10 @@ void initChangeTables(void) {
|
|||||||
set_sc(MH_PAIN_KILLER , SC_PAIN_KILLER , SI_PAIN_KILLER , SCB_ASPD );
|
set_sc(MH_PAIN_KILLER , SC_PAIN_KILLER , SI_PAIN_KILLER , SCB_ASPD );
|
||||||
|
|
||||||
add_sc(MH_STYLE_CHANGE , SC_STYLE_CHANGE );
|
add_sc(MH_STYLE_CHANGE , SC_STYLE_CHANGE );
|
||||||
set_sc(MH_TINDER_BREAKER , SC_TINDER_BREAKER2 , SI_TINDER_BREAKER, SCB_FLEE );
|
set_sc(MH_TINDER_BREAKER , SC_TINDER_BREAKER2 , SI_TINDER_BREAKER , SCB_FLEE );
|
||||||
set_sc(MH_TINDER_BREAKER , SC_TINDER_BREAKER , SI_TINDER_BREAKER_POSTDELAY, SCB_FLEE );
|
set_sc(MH_TINDER_BREAKER , SC_TINDER_BREAKER , SI_TINDER_BREAKER_POSTDELAY , SCB_FLEE );
|
||||||
set_sc(MH_CBC , SC_CBC, SI_CBC , SCB_FLEE );
|
set_sc(MH_CBC , SC_CBC , SI_CBC , SCB_FLEE );
|
||||||
set_sc(MH_EQC , SC_EQC, SI_EQC , SCB_DEF2|SCB_BATK|SCB_MAXHP );
|
set_sc(MH_EQC , SC_EQC , SI_EQC , SCB_DEF2|SCB_BATK|SCB_MAXHP );
|
||||||
|
|
||||||
add_sc( MER_CRASH , SC_STUN );
|
add_sc( MER_CRASH , SC_STUN );
|
||||||
set_sc( MER_PROVOKE , SC_PROVOKE , SI_PROVOKE , SCB_DEF|SCB_DEF2|SCB_BATK|SCB_WATK );
|
set_sc( MER_PROVOKE , SC_PROVOKE , SI_PROVOKE , SCB_DEF|SCB_DEF2|SCB_BATK|SCB_WATK );
|
||||||
@ -635,7 +635,7 @@ void initChangeTables(void) {
|
|||||||
set_sc( SC_STRIPACCESSARY , SC__STRIPACCESSORY , SI_STRIPACCESSARY , SCB_DEX|SCB_INT|SCB_LUK );
|
set_sc( SC_STRIPACCESSARY , SC__STRIPACCESSORY , SI_STRIPACCESSARY , SCB_DEX|SCB_INT|SCB_LUK );
|
||||||
set_sc_with_vfx( SC_MANHOLE , SC__MANHOLE , SI_MANHOLE , SCB_NONE );
|
set_sc_with_vfx( SC_MANHOLE , SC__MANHOLE , SI_MANHOLE , SCB_NONE );
|
||||||
add_sc( SC_CHAOSPANIC , SC_CONFUSION );
|
add_sc( SC_CHAOSPANIC , SC_CONFUSION );
|
||||||
set_sc_with_vfx( SC_BLOODYLUST , SC__BLOODYLUST , SI_BERSERK , SCB_DEF | SCB_DEF2 | SCB_MDEF | SCB_MDEF2 | SCB_FLEE | SCB_SPEED | SCB_ASPD | SCB_MAXHP | SCB_REGEN );
|
add_sc( SC_BLOODYLUST , SC_BERSERK );
|
||||||
/**
|
/**
|
||||||
* Sura
|
* Sura
|
||||||
**/
|
**/
|
||||||
@ -1048,7 +1048,6 @@ void initChangeTables(void) {
|
|||||||
StatusChangeStateTable[SC_BERSERK] |= SCS_NOCHAT;
|
StatusChangeStateTable[SC_BERSERK] |= SCS_NOCHAT;
|
||||||
StatusChangeStateTable[SC_SATURDAYNIGHTFEVER] |= SCS_NOCHAT;
|
StatusChangeStateTable[SC_SATURDAYNIGHTFEVER] |= SCS_NOCHAT;
|
||||||
StatusChangeStateTable[SC_DEEPSLEEP] |= SCS_NOCHAT;
|
StatusChangeStateTable[SC_DEEPSLEEP] |= SCS_NOCHAT;
|
||||||
StatusChangeStateTable[SC__BLOODYLUST] |= SCS_NOCHAT;
|
|
||||||
StatusChangeStateTable[SC_NOCHAT] |= SCS_NOCHAT|SCS_NOCHATCOND;
|
StatusChangeStateTable[SC_NOCHAT] |= SCS_NOCHAT|SCS_NOCHATCOND;
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -1233,8 +1232,6 @@ int status_damage(struct block_list *src,struct block_list *target,int hp, int s
|
|||||||
status_change_end(target, SC_RAISINGDRAGON, INVALID_TIMER);
|
status_change_end(target, SC_RAISINGDRAGON, INVALID_TIMER);
|
||||||
if (sc->data[SC_SATURDAYNIGHTFEVER] && status->hp <= 100)
|
if (sc->data[SC_SATURDAYNIGHTFEVER] && status->hp <= 100)
|
||||||
status_change_end(target, SC_SATURDAYNIGHTFEVER, INVALID_TIMER);
|
status_change_end(target, SC_SATURDAYNIGHTFEVER, INVALID_TIMER);
|
||||||
if (sc->data[SC__BLOODYLUST] && status->hp <= 100)
|
|
||||||
status_change_end(target, SC__BLOODYLUST, INVALID_TIMER);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (target->type) {
|
switch (target->type) {
|
||||||
@ -1367,7 +1364,7 @@ int status_heal(struct block_list *bl,int hp,int sp, int flag)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if(hp) {
|
if(hp) {
|
||||||
if( sc && (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) ) {
|
if( sc && (sc->data[SC_BERSERK]) ) {
|
||||||
if( flag&1 )
|
if( flag&1 )
|
||||||
flag &= ~2;
|
flag &= ~2;
|
||||||
else
|
else
|
||||||
@ -3488,7 +3485,7 @@ void status_calc_regen_rate(struct block_list *bl, struct regen_data *regen, str
|
|||||||
if (
|
if (
|
||||||
(sc->data[SC_POISON] && !sc->data[SC_SLOWPOISON])
|
(sc->data[SC_POISON] && !sc->data[SC_SLOWPOISON])
|
||||||
|| (sc->data[SC_DPOISON] && !sc->data[SC_SLOWPOISON])
|
|| (sc->data[SC_DPOISON] && !sc->data[SC_SLOWPOISON])
|
||||||
|| sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]
|
|| sc->data[SC_BERSERK]
|
||||||
|| sc->data[SC_TRICKDEAD]
|
|| sc->data[SC_TRICKDEAD]
|
||||||
|| sc->data[SC_BLEEDING]
|
|| sc->data[SC_BLEEDING]
|
||||||
|| sc->data[SC_MAGICMUSHROOM]
|
|| sc->data[SC_MAGICMUSHROOM]
|
||||||
@ -4910,7 +4907,7 @@ static signed short status_calc_flee(struct block_list *bl, struct status_change
|
|||||||
flee += flee * sc->data[SC_INCFLEERATE]->val1/100;
|
flee += flee * sc->data[SC_INCFLEERATE]->val1/100;
|
||||||
if(sc->data[SC_SPIDERWEB] && sc->data[SC_SPIDERWEB]->val1)
|
if(sc->data[SC_SPIDERWEB] && sc->data[SC_SPIDERWEB]->val1)
|
||||||
flee -= flee * 50/100;
|
flee -= flee * 50/100;
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
flee -= flee * 50/100;
|
flee -= flee * 50/100;
|
||||||
if(sc->data[SC_BLIND])
|
if(sc->data[SC_BLIND])
|
||||||
flee -= flee * 25/100;
|
flee -= flee * 25/100;
|
||||||
@ -4957,7 +4954,7 @@ static defType status_calc_def(struct block_list *bl, struct status_change *sc,
|
|||||||
if(!sc || !sc->count)
|
if(!sc || !sc->count)
|
||||||
return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX);
|
return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX);
|
||||||
|
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
return 0;
|
return 0;
|
||||||
if(sc->data[SC_SKA])
|
if(sc->data[SC_SKA])
|
||||||
return sc->data[SC_SKA]->val3;
|
return sc->data[SC_SKA]->val3;
|
||||||
@ -5037,7 +5034,7 @@ static signed short status_calc_def2(struct block_list *bl, struct status_change
|
|||||||
return (short)cap_value(def2,1,SHRT_MAX);
|
return (short)cap_value(def2,1,SHRT_MAX);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
return 0;
|
return 0;
|
||||||
if(sc->data[SC_ETERNALCHAOS])
|
if(sc->data[SC_ETERNALCHAOS])
|
||||||
return 0;
|
return 0;
|
||||||
@ -5095,7 +5092,7 @@ static defType status_calc_mdef(struct block_list *bl, struct status_change *sc,
|
|||||||
if(!sc || !sc->count)
|
if(!sc || !sc->count)
|
||||||
return (defType)cap_value(mdef,DEFTYPE_MIN,DEFTYPE_MAX);
|
return (defType)cap_value(mdef,DEFTYPE_MIN,DEFTYPE_MAX);
|
||||||
|
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
return 0;
|
return 0;
|
||||||
if(sc->data[SC_BARRIER])
|
if(sc->data[SC_BARRIER])
|
||||||
return 100;
|
return 100;
|
||||||
@ -5145,7 +5142,7 @@ static signed short status_calc_mdef2(struct block_list *bl, struct status_chang
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
return 0;
|
return 0;
|
||||||
if(sc->data[SC_SKA])
|
if(sc->data[SC_SKA])
|
||||||
return 90;
|
return 90;
|
||||||
@ -5290,7 +5287,7 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha
|
|||||||
val = max( val, 1 * pc_checkskill(sd,TF_MISS) );
|
val = max( val, 1 * pc_checkskill(sd,TF_MISS) );
|
||||||
if( sc->data[SC_CLOAKING] && (sc->data[SC_CLOAKING]->val4&1) == 1 )
|
if( sc->data[SC_CLOAKING] && (sc->data[SC_CLOAKING]->val4&1) == 1 )
|
||||||
val = max( val, sc->data[SC_CLOAKING]->val1 >= 10 ? 25 : 3 * sc->data[SC_CLOAKING]->val1 - 3 );
|
val = max( val, sc->data[SC_CLOAKING]->val1 >= 10 ? 25 : 3 * sc->data[SC_CLOAKING]->val1 - 3 );
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if( sc->data[SC_BERSERK] )
|
||||||
val = max( val, 25 );
|
val = max( val, 25 );
|
||||||
if( sc->data[SC_RUN] )
|
if( sc->data[SC_RUN] )
|
||||||
val = max( val, 55 );
|
val = max( val, 55 );
|
||||||
@ -5405,7 +5402,7 @@ static short status_calc_aspd(struct block_list *bl, struct status_change *sc, s
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if((sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) && skills1 < 15)
|
if(sc->data[SC_BERSERK] && skills1 < 15)
|
||||||
skills1 = 15;
|
skills1 = 15;
|
||||||
else if(sc->data[SC_MADNESSCANCEL] && skills1 < 15) // needs more info
|
else if(sc->data[SC_MADNESSCANCEL] && skills1 < 15) // needs more info
|
||||||
skills1 = 15;
|
skills1 = 15;
|
||||||
@ -5550,7 +5547,7 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change *
|
|||||||
}
|
}
|
||||||
aspd_rate -= max;
|
aspd_rate -= max;
|
||||||
|
|
||||||
if((sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]))
|
if(sc->data[SC_BERSERK])
|
||||||
aspd_rate -= 300;
|
aspd_rate -= 300;
|
||||||
else if(sc->data[SC_MADNESSCANCEL])
|
else if(sc->data[SC_MADNESSCANCEL])
|
||||||
aspd_rate -= 200;
|
aspd_rate -= 200;
|
||||||
@ -5652,7 +5649,7 @@ static unsigned int status_calc_maxhp(struct block_list *bl, struct status_chang
|
|||||||
maxhp += maxhp * sc->data[SC_APPLEIDUN]->val2/100;
|
maxhp += maxhp * sc->data[SC_APPLEIDUN]->val2/100;
|
||||||
if(sc->data[SC_DELUGE])
|
if(sc->data[SC_DELUGE])
|
||||||
maxhp += maxhp * sc->data[SC_DELUGE]->val2/100;
|
maxhp += maxhp * sc->data[SC_DELUGE]->val2/100;
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])
|
if(sc->data[SC_BERSERK])
|
||||||
maxhp += maxhp * 2;
|
maxhp += maxhp * 2;
|
||||||
if(sc->data[SC_MARIONETTE])
|
if(sc->data[SC_MARIONETTE])
|
||||||
maxhp -= 1000;
|
maxhp -= 1000;
|
||||||
@ -6310,7 +6307,6 @@ int status_get_sc_def(struct block_list *src, struct block_list *bl, enum sc_typ
|
|||||||
case SC__LAZINESS:
|
case SC__LAZINESS:
|
||||||
case SC__UNLUCKY:
|
case SC__UNLUCKY:
|
||||||
case SC__WEAKNESS:
|
case SC__WEAKNESS:
|
||||||
case SC__BLOODYLUST:
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -6690,12 +6686,8 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
//There all like berserk, do not everlap each other
|
//There all like berserk, do not everlap each other
|
||||||
case SC__BLOODYLUST:
|
|
||||||
if(!sd) return 0; //should only affect player
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
if (((type == SC_BERSERK) && (sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC__BLOODYLUST]))
|
if(sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC__BLOODYLUST])
|
||||||
|| ((type == SC__BLOODYLUST) && (sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC_BERSERK]))
|
|
||||||
)
|
|
||||||
return 0;
|
return 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -6946,7 +6938,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC_SATURDAYNIGHTFEVER:
|
case SC_SATURDAYNIGHTFEVER:
|
||||||
if (sc->data[SC_BERSERK] || sc->data[SC_INSPIRATION] || sc->data[SC__BLOODYLUST])
|
if (sc->data[SC_BERSERK] || sc->data[SC_INSPIRATION])
|
||||||
return 0;
|
return 0;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -7067,8 +7059,9 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
status_change_end(bl, SC_CLOSECONFINE, INVALID_TIMER);
|
status_change_end(bl, SC_CLOSECONFINE, INVALID_TIMER);
|
||||||
status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER);
|
status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER);
|
||||||
break;
|
break;
|
||||||
case SC__BLOODYLUST:
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
|
if( val3 == SC__BLOODYLUST )
|
||||||
|
break;
|
||||||
if(battle_config.berserk_cancels_buffs) {
|
if(battle_config.berserk_cancels_buffs) {
|
||||||
status_change_end(bl, SC_ONEHAND, INVALID_TIMER);
|
status_change_end(bl, SC_ONEHAND, INVALID_TIMER);
|
||||||
status_change_end(bl, SC_TWOHANDQUICKEN, INVALID_TIMER);
|
status_change_end(bl, SC_TWOHANDQUICKEN, INVALID_TIMER);
|
||||||
@ -7324,7 +7317,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
val4 = sce->val4;
|
val4 = sce->val4;
|
||||||
break;
|
break;
|
||||||
case SC_LERADSDEW:
|
case SC_LERADSDEW:
|
||||||
if (sc && (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]))
|
if (sc && sc->data[SC_BERSERK])
|
||||||
return 0;
|
return 0;
|
||||||
case SC_SHAPESHIFT:
|
case SC_SHAPESHIFT:
|
||||||
case SC_PROPERTYWALK:
|
case SC_PROPERTYWALK:
|
||||||
@ -7785,9 +7778,10 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
if (!sc->data[SC_ENDURE] || !sc->data[SC_ENDURE]->val4)
|
if( val3 == SC__BLOODYLUST )
|
||||||
|
sc_start(src,bl,(sc_type)val3,100,val1,tick);
|
||||||
|
if (!val3 && !(sc->data[SC_ENDURE] && sc->data[SC_ENDURE]->val4))
|
||||||
sc_start4(src,bl, SC_ENDURE, 100,10,0,0,2, tick);
|
sc_start4(src,bl, SC_ENDURE, 100,10,0,0,2, tick);
|
||||||
case SC__BLOODYLUST:
|
|
||||||
//HP healing is performing after the calc_status call.
|
//HP healing is performing after the calc_status call.
|
||||||
//Val2 holds HP penalty
|
//Val2 holds HP penalty
|
||||||
if (!val4) val4 = skill_get_time2(status_sc2skill(type),val1);
|
if (!val4) val4 = skill_get_time2(status_sc2skill(type),val1);
|
||||||
@ -8962,7 +8956,6 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
break;
|
break;
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
opt_flag = 0;
|
opt_flag = 0;
|
||||||
// case SC__BLOODYLUST:
|
|
||||||
sc->opt3 |= OPT3_BERSERK;
|
sc->opt3 |= OPT3_BERSERK;
|
||||||
break;
|
break;
|
||||||
// case ???: // doesn't seem to do anything
|
// case ???: // doesn't seem to do anything
|
||||||
@ -9101,7 +9094,6 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
pet_sc_check(sd, type); //Skotlex: Pet Status Effect Healing
|
pet_sc_check(sd, type); //Skotlex: Pet Status Effect Healing
|
||||||
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case SC__BLOODYLUST:
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
if (!(sce->val2)) { //don't heal if already set
|
if (!(sce->val2)) { //don't heal if already set
|
||||||
status_heal(bl, status->max_hp, 0, 1); //Do not use percent_heal as this healing must override BERSERK's block.
|
status_heal(bl, status->max_hp, 0, 1); //Do not use percent_heal as this healing must override BERSERK's block.
|
||||||
@ -9580,15 +9572,15 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const
|
|||||||
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
case SC_SATURDAYNIGHTFEVER:
|
case SC_SATURDAYNIGHTFEVER:
|
||||||
//If val2 is removed, no HP penalty (dispelled?) [Skotlex]
|
if(status->hp > 200 && sc && sc->data[SC__BLOODYLUST]) {
|
||||||
if (status->hp > 100 && sce->val2)
|
status_percent_heal(bl, 100, 0);
|
||||||
|
status_change_end(bl, SC__BLOODYLUST, INVALID_TIMER);
|
||||||
|
} else if (status->hp > 100 && sce->val2) //If val2 is removed, no HP penalty (dispelled?) [Skotlex]
|
||||||
status_set_hp(bl, 100, 0);
|
status_set_hp(bl, 100, 0);
|
||||||
if(sc->data[SC_ENDURE] && sc->data[SC_ENDURE]->val4 == 2)
|
if(sc->data[SC_ENDURE] && sc->data[SC_ENDURE]->val4 == 2) {
|
||||||
{
|
|
||||||
sc->data[SC_ENDURE]->val4 = 0;
|
sc->data[SC_ENDURE]->val4 = 0;
|
||||||
status_change_end(bl, SC_ENDURE, INVALID_TIMER);
|
status_change_end(bl, SC_ENDURE, INVALID_TIMER);
|
||||||
}
|
}
|
||||||
case SC__BLOODYLUST:
|
|
||||||
sc_start4(bl, bl, SC_REGENERATION, 100, 10,0,0,(RGN_HP|RGN_SP), skill_get_time(LK_BERSERK, sce->val1));
|
sc_start4(bl, bl, SC_REGENERATION, 100, 10,0,0,(RGN_HP|RGN_SP), skill_get_time(LK_BERSERK, sce->val1));
|
||||||
if( type == SC_SATURDAYNIGHTFEVER ) //Sit down force of Saturday Night Fever has the duration of only 3 seconds.
|
if( type == SC_SATURDAYNIGHTFEVER ) //Sit down force of Saturday Night Fever has the duration of only 3 seconds.
|
||||||
sc_start(bl, bl,SC_SITDOWN_FORCE,100,sce->val1,skill_get_time2(WM_SATURDAY_NIGHT_FEVER,sce->val1));
|
sc_start(bl, bl,SC_SITDOWN_FORCE,100,sce->val1,skill_get_time2(WM_SATURDAY_NIGHT_FEVER,sce->val1));
|
||||||
@ -9875,7 +9867,6 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const
|
|||||||
break;
|
break;
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
opt_flag = 0;
|
opt_flag = 0;
|
||||||
// case SC__BLOODYLUST:
|
|
||||||
sc->opt3 &= ~OPT3_BERSERK;
|
sc->opt3 &= ~OPT3_BERSERK;
|
||||||
break;
|
break;
|
||||||
// case ???: // doesn't seem to do anything
|
// case ???: // doesn't seem to do anything
|
||||||
@ -10257,7 +10248,6 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC__BLOODYLUST:
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
// 5% every 10 seconds [DracoRPG]
|
// 5% every 10 seconds [DracoRPG]
|
||||||
if( --( sce->val3 ) > 0 && status_charge(bl, sce->val2, 0) && status->hp > 100 )
|
if( --( sce->val3 ) > 0 && status_charge(bl, sce->val2, 0) && status->hp > 100 )
|
||||||
@ -11015,7 +11005,6 @@ int status_change_clear_buffs (struct block_list* bl, int type)
|
|||||||
continue;
|
continue;
|
||||||
break;
|
break;
|
||||||
//The rest are buffs that can be removed.
|
//The rest are buffs that can be removed.
|
||||||
case SC__BLOODYLUST:
|
|
||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
case SC_SATURDAYNIGHTFEVER:
|
case SC_SATURDAYNIGHTFEVER:
|
||||||
if (!(type&1))
|
if (!(type&1))
|
||||||
|
@ -987,8 +987,7 @@ int unit_can_move(struct block_list *bl) {
|
|||||||
(sc->data[SC_DANCING]->val1&0xFFFF) == CG_MOONLIT ||
|
(sc->data[SC_DANCING]->val1&0xFFFF) == CG_MOONLIT ||
|
||||||
(sc->data[SC_DANCING]->val1&0xFFFF) == CG_HERMODE
|
(sc->data[SC_DANCING]->val1&0xFFFF) == CG_HERMODE
|
||||||
) )
|
) )
|
||||||
|| (sc->data[SC_CLOAKING] && //Need wall at level 1-2
|
|| (sc->data[SC_CLOAKING] && sc->data[SC_CLOAKING]->val1 < 3) // Can't move at level less than 3
|
||||||
sc->data[SC_CLOAKING]->val1 < 3 && !(sc->data[SC_CLOAKING]->val4&1))
|
|
||||||
)
|
)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
@ -1475,6 +1474,11 @@ int unit_skilluse_pos2( struct block_list *src, short skill_x, short skill_y, ui
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if( (skill_id >= SC_MANHOLE && skill_id <= SC_FEINTBOMB) && map_getcell(src->m, skill_x, skill_y, CELL_CHKMAELSTROM) ) {
|
||||||
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (!status_check_skilluse(src, NULL, skill_id, 0))
|
if (!status_check_skilluse(src, NULL, skill_id, 0))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user