简体   繁体   中英

Why Won't Form Get Focus?

I have a form that is launched modally like this:

private void find_street_Click(object sender, EventArgs e)
{
  this.WindowState = FormWindowState.Minimized;
  Form findForm = new FindStreet();
  findForm.ShowDialog();
  this.WindowState = FormWindowState.Normal;
}

The form launches correctly, and the cursor is in the first text box, whose TabIndex is set to 1.

Along with the InitializeComponent(); call, these commands are present.

public FindStreet()
{
  InitializeComponent();
  this.TopMost = true;
  this.BringToFront();
  this.Focus();
}

I have looked at and tried a number of examples. The cursor appears in the correct control, but the form's window does not have the focus. The problem is that if a user starts typing, even though the newly launched form is visible, those keystrokes are not going into the text box.

Remove the code in public FindStreet() and in load event of FindStreet add:

this.TopMost = true; //i don't know why you need this.
this.Activate();

When you minimize your main form the next one in z-order get the cursor. this.Focus() doesn't do anything. You need to Activate the dialog.

A dialog requires an owner, that cannot be a minimized window. Now accidents start to happen, starting with your WindowState assignment. Your app doesn't have a window left that can receive the focus so Windows is forced to find another one, that will be one owned by another application. Same problem happens when you close the dialog.

You can still get the intended effect, you must hide your main window after the dialog is displayed, show it again before the dialog closes. That requires a bit of hackorama:

    using (var dlg = FindStreet()) {
        // Show main window when dialog is closing
        dlg.FormClosing += new FormClosingEventHandler((s, cea) => {
            if (!cea.Cancel) this.Show();
        });
        // Hide main window after dialog is shown
        this.BeginInvoke(new Action(() => {
            this.Hide();
        }));
        dlg.StartPosition = FormStartPosition.Manual;
        dlg.Location = this.Location;
        if (dlg.ShowDialog() == System.Windows.Forms.DialogResult.OK) {
            // etc...
        }
    }

And remove the hacks from the FindStreet constructor. Watch out for event order if you have a FormClosing event handler in FindStreet, be sure to override OnFormClosing() instead.

If you want to set a specific control as the current active control then try this:

this.ActiveControl = myTextBox;

This will place the cursor you want as the main focus, when the form loads. So try this out:

public FindStreet()
{
  InitializeComponent();
  this.TopMost = true;
  this.BringToFront();
  this.Focus();
  this.ActiveControl = myTextBox;
}

Here is the link to Focus() which should explain why your focus call was not working.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM