Frage

In einem Teil der Anwendung, an der ich arbeite, gibt es ein Formular-Steuerelement, das bedeutet eine Validierung der Empfang der CMExit Nachricht, das ist genau, wie Delphi Dokumentation sagt, es zu tun (in diesem Beispiel aus der Delphi-Hilfe-Dateien):

procedure TDBCalendar.CMExit(var Message: TWMNoParams);
begin
 try
  FDataLink.UpdateRecord;                          { tell data link to update database }
 except
  on Exception do SetFocus;                      { if it failed, don't let focus leave }
 end;
 inherited;
end;

Der Zweck dieses ist zu führen die Validierung, sobald das Steuerelement den Fokus verliert.So, zum Beispiel, wenn ich klicken Sie auf die Schaltfläche OK, die form, die Kontrolle, den Fokus verlieren, würde diese Methode ausführen und auf eine Ausnahme würde den Fokus wieder auf das Formular-Steuerelement.(So ist der "click" - Ereignis auf die Schaltfläche OK, würde nie gehen Sie durch und der dialog würde niemals in der Nähe).

Das problem, das ich habe, ist, dass diese form-control ist in einen modalen dialog-Fenster.Auf OK klicken, geschieht in der Tat senden Sie die CMExit Nachricht und bewirkt, dass der Datensatz zu aktualisieren (und die überprüfung stattfinden).Jedoch, drücken der Taste Enter während der Formular-Steuerelement bewirkt, dass das modale Dialogfeld zu schließen ohne das senden der CMExit Nachricht.Es ist, als ob die form-control "nie den Fokus verliert".Dies bedeutet, dass nicht nur der dialog schließen, ohne die form tatsächlich der Validierung der Daten, aber die Daten ist nicht aktualisiert, entweder.

Angesichts dieses problem, wo ist der beste Platz für mich, um meinen Datensatz zu aktualisieren/Validierung code?Ich konnte oben verschieben, um das Dialogfeld Formular selbst, und implementieren Sie es in das OnCloseQuery-handler, aber dies würde bedeuten, dass die Logik wird dupliziert, sowohl in der form-control und auf dem Formular selbst.(Das Formular-Steuerelement verwendet, in anderen Orten, und ich möchte, um zu vermeiden, ändern Ihr Verhalten).

(Ich spekulieren, dass CMExit nicht ausgelöst, da die Steuerung eigentlich nie tut den Fokus verlieren.Das Formular wird geschlossen, aber die form noch Kontrolle "hat den Fokus" auf das geschlossene form.)

War es hilfreich?

Lösung

Schließen Sie ein Formular muss nicht unbedingt Feuer, das auf dem exit-Ereignis eines TControl.Der Benutzer könnte dann drücken Sie Alt-F4, zum Beispiel.

Ich würde vorschlagen, bewegen die Validierung, um eine separate proc, und rufen Sie die separate proc sowohl aus den auf-Ausgang und on-close-Ereignisse.

Der folgende code sollte funktionieren, ohne zu viel änderung:

function TDBCalendar.UpdateSuccessful: boolean;
begin
  { tell data link to update database }
  { if successful, return True, else return False }
  { this function must be Public if a form is gonna check this value }
  Result := True;
  try
    FDataLink.UpdateRecord;
  except on Exception do
    Result := False;
  end;
  inherited;
end;

procedure TDBCalendar.CMExit(var Message: TWMNoParams);
begin
  //if not valid, then don't let them leave
  if not(UpdateSuccessful) then begin
    SetFocus;
  end;
end;

///////////////////////////////////////////
//on the form that contains your control...
///////////////////////////////////////////

procedure TMyForm.FormClose(Sender: TObject; var Action: TCloseAction);
begin
  //if not valid, then don't let them close the form
  if not(dbcal.ControlIsValid) then begin
    Action := caNone;
  end
  else begin
    inherited;
  end;
end;
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top