Delphi-PRAXiS
Seite 1 von 3  1 23      

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   GUI-Design mit VCL / FireMonkey / Common Controls (https://www.delphipraxis.net/18-gui-design-mit-vcl-firemonkey-common-controls/)
-   -   Delphi "Don't ask again" Messagedialog ? (https://www.delphipraxis.net/132114-dont-ask-again-messagedialog.html)

ralfiii 6. Apr 2009 13:37


"Don't ask again" Messagedialog ?
 
Hi!

Oftmals wär's ja praktisch dem Benutzer bei Warnungen/Bestätigungen die per MessageDlg erledigt werden eine "Never ask again" checkbox mitanzubieten.

Ein Standardproblem.

Bevor ich jetzt das Rad neu erfinde (bzw. programmiere): Gibt's für das Problem empfohlene Problemlösungen / fertige, halbwegs etablierte Komponenten?

Oder anders: Wo wird das Messagedialog-Fenster denn zusammengebaut? (Das ist ja meines wissens nach keine Kapselung sondern was Delphi-spezifisches, oder lieg' ich da falsch?)

Danke!
Ralf

DeddyH 6. Apr 2009 13:42

Re: "Don't ask again" Messagedialog ?
 
Ich hab da beim Zauberer etwas gefunden: http://www.dbrsoftware.de/delphi/nichtdlg.php

Luckie 6. Apr 2009 13:55

Re: "Don't ask again" Messagedialog ?
 
Meinst du sowas: http://www.michael-puff.de/Artikel/D...logAgain.shtml

gmc616 6. Apr 2009 13:56

Re: "Don't ask again" Messagedialog ?
 
Das Beispiel vom Zauberer funktioniert über die WinAPI und Registry.

Ich hatte mal das gleiche Problem, wollte aber ohne die Registry auskommen. Deshalb hab ich mir selbst etwas gebastelt.
Delphi-Quellcode:
function MyMsgBoxx (psText,psTitle : string; AShowAgainChecked : boolean = false; AIcon : Integer ) : boolean;
VAR
  AMsgDialog                 : TForm;
  ACheckBox                  : TCheckBox;
  AImg : TComponent;
  bShowAgain : boolean;
  btnOk : TControl;
  nHeigth : integer;
BEGIN
  bShowAgain := true;
  AMsgDialog := CreateMessageDialog(psText, mtWarning, [mbOk]);
  AMsgDialog.FormStyle := fsStayOnTop;
  AImg := AMsgDialog.FindComponent('Image');
  if AImg <> nil then
  begin
     // eigene Icon-Lade-Funktion
     TImage(AImg).Picture.Icon := GetIconByName(IntToStr(AIcon));
  end;

  btnOk := AMsgDialog.FindChildControl('OK');
  if btnOk <> nil then
  begin
    nHeigth := btnOk.top + btnOk.Height + 24;
  end else begin
    nHeigth := 169;
  end;

  ACheckBox := TCheckBox.Create(AMsgDialog);
  WITH AMsgDialog DO
  begin
    TRY
      Caption := psTitle;
      ClientHeight := nHeigth;
      WITH ACheckBox DO
      BEGIN
          Parent := AMsgDialog;
          Caption := 'Diesen Hinweis nicht mehr anzeigen.';
          width := 190;
          top := nHeigth - 20;
          Left := 8;
          Checked := AShowAgainChecked;
      END;

      ShowModal;

      bShowAgain := Not (ACheckBox.Checked);
    FINALLY
      ACheckBox.Free;
      Free;
    END;
  END;
  Result := bShowAgain;
end;
Das ganze ist zwar (noch) nicht der Stein des Weißen, aber für mich erfüllt es seine Zwecke.

DeddyH 6. Apr 2009 14:00

Re: "Don't ask again" Messagedialog ?
 
Registry aber nur dann, wenn Du den Dialog wieder anzeigen lassen möchtest, da Du ja dann den Wert löschen musst.

Jakob Ullmann 6. Apr 2009 15:15

Re: "Don't ask again" Messagedialog ?
 
Da finde ich das, was Luckie gepostet hat, aber kürzer. :wink:

ralfiii 6. Apr 2009 15:18

Re: "Don't ask again" Messagedialog ?
 
Zitat:

Zitat von Luckie

So ähnlich.
Tragischerweise ist die M$ MessageBoxCheck Implementierung ziemlich dämlich,
Man kann z.B: nur merken ob das Erscheinen eines Dialogs erwünscht ist, nicht aber das Ergebnis.

Eine typische Frage wäre ja:

"Wollen Sie das Programm wirklich beenden?" - OK, Cancel.
In dem Fall sollte sich der Dialog "OK" merken, Cancel nicht (sonst kann ich das Programm ja nie mehr beenden)

Oder, noch ausgefeilter: "Wollen sie vor dem beenden die Daten speichern?" (Ja, Nein, Abbrechen). Ja und nein sollte sich das Ding merken und beim nächsten Aufruf den selben Wert zurückgeben, bei Abbruch natürlich nicht.


...ich schätze das muss man noch was dazustricken.

mjustin 6. Apr 2009 15:57

Re: "Don't ask again" Messagedialog ?
 
Zitat:

Zitat von ralfiii
Oftmals wär's ja praktisch dem Benutzer bei Warnungen/Bestätigungen die per MessageDlg erledigt werden eine "Never ask again" checkbox mitanzubieten.

Ein Standardproblem.

Standardlösung gibt es in der JVCL - DSA-Dialoge

Cheers,

ralfiii 6. Apr 2009 16:00

Re: "Don't ask again" Messagedialog ?
 
Zitat:

Zitat von mjustin
Standardlösung gibt es in der JVCL - DSA-Dialoge
Cheers,

Uups.
Das kam leider zu spät.

Hier eine Lösung:

Delphi-Quellcode:
// MessageDialog with "Don't ask again" checkbox
// Based on code from [url]http://www.dbrsoftware.de/delphi/nichtdlg.php[/url]
// Discussion: [url]http://www.delphipraxis.net/post1023099.html[/url]
//
// ATT: Could return unexpected values if the list of possible results
//      was changed between versions and such an unexpected value was
//      stored in registry by an older version of the software
// Take standard window captions from Consts.pas, e.g. SMsgDlgConfirm
function DsaMessageDlg(h: THandle; Text, Caption, DsaDialogId: string;
  uType: Uint): integer;
var HL: THandle;
    Dlg: function(h: THandle; Txt, Title: PChar; dw: DWORD; nll: integer;
                  GStr: PChar): integer; stdcall;
    DSA : boolean;
const SxDsaBaseKey = '\Software\SpoonworX\DontShowAgain';
      MsDsaKey = '\Software\Microsoft\Windows\CurrentVersion\Explorer\DontShowMeThisDialogAgain';
begin
     with TRegIniFile.Create(SxDsaBaseKey, KEY_READ or Key_Write) do
     begin
          // by holding down CTRL -> unlock!
          if GetAsyncKeyState(VK_CONTROL) and $8000<>0 then
             DeleteKey('', DsaDialogId);

          // Check if a default result is already defined
          result:=ReadInteger('', DsaDialogId, -1);
          Free;
     end;

     // Show Messagedialog
     if result=-1 then
     begin
          // Maintain dialog is shown
          //   (clean old preferences - depends only from value in
          with TRegIniFile.Create(MsDsaKey, Key_Write) do
          begin
               DeleteKey('', DsaDialogId);
               Free;
          end;

          // Use standard "hidden" dialog with checkbox
          result := maxint;
          HL := LoadLibrary('shlwapi.dll');
          if HL <> 0 then begin
            @Dlg := GetProcAddress(HL, MAKEINTRESOURCE($B9));
            if Assigned(Dlg) then
              result := Dlg(h, PChar(Text), PChar(Caption),
                uType, 0, PChar(DsaDialogId));
            FreeLibrary(HL);
          end;

          // Determine if "don't show again" checkbox was visible
          with TRegIniFile.Create(MsDsaKey, KEY_READ or Key_Write) do
          begin
               DSA:=ValueExists(DsaDialogId);
               if DSA then
                  DeleteKey('', DsaDialogId);
               Free;
          end;

          // If DSA-checkbox was checked -> store defautl result of dialog
          if DSA and (result<>IDCANCEL) then
             with TRegIniFile.Create(SxDsaBaseKey, Key_Write) do
             begin
                  WriteInteger('', DsaDialogId, result);
                  Free;
             end;
     end;
end;

xZise 6. Apr 2009 17:00

Re: "Don't ask again" Messagedialog ?
 
Hallo,

und unter Windows Vista kann man sogar den TaskDialog nehmen.

MfG
xZise

PS: Cooler Artikel :thumb:


Alle Zeitangaben in WEZ +1. Es ist jetzt 09:50 Uhr.
Seite 1 von 3  1 23      

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz