Grand Silence: в данном случае - Dispatcher - это главный поток. Т.е. для ваших целей - он только в этом месте это главный поток, после чего снова вернётся в тот, из которого был создан. Для UI элементов есть свой диспатчер:
form1.Dispatcher.Invoke(()=>{ ...... });
textBox.Dispatcher.Invoke(()=>{ textBox.Text = "блабла"; });
в вашем случае отдельно создавать ненужно, просто пишите вместо
bob.Say("Bye");
это:
Dispatcher.Invoke(()=>{ bob.Say("Bye"); });
ну и по идеи (если я правильно понял) - должно работать
Мария: вы отправляете btn в Server.SendMessageToAll(btnStatus, tbLogin.Text, btn);
в моем коде я туда не отправляю 3-им аргументом ничего, я отправляю в TakeMessage(btnStatus, tbLogin.Text, btn); поскольку вы не показали, что у вас выполняется в Server.SendMessageToAll() - я его никак не трогал
Алексей Смирнов:
using System;
using System.IO;
using System.Net;
using System.Net.Http;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
namespace ConsoleApplication3
{
public static class Program
{
private static string html = "Ошибка";
Kirill Rud: Dispatcher нужно создавать тогда, когда UI элемент (label, progressbar, textblock, textbox и т.д.) выполняются не в основном потоке (например, вы загружаете файл и хотите в "реальном времени" смотреть проценты и писать их в label) а сам процесс должен проходить в фоновом потоке (чтобы форма не зависала)... вот тут и нужен Dispatcher . для разных UI элементов (к примеру lbel.text = textbox.text) создавайте общий диспатчер => Dispatcher.Invoke(()=> { lbel.text = textbox.text; }); Если они между собой не связаны - то для каждого свой Dispatcher => lbel.Dispatcher .Invoke(()=>{lbel.text = "что-то"; }); , textbox.Dispatcher .Invoke(()=>{ textbox.text = "что-то"; });
если вы хотите вывести " на Label вывожу текст с textBox " - в методе, который исполняется в главном потоке, то Dispatcher не нужен. Главный поток создаётся по умолчанию при запуске приложения. И пока сам метод (который что-то выполняет) не запихнете сюда DATA.SubThread = new Thread(() => ... а лучше вместо этого писать так:
Task.Run(()=> { метод(); }); (Так короче и лучше, но сразу но, Thread и Task разные вещи, но в принципе выполняют одно и тоже) и когда "метод()" будет внутри Task (или new Thread) - вот тогда и нужен Dispatcher
Алексей Смирнов: можно опять же использовать Regex для этого) но сама процедура написания шаблона для меня (если не могу сгуглить) - весьма неприятная и затратная) т.к. до конца полностью не понимаю регулярку)
Алексей Смирнов: для получение содержимого атрибутов нету универсального способа (наверно), по-этому для конкретных задач лучше самим написать метод... используя такие вещи как IndexOf(), LastIndex(), и Substring(); в индексы передавать к примеру "=" или "\""
Алексей Смирнов: какая разница) я в том смысле - суть - использовать регулярные выражения )
На счёт HttpClient, вот стандартный код получения содержимого html-ки:
string page = "http://блаблабла.ру/";
// ... используем HttpClient.
using (HttpClient client = new HttpClient())
using (HttpResponseMessage response = await client.GetAsync(page))
using (HttpContent content = response.Content)
{
// ... записать ответ
string result = await content.ReadAsStringAsync();
// ... Показать html
if (result != null)
{
Console.WriteLine(result);
}
}
}
Kirill Rud: на здоровье) поскольку с потоками вы наверно не очень знакомы) и рано или поздно с ними столкнётесь) то сразу говорю) (про WPF) - все визуальные изменения (тот же прогресс бар или показ процентов загрузки в текст блоке) выполняются в главном потоке. И иногда нужно создать что-то, чтобы выполнялось тут: DATA.SubThread = new Thread(() => { тут что-то выполняется; }); и это "что-то" должно влиять на прогресс бар или текстбокс (к примеру). Так вот, чтобы изменения были видны, нужно для каждого UI-элемента (текстбокс, прогрессбар и т.д.) вызывать свой поток... это делается легко. Допустим, выше код он должен работать внутри DATA.SubThread = new Thread(() => { тут внутри; }); тогда к progressBar1 нужно создать Dispatcher... :
progressBar1.Dispatcher.Invoke(()=>{ progressBar1.Value = e.ProgressPercentage; }); вот так.
Dispatcher - хрень, которая регулирует (сама) очередями потока. Т.е. вы создаете специально для progressBar1 Dispatcher и в него пихаете то, что должно выполняться напрямую с этим объектом.... если был был textbox, то делается аналогично:
textbox1.Dispatcher.Invoke(()=>{ textbox1.Text = "Что-то"; }); И так для каждого UI элемента есть свой Dispatcher. В wpf я часто такое использую... есть ещё и главный Dispatcher (основной UI поток), который можно использовать для всех UI элементов в совокупе:
this.Dispatcher.Invoke(()=>{progressBar1.Value = e.ProgressPercentage; textbox1.Text = "Что-то"; }); (п.с. "this." не обязательно использовать, можно просто Dispatcher.Invoke(()=>{ .... )
и сам Dispatcher (в обоих случаях) нужно вызывать как можно реже... т.е. следующий пример "негодно":
this.Dispatcher.Invoke(()=>
{
... тут куча логики, вычисления...
опять вычисления...
и тут уже progressBar1.Value = e.ProgressPercentage;
логика ... вычисления...
});
Kirill Rud: не совсем) у WebClient - свои есть евенты (загрузка, окончание загрузки и т.д.), у Mouse - свои, у Button свои (наведение курсора мыши, покидание курсора мыши, клик по кнопке, когда кнопка загружается (появляется на форме) и т.д.) - к этим эвентам можно создать обработчики. К примеру к WebClient нельзя приделать эвент (кликнуть мышкой, или навести мышку на него как у кнопки...). А так, в самом обработчике можно делать всё, что компилятору угодно)