-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathusertunnel.pas
154 lines (135 loc) · 3.83 KB
/
usertunnel.pas
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
unit usertunnel;
interface
uses
SysUtils, Classes, IdBaseComponent, IdComponent, IdTCPConnection,
IdTCPClient, IdThreadComponent, idcontext, messageSend,IdGlobal,
IdBuffer, messagePackage, ygo_client_protocol;
type
pidcontext = ^tidcontext;
pdUserTunnel = ^TdUserTunnel;
TdUserTunnel = class(TDataModule)
IdTCPClient1: TIdTCPClient;
IdThreadComponent1: TIdThreadComponent;
procedure IdThreadComponent1Run(Sender: TIdThreadComponent);
procedure IdTCPClient1Connected(Sender: TObject);
procedure IdTCPClient1Disconnected(Sender: TObject);
procedure IdTCPClient1Status(ASender: TObject;
const AStatus: TIdStatus; const AStatusText: String);
private
{ Private declarations }
public
{ Public declarations }
roomport:integer;
peercontext:Tidcontext;
Connected:boolean;
function connectserver:boolean;
procedure whendisconnect;
end;
implementation
uses Dialogs, sys;
{$R *.dfm}
{ TdUserTunnel }
function TdUserTunnel.connectserver:boolean;
begin
IdTCPClient1.Connect('127.0.0.1',roomport);
IdTCPClient1.IOHandler.ReadTimeout:=300000;
if IdTCPClient1.Connected then
begin
Connected:=true;
result:=true;
end;
end;
procedure TdUserTunnel.IdThreadComponent1Run(Sender: TIdThreadComponent);
var stream:tmemorystream;
i:integer;
buff:TIdBytes;
recv:pointer;
tmproom:troom;
procedure roomlistrefresh(room:troom;context:tidcontext);
var j:integer;
begin
if not assigned(room.userlist) then
room.userlist:=tlist.Create;
for j:=0 to room.userlist.Count-1 do
begin
if room.userlist[j]=context then exit;
end;
room.userlist.Add(context);
end;
begin
try
IdTCPClient1.IOHandler.ReadBytes(buff,2,false);
except
exit;
end;
i:=BytesToWord(buff);
stream:=tmemorystream.Create;
try
IdTCPClient1.IOHandler.ReadStream(stream,i);
recv:=stream.Memory;
case ord(tpackage(recv^).protocolhead1) of
STOC_TYPE_CHANGE:
begin
Tuserinfo(peercontext).pos:=ord(tplayerpostion(recv^).pos);
tmproom:=Tuserinfo(peercontext).room;
roomlistrefresh(tmproom,peercontext);
end;
STOC_DUEL_START:
begin
tmproom:=Tuserinfo(peercontext).room;
tmproom.duelstart:=true;
end;
STOC_GAME_MSG:
begin
end;
end;
peersendstream(peercontext,stream);
finally
stream.Free;
end;
end;
procedure TdUserTunnel.IdTCPClient1Connected(Sender: TObject);
begin
Connected:=true;
IdThreadComponent1.Start;
end;
procedure TdUserTunnel.IdTCPClient1Disconnected(Sender: TObject);
begin
whendisconnect;
end;
procedure TdUserTunnel.IdTCPClient1Status(ASender: TObject;
const AStatus: TIdStatus; const AStatusText: String);
begin
if AStatus=hsDisconnected then
begin
Connected:=false; //TCP断开
whendisconnect;
end;
end;
procedure TdUserTunnel.whendisconnect;
var i:integer;
begin
Connected:=false;
try
if assigned(peercontext) then
peercontext.Connection.Disconnect
else
exit;
except
end;
if (tuserinfo(peercontext).pos=16) or ((tuserinfo(peercontext).pos=1)
and tuserinfo(peercontext).room.duelstart) then
begin
if not assigned(tuserinfo(peercontext).room.userlist) then exit;
//通知同一个房间的所有客户端掉线
for i:=0 to tuserinfo(peercontext).room.userlist.count-1 do
begin
try
if assigned(tuserinfo(tuserinfo(peercontext).room.userlist[i]).dm_usertl) then
tuserinfo(tuserinfo(peercontext).room.userlist[i]).dm_usertl.IdTCPClient1.Disconnect;
except
end;
end;
end;
end;
end.