Statistics
| Branch: | Tag: | Revision:

root / Client / UfrmRegionControl.pas @ 13:c78b5eafa10e

History | View | Annotate | Download (18.2 kB)

1
(*
2
 * CDDL HEADER START
3
 *
4
 * The contents of this file are subject to the terms of the
5
 * Common Development and Distribution License, Version 1.0 only
6
 * (the "License").  You may not use this file except in compliance
7
 * with the License.
8
 *
9
 * You can obtain a copy of the license at
10
 * http://www.opensource.org/licenses/cddl1.php.
11
 * See the License for the specific language governing permissions
12
 * and limitations under the License.
13
 *
14
 * When distributing Covered Code, include this CDDL HEADER in each
15
 * file and include the License file at
16
 * http://www.opensource.org/licenses/cddl1.php.  If applicable,
17
 * add the following below this CDDL HEADER, with the fields enclosed
18
 * by brackets "[]" replaced with your own identifying * information:
19
 *      Portions Copyright [yyyy] [name of copyright owner]
20
 *
21
 * CDDL HEADER END
22
 *
23
 *
24
 *      Portions Copyright 2008 Andreas Schneider
25
 *)
26
unit UfrmRegionControl;
27
28
{$mode objfpc}{$H+}
29
30
interface
31
32
uses
33
  Classes, SysUtils, math, LResources, Forms, Controls, Graphics, Dialogs,
34
  VirtualTrees, ExtCtrls, ImagingComponents, StdCtrls, Buttons, Spin, LCLIntf,
35
  UEnhancedMemoryStream, Menus, URectList;
36
37
type
38
  TAreaMoveType = (amLeft, amTop, amRight, amBottom);
39
  TAreaMove = set of TAreaMoveType;
40
41
  { TfrmRegionControl }
42
43
  TfrmRegionControl = class(TForm)
44
    btnAddArea: TSpeedButton;
45
    btnClearArea: TSpeedButton;
46
    btnDeleteArea: TSpeedButton;
47
    btnClose: TButton;
48
    btnSave: TButton;
49
    Label1: TLabel;
50
    lblX: TLabel;
51
    lblY: TLabel;
52
    mnuAddRegion: TMenuItem;
53
    mnuRemoveRegion: TMenuItem;
54
    Panel1: TPanel;
55
    Panel2: TPanel;
56
    Panel3: TPanel;
57
    pbArea: TPaintBox;
58
    pnlAreaControls: TPanel;
59
    pmRegions: TPopupMenu;
60
    sbArea: TScrollBox;
61
    seX1: TSpinEdit;
62
    seX2: TSpinEdit;
63
    seY1: TSpinEdit;
64
    seY2: TSpinEdit;
65
    vstRegions: TVirtualStringTree;
66
    vstArea: TVirtualStringTree;
67
    procedure mnuAddRegionClick(Sender: TObject);
68
    procedure mnuRemoveRegionClick(Sender: TObject);
69
    procedure btnAddAreaClick(Sender: TObject);
70
    procedure btnClearAreaClick(Sender: TObject);
71
    procedure btnCloseClick(Sender: TObject);
72
    procedure btnDeleteAreaClick(Sender: TObject);
73
    procedure btnSaveClick(Sender: TObject);
74
    procedure FormCreate(Sender: TObject);
75
    procedure FormDestroy(Sender: TObject);
76
    procedure FormShow(Sender: TObject);
77
    procedure pbAreaMouseDown(Sender: TObject; Button: TMouseButton;
78
      Shift: TShiftState; X, Y: Integer);
79
    procedure pbAreaMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer
80
      );
81
    procedure pbAreaPaint(Sender: TObject);
82
    procedure seX1Change(Sender: TObject);
83
    procedure vstAreaChange(Sender: TBaseVirtualTree; Node: PVirtualNode);
84
    procedure vstAreaGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
85
      Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
