MSDN.WhiteKnight - Stack Overflow answers
Ответ на "Как получить событие LoadCompleted контрола WebBrowser, не вставляя данный контрол в XAML?"
Answer 779065
Действительно, событие
LoadCompleted
для WPF WebBrowser не вызывается до тех пор, пока он не добавлен в какое-либо отображаемое окно или элемент управления, это известная проблема. Причина ее в том, как WebBrowser осуществляет инициализацию своего внутреннего ActiveX-элемента Internet Explorer, который и занимается загрузкой страницы. Это можно понять, посмотрев в его исходный код на Reference Source.Для корректной работы события
DocumentCompleted
внутреннего ActiveX-объекта классActiveXHost
должен быть переведен в состояниеActiveXState.InPlaceActive
. По умолчанию он находится вActiveXState.Running
(см. инициализацию свойства), переход в состояние InPlaceActive происходит при вызове метода BuildWindowCore, который вызывается только при отображении родительского окна элемента. Это поведение отличается от аналогичного элемента в WinForms, который сразу переводится в InPlaceActive при инициализации, см. здесь).Решение 1 - Использование WinForms WebBrowser
Элемент WebBrowser в WinForms избавлен от этой проблемы (аналогичное событие
DocumentCompleted
всегда вызывается), и функционально ни в чем не уступает элементу из WPF. Можно просто добавить ссылку на System.Windows.Forms и использовать его.Решение 2 - Использование окна за пределами экрана
Для вызова
BuildWindowCore
требуется видимое окно, однако никто не запрещает сделать координаты отрицательными и поместить окно за пределы экрана:Window wnd = new Window(); wnd.Content = browser; wnd.ShowInTaskbar = false; wnd.Top = -1000; wnd.Left = -1000; wnd.Width = 0; wnd.Height = 0; wnd.Show();
Решение 3 - Грязный хак с использованием отражения
Просто вызвать внутренний метод
TransitionUpTo
, передав в качества аргумента константу InPlaceActive (4):using System.Reflection; const int InPlaceActive = 4; //... var method = browser.GetType().GetMethod("TransitionUpTo",BindingFlags.NonPublic | BindingFlags.Instance); method.Invoke(browser, new object[] {InPlaceActive});
Content is retrieved from StackExchange API.
Auto-generated by ruso-archive tools.