当帧上的事件发生时触发在窗体上触发的事件

时间:2013-06-21 19:52:23

标签: delphi

我有一个包含列表框的表单。该表单也是一个框架的父级,该框架包含一个滚动框,在该框架上绘制了面板。当用户从列表框中选择x个项目并单击面板时,面板会细分为x个较小的面板(例如,如果用户从列表框中选择3个项目,然后单击框架上的单个面板,则会划分本身分为3个较小的小组)。

我们为每个面板设置了一个限制,以确定可以为面板选择多少项目(例如,用户将限制设置为2然后选择3个项目并尝试单击面板,警告显示说你不能这样做)当警告显示时我想将项目返回到列表框,以便用户让他们选择(因为动作无法完成,因为不允许)。

我编写了这段代码来完成我想要的,问题是在事件发生时我没有这些对象(我尝试将父表单添加到Implementation uses子句并使用fmSeatingAssignments.UndoSelection调用它,但是很快发现我需要的对象实例超出了范围。)

procedure TfmSeatAssignments.UndoSelection;
Var
 I: Integer;
begin
 for I := 0 to FVehicleLayout.SelStudents.Count - 1 do
 begin
  ListBox1.Items.Add(FVehicleLayout.SelStudents[I]);
 end;
 For I := 0 to ListBox1.Count - 1 do
 begin
  ListBox1.Selected[I] := False;
 end;
 FVehicleLayout.SelStudents.Clear;
end; 

FVehicleLayout是框架并包含一个Stringlist,它接收所选项目(然后从列表框中删除)。我想在以下代码中的对话框关闭之后调用上述代码,该代码在框架上:

procedure TFrameVehicleLayout.ClickEvent(Sender: TObject);
var
 I,Row,Side: Integer;
begin
TooManyOstrichs := False;
If SelStudents.Count > 0 then
begin
 Side := -1;
 For I:=0 to High(Bus.BusSide) do
 begin
 If Bus.BusSide[I].LookupPanel(TPanel(Sender), Row) Then
 begin
  Side := I;
  break;
 end;
end;
If Side = 0 then
begin
 If SelStudents.Count > VehicleLayout.fDSSeats then
 begin
  vsiMessageDlg('The number of selected students exceeds the amount allowed ' +
               'per row for this bus side. Please try again.',
              mtWarning, [mbok], mbok, Self.Handle);

  //Call fmSeatAssignments.UndoSelection
  exit;
 end;
end;
if side <> -1 then
begin
  TRow(Bus.BusSide[Side].Rows[Row]).Occupants.Assign(SelStudents);
  TRow(Bus.BusSide[Side].Rows[Row]).FreePanels;
  TRow(Bus.BusSide[Side].Rows[Row]).BuildPanelArray;
  ShowLayout;
  SelStudents.Clear;
 end;
end;
end;

如何将SelStudents stringlist中的这些项目重新放回列表框中的任何帮助都将非常感激。如果其中任何一个令人困惑或不够清楚,请告诉我,我将制作演示程序并发布完整代码。提前感谢您提供的任何帮助。

1 个答案:

答案 0 :(得分:1)

您需要的唯一外部参考是列表框。您可以在框架上声明一个字段,并在创建框架时将其设置为表单的列表框,当然您需要使用此解决方案将UndoSelection方法移动到框架。

或者,如果您不想移动方法,则可以在框架上声明和发布事件,并在创建时为其分配父窗体的过程。可能看起来像这样:

type
  TFrameVehicleLayout = class(TFrame)
  private
    FOnUndoSelection: TNotifyEvent;
  public
    property OnUndoSelection: TNotifyEvent read FOnUndoSelection write FOnUndoSelection;
  end;

procedure TFrameVehicleLayout.ClickEvent(Sender: TObject);
..
begin
  ..
  if Assigned(OnUndoSelection) then
    OnUndoSelection(Self);
  ..

在表格中分配属性:

type
  TfmSeatAssignments = class(TForm)
    ..
  private
    procedure OnFrameUndoSelection(Sender: TObject);
  public
    ..


var
  F: TFrameVehicleLayout;
begin
  F := TFrameVehicleLayout.Create(Self);
  F.OnUndoSelection := OnFrameUndoSelection;
  ..


您还可以获取框架的父窗体(`GetParentForm¯)并迭代控件,直到找到列表框。或者可以将用户消息发布到它理解的表单。也可能有其他解决方案。

相关问题