当前位置: 首页 > 知识库问答 >
问题:

在无边界窗体上使用windows动画

丌官高远
2023-03-14

最近,我(主要出于好奇)制作了一个无边界表单。在制作了我自己的标题栏后,它包括标题和三个按钮(最小化、最大化和关闭),就像每个普通的Windows程序一样。我还为这些按钮编写了代码(只要问一下你是否想看到代码)。

但是,我注意到没有动画。我的意思是,例如,如果我单击最小化按钮,没有动画,程序立即消失(它不关闭,按钮工作,但没有动画)。这种情况在所有情况下都会发生:当我打开程序时,它会立即出现,当我关闭它时,它会立即消失。

是否有一些方法可以使用标准Windows程序使用的这些动画?

共有2个答案

宗晟
2023-03-14

我知道一年多前有人问过这个问题,但我也遇到了同样的问题,并找到了一个很好的解决方案。看看Github的回购协议
添加FormBase。cs和本机。cs到您的项目。

你要做的基本上是创建一个表单,即Main。cs并从FormBase派生

主要的cs

public Main()
{
        InitializeComponent();

        // Redraw gripper on resize
        this.SetStyle(ControlStyles.ResizeRedraw, true);
        // Ability to minimize/restore the form with animation
        this.FormBorderStyle = FormBorderStyle.Sizable;
}

// Draw the gripper on the bottom right corner
protected override void OnPaint(PaintEventArgs e)
{
        Rectangle rc = new Rectangle(this.ClientSize.Width - cGrip, this.ClientSize.Height - cGrip, cGrip, cGrip);
        ControlPaint.DrawSizeGrip(e.Graphics, this.BackColor, rc);
        rc = new Rectangle(0, 0, this.ClientSize.Width, cCaption);
        e.Graphics.FillRectangle(Brushes.DarkBlue, rc);
        SizeGripStyle = SizeGripStyle.Hide;
}

// Override WndProc to add resize ability -> Cursor
protected override void WndProc(ref Message m)
{
        if (m.Msg == 0x84)
        {  // Trap WM_NCHITTEST
            Point pos = new Point(m.LParam.ToInt32() & 0xffff, m.LParam.ToInt32() >> 16);
            pos = this.PointToClient(pos);
            if (pos.X >= this.ClientSize.Width - cGrip && pos.Y >= this.ClientSize.Height - cGrip)
            {
                m.Result = (IntPtr)17; // HTBOTTOMRIGHT
                return;
            }
        }
        base.WndProc(ref m);
}

我还删除了FormBase中的第147行。cs,因为我的表单具有圆形边缘(m.HWnd,0,0,pos.cx,pos.cy)

倪鹏
2023-03-14

似乎不可能在无边界形式上具有动画效果。然而,有两种可能的解决方法。

>

  • 在最小化或还原之前,将FormBorderStyle设置回Sizable,然后在固件后设置回none。

    改用AnimateWindow功能。动画往往发生在窗口当前所在的位置。这些功能可以应用于任何控件,而不仅仅是顶级窗口。

    以下是一些示例代码:

        class FormA : Form {
    
            private const int WM_SYSCOMMAND = 0x0112;
            private const int SC_MINIMIZE = 0xF020;
            private const int SC_RESTORE = 0xF120; 
            protected override void WndProc(ref Message m) {
                switch (m.Msg) {
                    case WM_SYSCOMMAND:
                        int command = m.WParam.ToInt32();
                        if (command == SC_RESTORE) {
                            this.FormBorderStyle = FormBorderStyle.Sizable;
                            this.ControlBox = true;
                        }
                    break;
                }
                base.WndProc(ref m);
            }
        }
    
    [DllImport("user32.dll")]
    static extern bool AnimateWindow(IntPtr hwnd, int dwTime, int dwFlags);
    
    private const int AW_VER_POSITIVE = 0x00000004;
    private const int AW_VER_NEGATIVE = 0x00000008;
    private const int AW_SLIDE =        0x00040000;
    private const int AW_HIDE = 0x00010000;
    
    
                [STAThread]
                static void Main() {
                    Application.EnableVisualStyles();
                    Form f = new FormA();
                    f.ControlBox = false;
                    f.FormBorderStyle = FormBorderStyle.None;
    
                    bool isMinimizing = false;
                    var mb = new Button { Text = "Min" };
                    mb.Click += delegate {
                        isMinimizing = true;
                        f.FormBorderStyle = FormBorderStyle.Sizable;
                        f.ControlBox = true;
                        f.WindowState = FormWindowState.Minimized;
                        f.FormBorderStyle = FormBorderStyle.None;
                        isMinimizing = false;
                        //AnimateWindow(f.Handle, 300, AW_SLIDE | AW_VER_POSITIVE | AW_HIDE);
    
                    };
                    f.SizeChanged += delegate {
                        if (isMinimizing)
                            return;
                        if (f.WindowState != FormWindowState.Minimized)
                            f.FormBorderStyle = FormBorderStyle.None;
                    };
    
                    f.Controls.Add(mb);
                    Application.Run(f);
            }
    

  •  类似资料:
    • 问题内容: 他们是否是使特定窗口在Linux上无边界的标准方法?我相信窗口边框是由您的窗口管理器绘制的,所以可能我只需要使用一个特定的窗口管理器(可以找到,我只需要知道哪个窗口管理器即可)…我希望是所有的窗口管理器都可能遵循一些标准,使我能够以编程方式执行此操作… 问题答案: 使用Xlib和old : 这些天NETWM / EWMH提示是首选,但据我所知,所有现代的窗口管理器还支持这一点。

    • 我正在制作一个在Windows上具有无边界窗口的应用程序。然而,由于窗口是无边界的,我没有areo阴影、捕捉、最小化动画或抖动。我环顾四周,没有找到解释如何实现这一点的网站。然而,我知道这是可能的,因为Office 2013、Visual Studio 2012和Steam都具有这些功能,并且没有边界。我专门使用QT和C,但如果您已经为另一个窗口库解决了这个问题,我也想听听您的解决方案。任何一个我

    • 问题内容: 两种方法中的哪一种符合W3C标准?它们在浏览器中的表现均符合预期吗? 边界:无; 边界:0; 问题答案: 两者均有效。 这是你的选择。 我喜欢,因为它更短。我觉得这更容易阅读。您可能会发现更清晰。我们生活在功能强大的CSS后处理器世界中,因此我建议您使用您喜欢的任何东西,然后通过“压缩机”运行它。这里没有值得战斗的圣战。 综上所述,如果您要手写所有的生产CSS,尽管评论中有些抱怨,但我

    • 我的EmployeeDB类 使用系统;使用System.Collections.Generic;使用System.LINQ;使用System.Text;使用System.Data.SQLClient;使用System.Data; 命名空间测试{公共类employeeedb{私有字符串连接字符串; 然后构建类库,并将引用添加到windows窗体项目中。

    • 我正在用JavaFX和场景构建器编程一个音乐播放器。我的问题是,如果我调整我的程序的窗口大小,UI不会随之增长。如何使UI具有响应性? 在我加了SplashScreen之前,它工作得很好。从那时起,我试图让它工作,但我不能找到任何解决方案在网上! 请帮帮我,提前谢谢! FXML: 飞溅FXML:

    • 求一个在windows上 可以自动关闭长时间不使用的窗体的软件, 如果可以 希望也说出一个linux平台的同作用的软件?