⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 game.pas

📁 RO模拟器!!适合玩仙境传说的玩家们呦~
💻 PAS
📖 第 1 页 / 共 4 页
字号:
unit Game;



interface

uses
	Windows, MMSystem, Forms, Classes, Math, SysUtils, ScktComp,
	Path, Script, Common, Zip, SQLData, FusionSQL, Game_Master, Globals;

//==============================================================================
// 娭悢掕媊
		procedure sv3PacketProcess(Socket: TCustomWinSocket);
//==============================================================================


implementation

//==============================================================================


(*-----------------------------------------------------------------------------*
// 僎乕儉僒乕僶乕僷働僢僩張棟

???
Appears to have a large portion of the game logic intermixed with a
case statement that processes incoming messages from the server.

CRW - 2004/04/07
- Applied consistant formatting to PART of this 7300 line long routine so it's
  now sane to look at.
- Separated variables, one per line, no exceptions.
- Started Translation of the SJIS code from the original coder(s) in the form:
  <original> ' Lit. "'<Edited_Babelfish_Translation_Here>'"'

  I hope this helps a wee bit. :P

*-----------------------------------------------------------------------------*)
Procedure sv3PacketProcess(Socket: TCustomWinSocket);
Var
	i     : Integer;
  h     : Integer;
	j     : Integer;
	k     : Integer;
	ii    : Integer;
	cmd   : Word;
	w     : Word;
	w1    : Word;
	w2    : Word;
  w3    : Word;
{捛壛}
	wjob  : Int64;
{捛壛僐僐傑偱}
{傾僀僥儉惢憿捛壛}
	m1      : Word;//庡偵惢憿偝傟傞傾僀僥儉偺ID偲偟偰棙梡
	m       : Array[0..2] of Word;//庡偵惢憿傾僀僥儉偵晄壜偝傟傞懏惈愇丄惎偺偐偗傜偺ID偲偟偰棙梡
	e,e2    : Word;//庡偵惢憿帪徚旓傾僀僥儉偺Inventory撪専嶕帪偵棙梡
	anvil   : Word;//嬥晘偵傛偭偰忋偑傞惉岟棪
{傾僀僥儉惢憿捛壛僐僐傑偱}
	id1       : Cardinal;
  id2       : Cardinal;

	L         : Cardinal; //was lowercase "l"
	L2        : Cardinal; //was lowercase "l2" (close to 1 or I in the wrong font)
	weight    : Cardinal;
  c         : Cardinal;
	b         : Byte;
  b1        : Byte;
	Len       : Integer;

	Str       : String;
  Str2      : String;
	AccountID : String;
	CharaID   : String;
	NpcID     : String;

	tp  : TPlayer;
	tc  : TChara;
	tc1 : TChara;
	tm  : TMap;
	tn  : TNPC;
	ts  : TMob;
  ts1 : TMob;
  tss : TSlaveDB;
  ma  : TMArrowDB;
  tid : TIDTbl;
	ti  : TItem;
	tk  : TSkill;
	tl  : TSkillDB;
	td  : TItemDB;

{傾僀僥儉惢憿捛壛}
	tma : TMaterialDB;
{傾僀僥儉惢憿捛壛僐僐傑偱}
{僷乕僥傿乕婡擻捛壛}
	tpa : TParty;
{僷乕僥傿乕婡擻捛壛僐僐傑偱}
{僠儍僢僩儖乕儉婡擻捛壛}
	tcr : TChatRoom;
{僠儍僢僩儖乕儉婡擻捛壛僐僐傑偱}
{業揦僗僉儖捛壛}
	tv  : TVender;
{業揦僗僉儖捛壛僐僐傑偱}
{庢堷婡擻捛壛}
	tdl : TDealings;
  twp : TWarpDatabase;
{庢堷婡擻捛壛僐僐傑偱}
{僉儏乕儁僢僩}
  tpd : TPetDB;
  tmd : TMobDB;
  tpe :TPet;

  i1  : Integer;
  j1  : Integer;
  k1  : Integer;
{僉儏乕儁僢僩偙偙傑偱}
{NPC僀儀儞僩捛壛}
	mi  : MapTbl;
{NPC僀儀儞僩捛壛僐僐傑偱}
{僊儖僪婡擻捛壛}
	tg    : TGuild;
	tg1   : TGuild;
	tgb   : TGBan;
	tgl   : TGRel;
	tp1   : TPlayer;
{僊儖僪婡擻捛壛僐僐傑偱}
	ta  : TMapList;
	xy  : TPoint;
  s   : String;
	SL  : TStringList;
	ww      : array of array of Word; //CRW This is dynamic 2-dim array??
	tmpbuf  : array of Byte;

  afm_compressed  : TZip;
  afm             : Textfile;
  letter          : Char;
  MapName         : String;
  dat             : TMemoryStream;
  h2              :array[0..3] of Single; //CRW What is this for??
  maptype         : Integer;
  txt             :textfile;
 txt1  :string;

