Jak w Delphi przejść z jednej formy ShowModal na drugą? Jak zamknąć Form.ShowModal z kodu tej formy?

0

Witam.
Temat wydawał się banalny dopóki go nie ruszyłem..

W skrócie:

  1. Są formy Główna i Form2, Form3, Form4.

  2. Chodzi o przejścia między formami Form2, Form3, Form4 wywoływanymi z ShowModal na zasadzie Buttonów Poprzedni, następny. A dokładniej jak zamknąć Form2 otwartej przez ShowModal z kodu Form2?

  3. Chodzi o to że Form2 była otwarta przez ShowModal, ma Button Następny po kliknięciu którego chciałem zamknąć Form2 i otworzyć Form3.ShowModal jak w poniższym przykładzie. I tak przechodzić pomiędzy formami.

var
  Form1: TForm1;

implementation
Uses
   Unit2,Unit3,Unit4;

{$R *.dfm}

procedure TForm1.Button_StartShowModalClick(Sender: TObject);
begin
   Form2.ShowModal;
end;
var
  Form2: TForm2;

implementation
Uses
   Unit3,Unit4;

{$R *.dfm}

procedure TForm2.Button_NastepnyClick(Sender: TObject);
begin
   Form2.Close;
   Form3.ShowModal;
end;
var
  Form3: TForm3;

implementation
Uses
   Unit2,Unit4;

{$R *.dfm}

procedure TForm3.Button_NastepnyClick(Sender: TObject);
begin
   Form3.Close;
   Form4.ShowModal;
end;

procedure TForm3.Button_PoprzedniClick(Sender: TObject);
begin
   Form3.Close;
   Form2.ShowModal;
end;
var
  Form4: TForm4;

implementation
Uses
   Unit2,Unit3;

{$R *.dfm}

procedure TForm4.Button_PoprzedniClick(Sender: TObject);
begin
   Form4.Close;
   Form3.ShowModal;
end;

To już tak obrazowo.

  1. Oczywiście w tej postaci Forma zamykana nie znika a pojawia się forma otwierana. Przez co potem nie można wrócić bo wyskakuje błąd, że nie można pokazać formy która już jest widoczna - to wiadomo.

  2. Jakby ktoś pytał o Form.Show to chciałbym tego właśnie uniknąć bo program ma być odporny na błędy a na formie głównej są ustawienia które wolałbym mieć niedostępne w momencie gdy się obsługuje Form2 - Form4. Dlatego aktywna ShowModal jest najwygodniejszym rozwiązaniem.

  3. Gdzieś po drodze były pomysły w stylu zmiana trybu ShowModal ale trzeba to jeszcze umieć przetrawić, wiec zaglądanie do kodu procki i testowanie pojedynczych linii w stylu

procedure TForm2.Button_NastepnyClick(Sender: TObject);
begin
   Exclude(Form2.FFormState, fsShowing);
   Form2.Close;
   Form3.ShowModal;
end;

nie pomaga

co ciekawe znalazłem coś takiego i też nic

procedure TForm2.Button_NastepnyClick(Sender: TObject);
begin
   Form2.CloseModal;         // zamiana kolejności też nie pomogła
   Form3.ShowModal;
end;

Co tu dużo pisać ... utknąłem.

poprawienie tagów wątku - furious programming

0
procedure TForm1.Button_StartShowModalClick(Sender: TObject);
begin
   Form2.ShowModal;
   Form3.ShowModal;
   Form4.ShowModal;
end;

A w formach 2-4 pod przyciskiem "Następny" dajesz po prostu Close;

0

Na obecne potrzeby przed pokazaniem form w

Form.Show; 

Panele z elementami ustawiłem na

Panel.Enable:= False;

a potem przywracam poprzedni stan.
Było by jednak dobrze na przyszłość znać sposób na zamykanie ShowModal. Żeby nie dać użytkownikowi możliwości przejścia na inną formę skoro ma działać tylko na tych konkretnych.

2

Jak już jesteś w formie modalnej to tylko ona może coś zrobić.
Czyli np wyświetlić kolejną formę modalną.
Zamknąć formę modalną można np tak: Form1.ModalResult:=mrCancel;

0

Niestety nie skutkuje:

procedure TForm2.Button_NastepnyClick(Sender: TObject);
begin
   Form2.ModalResult:=mrCancel;       // w odwrotnej kolejności też nie działa
   Form3.ShowModal;
end;

Pokazuje się Form3 a Form2 nie znika (jest pod Form3), przez co gdy jestem na Form3 i klikam "poprzedni" aby wejść na Form2, wyskakuje błąd że Form2 jest już widoczna i użytkownik jest "skazany" na bytność na Form3.

A właśnie chodzi o to żeby zamknąć Form2 z przycisku na Form2, żeby nie musieć się cofać do formy głównej.

0

Może chodzi o coś takiego, jak w działaniu kodu oraz exeka, które dołączyłem do tego posta?

0

Jak się tak temu przyjrzeć to też jest to sposób ale ja w Tej chwili mam formę główną oprogramowaną pod właśnie taki wygląd i właśnie takie wyskakujące Formy aktywne. I to muszę jakoś uratować.
@ czyli to samo tylko spróbuj nie z **Show ** a **ShowModal **.

Albo może Show + coś co ją utrzymuje w "charakterze ShowModal", żeby nie można było kliknąć innej formy z aplikacji poza ta formą aktywną.
Ale efekt miałby być taki jak pokazałeś.

0

Przed Form3.ShowModal możesz użyć Form2.Hide co zamaskuje formę pod trzecią. Możesz ją później przywrócić przez Show.
Co do innego podejścia, zamiast paneli możesz też posłużyć się ramkami (komponent Frames) będziesz mógł przynajmniej później łatwiej edytować poszczególne kroki wizarda zamiast przemieszczać panele i składać je ponownie.

0

Pokaż formy na TPanel + TPageControl i problem z głowy.
Pokazujesz wszystkie naraz, ale widoczna będzie tylko jedna.

http://www.tek-tips.com/viewthread.cfm?qid=1467433

3

A jak się upierasz aby kombinować z tymi modalnymi formami to masz procedurę za pomocą której wywołuj kolejne formy:

//1 parametr to forma która ma by zamknięta (jeżeli żadna to nil a zwykle to będzie Self)
//2 parametr to forma która ma by pokazana
procedure ShowModalForm(CloseForm, ShowForm: TForm);
type
  PFormState = ^TFormState;
var
  pFS: PFormState;
begin
  if Assigned(CloseForm) then
  begin
    CloseForm.Hide;
    CloseForm.ModalResult:= mrOK;
  end;
  if Assigned(ShowForm) then
  begin
    pFS:= @ShowForm.FormState; //ta właściwość jest tylko do odczytu a ona psuje imprezę to trzeba ją na siłę zmodyfikować
    Exclude(pFS^, fsModal); //usuwając niepotrzebnie pozostający fsModal z FormState bo nie można tego zrobić żadną dostępną metodą
    ShowForm.ShowModal;
  end;
end;
0

Właśnie o takie cudo chodziło. Dziękuję.

Edit.
Miałem jeszcze spytać o przeciwność tego ale od tego zdaje się Enabled jest.

1 użytkowników online, w tym zalogowanych: 0, gości: 1