How main WPF window knows when secondary WPF window is closed - c#

I faced a problem. I have two WPF windows in my project and I open the second WPF window by pressing the button on the main WPF window. But when I close the second window I need the first window to know that this happened and to do some action. How do I make this? I tried isLoaded and Application.Current.Windows, but both of them didn't work as I needed. Any ideas? Thank you in advance.

You can use like this.
public void CreateNewWindow()
{
Window wind=new Window();
wind.Closing+=yourClosingHandler;
}
void yourClosingHandler(object sender, CancelEventArgs e)
{
//do some staff
}

Related

Navigation between Pages and Windows in WPF

I have an issue that I am trying to resolve. I have two WPF windows. Those windows house the pages with content. My problem is not navigating page to page but rather window to window. here is an example of the code:
LoginPortal Design
<Grid>
<Frame x:Name="MainFrame" NavigationUIVisibility="Hidden"/>
</Grid>
LoginPortal Code
public LoginPortalMain()
{
InitializeComponent();
MainFrame.Navigate(new Uri("/Pages/LoginPortal.xaml", UriKind.RelativeOrAbsolute));
}
This is my Login portal that houses 4 buttons. Each button opens the second window which is houses several pages.
private void BtnSales_Click(object sender, RoutedEventArgs e)
{
var w = Application.Current.Windows[0];
w.Hide();
MainWindow mn = new MainWindow();
mn.Content = new SalesPage();
mn.Show();
}
When this button is clicked it opens the second WPF Window which is where several pages are housed. There is no problem with navigation. The problem starts when I wire the Closing event from the MainWindow to go back to the LoginPortalMain
private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
LoginPortalMain lgm = Application.Current.MainWindow as LoginPortalMain;
lgm.Show();
}
It then goes back to the start again. Now my problem is if I click on the same button again. It just duplicates everything. Then on closing anything it just adds new windows. If I then exit out of any window, it throws an error in picture below. My question is, is there a way to either dispose of the navigation once the MainWindow is closed. So there is no duplicate windows once you close the mainWindow a second time. I have used navigation before on a single window but not on multiple windows.
I may have to rethink this whole structure and use custom UserControls and figure out the animation sequence from Pages to UserControls. However, any help would be greatly appreciated.
enter image description here
enter image description here
enter image description here
enter image description here
enter image description here
If you only want to be able to open one instance of the new window try showing and hiding a single window instance.
When the open window button is pressed create the window if need and show it.
private OtherWindow mOtherWindow;
private void OpenWindowButtonClick(object sender, RoutedEventArgs e)
{
mOtherWindow ??= new OtherWindow(); //initialize child window on first call
mOtherWindow.Show();
}
When the other window is closed hide it and cancel the close request. You could also reset the other window state here for the next time it is shown.
private void OtherWindowClosingEvent(object sender, System.ComponentModel.CancelEventArgs e)
{
((Window)sender).Hide();
Application.Current.MainWindow.Activate();
e.Cancel = true;
}

Pushing window to foreground

i'm using a listview to display multiple items to the user. Now I want that the user has the ability to open an detail window with an double click. This works fine but when the window is opened it's immediatly pushed to the background.
I tried several things with the window state etc. the result was in every situation terrible(window is pushed to background or the window is a permanent overlay). The only solution that works relative well is that I change the DoubleClick Event in a MouseLeftButtonUp Event. When a user now click an item the window are in the foreground.
This is my code from the controller class:
public void ShowDetails(object details)
{
Details detailWindow = new Details(this, Config.GetCultureInformation());
detailWindow.LoadData(details);
detailWindow.Show();
}
This my code from the UI Class
private void listViewItem_MouseClick(object sender, MouseButtonEventArgs e)
{
ListViewItem item = sender as ListViewItem;
AppControl.ShowDetails(item.Content);
}
You should show it as modal.
public void ShowDetails(object details)
{
Details detailWindow = new Details(this, Config.GetCultureInformation());
detailWindow.LoadData(details);
detailWindow.ShowDialog(); //Instead of detailWindow.Show();
}
If you want to keep your main window without freeze use detailWindow.BringToFront() or detailWindow.TopMost = true, take a loot at this other post
Source here.
Ok. Thank you for your help and with Topmost I find I way to create a solution that suits for me.
In the constructor of my window I set topmost to true and in the Window is Loaded Event I set topmost to false. My Window is prominent in the foreground but the user can go out of it and can handle things in the main app.

How to close a form in UserControl

