Link to home
Create AccountLog in
Avatar of pr2501
pr2501

asked on

How to add to my class new properties

Now with code below i can create as many TSahapes and TLabels as i want and move them around the form.

How can i give to itch tshape name as shape1, shape2.....

And see names as hint (when i put mouse on it) and also to change label text (caption) to shape1, shap2....

?
TMyObject=Class(TObject)
  private
   _Label:TLabel; // I use a _ convention instead of 'conventional' fXXX. I find it more readable
   _Shape:TShape;
   function GetLeft:Integer;
   function GetTop:Integer;
  public
   Constructor Create(aParent:TWinControl);
   Destructor Destroy; override;
   Procedure SetPosition(X,Y:Integer);
   property Labelmy:TLabel read _Label;
   property Shape:TShape read _Shape;
   property Left:Integer read GetLeft;
   property Top:Integer read GetTop;
  end;


procedure TForm1.object1Click(Sender: TObject);
begin
 CreateNewObject(self);
end;
procedure TForm1.CreateNewObject(Owner:TWinControl);
begin
 FSelectedObject := TMyObject.Create(Owner);
 FMyObjectList.Add(FSelectedObject);
end ;
Constructor TMyObject.Create(aParent:TWinControl);  //create
begin
 _Label:=TLabel.Create(aParent);
 With _Label do
  begin
   Parent:=aParent;
   Tag:=Integer(Self);
  Width := 10; // Shouldn't you use autosize ?
   Height := 10;
   Caption:='new';
  end; 
 _Shape:=TShape.Create(aParent);
 With _Shape do
  begin
   Parent:=aParent;
   Tag:=Integer(Self);
   hint:= inttostr(tag);
   Width := 10;
   Height := 10;
   Brush.Color := clwhite;
  onMouseDown := Form1.ShapeMouseDown;
   onMouseMove := Form1.ShapeMouseMove;
  //onMouseUp := Form2.ShapeMouseUp;
  end; 
 SetPosition(10,10);
end;

 procedure TForm1.ShapeMouseDown(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer);
 var
 i:integer;
 begin
 FSelectedObject := TMyObject(TShape(Sender).Tag);
 //edit1.text:= inttostr(TShape(Sender).Tag);
     //FSelectedObject._Shape.Name:='shape'+inttostr(i);
        //FSelectedObject._Shape.Hint:='1';
      //edit1.text:= FSelectedObject._Shape.Name;
     //  inc(i);
 if ssLeft in Shift then
  begin
   _Pos.X := FSelectedObject.Left-Mouse.CursorPos.X;
   _Pos.Y := FSelectedObject.Top-Mouse.CursorPos.Y;
  end;
end;

procedure TForm1.ShapeMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer);
begin
 // only dragging with left mouse button
 if not (ssLeft in Shift) then FSelectedObject := nil;
 if not Assigned(FSelectedObject) then Exit;
 // Don't use X & Y directly as they are relative to the object, which is moving
 FSelectedObject.SetPosition( _Pos.X + Mouse.CursorPos.X , _Pos.Y + Mouse.CursorPos.Y );
end;

Open in new window

Avatar of jimyX
jimyX

You can make a function that returns the number of the shapes on the form plus one and that can be assigned as a name when creating a new shape:

Function GetTShapeCount(): String;
var
  i, num : Integer;
begin
  num := 0;
  for i := 0 to Form1.ComponentCount-1 do  
    begin
      if Form1.Components[i] is TShape then
        inc(num);  
    end;
  result := 'Shape'+IntToStr(num+1);
end;

procedure TForm1.object1Click(Sender: TObject);
begin
 CreateNewObject(self);
end;

procedure TForm1.CreateNewObject(Owner:TWinControl);
begin
 FSelectedObject := TMyObject.Create(Owner);
 FMyObjectList.Add(FSelectedObject);
end ;

Constructor TMyObject.Create(aParent:TWinControl);  //create
begin
 _Label:=TLabel.Create(aParent);
 With _Label do
  begin
   Parent:=aParent;
   Tag:=Integer(Self);
   Width := 10; // Shouldn't you use autosize ?
   Height := 10;
   Caption:=GetTShapeCount(); <- It will be the new shape name // 'new';
  end; 
 _Shape:=TShape.Create(aParent);
  With _Shape do
    begin
      Parent:=aParent;
      Name := GetTShapeCount();  <-- Here it gives name by adding one to the last created shape
      Tag:=Integer(Self);
      hint:= inttostr(tag);
      Width := 10;
      Height := 10;
      Brush.Color := clwhite;
      onMouseDown := Form1.ShapeMouseDown;
      onMouseMove := Form1.ShapeMouseMove;
     //onMouseUp := Form2.ShapeMouseUp;
    end; 
  SetPosition(10,10);
end;

Open in new window

Avatar of pr2501

ASKER



Where i have to declare:

Function GetTShapeCount: String;
first thing:
your control (or it's children) will be displayed on a form > it should descend from TControl (and better from TWinControl)
next thing:
a: do you want your controls within a boundary,
     and do you want to set properties for that boundary > descend from something like TPanel
     and add components with the panel as owner
b: do you want your controls to be managed, and need mouse input, sizing, etc > descend your managing control
     from TControl or TWinControl, also adding others with owner this class

if you want a good sample > TLabeledEdit
there is a lot of source in examples in the $Delphi\Source\win32\vcl\ExtCtrls.pas
ASKER CERTIFIED SOLUTION
Avatar of Ephraim Wangoya
Ephraim Wangoya
Flag of United States of America image

Link to home
membership
Create an account to see this answer
Signing up is free. No credit card required.
Create Account
Hi ewangoya,

You are right if shapes will be deleted. According to my past experience with this project (I have participated in couple of questions of pr2501 about this same idea) I do not remember Deletion was implemented. Based on that I assumed all shapes are kept on the form, but anyway, you are right, still it was an assumption from my side.

BTW long time, where have you been? Enjoying Christmas?

Yeah, I took a few days off for Christmas
Hope you enjoyed yours too

Have a happy new year
Ya I did enjoy it.
Happy 2011 to you too.