/[winpt]/trunk/PTD/PTD.cpp
ViewVC logotype

Diff of /trunk/PTD/PTD.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2 by twoaday, Mon Jan 31 11:02:21 2005 UTC revision 61 by werner, Wed Nov 2 14:48:01 2005 UTC
# Line 1  Line 1 
1  /* PTD.cpp - Privacy Tray Dynamic  /* PTD.cpp - Privacy Tray Dynamic
2   *      Copyright (C) 2002-2005 Timo Schulz   *      Copyright (C) 2002-2005 Timo Schulz
3   *   *
4   * This file is part of WinPT.   * This file is part of WinPT.
5   *   *
6   * WinPT is free software; you can redistribute it and/or modify   * WinPT is free software; you can redistribute it and/or modify
7   * it under the terms of the GNU General Public License as published by   * it under the terms of the GNU General Public License as published by
8   * the Free Software Foundation; either version 2 of the License, or   * the Free Software Foundation; either version 2 of the License, or
9   * (at your option) any later version.   * (at your option) any later version.
10   *   *
11   * WinPT is distributed in the hope that it will be useful,   * WinPT is distributed in the hope that it will be useful,
12   * but WITHOUT ANY WARRANTY; without even the implied warranty of   * but WITHOUT ANY WARRANTY; without even the implied warranty of
13   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14   * GNU General Public License for more details.   * GNU General Public License for more details.
15   *   *
16   * You should have received a copy of the GNU General Public License   * You should have received a copy of the GNU General Public License
17   * along with WinPT; if not, write to the Free Software Foundation,   * along with WinPT; if not, write to the Free Software Foundation,
18   * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA   * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19   */   */
20    
21  #include <windows.h>  #ifdef HAVE_CONFIG_H
22  #include <stdio.h>  #include <config.h>
23    #endif
24  HINSTANCE glob_hinst;  
25    #include <windows.h>
26  /* We need a special section in the DLL for storing our shared data */  #include <windows.h>
27  #pragma data_seg(".SHARDAT")  #include <stdio.h>
28  static HHOOK cbt_hook = NULL;  #include <ocidl.h>
29  static DWORD tray_proc_id = 0;  #include <olectl.h>
30  static HWND shell_traywnd = 0;  
31  static HWND curr_focus = NULL;  #include "wptJPG.h"
32  static HWND rebar_w32 = NULL;  
33  static HWND mstask_swc = NULL;  HINSTANCE glob_hinst;
34  static HWND systab_c32 = NULL;  
35  #pragma data_seg()  /* We need a special section in the DLL for storing our shared data.
36       This shared data is required by the hook function becuase theat
37  static unsigned * journ_keys = 0;     function is called in the context of the actual thread running the
38  static unsigned key_idx = 0;     hook and thus we need a way to communicate the result of our hook
39  static unsigned nkeys = 0;     function back to us.  We use a shared data segment for this. */
40  static HHOOK journ_hook = NULL;  #ifdef __GNUC__
41    #define ATTR_SEC __attribute__((section (".SHARDAT"), shared))
42    #else
43  static LRESULT CALLBACK  #define ATTR_SEC
44  PTD_CBT_proc (int code, WPARAM wparam, LPARAM lparam)  #pragma data_seg(".SHARDAT")
45  {  #endif
46      HWND curr_hwnd = NULL;        static HHOOK cbt_hook      ATTR_SEC = NULL; /* CTB hook handle. */
47      DWORD proc_id = 0;  static DWORD tray_proc_id  ATTR_SEC = 0;    /* WinPT PID */
48        static HWND  shell_traywnd ATTR_SEC = 0;    /* Tray window handle. */
49      if (code >= 0 && code == HCBT_SETFOCUS) {  static HWND  curr_focus    ATTR_SEC = NULL; /* Current window focus handle. */
50          /* A window is about to receive the keyboard focus */            static HWND  rebar_w32     ATTR_SEC = NULL;
51            static HWND  mstask_swc    ATTR_SEC = NULL;
52          curr_hwnd = (HWND)wparam;  static HWND  systab_c32    ATTR_SEC = NULL;
53          GetWindowThreadProcessId( curr_hwnd, &proc_id );  #ifndef __GNUC__
54          /* Only if the current window is different from this window list,  #pragma data_seg()
55             we set the new focus. For more information read the hint in  #endif
56             PTD_initialize. */  #undef ATTR_SEC
57          if ((proc_id != tray_proc_id)  
58               && (curr_hwnd != NULL)  
59               && (curr_hwnd != curr_focus)  static unsigned *journ_keys = 0;
60               && (curr_hwnd != shell_traywnd)  static unsigned key_idx = 0;
61               && (curr_hwnd != systab_c32)  static unsigned nkeys = 0;
62               && (curr_hwnd != mstask_swc)  static HHOOK journ_hook = NULL;     /* Journaling hook  handle. */
63               && (curr_hwnd != rebar_w32)) {  
64              curr_focus = curr_hwnd;  
65          }  static LRESULT CALLBACK
66      }  PTD_CBT_proc (int code, WPARAM wparam, LPARAM lparam)
67        {
68      return  CallNextHookEx (cbt_hook , code, wparam, lparam);      HWND curr_hwnd = NULL;      
69  } /* PTD_CBT_proc */      DWORD proc_id = 0;
70        
71        if (code >= 0 && code == HCBT_SETFOCUS) {
72  HWND          /* A window is about to receive the keyboard focus */          
73  PTD_get_curr_hwnd (void)          
74  {          curr_hwnd = (HWND)wparam;
75      return curr_focus;          GetWindowThreadProcessId( curr_hwnd, &proc_id );
76  } /* PTD_get_curr_hwnd */          /* Only if the current window is different from this window list,
77               we set the new focus. For more information read the hint in
78               PTD_initialize. */
79  BOOL          if ((proc_id != tray_proc_id)
80  PTD_initialize (void)               && (curr_hwnd != NULL)
81  {               && (curr_hwnd != curr_focus)
82      tray_proc_id = GetCurrentProcessId( );               && (curr_hwnd != shell_traywnd)
83      cbt_hook = SetWindowsHookEx( WH_CBT, PTD_CBT_proc, glob_hinst, 0 );               && (curr_hwnd != systab_c32)
84      if( cbt_hook == NULL )                             && (curr_hwnd != mstask_swc)
85          return FALSE;               && (curr_hwnd != rebar_w32)) {
86                    curr_focus = curr_hwnd;
87      /* Okay, what are we doing here:          }
88       * In the past I used the Spy++ application to find out why the old current window      }
89       * doesn't work on so much systems. Now we try to use the computer based training      
90       * hook, more precise the HCBT_SETFOCUS to find out the last window focus. But to      return  CallNextHookEx (cbt_hook , code, wparam, lparam);
91       * succeed we need to ignore some windows because otherwise our own window or a  }
92       * window from the taskbar would be recognized.  
93       *  
94       * Here is what the Spy++ says about the windows order:  /* Return the last selected window */
95       * Shell_TrayWnd  extern "C" HWND
96       *  \ ReBarWindow32  PTD_get_curr_hwnd (void)
97       *                \ MSTaskSwWClass  {
98       *                               \ SysTabControl32      return curr_focus;
99       *  }
100       * As a result we need to ignore those windows to prevent failured in the code.  
101       */  
102      shell_traywnd = FindWindowEx (NULL, NULL, "Shell_TrayWnd", NULL);  /* Initialize CTB hook and try to find the system windows. */
103      rebar_w32 = FindWindowEx (shell_traywnd, NULL, "ReBarWindow32", NULL);  extern "C" BOOL
104      mstask_swc = FindWindowEx (rebar_w32, NULL, "MSTaskSwWClass", NULL);  PTD_initialize (void)
105      systab_c32 = FindWindowEx (mstask_swc, NULL, "SysTabControl32", NULL);  {
106            tray_proc_id = GetCurrentProcessId ();
107      /*_log_box ("tray_proc_id=%u cbt_hook=%p shell_traywnd=%p rebar_w32=%p "      cbt_hook = SetWindowsHookEx (WH_CBT, PTD_CBT_proc, glob_hinst, 0);
108                  "mstask_swc=%p systab_c32=%p",      if (cbt_hook == NULL)
109                  tray_proc_id, cbt_hook, shell_traywnd, rebar_w32,          return FALSE;
110                  mstask_swc, systab_c32);*/      
111        
112      return TRUE;      /* Okay, what are we doing here:
113  } /* PTD_initialize */       * In the past I used the Spy++ application to find out why the old current
114         * window doesn't work on so much systems. Now we try to use the computer
115         * based training hook, more precise the HCBT_SETFOCUS to find out the
116  void       * last window focus. But to succeed we need to ignore some windows
117  PTD_delete (void)       * because otherwise our own window or a window from the taskbar
118  {       * would be recognized.
119      if (!cbt_hook)       *
120          return;       * Here is what the Spy++ says about the windows order:
121      UnhookWindowsHookEx (cbt_hook);       * Shell_TrayWnd
122      cbt_hook = NULL;       *  \ ReBarWindow32
123      shell_traywnd = NULL;       *                \ MSTaskSwWClass
124      tray_proc_id = 0;       *                               \ SysTabControl32
125  } /* PTD_delete */       *
126         * As a result we need to ignore those windows to prevent failured
127         * in the code.
128  int       */
129  PTD_is_used (void)      shell_traywnd = FindWindowEx (NULL, NULL, "Shell_TrayWnd", NULL);
130  {      rebar_w32 = FindWindowEx (shell_traywnd, NULL, "ReBarWindow32", NULL);
131      return shell_traywnd && cbt_hook;      mstask_swc = FindWindowEx (rebar_w32, NULL, "MSTaskSwWClass", NULL);
132  } /* PTD_is_used */      systab_c32 = FindWindowEx (mstask_swc, NULL, "SysTabControl32", NULL);
133        
134        /*log_foo ("tray_proc_id=%u cbt_hook=%p shell_traywnd=%p rebar_w32=%p "
135  LRESULT CALLBACK                 "mstask_swc=%p systab_c32=%p",
136  PTD_playback_proc (int code, WPARAM wparam, LPARAM lparam)                 tray_proc_id, cbt_hook, shell_traywnd, rebar_w32,
137  {                 mstask_swc, systab_c32);*/
138      LPEVENTMSG em;      
139            return TRUE;
140      if (code == HC_SKIP) {  }
141          key_idx++;  
142          if (key_idx == nkeys) {  
143              UnhookWindowsHookEx (journ_hook);  /* Remove the CTB hook from the system and reset all variables. */
144              journ_hook = NULL;  extern "C" void
145          }  PTD_delete (void)
146          return 0;  {
147      }      if (!cbt_hook)
148      else if (code == HC_GETNEXT) {          return;
149          /* Here is an overview what the event message struct can contain:      UnhookWindowsHookEx (cbt_hook);
150           * message - WM_KEYUP, WM_KEYDOWN, WM_SYSKEYUP, WM_SYSKEYDOWN:      cbt_hook = NULL;
151           * paramL - specifies the virtual key code of the key that was pressed.      shell_traywnd = NULL;
152           * paramH - specifies the scan code.                                  tray_proc_id = 0;
153           */  }
154          em = (LPEVENTMSG )lparam;  
155          if (journ_keys[key_idx] & 0x8000)  
156              em->message = journ_keys[key_idx] & 0x4000 ? WM_SYSKEYDOWN : WM_KEYDOWN;  /* Return if the CTB hook is currently used. */
157          else  extern "C" int
158              em->message = journ_keys[key_idx] & 0x4000 ? WM_SYSKEYUP : WM_KEYUP;  PTD_is_used (void)
159          em->paramL = LOBYTE( journ_keys[key_idx] )  {
160              | (MapVirtualKey (LOBYTE (journ_keys[key_idx]), 0) << 8);      return shell_traywnd && cbt_hook;
161          em->paramH = 1;  }
162          em->time = GetTickCount ();  
163          return 0;  
164      }  static LRESULT CALLBACK
165        PTD_playback_proc (int code, WPARAM wparam, LPARAM lparam)
166      return CallNextHookEx (journ_hook, code, wparam, lparam);  {
167  } /* PTD_Playback_proc */      LPEVENTMSG em;
168        
169        if (code == HC_SKIP) {
170  BOOL          key_idx++;
171  PTD_keyb_send (UINT * keys, UINT n_keys)          if (key_idx == nkeys) {
172  {              UnhookWindowsHookEx (journ_hook);
173      MSG msg;              journ_hook = NULL;
174            }
175      journ_keys = keys;          return 0;
176      key_idx = 0;      }
177      nkeys =  n_keys;          else if (code == HC_GETNEXT) {
178                /* Here is an overview what the event message struct can contain:
179      if (journ_hook)           * message - WM_KEYUP, WM_KEYDOWN, WM_SYSKEYUP, WM_SYSKEYDOWN:
180          return FALSE;           * paramL - specifies the virtual key code of the key that was pressed.
181                 * paramH - specifies the scan code.                            
182      while (GetAsyncKeyState (VK_MENU) & 0x8000           */
183              || GetAsyncKeyState (VK_SHIFT) & 0x8000          em = (LPEVENTMSG )lparam;
184              || GetAsyncKeyState (VK_CONTROL) & 0x8000) {          if (journ_keys[key_idx] & 0x8000)
185          if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) {              em->message = journ_keys[key_idx] & 0x4000 ? WM_SYSKEYDOWN : WM_KEYDOWN;
186              if (msg.message == WM_QUIT) {          else
187                  PostMessage (msg.hwnd, msg.message, msg.wParam, msg.lParam);              em->message = journ_keys[key_idx] & 0x4000 ? WM_SYSKEYUP : WM_KEYUP;
188                  return FALSE;          em->paramL = LOBYTE( journ_keys[key_idx] )
189              }              | (MapVirtualKey (LOBYTE (journ_keys[key_idx]), 0) << 8);
190              TranslateMessage (&msg);          em->paramH = 1;
191              DispatchMessage (&msg);          em->time = GetTickCount ();
192          }          return 0;
193      }      }
194      journ_hook = SetWindowsHookEx (WH_JOURNALPLAYBACK,      
195                                     (HOOKPROC)PTD_playback_proc,      return CallNextHookEx (journ_hook, code, wparam, lparam);
196                                     glob_hinst, 0);  } /* PTD_Playback_proc */
197      if (journ_hook == NULL)  
198          return FALSE;  
199        
200      while (journ_hook) {  extern "C" BOOL
201          if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) {  PTD_keyb_send (UINT *keys, UINT n_keys)
202              if (msg.message == WM_QUIT) {  {
203                  if (journ_hook)      MSG msg;
204                      UnhookWindowsHookEx (journ_hook);      journ_keys = keys;
205                  PostMessage (msg.hwnd, msg.message, msg.wParam, msg.wParam);      key_idx = 0;
206              }      nkeys =  n_keys;    
207              TranslateMessage (&msg);      
208              DispatchMessage (&msg);      if (journ_hook)
209          }          return FALSE;
210      }      
211            while (GetAsyncKeyState (VK_MENU) & 0x8000
212      return TRUE;              || GetAsyncKeyState (VK_SHIFT) & 0x8000
213  } /* PTD_keyb_send */              || GetAsyncKeyState (VK_CONTROL) & 0x8000) {
214            if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) {
215                if (msg.message == WM_QUIT) {
216  const char *                  PostMessage (msg.hwnd, msg.message, msg.wParam, msg.lParam);
217  PTD_get_version (void)                  return FALSE;
218  {              }
219      return "0.8.0";              TranslateMessage (&msg);
220  } /* PTD_get_version */              DispatchMessage (&msg);
221            }
222                        }
223  BOOL WINAPI      journ_hook = SetWindowsHookEx (WH_JOURNALPLAYBACK,
224  DllMain (HINSTANCE hinst, DWORD reason, LPVOID reserv)                                     (HOOKPROC)PTD_playback_proc,
225  {                                     glob_hinst, 0);
226      switch (reason)  {      if (journ_hook == NULL)
227      case DLL_PROCESS_ATTACH:          return FALSE;
228          glob_hinst = hinst;      
229          break;      while (journ_hook) {
230      case DLL_THREAD_ATTACH:            if (PeekMessage (&msg, NULL, 0, 0, PM_REMOVE)) {
231          break;              if (msg.message == WM_QUIT) {
232      case DLL_THREAD_DETACH:                    if (journ_hook)
233          break;                      UnhookWindowsHookEx (journ_hook);
234      case DLL_PROCESS_DETACH:                  PostMessage (msg.hwnd, msg.message, msg.wParam, msg.wParam);
235          break;              }
236      }              TranslateMessage (&msg);
237      return TRUE;              DispatchMessage (&msg);
238  } /* DllMain */          }
239        }
240        
241        return TRUE;
242    }
243    
244    
245    /* Display a JPG picture in the given window at the given point. */
246    extern "C" int
247    PTD_jpg_show (HWND hwnd, POINT *p, LPCSTR name)
248    {
249        CJPG jpg;
250        HDC hdc;
251        POINT p2;
252        BOOL rc;
253    
254        rc = jpg.load (name);
255        if (!rc)
256            return -1; /* XXX: use real return code. */
257        hdc = GetWindowDC (hwnd);
258        rc = jpg.updateSizeOnDC (hdc);
259        if (!rc) {
260            ReleaseDC (hwnd, hdc);
261            return -2; /* XXX: use real return code. */
262        }
263    
264        p2.x = jpg.m_Width;
265        p2.y = jpg.m_Height;
266        rc = jpg.show (hdc, p, &p2, 0, 0);
267    
268        ReleaseDC (hwnd, hdc);
269        jpg.freePictureData ();
270        return rc;
271    }
272    
273    
274                    
275    extern "C" int WINAPI
276    DllMain (HINSTANCE hinst, DWORD reason, LPVOID reserv)
277    {
278        switch (reason)  {
279        case DLL_PROCESS_ATTACH:
280            glob_hinst = hinst;
281            break;
282        case DLL_THREAD_ATTACH:  
283            break;
284        case DLL_THREAD_DETACH:  
285            break;
286        case DLL_PROCESS_DETACH:
287            break;
288        }
289        return TRUE;
290    }
291    

Legend:
Removed from v.2  
changed lines
  Added in v.61

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26