Как запустить Task в Sta? У класса Thread есть метод SetApartmentState, а что делать с классом Task, если мне надо в другом потоке создать экзeмпляр класса System.Windows.Forms.WebBrowser в другом потоке?
1 Answers
Apartment state — это на уровне COM свойство нативного потока (класс Thread — обёртка над ним). В общем случае для задач (task) такое понятие не существует в принципе. Планировщик задач (task scheduler) по умолчанию использует потоки из пула, для которых задать apartment state невозможно, потому что они полностью управляются фреймворком.
Вы можете использовать кастомный TaskScheduler, который полагается на созданные вручную потоки, а не на потоки из пула. Примеры кастомных планировщиков можно найти на MSDN: Samples for Parallel Programming with the .NET Framework (статья с описанием: ParallelExtensionsExtras Tour - #7 - Additional TaskSchedulers). Вас интересует StaTaskScheduler.
В слегка переписанном виде можете посмотреть его у меня в приватном фреймворке: ApartmentTaskScheduler.cs (permalink, search). В коде используется несколько прибамбасов, но от них легко избавиться.
- 32,103
-
Поскольку ТС хочет запустить WinForms-код, возможно, ему просто нужен WinForms-аналог вот этого. // То есть, вот этого, в том примере обрезан диспетчер. – VladD Nov 06 '15 at 16:00
-
@VladD Если нужно "просто запустить", то достаточно
new Thread(() => { }) { ApartmentState = ApartmentState.STA }.Start(), не? – Kyubey Nov 06 '15 at 16:24 -
Ну, на таком потоке нельзя будет работать с WPF-контролами, т. к. не бежит диспетчер. По аналогии, мне казалось, что нужно запустить
Application.Runв этом потоке, чтобы работать сSystem.Windows.Forms.*(но я не уверен, опыта работы с winforms нет вообще). – VladD Nov 06 '15 at 16:32 -
@VladD Вроде, что-то в духе
... () => { Application.Run(new Form()); } ...– Kyubey Nov 06 '15 at 16:43 -
Угу, как раз пробую такое. Сейчас только разберусь, как скрыть эту новую форму. Хотя, если юзер захочет работать с контролами, сможет ли он это делать без своей формы? – VladD Nov 06 '15 at 16:45
-
-
-
Хотел, да. Но у меня логическая нестыковка с формами: когда их показывать, так что... – VladD Nov 06 '15 at 16:51
-
Чёрт! С невидимой формой не запускается message loop, InvokeRequired выдаёт всё время false :-\ – VladD Nov 06 '15 at 16:56
-
@Glorfindel (1) Никого из редакторов не смутило, что ссылка не была заменена на рабочую, а по сути просто удалена? (1) – Kyubey Oct 30 '22 at 13:26
-
@SNick (2) Никого из редакторов не смутило, что ссылка не была заменена на рабочую, а по сути просто удалена? (2) – Kyubey Oct 30 '22 at 13:27
-
@aleksandrbarakin (3) Никого из редакторов не смутило, что ссылка не была заменена на рабочую, а по сути просто удалена? (3) – Kyubey Oct 30 '22 at 13:27
-
@Kyubey thanks for catching that, my script didn't know https://learn.microsoft.com/en-us/samples/browse/ is a 'dead end'. Do you know of any proper substitution? https://web.archive.org/web/20130928022438/https://code.msdn.microsoft.com/ParExtSamples works, but it's not 'live' ... – Glorfindel Nov 18 '22 at 17:17
-
@Kyubey thanks for catching that, my script didn't know learn.microsoft.com/en-us/samples/browse is a 'dead end'. I see you found a replacement, I'll update my script. – Glorfindel Nov 18 '22 at 17:45