C# WPF 建立无边框(标题栏)的登录窗口

Posted 沐汐 vicky

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C# WPF 建立无边框(标题栏)的登录窗口相关的知识,希望对你有一定的参考价值。

前言:笔者最近用c#写WPF做了一个项目,此前未曾做过完整的WPF项目,算是一边学一边用,网上搜了不少资料,效率当然是不敢恭维的,有时会在一些很简单的问题上纠结很长时间,血与泪的教训可不少

不过,正如电视剧某榜里的一句话:既然我活了下来,就不会白白活着!笔者怎么也算挣扎过了,有些经验与教训可以分享,趁着记忆深刻总结写下来。希望后来者少走弯路,提高工作效率。如果有写得不好的地方,希望读者能够指正,一起进步!

---------------------------------

今天先从登录窗口说起:

1. 效果图

先来看看效果图,简洁,风格统一,完全不会被Window操作系统主题的影响。

技术分享

2. 实现方法

WPF做这样的窗口非常简单,只有需在窗口设计中设置两个属性,一个是AllowsTransparency, 设置为 Ture;  一个是 WindowStyle, 设置为 None。

技术分享

注:是Window的属性,不要选中其他的控件。

另外,如果AllowsTransparency="True",那么 WindowStyle只能为 None, VS2015 已经做到连动设置,只要勾选AllowsTransparency,后一个也跟着变了。但 VS2008 还是需要用户分别设置,不然会报错。

还有一个问题不得不提,AllowsTransparency="True" 之后就无法使用 WindowsFormsHost控件了,因为就算用了,WFH里的任何控件也是透明无法显示出来的,比如ReportViewer!

3.窗口任意空白地方实现鼠标拖拽

标题栏上有最大化最小化和关闭的按钮,其中在登录窗口我们一般是不会使用最大化按钮的。可是不得不说,标题栏还有一个很实用的作用,就是可以拖拽整个窗口,用户只要单击标题栏不放,就可以拖到桌面的任何地方。如今把标题栏隐藏之后,该如何弥补呢?

为窗口添加一个 MouseLeftButtonDown 的事件,代码如下:

        private void Window_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
        {
            try
            {
                this.DragMove();
            }
            catch { }
        }

这样就OK了!

注:网上有些示例里,没有用 try{}catch{},而只有一行代码

this.DragMove();

如果在登录窗口,只有那么几个控件和事件的话,应该也是无大碍的。

在这里笔者有个小小的经验必须分享一下:

由于在主界面里也使用了这种无标题栏的窗口,鼠标在Gridview上操作时,经常会引发异常崩溃。

所以笔者认为最好加 try...catch... 避免异常,哪怕是登录窗口也不例外。

4. 输入密码后按回车登录

很多网站会注意这种情况,输入密码后回车,系统就可以登录,这就是良好的用户体验。(当然,也有些网站不注意用户体验,用户必须用鼠标去点击登录的)

其实在密码框添加一个 KeyDown 事件就可以

        private void txt_Pwd_KeyDown(object sender, KeyEventArgs e)
        {
            switch (e.Key)
            {
                case Key.Enter:
                    btn_login_Click(btn_login, null);
                    break;

                default:
                    break;
            }
        }    

So easy !

5. 按Enter(回车)跳到下一控件

提到回车登录,顺便提一下,有些人不喜欢输入用户名后,又要用鼠标移到密码框,又键盘又鼠标,比如笔者。

事实上 Tab键 可以让用户在比较简单的界面摆脱鼠标,不过要注意在窗口设计时调好控件的 TabIndex 顺序。

当然在此基础上也可以加一个 Enter 设置的功能,只要在后台代码重写窗口的 OnKeyDown 事件,如下:

        //按下回车后跳入下一个控件
        protected override void OnKeyDown(KeyEventArgs e)
        {
            if (e.Key == Key.Enter)
            {
                // MoveFocus takes a TraveralReqest as its argument.
                TraversalRequest request = new TraversalRequest(FocusNavigationDirection.Next);

                // Gets the element with keyboard focus.
                UIElement elementWithFocus = Keyboard.FocusedElement as UIElement;

                // Change keyboard focus.
                if (elementWithFocus != null)
                {
                    elementWithFocus.MoveFocus(request);
                }
                e.Handled = true;
            }
            base.OnKeyDown(e);
        }

6. 运行时打开登录窗口

登录窗口毕竟不是主窗口,登录后要关闭的,所以Startup的路径不是登录窗口,但登录的时候是不能打开主窗口的,如果用户关闭登录窗口,退出程序。

实现方法:

项目下有一个App.xaml文件,Startup 指向主窗口的路径,然后打开后台代码 App.xaml.cs,重写OnStartup事件,判断一下登录窗口的 DialogResult 如果返回ture,就正常打开主窗口,如果为 false,则关闭整个程序。代码:

        //打开登录窗口,成功后进入主窗口
        protected override void OnStartup(StartupEventArgs e)
        {
            try
            {
                OneInstanceOnly();//仅运行一个实例
//#if !DEBUG
                // 运行登录窗口
                Application.Current.ShutdownMode = System.Windows.ShutdownMode.OnExplicitShutdown;
                LoginWindow window = new LoginWindow();
                bool? dialogResult = window.ShowDialog();
                if (Utils.IsTrue(dialogResult))
                {
                    base.OnStartup(e);
                    Application.Current.ShutdownMode = ShutdownMode.OnMainWindowClose;
                }
                else
                {
                    this.Shutdown();
                }
//#endif
            }
            catch (Exception ex)
            {
                UIUtils.ShowException(ex);
            }
        }

留意 ShutdownMode 的变化

 

以上是关于C# WPF 建立无边框(标题栏)的登录窗口的主要内容,如果未能解决你的问题,请参考以下文章

在WPF中,当在无边框窗口中拖动自定义的标题栏时,窗口会恢复,如何实现呢?

如何在文件后面没有代码的情况下移动无边框 wpf 窗口

VB如何用CreateWindowEx 创建无标题栏无边框窗体?

VC MFC中如何制作无边框窗口

【WPF】自定义标题栏

C# winform怎么样把窗口设置成两边和下面无边框,求沟通。。。