You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C# Winform实现无闪烁启动:后台加载主窗体并显示闪屏

WinForms 启动闪烁与闪屏优化方案

问题分析

你用WindowsFormsApplicationBase的方案没达到预期,核心问题是:默认逻辑下主窗体的构造、加载仍在主线程执行,会阻塞闪屏的消息循环,而且主窗体首次绘制时因缺少双缓冲处理,依然会出现闪烁。要实现类似Photoshop的启动效果,必须做到闪屏在主线程保持响应,耗时初始化逻辑移到后台,主窗体准备完成后无闪烁显示。

实现步骤与代码

1. 闪屏窗体优化(MySplashScreen)

先确保闪屏自身无闪烁,设置以下属性:

public MySplashScreen()
{
    InitializeComponent();
    FormBorderStyle = FormBorderStyle.None;
    StartPosition = FormStartPosition.CenterScreen;
    ShowInTaskbar = false;
    DoubleBuffered = true;
    // 可选:设置置顶,避免被其他窗口遮挡
    TopMost = true;
}

2. 主程序入口改造(Program.cs)

将耗时初始化逻辑移到后台线程,主线程专注维护闪屏,待准备完成后再显示主窗体:

using System;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace MyApp;

internal static class Program
{
    [STAThread]
    private static void Main()
    {
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        Application.SetHighDpiMode(HighDpiMode.PerMonitorV2); // 适配高分屏,减少闪烁

        // 显示闪屏并强制刷新,避免空白
        var splashScreen = new MySplashScreen();
        splashScreen.Show();
        splashScreen.Refresh();

        // 后台执行耗时初始化(仅处理非UI逻辑:加载配置、预加载资源、初始化数据等)
        Task.Run(() =>
        {
            InitializeApplicationResources();
        }).ContinueWith(task =>
        {
            // 回到主线程创建主窗体
            var mainForm = new MyMainForm();
            // 给主窗体开启双缓冲,消除首次显示闪烁
            EnableDoubleBuffering(mainForm);

            // 关闭闪屏并释放资源
            splashScreen.Close();
            splashScreen.Dispose();

            // 启动主窗体消息循环
            Application.Run(mainForm);
        }, TaskScheduler.FromCurrentSynchronizationContext());

        // 维持闪屏的消息循环,直到主窗体准备完成
        while (splashScreen.Visible)
        {
            Application.DoEvents();
        }
    }

    /// <summary>
    /// 开启控件双缓冲,消除绘制闪烁
    /// </summary>
    private static void EnableDoubleBuffering(Control control)
    {
        if (!SystemInformation.TerminalServerSession)
        {
            control.SetStyle(
                ControlStyles.OptimizedDoubleBuffer |
                ControlStyles.AllPaintingInWmPaint |
                ControlStyles.UserPaint,
                true);
            control.UpdateStyles();
        }
    }

    /// <summary>
    /// 耗时初始化逻辑(替换为你的业务代码)
    /// </summary>
    private static void InitializeApplicationResources()
    {
        // 示例:模拟加载大型资源、初始化第三方组件等操作
        // 实际开发中替换为你的真实逻辑
        System.Threading.Thread.Sleep(2000);
    }
}

3. 主窗体优化(MyMainForm)

  • 构造函数仅做基础UI初始化,不要放耗时逻辑;
  • 在构造函数中调用EnableDoubleBuffering(this),确保自身无闪烁;
  • Load事件仅做轻量UI绑定操作,避免阻塞显示。

关键注意事项

  • 禁止在后台线程创建WinForms控件:所有UI控件必须在主线程实例化,后台线程仅处理数据、资源加载等非UI任务;
  • 双缓冲仅在非终端服务环境生效:代码中已通过SystemInformation.TerminalServerSession判断,避免兼容性问题;
  • 闪屏置顶设置:根据需求决定是否开启TopMost = true,确保启动过程中闪屏始终可见。

内容的提问来源于stack exchange,提问作者Johnny Wind

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 09:51:24