Ir al contenido



Foto

Escribir una notificación en el SysTray


  • Por favor identifícate para responder
20 respuestas en este tema

#1 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 14 septiembre 2015 - 11:45

Es útil escribir notificaciones en el SysTray y resulta profesional hacerlo, para ello ya publiqué el componente SysTrayIcon. En esta ocasión muestro como hacerlo sin necesidad de dicho componente, para aplicaciones sencillas.
Utiliza sólo la API y sigue el estándar de Win10:
 

Definiciones:


delphi
  1. TNotifyIconData = record
  2. cbSize: DWORD;
  3. Wnd: HWND;
  4. uID: UINT;
  5. uFlags: UINT;
  6. uCallbackMessage: UINT;
  7. hIcon: HICON;
  8. szTip: array [0..127] of AnsiChar;
  9. dwState: DWORD;
  10. dwStateMask: DWORD;
  11. szInfo: array [0..255] of AnsiChar;
  12. uTimeout: UINT;
  13. szInfoTitle: array [0..63] of AnsiChar;
  14. dwInfoFlags: DWORD;
  15. end;
  16.  
  17. // Ampliaciones para Vista
  18. const NIIF_INFO = $00000001;
  19. const NIF_INFO = $00000010;
  20. const NIF_REALTIME = $00000040;
  21. const NIF_SHOWTIP = $00000080;
  22. const NIIF_USER = $00000004;

El procedimiento:


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String);
  2. var
  3.   Data: TNotifyIconData;
  4. begin
  5.   ZeroMemory(@Data, sizeof(TNotifyIconData));
  6.   Data.cbSize:= sizeof(TNotifyIconData);
  7.   Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8.   Data.dwInfoFlags:= NIIF_INFO;
  9.   lstrcpyn(Data.szInfoTitle, PCHAR(Titulo), 64-1);
  10.   lstrcpyn(Data.szInfo, PCHAR(Texto), 256-1);
  11.   Data.uTimeOut:= 1000;
  12.   Data.Wnd:=  Handle;
  13.   Shell_NotifyIcon(NIM_ADD, @Data);
  14.   Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. Shell_NotifyIcon(NIM_DELETE, @Data); // Para WinXP comentar esta línea. En el resto de S.O. funciona con esta línea comentada
  16. end;

Uso:


delphi
  1. procedure TForm1.Button2Click(Sender: TObject);
  2. begin
  3. ShowBalloon(Handle, Edit1.Text, Edit2.Text);
  4. end;

Subo un proyecto de ejemplo.
Saludos.

Archivos adjuntos


  • 4

#2 ELKurgan

ELKurgan

    Advanced Member

  • Miembro Platino
  • PipPipPip
  • 543 mensajes
  • LocationEspaña

Escrito 14 septiembre 2015 - 11:35

Como siempre, muy bueno

 

:ap:


  • 0

#3 cram

cram

    Advanced Member

  • Miembro Platino
  • PipPipPip
  • 824 mensajes
  • LocationMisiones, Argentina

Escrito 15 septiembre 2015 - 05:09

Muy bueno, relamente.

Aunque si nos proponemos, todo se puede programar por medio de la API, incluso, los motores de bases de datos se pueden usar con lenguaje puro sin usar los componentes provistos por la VCL o FM, eso sí: hay que trabajar mucho.

Antes tenía esa visión de Escafandra y me proponía hacer las cosas yo mismo. Lamento haber dejado ese lado de la programación, supongo que lo hice cuando empecé a programar sistemas de tipo contable.

 

Saludos


  • 0

#4 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 15 septiembre 2015 - 08:52

Muy bueno, relamente.
Aunque si nos proponemos, todo se puede programar por medio de la API, incluso, los motores de bases de datos se pueden usar con lenguaje puro sin usar los componentes provistos por la VCL o FM, eso sí: hay que trabajar mucho.
Antes tenía esa visión de Escafandra y me proponía hacer las cosas yo mismo. Lamento haber dejado ese lado de la programación, supongo que lo hice cuando empecé a programar sistemas de tipo contable.

Saludos

Estas cosas y forma de programar viene bien para pequeños proyectos en los que el tamaño del ejecutable prima. Vas añadiendo funciones a tu librería y luego no cuesta nada ir añadiendo código reutilizado. Tengo mi PC lleno de estas pequeñas cosas que añado según necesidades.


Saludos.
  • 0

#5 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 15 septiembre 2015 - 09:18

Dada mi debilidad por el C/C++ voy a publicar el truco en ese lenguaje:
 


cpp
  1. // Ampliaciones para Vista
  2. #define NIIF_INFO 0x00000001
  3. #define NIF_INFO 0x00000010
  4. #define NIF_REALTIME 0x00000040
  5. #define NIF_SHOWTIP 0x00000080
  6. #define NIIF_USER 0x00000004
  7.  
  8.  
  9. void ShowBalloon(HANDLE Handle, PCHAR Titulo, PCHAR Texto)
  10. {
  11. NOTIFYICONDATA Data;
  12. ZeroMemory(&Data, sizeof(NOTIFYICONDATA));
  13. Data.cbSize = sizeof(TNotifyIconData);
  14. Data.uFlags = NIF_ICON | NIF_INFO | NIF_REALTIME;
  15. Data.dwInfoFlags = NIIF_INFO;
  16. lstrcpyn(Data.szInfoTitle, Titulo, 64-1);
  17. lstrcpyn(Data.szInfo, Texto, 256-1);
  18. Data.uTimeout = 1000;
  19. Data.hWnd = Handle;
  20. Shell_NotifyIcon(NIM_ADD, &Data);
  21. Shell_NotifyIcon(NIM_MODIFY, &Data);
  22. }

 
 
Y la forma de uso:


cpp
  1. void __fastcall TForm1::Button1Click(TObject *Sender)
  2. {
  3. ShowBalloon(Handle, Edit1->Text.c_str(), Edit2->Text.c_str());
  4. }

Saludos


  • 1

#6 Delphius

Delphius

    Advanced Member

  • Administrador
  • 6.257 mensajes
  • LocationArgentina

Escrito 16 septiembre 2015 - 12:19

Interesante.

Estoy estudiando para un proyecto que tengo en mano la posibilidad de implementar algo de notificaciones. Pensé en algo como lo que tiene Dropbox y Copy que muestra/notifica/alerta los cambios que se realizan. Y también he pensado en la notificación en la SysTray como en tu ejemplo.

 

Se que esto de la API es en Windows, y en vista a que tengo a un "cliente" que emplea Linux me limita. Espero que Lazarus tenga algo parecido multiplataforma, sino habrá que estudiarle la vuelta.

Lo deseable es que la aplicación esté en 2do plano, para no tener que tenerla minimizada. Y como se trata de una aplicación que estará monitoreando, pienso que una buena manera de reportar los cambios del monitoreo en forma de notificaciones.

 

Saludos,


  • 0

#7 Koalasoft

Koalasoft

    Advanced Member

  • Miembros
  • PipPipPip
  • 141 mensajes
  • LocationMéxico

Escrito 03 enero 2017 - 07:13

Es útil escribir notificaciones en el SysTray y resulta profesional hacerlo, para ello ya publiqué el componente SysTrayIcon. En esta ocasión muestro como hacerlo sin necesidad de dicho componente, para aplicaciones sencillas.
Utiliza sólo la API y sigue el estándar de Win10:
 

Definiciones:


delphi
  1. TNotifyIconData = record
  2. cbSize: DWORD;
  3. Wnd: HWND;
  4. uID: UINT;
  5. uFlags: UINT;
  6. uCallbackMessage: UINT;
  7. hIcon: HICON;
  8. szTip: array [0..127] of AnsiChar;
  9. dwState: DWORD;
  10. dwStateMask: DWORD;
  11. szInfo: array [0..255] of AnsiChar;
  12. uTimeout: UINT;
  13. szInfoTitle: array [0..63] of AnsiChar;
  14. dwInfoFlags: DWORD;
  15. end;
  16.  
  17. // Ampliaciones para Vista
  18. const NIIF_INFO = $00000001;
  19. const NIF_INFO = $00000010;
  20. const NIF_REALTIME = $00000040;
  21. const NIF_SHOWTIP = $00000080;
  22. const NIIF_USER = $00000004;

El procedimiento:


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String);
  2. var
  3.   Data: TNotifyIconData;
  4. begin
  5.   ZeroMemory(@Data, sizeof(TNotifyIconData));
  6.   Data.cbSize:= sizeof(TNotifyIconData);
  7.   Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8.   Data.dwInfoFlags:= NIIF_INFO;
  9.   lstrcpyn(Data.szInfoTitle, PCHAR(Titulo), 64-1);
  10.   lstrcpyn(Data.szInfo, PCHAR(Texto), 256-1);
  11.   Data.uTimeOut:= 1000;
  12.   Data.Wnd:=  Handle;
  13.   Shell_NotifyIcon(NIM_ADD, @Data);
  14.   Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. Shell_NotifyIcon(NIM_DELETE, @Data); // Para WinXP comentar esta línea. En el resto de S.O. funciona con esta línea comentada
  16. end;

Uso:


delphi
  1. procedure TForm1.Button2Click(Sender: TObject);
  2. begin
  3. ShowBalloon(Handle, Edit1.Text, Edit2.Text);
  4. end;

Subo un proyecto de ejemplo.
Saludos.

 

Muchas gracias por tu ejemplo, una pregunta .. 

Cómo sería para que en la notificación en lugar de poner el símbolo de información, esta vez fuera de error?


  • 0

#8 Delphius

Delphius

    Advanced Member

  • Administrador
  • 6.257 mensajes
  • LocationArgentina

Escrito 03 enero 2017 - 08:30

Con NIF_WARNING. Más info en su página de MSDN.

Perdón, con NIIF_WARNING.

 

Saludos,


  • 0

#9 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 04 enero 2017 - 05:19

Muchas gracias por tu ejemplo, una pregunta .. 
Cómo sería para que en la notificación en lugar de poner el símbolo de información, esta vez fuera de error?

El código podría modificarse así:


delphi
  1.   TNotifyIconData = record
  2.     cbSize: DWORD;
  3.     Wnd: HWND;
  4.     uID: UINT;
  5.     uFlags: UINT;
  6.     uCallbackMessage: UINT;
  7.     hIcon: HICON;
  8.     szTip: array [0..127] of AnsiChar;
  9.     dwState: DWORD;
  10.     dwStateMask: DWORD;
  11.     szInfo: array [0..255] of AnsiChar;
  12.     uTimeout: UINT;
  13.     szInfoTitle: array [0..63] of AnsiChar;
  14.     dwInfoFlags: DWORD;
  15.   end;
  16.  
  17. // Ampliaciones para Vista
  18. const NIF_INFO     = $00000010;
  19. const NIF_REALTIME = $00000040;
  20. const NIF_SHOWTIP  = $00000080;
  21.  
  22. // InfoFlags
  23. const NIIF_NONE    = $00000000;
  24. const NIIF_INFO    = $00000001;
  25. const NIIF_WARNING = $00000002;
  26. const NIIF_ERROR   = $00000003;
  27. const NIIF_USER    = $00000004;


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconData;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconData));
  6. Data.cbSize:= sizeof(TNotifyIconData);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpyn(Data.szInfoTitle, PCHAR(Titulo), 64-1);
  10. lstrcpyn(Data.szInfo, PCHAR(Texto), 256-1);
  11. Data.uTimeOut:= 1000;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIcon(NIM_ADD, @Data);
  14. Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Las InfoFlags de iconos de notificación no son sumables.

 

Subo un proyecto de ejemplo delphi7

Archivos adjuntos


  • 0

#10 Koalasoft

Koalasoft

    Advanced Member

  • Miembros
  • PipPipPip
  • 141 mensajes
  • LocationMéxico

Escrito 04 enero 2017 - 10:03

El código podría modificarse así:


delphi
  1.   TNotifyIconData = record
  2.     cbSize: DWORD;
  3.     Wnd: HWND;
  4.     uID: UINT;
  5.     uFlags: UINT;
  6.     uCallbackMessage: UINT;
  7.     hIcon: HICON;
  8.     szTip: array [0..127] of AnsiChar;
  9.     dwState: DWORD;
  10.     dwStateMask: DWORD;
  11.     szInfo: array [0..255] of AnsiChar;
  12.     uTimeout: UINT;
  13.     szInfoTitle: array [0..63] of AnsiChar;
  14.     dwInfoFlags: DWORD;
  15.   end;
  16.  
  17. // Ampliaciones para Vista
  18. const NIF_INFO     = $00000010;
  19. const NIF_REALTIME = $00000040;
  20. const NIF_SHOWTIP  = $00000080;
  21.  
  22. // InfoFlags
  23. const NIIF_NONE    = $00000000;
  24. const NIIF_INFO    = $00000001;
  25. const NIIF_WARNING = $00000002;
  26. const NIIF_ERROR   = $00000003;
  27. const NIIF_USER    = $00000004;


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconData;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconData));
  6. Data.cbSize:= sizeof(TNotifyIconData);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpyn(Data.szInfoTitle, PCHAR(Titulo), 64-1);
  10. lstrcpyn(Data.szInfo, PCHAR(Texto), 256-1);
  11. Data.uTimeOut:= 1000;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIcon(NIM_ADD, @Data);
  14. Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Las InfoFlags de iconos de notificación no son sumables.

 

Subo un proyecto de ejemplo delphi7

 

Acabo de checar tu programa, tengo Windows 10 con Delphi 7, al ejecutarlo todo muy bien, gracias por el ejemplo, pero .. un detalle curioso, al dar click y mostrarme la notificación .. manda el mensaje dos veces seguidas, una después del otro .. es normal eso?


  • 0

#11 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 04 enero 2017 - 10:50

Acabo de checar tu programa, tengo Windows 10 con Delphi 7, al ejecutarlo todo muy bien, gracias por el ejemplo, pero .. un detalle curioso, al dar click y mostrarme la notificación .. manda el mensaje dos veces seguidas, una después del otro .. es normal eso?

Si estas usando Windows >= Vista, Data.uTimeOut se refiere a la versión de Shell notification (en XP es un TimeOut). Sustituye el valor por  1:


delphi
  1. Data.uTimeOut:= 1;

795db52491f0213506d35105eb58137do.gif


 

Saludos.


  • 1

#12 Koalasoft

Koalasoft

    Advanced Member

  • Miembros
  • PipPipPip
  • 141 mensajes
  • LocationMéxico

Escrito 13 diciembre 2017 - 11:35

Si estas usando Windows >= Vista, Data.uTimeOut se refiere a la versión de Shell notification (en XP es un TimeOut). Sustituye el valor por  1:


delphi
  1. Data.uTimeOut:= 1;

795db52491f0213506d35105eb58137do.gif


 

Saludos.

 

Estimado, después de que W10 hizo una actualización, este tipo de mensajes ya no funciona, sabes a que se deberá esto? les ha pasado?


  • 0

#13 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 19 diciembre 2017 - 01:01

Estimado, después de que W10 hizo una actualización, este tipo de mensajes ya no funciona, sabes a que se deberá esto? les ha pasado?

 

Parece que a M$ le gusta cambiar cosas

 

Comenta esta línea y me cuentas:


delphi
  1. Shell_NotifyIcon(NIM_DELETE, @Data);

Debería quedarte como sigue:


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconData;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconData));
  6. Data.cbSize:= sizeof(TNotifyIconData);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpyn(Data.szInfoTitle, PCHAR(Titulo), 64-1);
  10. lstrcpyn(Data.szInfo, PCHAR(Texto), 256-1);
  11. Data.uTimeOut:= 1;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIcon(NIM_ADD, @Data);
  14. Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. //Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Saludos.


  • 1

#14 egostar

egostar

    missing my father, I love my mother.

  • Administrador
  • 13.953 mensajes
  • LocationMéxico

Escrito 19 diciembre 2017 - 09:53

Parece que a M$ le gusta cambiar cosas

 

Si que le gusta cambiarlas :D

 

Acaba de instalarse la ultima version de Win10 en mi máquina y si que veo algunas diferencias aunque muy sutiles.

 

Saludos


  • 0

#15 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 19 diciembre 2017 - 02:53

Si que le gusta cambiarlas :D

 

Acaba de instalarse la ultima version de Win10 en mi máquina y si que veo algunas diferencias aunque muy sutiles.

 

Saludos

He probado en Win8 actualizado y el código precisa comentar Shell_NotifyIcon(NIM_DELETE, @Data), tambien en WinXP, sin embargo no en Win10 actualizado. Por lo tanto lo mejor es comentarlo siempre como expongo aquí.

 

Saludos.


  • 1

#16 enecumene

enecumene

    Webmaster

  • Administrador
  • 7.404 mensajes
  • LocationRepública Dominicana

Escrito 13 marzo 2019 - 09:08

Revivo el tema por un problema que se me está presentando con Delphi XE7, y es la incompatibilidad de tipos de datos en Data.szInfoTitle y Data.szInfo que están declarados como array de AnsiChar, pero lstrcpyn espera un tipo de datos PWideChar, hice los siguientes cambios y resultados:
 
- cambié ambas propiedades a PWideChar, al ejecutar me lanza un error tipo de creación de objetos.
- cambié ambas propiedades a array[..] of widechar, al ejecutar no hace nada ni marca error alguno.
 
Esto lo realizo con Delphi XE7 y wins 10.
 
Saludos.
 

He probado en Win8 actualizado y el código precisa comentar Shell_NotifyIcon(NIM_DELETE, @Data), tambien en WinXP, sin embargo no en Win10 actualizado. Por lo tanto lo mejor es comentarlo siempre como expongo aquí.
 
Saludos.


  • 0

#17 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 13 marzo 2019 - 10:34

Revivo el tema por un problema que se me está presentando con Delphi XE7, y es la incompatibilidad de tipos de datos en Data.szInfoTitle y Data.szInfo que están declarados como array de AnsiChar, pero lstrcpyn espera un tipo de datos PWideChar, hice los siguientes cambios y resultados:
 
- cambié ambas propiedades a PWideChar, al ejecutar me lanza un error tipo de creación de objetos.
- cambié ambas propiedades a array[..] of widechar, al ejecutar no hace nada ni marca error alguno.
 
Esto lo realizo con Delphi XE7 y wins 10.
 
Saludos.
 

 

Prueba usando de forma nativa PWCHAR de esta forma:


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconDataW;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconDataW));
  6. Data.cbSize:= sizeof(TNotifyIconDataW);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpyn(Data.szInfoTitle, PWCHAR(Titulo), 64*sizeof(WCHAR)-1);
  10. lstrcpyn(Data.szInfo, PWCHAR(Texto), 256*sizeof(WCHAR)-1);
  11. Data.uTimeOut:= 1;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIcon(NIM_ADD, @Data);
  14. Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. //Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Saludos.


  • 0

#18 enecumene

enecumene

    Webmaster

  • Administrador
  • 7.404 mensajes
  • LocationRepública Dominicana

Escrito 13 marzo 2019 - 10:50

Prueba usando de forma nativa PWCHAR de esta forma:


delphi
  1. procedure ShowBalloon(Handle: THANDLE; Titulo, Texto: String; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconDataW;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconDataW));
  6. Data.cbSize:= sizeof(TNotifyIconDataW);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpyn(Data.szInfoTitle, PWCHAR(Titulo), 64*sizeof(WCHAR)-1);
  10. lstrcpyn(Data.szInfo, PWCHAR(Texto), 256*sizeof(WCHAR)-1);
  11. Data.uTimeOut:= 1;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIcon(NIM_ADD, @Data);
  14. Shell_NotifyIcon(NIM_MODIFY, @Data);
  15. //Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Saludos.

 

Gracias, pero igual insiste,

 

[dcc32 Error] sisNotifications.pas(51): E2010 Incompatible types: 'PWideChar' and 'array[0..63] of AnsiChar'

 


  • 0

#19 enecumene

enecumene

    Webmaster

  • Administrador
  • 7.404 mensajes
  • LocationRepública Dominicana

Escrito 13 marzo 2019 - 11:01

Esto sucede cuando cambio las propiedades szInfoTitle y szInfo a PWideCHar:

 

---------------------------
Debugger Exception Notification
---------------------------
Project SisAuto.exe raised exception class $C0000005 with message 'access violation at 0x77169c8f: write of address 0x00000000'.
---------------------------
Break   Continue   Help   
---------------------------
 


  • 0

#20 escafandra

escafandra

    Advanced Member

  • Moderadores
  • PipPipPip
  • 3.839 mensajes
  • LocationMadrid - España

Escrito 13 marzo 2019 - 03:31

[dcc32 Error] sisNotifications.pas(51): E2010 Incompatible types: 'PWideChar' and 'array[0..63] of AnsiChar'

 Quizás no has caído en que el último código No usa TNotifyIconData sino TNotifyIconDataW que usa precisamente WCHAR.

 

El error se debe a que en TNotifyIconData definido en este hilo corresponde a la versión TNotifyIconDataA para usar AnsiChar. Los arrays no puedes asignarlos a un puntero PWCHAR ó PAnsiChar sino llenarlos (lstrcpynA) y en ese caso se desbordan al llenarlos con WCHAR ((lstrcpynW) que ocupan el doble de espacio.

 

Supongo que Delphi XE7 tiene definidas TNotifyIconDataA y TNotifyIconDataW, Berlín si las trae, con lo que la definición dada en este truco sobraría (se hizo para delphi7) y el código expuesto compilará. En caso de que no lo tenga definido puedes usar esta:


delphi
  1. TNotifyIconDataW = record
  2. cbSize: DWORD;
  3. Wnd: HWND;
  4. uID: UINT;
  5. uFlags: UINT;
  6. uCallbackMessage: UINT;
  7. hIcon: HICON;
  8. szTip: array [0..127] of WCHAR;
  9. dwState: DWORD;
  10. dwStateMask: DWORD;
  11. szInfo: array [0..255] of WCHAR;
  12. uTimeout: UINT;
  13. szInfoTitle: array [0..63] of WCHAR;
  14. dwInfoFlags: DWORD;
  15. guidItem: TGUID;
  16. hBalloonIcon: HICON;
  17. end;

Puedes consultar las definiciones dadas por M$ aquí.

Por cierto, M$ ha añadido los dos últimos elementos de la estructura (guidItem y hBalloonIcon) en ambas versiones

 

 

En el caso de que prefieras el uso de PAnsiChar y AnsiString, puedes usar esta otra modificación para este caso:


delphi
  1. procedure ShowBalloonA(Handle: THANDLE; Titulo, Texto: AnsiString; InfoFlags: DWORD);
  2. var
  3. Data: TNotifyIconDataA;
  4. begin
  5. ZeroMemory(@Data, sizeof(TNotifyIconDataA));
  6. Data.cbSize:= sizeof(TNotifyIconDataA);
  7. Data.uFlags:= NIF_ICON or NIF_INFO or NIF_REALTIME;
  8. Data.dwInfoFlags:= InfoFlags;
  9. lstrcpynA(Data.szInfoTitle, PAnsiCHAR(Titulo), 64-1);
  10. lstrcpynA(Data.szInfo, PAnsiCHAR(Texto), 256-1);
  11. Data.uTimeOut:= 1;
  12. Data.Wnd:= Handle;
  13. Shell_NotifyIconA(NIM_ADD, @Data);
  14. Shell_NotifyIconA(NIM_MODIFY, @Data);
  15. //Shell_NotifyIcon(NIM_DELETE, @Data);
  16. end;

Una última aclaración, las API versión W usan PWCHAR y las versión tipo A usa PAnsiChar

 

 

Saludos.


  • 1