winforms icon indicating copy to clipboard operation
winforms copied to clipboard

form.ShowDialog(owner) with owner that is Topmost stays hidden behind the owner

Open fivage opened this issue 4 years ago • 12 comments

  • .NET Core Version: 5

  • Have you experienced this same bug with .NET Framework?: No, works correctly in 4.7.2

Problem description:

form.ShowDialog(owner) with owner that is Topmost stays hidden behind the owner.

Expected behavior:

It should be put in front of the owner

fivage avatar Nov 16 '21 14:11 fivage

Please provide a repro that shows the issue. Also an animation of the issue would help.

RussKie avatar Nov 17 '21 00:11 RussKie

This submission has been automatically marked as stale because it has been marked as requiring author feedback but has not had any activity for 14 days.

It will be closed if no further activity occurs within 7 days of this comment.

ghost avatar Dec 01 '21 01:12 ghost

WinFormsApp2.zip

public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            this.TopMost = true;
        }

        private void OpenPopupButton_Click(object sender, EventArgs e)
        {
            PopupForm popupForm = new();
            popupForm.ShowDialog(this);  // PopupForm should be in front of Form1, but is positioned behind Form1 
        }
    }

fivage avatar Dec 01 '21 08:12 fivage

A workaround seems to be to set TopMost = true in the child window if it detects that its parent has TopMost enabled.

hyperquantum avatar Feb 15 '22 14:02 hyperquantum

@hyperquantum that looks like a reasonable workaround. @Olina-Zhang can you help us figure out where this one changed? Was it working in 3.1 the same as it did in 4.7.2/4.8?

merriemcgaw avatar Feb 24 '22 23:02 merriemcgaw

@merriemcgaw verified this issue in .Net Core 3.1, it works well, and it repro in .Net 5.0/6.0/7.0.

Here is a gif in .Net Core 3.1 behavior: 3_1

Olina-Zhang avatar Mar 01 '22 09:03 Olina-Zhang

Related #9351

elachlan avatar Jul 17 '23 10:07 elachlan

Hello, We have encountered a similar behavior when using a derivative of MS CommonDialog. In this case, our Form has the TopMost property set to true. When CommonDialog is shown it will be placed under the Form. It can be reproduced using the following code:

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
        this.TopMost = true;
    }

    private void radButton1_Click_1(object sender, EventArgs e)
    {
        new MyCommonDialog().ShowDialog();
    }
}

public class MyCommonDialog : CommonDialog
{
    private Form myForm = new Form();

    public override void Reset()
    {
    }

    protected override bool RunDialog(IntPtr hwndOwner)
    {
        return ((Form)myForm).ShowDialog(NativeWindow.FromHandle(hwndOwner)) == DialogResult.OK;
    }
} 

This behavior is not observed in NetCore 3.1. It is reproducible in Net 5 and above. Dialog-TopMost

I am also attaching my test project.

Show_TopMost.zip

DinkoK avatar Aug 11 '23 08:08 DinkoK

same problem in .net 6

sgf avatar Jan 23 '24 09:01 sgf

Same problem in .NET 8.

Also, the workaround only works if TopMost = true is set on the child dialog after ShowDialog is called (e.g. inside the child form's Load event handler).

SteffenSchwaiger avatar Jan 24 '24 12:01 SteffenSchwaiger

Same problem in .NET 8.

Also, the workaround only works if TopMost = true is set on the child dialog after ShowDialog is called (e.g. inside the child form's Load event handler).

I came across this issue after upgrading to .NET 8 from Framework 4.8.

Setting the child form's TopMost after instantiating it but prior to calling ShowDialog() also works:

using var frmChild = new FrmChild();
frmChild.TopMost = TopMost;
frmChild.ShowDialog();

xv avatar May 15 '24 04:05 xv

We also migrated to .NET 9.0 from .NET Framework 4.8 and having same issue: https://jaex.getsharex.com/2025/06/q1Y7l3WOF73x.mp4

Even we set owner handle on ShowDialog method, still dialogs opening behind top most window. This was not the case with .NET Framework 4.8.

Jaex avatar Jun 22 '25 09:06 Jaex

My workaround:

public static DialogResult ShowDialogTopMost(this Form form, Form owner)
{
    if (owner != null && owner.TopMost)
    {
        form.TopMost = true;
    }

    return form.ShowDialog(owner);
}

Jaex avatar Jun 30 '25 04:06 Jaex