📄 database.pas
字号:
txt : TextFile;
// Variables for creating the new AI list
txt2: TextFile;
str1: string;
SL : TStringList;
SL1 : TStringList;
ta : TMapList;
td : TItemDB;
{捛壛}
wj : Int64;
{捛壛僐僐傑偱}
{傾僀僥儉惢憿捛壛}
tma : TMaterialDB;
{傾僀僥儉惢憿捛壛僐僐傑偱}
{巵{敔捛壛}
tss : TSlaveDB;
tid : TIDTbl;
tGM : TGM_Table;
ma : TMArrowDB;
{巵{敔捛壛僐僐傑偱}
{僉儏乕儁僢僩}
tp : TPetDB;
{僉儏乕儁僢僩偙偙傑偱}
{NPC僀儀儞僩捛壛}
mi : MapTbl;
{NPC僀儀儞僩捛壛僐僐傑偱}
tb : TMobDB;
ts : TMobDB;
tsAI : TMobAIDB;
tsAI2 : TMobAIDBFusion;
twp : TWarpDatabase;
tGlobal : TGlobalVars;
tt : TTerritoryDB;
tl : TSkillDB;
sr : TSearchRec;
dat : TFileStream;
jf : array[0..MAX_JOB_NUMBER] of Boolean;
afm_compressed : TZip;
afm : Textfile;
begin
if NOT DataBaseFilesExist then begin
MessageBox(
Handle,
'你的服务器端文件不完整,请到Nweiss官方网站下载完整版!',
'Nweiss Pro '+ RELEASE_VERSION,
MB_OK or MB_ICONSTOP
);
Application.Terminate;
Exit;
end;
//gat僼傽僀儖偺懚嵼傪僠僃僢僋
debugout.lines.add('[' + TimeToStr(Now) + '] ' + 'Map data loading...');
Application.ProcessMessages;
if FindFirst(AppPath + 'map\*.af2', $27, sr) = 0 then begin
repeat
CreateDir('map\tmpFiles');
afm_compressed := tzip.create(afm_compressed);
afm_compressed.Filename := AppPath+'map\'+sr.Name;
afm_compressed.ExtractPath := AppPath+'map\tmpFiles';
afm_compressed.Extract;
sr.Name := StringReplace(sr.Name, '.af2', '.out',
[rfReplaceAll, rfIgnoreCase]);
assignfile(afm,AppPath + 'map\tmpFiles\' + sr.Name);
Reset(afm);
ReadLn(afm,str);
if (str <> 'ADVANCED FUSION MAP') then begin
MessageBox(Handle, PChar('地图初始化错误: ' + sr.Name), 'NWeiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
ReadLn(afm,str);
ReadLn(afm,xy.X,xy.Y);
CloseFile(afm);
if (xy.X < 0) or (xy.X > 511) or (xy.Y < 0) or (xy.Y > 511) then begin
MessageBox(Handle, PChar('地图大小错误 : ' + sr.Name), 'NWeiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
//txtDebug.Lines.Add(Format('MapData: %s [%dx%d]', [sr.Name, xy.X, xy.Y]));
//Application.ProcessMessages;
ta := TMapList.Create;
ta.Name := LowerCase(ChangeFileExt(sr.Name, ''));
ta.Ext := 'af2';
ta.Size := xy;
ta.Mode := 0;
MapList.AddObject(ta.Name, ta);
until FindNext(sr) <> 0;
FindClose(sr);
afm_compressed.Free;
end;
if FindFirst(AppPath + 'map\*.afm', $27, sr) = 0 then begin
repeat
assignfile(afm,AppPath + 'map\' + sr.Name);
Reset(afm);
ReadLn(afm,str);
if (str <> 'ADVANCED FUSION MAP') then begin
MessageBox(Handle, PChar('地图初始化错误: ' + sr.Name), 'Nweiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
ReadLn(afm,str);
ReadLn(afm,xy.X,xy.Y);
CloseFile(afm);
if (xy.X < 0) or (xy.X > 511) or (xy.Y < 0) or (xy.Y > 511) then begin
MessageBox(Handle, PChar('地图大小错误 : ' + sr.Name), 'Nweiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
//txtDebug.Lines.Add(Format('MapData: %s [%dx%d]', [sr.Name, xy.X, xy.Y]));
//Application.ProcessMessages;
ta := TMapList.Create;
ta.Name := LowerCase(ChangeFileExt(sr.Name, ''));
ta.Ext := 'afm';
ta.Size := xy;
ta.Mode := 0;
MapList.AddObject(ta.Name, ta);
until FindNext(sr) <> 0;
FindClose(sr);
end;
if FindFirst(AppPath + 'map\*.dwm', $27, sr) = 0 then begin
repeat dat := TFileStream.Create(AppPath + 'map\' + sr.Name, fmOpenRead, fmShareDenyWrite); SetLength(str, 3); dat.Read(str[1], 3); if str <> 'DWM' then begin MessageBox(Handle, PChar('地图初始化错误 : ' + sr.Name), 'NWeiss Pro', MB_OK or MB_ICONSTOP); Application.Terminate; exit; end; dat.Read(w, 2); dat.Read(xy.X, 4); dat.Read(xy.Y, 4); dat.Free; if (xy.X < 0) or (xy.X > 511) or (xy.Y < 0) or (xy.Y > 511) then begin MessageBox(Handle, PChar('地图大小错误 : ' + sr.Name), 'NWeiss Pro', MB_OK or MB_ICONSTOP); Application.Terminate; exit; end; //txtDebug.Lines.Add(Format('MapData: %s [%dx%d]', [sr.Name, xy.X, xy.Y])); //Application.ProcessMessages; ta := TMapList.Create; ta.Name := LowerCase(ChangeFileExt(sr.Name, '')); ta.Ext := 'dwm'; ta.Size := xy; ta.Mode := 0; MapList.AddObject(ta.Name, ta); until FindNext(sr) <> 0; FindClose(sr); end;
if FindFirst(AppPath + 'map\*.gat', $27, sr) = 0 then begin
repeat
dat := TFileStream.Create(AppPath + 'map\' + sr.Name, fmOpenRead, fmShareDenyWrite);
SetLength(str, 4);
dat.Read(str[1], 4);
if str <> 'GRAT' then begin
MessageBox(Handle, PChar('地图初始化错误 : ' + sr.Name), 'Nweiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
dat.Read(w, 2);
dat.Read(xy.X, 4);
dat.Read(xy.Y, 4);
dat.Free;
if (xy.X < 0) or (xy.X > 511) or (xy.Y < 0) or (xy.Y > 511) then begin
MessageBox(Handle, PChar('地图大小错误 : ' + sr.Name), 'Nweiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
//txtDebug.Lines.Add(Format('MapData: %s [%dx%d]', [sr.Name, xy.X, xy.Y]));
//Application.ProcessMessages;
ta := TMapList.Create;
ta.Name := LowerCase(ChangeFileExt(sr.Name, ''));
ta.Ext := 'gat';
ta.Size := xy;
ta.Mode := 0;
MapList.AddObject(ta.Name, ta);
until FindNext(sr) <> 0;
FindClose(sr);
end;
if MapList.IndexOf('prontera') = -1 then begin
//嵟掅尷丄prontera.gat偑側偄偲婲摦偟側偄
MessageBox(Handle, 'Prontera 地图文件丢失。', 'Nweiss', MB_OK or MB_ICONSTOP);
Application.Terminate;
exit;
end;
debugout.lines.add('[' + TimeToStr(Now) + '] ' + Format('-> Total %d map(s) loaded.', [MapList.Count]));
Application.ProcessMessages;
{ChrstphrR 2004/05/24 -- Moved so that early exits aren't memory leaks too}
SL := TStringList.Create;
SL1 := TStringList.Create;
//傾僀僥儉僨乕僞儘乕僪
debugout.lines.add('[' + TimeToStr(Now) + '] ' + 'Item database loading...');
Application.ProcessMessages;
AssignFile(txt, AppPath + 'database\item_db.txt');
Reset(txt);
Readln(txt, str);
while not eof(txt) do begin
sl.Clear;
Readln(txt, str);
sl.DelimitedText := str;
for i := sl.Count to 43 do
sl.Add('0');
for i := 0 to 43 do
if (i <> 1) and (i <> 2) and (sl.Strings[i] = '') then sl.Strings[i] := '0';
td := TItemDB.Create;
with td do begin
ID := StrToInt(sl.Strings[0]);
Name := sl.Strings[1];
JName := sl.Strings[2];
IType := StrToInt(sl.Strings[3]);
IEquip := ((IType = 4) or (IType = 5));
Price := StrToInt(sl.Strings[4]);
Sell := StrToInt(sl.Strings[5]);
Weight := StrToInt(sl.Strings[6]);
ATK := StrToInt(sl.Strings[7]);
MATK := StrToInt(sl.Strings[8]);
DEF := StrToInt(sl.Strings[9]);
MDEF := StrToInt(sl.Strings[10]);
Range := StrToInt(sl.Strings[11]);
Slot := StrToInt(sl.Strings[12]);
for i := 0 to 5 do
Param[i] := StrToInt(sl.Strings[13+i]);
HIT := StrToInt(sl.Strings[19]);
FLEE := StrToInt(sl.Strings[20]);
Crit := StrToInt(sl.Strings[21]);
Avoid := StrToInt(sl.Strings[22]);
Cast := StrToInt(sl.Strings[23]);
Gender := StrToInt(sl.Strings[25]);
Loc := StrToInt(sl.Strings[26]);
wLV := StrToInt(sl.Strings[27]);
eLV := StrToInt(sl.Strings[28]);
View := StrToInt(sl.Strings[29]);
Element := StrToInt(sl.Strings[30]);
Effect := StrToInt(sl.Strings[31]);
{Fix}
Job := StrToInt64(sl.Strings[24]);
if Job <> 0 then begin
//Bit recombination
for i := 0 to LOWER_JOB_END do begin
jf[i] := boolean((Job and (1 shl i)) <> 0);
if (i < (LOWER_JOB_END - 1)) and (jf[i]) then begin
jf[i + LOWER_JOB_END + 1] := true;
end;
end;
// Novice swordsman mage archer
Job := Int64(jf[ 0]) * $0001 + Int64(jf[ 1]) * $0002 + Int64(jf[ 2]) * $0004 + Int64(jf[ 3]) * $0008;
// aco merchant thief knight
Job := Job + Int64(jf[ 4]) * $0010 + Int64(jf[ 5]) * $0020 + Int64(jf[ 6]) * $0040 + Int64(jf[ 7]) * $0080;
// priest Wizard blacksmith hunter
Job := Job + Int64(jf[10]) * $0100 + Int64(jf[ 8]) * $0200 + Int64(jf[ 11]) * $0400 + Int64(jf[ 9]) * $0800;
// Asassin
Job := Job + Int64(jf[12]) * $1000;
//巄掕
Job := Job or Int64(jf[14]) * $004000; //Crusader
Job := Job or Int64(jf[15]) * $008000; //Monk
Job := Job or Int64(jf[16]) * $010000; //Sage
Job := Job or Int64(jf[17]) * $020000; //Rogue
Job := Job or Int64(jf[18]) * $040000; //Alchemist
Job := Job or Int64(jf[19]) * $080000; //Bard
Job := Job or Int64(jf[20]) * $100000; //Dancer
// $200000: Groom, $400000: Bride...
Job := Job or Int64(jf[23]) * $800000; //Super Novice
//Crusader Same as a swordsman and knight
if Boolean(Job and $0002) or Boolean(Job and $0080) then Job := Job or $4000;
// Super Novices get all Novice equipments.
if Boolean(Job and $0001) then Job := Job or $800000;
//Monk
if IType = 5 then begin //Same as aco
if Boolean(Job and $0010) or Boolean(Job and $0100) then Job := Job or $8000;
end else if IType = 4 then begin //weapons same as aco, knuckle system
if Boolean(Job and $0010) then Job := Job or $8000;
if View = 12 then Job := Job or $8000;
end;
//Sage Same attribute as mage
if Boolean(Job and $0004) or Boolean(Job and $0200) then Job := Job or $10000;
//Possible equiptment
if (IType = 4) and (View = 15) then Job := Job or $10000;
//Rogue same as hunter. uses bow
if Boolean(Job and $0040) then Job := Job or $20000;
//Alchemist Same as Blacksmith
if Boolean(Job and $0020) or Boolean(Job and $0400) then Job := Job or $40000;
//Bard
//Dancer
if IType = 5 then begin //Same defence equiptment as hunter
if Boolean(Job and $0008) or Boolean(Job and $0800) then Job := Job or $180000;
end;
if IType = 4 then begin
if View = 13 then Job := Job or $080000; //Music instrument
if View = 14 then Job := Job or $100000; //Whip
if View = 11 then begin //Bows equip for both?
if Boolean(Job and $0008) or Boolean(Job and $0800) then Job := Job or $180000;
if Boolean(Job and $0001) then Job := Job or $180000 end;
end;
// Colus, 20040304: Kludged method of porting the reqs to upper jobs
for i := 0 to LOWER_JOB_END do begin
//if (i < (LOWER_JOB_END - 1)) and (jf[i]) then begin
if (i < (LOWER_JOB_END - 1)) and (Job and (1 shl i) <> 0) then begin
Job := Job or Int64(1) shl (i + LOWER_JOB_END + 1);
end;
end;
end;
{FIX Stop}
HP1 := StrToInt(sl.Strings[32]);
HP2 := StrToInt(sl.Strings[33]);
SP1 := StrToInt(sl.Strings[34]);
SP2 := StrToInt(sl.Strings[35]);
//Rare := StrToBool(sl.Strings[36]);
//Box := StrToInt(sl.Strings[37]);
for i := 0 to 9 do begin
DamageFixR[i] := 0;
DamageFixE[i] := 0;
end;
//if ID > 4000 then debugout.lines.add('[' + TimeToStr(Now) + '] ' + Format('ID = %d', [ID]));
DamageFixR[StrToInt(sl.Strings[36])] := StrToInt(sl.Strings[37]);
DamageFixE[StrToInt(sl.Strings[38])] := StrToInt(sl.Strings[39]);
i := StrToInt(sl.Strings[40]);
if i <> 0 then begin
if (i mod 10) = 0 then begin
SFixPer2[(i div 10)-1] := StrToInt(sl.Strings[41]) div 100;
end else begin
SFixPer1[(i mod 10)-1] := StrToInt(sl.Strings[41]) mod 100;
end;
end;
for i := 0 to MAX_SKILL_NUMBER do AddSkill[i] := 0;
AddSkill[StrToInt(sl.Strings[42])] := StrToInt(sl.Strings[43]);
case td.Effect of
202: {Monster Knockback}
begin
SpecialAttack := 1; {Knockback}
end;
203: {Splash Damage}
begin
SplashAttack := true;
end;
204: {Splash + Knockback}
begin
SplashAttack := true; {Splash}
SpecialAttack := 1; {Knockback}
end;
205: {Fatal Blow}
begin
SpecialAttack := 2; {Fatal Blow}
end;
end;
case ID of
4115:
begin
DrainFix[0] := 3; // Hunter Fly Card
DrainPer[0] := 15;
end;
4082: DamageFixS[0] := 15; // Desert Wolf Card
4092: DamageFixS[1] := 15; // Skel Worker Card
4126: DamageFixS[2] := 15; // Minorous Card
4125: // Deviace Card (changed from Deviruchi, 5->7% bonus
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -