Sto cercando di ottenere l'evento Close del tipo .NET WebBrowser, che non sembra funzionare correttamente. (EDIT:. Questo evento viene emesso quando la chiamata window.close()
è rilasciato in uno script in esecuzione nel browser)Eccezione generata quando WndProc è sovraccarico
Una soluzione che ho visto è quello di extend the WebBrowser
class and override
the WndProc
method.
mio codice di estensione è la seguente:
type internal ExtendedBrowser() = class
inherit System.Windows.Forms.WebBrowser()
let WM_PARENTNOTIFY : int = 0x0210
let WM_DESTROY : int = 0x0002
let closed : Event<unit> = new Event<unit>()
do()
[<System.Security.Permissions.PermissionSet(System.Security.Permissions.SecurityAction.Demand, Name = "FullTrust")>]
override this.WndProc (msg : Message byref) =
match msg.Msg with
| wm when wm = WM_PARENTNOTIFY ->
if (not base.DesignMode) && (msg.WParam.ToInt32() = WM_DESTROY)
then closed.Trigger()
base.DefWndProc(ref msg)
| _ ->
base.WndProc(ref msg)
member this.Closed = closed.Publish
end
questo finisce per causare una generazione di un'eccezione quando un'istanza del tipo si accede:
Unhandled Exception: System.Reflection.TargetInvocationException: Unable to get the window handle for the 'ExtendedBrowser' control. Windowless ActiveX controls are not supported. ---> System.ComponentModel.Win32Exception: Error creating window handle.
at System.Windows.Forms.NativeWindow.CreateHandle(CreateParams cp)
at System.Windows.Forms.Control.CreateHandle()
at System.Windows.Forms.Control.get_Handle()
at System.Windows.Forms.WebBrowserBase.DoVerb(Int32 verb)
at System.Windows.Forms.WebBrowserBase.TransitionFromRunningToInPlaceActive()
--- End of inner exception stack trace ---
at System.Windows.Forms.WebBrowserBase.TransitionFromRunningToInPlaceActive()
at System.Windows.Forms.WebBrowserBase.TransitionUpTo(AXState state)
at System.Windows.Forms.WebBrowser.get_AxIWebBrowser2()
at System.Windows.Forms.WebBrowser.PerformNavigate2(Object& URL, Object& flag
s, Object& targetFrameName, Object& postData, Object& headers)
at System.Windows.Forms.WebBrowser.Navigate(String urlString)
at [PRODUCT].Application.WebBrowser..ctor() in C:\[PATH]\WebBrowser.fs:line 107
at Program.Main.main(String[] args) in C:\[PATH]\Program.fs:line 79
Press any key to continue . . .
Attualmente si tratta di erroring su una chiamata a Navigate("about:blank")
(il primo accesso dell'istanza dopo la sua costruzione). Posso commentare l'override WndProc
e le cose funzionano bene (oltre a mancare l'evento close).
Qualcuno ha detto che si doveva put the security attribute on the WndProc
override così l'ho fatto e non ho sistemato le cose.
Qualcuno ha detto che è possibile effettuare il disable the DEP, ma ho provato e non mi ha permesso di escludere l'EXE.
Un'istanza dell'estensione viene creata in un wrapper per il browser (chiamato anche WebBrowser) e un'istanza di questo viene creata nel mio main
, che è in esecuzione in uno [STATO] (che sembra anche essere richiesto).
Qualcuno sa cosa potrebbe andare storto?
(Che cosa sono davvero dopo è un modo per ottenere la notifica della chiusura dell'evento, quindi se qualcuno conosce un percorso alternativo a quello sarei felice di sentirlo.)
Purtroppo, il modulo padre non si chiuderà quando viene emesso questo evento - Sto cercando di acquisire una chiamata nel browser al metodo 'window.close()', dopo di che rimuoverò il browser istanza dal modulo. Cercherò e vedrò se c'è qualcos'altro in questa strada che potrebbe essere utile; grazie per il suggerimento! – paul
Nessun problema. Si potrebbe anche provare l'approccio basato su 'Timer' suggerito qui: [window.close() congela il controllo WebBrowser di .NET 2.0 nell'applicazione Windows Form] (https://blogs.msdn.com/b/jpsanders/archive/2008/ 23/04/window-chiude-blocca-nET-2-0-browser web-controllo-in-finestre-form-Application.aspx? Redirected = true). È un post di follow-up per l'approccio basato su "estensione" a cui ti sei collegato nella tua domanda. –
Ho trovato qual era il problema! (Vedi la mia risposta.) - Avevo visto quel post sull'approccio basato sul timer ma non mi era venuto in mente di usarlo dato che non sto usando .NET 2.0 e non stavo vivendo il congelamento. Grazie ancora per il tuo contributo! – paul