Opening another form in an MDI container - c#

Please refer to the diagram below:
I'm looking for the best way from one form to open another form. Once the menu form is open, I want to close the login form. I have tried to do this, but I got lost when I try to call it as a child of the MDI container.

The reason your main form isn't showing is because once you close the login form, your application's message pump is shut down, which causes the entire application to exit. The Windows message loop is tied to the login form because that's the one you have set as the startup form in your project properties. Look in your "Program.cs" file, and you'll see the responsible bit of code: Application.Run(new LoginForm()). Check out the documentation for that method here on MSDN, which explains this in greater detail.
The best solution is to move the code out of your login form into the "Program.cs" file. When your program first starts, you'll create and show the login form as a modal dialog (which runs on a separate message loop and blocks execution of the rest of your code until it closes). When the login dialog closes, you'll check its DialogResult property to see if the login was successful. If it was, you can start the main form using Application.Run (thus creating the main message loop); otherwise, you can exit the application without showing any form at all. Something like this:
static void Main()
{
LoginForm fLogin = new LoginForm();
if (fLogin.ShowDialog() == DialogResult.OK)
{
Application.Run(new MainForm());
}
else
{
Application.Exit();
}
}

if you develop WPF form, you can use 'http://wpfmdi.codeplex.com/'. or in Win Form you could play with form such that you want

try this
//global form
LoginForm login = new LoginForm();
public void menuOpen()
{
if(login.Visible)
login.Close();
}

Related

Closed form still showing in taskbar

Creating a multi-form program linked to a database with login features in c#.
Tried moving between forms using show(), showdialog() and close(), dispose(), hide().
Once past the login form, the program will not properly close the forms.
It closes the form so the user can no longer access its controls, however, the 'closed' form remains completely visible in the windows taskbar and tab menus.
The user can even hover over the taskbar icon for said 'closed' form and see all the information there!
As the program will be handling sensitive personal information. I need help to stop this problem from happening.
Code from a back button on secondary form aimed to completely close the active form and open the main form.
"Curform" is defined outside the method as it is used in multiple buttons within the program.
Form CurForm = Form.ActiveForm;
public void Btn_Back_Click()
{
var MainForm = new MainForm();
MainForm.Show();
CurForm.Close();
}
Use directly active form instead of curForm
Form.ActiveForm.Close();
If you want to use curForm in other parts of the code update curForm when you have created the new form, like this:
Form CurForm;
public void Btn_Back_Click()
{
CurForm= new MainForm();
CurForm.Show();
// Do some things
CurForm.Close();
}

C# unload and load form / hide and close

I am coding a simple sidescroller in C# using Windows Form Applications. I want it so when the player touches an exit point, this immediately loads a new level.
To implement this, I use the following code:
if (player.Bounds.IntersectsWith(exit.Bounds))
{
Form2 myNewForm = new Form2();
myNewForm.Visible = true;
this.Hide();
}
This works. However, it loads numerous instances of form2 - I only want it to load once. I don't know how to write this (sorry, I'm a newbie - it took me a while just to write this code!).
Also, loading a level via a new form is inefficient. Is there a way to unload the open form to load the next one in the same window/instance, rather than creating another separate window?
Sorry if this is unclear. I've done my best research + I'm new. Please don't mention XNA! Thanks.
You need a small modification to your project's Program.cs file to change the way your app decides to terminate. You simple exit when there no more windows left. Make it look like this:
static class Program {
[STAThread]
static void Main() {
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
var start = new Form1();
start.FormClosed += WindowClosed;
start.Show();
Application.Run();
}
static void WindowClosed(object sender, FormClosedEventArgs e) {
if (Application.OpenForms.Count == 0) Application.Exit();
else Application.OpenForms[0].FormClosed += WindowClosed;
}
}
Now it is simple:
if (player.Bounds.IntersectsWith(exit.Bounds))
{
new Form2().Show();
this.Close();
}
You can use Application.OpenForms[] collection to retrieve the Opened form instance and then Show it.
Try This:
Form2 frmMyForm = (Form2)Application.OpenForms["formName"];
frmMyForm.Show();
The actual problem is not in your form being loaded multiple times, but in your game logic not being suspended when the end of the level is reached. It means that your game keeps playing an old level when a new level is already loaded.
If Form1 is the main form then your whole application will shutdown. You need bootstraper which will be the entry point of your application, not the Form1. If you do that your Form1 will be a child in the same sense as will be Form2. You can open and close them without shutting down the application. If you don't know how to do that, just create another empty form, let's call it Main and make it the starting form of your application. Then hide it and open Form1 from Main form as Modal. Then when you complete level in Form1, close Form1, the code flow will return to Main form and you'll spawn Form2 from Main form as Modal. You'll have fully predictable logic, where all forms are opened from a single controlled place.

