Reputation: 1789
I have an app that runs in the system tray and when a user presses a combation of buttons it displays a WinForm to be filled out and sends an email. Everything works great but the part when the WinForm is displayed. It shows on top and the focus appears to be on the text box but the window is not active.
Code used to to call the Popup form.
My.Forms.frmpopup.ShowDialog()
Code on the Popup Form
Private Sub frmPopup_Shown(sender As Object, e As EventArgs) Handles Me.Shown
Activate()
BringToFront()
End Sub
Private Sub frmPopup_Load(sender As Object, e As EventArgs) Handles Me.Load
TextBoxName.Focus()
End Sub
The real kick in the pants is that this works as long as the user is not currently focused on an Internet Explorer Window. If I find a solution I'll post it.
It appears merging the two Subs into a single sub fixes the issue, I'll continue to test.
Private Sub frmPopup_Shown(sender As Object, e As EventArgs) Handles Me.Shown Activate() BringToFront() TextBoxName.Focus() End Sub
Upvotes: 1
Views: 2522
Reputation: 252
In my use-case* the following showed the desired result:
popup.Show();
popup.Activate();
where popup: Form
. Not sure why you have to call the Activate()
after the Show()
method, but that proved to be working correctly.
Use-case
My use-case was showing popup along with the loader form. Both the popup and the loader are top level forms and are triggered with the ShowDialog()
method. They are executed in separate threads with the idea that loader form is displayed while the popup form is fetching its data. Once the long operation (i.e. fetching) is completed, the loader form closes and the popup form is shown.
Everything was working as described, except that the popup was not focused after the loader closes.
The given two lines of code are solving my problem and now everything is working as expected.
Upvotes: 0
Reputation:
SendToTop(true)
should bring the window to TopMost.
Private Const SWP_NOSIZE As Integer = &H1
Private Const SWP_NOMOVE As Integer = &H2
Private Shared ReadOnly HWND_TOPMOST As New IntPtr(-1)
Private Shared ReadOnly HWND_NOTOPMOST As New IntPtr(-2)
Public Declare Function SetWindowPos Lib "user32" (ByVal hWnd As IntPtr, ByVal hWndInsertAfter As IntPtr, ByVal X As Integer, ByVal Y As Integer, ByVal cx As Integer, ByVal cy As Integer, ByVal uFlags As Integer) As Boolean
Public Sub SendToTop(toTop As Boolean)
If toTop Then
SetWindowPos(Me.Handle, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE Or SWP_NOSIZE)
Else
SetWindowPos(Me.Handle, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOSIZE Or SWP_NOMOVE)
End If
End Sub
Upvotes: 1
Reputation: 154
Make sure your application has focus as well...
Include the following import...
<Runtime.InteropServices.DllImport("user32.dll", SetLastError:=True, CharSet:=Runtime.InteropServices.CharSet.Auto)> _
Private Shared Function SetForegroundWindow(ByVal hWnd As IntPtr) As Long
End Function
And before you call the pop-up, or from within the pop-up LOAD event, call
SetForegroundWindow(Me.Handle)
Upvotes: 1