I created a UserControl with the buttons Save, Close and Cancel. I want to close the form without saving on the Cancel button, prompt a message to save on the Close button and Save without closing on the Save button. Normally, I would have used this.Close() on the Cancel button, but the UserControl doesn't have such an option. So I guess I have to set a property for that.
Scrolling down the "Questions that may already have your answer" section, I came across this question: How to close a ChildWindow from an UserControl button loaded inside it? I used the following C# code:
private void btnCancel_Click(object sender, EventArgs e)
{
ProjectInfo infoScreen = (ProjectInfo)this.Parent;
infoScreen.Close();
}
This does the job for one screen, but I wonder if I have to apply this code for all the screen I have? I think there should be a more efficient way. So my question is: Do I need to apply this code for every form I have, or is there another (more efficient) way?
you can use
((Form)this.TopLevelControl).Close();
you can use the FindForm method available for any control:
private void btnCancel_Click(object sender, EventArgs e)
{
Form tmp = this.FindForm();
tmp.Close();
tmp.Dispose();
}
Do not forget to Dispose the form to release resources.
Hope this helps.
You also can close one form in any part of the code using a remote thread:
MyNamespace.MyForm FormThread = (MyNamespace.MyForm)Application.OpenForms["MyForm"];
FormThread.Close();
I found the simple answer :) I all ready thought of something like that.
To close a WinForm in a ButtonClicked Event inside a UserControl use the following code:
private void btnCancel_Click(object sender, EventArgs e)
{
Form someForm = (Form)this.Parent;
someForm.Close();
}

ClickOnce and inactive main window

My application uses ClickOnce technology for deployment. However I have problem when user starts using the application. The scenario for reproducing the problem is as follows:
User clicks on application's shortcut in order to run the application
ClickOnce's "Launching application" dialog box appears in order to check for updates
"Launching application" dialog box disappears
Splashscreen appears
Main window (login window) appears - however it's not active nor has a focus
Because main window is not active, user has to click on it before he/she can start typing username and password. How can I resolve this problem so the main window is active after it appears? I've tried the following code but it's not working:
protected override void OnInitialized(EventArgs e)
{
while (!this.IsFocused) { this.Focus(); WPFWaitForPriority.WaitForPriority(DispatcherPriority.Background); }
base.OnInitialized(e);
}
Most likely you're giving focus to the splash screen. So when it closes nothing has focus any longer. After closing the form call the Select Method on the control you want to have focus(the username textbox i'm guessing).
Select for Focus
try this code:
Pseudo code:
OnShown
this.focus
I mean.
Use diffrent event.
I have a WPF / ClickOnce application and don't have the same problem. I don't use the StartupUri of App.xaml, I manually show the login window instead as follows in App.xaml.cs:
protected override void OnStartup(StartupEventArgs e)
{
this.DispatcherUnhandledException += new System.Windows.Threading.DispatcherUnhandledExceptionEventHandler(App_DispatcherUnhandledException);
this.Exit += new ExitEventHandler(App_Exit);
base.OnStartup(e);
ShowLogin();
}
private MainWindow _mainWindow;
private void ShowLogin()
{
_mainWindow = new MainWindow(delegate()
{
//.......
});
_mainWindow.Closed += new EventHandler(_mainWindow_Closed);
this.MainWindow = _mainWindow;
this.MainWindow.Show();
}
As per my understanding you can programatically trigger click event once inside constructor .
How about LoginForm.Activate() after the splash screen is closed and the LoginForm is displayed?
Maybe try to get focus on TextBox on that form. Login name for example.
I think OnInitialized event may be too early. OnShown should be good.
Are you using Visual Studio? I know if you go to the form properties under the project tab, you can specify the start up object. Perhaps you can specify your main form and the splashscreen can load in front of it.
have you tried:
protected override void OnInitialized(EventArgs e)
{
while (this.CanFocus) { this.Focus(); WPFWaitForPriority.WaitForPriority(DispatcherPriority.Background); }
base.OnInitialized(e);
}

How to open in(on) the current window?

I think my question is simple but i can not handle with it.
If i have window and a button on it and i want to open other window control on that window how can i do that?
I try do that through the VSM but I jam and still don't know how to do that. Maybe there is a simplier way?
Yes. Thank all of you for answers, but I think i didn't specify clearly what i wanted to get.
Methods: Show() and ShowDialog() opens new windows and i wanted to open controls in current window.
I think about something like that:
newWindowControl nwc = new newWindowControl();
LayoutRoot.Children.Add(nwc);
but in VSM.
I don't know if it is possible to do that.
If you want to open another window on top of existing window, just like a popup.. You can simply Initialize a new window and call its show method.
//Second window is of type Window
SecondWindow window = new SecondWindow();
window.Show();
private void button1_Click(object sender, EventArgs e)
{
using (Form2 form2 = new Form2())
{
form2.ShowDialog();
}
}

Categories

Resources