Solved

Activating an application and correctly setting the focus

Posted on 2007-11-14
4
2,539 Views
Last Modified: 2013-11-22
I've a series of applications which can be used concurrently. The user can switch between the applications without alt-tabbing, from within each application.

This works fine, but...

If application A switches to application B, and application B has a modal dialog open, it's the main form which is shown - not the modal dialog. The user then clicks on the main form and of course nothing happens other than a series of beeps. The user has to alt tab to bring the modal dialog into view and then close this to allow access to the application.

How can I achieve the same result as alt-tabbing? This is how I'm doing it at the moment...

     Result := FindWindow(Pchar(ThisWindowClass), nil);
     ShowWindow(Result, SW_RESTORE);
     ShowWindow(Result, SW_SHOWMAXIMIZED);
     SendMessage(Result, WM_ACTIVATEAPP, 1, 0);


Thanks for any help.


Steve
0
Comment
Question by:steve-west
  • 2
  • 2
4 Comments
 
LVL 21

Expert Comment

by:developmentguru
ID: 20283097
I found some code that does this, here is the link.  check out the section on how to steal focus.

http://www.codeproject.com/dialog/dlgboxtricks.asp?df=100&forumid=3124&exp=0&select=1718923

If you need me to provide a Delphi example, I will see what I can do.

Let me know.
0
 

Author Comment

by:steve-west
ID: 20287767
Thank you for this, but I don't see any topics within the link which are relevant.

There is a section which relates to setting the focus to a KNOWN modal dialog but this is not what I'm after.

Application A switches to application B.

Application B could have nth number of Modal dialog boxes opened on top of each other. The way I'm currently doing this results in only the main form of application B showing, but with the dialog boxes open, the application is effectively disabled.

I need to do exactly what Alt-tabbing does - i.e. show the topmost dialog. I could send a message to the application telling it to show the topmost dialog, but how do I do this (showing the window that is, not the messagey part).

Regards

Steve
0
 
LVL 21

Accepted Solution

by:
developmentguru earned 500 total points
ID: 20291463
I used code directly off the link in my example.  I created one program that just had a buton that brought up the modal file open dialog.  I called the form TLaunchDialog and the title was LaunchDialog.  I left it running.  In my second application I used the following code and it works as you stated you wanted it to.

procedure TForm2.Button1Click(Sender: TObject);
var
  WindowHandle : THandle;

begin
  WindowHandle := FindWindow('TLaunchDialog', 'LaunchDialog');

  if WindowHandle <> 0 then
    begin
      AttachThreadInput(GetWindowThreadProcessId(WindowHandle),
        GetCurrentThreadID(), true);

      SetForegroundWindow(WindowHandle);

      AttachThreadInput(GetWindowThreadProcessId(WindowHandle),
        GetCurrentThreadID(), false);
    end;
end;

Let me know if you need more.
0
 

Author Comment

by:steve-west
ID: 20297014
I agree, the solution you propose will return focus to an application with an open modal dialog.

The problem with this method, you have to know the class of the form you are bringing to the front. The applications that the user can switch between them hold over 3000 forms so it's not practical to code for each class type.

I've eventually managed to implement this successfully with the following approach.

1. Switch to application B from A by finding application's B main window and showing that.

2. Send application B a user defined message

3. When Application B receives this, it runs through the list of all open screens and for any screen which itself has an open screen, then bring the topmost screen to the front.


Since your solution does work, although not really suitable for my situation, I'll award the points.

Thanks fro your help

Steve







procedure TPRIAMCoreMainF.UMEnsureRestored(var Msg: TMessage);

var

  iCounter : integer;

  ComCounter: Integer;

  HasScreens : boolean;

begin

  //

  // Restore application

  if IsIconic(Application.Handle) then

    Application.Restore;

  if not Visible then

    Visible := True;

  Application.BringToFront;
 

  //

  // Ensure all TOPMOST modal screens are brought to the front

  for iCounter := 0 to Screen.FormCount - 1  do

  begin

    if Screen.Forms[iCounter].Visible and

      (Screen.Forms[iCounter].FormStyle = fsNormal) and

      //

      // ignore embedded forms

      (not (Screen.Forms[iCounter] is TPriamConnF))  then

    begin

        HasScreens := false;

        for ComCounter := 0 to Screen.Forms[iCounter].ComponentCount - 1 do

        begin

          if Screen.Forms[iCounter].Components[ComCounter] is TForm then

          begin

            HasScreens := true;

            TForm(Screen.Forms[iCounter].Components[ComCounter]).BringToFront;

            Break;

          end;

        end;

        if not HasScreens then

          Screen.Forms[iCounter].BringToFront;

    end;

  end;

end;

Open in new window

0

Featured Post

Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

Question has a verified solution.

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

Suggested Solutions

Introduction The parallel port is a very commonly known port, it was widely used to connect a printer to the PC, if you look at the back of your computer, for those who don't have newer computers, there will be a port with 25 pins and a small print…
Introduction I have seen many questions in this Delphi topic area where queries in threads are needed or suggested. I know bumped into a similar need. This article will address some of the concepts when dealing with a multithreaded delphi database…
This tutorial gives a high-level tour of the interface of Marketo (a marketing automation tool to help businesses track and engage prospective customers and drive them to purchase). You will see the main areas including Marketing Activities, Design …
Learn how to create flexible layouts using relative units in CSS.  New relative units added in CSS3 include vw(viewports width), vh(viewports height), vmin(minimum of viewports height and width), and vmax (maximum of viewports height and width).

911 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

Need Help in Real-Time?

Connect with top rated Experts

17 Experts available now in Live!

Get 1:1 Help Now