Begin(* Proc sv3PacketProcess() *)

  j := 0;
  tcr := nil;
	while Socket.ReceiveLength >= 2 do
  begin
		//len := Socket.ReceiveLength;
		Socket.ReceiveBuf(buf[0], 2);
		RFIFOW(0, cmd);
		//if cmd = $00c8 then
		//	//debugout.lines.add('[' + TimeToStr(Now) + '] ' + '!');
		tc := Socket.Data;
		if (cmd > MAX_PACKET_NUMBER) then begin
			//debugout.lines.add('[' + TimeToStr(Now) + '] ' + '晄柧側僷働僢僩' + IntToStr(Socket.ReceiveLength) + '僶僀僩傪攋婞偟傑偟偨');
			SetLength(tmpbuf, Socket.ReceiveLength);
			Socket.ReceiveBuf(tmpbuf[0], Socket.ReceiveLength);
			Continue;
		end;
		Assert((cmd > 0) AND (cmd <= MAX_PACKET_NUMBER), 'Packet Type: index error ' + IntToStr(cmd));
		if PacketLength[cmd] = -1 then begin
			Socket.ReceiveBuf(buf[2], 2);
			RFIFOW(2, w);
			Socket.ReceiveBuf(buf[4], w - 4);
			//debugout.lines.add('[' + TimeToStr(Now) + '] ' + Format('3:%.8d CMD %.4x len:%d plen:%d', [tc.ID, cmd, w, len]));
		end else begin
			Socket.ReceiveBuf(buf[2], PacketLength[cmd] - 2);
			//if cmd <> $0072 then begin
			//debugout.lines.add('[' + TimeToStr(Now) + '] ' + Format('3:%.8d CMD %.4x', [tc.ID, cmd]));
			//end;
		end;
    //debugout.lines.add('[' + TimeToStr(Now) + '] ' + 'Command:' + IntToStr(cmd));

		case cmd of
		//--------------------------------------------------------------------------
		$0072: //僎乕儉嶪愙懕梫媮    Lit. "Game socket connection requested"
			begin
				RFIFOL( 2, L);
				accountid := IntToStr(L);
				//debugout.lines.add('[' + TimeToStr(Now) + '] ' + Format('3:%.8d CMD %.4x', [l, cmd]));
				//debugout.lines.add('[' + TimeToStr(Now) + '] ' + '		AccountID = ' + IntToHex(l, 4));
				RFIFOL( 6, l2);
				charaid := IntToStr(l2);
				//debugout.lines.add('[' + TimeToStr(Now) + '] ' + '		CharaID = ' + IntToHex(l, 4));
				RFIFOL(10, id1);
				//debugout.lines.add('[' + TimeToStr(Now) + '] ' + '		LoginID1 = ' + IntToHex(id1, 4));
				//RFIFOL(14, id2);
				if (Player.IndexOf(L) <> -1) and (Chara.IndexOf(L2) <> -1) then begin
					tp := Player.IndexOfObject(L) as TPlayer;
					tc := Chara.IndexOfObject(L2) as TChara;

					//if tc.IP = Socket.RemoteAddress then begin
					if (tp.LoginID1 = id1) and (tp.LoginID1 <> 0) then begin
						tc.ver2 := tp.ver2;
						//tp.LoginID1 := 0;
						tc.Login := 1;
						//tc.ID := tp.ID;
						//tc.Gender := tp.Gender;
						tc.PData := tp;
						if CharaPID.IndexOf(tc.ID) = -1 then CharaPID.AddObject(tc.ID, tc);
						tc.Socket := Socket;
						Socket.Data := tc;
						WFIFOL(0, $00000000);
						Socket.SendBuf(buf, 4);

						WFIFOW(0, $0073);
						WFIFOL(2, timeGetTime());
						WFIFOM1(6, tc.Point);
						WFIFOW(9, $0505);
						Socket.SendBuf(buf, 11);

						//慜夞儚乕僾偵幐攕偟偰棊偪偨偲偒偺暅媽張棟
						if tc.tmpMap <> '' then begin
							tc.Map := tc.tmpMap;
							tc.tmpMap := '';
						end;

						//儅僢僾儘乕僪
						if Map.IndexOf(tc.Map) = -1 then begin
							MapLoad(tc.Map);
						end;
{僊儖僪婡擻捛壛}
						j := GuildList.IndexOf(tc.GuildID);
						if (j <> -1) then begin
							tg := GuildList.Objects[j] as TGuild;
							//儊儞僶乕偵捠抦
							WFIFOW( 0, $016d);
							WFIFOL( 2, tc.ID);
							WFIFOL( 6, tc.CID);
							WFIFOL(10, 1);
							SendGuildMCmd(tc, 14, true);
							//僊儖僪忣曬
							SendGLoginInfo(tg, tc);
						end;

					//CRW -- Broadcasts Welcome Message to all Users.
					if (Option_WelcomeMsg) then begin
                                              Application.ProcessMessages;
                                              str2:=WelcomeMsg;
                                              if str2='blue' then str2 := 'blue欢迎 '+tc.Name+' 来到 '+ServerName+' 服务器,祝你玩的愉快!';
                                              if str2='' then str2 := '欢迎 '+tc.Name+' 来到 '+ServerName+' 服务器,祝你玩的愉快!';
						//CRW -- why is "w" 200 -- should it not be SizeOf(str2) ??
						w := 200;
						WFIFOW(0, $009a);
						WFIFOW(2, w);
						WFIFOS(4, str2, w-4);
						for i := 0 to CharaName.Count - 1 do begin
							tc1 := CharaName.Objects[i] as TChara;
							if tc1.Login = 2 then begin
								tc1.Socket.SendBuf(buf, w);
							end;
						end;
						tc.Socket.SendBuf(buf, w);
					end;//if (Option.WelcomeMsg)

					if (Option_MOTD) then begin
						//Read each line of the MOTD, send all but blank lines.
						//Only sent to the character joining.
						SendMOTD(tc);
					end;//if (Option_MOTD)

{僊儖僪婡擻捛壛僐僐傑偱}
					end else begin
						WFIFOW(0, $0074); //偁偭偰傞偐側丠
						WFIFOB(2, 0);
						Socket.SendBuf(buf, 3);
					end;
				end;
			end;//$0072
		//--------------------------------------------------------------------------
		$007d: // Map loading completed (display the map to user)
			begin
				if tc.tmpMap <> '' then begin
					tc.Map := tc.tmpMap;
					tc.tmpMap := '';
				end;
        if Map.IndexOf(tc.Map) <> - 1 then begin
				tm := Map.Objects[Map.IndexOf(tc.Map)] as TMap;
				while tm.Mode < 2 do
					Application.ProcessMessages;

				tc.MData := tm;
				if CharaPID.IndexOf(tc.ID) = -1 then CharaPID.AddObject(tc.ID, tc);
        if MapInfo.IndexOf(tm.Name) <> -1 then begin
        mi := MapInfo.Objects[MapInfo.IndexOf(tm.Name)] as MapTbl;

				// Add this character to the charlist for this map
				tm.CList.AddObject(tc.ID, tc);
				tm.Block[tc.Point.X div 8][tc.Point.Y div 8].CList.AddObject(tc.ID, tc);

        // Colus, 20040409: Gave the option to enable lower class dyes.
        // This should be removed when Gravity reenables them.
        { Alex: moved up here to prevent the flicker of changing colors }
        UpdateLook(tm, tc, 7, tc.ClothesColor, 0, true);                

        //Grace Time
        if mi.PvPG = true then begin
          tc.GraceTick := timeGetTime() + 15000;
        end else begin
          tc.GraceTick := timeGetTime() + 5000;
        end;

				// If dead, recover status/HP as necessary
				if tc.Sit = 1 then tc.Sit := 3;
				if tc.HP = 0 then begin
          if tc.JID = 0 then begin
            tc.HP := tc.MAXHP div 2;
            if tc.FullRecover then begin
              tc.HP := tc.MAXHP;
              tc.SP := tc.MAXSP;
            end;
          end else begin
            if tc.FullRecover then begin
              tc.HP := tc.MAXHP;
              tc.SP := tc.MAXSP;
            end else begin
              tc.HP := 1;
            end;
          end;
        end;

        // Reset vending/chat/trade/deal status
				tc.VenderID := 0;
				tc.ChatRoomID := 0;
				tc.DealingID := 0;
				tc.PreDealID := 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -