向导型窗口切换问题! (200分)

  • 主题发起人 主题发起人 wuyaobin
  • 开始时间 开始时间
W

wuyaobin

Unregistered / Unconfirmed
GUEST, unregistred user!
我想利用窗口融合技术做一个向导型界面!
主窗口:有一个Panel,一个上一步按钮,一个下一步按钮。
融合到主窗口Panel中的子窗口:共有20个,Form1,Form2,Form3......Form20
按下一步按钮时由Form1切换到Form2(Form1释放,建立Form2并融合到Panel上),再按一次则切换到Form3,上一步按钮类似。

为了以后修改界面顺序或增加界面方便,我有一个想法:把所有窗口的有关“参数”放到一个记录数组中,以后只需修改这个记录数组即可改变向导次序或增减界面,而不用修改其它代码!

如:记录数组
type
TFormPoint=record//记录某个窗口的参数
FormClass:TFormClass;
Form:TForm
...
end;
var
FormOrder:array[0..19] of TFormPoint;//所有窗口

FormOrder[0].FormClass:=TForm1;
FormOrder[0].Form:=Form1;
...
...
...
初始化这个数组后,用ShowForm(FormClass:TFormClass;Form:TForm; Panel: TPanel);实现界面的切换。
上面的代码只是假设,我实现不了(建立的Form1窗口在主窗口上不能用Form1.Label1.Caption:='Test'访问,错了但不知怎样改)。
请各位富翁啦指正!或者你有更好的方法请告诉我。
 
向导一般是用NoteBook做比较好吧!


访问出错是因为该窗体尚未创建
 
用PageControl就ok了,记得把里面每个TabSheet的TabVisible属性改成False
 
最好的方法就是用PageControl+Frames来做,用PageControl向楼上说的那样来设,在跳转方面很方便,而用FRAMES可将不同界面的功能相对的独立出来,你参考一下吧
 
To andy263
我知道是因为该窗体尚未创建,如这样创建窗体就没有问题,
Form1:=TForm1.Create(Application);
...
不采用Notebook和PageControl,维护比较麻烦!
按照上面的思路如何实现?(只需修改一个记录数据即可,维护很方便)
 
你的思路是对的,在各个窗体之间传递变量或参数
可以用一个StringList来提供,

你用TFrame更好一些,
首先建立一个基类,具有一个接口,可以传入参数和传出返回值
然后,所有的窗口都从此类继承,

主窗口实现一个下面的过程
TMyFrmClass = class of TMyFrame;

function SwitchToFrm(ClassName: String; AParent: TControl): TMyFrame;
var
FrmClass: TMyFrmClass;
begin
FrmClass := TMyFrmClass(GetClass(ClassName));
if Assigned(FrmClass) then
begin
Result := FrmClass.Create(Self);
Result.Align = alClient;
Result.Parent := AParent;
.......
end;
.......
end;
 
向导窗口之间的的位置可以用 ini文件定义,
不必写死在程序中,各个窗体之间的参数传递也可以自动进行(统一处理)
 
to lich:
如果按你的思路实现,将是非常方便的!只需修改一个ini文件即可。
你是否有现成的例子?请Email过来:wuyaobin@21cn.com,多谢!

还有,在主窗体上有一时钟控件,要调用每个窗体的某个函数。
而且有些窗体会有分支,该怎么样实现呢?
 
到这里来吧
http://www.playicq.com/dispdocnew.php?id=13117
ftp://new:new1234567@61.129.70.192/datanew/200402191443316051.rar
 
利用了对象多态和继承,根据类的名字创建类等技术
以及字符串列表的使用
 
先谢了,试试先
 
程序中带的那个Forms主要改了些什么?我用的是D7,编译会出错,把它删除或改名后就没事了,请问有什么用?
原程序总是释放不了Frame1,把TMainFrm.FormCreate中的
CurrFrm := SwitchNext;
改为
SwitchNext;就可以了。
 
是我的Forms单元修改版playicq上面可以下载到d7的版本
只是一个修改版,和原来的基本上是兼容的,所以不用也没关系

你说的那个问题是因为 SwitchNext 中少了一行代码(粗心造成的)
忘记处理函数的返回值了,代码加在后面的那个位置
如下:
function TMainFrm.SwitchToFrm(FrmName: String; Panel: TWinControl): TMyFrame;
var
MyFrmClass: TMyFrmClass;
begin
// 下面的两种方法是等效的
//MyFrmClass := TMyFrmClass(GetClass(FrmName));
TPersistentClass(MyFrmClass) := GetClass(FrmName);

Result := nil;
// 此类必须被注册,而且从TMyFrame继承
if Assigned(MyFrmClass) and
MyFrmClass.InheritsFrom(TMyFrame) then
begin
Result := MyFrmClass.Create(Self);
Result.Parent := Panel;
end;
end;

function TMainFrm.SwitchNext(ToForward: Boolean): TMyFrame;
var
NewFrm: TMyFrame;
S, FrmNa: String;
NewStep: Integer;
begin
Result := nil;
if Assigned(CurrFrm) then
begin
mParams.Assign(CurrFrm.Params);
end;
if ToForward then
NewStep := CurrStep + 1
else
NewStep := CurrStep - 1;
if (NewStep >= 1) and (NewStep <= mSteps.Count) then
begin
if mParams.Values['nextstep'] <> '' then
S := mParams.Values['nextstep']
else
S := 'step' + IntToStr(NewStep);
mParams.Values['nextstep'] := '';
NewStep := mSteps.IndexOfName(S) + 1;
FrmNa := mSteps.Values;
NewFrm := SwitchToFrm(FrmNa, Panel1);
if not Assigned(NewFrm) then
begin
ShowMessage('未定义的Frame:' + FrmNa);
Exit;
end;
FreeAndNil(CurrFrm);
NewFrm.Params := mParams;
Result := NewFrm;
CurrFrm := NewFrm;
CurrFrm.Name := '';
CurrStep := NewStep;
end;
UpdateBtn;
end;
 
你可以通过修改配置文件随意设置窗口的顺序
也可以在窗口之间传递字符串参数

mSteps中的内容
和 mParams中的内容可以自己填写生成

做安装程序可就方便多了

不过mParams的效率太低,建议使用TStringHash 类
 
完成你这个功能我觉得用ABC组件中的TabcFormPanel控件比较方便
不过这个组件比较大,我自己裁减了一个,如果需要留个mail
 
接受答案了.
 
lich:还有一个问题,比如在MyFrame1中放一个按钮,让它直接切换到另一个窗口,会出现Abstract Error,请问有什么解决方法?
 
to yostgxf:
发一个过来 wuyaobin@21cn.com,先谢了!
 
发出了,请查收
 
to lich:
给了分就不理了?有你的联系方式吗?如Email什么的
 

Similar threads

S
回复
0
查看
3K
SUNSTONE的Delphi笔记
S
S
回复
0
查看
2K
SUNSTONE的Delphi笔记
S
D
回复
0
查看
2K
DelphiTeacher的专栏
D
D
回复
0
查看
1K
DelphiTeacher的专栏
D
D
回复
0
查看
1K
DelphiTeacher的专栏
D
后退
顶部