9

C# WPF アプリケーション

を使用して、起動時にSplashScreenを最小限の時間表示しています

Thread.Sleep(int); //int = milliseconds to display splash screen

そのスリープ時間に達すると、コードが再開され、SplashScreen がフェードアウトして閉じます。

SplashScreen.Close(Timespan.FromMilliseconds(int)); //int = milliseconds fade-out

この時点で一時停止して、SplashScreen が 100% 透明になり、完全に閉じられるまで待ってから、コンソールへの IE の書き込みまたは MainWindow の表示など、他のタスクを続行します。

(TimeSpan.FromMilliseconds(int)) が完了したときに発生するイベントはありますか? 他の提案はありますか?

namespace StartupSplash
{
    public class SplashScreenStartup
    {
        //IMPORTANT:set image property to Resource and NOT Splash Screen
        private SplashScreen Splash = new SplashScreen("Resources/SplashScreen.png");

        public void SplashScreenStartUp()
        {
            Splash.Show(false, true);
            Thread.Sleep(3000); // Pause code, display splash screen 3 seconds
            Splash.Close(TimeSpan.FromMilliseconds(3000)); // 3 second splash fade-out
            // I want to wait until splash screen fadeOut has completed before
            // this next console output is performed.
            Console.WriteLine("Executes before Splash fadeOut completes.");
        }

    }
4

5 に答える 5

3

たぶん、このコードはあなたを助けることができます. backgroundworker クラスの使用:

BackgroundWorker worker = new BackgroundWorker();
worker.DoWork += (o, ea) => 
{
   // Dispatcher.Invoke commands the dispatcher to do something
   Dispatcher.Invoke((Action)(() => Splash.Close(TimeSpan.FromMilliseconds(3000)));
   // Sleeps this worker but NOT the UI
   Thread.Sleep(3000);
};
worker.RunWorkerCompleted += (o, ea) =>
{
    // Open your mainwindow sample
    MainWindow w = new MainWindow();
    w.Show();
};

//Runs the worker on its own thread
worker.RunWorkerAsync();

これにより、スプラッシュスクリーンのクローズが開始され、スリープが終了すると、メインウィンドウが開きます。私は実際にこれに非常によく似たものを使用して、WPF アプリのログインとフェッチ情報を実装し、進行状況バーを表示し、その中のテキストを「サーバーへの接続」、「ログイン」、「データの取得」などに更新します。

于 2012-11-04T17:16:04.040 に答える
1

次のコードが機能することがわかりました。理由はよくわかりませんが、これをよりよく理解するために詳しく調べます。

必要に応じて批評してください。私は学び、共有するためにここにいます。乾杯。

class Tester
    {
    // Create splash screen instance and reference the image location.
    // IMPORTANT Ensure that the image properties are set to Resource and NOT Splash Screen
    private SplashScreen Splash = new SplashScreen("Resources/SplashScreen.png");

    public void Display()
    {
        Splash.Show(false, true);
        // pause the code, thus, displaying the splash for 3 seconds
        Thread.Sleep(3000); 
        // close the splash
        Close();
    }

    private void Close()
    {
        // sets the fadeout time in milliseconds
        int fadeOutTime = 1500; 

        // wait until the splash screen fadeOut has completed before writing to the console
        BackgroundWorker worker = new BackgroundWorker();
        worker.DoWork += (o, ea) =>
        {
            // Run background task (fade out and close the splash)
            Splash.Close(TimeSpan.FromMilliseconds(fadeOutTime));
            // Sleep this worker but NOT the UI (for the same time as the fade out time)
            Thread.Sleep(fadeOutTime);
        };
        worker.RunWorkerCompleted += (o, ea) =>
        {
            // Execute task after splash has closed completely
            Console.WriteLine("This is after the splash screen fadeOut completes.");
        };
        // start the background task, on it's own thread
        worker.RunWorkerAsync(); 
    }

}
于 2012-11-05T05:48:53.900 に答える
0

TimeSpanの完了時にリッスンするイベントは見つかりませんでした。また、スレッドを停止しないことを決定した後、代わりにDispatcherTimersを使用することにしました。

(参照用に、ロジックを間引いてこの1つのクラスに含めました)

using System;
using System.Windows;
using System.Windows.Threading;


namespace StartupSplash2
{

public partial class MainWindow : Window
{
    private DispatcherTimer visibleTimer;
    private DispatcherTimer fadeoutTimer;
    private SplashScreen splash;
    private int visibleTime = (4000); //milliseconds of splash visible time
    private int fadeoutTime = (1500); //milliseconds of splash fadeout time

    public MainWindow()
    {   
        //hide this MainWindow window until splash completes
        this.Visibility = Visibility.Hidden; 
        InitializeComponent();
        splashIn(); //start the splash
    }

    private void splashIn()
    {
        splash = new SplashScreen("Resources/SplashScreen.png"); //ensure image property is set to Resource and not screen saver
        visibleTimer = new DispatcherTimer(); //timer controlling how long splash is visible
        visibleTimer.Interval = TimeSpan.FromMilliseconds(visibleTime);
        visibleTimer.Tick += showTimer_Tick; //when timer time is reached, call 'showTimer_Tick" to begin fadeout
        splash.Show(false, true); //display splash
        visibleTimer.Start();
    }

    private void showTimer_Tick(object sender, EventArgs e)
    {
        visibleTimer.Stop();
        visibleTimer = null; //clear the unused timer
        fadeoutTimer = new DispatcherTimer();
        fadeoutTimer.Interval = TimeSpan.FromMilliseconds(fadeoutTime); //a timer that runs while splash fades out and controlls when main window is displayed
        fadeoutTimer.Tick += fadeTimer_Tick; //when fadeout timer is reached, call 'fadeTimer_Tick' to show main window
        splash.Close(TimeSpan.FromMilliseconds(fadeoutTime)); //begin splash fadeout to close
        fadeoutTimer.Start();
    }

    private void fadeTimer_Tick(object sender, EventArgs e)
    {
        fadeoutTimer.Stop();
        fadeoutTimer = null; //clear the unused timer
        splash = null; //clear the splash var
        MainWindowReady(); //call method to display main window
    }

    public void MainWindowReady()
    {
        this.Visibility = Visibility.Visible;
        //Here is the start of the Main Window Code
        this.Content = "Ok, the app is ready to roll";
    }

  }
}
于 2012-11-12T04:02:02.253 に答える
0

最終的に、以前のコメントで間違ったツリーを鳴らしていたという結論に達しました。バックグラウンドで SplashScreen を表示することは問題があり (何を試しても、自動的に閉じられませんでした)、不要です。これが私が最終的に得たものです... 本当に簡単です!

using System;
using System.Net;
using System.Windows;

namespace WpfApplication1
{
  /// <summary>
  /// Interaction logic for Window1.xaml
  /// </summary>
  public partial class Window1 : Window
  {
    public Window1() {
      InitializeComponent();
    }

    private void Window_Loaded(object sender, RoutedEventArgs e) {
      // show the splash screen
      // nb: Resources/SplashScreenImage.png file Properties ~ Build Action='Resource'
      var splashScreen = new SplashScreen("Resources/SplashScreenImage.png");
      splashScreen.Show(false); // don't close automatically
      // ... initialise my application ...
      Initialise();
      // close the splash screen.
      splashScreen.Close(TimeSpan.FromMilliseconds(250D));
    }

    private void Initialise() {
      // do my long-running application initialisation on the main thread. 
      // In reality you'd do this download asyncronously, but in this case
      // it serves as a simple proxy for some "heavy" inititalisation work.
      textBox1.Text = new WebClient().DownloadString("http://stackoverflow.com/questions/13213625/splashscreen-closetimespan-frommilliseconds-listen-for-closed-event");
    }
  }

}

それが役立つことを願っています...私はそれが役立つとはまったく確信していません;-)

乾杯。キース。

PS: スプラッシュが閉じないのはなぜですか? 私の推測では、WPF の event-dispatch-thread に相当するもの (名前が何であれ) でのみ利用可能な (つまり、サブスクライブ可能な) イベントに内部的に依存しています。

于 2012-11-05T08:06:55.177 に答える
0

SplashScreen の有効期限が切れた後にアプリを起動できるようにする SplashScreen.Dismissed というイベントを見つけました。ただ、最低限必要なOSがWindows8で、使えませんでした。詳細については、MSDNを参照してください。

于 2012-11-16T13:21:10.997 に答える