C# application exits when I dispose

Basically I have a Login window which should close once the user logs in and show another window, for now I've just hid it(Form.Hide()) however I do not wish to take unnescesary system resources and I don't need the login window after I already logged in.
this is the code snippet where I perform the operation:
MainWindow w = new MainWindow();
TimeRegisterApI.Instance.Windows.Add(w.Text,w);
TimeRegisterApI.Instance.Windows[w.Text].Show();
this.Dispose();
Windows is a dictionary that stores references of forms with their title as the key.
TimeRegisterApi is a singleton.
Basically what happens is that my application exits after I login instead of just disposing the login window, when I want it to dispose(close and go to the garbage collector.)
I know that having the title as key might cause duplicate key entries but in my current design it's no problem.
You have to make your window form login as a modal form which parent is your mainform
it will allow you to wait an answer (like a savedialog) and return to your main window form)
this is your main form so you exist
ok I fixed the problem, basically what happens is that when the window that is run from program.cs at application.run(window) gets disposed it closes the program because it's the main window, I think it would be possible to do an e.cancel on the dispose event of this window, however I solved the problem by running the window in a new application.run like this:
from program.cs, relevant lines
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new LoginWindow());
start();
}
public static void start()
{
if (TimeRegisterApI.isLoggedIn())
{
MainWindow w = new MainWindow();
Application.Run(w);
}
}

Login screen using user custom control

I have followed some advices I got here today and would need a bit more help now:
I have an user control with login logic.
In mainForm I am using this:
private void Form1_Load(object sender, EventArgs e)
{
LoginScreen login = new MainMenu();
login.Parent = this;
login.Dock = DockStyle.Fill;
login.Show();
}
But I guess it is not modal and thus does not stop the original Form application. Sure I would need the main Form to do not continue until the login form is closed (and login sucessfull).
Would using an event correct? Let login object to raise an event that login was successfull and let the MainForm handle it - run the app?
EDIT: This is user control, no ShowDialog method available.
Simply use ShowDialog() instead of Show().
Besides, ShowDialog() returns a DialogResult, so you can check if user doesn't press OK and close the form in that case:
if(form.ShowDialog() != DialogResult.OK)
{
this.Close();
}else
{
//if login it's ok continue with main form loading...
}
EDIT:
Given that it's a usercontrol:
Create a new form class and add the user control in it (e.g. using designer)
Instanciate it and call ShowDialog() in your FormLoad code (the code is similar to the one you posted, but you need to instanciate the login form instead of your usercontrol)
Instead of login.Show(); you might uselogin.ShowDialog(this);, making it a modal pop-up for the form.
If it's not derived from the Form class (which is odd), just create a windows form and put your control on it, then call ShowDialog method of the form. You'll have to wire closing of the form to the controls on your login screen somehow, though. If it fires some events it shouldn't be a problem.

How to close a form and open a new form up?

I am wondering how do I close a form after I open up a new form.
For instance I have a login form and when they login I open a new form up but I want to close the login form down.
So how would I do this?
I am making these forms on windows mobile 6 compact edition. Not sure if it would be different then in windows forms.
Could do it like this:
static class Program
{
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
if (DialogResult.OK == new LoginForm().ShowDialog())
{
Application.Run(new MainForm());
}
}
}
Should ensure the LoginForm closes with DialogResult.OK if valid credentials and with DialogResult.Cancel otherwise:
private void ValidateLogin(...)
{
... // check credentials
if(validCredentials)
{
this.DialogResult = DialogResult.OK;
this.Close();
}
else
{
... // up to you, maybe keep the form displayed to give user a chance to enter correct credentials
}
}
}
No need to hide anything.
If the main form is the Login window, you will only be able to hide it, since if you close it all other child windows will be closed too.
You have 2 options I guess:
1- Make your application's form, the main one. When the application starts, hide it and display the login window. When the login window is closed, show the main form.
2- Once the user enters his credentials in the login window, hide it (do not close it), and then open the other form. When the second one is closed, close both to shut the application down.
Most desktop apps implement login forms as modal dialogs. If you do the same thing, you would first display the main form, and then immediately display the login as a modal dialog, from the main form's form_loaded event. Once the login dialog has been closed, you can obtain login credentials from it and continue.
Just call Form.Close().
You will need to get an object for the login form that is open, or if you are in the login form when you want to close it, try calling this.Close()
I'm crazy, but I would suggest only using one form. Make the rest of your forms UserControls and just swap them in and out of the main form. Then you don't have to worry about any of this rubbish.
My Program.cs usually looks something like:
public class Program
{
static void Main()
{
MyApp application = new MyApp();
application.Initialise();
Application.Run(application.MainForm);
}
}
This way I can keep initialisation and logic outside of forms.

Categories