Заредете WPF Combobox в отделна нишка

Опитвам се да заредя този комбиниран списък с таблица от базата данни, всичко работи добре, но има много записи и зареждането отнема минута. Бих искал да преместя това в отделна нишка, но продължавам да получавам кръстосани нишки. Мисля, че напречната нишка се случва b/c, падащият списък е в нишката на потребителския интерфейс. Някой знае ли прост начин да се постигне това.

Благодаря Майкъл

private void BindComboBox()
{
        SqlConnection con = Program.GetConnection;
        SqlDataAdapter da = new SqlDataAdapter("SELECT ContactId, FullName FROM dbo.Contact WHERE FULLNAME IS NOT NULL", con);
        DataSet ds = new DataSet();
        da.Fill(ds, "dbo.Contact");

        SearchBOX.ItemsSource =  ds.Tables[0].DefaultView;
        SearchBOX.DisplayMemberPath = ds.Tables[0].Columns["FullName"].ToString();
        SearchBOX.SelectedValuePath = ds.Tables[0].Columns["ContactId"].ToString();
        SearchBOX.IsEnabled = true;
}

person perirose    schedule 04.06.2014    source източник
comment
Използвайте Dispatcher.BeginInvoke около операциите на потребителския интерфейс. Дори по-добре, просто обвържете ItemsSource и актуализирайте свойството за поддръжка във вашата нова нишка.   -  person BradleyDotNET    schedule 04.06.2014
comment
боже, благодаря за отговора   -  person perirose    schedule 05.06.2014
comment
Може да използва фонов работник за зареждане на данните в друга нишка. След това обвързвате данните към контролата на потребителския интерфейс в събитието завършено. Само основната нишка има достъп до UI контрола. И така, какво е над празния ред, което правите на backgroundoworker.   -  person paparazzo    schedule 05.06.2014
comment
защо не използвате един от най-мощните аспекти на WPF - обвързване на данни?   -  person mcy    schedule 05.06.2014


Отговори (2)


Опитай това :

 Dispatcher.Invoke(new Action(() =>
    {
        // Your combo items loading code here
    }));
person HichemSeeSharp    schedule 04.06.2014

Ще спомена възможните решения

  1. Dispatcher.Invoke за последователно извикване или Dispatcher.BeginInvoke за асинхронно
  2. Нова тема от

    var thread = new Thread(new ThreadStart(delegate{ code to update }));
    

това не се препоръчва, тъй като отнема много време и памет за създаване на една нишка, вместо това използвайте това

ThreadPool.QueueUserWorkItem(new WaitCallback(delegate
                {

                }));

той създава нишка и когато приключи работата си, го връща обратно в пула, състоянието му се променя на неактивен и когато се добави нов метод към пула, не се създава автоматично нишка, но започва от търсене на неактивна нишка и след това го събужда. Не прилагайте времеемки методи в него, тъй като може да се окаже, че няколко нишки работят, а други чакат безучастно.

3. Друг изход е BackgroundWorker. Той използва SynchronizationContext за превключване между обикновена нишка и UI нишка.

        var worker = new BackgroundWorker();
        worker.DoWork += worker_DoWork;
        worker.WorkerReportsProgress = true;
        worker.ProgressChanged += worker_ProgressChanged;
        worker.RunWorkerCompleted += worker_RunWorkerCompleted;
        worker.RunWorkerAsync();

Методът ProgressChanged и RunWorkerCompleted работят върху UI поток. Между другото Backgroundworker използва ThreadPool. Нишките са настроени да бъдат фонова нишка (което означава, че когато изключите приложението, нишките също ще бъдат затворени). Избягвайте замразяването на нишката на потребителския интерфейс. Помислете да не зареждате всичко в началото, а постепенно, докато превъртате надолу в списъчната кутия.

person Maximus    schedule 04.06.2014