86
    procedure vstRegionsChange(Sender: TBaseVirtualTree; Node: PVirtualNode);
87
    procedure vstRegionsFreeNode(Sender: TBaseVirtualTree; Node: PVirtualNode);
88
    procedure vstRegionsGetText(Sender: TBaseVirtualTree; Node: PVirtualNode;
89
      Column: TColumnIndex; TextType: TVSTTextType; var CellText: WideString);
90
  protected
91
    FLastX: Integer;
92
    FLastY: Integer;
93
    FAreaMove: TAreaMove;
94
    function FindRegion(AName: string): PVirtualNode;
95
    procedure OnModifyRegionPacket(ABuffer: TEnhancedMemoryStream);
96
    procedure OnDeleteRegionPacket(ABuffer: TEnhancedMemoryStream);
97
    procedure OnListRegionsPacket(ABuffer: TEnhancedMemoryStream);
98
  private
99
    { private declarations }
100
  public
101
    { public declarations }
102
  end; 
103
  
104
var
105
  frmRegionControl: TfrmRegionControl;
106
107
implementation
108
109
uses
110
  UGameResources, UfrmRadar, UfrmMain, UdmNetwork, UPacket, UGUIPlatformUtils,
111
  UAdminHandling, UPacketHandlers;
112
113
type
114
115
  PRegionInfo = ^TRegionInfo;
116
  TRegionInfo = record
117
    Name: string;
118
    Areas: TRectList;
119
  end;
120
121
  { TModifyRegionPacket }
122
123
  TModifyRegionPacket = class(TPacket)
124
    constructor Create(ARegionInfo: TRegionInfo);
125
  end;
126
127
  { TDeleteRegionPacket }
128
129
  TDeleteRegionPacket = class(TPacket)
130
    constructor Create(AName: string);
131
  end;
132
133
  { TRequestRegionListPacket }
134
135
  TRequestRegionListPacket = class(TPacket)
136
    constructor Create;
137
  end;
138
139
{ TModifyRegionPacket }
140
141
constructor TModifyRegionPacket.Create(ARegionInfo: TRegionInfo);
142
var
143
  i: Integer;
144
  count: Byte;
145
  area: TRect;
146
begin
147
  inherited Create($03, 0); //Admin Packet
148
  FStream.WriteByte($08); //Admin PacketID
149
  FStream.WriteStringNull(ARegionInfo.Name);
150
  count := Min(ARegionInfo.Areas.Count, 256);
151
  FStream.WriteByte(count);
152
  for i := 0 to count - 1 do
153
  begin
154
    area := ARegionInfo.Areas.Rects[i];
155
    FStream.WriteWord(area.Left);
156
    FStream.WriteWord(area.Top);
157
    FStream.WriteWord(area.Right);
158
    FStream.WriteWord(area.Bottom);
159
  end;
160
end;
161
162
{ TDeleteRegionPacket }
163
164
constructor TDeleteRegionPacket.Create(AName: string);
165
begin
166
  inherited Create($03, 0); //Admin Packet
167
  FStream.WriteByte($09); //Admin PacketID
168
  FStream.WriteStringNull(AName);
169
end;
170
171
{ TRequestRegionListPacket }
172
173
constructor TRequestRegionListPacket.Create;
174
begin
175
  inherited Create($03, 0); //Admin Packet
176
  FStream.WriteByte($0A); //Admin PacketID
177
end;
178
179
{ TfrmRegionControl }
180
181
procedure TfrmRegionControl.FormCreate(Sender: TObject);
182
begin
183
  pbArea.Width := frmRadarMap.Radar.Width;
184
  pbArea.Height := frmRadarMap.Radar.Height;
185
  seX1.MaxValue := ResMan.Landscape.CellWidth;
186
  seX2.MaxValue := ResMan.Landscape.CellWidth;
187
  seY1.MaxValue := ResMan.Landscape.CellHeight;
188
  seY2.MaxValue := ResMan.Landscape.CellHeight;
189
  
190
  vstArea.NodeDataSize := SizeOf(TRect);
191
  vstRegions.NodeDataSize := SizeOf(TRegionInfo);
192
  
193
  frmRadarMap.Dependencies.Add(pbArea);
194
195
  AssignAdminPacketHandler($08, TPacketHandler.Create(0, @OnModifyRegionPacket));
196
  AssignAdminPacketHandler($09, TPacketHandler.Create(0, @OnDeleteRegionPacket));
197
  AssignAdminPacketHandler($0A, TPacketHandler.Create(0, @OnListRegionsPacket));
198
end;
199
200
procedure TfrmRegionControl.FormDestroy(Sender: TObject);
201
begin
202
  frmRadarMap.Dependencies.Remove(pbArea);
203
  if AdminPacketHandlers[$08] <> nil then FreeAndNil(AdminPacketHandlers[$08]);
204
  if AdminPacketHandlers[$09] <> nil then FreeAndNil(AdminPacketHandlers[$09]);
205
  if AdminPacketHandlers[$0A] <> nil then FreeAndNil(AdminPacketHandlers[$0A]);
206
end;
207
208
procedure TfrmRegionControl.FormShow(Sender: TObject);
209
begin
210
  SetWindowParent(Handle, frmMain.Handle);
211
  btnSave.Enabled := False; //no changes yet
212
  dmNetwork.Send(TRequestRegionListPacket.Create);
213
end;
214
215
procedure TfrmRegionControl.btnSaveClick(Sender: TObject);
216
var
217
  regionNode: PVirtualNode;
218
  regionInfo: PRegionInfo;
219
  areaNode: PVirtualNode;
220
  areaInfo: PRect;
221
begin
222
  btnSave.Enabled := False;
223
224
  //Refresh the current region
225
  regionNode := vstRegions.GetFirstSelected;
226
  if regionNode <> nil then
227
  begin
228
    regionInfo := vstRegions.GetNodeData(regionNode);
229
    regionInfo^.Areas.Clear;
230
    areaNode := vstArea.GetFirst;
231
    while areaNode <> nil do
232
    begin
233
      areaInfo := vstArea.GetNodeData(areaNode);
234
      regionInfo^.Areas.Add(areaInfo^.Left, areaInfo^.Top, areaInfo^.Right,
235
        areaInfo^.Bottom);
236
      areaNode := vstArea.GetNext(areaNode);
237
    end;
238
239
    //Send the modified values
240
    dmNetwork.Send(TModifyRegionPacket.Create(regionInfo^));
241
  end;
242
243
  //Clear the selection
244
  vstRegions.ClearSelection;
245
end;
246
247
procedure TfrmRegionControl.mnuAddRegionClick(Sender: TObject);
248
var
249
  regionName: string;
250
  node: PVirtualNode;
251
  regionInfo: PRegionInfo;
252
begin
253
  regionName := '';
254
  if InputQuery('New Region', 'Enter the name for the new region:', regionName) then
255
  begin
256
    if FindRegion(regionName) = nil then
257
    begin
258
      node := vstRegions.AddChild(nil);
259
      regionInfo := vstRegions.GetNodeData(node);
260
      regionInfo^.Name := regionName;
261
      regionInfo^.Areas := TRectList.Create;
262
      vstRegions.ClearSelection;
263
      vstRegions.Selected[node] := True;
264
      btnSave.Enabled := True;
265
    end else
266
    begin
267
      MessageDlg('New Region', 'The region could not be added. A region with ' +
268
        'that name already exists.', mtError, [mbOK], 0);
269
    end;
270
  end;
271
end;
272
273
procedure TfrmRegionControl.mnuRemoveRegionClick(Sender: TObject);
274
var
275
  regionNode: PVirtualNode;
276
  regionInfo: PRegionInfo;
277
begin
278
  regionNode := vstRegions.GetFirstSelected;
279
  if (regionNode <> nil) and (MessageDlg('Delete Region', 'Are you sure, you ' +
280
    'want to delete the selected region?', mtConfirmation, [mbYes, mbNo], 0) = mrYes) then
281
  begin
282
    regionInfo := vstRegions.GetNodeData(regionNode);
283
    dmNetwork.Send(TDeleteRegionPacket.Create(regionInfo^.Name));
284
    vstRegions.Selected[regionNode] := False;
285
  end;
286
end;
287
288
procedure TfrmRegionControl.btnAddAreaClick(Sender: TObject);
289
var
290
  node: PVirtualNode;
291
  areaInfo: PRect;
292
begin
293
  node := vstArea.AddChild(nil);
294
  areaInfo := vstArea.GetNodeData(node);
295
  areaInfo^.Left := 0;
296
  areaInfo^.Top := 0;
297
  areaInfo^.Right := 0;
298
  areaInfo^.Bottom := 0;
299
  vstArea.ClearSelection;
300
  vstArea.Selected[node] := True;
301
  vstArea.FocusedNode := node;
302
303
  btnSave.Enabled := True; //possible change to be saved
304
end;
305
306
procedure TfrmRegionControl.btnClearAreaClick(Sender: TObject);
307
begin
308
  vstArea.Clear;
309
  vstAreaChange(vstArea, nil);
310
end;
311
312
procedure TfrmRegionControl.btnCloseClick(Sender: TObject);
313
begin
314
  if btnSave.Enabled and (MessageDlg('Unsaved changes', 'There are unsaved ' +
315
    'changes.' + #13#10+#13#10+ 'Do you want to save them now?',
316
    mtConfirmation, [mbYes, mbNo], 0) = mrYes) then
317
  begin
318
    btnSaveClick(Sender);
319
  end;
320
321
  Close;
322
end;
323
324
procedure TfrmRegionControl.btnDeleteAreaClick(Sender: TObject);
325
begin
326
  vstArea.DeleteSelectedNodes;
327
  vstAreaChange(vstArea, nil);
328
329
  btnSave.Enabled := True; //possible change to be saved
330
end;
331
332
procedure TfrmRegionControl.pbAreaMouseDown(Sender: TObject;
333
  Button: TMouseButton; Shift: TShiftState; X, Y: Integer);
334
var
335
  areaNode, match: PVirtualNode;
336
  areaInfo: PRect;
337
  p: TPoint;
338
begin
339
  FAreaMove := [];
340
  p := Point(X * 8, Y * 8);
341
  match := nil;
342
  areaNode := vstArea.GetFirst;
343
  while areaNode <> nil do //find the last matching area
344
  begin
345
    areaInfo := vstArea.GetNodeData(areaNode);
346
    if PtInRect(areaInfo^, p) then
347
      match := areaNode;
348
    areaNode := vstArea.GetNext(areaNode);
349
  end;
350
  if match <> nil then
351
  begin
352
    areaInfo := vstArea.GetNodeData(match);
353
    if p.x - areaInfo^.Left <= 64 then Include(FAreaMove, amLeft);
354
    if p.y - areaInfo^.Top <= 64 then Include(FAreaMove, amTop);
355
    if areaInfo^.Right - p.x <= 64 then Include(FAreaMove, amRight);
356
    if areaInfo^.Bottom - p.y <= 64 then Include(FAreaMove, amBottom);
357
    if FAreaMove = [] then
358
      FAreaMove := [amLeft, amTop, amRight, amBottom];
359
  end else
360
  begin
361
    match := vstArea.AddChild(nil);
362
    areaInfo := vstArea.GetNodeData(match);
363
    areaInfo^.Left := p.x;
364
    areaInfo^.Top := p.y;
365
    areaInfo^.Right := p.x;
366
    areaInfo^.Bottom := p.y;
367
    pbArea.Repaint;
368
    FAreaMove := [amRight, amBottom];
369
  end;
370
  vstArea.ClearSelection;
371
  vstArea.Selected[match] := True;
372
  FLastX := X;
373
  FLastY := Y;
374
end;
375
376
procedure TfrmRegionControl.pbAreaMouseMove(Sender: TObject;
377
  Shift: TShiftState; X, Y: Integer);
378
var
379
  offsetX, offsetY: Integer;
380
begin
381
  if (ssLeft in Shift) and (vstArea.GetFirstSelected <> nil) then
382
  begin
383
    offsetX := (X - FLastX) * 8;
384
    offsetY := (Y - FLastY) * 8;
385
    if amLeft in FAreaMove then seX1.Value := seX1.Value + offsetX;
386
    if amRight in FAreaMove then seX2.Value := seX2.Value + offsetX;
387
    if amTop in FAreaMove then seY1.Value := seY1.Value + offsetY;
388
    if amBottom in FAreaMove then seY2.Value := seY2.Value + offsetY;
389
    FLastX := X;
390
    FLastY := Y;
391
    seX1Change(nil);
392
  end;
393
end;
394
395
procedure TfrmRegionControl.pbAreaPaint(Sender: TObject);
396
var
397
  node: PVirtualNode;
398
  areaInfo: PRect;
399
begin
400
  DisplayImage(pbArea.Canvas, 0, 0, frmRadarMap.Radar);
401
  pbArea.Canvas.Pen.Color := clRed;
402
  pbArea.Canvas.Brush.Color := clMaroon;
403
  pbArea.Canvas.Brush.Style := bsFDiagonal;
404
  node := vstArea.GetFirst;
405
  while node <> nil do
406
  begin
407
    if vstArea.Selected[node] then
408
    begin
409
      pbArea.Canvas.Pen.Width := 2;
410
      pbArea.Canvas.Pen.Style := psSolid;
411
    end else
412
    begin
413
      pbArea.Canvas.Pen.Width := 1;
414
      pbArea.Canvas.Pen.Style := psDot;
415
    end;
416
    areaInfo := vstArea.GetNodeData(node);
417
    pbArea.Canvas.Rectangle(areaInfo^.Left div 8, areaInfo^.Top div 8,
418
      areaInfo^.Right div 8 + 1, areaInfo^.Bottom div 8 + 1);
419
    node := vstArea.GetNext(node);
420
  end;
421
end;
422
423
procedure TfrmRegionControl.seX1Change(Sender: TObject);
424
var
425
  node: PVirtualNode;
426
  areaInfo: PRect;
427
begin
428
  node := vstArea.GetFirstSelected;
429
  if node <> nil then
430
  begin
431
    areaInfo := vstArea.GetNodeData(node);
432
    areaInfo^.Left := seX1.Value;
433
    areaInfo^.Right := seX2.Value;
434
    areaInfo^.Top := seY1.Value;
435
    areaInfo^.Bottom := seY2.Value;
436
    vstArea.InvalidateNode(node);
437
    pbArea.Repaint;
438
439
    btnSave.Enabled := True; //possible change to be saved
440
  end;
441
end;
442
443
procedure TfrmRegionControl.vstAreaChange(Sender: TBaseVirtualTree;
444
  Node: PVirtualNode);
445
var
446
  areaInfo: PRect;
447
  selected: Boolean;
448
begin
449
  selected := (Node <> nil) and Sender.Selected[Node];
450
  btnDeleteArea.Enabled := selected;
451
  lblX.Enabled := selected;
452
  lblY.Enabled := selected;
453
  seX1.Enabled := selected;
454
  seX2.Enabled := selected;
455
  seY1.Enabled := selected;
456
  seY2.Enabled := selected;
457
  if selected then
458
  begin
459
    areaInfo := Sender.GetNodeData(Node);
460
    seX1.Value := areaInfo^.Left;
461
    seX2.Value := areaInfo^.Right;
462
    seY1.Value := areaInfo^.Top;
463
    seY2.Value := areaInfo^.Bottom;
464
  end;
465
  pbArea.Repaint;
466
end;
467
468
procedure TfrmRegionControl.vstAreaGetText(Sender: TBaseVirtualTree;
469
  Node: PVirtualNode; Column: TColumnIndex; TextType: TVSTTextType;
470
  var CellText: WideString);
471
var
472
  areaInfo: PRect;
473
begin
474
  areaInfo := Sender.GetNodeData(Node);
475
  CellText := Format('(%d, %d), (%d, %d)', [areaInfo^.Left, areaInfo^.Top,
476
    areaInfo^.Right, areaInfo^.Bottom]);
477
end;
478
479
procedure TfrmRegionControl.vstRegionsChange(Sender: TBaseVirtualTree;
480
  Node: PVirtualNode);
481
var
482
  i: Integer;
483
  selected, areaNode: PVirtualNode;
484
  regionInfo: PRegionInfo;
485
  areaInfo: PRect;
486
begin
487
  if btnSave.Enabled and (MessageDlg('Unsaved changes', 'There are unsaved ' +
488
    'changes.' + #13#10+#13#10+ 'Do you want to save them now?',
489
    mtConfirmation, [mbYes, mbNo], 0) = mrYes) then
490
  begin
491
    btnSaveClick(Sender);
492
  end;
493
494
  vstArea.BeginUpdate;
495
  vstArea.Clear;
496
  selected := Sender.GetFirstSelected;
497
  if selected <> nil then
498
  begin
499
    btnAddArea.Enabled := True;
500
    btnClearArea.Enabled := True;
501
    mnuRemoveRegion.Enabled := True;
502
503
    regionInfo := Sender.GetNodeData(selected);
504
    for i := 0 to regionInfo^.Areas.Count - 1 do
505
    begin
506
      areaNode := vstArea.AddChild(nil);
507
      areaInfo := vstArea.GetNodeData(areaNode);
508
      with regionInfo^.Areas.Rects[i] do
509
      begin
510
        areaInfo^.Left   := Left;
511
        areaInfo^.Top    := Top;
512
        areaInfo^.Right  := Right;
513
        areaInfo^.Bottom := Bottom;
514
      end;
515
    end;
516
  end else
517
  begin
518
    btnAddArea.Enabled := False;
519
    btnDeleteArea.Enabled := False;
520
    btnClearArea.Enabled := False;
521
    mnuRemoveRegion.Enabled := False;
522
  end;
523
  vstArea.EndUpdate;
524
  pbArea.Repaint;
525
526
  btnSave.Enabled := False; //no changes to be saved
527
end;
528
529
procedure TfrmRegionControl.vstRegionsFreeNode(Sender: TBaseVirtualTree;
530
  Node: PVirtualNode);
531
var
532
  regionInfo: PRegionInfo;
533
begin
534
  regionInfo := Sender.GetNodeData(Node);
535
  if regionInfo^.Areas <> nil then FreeAndNil(regionInfo^.Areas);
536
end;
537
538
procedure TfrmRegionControl.vstRegionsGetText(Sender: TBaseVirtualTree;
539
  Node: PVirtualNode; Column: TColumnIndex; TextType: TVSTTextType;
540
  var CellText: WideString);
541
var
542
  regionInfo: PRegionInfo;
543
begin
544
  regionInfo := Sender.GetNodeData(Node);
545
  CellText := regionInfo^.Name;
546
end;
547
548
function TfrmRegionControl.FindRegion(AName: string): PVirtualNode;
549
var
550
  regionInfo: PRegionInfo;
551
  found: Boolean;
552
begin
553
  found := False;
554
  Result := vstRegions.GetFirst;
555
  while (Result <> nil) and (not found) do
556
  begin
557
    regionInfo := vstRegions.GetNodeData(Result);
558
    if regionInfo^.Name = AName then
559
      found := True
560
    else
561
      Result := vstRegions.GetNext(Result);
562
  end;
563
end;
564
565
procedure TfrmRegionControl.OnModifyRegionPacket(ABuffer: TEnhancedMemoryStream);
566
var
567
  regionName: string;
568
  regionNode: PVirtualNode;
569
  regionInfo: PRegionInfo;
570
  areaCount: Byte;
571
  i: Integer;
572
  x1, y1, x2, y2: Word;
573
begin
574
  ABuffer.ReadByte; //status, not used yet
575
576
  //TODO : Ask user how to proceed, if the added/modified packet conflicts with the currently edited region
577
578
  regionName := ABuffer.ReadStringNull;
579
  regionNode := FindRegion(regionName);
580
  if regionNode = nil then
581
  begin
582
    regionNode := vstRegions.AddChild(nil);
583
    regionInfo := vstRegions.GetNodeData(regionNode);
584
    regionInfo^.Name := regionName;
585
    regionInfo^.Areas := TRectList.Create;
586
  end else
587
  begin
588
    regionInfo := vstRegions.GetNodeData(regionNode);
589
    regionInfo^.Areas.Clear;
590
  end;
591
592
  areaCount := ABuffer.ReadByte;
593
  for i := 0 to areaCount - 1 do
594
  begin
595
    x1 := ABuffer.ReadWord;
596
    y1 := ABuffer.ReadWord;
597
    x2 := ABuffer.ReadWord;
598
    y2 := ABuffer.ReadWord;
599
    regionInfo^.Areas.Add(x1, y1, x2, y2);
600
  end;
601
602
  if vstRegions.Selected[regionNode] then
603
  begin
604
    btnSave.Enabled := False;
605
    vstRegionsChange(vstRegions, regionNode);
606
  end;
607
end;
608
609
procedure TfrmRegionControl.OnDeleteRegionPacket(ABuffer: TEnhancedMemoryStream);
610
var
611
  regionName: string;
612
  regionNode: PVirtualNode;
613
begin
614
  ABuffer.ReadByte; //status, not used yet
615
  regionName := ABuffer.ReadStringNull;
616
  regionNode := FindRegion(regionName);
617
618
  //TODO : Ask user how to proceed, if the deleted packet conflicts with the currently edited region
619
620
  if regionNode <> nil then
621
    vstRegions.DeleteNode(regionNode);
622
end;
623
624
procedure TfrmRegionControl.OnListRegionsPacket(ABuffer: TEnhancedMemoryStream);
625
var
626
  regionCount, areaCount: Byte;
627
  i, j, x1, x2, y1, y2: Integer;
628
  node: PVirtualNode;
629
  regionInfo: PRegionInfo;
630
begin
631
  vstRegions.BeginUpdate;
632
  vstRegions.Clear;
633
  regionCount := ABuffer.ReadByte;
634
  for i := 0 to regionCount - 1 do
635
  begin
636
   node := vstRegions.AddChild(nil);
637
   regionInfo := vstRegions.GetNodeData(node);
638
   regionInfo^.Name := ABuffer.ReadStringNull;
639
   regionInfo^.Areas := TRectList.Create;
640
   areaCount := ABuffer.ReadByte;
641
   for j := 0 to areaCount - 1 do
642
   begin
643
     x1 := ABuffer.ReadWord;
644
     y1 := ABuffer.ReadWord;
645
     x2 := ABuffer.ReadWord;
646
     y2 := ABuffer.ReadWord;
647
     regionInfo^.Areas.Add(x1, y1, x2, y2);
648
   end;
649
  end;
650
  vstRegions.EndUpdate;
651
end;
652
653
initialization
654
  {$I UfrmRegionControl.lrs}
655
656
end.