Solved

Component Properties read component#2

Posted on 2001-08-07
7
218 Views
Last Modified: 2010-04-06
Another question regarding properties.
I have a TControl property in my component, I place the component and a checkbutton on the form then assign then checkbutton to the control-property.

I then select the checkbox again and cut it using ctrl+x, bang I get a big error and have to close delphi. What can I do?
0
Comment
Question by:bnz
  • 3
  • 2
  • 2
7 Comments
 
LVL 21

Expert Comment

by:gemarti
ID: 6362159
Maybe you need to disassociate the checkbutton from your control when your app detects ctrl x.
how did you bind the two together? (...assign the checkbutton to the control-property...) Just undo what ever it is you did.

More information would be beneficial the the other experts and would probably get your problem solved quicker.
0
 

Author Comment

by:bnz
ID: 6362184
I just choose the checkbox in TControl property via Object Inspector.

I will post the code - it's a free component I'm working on. Hope it's not too big.

unit CheckGroupBox;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls;

type
  //Hack to read protected properties  
  TControlFake = class(TControl);
  TButtonControlFake = class(TButtonControl);  

  TEnabledEvent = procedure(Sender: TObject; Enabled: boolean) of object;

  TCheckGroupBox = class(TGroupBox)
  private
    OldCaption: string;
    FPositionCheckComponent: Boolean;
    FOnEnabled: TEnabledEvent;
    FCheckComponent: TControl;
    FOldCheckComponentOnClick: TNotifyEvent;
    procedure SetCaption(const Value: TCaption);
    procedure SetCheckComponent(const Value: TControl);
    procedure CheckComponentOnClick(Sender: TObject);
    function CheckComponentChecked: boolean;
    procedure SetPositionCheckComponent(const Value: Boolean);
    function ComponentToString(Component: TComponent): string;
  protected
    procedure SetEnabled(Value: Boolean); override;
    procedure Loaded; override;
  public
    constructor Create(AOwner: TComponent); override;
    procedure Update; override;
    procedure SetBounds(ALeft, ATop, AWidth, AHeight: Integer); override;    
  published
    property OnEnabled: TEnabledEvent read FOnEnabled write FOnEnabled;
    property Caption write SetCaption;
    property CheckComponent: TControl read FCheckComponent write SetCheckComponent;
    property PositionCheckComponent: Boolean read FPositionCheckComponent write SetPositionCheckComponent;
  end;

procedure Register;

implementation

{$R CheckGroupBox.Res}

procedure Register;
begin
  RegisterComponents('Samples', [TCheckGroupBox]);
end;

constructor TCheckGroupBox.Create(AOwner: TComponent);
begin
  inherited;

  PositionCheckComponent := True;
  OldCaption := Caption;  
end;

procedure TCheckGroupBox.Loaded;
begin
  inherited;

  Update;
end;

procedure TCheckGroupBox.Update;
begin
  inherited;
  Caption := Caption;
  Left := Left;
  Top := Top;
  PositionCheckComponent := FPositionCheckComponent;
  Enabled := Enabled and CheckComponentChecked;
end;

procedure TCheckGroupBox.SetCaption(const Value: TCaption);
begin
  if Value <> '' then
    OldCaption := Value;

  //if FCheckComponent <> nil clear groupbox caption
  if FCheckComponent <> nil then
      inherited Caption := ''
  else
      inherited Caption := OldCaption;
end;

procedure TCheckGroupBox.SetBounds(ALeft, ATop, AWidth, AHeight: Integer);
begin
  inherited;
  //Update CheckComponent position
  PositionCheckComponent := FPositionCheckComponent;
end;

procedure TCheckGroupBox.SetCheckComponent(const Value: TControl);
begin
width := width +5;
  if Value is TCheckGroupBox then
    raise Exception.Create('Assigned TCheckGroupBox to itself');

  FCheckComponent := Value;

  if FCheckComponent <> nil then
  begin
    FCheckComponent.FreeNotification(Self);
    FCheckComponent.BringToFront;
    //Saves old eventhandler
    if Assigned( TControlFake(FCheckComponent).OnClick ) then
        FOldCheckComponentOnClick := TControlFake(FCheckComponent).OnClick;

    TControlFake(FCheckComponent).OnClick := CheckComponentOnClick;
    Update;
  end;
end;

procedure TCheckGroupBox.SetPositionCheckComponent(const Value: Boolean);
begin
  //Align check component at groupbox
  FPositionCheckComponent := Value;
  if Value and (FCheckComponent <> nil) then
  begin
    FCheckComponent.Left := Left + 8;
    FCheckComponent.Top  := Top - 3;
  end;
end;

procedure TCheckGroupBox.SetEnabled(Value: Boolean);
var
  i: integer;
begin
  inherited;

  //Disable all controls
  for i := 0 to ControlCount-1 do
    Controls[i].Enabled := Value and CheckComponentChecked;

  if Assigned(OnEnabled) then
    FOnEnabled(Self, Value);
end;

function TCheckGroupBox.CheckComponentChecked: boolean;
var
  S: string;
begin
  if FCheckComponent is TButtonControl then
    Result := TButtonControlFake(FCheckComponent).Checked
  else if FCheckComponent <> nil then
  //Read the properties of the CheckComponent, it must have a property named Checked
  begin
     S := ComponentToString(FCheckComponent);
     Result := Pos('Checked = True', S) > 0;
  end
  else
     Result := True;
end;

function TCheckGroupBox.ComponentToString(Component: TComponent): string;
var
  StrStream: TStringStream;
begin
    StrStream := TStringStream.Create(Result);
    try
      StrStream.WriteComponent(Component);
      StrStream.Position := 0;
      ObjectBinaryToText(StrStream, StrStream);
      StrStream.Position := 0;
      Result := StrStream.DataString;
    finally
      StrStream.Free;
    end;
end;

procedure TCheckGroupBox.CheckComponentOnClick(Sender: TObject);
begin
  Enabled := CheckComponentChecked;
  //Call old event
  if Assigned(FOldCheckComponentOnClick) then
    FOldCheckComponentOnClick(Self);
end;

end.
0
 

Author Comment

by:bnz
ID: 6362187
the width:=width+5 is just to see when the SetCheckComponent is called, it doesn't get called when I cut the component away.
0
Industry Leaders: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 21

Expert Comment

by:gemarti
ID: 6362656
I cannot seem to duplicate your problem.

I compiled the code. I did make a change to the compiler directive. I removed {$R GroupCheckBox.Res}.

I tried putting a Checkbox on the control and then ctrl-x...no problem.

Then I tried a radio button...still no problem


When you used the wizard to create the new control did you select TControl (Controls) or TControls (QControls)..I'm not sure what difference it would make but I selected TControl (Controls). I did not try the QControls....
0
 
LVL 27

Expert Comment

by:kretzschmar
ID: 6362676
you should override the notification-method,
and set your property to nil there if your checkbox tells you there that it will be removed
(Action = opRemove)

meikl ;-)
0
 
LVL 27

Accepted Solution

by:
kretzschmar earned 100 total points
ID: 6362687
a sample

procedure TCheckGroupBox.Notification(AComponent: TComponent; Operation: TOperation);
begin
  If (AComponent = FCheckComponent) and (Operation = opRemove) then
    FCheckComponent := Nil;
end;



 
0
 

Author Comment

by:bnz
ID: 6363181
Yes, very nice... thanks
0

Featured Post

Industry Leaders: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

Question has a verified solution.

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

This article explains how to create forms/units independent of other forms/units object names in a delphi project. Have you ever created a form for user input in a Delphi project and then had the need to have that same form in a other Delphi proj…
In this tutorial I will show you how to use the Windows Speech API in Delphi. I will only cover basic functions such as text to speech and controlling the speed of the speech. SAPI Installation First you need to install the SAPI type library, th…

713 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