📄 skills.pas
字号:
end else begin
//Formula = (( BaseLv + INT) / 8偺抂悢愗幪偰 ) * ( 僸乕儖Lv x 8 + 4 )
dmg[0] := ((BaseLV + Param[3]) div 8) * tl.Data1[MUseLV];
ts.HP := ts.HP + dmg[0];
if ts.HP > Integer(ts.Data.HP) then ts.HP := ts.Data.HP;
//Send Skill packet
WFIFOW( 0, $011a);
WFIFOW( 2, MSkill);
WFIFOW( 4, dmg[0]);
WFIFOL( 6, MTarget);
WFIFOL(10, ID);
WFIFOB(14, 1);
SendBCmd(tm, ts.Point, 15);
end;
//Set Character Delay Tick
tc.MTick := Tick + 1000;
end else begin
MMode := 4;
Exit;
end;
end;
30: {Decrease Agility}
begin
//Send Graphics Packet
WFIFOW( 0, $011a);
WFIFOW( 2, MSkill);
WFIFOW( 4, MUseLV);
WFIFOL( 6, ts.ID);
WFIFOL(10, ID);
WFIFOB(14, 1);
SendBCmd(tm, ts.Point, 15);
if tc.Skill[30].EffectLV > 5 then begin
ts.speed := ts.speed + 45;
end else begin
ts.speed := ts.speed + 30;
end;
tc.MTick := Tick + 1000;
end;
{Alcolyte Skills Player vs monster end}
{Archer Skills player vs monster begin}
47: {Arrow Shower}
begin
if (Arrow = 0) or (Item[Arrow].Amount < 9) then begin
WFIFOW(0, $013b);
WFIFOW(2, 0);
Socket.SendBuf(buf, 4);
ATick := ATick + ADelay;
Exit;
end;
Dec(Item[Arrow].Amount,9);
WFIFOW( 0, $00af);
WFIFOW( 2, Arrow);
WFIFOW( 4, 9);
Socket.SendBuf(buf, 6);
if Item[Arrow].Amount = 0 then begin
Item[Arrow].ID := 0;
Arrow := 0;
end;
frmMain.DamageCalc1(tm, tc, ts, Tick, 0, tl.Data1[MUseLV], tl.Element, tl.Data1[MUseLV]);
if dmg[0] < 0 then dmg[0] := 0; //No Negate Damage
//Send Attack Packet
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], 1, 6);
if not frmMain.DamageProcess1(tm, tc, ts, dmg[0], Tick) then begin
frmMain.StatCalc1(tc, ts, Tick);
end;
xy := ts.Point;
//Begin Area Effect
sl.Clear;
for j1 := (xy.Y - tl.Range2) div 8 to (xy.Y + tl.Range2) div 8 do begin
for i1 := (xy.X - tl.Range2) div 8 to (xy.X + tl.Range2) div 8 do begin
for k1 := 0 to tm.Block[i1][j1].Mob.Count - 1 do begin
if ((tm.Block[i1][j1].Mob.Objects[k1] is TMob) = false) then Continue;
ts1 := tm.Block[i1][j1].Mob.Objects[k1] as TMob;
//NotTargetMonster
//NotYourGuildMonster
if (ts = ts1) or ((tc.GuildID <> 0) and (ts1.isGuardian = tc.GuildID)) or ((tc.GuildID <> 0) and (ts1.GID = tc.GuildID)) then Continue;
if (abs(ts1.Point.X - xy.X) <= tl.Range2) and (abs(ts1.Point.Y - xy.Y) <= tl.Range2) then
sl.AddObject(IntToStr(ts1.ID),ts1);
end;
end;
end;
if sl.Count <> 0 then begin
for k1 := 0 to sl.Count - 1 do begin
ts1 := sl.Objects[k1] as TMob;
j := 0;
case tc.Dir of
0:
begin
if ts1.Point.Y < tc.Point.Y then j := 1;
end;
1:
begin
if (ts1.Point.X < tc.Point.X) and (ts1.Point.Y > tc.Point.Y) then j := 1;
end;
2:
begin
if ts1.Point.X > tc.Point.X then j := 1;
end;
3:
begin
if (ts1.Point.X < tc.Point.X) and (ts1.Point.Y < tc.Point.Y) then j := 1;
end;
4:
begin
if ts1.Point.Y > tc.Point.Y then j := 1;
end;
5:
begin
if (ts1.Point.X > tc.Point.X) and (ts1.Point.Y > tc.Point.Y) then j := 1;
end;
6:
begin
if ts1.Point.X < tc.Point.X then j := 1;
end;
7:
begin
if (ts1.Point.X > tc.Point.X) and (ts1.Point.Y > tc.Point.Y) then j := 1;
end;
end;
if j <> 1 then begin
frmMain.DamageCalc1(tm, tc, ts1, Tick, 0, tl.Data1[MUseLV], tl.Element, tl.Data2[MUseLV]);
if dmg[0] < 0 then dmg[0] := 0; //No Negative Damage
//Send Graphics Packet
SendCSkillAtk1(tm, tc, ts1, Tick, dmg[0], 1, 5);
//Damage Process for Monster
if not frmMain.DamageProcess1(tm, tc, ts1, dmg[0], Tick) then
frmMain.StatCalc1(tc, ts1, Tick);
end;
end;
end;
end;
{Archer Skills player vs monster end}
{Thief Skills player vs monster begin}
50: {Steal}
{Colus, 20040305: Redid it all. Again. Using info on formulas obtained
from fansites and confirmations on algorithm from disassemblers.}
begin
if not (StealItem(tc)) then begin
SendSkillError(tc, 0);
tc.MMode := 4;
tc.MPoint.X := 0;
tc.MPoint.Y := 0;
DecSP(tc, 50, MUseLV);
end;
// Delay after stealing
tc.MTick := Tick + 1000;
end; {end Steal}
52: {Poison}
begin
frmMain.DamageCalc1(tm, tc, ts, Tick, 0, 100, tl.Element);
dmg[0] := dmg[0] + 15 * MUseLV;
dmg[0] := dmg[0] * ElementTable[tl.Element][ts.Element] div 100;
if dmg[0] < 0 then dmg[0] := 0; //No Negative Damage
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], 1);
k1 := (BaseLV * 2 + MUseLV * 3 + 10) - (ts.Data.LV * 2 + ts.Data.Param[2]);
k1 := k1 * 10;
if Random(1000) < k1 then begin
if not Boolean(ts.Stat2 and 1) then
ts.HealthTick[0] := Tick + tc.aMotion
else ts.HealthTick[0] := ts.HealthTick[0] + 30000;
end;
frmMain.DamageProcess1(tm, tc, ts, dmg[0], Tick);
end;
{Thief Skills player vs monster end}
54: {Resurrection}
begin
j := SearchCInventory(tc, 717, false);
if ((j <> 0) and (tc.Item[j].Amount >= 1)) or (NoJamstone = True) or (tc.ItemSkill = true) then begin
//Damage Calculation
// Colus, 20040123: Rearranged checks for undead, itemskill, and item usage
if (ts.Data.Race = 1) or (ts.Element mod 20 = 9) then begin
if NOT (NoJamstone AND ItemSkill ) then UseItem(tc, j);
if (Random(1000) < MUseLV * 20 + Param[3] + Param[5] + BaseLV + Trunc((1 - HP / MAXHP) * 200)) and (ts.Data.MEXP = 0) then begin
dmg[0] := ts.HP;
end else begin
dmg[0] := (BaseLV + Param[3] + (MUseLV * 10)) * ElementTable[6][ts.Element] div 100;
if dmg[0] < 0 then dmg[0] := 0; //杺朄峌寕偱偺夞暅偼枹幚憰
end;
// Shouldn't need to cap this any more...
//if (dmg[0] div $010000) <> 0 then dmg[0] := $07FFF; //曐尟
if (ts.EffectTick[0] > Tick) then dmg[0] := dmg[0] * 2;
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], 1);
frmMain.DamageProcess1(tm, tc, ts, dmg[0], Tick);
tc.MTick := Tick + 3000;
end else begin
tc.MMode := 4;
tc.MPoint.X := 0;
tc.MPoint.Y := 0;
end;
end else begin
SendSkillError(tc, 8); //No Blue Gemstone
tc.MMode := 4;
tc.MPoint.X := 0;
tc.MPoint.Y := 0;
Exit;
end;
end;
{Knight skills player vs monster end}
56: {Pierce}
begin
//Check if player has a Spear
if (tc.Weapon = 4) or (tc.Weapon = 5) then begin
frmMain.DamageCalc1(tm, tc, ts, Tick, 0, tl.Data1[MUseLV], tl.Element, 0);
j := ts.Data.Scale + 1;
dmg[0] := dmg[0] * j;
if dmg[0] < 0 then dmg[0] := 0;
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], j);
if not frmMain.DamageProcess1(tm, tc, ts, dmg[0], Tick) then
frmMain.StatCalc1(tc, ts, Tick);
end else begin
SendSkillError(tc, 6);
MMode := 4;
Exit;
end;
end;
57: {Brandish Spear}
begin
//if ts.HP <= 0 then exit;
if (tc.Weapon = 4) or (tc.Weapon = 5) then begin
xy.X := ts.Point.X - Point.X;
xy.Y := ts.Point.Y - Point.Y;
if abs(xy.X) > abs(xy.Y) * 3 then begin
if xy.X > 0 then b := 6 else b := 2;
end else if abs(xy.Y) > abs(xy.X) * 3 then begin
if xy.Y > 0 then b := 0 else b := 4;
end else begin
if xy.X > 0 then begin
if xy.Y > 0 then b := 7 else b := 5;
end else begin
if xy.Y > 0 then b := 1 else b := 3;
end;
end;
frmMain.DamageCalc1(tm, tc, ts, Tick, 0, tl.Data1[MUseLV], tl.Element, 0);
if dmg[0] < 0 then dmg[0] := 0;
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], 1);
if (dmg[0] > 0) then begin
xy := ts.Point;
sl.Clear;
for j1 := (xy.Y - tl.Range2) div 8 to (xy.Y + tl.Range2) div 8 do begin
for i1 := (xy.X - tl.Range2) div 8 to (xy.X + tl.Range2) div 8 do begin
for k1 := 0 to tm.Block[i1][j1].Mob.Count - 1 do begin
ts1 := tm.Block[i1][j1].Mob.Objects[k1] as TMob;
//NotTargetMonster
if ts = ts1 then
Continue;
if (abs(ts1.Point.X - xy.X) <= tl.Range2) and (abs(ts1.Point.Y - xy.Y) <= tl.Range2) then
sl.AddObject(IntToStr(ts1.ID),ts1);
end;
end;
end;
if sl.Count <> 0 then begin
for k1 := 0 to sl.Count - 1 do begin
ts1 := sl.Objects[k1] as TMob;
frmMain.DamageCalc1(tm, tc, ts1, Tick, 0, tl.Data1[MUseLV], tl.Element, tl.Data2[MUseLV]);
if dmg[0] < 0 then
dmg[0] := 0;
SendCSkillAtk1(tm, tc, ts1, Tick, dmg[0], 1, 5);
if not frmMain.DamageProcess1(tm, tc, ts1, dmg[0], Tick) then
frmMain.StatCalc1(tc, ts1, Tick);
SetLength(bb, 6);
bb[0] := 6;
xy := ts1.Point;
if ts1.HP <= 0 then break;
DirMove(tm, ts1.Point, b, bb);
if (xy.X div 8 <> ts1.Point.X div 8) or (xy.Y div 8 <> ts1.Point.Y div 8) then begin
with tm.Block[xy.X div 8][xy.Y div 8].Mob do begin
Assert(IndexOf(ts1.ID) <> -1, 'MobBlockDelete Error');
Delete(IndexOf(ts1.ID));
end;
tm.Block[ts1.Point.X div 8][ts1.Point.Y div 8].Mob.AddObject(ts1.ID, ts1);
ts1.pcnt := 0;
UpdateMonsterLocation(tm, ts1);
end;
end;
end;
end;
if not frmMain.DamageProcess1(tm, tc, ts, dmg[0], Tick) then begin
frmMain.StatCalc1(tc, ts, Tick);
end;
end else begin
SendSkillError(tc, 6);
MMode := 4;
Exit;
end;
end;
58: {Spear Stab}
begin
if (tc.Weapon = 4) or (tc.Weapon = 5) then begin
xy.X := ts.Point.X - Point.X;
xy.Y := ts.Point.Y - Point.Y;
if abs(xy.X) > abs(xy.Y) * 3 then begin
//Knockback Distance?
if xy.X > 0 then b := 6 else b := 2;
end else if abs(xy.Y) > abs(xy.X) * 3 then begin
//廲岦偒
if xy.Y > 0 then b := 0 else b := 4;
end else begin
if xy.X > 0 then begin
if xy.Y > 0 then b := 7 else b := 5;
end else begin
if xy.Y > 0 then b := 1 else b := 3;
end;
end;
//Calculate Damage
frmMain.DamageCalc1(tm, tc, ts, Tick, 0, tl.Data1[MUseLV], tl.Element, 0);
if dmg[0] < 0 then dmg[0] := 0; //No Negative Damage
//Send Attacking Packet
SendCSkillAtk1(tm, tc, ts, Tick, dmg[0], 1);
//Begin Knockback
if (dmg[0] > 0) then begin
SetLength(bb, 6);
bb[0] := 6;
xy := ts.Point;
DirMove(tm, ts.Point, b, bb);
//Knockback Monster
if (xy.X div 8 <> ts.Point.X div 8) or (xy.Y div 8 <> ts.Point.Y div 8) then begin
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -