Go Premium for a chance to win a PS4. Enter to Win

x
?
Solved

Creating Dynamic GUI at runtime.

Posted on 2004-04-26
7
Medium Priority
?
642 Views
Last Modified: 2010-04-05
OKay, in ma previous question, i learned how to read a custom script and execute it. (thx mokule).
My aim was to create Dynamic GUI at runtime. Like i press a button, it creates another button with name/caption etc.. and other controls/components.

i used the following code (mokule)
///TemplateForm: Array[1..300] of Tform2;
                                               //ignore the data n todata//
procedure TForm1.CollectGUIData(data,todata:string);
var
  str, PageName: string;
  bRead: boolean;
  f: TextFile;
  List:TStringList;
  i,TemplateID:integer;
begin
bRead := False;  // flag for reading
AssignFile(F,data);
Reset(F);
while not Eof(F) do
  begin
  Readln(F,str);
  if bRead then
    begin
    if Pos('@endnewpage',str) > 0 then // end of block found
      begin
      break;
      end
    else
      memo1.Lines.Add(str);
      TemplateForm[TemplateID]:= Tform2.Create(nil);
      for  i:=  0 to  memo1.Lines.Count -1 do begin
      if Pos('Label',memo1.Lines.Strings[i]) > 0 then
    Createlbl(11,13,'Caption','MyLabel1', TemplateForm[TemplateID]);
     
      end;


     TemplateForm[TemplateID].BorderStyle:=bsSizeable;
     TemplateForm[TemplateID].Align:= alNone;
     TemplateForm[TemplateID].Show;

    end
  else if Pos('@newpage',str) > 0 then // start of block found
    begin
// add counter here for not reading the first block but any other
    PageName:= split(str,'=',2);
    TemplateID:= strtoint(split(str,'=',3));
    bRead := True;
    end;
  end;
CloseFile(F);
end;
////////////////the txt file script
@newpage=My New Page Title=1
 Label 11 16 Caption MyName
 Label 12 22 MyCaption MyName2
@endnewpage=1
///////////////////////////////
the above code isolates the lines between @newpage and @endnewpage into a memo. and it reads all the lines beginning with Label.
Since 2 labels are in the script. it creats a form with 2 labels at their specified cordinates - Top/Left.

now the problem is here...
With every new control a new form is created. Like in One form Label of name = MyName is created and in another form Label with MyName and MyName2 is created.
To sum it up.. the no of controls is equal to the no. of forms created.  I want only one form with those 2 controls.

i found that when i simply create  a form with 3 controls. it works fine .. but when i read it from memo, like in the above code and use For := 0 to memo.lines.count - 1 it creates many forms.

sum help here is appreciated. I wouldnt mind any one putting up there createlbl(); code
0
Comment
Question by:sesycelina
7 Comments
 
LVL 17

Assisted Solution

by:mokule
mokule earned 60 total points
ID: 10916492
This should be not in loop reading file, but after reading (after CloseFile fx)

      TemplateForm[TemplateID]:= Tform2.Create(nil);
      for  i:=  0 to  memo1.Lines.Count -1 do begin
      if Pos('Label',memo1.Lines.Strings[i]) > 0 then
    Createlbl(11,13,'Caption','MyLabel1', TemplateForm[TemplateID]);
     
      end;


     TemplateForm[TemplateID].BorderStyle:=bsSizeable;
     TemplateForm[TemplateID].Align:= alNone;
     TemplateForm[TemplateID].Show;

0
 
LVL 3

Accepted Solution

by:
Kunfufaresi earned 90 total points
ID: 10916528
Hello,

I once created something like that in a file named form.dat you can paste this
E ; Name:          ; 120 ; 30 ;  30 ; 200
E ; Surname:       ; 120 ; 30 ;  70 ; 200
C ; City / State:  ; 120 ; 30 ; 110 ; 200 ; Istanbul,Ankara,Izmir,Edirne
X ; Do you agree?: ; 120 ; 30 ; 150 ; 200
 
and the formcreate is

procedure TForm1.FormCreate(Sender: TObject);
var
 t:TextFile;
 s:String;
 xEdit : TEdit;
 xLabel : TLabel;
 xButton : TButton;
 xCheckBox : TCheckBox;
 xComboBox : TComboBox;
 ts,ts2 : TStringList;

begin
 appdir:=extractfiledir(application.exename)+'\';

 if fileexists(appdir+'form.dat') then
 begin
  AssignFile(t,appdir+'form.dat');
  reset(t);
  ts := TStringList.Create;
  repeat
   readln(t,s);
   ts.clear;
   split(s,';',ts);

   if trim(ts[0])='E' then
   begin
    xLabel := TLabel.Create(form1);
    xLabel.Left        := strtoint(trim(ts[3]));
    xLabel.Top         := strtoint(trim(ts[4]));
    xLabel.AutoSize    := TRUE;
    xLabel.Height      := 21;
    xLabel.parent      := Form1;
    xLabel.Visible     := TRUE;
//   xLabel.Name        := s;
    xLabel.Caption     := trim(ts[1]);


    xEdit := TEdit.Create(form1);
    xEdit.Left        := xLabel.Left+ strtoint(trim(ts[2])) + 5;
    xEdit.Top         := xLabel.Top - 3;
    xEdit.Width       := strtoint(trim(ts[5]));
    xEdit.Height      := 21;
    xEdit.parent      := form1;
    xEdit.Visible     := TRUE;
//   xEdit.OnMouseDown := xMouseDown;
//   xEdit.OnMouseMove := xMouseMove;
//   xEdit.OnMouseUp   := xMouseUp;
//   xEdit.ReadOnly    := TRUE;
    xEdit.Enabled     := TRUE;
//   xEdit.Name        := s;
//   xEdit.Text        := s;
//   xEdit.Enabled     := FALSE;
   end;

   if trim(ts[0])='X' then
   begin
    xLabel := TLabel.Create(form1);
    xLabel.Left        := strtoint(trim(ts[3]));
    xLabel.Top         := strtoint(trim(ts[4]));
    xLabel.AutoSize    := TRUE;
    xLabel.Height      := 21;
    xLabel.parent      := Form1;
    xLabel.Visible     := TRUE;
//   xLabel.Name        := s;
    xLabel.Caption     := trim(ts[1]);


    xCheckBox := TCheckBox.Create(form1);
    xCheckBox.Left        := xLabel.Left+ strtoint(trim(ts[2])) + 5;
    xCheckBox.Top         := xLabel.Top - 3;
    xCheckBox.Width       := strtoint(trim(ts[5]));
    xCheckBox.Height      := 21;
    xCheckBox.parent      := form1;
    xCheckBox.Visible     := TRUE;
//   xCheckBox.OnMouseDown := xMouseDown;
//   xCheckBox.OnMouseMove := xMouseMove;
//   xCheckBox.OnMouseUp   := xMouseUp;
//   xCheckBox.ReadOnly    := TRUE;
    xCheckBox.Enabled     := TRUE;
//   xCheckBox.Name        := s;
//   xCheckBox.Text        := s;
//   xCheckBox.Enabled     := FALSE;
   end;

   if trim(ts[0])='C' then
   begin
    xLabel := TLabel.Create(form1);
    xLabel.Left        := strtoint(trim(ts[3]));
    xLabel.Top         := strtoint(trim(ts[4]));
    xLabel.AutoSize    := TRUE;
    xLabel.Height      := 21;
    xLabel.parent      := Form1;
    xLabel.Visible     := TRUE;
//   xLabel.Name        := s;
    xLabel.Caption     := trim(ts[1]);


    xComboBox := TComboBox.Create(form1);
    xComboBox.Left        := xLabel.Left+ strtoint(trim(ts[2])) + 5;
    xComboBox.Top         := xLabel.Top - 3;
    xComboBox.Width       := strtoint(trim(ts[5]));
    xComboBox.Height      := 21;
    xComboBox.parent      := form1;
    xComboBox.Visible     := TRUE;
    Split(trim(ts[6]),',',xComboBox.Items);
    xComboBox.Text := 'Please Select';
   
//   xComboBox.OnMouseDown := xMouseDown;
//   xComboBox.OnMouseMove := xMouseMove;
//   xComboBox.OnMouseUp   := xMouseUp;
//   xComboBox.ReadOnly    := TRUE;
    xComboBox.Enabled     := TRUE;
//   xComboBox.Name        := s;
//   xComboBox.Text        := s;
//   xComboBox.Enabled     := FALSE;
   end;

  until eof(t);
  closefile(t);
 end;
end;

All apeare on the same form because of

TComboBox.Create(form1);

Kunfu Faresi
0
 
LVL 3

Expert Comment

by:Kunfufaresi
ID: 10916547
ok and you would need split

procedure Split(aValue : string; aDelimiter : Char; Result : TStrings);
var
  X : Integer;
  S : string;
begin
  if Result = nil then Result := TStringList.Create;
  Result.Clear;
  S := '';
  for X:=1 to Length(aValue) do begin
    if aValue[X] <> aDelimiter then
      S:=S + aValue[X]
    else begin
      Result.Add(S);
      S := '';
    end;
  end;
  if S <> '' then Result.Add(S);
end;

Kunfu Faresi
0
Concerto Cloud for Software Providers & ISVs

Can Concerto Cloud Services help you focus on evolving your application offerings, while delivering the best cloud experience to your customers? From DevOps to revenue models and customer support, the answer is yes!

Learn how Concerto can help you.

 

Author Comment

by:sesycelina
ID: 10916726
hey thx. i got it now. Kunfu Faresi, i had most of that figured out. It was pretty foolish of me to place the code in da loop. mokula thx again...

Last question concerning this.
my TemplateForm is
TemplateForm : Array[0..300] of Tform2;

and i retrived the Template[ID] from the txt file.
How will i be able to figure out that Template[{ID}] has been already created. so that it would be created again.

Like TemplateForm[1]. it will be created on first call. In the second call, it should check to see whether 1=form is created or not. Is there any inbuilt system proc to check this.

or should i simply use TStringList and add the TemplateID and compare it when FormCreation is called?

thx
celina
0
 
LVL 17

Expert Comment

by:mokule
ID: 10916809
You can fill TemplateForm with nil and then check.
0
 
LVL 12

Expert Comment

by:Ivanov_G
ID: 10917127

  use ini file
   for example

  [Form1]
  Color=clBlue
  Left=200
 
  [Form1Label1]
  Caption=Test

  then

     uses IniFiles.... etc
0
 
LVL 3

Expert Comment

by:Kunfufaresi
ID: 10917464
hello

you can also

TemplateForm : Array[0..300] of Record
                                                 form:Tform2;
                                                 inuse:boolean;
                                               end;

then you could in the begining set all inuse to false and later turn it to true while creating them. but
if templateform[0]<>null then ... should work too i think

Kunfu Faresi
0

Featured Post

Free Tool: Path Explorer

An intuitive utility to help find the CSS path to UI elements on a webpage. These paths are used frequently in a variety of front-end development and QA automation tasks.

One of a set of tools we're offering as a way of saying thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
In my programming career I have only very rarely run into situations where operator overloading would be of any use in my work.  Normally those situations involved math with either overly large numbers (hundreds of thousands of digits or accuracy re…
this video summaries big data hadoop online training demo (http://onlineitguru.com/big-data-hadoop-online-training-placement.html) , and covers basics in big data hadoop .
Is your data getting by on basic protection measures? In today’s climate of debilitating malware and ransomware—like WannaCry—that may not be enough. You need to establish more than basics, like a recovery plan that protects both data and endpoints.…
Suggested Courses

886 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question