簡體   English   中英

單獨的UI線程上的WPF控件?

[英]WPF Control On Separate UI Thread?

我正在制作一個媒體播放器,現在..我添加了一個實時搜索功能來搜索歌曲等等(有些東西,如WMP實時搜索),即當你輸入關鍵字時,搜索就會發生。

在搜索過程中,訪問數據庫並加載IEnumerable是通過BackGroundProcess在另一個線程上完成的。 通過調用UIElement的調度程序來更新UI。

這個過程相當快,但是當您在文本框中輸入搜索關鍵字時,似乎存在一個小的延遲,這是因為Listbox.ItemSource更新需要一些時間。 也就是說你要搜索“Adele”,當你輸入“a”時,搜索功能會加載“A”的結果,但是當我們輸入整個單詞“Adele”時,它有時間顯示“d” “”e“”“l”“e”並且這些字母之間存在輕微的滯后。

在這個搜索過程中,當我停止更新UI時,搜索過程看起來非常流暢,這只對我意味着Listbox鎖定線程,因此當Listbox完成其處理時,播放器的UI的其余部分被卡在那里。

因此,我相信如果我可以將Listbox Control放到另一個UI線程中,無論加載列表框所花費的時間如何,我都可以保持播放器的流暢。 僅供參考:數據虛擬化就在那里,ListBox的UI虛擬化正在運行

如何將ListBox控件放到另一個UI線程上? WPF,C#

提前致謝 :)

如果您在每個按鍵上查詢數據庫 - 這會導致您在快速鍵入(甚至正常)時出現延遲

你最好限制請求,我們用它來調度調度程序線程。

public static class DispatcherExtensions
{
    private static Dictionary<string, DispatcherTimer> timers =
        new Dictionary<string, DispatcherTimer>();
    private static readonly object syncRoot = new object();

    public static string DelayInvoke(this Dispatcher dispatcher, string namedInvocation,
        Action action, TimeSpan delay,
        DispatcherPriority priority = DispatcherPriority.Normal)
    {
        lock (syncRoot)
        {
            if (String.IsNullOrEmpty(namedInvocation))
            {
                namedInvocation = Guid.NewGuid().ToString();
            }
            else
            {
                RemoveTimer(namedInvocation);
            }
            var timer = new DispatcherTimer(delay, priority, (s, e) =>
                {
                    RemoveTimer(namedInvocation);
                    action();
                }, dispatcher);
            timer.Start();
            timers.Add(namedInvocation, timer);
            return namedInvocation;
        }
    }


    public static void CancelNamedInvocation(this Dispatcher dispatcher, string namedInvocation)
    {
        lock (syncRoot)
        {
            RemoveTimer(namedInvocation);
        }
    }

    private static void RemoveTimer(string namedInvocation)
    {
        if (!timers.ContainsKey(namedInvocation)) return;
        timers[namedInvocation].Stop();
        timers.Remove(namedInvocation);
    } 


} 

假設您沒有使用MVVM,您可以在單擊按鈕時輕松使用它

Dispatcher.CurrentDispatcher.DelayInvoke("UpdateSearch",
       YourMethodThatStartsBackgroundThread,Timespan.FromSeconds(1));

另外值得注意的是:如果您使用的是4.5,那么您可以查看綁定的Delay屬性。

在ASP.NET中,通常我們使用兩種技術

  • 等待最多3個字符開始搜索。
  • 在用戶停止鍵入之后等待幾毫秒並且在開始搜索之前,當用戶鍵入快於幾毫秒時,您的搜索詞將包含多個字符。 第二個選項包括在用戶開始輸入時啟動計時器,並在按下每個鍵時將此計時器設置為零(不停止)。 當用戶停止鍵入2000毫秒(例如)時,執行搜索

一種完美的方法是結合這兩種技術:只搜索搜索條件中是否有3個或更多字符,並使用計時器。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM