WPF - Bring application to front from system tray - wpf

I am using System.Windows.Forms.NotifyIcon to minimize my app to system tray. I wanted to bring back the application to front when user tries to open another instance of it.
The code from this site works fine if the first instance of app is hidden behind other apps, but not when minimized to system tray.
How can I implement this with WPF?

You Can acheive this by registering click event for the notify icon, you can
private void SetSystemTrayIcon()
{
System.Windows.Forms.NotifyIcon notifyIcon = new System.Windows.Forms.NotifyIcon
{
Icon = new System.Drawing.Icon(sri.Stream),
Visible = true
};
notifyIcon.Click += NotifyIcon_Click;
}
private void NotifyIcon_Click(object sender, EventArgs e)
{
var mainWindow = Application.Current.Windows[0];
mainWindow.Show();
}
I hope this can help you

Related

Wpf not all windows are maximized from taskbar

I have three windows. FirstWindow, SecondWindow and ThirdWindow. FirstWindow has button and click on this button opens the SecondWindow. Analogously, SecondWindow has button and click on this button opens the ThirdWindow. Owner property of the SecondWindow is set as FirstWindow and Owner property of the ThirdWindow is set as SecondWindow. The scenario discribing problem:
Open all windows in a row. It will be looked like this:
Then minimize all windows by click on corresponding icon at top right corner of ThirdWindow.
If you will try to maximize all windows by clicking on FirstLevelWindow or ThirdLevelWinow in taskbar - all will be ok, three windows will be maximized. But if you will click on SecondWindow you will see this:
How can I fix it, or it is just WPF bug? I can give archived expample project if it helps.
UPDATE
Minimize window - click "_" icon, left icon in iconbar of the window. All windows are modal, i.e it opens with ShowDialog() method, not with Show() method. So if you minimize third window - all the windows will be minimized.
Here the code if you don't want download project by link:
FirstWindow XAML:
<Button Click="OpenChildWindow"
Content="ChildWindow"/>
FirstWindow .cs:
private void OpenChildWindow(Object sender, RoutedEventArgs e)
{
var window = new SecondLevelWindow();
window.Owner = this;
window.ShowDialog();
}
SecondWindow XAML:
<Button Click="OpenChildWindow"
Content="ChildWindow"/>
SecondWindow .cs:
private void OpenChildWindow(Object sender, RoutedEventArgs e)
{
var window = new ThirdLevelWindow();
window.Owner = this;
window.ShowDialog();
}
ThirdWindow is empty window without any content.
Here link to example project
I've just found, that bug is not reproduced if property ResizeMode of ThirdWindow is set to "NoResize". Mb it will be usefull information.
Well, I admit I have no idea what is going on. Did you try to add a fourth window? This become even stranger: the second window bring back the third, but the fourth is still not back.
Anyway, If I had to manage this problem, I would keep a reference of my childWindow in each parent Window. This way on any interesting event (like activate on the second window in your example) I could manage the state of my child as required (WindowState.Normal in your case).
It could be something like that: in xaml of secondWindow:
Activated="SecondLevelWindow_OnActivated"
And then in code behind:
private ThirdLevelWindow _window;
public SecondLevelWindow()
{
InitializeComponent();
}
private void OpenChildWindow(Object sender, RoutedEventArgs e)
{
_window = new ThirdLevelWindow ();
_window.Owner = this;
_window.ShowDialog();
}
public void SecondLevelWindow_OnActivated(object sender, EventArgs e)
{
if (_window != null)
{
_window.WindowState = WindowState.Normal;
}
}
This is a start, but you could also inspect your current state to define the state of your child.
Hope it helps.

ALT-TAB always activates main window in WPF app with multiple owned windows

