Newsgroup: it.comp.lang.delphi
Titolo: eventi personalizzati

senza ricorrere ai form bidirezionali, sto cercando di applicare
un evento personalizzato in modo che 2 form comunichino tra loro
L'evento viene intercettato alla pressioe di un Button su Form2,
il problema e' come identificare su ButtonPressed(Sender: TObject);
il Button cliccato , dal momento che Sender risulta vuoto Sender()
la verifica del tipo if Sender=btnChiudi non identifica alcun TButton
mi da un chiarimento ?
Maurizio
^^^^
Form1 - ha 1 Button
type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    procedure ButtonPressed(Sender: TObject);
....
procedure TForm1.Button1Click(Sender: TObject);
begin
  Button1.Enabled:=False;
  myForm:=TForm2.Create(Self);
  myForm.OnButtonPress := ButtonPressed;
  myForm.Show;
end;
procedure TForm1.ButtonPressed(Sender: TObject);
begin
  if Sender=btnChiudi then Button1.Enabled:=True;
end;
Form2 - ha 2 button uno e' chiamato btnChiudi
type
  TForm2 = class(TForm)
    btnChiudi: TButton;
    Button1: TButton;
    procedure btnChiudiClick(Sender: TObject);
    procedure FormClose(Sender: TObject; var Action: TCloseAction);
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    FOnButtonPress: TNotifyEvent;
  public
    { Public declarations }
    property OnButtonPress: TNotifyEvent read FOnButtonPress write 
FOnButtonPress;
  end;
procedure TForm2.btnChiudiClick(Sender: TObject);
begin
  if Assigned(FOnButtonPress) then
  begin
   FOnButtonPress(Self);
  end;
  close;
end;

 ha scritto nel messaggio 
news:473dd761$0$36440$4faf...@reader5.news.tin.it...



<cut>
Ti complichi inutilmente la vita, rendendo il tuo codice troppo legato
all'interfaccia utente, difficile da controllare, quasi impossibile da
modificare in seguito e non espandibile. Usa invece i messaggi di windows
per comunicare "eventi" tra form diverse.
Esempio:
Vuoi creare una form secondaria che permetta di visualizzare o nascondere
un bottone sulla form principale. Come fai?
1. ti crei due form: FormPrincipale (unit1) e FormSecondaria (unit2) e su
entrambe piazzi due TButton;
2. Nella unit principale crei un messaggio personalizzato (l'ideale sarebbe
averlo in una unit comune a tutte quelle che compongono il progetto):
// crei il tuo messaggio
WM_Controllo = wm_user+100;
3. Nella form principale rendi il Button2 non visibile, mentre nell'evento
onClick dei due bottoni fai:
procedure TFormPrincipale.Button1Click(Sender: TObject);
begin
 // il button1 visualizza la form secondaria
 unit2.FormSecondaria.Show
end;
procedure TFormPrincipale.Button2Click(Sender: TObject);
begin
 // il button2 chiude la form secondaria
 unit2.formsecondaria.Close
end;
4. A questo punto bisogna creare il gestore del messaggio (il fulcro
dell'applicazione);
dopo averlo dichiarato:
 private
    { Private declarations }
    procedure RiceviDaForm(var Message: TMessage); message WM_Controllo;
faccio in modo che, a seconda del parametro contenuto nel messaggio, lo
stato del Button2 si modifichi (nell'esempio, banalmente i valori sono 0 e
1):
procedure TFormPrincipale.RiceviDaForm(var Message: TMessage);
begin
 case Message.WParam of
  0 : begin
       // nascondo il button2
       Button2.Visible := False
      end;
  1 : begin
       // visualizzo il button2
       Button2.Visible := True
   end;
  end; // case
 end;
A questo punto la form Principale possiede un gestore che permette di
visualizzare/nascondere il button2 inviando semplicemente un messaggio con
il giusto valore nel parametro WParam.
5. Usiamo questo gestore: nella FomSecondaria, nell' onClick dei due
bottoni, mi limito ad inviare il messaggio ed il parametro che mi serve:
procedure TFormSecondaria.Button1Click(Sender: TObject);
begin
 // voglio visualizzare il button2 dulla FormPrincipale
 postmessage(unit1.formprincipale.Handle, WM_Controllo, 1, 0)
end;
procedure TFormSecondaria.Button2Click(Sender: TObject);
begin
 // voglio nascondere il button2 sulla FormPrincipale
 postmessage(unit1.formprincipale.Handle, WM_Controllo, 0, 0)
end;
Questo e' tutto, senza infognarsi con Sender, riferimenti incrociati, unit
interdipendenti, ecc...
Hai bisogno di espandere questo semplice "scheletro" di gestione? E'
semplice. Per esempio, mettiamo che ci sia un bottone della FormTerza (una
nuova form aggiunta in seguito) che deve modificare la caption della
formPrincipale.
Il gestore RiceviDaForm lo modifichi aggiungendo nel case .. of:
  2 : begin
       // modifico la caption
       Caption := 'Nuovo Titolo'
     end;
mentre il bottone della FormTerza si limitera' ad inviare il messaggio con 
il
parametro 2:
procedure TForm3.Button1Click(Sender: TObject);
begin
  // voglio cambiare la caption della FormPrincipale
 postmessage(unit1.formprincipale.Handle, WM_Controllo, 2, 0)
end;
E cosi' via ...
Ciao
ACSH
-- 
Il più grande sbaglio nel progettare software
a prova di stupido è sottostimare l'enorme
ingegnosità degli stupidi.

 [...]
il tuo suggerimento funziona, se metto il messaggio nella form principale
unit Unit3;
interface
uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;
const wm_Controllo=wm_user+100;
type
  TForm3 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    procedure RiceviDaForm(var Msg:TMessage); message wm_Controllo;
  public
    { Public declarations }
  end;
se invece metto il messaggio su una unit separata
unit Unit5;
interface
uses
  Windows, Messages, Classes;
implementation
const
  wm_controllo=wm_user+100;
end.
e modifico il form principale aggiungendo la unit che contiene il messaggio
(unit5), il compilatore segnala che nella procedure RicevidaForm ,
wm_Controllo non e' dichiarato.
unit Unit3;
interface
uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, unit5;
type
  TForm3 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    procedure RiceviDaForm(var Msg:TMessage); message wm_Controllo;
  public
    { Public declarations }
  end;
ciao Maurizio

"Maurizio"  ha scritto nel messaggio
[...]
spostando prima di implementation, viene accettata,
e funziona regolarmente.
unit Unit5;
interface
uses
  Windows, Messages, Classes;
const
  wm_controllo=wm_user+100;
implementation
noto pero' che in ogni caso le form si riferiscono a vicenda
form principale -> usa Form secondario e unit comune (Unit5)
il form secondario si autoriferisce a form principale nelle uses
usare i messagges , equivale comunque ad usare delle form bidirezionali.
Maurizio