FiveTech Support Forums

FiveWin / Harbour / xBase community
Board index FiveWin para Harbour/xHarbour Bloqueo de aplicacion usando Webvie2
Posts: 483
Joined: Sat Feb 03, 2007 06:36 AM

Bloqueo de aplicacion usando Webvie2

Posted: Sat Sep 05, 2026 03:26 PM

Hola a todos.
No se si alguien ha tenido este problema, pero la usar la clase Webview2, al salir de la misma, el sistema se bloquea.
En este codigo

STATIC oWeb

FUNCTION VentanWeb()
...
..
   ACTIVATE WINDOW oWnd ;
      ON INIT WebVie2Init( oWnd ) ;
      ON RESIZE WndResize( nWidth, nHeight ) 

   HB_SYMBOL_UNUSED( oBrw )

Return NIL

//--------------------------------------------------------------------------//
STATIC FUNCTION WebVie2Init( oWnd )

   LOCAL oRc, cHtml

   oRc := oWnd:GetCliRect()

   oWeb := TWebView2():New( oWnd )
   oWeb:SetUserAgent( "Mozilla/5.0 Sistema Prueba" )
   oWeb:bOnBind := { | cJson, cCalls | VentanaBind( cJson, cCalls ) }

   cHtml := HtmlWebView()
   oWeb:SetHtml( cHtml )
   oWeb:SetSize( oRc:nWidth, oRc:nHeight )

Return NIL

Todo funciona bien, pero al salir de esta ventana, e iungresar a otra opcion de la aplicación se bloquea totalmente.

Esto me pasa tanto en la version de 32 bits como en la de 64 bits.

Si alguien me puede dar alguna idea de que puede estar pasando se lo agradeceré bastante.

Saludos cordiales.

Carlos Sincuir

Posts: 44508
Joined: Thu Oct 06, 2005 05:47 PM

Re: Bloqueo de aplicacion usando Webvie2

Posted: Sat Sep 05, 2026 03:36 PM

Estimado Carlos,

Lo tienes localizado: nunca liberas el WebView al cerrar la ventana, y la clase no lo hace por ti. Te detallo la cadena completa, verificada en el fuente:
Qué pasa

  1. oWeb:End() no se llama nunca. Tu oWeb es STATIC y el ACTIVATE WINDOW no tiene cláusula VALID. Al cerrar la ventana muere el HWND padre, pero el controller COM (ICoreWebView2Controller) sigue vivo: lo único que lo destruye es TWebView2:End() → webview2_end() → delete (source/classes/twebview2.prg:51, source/internal/twebview/cwebview.cpp:734).
  2. El destructor además fuga por diseño: TWebView() quita los handlers y libera los settings, pero no llama a pController->Close() ni hace Release() del controller/core. Cada visita deja un browser Edge huérfano y un proceso rondando.
  3. El objeto Harbour queda eternamente referenciado: New() hace AAdd( aWebViews, Self ) y nada lo quita jamás.
  4. Al reentrar se crea un segundo controller sobre la misma user-data-folder por defecto (%APPDATA%\<tuExe>), con el primero fugado aún vivo. Y aquí está el bloqueo: Initialize(), Navigate() y SetHtml() esperan la creación async con while( bBusy ) SysRefresh();. Si la creación no completa, ese bucle no sale nunca → la app se queda totalmente bloqueada bombeando mensajes. Por eso te pasa igual en 32 y 64 bits: es lógica, no arquitectura.
  5. Agravante: WebView2_OnBind() resuelve con aWebViews[ AScan(...) ] sin comprobar si es 0 (los otros dos callbacks sí lo comprueban), así que mensajes JS del controller fugado pueden caer en el objeto muerto, cuya ventana ya no existe.
    La prueba de que End() es obligatorio la da el propio framework: FW_WebView() (mismo twebview2.prg, líneas 251-264) engancha oWnd:bValid := { || oWeb:End(), .t. }, y el sample samples/ai/opencode2.prg:2021 limpia con oWeb:End() + oWeb := nil en su Cleanup().
    La corrección (lado app)
    STATIC oWeb := nil

FUNCTION VentanWeb()
...
ACTIVATE WINDOW oWnd ;
ON INIT WebVie2Init( oWnd ) ;
VALID WebVie2End() ;
ON RESIZE ( oWeb:SetSize( oWnd:nWidth, oWnd:nHeight ) )
return nil

STATIC FUNCTION WebVie2End()
if oWeb != nil
oWeb:End()
oWeb := nil
endif
return .t.
Dos detalles más en tu código: en ON RESIZE WndResize( nWidth, nHeight ), nWidth/nHeight no existen en ese ámbito — usa oWnd:nWidth/oWnd:nHeight (o bResized, que sí recibe {|nType,nWidth,nHeight|}); y blinda WndResize()/VentanaBind() con if oWeb == nil ... return, porque pueden llegar callbacks con la ventana a medio cerrar.
Lado framework (pendiente, si quieres)
TWebView2:Destroy() hoy es VIRTUAL vacío; puedo implementarlo para que llame a End() y saque el objeto de aWebViews, blindar GetWebView() contra AScan()==0, y añadir pController->Close() + Release() en TWebView(). Eso exige reconstruir la lib C — dime y lo hago con su entrada en whatsnew.txt.

regards, saludos

Antonio Linares
www.fivetechsoft.com
Posts: 483
Joined: Sat Feb 03, 2007 06:36 AM

Re: Bloqueo de aplicacion usando Webvie2

Posted: Sat Sep 05, 2026 06:02 PM

Gracias Antonio por el tip, voy a hacer las pruebas y comento luego como me va. Feliz fin de semana.

Carlos

Posts: 483
Joined: Sat Feb 03, 2007 06:36 AM

Re: Bloqueo de aplicacion usando Webvie2

Posted: Sat Sep 05, 2026 09:25 PM

Antonio, ya he aplicado lo que indicas, del lado app en 32 y 64 bits:

  • VALID llama oWeb:End() con el HWND padre aún vivo (TMdiChild:End evalúa bValid antes de ChildClose).
  • End() saca el objeto de aWebViews, anula callbacks y llama WebView2_End().
  • Carpeta user-data distinta por instancia (%LOCALAPPDATA%\SEM70\wv2_N).
  • GetWebView / OnBind blindados si AScan==0.

Pero lastimosamente, el bloqueo sigue. Aca te explico un poco mas el proceso:

  1. Abro un proces de Análisis Contable (TWebView2 en MDICHILD), que suo con Webvie2, genero un reporte de Balance General (reporte nativo FWH, no WebView).
  2. Cierro con la X. La ventana desaparece bien.
  3. Abro Mantenimiento de Cuentas Contables: el TXBrowse lista bien.
  4. Doble clic o botón Modificar: ACTIVATE DIALOG RESOURCE "CTASCONTA" → internamente DialogBox(). El diálogo no aparece y la aplicación se bloquea por completo.

NOTA: El menú del sistema es un menú Ribbon.

He realizado las pruebas con Grok, y despues de estos ultimos cambios me he pedido esto:

El listado del mantenimiento de cuentas es un MDI que lista las cuentas con xBrowse. El alta/edición usa DialogBox() (bucle modal anidado) y se cuelga. Eso encaja con un ICoreWebView2Controller huérfano cuyo filtro de mensajes/aceleradores sigue instalado porque el destructor de TWebView no llama pController->Close() ni Release().

Preguntar a Antonio si: ¿Puedee reconstruir FiveHC / FiveHC64 con:

  • pController->Close() + Release() del controller y del core en TWebView::TWebView / webview2_end()
  • TWebView2:Destroy() que llame End() y saque el objeto de aWebViews

Con eso debería desaparecer el freeze en cualquier ACTIVATE DIALOG posterior.

Que piensas al respecto?

Saludos cordiales.

Carlos

Posts: 44508
Joined: Thu Oct 06, 2005 05:47 PM

Re: Bloqueo de aplicacion usando Webvie2

Posted: Sun Sep 06, 2026 01:01 AM

Estimado Carlos,

Dile a Grok que ponga trazas y que genere un archivo log

Para que veamos hasta donde llega :idea:

regards, saludos

Antonio Linares
www.fivetechsoft.com

Continue the discussion