On Windows 7, .NET 4.0 I have a problem that can be reproduced by copying the following code into a blank WPF application generated by Visual Studio:
public MainWindow()
{
InitializeComponent();
Loaded += new RoutedEventHandler(MainWindow_Loaded);
}
void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
new Window() { Title = "Test", ShowInTaskbar = false, Owner = this }.Show();
}
Run app
Activate secondary window
Alt-Tab to other running application
Use mouse to activate our WPF app in taskbar
Now the WPF app is active again, with the secondary window activated and the main window deactivated, which is the expected (and desired) behavior.
Now do this instead (only step 4 differs):
Run app
Activate secondary window
Alt-Tab to other running application
Alt-Tab back to our WPF app
The WPF app is active again, but now the main window is activated.
Adding this code
private void Application_Activated(object sender, EventArgs e)
{
Windows[1].Activate();
}
to App.xaml.cs does not solve the problem because now in the second case both windows are activated. Also, clicking the secondary window does not deactivate the main window. I have to click the (already activated) main window and the secondary window again to achieve this.
How can I avoid this (only the secondary window should be active in both cases)?
CodeProject actually addresses this issue here, hope this is what you're looking for.
Combine with a post from Tamil Khason and in theory you can override the OnFocus event on a global level so that every time a window is on focus, that becomes the "main window" which will then be the target of ALT+TAB.
based on THIS solution the following code can maybe (not tested jet) also do the trick
protected override void OnStartup(StartupEventArgs e)
{
EventManager.RegisterClassHandler(typeof(Window), Window.LoadedEvent, new RoutedEventHandler(WindowLoaded));
base.OnStartup(e);
}
void WindowLoaded(object sender, RoutedEventArgs e)
{
Window w = sender as Window;
if (w != null)
{
// this part works in my case very well
w.Owner =Application.Current.Windows.OfType<Window>().SingleOrDefault(x => x.IsActive);
}
}

The best approach to show/hide windows indpendently

I am a student and am building a C# WPF application. It has three windows:
Sign in window
Create account window
and Main application window.
I uploaded a figure to show the type of navigation I am trying to implement:
I do not think it is correct to make a window show up/hide inside the close/load event of another window.
Can someone show me the right way to implement this navigation?
Also, is it a good practice to make the three windows private properties of the application class?
The last window has a frame control to support page navigation. Again, is it better to make the three pages private properties of MainWindow application?
I am sorry if this is so obvious or easy to do.
Thanks
I would not have the three windows as properties of the application. I'd instanciate a copy of the sign-in window and use that as my central point of control.
When the user logs in, hide the sign in window, show a new main window and add a hook on the main windows Closed event.
e.g
if (logonSuccess)
{
var mainWindow = new MainWindow();
mainWindow.Closed += ReshowSignupWindow;
}
I'd also have the sign-in window do the same for the create account window. Thus, I'd have the create account window return to the signup window which would either reshow itself or start the main window if an account was created.
e.g.:
// In sign-in window, handle the create window being closed
private void CreateWindowClosedHandler(object sender, EventArgs e)
{
if (accountCreatedOK)
{
ShowMainWindow();
}
else
{
ReshowSignupWindow();
}
}
I'd probably look at having the create account window shown as a dialog window via a call to ShowDialog().
Hope that helps...
Something like this code might do it (untested, I just typed it in visual studio to autoformat the code)
The XAML is for the Login Dialog. The RegistrationDialog should be similar, except for the button and handler for the registration Button.
<Window x:Class="WpfApplication1.LoginWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="LoginWindow">
<StackPanel>
<Button IsDefault="True" Content="Submit" Click="SubmitButton_Click"/>
<Button IsCancel="True" Content="Cancel" />
<Button Content="CreateAccount" Click="CreateAccountButton_Click"/>
</StackPanel>
</Window>
//Handler of LoginWindow and RegistrationWindow
private void SubmitButton_Click(object sender, RoutedEventArgs e)
{
this.DialogResult = true;
}
//Handler of LoginWindow only
private void CreateAccountButton_Click(object sender, RoutedEventArgs e)
{
this.IsCreatingAccount = true;
this.DialogResult = false;
}
public partial class App : Application
{
protected override void OnStartup(StartupEventArgs e)
{
bool isCanceled;
while (loginWin.ShowDialog() == false && !isCanceled)
{
if (loginWin.IsAccountCreationRequested)
{
if (registrationWin.ShowDialog())
{
isCanceled = true;
}
else
{
loginWin.IsAccountCreationRequested = false;
}
}
else
{
isCanceled = true;
}
}
if (loginWin.DialogResult) MainWindow.Show();
}
}
I am currently working on a Silverlight Application which is more or less similar to your application. What i feel is your can have 2 xaml controls(one for Login and other for your main application). For create account, you can use a child window which will be called from login control. And use a TabControl in your main application which will hold your other 3 xaml controls(Page1.xaml, Page2.xaml and Page3.xaml). Feel free to ask if you have any issues.
Dont forget to mark my reply as answer if it solves your problem.
I suggest you to follow the pattern. Your logic looks tightly binding with UI(user Interface) and logics.
The best pattern i like is for WPF or Silverlight is MVVM(Model View View Model). There are lot of Examples available in google for MVVM.
Just put a glance in anyone MVVM example you will be clear in developing WPF or Silverlight app.
some links are below,
http://msdn.microsoft.com/en-us/magazine/dd419663.aspx
http://www.c-sharpcorner.com/UploadFile/raj1979/simple-mvvm-pattern-in-wpf/
http://www.codeproject.com/Articles/126249/MVVM-Pattern-in-WPF-A-Simple-Tutorial-for-Absolute

How to display a splash screen using Caliburn Micro

I'm using Caliburn Micro v1.3 with WPF. I would like to display a splash screen while my app loads.
I have overriden OnStartup as below but can't see how to close my splash when the base.OnStartup complete
protected override void OnStartup(object sender, System.Windows.StartupEventArgs e)
{
var wm = new WindowManager();
var vm = new StatusReporterViewModel("TEST", "information", null);
try
{
wm.ShowWindow(vm);
base.OnStartup(sender, e);
}
finally
{
vm.TryClose();
}
}
Any ideas?
Cheers
Steve
If you want to use the default WPF splash mechanism then it requires no code.
Add an image file to your WPF .EXE project and then set the properties on the image to "SplashScreen"
If your Splash Screen is an actual customized Window, you can close the SplashScreen in the OnInitialize() Method of your ShellViewModel (or if you dont have a shell, the first view model that gets activated). To get a reference to the SplashScreen in your Shell either inject it or make it a singleton

Winforms - why does a "Show()" after a system tray double click end up in my app minimized?

Winforms - why does a "Show()" after a system tray double click end up in my app minimized?
How do I ensure Inthe notifyicon double click event that my hidden main form comes back visible as normal, not minimized (nor maximised for that matter too)
I would guess that you put your application in tray on minimize action. In that case, Show just restores visibility.
Try adding form.WindowState = Normal before Show().
Hiding your form with the NotifyIcon is often desirable so your app starts in the tray right away. You can prevent it from getting visible by overriding the SetVisibleCore() method. You also typically want to prevent it from closing when the user clicks the X button, override the OnFormClosing method to hide the form. You'll want a context menu to allow the user to really quit your app.
Add a NotifyIcon and a ContextMenuStrip to your form. Give the CMS the Show and Exit menu commands. Make the form code look like this:
public partial class Form1 : Form {
bool mAllowClose;
public Form1() {
InitializeComponent();
notifyIcon1.DoubleClick += notifyIcon1_DoubleClick;
notifyIcon1.ContextMenuStrip = contextMenuStrip1;
showToolStripMenuItem.Click += notifyIcon1_DoubleClick;
exitToolStripMenuItem.Click += (o, e) => { mAllowClose = true; Close(); };
}
protected override void SetVisibleCore(bool value) {
// Prevent form getting visible when started
// Beware that the Load event won't run until it becomes visible
if (!this.IsHandleCreated) {
this.CreateHandle();
value = false;
}
base.SetVisibleCore(value);
}
protected override void OnFormClosing(FormClosingEventArgs e) {
if (!this.mAllowClose) { // Just hide, unless the user used the ContextMenuStrip
e.Cancel = true;
this.Hide();
}
}
void notifyIcon1_DoubleClick(object sender, EventArgs e) {
this.WindowState = FormWindowState.Normal; // Just in case...
this.Show();
}
}

Resources