- Added client side visualization of area restrictions
- Added an icon to the "Region control" menu item - Changed the former TAccessLevelChangedPacket and the TLoginResponsePacket to add informations about the writeable areas - Changed OnModifyUserPacket to update clients according to new accesslevel/area restrictions - Changed OnModifyRegionPacket to update clients using that particular region - Fixed UPacketHandlers.ValidateAccess to check the region bounds according to the PtInRect function
This commit is contained in:
parent
91af86a294
commit
1c3d624949
|
@ -31,7 +31,8 @@ interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Classes, SysUtils, LResources, Forms, Controls, Dialogs, lNetComponents, lNet,
|
Classes, SysUtils, LResources, Forms, Controls, Dialogs, lNetComponents, lNet,
|
||||||
UEnhancedMemoryStream, UPacket, UEnums, ExtCtrls, dateutils;
|
UEnhancedMemoryStream, UPacket, UEnums, ExtCtrls, dateutils, URectList,
|
||||||
|
LCLIntf;
|
||||||
|
|
||||||
type
|
type
|
||||||
|
|
||||||
|
@ -56,6 +57,7 @@ type
|
||||||
FAccessLevel: TAccessLevel;
|
FAccessLevel: TAccessLevel;
|
||||||
FDataDir: string;
|
FDataDir: string;
|
||||||
FLastPacket: TDateTime;
|
FLastPacket: TDateTime;
|
||||||
|
FWriteMap: TRectList;
|
||||||
procedure OnCanSend(ASocket: TLSocket);
|
procedure OnCanSend(ASocket: TLSocket);
|
||||||
procedure OnConnectionHandlingPacket(ABuffer: TEnhancedMemoryStream);
|
procedure OnConnectionHandlingPacket(ABuffer: TEnhancedMemoryStream);
|
||||||
procedure ProcessQueue;
|
procedure ProcessQueue;
|
||||||
|
@ -63,9 +65,11 @@ type
|
||||||
public
|
public
|
||||||
property Username: string read FUsername;
|
property Username: string read FUsername;
|
||||||
property AccessLevel: TAccessLevel read FAccessLevel write FAccessLevel;
|
property AccessLevel: TAccessLevel read FAccessLevel write FAccessLevel;
|
||||||
|
function CanWrite(AX, AY: Word): Boolean;
|
||||||
procedure Send(APacket: TPacket);
|
procedure Send(APacket: TPacket);
|
||||||
procedure Disconnect;
|
procedure Disconnect;
|
||||||
procedure CheckClose(ASender: TForm);
|
procedure CheckClose(ASender: TForm);
|
||||||
|
procedure UpdateWriteMap(AStream: TEnhancedMemoryStream);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
var
|
var
|
||||||
|
@ -98,6 +102,7 @@ begin
|
||||||
if FSendQueue <> nil then FreeAndNil(FSendQueue);
|
if FSendQueue <> nil then FreeAndNil(FSendQueue);
|
||||||
if FReceiveQueue <> nil then FreeAndNil(FReceiveQueue);
|
if FReceiveQueue <> nil then FreeAndNil(FReceiveQueue);
|
||||||
if PacketHandlers[$02] <> nil then FreeAndNil(PacketHandlers[$02]);
|
if PacketHandlers[$02] <> nil then FreeAndNil(PacketHandlers[$02]);
|
||||||
|
if FWriteMap <> nil then FreeAndNil(FWriteMap);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure TdmNetwork.TCPClientConnect(aSocket: TLSocket);
|
procedure TdmNetwork.TCPClientConnect(aSocket: TLSocket);
|
||||||
|
@ -194,6 +199,12 @@ begin
|
||||||
width := ABuffer.ReadWord;
|
width := ABuffer.ReadWord;
|
||||||
height := ABuffer.ReadWord;
|
height := ABuffer.ReadWord;
|
||||||
ResMan.InitLandscape(width, height);
|
ResMan.InitLandscape(width, height);
|
||||||
|
|
||||||
|
{FWriteMap := TBits.Create(ResMan.Landscape.CellWidth * ResMan.Landscape.CellHeight);
|
||||||
|
FWriteMap.XorBits(FWriteMap); //set all to 1}
|
||||||
|
FWriteMap := TRectList.Create;
|
||||||
|
UpdateWriteMap(ABuffer);
|
||||||
|
|
||||||
frmMain := TfrmMain.Create(dmNetwork);
|
frmMain := TfrmMain.Create(dmNetwork);
|
||||||
frmRadarMap := TfrmRadarMap.Create(frmMain);
|
frmRadarMap := TfrmRadarMap.Create(frmMain);
|
||||||
frmLargeScaleCommand := TfrmLargeScaleCommand.Create(frmMain);
|
frmLargeScaleCommand := TfrmLargeScaleCommand.Create(frmMain);
|
||||||
|
@ -309,6 +320,7 @@ begin
|
||||||
frmMain.ApplicationProperties1.OnIdle := nil;
|
frmMain.ApplicationProperties1.OnIdle := nil;
|
||||||
FreeAndNil(frmMain);
|
FreeAndNil(frmMain);
|
||||||
end;
|
end;
|
||||||
|
if FWriteMap <> nil then FreeAndNil(FWriteMap);
|
||||||
if GameResourceManager <> nil then FreeAndNil(GameResourceManager);
|
if GameResourceManager <> nil then FreeAndNil(GameResourceManager);
|
||||||
frmInitialize.Hide;
|
frmInitialize.Hide;
|
||||||
while frmLogin.ShowModal = mrOK do
|
while frmLogin.ShowModal = mrOK do
|
||||||
|
@ -328,6 +340,21 @@ begin
|
||||||
FreeAndNil(frmLogin);
|
FreeAndNil(frmLogin);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function TdmNetwork.CanWrite(AX, AY: Word): Boolean;
|
||||||
|
var
|
||||||
|
i: Integer;
|
||||||
|
pt: TPoint;
|
||||||
|
begin
|
||||||
|
if FWriteMap.Count = 0 then Exit(True); //TODO : still too slow
|
||||||
|
|
||||||
|
pt := Point(AX, AY);
|
||||||
|
for i := 0 to FWriteMap.Count - 1 do
|
||||||
|
if PtInRect(FWriteMap.Rects[i], pt) then
|
||||||
|
Exit(True);
|
||||||
|
|
||||||
|
Result := False;
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TdmNetwork.Send(APacket: TPacket);
|
procedure TdmNetwork.Send(APacket: TPacket);
|
||||||
var
|
var
|
||||||
source: TEnhancedMemoryStream;
|
source: TEnhancedMemoryStream;
|
||||||
|
@ -357,6 +384,23 @@ begin
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TdmNetwork.UpdateWriteMap(AStream: TEnhancedMemoryStream);
|
||||||
|
var
|
||||||
|
x1, y1, x2, y2: Word;
|
||||||
|
i, areaCount: Integer;
|
||||||
|
begin
|
||||||
|
FWriteMap.Clear;
|
||||||
|
areaCount := AStream.ReadWord;
|
||||||
|
for i := 0 to areaCount - 1 do
|
||||||
|
begin
|
||||||
|
x1 := AStream.ReadWord;
|
||||||
|
y1 := AStream.ReadWord;
|
||||||
|
x2 := AStream.ReadWord;
|
||||||
|
y2 := AStream.ReadWord;
|
||||||
|
FWriteMap.Add(x1, y1, x2, y2);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
|
||||||
initialization
|
initialization
|
||||||
{$I UdmNetwork.lrs}
|
{$I UdmNetwork.lrs}
|
||||||
|
|
||||||
|
|
|
@ -1028,6 +1028,7 @@ object frmMain: TfrmMain
|
||||||
TreeOptions.MiscOptions = [toFullRepaintOnResize, toInitOnSave, toToggleOnDblClick, toWheelPanning]
|
TreeOptions.MiscOptions = [toFullRepaintOnResize, toInitOnSave, toToggleOnDblClick, toWheelPanning]
|
||||||
TreeOptions.PaintOptions = [toHideSelection, toShowButtons, toShowDropmark, toThemeAware, toUseBlendedImages]
|
TreeOptions.PaintOptions = [toHideSelection, toShowButtons, toShowDropmark, toThemeAware, toUseBlendedImages]
|
||||||
OnClick = vstChatClick
|
OnClick = vstChatClick
|
||||||
|
OnFreeNode = vstChatFreeNode
|
||||||
OnGetText = vstChatGetText
|
OnGetText = vstChatGetText
|
||||||
OnPaintText = vstChatPaintText
|
OnPaintText = vstChatPaintText
|
||||||
Columns = <
|
Columns = <
|
||||||
|
@ -1253,6 +1254,7 @@ object frmMain: TfrmMain
|
||||||
end
|
end
|
||||||
object mnuRegionControl: TMenuItem
|
object mnuRegionControl: TMenuItem
|
||||||
Caption = '&Region Management'
|
Caption = '&Region Management'
|
||||||
|
ImageIndex = 19
|
||||||
OnClick = mnuRegionControlClick
|
OnClick = mnuRegionControlClick
|
||||||
end
|
end
|
||||||
object mnuLargeScaleCommands: TMenuItem
|
object mnuLargeScaleCommands: TMenuItem
|
||||||
|
@ -1309,7 +1311,7 @@ object frmMain: TfrmMain
|
||||||
left = 264
|
left = 264
|
||||||
top = 32
|
top = 32
|
||||||
Bitmap = {
|
Bitmap = {
|
||||||
4C69130000001000000010000000000000000000000000000000000000000000
|
4C69140000001000000010000000000000000000000000000000000000000000
|
||||||
0000000000000000000000000000000000000000000000000000000000000000
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
0000D9A781FFD39E76FF00000000000000000000000000000000000000000000
|
0000D9A781FFD39E76FF00000000000000000000000000000000000000000000
|
||||||
0000000000000000000000000000ECBEA1FFE7BB9DFFE4B697FFE0B292FFDAAE
|
0000000000000000000000000000ECBEA1FFE7BB9DFFE4B697FFE0B292FFDAAE
|
||||||
|
@ -1917,7 +1919,39 @@ object frmMain: TfrmMain
|
||||||
000000000000000000FF000000FF000000FF000000FF00000000000000000000
|
000000000000000000FF000000FF000000FF000000FF00000000000000000000
|
||||||
0000000000000000000000000000000000000000000000000000000000000000
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
00000000000000000000000000FF000000FF0000000000000000000000000000
|
00000000000000000000000000FF000000FF0000000000000000000000000000
|
||||||
0000000000000000000000000000
|
0000000000000000000000000000536876FF5C6A5DFF5F6D60FF5F6D60FF5F6D
|
||||||
|
60FF5F6D60FF5F6D61FF5F6D61FF5F6D61FF5F6D61FF606D61FF606D62FF606D
|
||||||
|
62FF606D63FF5E6A5FFF454E46FF5C6A5DFFFBFCFBFFFCFEFCFFF7FCF8FFF7FC
|
||||||
|
F8FFF7FCF8FFF8FCF8FFF7FCF9FFF8FCF8FFF8FCF8FFECF7EEFFEDF7EEFFEFF6
|
||||||
|
EDFFEEF4ECFFEBF4EBFF5E6A5FFF5F6D60FFF7FCF8FF9DF9F9FF6CB4EDFF6271
|
||||||
|
FEFF80E7E9FF8CF4F4FF52CDCDFFECC2A4FFDDAD8AFFEBBA97FFDDA780FFE2AB
|
||||||
|
83FFDAA075FFD9EAD4FF616E64FF5F6D60FFF7FCF8FF8AEAEAFF72DDDEFF5665
|
||||||
|
F0FF569FDFFF73E8E8FF46C1C1FFBBBBA5FFD0A483FFDEB08EFFD19E7AFFD6A2
|
||||||
|
7AFFCF9871FFD7EBD5FF626E64FF5F6D61FFF7FCF8FF9FF9F9FF85E9EAFF84D3
|
||||||
|
FAFF525AF0FF87F2F7FF60DAD7FF98D5CAFFE0B79CFFEDC7A9FFE0B394FFE6B8
|
||||||
|
98FFDEAE8CFFD7ECD6FF636E64FF5F6D61FFF8FCF8FF90EAEAFF78DDDEFF81E9
|
||||||
|
EAFF4E6BE2FF639DEEFF5ED7D7FF5BCBC9FFD4B097FFE2BA9FFFA1ADA9FF58A5
|
||||||
|
D8FF85B1DBFF469DD0FF4E7C8CFF5F6D61FFF8FCF8FFA6F9F9FF8BE9EAFF99F8
|
||||||
|
FAFF78D3EBFF656BFFFF77DCEAFF70DFDEFFC1C5B5FFA8C8C8FF77BEE7FFB4D2
|
||||||
|
F0FFE5F3FFFFACD2EFFF4A89BEFF606D61FFF8FCF8FF9FF1F1FF81DDDFFF8AEA
|
||||||
|
EBFF75DEDEFF6591EEFF557EE2FF68DCDDFF5BBCC5FF80D5EDFFB2E3F9FF8BC0
|
||||||
|
E7FFAED3F6FFC4E0FCFF669DD0FF606D62FFF8FCF8FFAFFAFAFF94EBEBFFA2F9
|
||||||
|
FAFF8AEAEBFF95EDF3FF595FEBFF6BCFE5FF7CD4EEFFC4F6FDFF6CDDF6FF6DCA
|
||||||
|
EDFF63A3D7FF66A1D3FF617474FF606D63FFF8FCF8FFA4EBEDFF8DDFDFFF97EB
|
||||||
|
EBFF72CFB7FF74CA99FF4790BDFF79D3EEFFC7F7FDFF5FDCF5FF5BE2F7FF7AD6
|
||||||
|
F2FF4399DFFFB1D4D9FF646F66FF616E63FFF8FCF9FFBCFBFBFF9DE7DFFF93E1
|
||||||
|
BBFF77C997FF63BDAEFF77CBE7FFC7F7FDFF5EDCF5FF5AE1F7FF7BD4F1FF4395
|
||||||
|
DDFF589BC3FFD0E9DBFF646F66FF616E63FFF7FBF8FF9BDEC4FF73C393FF80CF
|
||||||
|
9FFF53AD9CFF73B9D5FFC2F6FDFF63DFF7FF5DE2F8FF79D3F0FF4395DAFF6CB8
|
||||||
|
A4FF74C38FFFD7EFDAFF646F66FF616E64FFECF7EEFF96DBAFFF7FC99AFF63AD
|
||||||
|
A5FF7AB6D5FF90B7D1FF55C9E4FF5BDFF5FF78D0EDFF4696D9FF76C1A1FF87D0
|
||||||
|
A0FF80CA9AFFD6EEDAFF646F66FF626E64FFEEF8EFFFA4DBBCFF8CCAA6FF4389
|
||||||
|
AAFFE0F2FFFF549AD8FF1A7ABEFF4998C5FF3B86BFFF6074E7FF81C5A3FF8CD0
|
||||||
|
A6FF85CAA0FFD2E9D7FF646F67FF5F6A60FFEBF5ECFFD4EDD7FFD4EED7FF2E67
|
||||||
|
84FF94C7F9FF91C9F9FF4185C9FF256BACFFB7D9D4FFD4E2ECFFCFE5D6FFD5ED
|
||||||
|
D9FFD8EFDCFFD5EDD9FF616C63FF454D47FF5F6A61FF636F64FF646F64FF143F
|
||||||
|
56FF295F86FF4988BCFF4A86A7FF5D7070FF646F66FF646F66FF646F67FF646F
|
||||||
|
67FF647067FF616C63FF474E48FF
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
object pmTileList: TPopupMenu
|
object pmTileList: TPopupMenu
|
||||||
|
|
|
@ -247,6 +247,7 @@ type
|
||||||
Y: Integer);
|
Y: Integer);
|
||||||
procedure vdtTilesScroll(Sender: TBaseVirtualTree; DeltaX, DeltaY: Integer);
|
procedure vdtTilesScroll(Sender: TBaseVirtualTree; DeltaX, DeltaY: Integer);
|
||||||
procedure vstChatClick(Sender: TObject);
|
procedure vstChatClick(Sender: TObject);
|
||||||
|
procedure vstChatFreeNode(Sender: TBaseVirtualTree; Node: PVirtualNode);
|
||||||
procedure vstChatGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
|
procedure vstChatGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
|
||||||
Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
|
Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
|
||||||
procedure vstChatPaintText(Sender: TBaseVirtualTree;
|
procedure vstChatPaintText(Sender: TBaseVirtualTree;
|
||||||
|
@ -283,6 +284,8 @@ type
|
||||||
procedure SetY(const AValue: Integer);
|
procedure SetY(const AValue: Integer);
|
||||||
procedure SetCurrentTile(const AValue: TWorldItem);
|
procedure SetCurrentTile(const AValue: TWorldItem);
|
||||||
procedure SetSelectedTile(const AValue: TWorldItem);
|
procedure SetSelectedTile(const AValue: TWorldItem);
|
||||||
|
procedure SetNormalLights; inline;
|
||||||
|
procedure SetDarkLights; inline;
|
||||||
procedure InitRender;
|
procedure InitRender;
|
||||||
procedure InitSize;
|
procedure InitSize;
|
||||||
procedure Render;
|
procedure Render;
|
||||||
|
@ -1373,6 +1376,15 @@ begin
|
||||||
edChat.SetFocus;
|
edChat.SetFocus;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TfrmMain.vstChatFreeNode(Sender: TBaseVirtualTree; Node: PVirtualNode);
|
||||||
|
var
|
||||||
|
chatInfo: PChatInfo;
|
||||||
|
begin
|
||||||
|
chatInfo := Sender.GetNodeData(Node);
|
||||||
|
chatInfo^.Sender := '';
|
||||||
|
chatInfo^.Msg := '';
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TfrmMain.vstChatGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
|
procedure TfrmMain.vstChatGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
|
||||||
Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
|
Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
|
||||||
var
|
var
|
||||||
|
@ -1557,11 +1569,27 @@ begin
|
||||||
FSelectedTile.OnDestroy.RegisterEvent(@TileRemoved);
|
FSelectedTile.OnDestroy.RegisterEvent(@TileRemoved);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
procedure TfrmMain.SetNormalLights;
|
||||||
|
const
|
||||||
|
specular: TGLArrayf4 = (2, 2, 2, 1);
|
||||||
|
ambient: TGLArrayf4 = (1, 1, 1, 1);
|
||||||
|
begin
|
||||||
|
glLightfv(GL_LIGHT0, GL_AMBIENT, @specular);
|
||||||
|
glLightModelfv(GL_LIGHT_MODEL_AMBIENT, @ambient);
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure TfrmMain.SetDarkLights;
|
||||||
|
const
|
||||||
|
specularDark: TGLArrayf4 = (0.5, 0.5, 0.5, 1);
|
||||||
|
ambientDark: TGLArrayf4 = (0.25, 0.25, 0.25, 1);
|
||||||
|
begin
|
||||||
|
glLightfv(GL_LIGHT0, GL_AMBIENT, @specularDark);
|
||||||
|
glLightModelfv(GL_LIGHT_MODEL_AMBIENT, @ambientDark);
|
||||||
|
end;
|
||||||
|
|
||||||
procedure TfrmMain.InitRender;
|
procedure TfrmMain.InitRender;
|
||||||
const
|
const
|
||||||
lightPosition: TGLArrayf4 = (-1, -1, 0.5, 0);
|
lightPosition: TGLArrayf4 = (-1, -1, 0.5, 0);
|
||||||
specular: TGLArrayf4 = (2, 2, 2, 1);
|
|
||||||
ambient: TGLArrayf4 = (1, 1, 1, 1);
|
|
||||||
begin
|
begin
|
||||||
glEnable(GL_ALPHA_TEST);
|
glEnable(GL_ALPHA_TEST);
|
||||||
glAlphaFunc(GL_GREATER, 0.1);
|
glAlphaFunc(GL_GREATER, 0.1);
|
||||||
|
@ -1574,8 +1602,6 @@ begin
|
||||||
|
|
||||||
glEnable(GL_LIGHT0);
|
glEnable(GL_LIGHT0);
|
||||||
glLightfv(GL_LIGHT0, GL_POSITION, @lightPosition);
|
glLightfv(GL_LIGHT0, GL_POSITION, @lightPosition);
|
||||||
glLightfv(GL_LIGHT0, GL_AMBIENT, @specular);
|
|
||||||
glLightModelfv(GL_LIGHT_MODEL_AMBIENT, @ambient);
|
|
||||||
glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_FALSE);
|
glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_FALSE);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
@ -1612,6 +1638,8 @@ var
|
||||||
tileRect: TRect;
|
tileRect: TRect;
|
||||||
virtualTile: TVirtualTile;
|
virtualTile: TVirtualTile;
|
||||||
staticsFilter: TStaticFilter;
|
staticsFilter: TStaticFilter;
|
||||||
|
editing: Boolean;
|
||||||
|
intensity: GLfloat;
|
||||||
|
|
||||||
procedure GetMapDrawOffset(x, y: Integer; out drawX, drawY: Single);
|
procedure GetMapDrawOffset(x, y: Integer; out drawX, drawY: Single);
|
||||||
begin
|
begin
|
||||||
|
@ -1667,7 +1695,19 @@ begin
|
||||||
(CurrentTile <> SelectedTile) and
|
(CurrentTile <> SelectedTile) and
|
||||||
PtInRect(tileRect, Point(FX + offsetX, FY + offsetY));
|
PtInRect(tileRect, Point(FX + offsetX, FY + offsetY));
|
||||||
|
|
||||||
if acDraw.Checked and (singleTarget or multiTarget) then
|
if acSelect.Checked or dmNetwork.CanWrite(FX + offsetX, FY + offsetY) then
|
||||||
|
begin
|
||||||
|
editing := True;
|
||||||
|
intensity := 1.0;
|
||||||
|
SetNormalLights;
|
||||||
|
end else
|
||||||
|
begin
|
||||||
|
editing := False;
|
||||||
|
intensity := 0.5;
|
||||||
|
SetDarkLights;
|
||||||
|
end;
|
||||||
|
|
||||||
|
if editing and acDraw.Checked and (singleTarget or multiTarget) then
|
||||||
begin
|
begin
|
||||||
ghostTile := FGhostTile;
|
ghostTile := FGhostTile;
|
||||||
if (ghostTile is TMapCell) and (not frmDrawSettings.cbForceAltitude.Checked) then
|
if (ghostTile is TMapCell) and (not frmDrawSettings.cbForceAltitude.Checked) then
|
||||||
|
@ -1691,7 +1731,9 @@ begin
|
||||||
|
|
||||||
for i := 0 to draw.Count - 1 do
|
for i := 0 to draw.Count - 1 do
|
||||||
begin
|
begin
|
||||||
if TObject(draw[i]) = virtualTile then
|
if not editing then
|
||||||
|
highlight := False
|
||||||
|
else if TObject(draw[i]) = virtualTile then
|
||||||
highlight := False
|
highlight := False
|
||||||
else if acDelete.Checked and multiTarget and (TObject(draw[i]) is TStaticItem) then
|
else if acDelete.Checked and multiTarget and (TObject(draw[i]) is TStaticItem) then
|
||||||
highlight := True
|
highlight := True
|
||||||
|
@ -1716,7 +1758,7 @@ begin
|
||||||
else
|
else
|
||||||
z := TWorldItem(draw[i]).Z;
|
z := TWorldItem(draw[i]).Z;
|
||||||
|
|
||||||
glColor4f(1.0, 1.0, 1.0, 1.0);
|
glColor4f(intensity, intensity, intensity, 1.0);
|
||||||
|
|
||||||
if TObject(draw[i]) = virtualTile then
|
if TObject(draw[i]) = virtualTile then
|
||||||
begin
|
begin
|
||||||
|
@ -1734,7 +1776,7 @@ begin
|
||||||
cell := TMapCell(draw[i]);
|
cell := TMapCell(draw[i]);
|
||||||
|
|
||||||
{if ResMan.Tiledata.LandTiles[cell.TileID].HasFlag(tdfTranslucent) then
|
{if ResMan.Tiledata.LandTiles[cell.TileID].HasFlag(tdfTranslucent) then
|
||||||
glColor4f(1.0, 1.0, 1.0, 0.5);} //Possible, but probably not like the OSI client
|
glColor4f(intensity, intensity, intensity, 0.5);} //Possible, but probably not like the OSI client
|
||||||
|
|
||||||
mat := nil;
|
mat := nil;
|
||||||
|
|
||||||
|
@ -1773,6 +1815,7 @@ begin
|
||||||
(TObject(draw[i]) = ghostTile) then //when we have a ghosttile, only draw that, but still store the real one
|
(TObject(draw[i]) = ghostTile) then //when we have a ghosttile, only draw that, but still store the real one
|
||||||
begin
|
begin
|
||||||
glBindTexture(GL_TEXTURE_2D, mat.Texture);
|
glBindTexture(GL_TEXTURE_2D, mat.Texture);
|
||||||
|
//if (not cell.Selected) and (intensity = 1.0) then
|
||||||
if not cell.Selected then
|
if not cell.Selected then
|
||||||
glEnable(GL_LIGHTING);
|
glEnable(GL_LIGHTING);
|
||||||
normals := FLandscape.Normals[offsetX, offsetY];
|
normals := FLandscape.Normals[offsetX, offsetY];
|
||||||
|
@ -1790,6 +1833,7 @@ begin
|
||||||
glNormal3f(normals[3].X, normals[3].Y, normals[3].Z);
|
glNormal3f(normals[3].X, normals[3].Y, normals[3].Z);
|
||||||
glTexCoord2f(0, 1); glVertex2d(drawX - 22, drawY + 22 - west * 4);
|
glTexCoord2f(0, 1); glVertex2d(drawX - 22, drawY + 22 - west * 4);
|
||||||
glEnd;
|
glEnd;
|
||||||
|
//if (not cell.Selected) and (intensity = 1.0) then
|
||||||
if not cell.Selected then
|
if not cell.Selected then
|
||||||
glDisable(GL_LIGHTING);
|
glDisable(GL_LIGHTING);
|
||||||
end;
|
end;
|
||||||
|
@ -1814,7 +1858,7 @@ begin
|
||||||
hue := nil;
|
hue := nil;
|
||||||
|
|
||||||
if staticTileData.HasFlag(tdfTranslucent) then
|
if staticTileData.HasFlag(tdfTranslucent) then
|
||||||
glColor4f(1.0, 1.0, 1.0, 0.5);
|
glColor4f(intensity, intensity, intensity, 0.5);
|
||||||
|
|
||||||
mat := FTextureManager.GetArtMaterial($4000 + staticItem.TileID, hue, (staticTileData.Flags and tdfPartialHue) = tdfPartialHue);
|
mat := FTextureManager.GetArtMaterial($4000 + staticItem.TileID, hue, (staticTileData.Flags and tdfPartialHue) = tdfPartialHue);
|
||||||
south := mat.RealHeight;
|
south := mat.RealHeight;
|
||||||
|
@ -2090,6 +2134,7 @@ procedure TfrmMain.OnClientHandlingPacket(ABuffer: TEnhancedMemoryStream);
|
||||||
var
|
var
|
||||||
sender, msg: string;
|
sender, msg: string;
|
||||||
i: Integer;
|
i: Integer;
|
||||||
|
accessLevel: TAccessLevel;
|
||||||
begin
|
begin
|
||||||
case ABuffer.ReadByte of
|
case ABuffer.ReadByte of
|
||||||
$01: //client connected
|
$01: //client connected
|
||||||
|
@ -2124,21 +2169,27 @@ begin
|
||||||
msg := ABuffer.ReadStringNull;
|
msg := ABuffer.ReadStringNull;
|
||||||
WriteChatMessage(sender, msg);
|
WriteChatMessage(sender, msg);
|
||||||
end;
|
end;
|
||||||
$07: //access level changed
|
$07: //access changed
|
||||||
begin
|
begin
|
||||||
dmNetwork.AccessLevel := TAccessLevel(ABuffer.ReadByte);
|
accessLevel := TAccessLevel(ABuffer.ReadByte);
|
||||||
if dmNetwork.AccessLevel = alNone then
|
dmNetwork.UpdateWriteMap(ABuffer);
|
||||||
|
|
||||||
|
if accessLevel <> dmNetwork.AccessLevel then
|
||||||
begin
|
begin
|
||||||
MessageDlg('AccessLevel change', 'Your account has been locked.', mtWarning, [mbOK], 0);
|
dmNetwork.AccessLevel := accessLevel;
|
||||||
mnuDisconnectClick(nil);
|
if accessLevel = alNone then
|
||||||
end else
|
begin
|
||||||
begin
|
MessageDlg('AccessLevel change', 'Your account has been locked.', mtWarning, [mbOK], 0);
|
||||||
ProcessAccessLevel;
|
mnuDisconnectClick(nil);
|
||||||
MessageDlg('AccessLevel change', Format('Your accesslevel has been changed to %s.', [GetAccessLevelString(dmNetwork.AccessLevel)]), mtWarning, [mbOK], 0);
|
end else
|
||||||
|
begin
|
||||||
|
ProcessAccessLevel;
|
||||||
|
MessageDlg('AccessLevel change', Format('Your accesslevel has been changed to %s.', [GetAccessLevelString(accessLevel)]), mtWarning, [mbOK], 0);
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
for i := Low(FAccessChangedListeners) to High(FAccessChangedListeners) do
|
for i := Low(FAccessChangedListeners) to High(FAccessChangedListeners) do
|
||||||
FAccessChangedListeners[i](dmNetwork.AccessLevel);
|
FAccessChangedListeners[i](accessLevel);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
@ -2189,7 +2240,8 @@ end;
|
||||||
|
|
||||||
function TfrmMain.CanBeModified(ATile: TWorldItem): Boolean;
|
function TfrmMain.CanBeModified(ATile: TWorldItem): Boolean;
|
||||||
begin
|
begin
|
||||||
Result := not (ATile is TVirtualTile);
|
Result := (not (ATile is TVirtualTile)) and
|
||||||
|
dmNetwork.CanWrite(ATile.X, ATile.Y);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
initialization
|
initialization
|
||||||
|
|
|
@ -122,7 +122,7 @@ implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
UGameResources, UfrmRadar, UfrmMain, UdmNetwork, UPacket, UGUIPlatformUtils,
|
UGameResources, UfrmRadar, UfrmMain, UdmNetwork, UPacket, UGUIPlatformUtils,
|
||||||
UAdminHandling, UPacketHandlers, UConsts;
|
UAdminHandling, UPacketHandlers;
|
||||||
|
|
||||||
type
|
type
|
||||||
{ TModifyRegionPacket }
|
{ TModifyRegionPacket }
|
||||||
|
|
|
@ -162,7 +162,7 @@ end;
|
||||||
procedure TAccount.Serialize(AElement: TDOMElement);
|
procedure TAccount.Serialize(AElement: TDOMElement);
|
||||||
var
|
var
|
||||||
i: Integer;
|
i: Integer;
|
||||||
child: TDOMElement;
|
child, regionNode: TDOMElement;
|
||||||
begin
|
begin
|
||||||
TXmlHelper.WriteString(AElement, 'Name', FName);
|
TXmlHelper.WriteString(AElement, 'Name', FName);
|
||||||
TXmlHelper.WriteString(AElement, 'PasswordHash', FPasswordHash);
|
TXmlHelper.WriteString(AElement, 'PasswordHash', FPasswordHash);
|
||||||
|
@ -171,7 +171,11 @@ begin
|
||||||
child := TXmlHelper.AssureElement(AElement, 'Regions');
|
child := TXmlHelper.AssureElement(AElement, 'Regions');
|
||||||
for i := 0 to FRegions.Count -1 do
|
for i := 0 to FRegions.Count -1 do
|
||||||
if Config.Regions.Find(FRegions[i]) <> nil then //Validate if the region (still) exists
|
if Config.Regions.Find(FRegions[i]) <> nil then //Validate if the region (still) exists
|
||||||
TXmlHelper.WriteString(child, 'Region', FRegions[i]);
|
begin
|
||||||
|
regionNode := child.OwnerDocument.CreateElement('Region');
|
||||||
|
child.AppendChild(regionNode);
|
||||||
|
regionNode.AppendChild(regionNode.OwnerDocument.CreateTextNode(FRegions[i]));
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TAccountList }
|
{ TAccountList }
|
||||||
|
|
|
@ -148,25 +148,24 @@ begin
|
||||||
if password <> '' then
|
if password <> '' then
|
||||||
account.PasswordHash := MD5Print(MD5String(password));
|
account.PasswordHash := MD5Print(MD5String(password));
|
||||||
|
|
||||||
|
account.AccessLevel := accessLevel;
|
||||||
|
|
||||||
account.Regions.Clear;
|
account.Regions.Clear;
|
||||||
for i := 0 to regionCount - 1 do
|
for i := 0 to regionCount - 1 do
|
||||||
account.Regions.Add(ABuffer.ReadStringNull);
|
account.Regions.Add(ABuffer.ReadStringNull);
|
||||||
account.Invalidate;
|
account.Invalidate;
|
||||||
|
|
||||||
if account.AccessLevel <> accessLevel then
|
CEDServerInstance.TCPServer.IterReset;
|
||||||
|
while CEDServerInstance.TCPServer.IterNext do
|
||||||
begin
|
begin
|
||||||
account.AccessLevel := accessLevel;
|
netState := TNetState(CEDServerInstance.TCPServer.Iterator.UserData);
|
||||||
CEDServerInstance.TCPServer.IterReset;
|
if (netState <> nil) and (netState.Account = account) then
|
||||||
while CEDServerInstance.TCPServer.IterNext do
|
|
||||||
begin
|
begin
|
||||||
netState := TNetState(CEDServerInstance.TCPServer.Iterator.UserData);
|
CEDServerInstance.SendPacket(netState,
|
||||||
if (netState <> nil) and (netState.Account = account) then
|
TAccessChangedPacket.Create(account));
|
||||||
begin
|
|
||||||
CEDServerInstance.SendPacket(netState,
|
|
||||||
TAccessLevelChangedPacket.Create(accessLevel));
|
|
||||||
end;
|
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
CEDServerInstance.SendPacket(ANetState,
|
CEDServerInstance.SendPacket(ANetState,
|
||||||
TModifyUserResponsePacket.Create(muModified, account));
|
TModifyUserResponsePacket.Create(muModified, account));
|
||||||
end else
|
end else
|
||||||
|
@ -238,6 +237,10 @@ var
|
||||||
status: TModifyRegionStatus;
|
status: TModifyRegionStatus;
|
||||||
i, areaCount: Integer;
|
i, areaCount: Integer;
|
||||||
x1, y1, x2, y2: Word;
|
x1, y1, x2, y2: Word;
|
||||||
|
|
||||||
|
account: TAccount;
|
||||||
|
needsUpdate: Boolean;
|
||||||
|
netState: TNetState;
|
||||||
begin
|
begin
|
||||||
regionName := ABuffer.ReadStringNull;
|
regionName := ABuffer.ReadStringNull;
|
||||||
|
|
||||||
|
@ -268,6 +271,31 @@ begin
|
||||||
|
|
||||||
AdminBroadcast(alAdministrator,
|
AdminBroadcast(alAdministrator,
|
||||||
TModifyRegionResponsePacket.Create(status, region));
|
TModifyRegionResponsePacket.Create(status, region));
|
||||||
|
|
||||||
|
if status = mrModified then
|
||||||
|
begin
|
||||||
|
CEDServerInstance.TCPServer.IterReset;
|
||||||
|
while CEDServerInstance.TCPServer.IterNext do
|
||||||
|
begin
|
||||||
|
netState := TNetState(CEDServerInstance.TCPServer.Iterator.UserData);
|
||||||
|
if netState <> nil then
|
||||||
|
begin
|
||||||
|
account := netState.Account;
|
||||||
|
i := 0;
|
||||||
|
needsUpdate := False;
|
||||||
|
while (i < account.Regions.Count) and (not needsUpdate) do
|
||||||
|
begin
|
||||||
|
if account.Regions.Strings[i] = regionName then
|
||||||
|
needsUpdate := True;
|
||||||
|
Inc(i);
|
||||||
|
end;
|
||||||
|
|
||||||
|
if needsUpdate then
|
||||||
|
CEDServerInstance.SendPacket(netState,
|
||||||
|
TAccessChangedPacket.Create(account))
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure OnDeleteRegionPacket(ABuffer: TEnhancedMemoryStream;
|
procedure OnDeleteRegionPacket(ABuffer: TEnhancedMemoryStream;
|
||||||
|
|
|
@ -21,7 +21,7 @@
|
||||||
* CDDL HEADER END
|
* CDDL HEADER END
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* Portions Copyright 2007 Andreas Schneider
|
* Portions Copyright 2008 Andreas Schneider
|
||||||
*)
|
*)
|
||||||
unit UClientHandling;
|
unit UClientHandling;
|
||||||
|
|
||||||
|
@ -31,7 +31,7 @@ interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
Classes, SysUtils, UPacket, UPacketHandlers, UConfig, UAccount, UNetState,
|
Classes, SysUtils, UPacket, UPacketHandlers, UConfig, UAccount, UNetState,
|
||||||
UEnhancedMemoryStream, UEnums, math;
|
UEnhancedMemoryStream, UEnums, Math;
|
||||||
|
|
||||||
type
|
type
|
||||||
|
|
||||||
|
@ -65,16 +65,23 @@ type
|
||||||
constructor Create(ASender, AMessage: string);
|
constructor Create(ASender, AMessage: string);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TAccessLevelChangedPacket }
|
{ TAccessChangedPacket }
|
||||||
|
|
||||||
TAccessLevelChangedPacket = class(TPacket)
|
TAccessChangedPacket = class(TPacket)
|
||||||
constructor Create(AAccessLevel: TAccessLevel);
|
constructor Create(AAccount: TAccount);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
procedure OnClientHandlerPacket(ABuffer: TEnhancedMemoryStream; ANetState: TNetState);
|
procedure OnClientHandlerPacket(ABuffer: TEnhancedMemoryStream;
|
||||||
procedure OnUpdateClientPosPacket(ABuffer: TEnhancedMemoryStream; ANetState: TNetState);
|
ANetState: TNetState);
|
||||||
procedure OnChatMessagePacket(ABuffer: TEnhancedMemoryStream; ANetState: TNetState);
|
procedure OnUpdateClientPosPacket(ABuffer: TEnhancedMemoryStream;
|
||||||
procedure OnGotoClientPosPacket(ABuffer: TEnhancedMemoryStream; ANetState: TNetState);
|
ANetState: TNetState);
|
||||||
|
procedure OnChatMessagePacket(ABuffer: TEnhancedMemoryStream;
|
||||||
|
ANetState: TNetState);
|
||||||
|
procedure OnGotoClientPosPacket(ABuffer: TEnhancedMemoryStream;
|
||||||
|
ANetState: TNetState);
|
||||||
|
|
||||||
|
procedure WriteAccountRestrictions(AStream: TEnhancedMemoryStream;
|
||||||
|
AAccount: TAccount);
|
||||||
|
|
||||||
var
|
var
|
||||||
ClientPacketHandlers: array[0..$FF] of TPacketHandler;
|
ClientPacketHandlers: array[0..$FF] of TPacketHandler;
|
||||||
|
@ -82,9 +89,10 @@ var
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
uses
|
uses
|
||||||
UCEDServer, UPackets;
|
UCEDServer, UPackets, URegions;
|
||||||
|
|
||||||
procedure OnClientHandlerPacket(ABuffer: TEnhancedMemoryStream; ANetState: TNetState);
|
procedure OnClientHandlerPacket(ABuffer: TEnhancedMemoryStream;
|
||||||
|
ANetState: TNetState);
|
||||||
var
|
var
|
||||||
packetHandler: TPacketHandler;
|
packetHandler: TPacketHandler;
|
||||||
begin
|
begin
|
||||||
|
@ -118,7 +126,46 @@ var
|
||||||
begin
|
begin
|
||||||
account := Config.Accounts.Find(ABuffer.ReadStringNull);
|
account := Config.Accounts.Find(ABuffer.ReadStringNull);
|
||||||
if account <> nil then
|
if account <> nil then
|
||||||
CEDServerInstance.SendPacket(ANetState, TSetClientPosPacket.Create(account.LastPos));
|
CEDServerInstance.SendPacket(ANetState,
|
||||||
|
TSetClientPosPacket.Create(account.LastPos));
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure WriteAccountRestrictions(AStream: TEnhancedMemoryStream;
|
||||||
|
AAccount: TAccount);
|
||||||
|
var
|
||||||
|
areaCount: Word;
|
||||||
|
i, j, offset, newOffset: Integer;
|
||||||
|
region: TRegion;
|
||||||
|
area: TRect;
|
||||||
|
begin
|
||||||
|
offset := AStream.Position;
|
||||||
|
areaCount := 0;
|
||||||
|
AStream.WriteWord(areaCount);
|
||||||
|
|
||||||
|
if AAccount.AccessLevel >= alAdministrator then
|
||||||
|
Exit; //Admins shouldn't have restrictions anyway
|
||||||
|
|
||||||
|
for i := 0 to AAccount.Regions.Count - 1 do
|
||||||
|
begin
|
||||||
|
region := Config.Regions.Find(AAccount.Regions.Strings[i]);
|
||||||
|
if region <> nil then
|
||||||
|
for j := 0 to region.Areas.Count - 1 do
|
||||||
|
begin
|
||||||
|
area := region.Areas.Rects[j];
|
||||||
|
AStream.WriteWord(area.Left);
|
||||||
|
AStream.WriteWord(area.Top);
|
||||||
|
AStream.WriteWord(area.Right);
|
||||||
|
AStream.WriteWord(area.Bottom);
|
||||||
|
Inc(areaCount);
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
if areaCount > 0 then
|
||||||
|
begin
|
||||||
|
newOffset := AStream.Position;
|
||||||
|
AStream.Position := offset;
|
||||||
|
AStream.WriteWord(areaCount);
|
||||||
|
AStream.Position := newOffset;
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TClientConnectedPacket }
|
{ TClientConnectedPacket }
|
||||||
|
@ -152,7 +199,8 @@ begin
|
||||||
begin
|
begin
|
||||||
repeat
|
repeat
|
||||||
netState := TNetState(CEDServerInstance.TCPServer.Iterator.UserData);
|
netState := TNetState(CEDServerInstance.TCPServer.Iterator.UserData);
|
||||||
if (netState <> nil) and (netState <> AAvoid) and (netState.Account <> nil) then
|
if (netState <> nil) and (netState <> AAvoid) and
|
||||||
|
(netState.Account <> nil) then
|
||||||
FStream.WriteStringNull(netState.Account.Name);
|
FStream.WriteStringNull(netState.Account.Name);
|
||||||
until not CEDServerInstance.TCPServer.IterNext;
|
until not CEDServerInstance.TCPServer.IterNext;
|
||||||
end;
|
end;
|
||||||
|
@ -178,13 +226,14 @@ begin
|
||||||
FStream.WriteStringNull(AMessage);
|
FStream.WriteStringNull(AMessage);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TAccessLevelChangedPacket }
|
{ TAccessChangedPacket }
|
||||||
|
|
||||||
constructor TAccessLevelChangedPacket.Create(AAccessLevel: TAccessLevel);
|
constructor TAccessChangedPacket.Create(AAccount: TAccount);
|
||||||
begin
|
begin
|
||||||
inherited Create($0C, 0);
|
inherited Create($0C, 0);
|
||||||
FStream.WriteByte($07);
|
FStream.WriteByte($07);
|
||||||
FStream.WriteByte(Byte(AAccessLevel));
|
FStream.WriteByte(Byte(AAccount.AccessLevel));
|
||||||
|
WriteAccountRestrictions(FStream, AAccount);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{$WARNINGS OFF}
|
{$WARNINGS OFF}
|
||||||
|
|
|
@ -44,7 +44,7 @@ type
|
||||||
{ TLoginResponsePacket }
|
{ TLoginResponsePacket }
|
||||||
|
|
||||||
TLoginResponsePacket = class(TPacket)
|
TLoginResponsePacket = class(TPacket)
|
||||||
constructor Create(AState: TLoginState; AAccessLevel: TAccessLevel = alNone);
|
constructor Create(AState: TLoginState; AAccount: TAccount = nil);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
{ TServerStatePacket }
|
{ TServerStatePacket }
|
||||||
|
@ -111,7 +111,7 @@ begin
|
||||||
begin
|
begin
|
||||||
Writeln(TimeStamp, 'Login (', username, '): ', ANetState.Socket.PeerAddress);
|
Writeln(TimeStamp, 'Login (', username, '): ', ANetState.Socket.PeerAddress);
|
||||||
ANetState.Account := account;
|
ANetState.Account := account;
|
||||||
CEDServerInstance.SendPacket(ANetState, TLoginResponsePacket.Create(lsOK, account.AccessLevel));
|
CEDServerInstance.SendPacket(ANetState, TLoginResponsePacket.Create(lsOK, account));
|
||||||
CEDServerInstance.SendPacket(ANetState, TCompressedPacket.Create(
|
CEDServerInstance.SendPacket(ANetState, TCompressedPacket.Create(
|
||||||
TClientListPacket.Create(ANetState)));
|
TClientListPacket.Create(ANetState)));
|
||||||
CEDServerInstance.SendPacket(nil, TClientConnectedPacket.Create(username));
|
CEDServerInstance.SendPacket(nil, TClientConnectedPacket.Create(username));
|
||||||
|
@ -154,16 +154,17 @@ end;
|
||||||
{ TLoginResponsePacket }
|
{ TLoginResponsePacket }
|
||||||
|
|
||||||
constructor TLoginResponsePacket.Create(AState: TLoginState;
|
constructor TLoginResponsePacket.Create(AState: TLoginState;
|
||||||
AAccessLevel: TAccessLevel = alNone);
|
AAccount: TAccount = nil);
|
||||||
begin
|
begin
|
||||||
inherited Create($02, 0);
|
inherited Create($02, 0);
|
||||||
FStream.WriteByte($03);
|
FStream.WriteByte($03);
|
||||||
FStream.WriteByte(Byte(AState));
|
FStream.WriteByte(Byte(AState));
|
||||||
if AState = lsOK then
|
if AState = lsOK then
|
||||||
begin
|
begin
|
||||||
FStream.WriteByte(Byte(AAccessLevel));
|
FStream.WriteByte(Byte(AAccount.AccessLevel));
|
||||||
FStream.WriteWord(Config.Map.Width);
|
FStream.WriteWord(Config.Map.Width);
|
||||||
FStream.WriteWord(Config.Map.Height);
|
FStream.WriteWord(Config.Map.Height);
|
||||||
|
WriteAccountRestrictions(FStream, AAccount);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
|
|
@ -85,8 +85,10 @@ begin
|
||||||
for j := 0 to region.Areas.Count - 1 do
|
for j := 0 to region.Areas.Count - 1 do
|
||||||
begin
|
begin
|
||||||
rect := region.Areas.Rects[j];
|
rect := region.Areas.Rects[j];
|
||||||
if InRange(AX, rect.Left, rect.Right) and
|
if (AX >= rect.Left) and
|
||||||
InRange(AY, rect.Top, rect.Bottom) then
|
(AX < rect.Right) and
|
||||||
|
(AY >= rect.Top) and
|
||||||
|
(AY < rect.Bottom) then
|
||||||
Exit(True);
|
Exit(True);
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
|
@ -40,7 +40,7 @@ uses
|
||||||
|
|
||||||
begin
|
begin
|
||||||
Writeln('');
|
Writeln('');
|
||||||
Writeln('UO CentrED Server Version ', ProductVersion);
|
Writeln('CentrED Server Version ', ProductVersion);
|
||||||
Writeln('Copyright ', Copyright);
|
Writeln('Copyright ', Copyright);
|
||||||
//Writeln('================================');
|
//Writeln('================================');
|
||||||
Writeln('');
|
Writeln('');
|
||||||
|
|
Loading…
Reference in New Issue