Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

527 lines
18 KiB

  1. /*++
  2. Copyright (c) 1990-1998 Microsoft Corporation, All Rights Reserved
  3. Module Name:
  4. UISTATE.C
  5. ++*/
  6. /**********************************************************************/
  7. #include "windows.h"
  8. #include "immdev.h"
  9. #include "fakeime.h"
  10. #include "resource.h"
  11. /**********************************************************************/
  12. /* */
  13. /* StatusWndProc() */
  14. /* IME UI window procedure */
  15. /* */
  16. /**********************************************************************/
  17. LRESULT CALLBACK StatusWndProc( hWnd, message, wParam, lParam )
  18. HWND hWnd;
  19. UINT message;
  20. WPARAM wParam;
  21. LPARAM lParam;
  22. {
  23. PAINTSTRUCT ps;
  24. HWND hUIWnd;
  25. HDC hDC;
  26. HBITMAP hbmpStatus;
  27. switch (message)
  28. {
  29. case WM_UI_UPDATE:
  30. InvalidateRect(hWnd,NULL,FALSE);
  31. break;
  32. case WM_PAINT:
  33. hDC = BeginPaint(hWnd,&ps);
  34. PaintStatus(hWnd,hDC,NULL,0);
  35. EndPaint(hWnd,&ps);
  36. break;
  37. case WM_MOUSEMOVE:
  38. case WM_SETCURSOR:
  39. case WM_LBUTTONUP:
  40. case WM_RBUTTONUP:
  41. ButtonStatus(hWnd,message,wParam,lParam);
  42. if ((message == WM_SETCURSOR) &&
  43. (HIWORD(lParam) != WM_LBUTTONDOWN) &&
  44. (HIWORD(lParam) != WM_RBUTTONDOWN))
  45. return DefWindowProc(hWnd,message,wParam,lParam);
  46. if ((message == WM_LBUTTONUP) || (message == WM_RBUTTONUP))
  47. {
  48. SetWindowLong(hWnd,FIGWL_MOUSE,0L);
  49. SetWindowLong(hWnd,FIGWL_PUSHSTATUS,0L);
  50. }
  51. break;
  52. case WM_MOVE:
  53. hUIWnd = (HWND)GetWindowLongPtr(hWnd,FIGWL_SVRWND);
  54. if (IsWindow(hUIWnd))
  55. SendMessage(hUIWnd,WM_UI_STATEMOVE,wParam,lParam);
  56. break;
  57. case WM_CREATE:
  58. hbmpStatus = LoadBitmap(hInst,TEXT("STATUSBMP"));
  59. SetWindowLongPtr(hWnd,FIGWL_STATUSBMP,(LONG_PTR)hbmpStatus);
  60. hbmpStatus = LoadBitmap(hInst,TEXT("CLOSEBMP"));
  61. SetWindowLongPtr(hWnd,FIGWL_CLOSEBMP,(LONG_PTR)hbmpStatus);
  62. break;
  63. case WM_DESTROY:
  64. hbmpStatus = (HBITMAP)GetWindowLongPtr(hWnd,FIGWL_STATUSBMP);
  65. DeleteObject(hbmpStatus);
  66. hbmpStatus = (HBITMAP)GetWindowLongPtr(hWnd,FIGWL_CLOSEBMP);
  67. DeleteObject(hbmpStatus);
  68. break;
  69. default:
  70. if (!MyIsIMEMessage(message))
  71. return DefWindowProc(hWnd,message,wParam,lParam);
  72. break;
  73. }
  74. return 0;
  75. }
  76. /**********************************************************************/
  77. /* */
  78. /* CheckPushedStatus() */
  79. /* */
  80. /**********************************************************************/
  81. DWORD PASCAL CheckPushedStatus( HWND hStatusWnd, LPPOINT lppt)
  82. {
  83. POINT pt;
  84. RECT rc;
  85. if (lppt)
  86. {
  87. pt = *lppt;
  88. ScreenToClient(hStatusWnd,&pt);
  89. GetClientRect(hStatusWnd,&rc);
  90. if (!PtInRect(&rc,pt))
  91. return 0;
  92. if (pt.y > GetSystemMetrics(SM_CYSMCAPTION))
  93. {
  94. if (pt.x < BTX)
  95. return PUSHED_STATUS_HDR;
  96. else if (pt.x < (BTX * 2))
  97. return PUSHED_STATUS_MODE;
  98. else if (pt.x < (BTX * 3))
  99. return PUSHED_STATUS_ROMAN;
  100. }
  101. else
  102. {
  103. rc.left = STCLBT_X;
  104. rc.top = STCLBT_Y;
  105. rc.right = STCLBT_X + STCLBT_DX;
  106. rc.bottom = STCLBT_Y + STCLBT_DY;
  107. if (PtInRect(&rc,pt))
  108. return PUSHED_STATUS_CLOSE;
  109. }
  110. }
  111. return 0;
  112. }
  113. /**********************************************************************/
  114. /* */
  115. /* BTXFromCmode() */
  116. /* */
  117. /**********************************************************************/
  118. int PASCAL BTXFromCmode( DWORD dwCmode)
  119. {
  120. if (dwCmode & IME_CMODE_FULLSHAPE)
  121. {
  122. if (!(dwCmode & IME_CMODE_LANGUAGE))
  123. return BTFALPH;
  124. else if ((dwCmode & IME_CMODE_LANGUAGE) == IME_CMODE_NATIVE)
  125. return BTFHIRA;
  126. else
  127. return BTFKATA;
  128. }
  129. else
  130. {
  131. if ((dwCmode & IME_CMODE_LANGUAGE) == IME_CMODE_ALPHANUMERIC)
  132. return BTHALPH;
  133. else
  134. return BTHKATA;
  135. }
  136. }
  137. /**********************************************************************/
  138. /* */
  139. /* PaintStatus() */
  140. /* */
  141. /**********************************************************************/
  142. void PASCAL PaintStatus( HWND hStatusWnd , HDC hDC, LPPOINT lppt, DWORD dwPushedStatus)
  143. {
  144. HIMC hIMC;
  145. LPINPUTCONTEXT lpIMC;
  146. HDC hMemDC;
  147. HBITMAP hbmpOld;
  148. int x;
  149. HWND hSvrWnd;
  150. hSvrWnd = (HWND)GetWindowLongPtr(hStatusWnd,FIGWL_SVRWND);
  151. if (hIMC = (HIMC)GetWindowLongPtr(hSvrWnd,IMMGWLP_IMC))
  152. {
  153. HBITMAP hbmpStatus;
  154. HBRUSH hOldBrush,hBrush;
  155. int nCyCap = GetSystemMetrics(SM_CYSMCAPTION);
  156. RECT rc;
  157. lpIMC = ImmLockIMC(hIMC);
  158. hMemDC = CreateCompatibleDC(hDC);
  159. // Paint Caption.
  160. hBrush = CreateSolidBrush(GetSysColor(COLOR_ACTIVECAPTION));
  161. hOldBrush = SelectObject(hDC,hBrush);
  162. rc.top = rc.left = 0;
  163. rc.right = BTX*3;
  164. rc.bottom = nCyCap;
  165. FillRect(hDC,&rc,hBrush);
  166. SelectObject(hDC,hOldBrush);
  167. DeleteObject(hBrush);
  168. // Paint CloseButton.
  169. hbmpStatus = (HBITMAP)GetWindowLongPtr(hStatusWnd,FIGWL_CLOSEBMP);
  170. hbmpOld = SelectObject(hMemDC,hbmpStatus);
  171. if (!(dwPushedStatus & PUSHED_STATUS_CLOSE))
  172. BitBlt(hDC,STCLBT_X,STCLBT_Y,STCLBT_DX,STCLBT_DY,
  173. hMemDC,0,0,SRCCOPY);
  174. else
  175. BitBlt(hDC,STCLBT_X,STCLBT_Y,STCLBT_DX,STCLBT_DY,
  176. hMemDC,STCLBT_DX,0,SRCCOPY);
  177. hbmpStatus = (HBITMAP)GetWindowLongPtr(hStatusWnd,FIGWL_STATUSBMP);
  178. SelectObject(hMemDC,hbmpStatus);
  179. // Paint HDR.
  180. x = BTEMPT;
  181. if (lpIMC->fOpen)
  182. x = 0;
  183. if (!(dwPushedStatus & PUSHED_STATUS_HDR))
  184. BitBlt(hDC,0,nCyCap,BTX,BTY,hMemDC,x,0,SRCCOPY);
  185. else
  186. BitBlt(hDC,0,nCyCap,BTX,BTY,hMemDC,x,BTY,SRCCOPY);
  187. // Paint MODE.
  188. x = BTXFromCmode(lpIMC->fdwConversion);
  189. if (!(dwPushedStatus & PUSHED_STATUS_MODE))
  190. BitBlt(hDC,BTX,nCyCap,BTX,BTY,hMemDC,x,0,SRCCOPY);
  191. else
  192. BitBlt(hDC,BTX,nCyCap,BTX,BTY,hMemDC,x,BTY,SRCCOPY);
  193. // Paint Roman MODE.
  194. x = BTEMPT;
  195. if (lpIMC->fdwConversion & IME_CMODE_ROMAN)
  196. x = BTROMA;
  197. if (!(dwPushedStatus & PUSHED_STATUS_ROMAN))
  198. BitBlt(hDC,BTX*2,nCyCap,BTX,BTY,hMemDC,x,0,SRCCOPY);
  199. else
  200. BitBlt(hDC,BTX*2,nCyCap,BTX,BTY,hMemDC,x,BTY,SRCCOPY);
  201. SelectObject(hMemDC,hbmpOld);
  202. DeleteDC(hMemDC);
  203. ImmUnlockIMC(hIMC);
  204. }
  205. }
  206. /**********************************************************************/
  207. /* */
  208. /* GetUINextMode(hWnd,message,wParam,lParam) */
  209. /* */
  210. /**********************************************************************/
  211. DWORD PASCAL GetUINextMode( DWORD fdwConversion, DWORD dwPushed)
  212. {
  213. DWORD dwTemp;
  214. BOOL fFullShape = ((fdwConversion & IME_CMODE_FULLSHAPE) != 0);
  215. //
  216. // When the mode button is pushed, the convmode will be chage as follow
  217. // rotation.
  218. //
  219. // FULLSHAPE,HIRAGANA ->
  220. // FULLSHAPE,KATAKANA ->
  221. // FULLSHAPE,ALPHANUMERIC ->
  222. // HALFSHAPE,KATAKANA ->
  223. // HALFSHAPE,ALPHANUMERIC ->
  224. // FULLSHAPE,HIRAGANA
  225. //
  226. if (dwPushed == PUSHED_STATUS_MODE)
  227. {
  228. dwTemp = fdwConversion & IME_CMODE_LANGUAGE;
  229. if ((fFullShape) && (dwTemp == IME_CMODE_NATIVE))
  230. return (fdwConversion & ~IME_CMODE_LANGUAGE) | IME_CMODE_KATAKANA | IME_CMODE_NATIVE;
  231. if ((fFullShape) && (dwTemp == (IME_CMODE_KATAKANA | IME_CMODE_NATIVE)))
  232. return (fdwConversion & ~IME_CMODE_LANGUAGE);
  233. if ((fFullShape) && (dwTemp == 0))
  234. {
  235. fdwConversion &= ~IME_CMODE_FULLSHAPE;
  236. return (fdwConversion & ~IME_CMODE_LANGUAGE)
  237. | IME_CMODE_KATAKANA | IME_CMODE_NATIVE;
  238. }
  239. if ((!fFullShape) && (dwTemp == (IME_CMODE_KATAKANA | IME_CMODE_NATIVE)))
  240. return (fdwConversion & ~IME_CMODE_LANGUAGE);
  241. if ((!fFullShape) && (!dwTemp))
  242. {
  243. fdwConversion |= IME_CMODE_FULLSHAPE;
  244. return (fdwConversion & ~IME_CMODE_LANGUAGE) | IME_CMODE_NATIVE;
  245. }
  246. }
  247. if (dwPushed == PUSHED_STATUS_ROMAN)
  248. {
  249. if (fdwConversion & IME_CMODE_ROMAN)
  250. return fdwConversion & ~IME_CMODE_ROMAN;
  251. else
  252. return fdwConversion | IME_CMODE_ROMAN;
  253. }
  254. return fdwConversion;
  255. }
  256. /**********************************************************************/
  257. /* */
  258. /* ButtonStatus(hStatusWnd,message,wParam,lParam) */
  259. /* */
  260. /**********************************************************************/
  261. void PASCAL ButtonStatus( HWND hStatusWnd, UINT message, WPARAM wParam, LPARAM lParam)
  262. {
  263. POINT pt;
  264. HDC hDC;
  265. DWORD dwMouse;
  266. DWORD dwPushedStatus;
  267. DWORD dwTemp;
  268. DWORD fdwConversion;
  269. HIMC hIMC;
  270. HWND hSvrWnd;
  271. BOOL fOpen;
  272. HMENU hMenu;
  273. static POINT ptdif;
  274. static RECT drc;
  275. static RECT rc;
  276. static DWORD dwCurrentPushedStatus;
  277. hDC = GetDC(hStatusWnd);
  278. switch (message)
  279. {
  280. case WM_SETCURSOR:
  281. if ( HIWORD(lParam) == WM_LBUTTONDOWN
  282. || HIWORD(lParam) == WM_RBUTTONDOWN )
  283. {
  284. GetCursorPos( &pt );
  285. SetCapture(hStatusWnd);
  286. GetWindowRect(hStatusWnd,&drc);
  287. ptdif.x = pt.x - drc.left;
  288. ptdif.y = pt.y - drc.top;
  289. rc = drc;
  290. rc.right -= rc.left;
  291. rc.bottom -= rc.top;
  292. SetWindowLong(hStatusWnd,FIGWL_MOUSE,FIM_CAPUTURED);
  293. SetWindowLong(hStatusWnd, FIGWL_PUSHSTATUS, dwPushedStatus = CheckPushedStatus(hStatusWnd,&pt));
  294. PaintStatus(hStatusWnd,hDC,&pt, dwPushedStatus);
  295. dwCurrentPushedStatus = dwPushedStatus;
  296. }
  297. break;
  298. case WM_MOUSEMOVE:
  299. dwMouse = GetWindowLong(hStatusWnd,FIGWL_MOUSE);
  300. if (!(dwPushedStatus = GetWindowLong(hStatusWnd, FIGWL_PUSHSTATUS)))
  301. {
  302. if (dwMouse & FIM_MOVED)
  303. {
  304. DrawUIBorder(&drc);
  305. GetCursorPos( &pt );
  306. drc.left = pt.x - ptdif.x;
  307. drc.top = pt.y - ptdif.y;
  308. drc.right = drc.left + rc.right;
  309. drc.bottom = drc.top + rc.bottom;
  310. DrawUIBorder(&drc);
  311. }
  312. else if (dwMouse & FIM_CAPUTURED)
  313. {
  314. DrawUIBorder(&drc);
  315. SetWindowLong(hStatusWnd,FIGWL_MOUSE,dwMouse | FIM_MOVED);
  316. }
  317. }
  318. else
  319. {
  320. GetCursorPos(&pt);
  321. dwTemp = CheckPushedStatus(hStatusWnd,&pt);
  322. if ((dwTemp ^ dwCurrentPushedStatus) & dwPushedStatus)
  323. PaintStatus(hStatusWnd,hDC,&pt, dwPushedStatus & dwTemp);
  324. dwCurrentPushedStatus = dwTemp;
  325. }
  326. break;
  327. case WM_RBUTTONUP:
  328. dwMouse = GetWindowLong(hStatusWnd,FIGWL_MOUSE);
  329. if (dwMouse & FIM_CAPUTURED)
  330. {
  331. ReleaseCapture();
  332. if (dwMouse & FIM_MOVED)
  333. {
  334. DrawUIBorder(&drc);
  335. GetCursorPos( &pt );
  336. MoveWindow(hStatusWnd,pt.x - ptdif.x,
  337. pt.y - ptdif.y,
  338. rc.right,
  339. rc.bottom,TRUE);
  340. }
  341. }
  342. PaintStatus(hStatusWnd,hDC,NULL,0);
  343. hSvrWnd = (HWND)GetWindowLongPtr(hStatusWnd,FIGWL_SVRWND);
  344. hMenu = LoadMenu(hInst, TEXT("RIGHTCLKMENU"));
  345. if (hMenu && (hIMC = (HIMC)GetWindowLongPtr(hSvrWnd,IMMGWLP_IMC)))
  346. {
  347. int cmd;
  348. HMENU hSubMenu = GetSubMenu(hMenu, 0);
  349. pt.x = (int)LOWORD(lParam),
  350. pt.y = (int)HIWORD(lParam),
  351. ClientToScreen(hStatusWnd, &pt);
  352. cmd = TrackPopupMenu(hSubMenu,
  353. TPM_RETURNCMD,
  354. pt.x,
  355. pt.y,
  356. 0,
  357. hStatusWnd,
  358. NULL);
  359. switch (cmd)
  360. {
  361. case IDM_RECONVERT:
  362. {
  363. DWORD dwSize = (DWORD) MyImmRequestMessage(hIMC, IMR_RECONVERTSTRING, 0);
  364. if (dwSize)
  365. {
  366. LPRECONVERTSTRING lpRS;
  367. lpRS = (LPRECONVERTSTRING)GlobalAlloc(GPTR, dwSize);
  368. lpRS->dwSize = dwSize;
  369. if (dwSize = (DWORD) MyImmRequestMessage(hIMC, IMR_RECONVERTSTRING, (LPARAM)lpRS)) {
  370. #ifdef DEBUG
  371. {
  372. TCHAR szDev[80];
  373. LPMYSTR lpDump= (LPMYSTR)(((LPSTR)lpRS) + lpRS->dwStrOffset);
  374. *(LPMYSTR)(lpDump + lpRS->dwStrLen) = MYTEXT('\0');
  375. OutputDebugString(TEXT("IMR_RECONVERTSTRING\r\n"));
  376. wsprintf(szDev, TEXT("dwSize %x\r\n"), lpRS->dwSize);
  377. OutputDebugString(szDev);
  378. wsprintf(szDev, TEXT("dwVersion %x\r\n"), lpRS->dwVersion);
  379. OutputDebugString(szDev);
  380. wsprintf(szDev, TEXT("dwStrLen %x\r\n"), lpRS->dwStrLen);
  381. OutputDebugString(szDev);
  382. wsprintf(szDev, TEXT("dwStrOffset %x\r\n"), lpRS->dwStrOffset);
  383. OutputDebugString(szDev);
  384. wsprintf(szDev, TEXT("dwCompStrLen %x\r\n"), lpRS->dwCompStrLen);
  385. OutputDebugString(szDev);
  386. wsprintf(szDev, TEXT("dwCompStrOffset %x\r\n"), lpRS->dwCompStrOffset);
  387. OutputDebugString(szDev);
  388. wsprintf(szDev, TEXT("dwTargetStrLen %x\r\n"), lpRS->dwTargetStrLen);
  389. OutputDebugString(szDev);
  390. wsprintf(szDev, TEXT("dwTargetStrOffset %x\r\n"), lpRS->dwTargetStrOffset);
  391. OutputDebugString(szDev);
  392. MyOutputDebugString(lpDump);
  393. OutputDebugString(TEXT("\r\n"));
  394. }
  395. #endif
  396. MyImmRequestMessage(hIMC, IMR_CONFIRMRECONVERTSTRING, (LPARAM)lpRS);
  397. }
  398. #ifdef DEBUG
  399. else
  400. OutputDebugString(TEXT("ImmRequestMessage returned 0\r\n"));
  401. #endif
  402. GlobalFree((HANDLE)lpRS);
  403. }
  404. break;
  405. }
  406. case IDM_ABOUT:
  407. ImmConfigureIME(GetKeyboardLayout(0), NULL, IME_CONFIG_GENERAL, 0);
  408. break;
  409. default:
  410. break;
  411. }
  412. }
  413. if (hMenu)
  414. DestroyMenu(hMenu);
  415. break;
  416. case WM_LBUTTONUP:
  417. dwMouse = GetWindowLong(hStatusWnd,FIGWL_MOUSE);
  418. if (dwMouse & FIM_CAPUTURED)
  419. {
  420. ReleaseCapture();
  421. if (dwMouse & FIM_MOVED)
  422. {
  423. DrawUIBorder(&drc);
  424. GetCursorPos( &pt );
  425. MoveWindow(hStatusWnd,pt.x - ptdif.x,
  426. pt.y - ptdif.y,
  427. rc.right,
  428. rc.bottom,TRUE);
  429. }
  430. }
  431. hSvrWnd = (HWND)GetWindowLongPtr(hStatusWnd,FIGWL_SVRWND);
  432. if (hIMC = (HIMC)GetWindowLongPtr(hSvrWnd,IMMGWLP_IMC))
  433. {
  434. GetCursorPos(&pt);
  435. dwPushedStatus = GetWindowLong(hStatusWnd, FIGWL_PUSHSTATUS);
  436. dwPushedStatus &= CheckPushedStatus(hStatusWnd,&pt);
  437. if (!dwPushedStatus) {
  438. } else if (dwPushedStatus == PUSHED_STATUS_CLOSE) {
  439. } else if (dwPushedStatus == PUSHED_STATUS_HDR)
  440. {
  441. fOpen = ImmGetOpenStatus(hIMC);
  442. fOpen = !fOpen;
  443. ImmSetOpenStatus(hIMC,fOpen);
  444. }
  445. else
  446. {
  447. ImmGetConversionStatus(hIMC,&fdwConversion,&dwTemp);
  448. fdwConversion = GetUINextMode(fdwConversion,dwPushedStatus);
  449. ImmSetConversionStatus(hIMC,fdwConversion,dwTemp);
  450. }
  451. }
  452. PaintStatus(hStatusWnd,hDC,NULL,0);
  453. break;
  454. }
  455. ReleaseDC(hStatusWnd,hDC);
  456. }
  457. /**********************************************************************/
  458. /* */
  459. /* UpdateStatusWindow(lpUIExtra) */
  460. /* */
  461. /**********************************************************************/
  462. void PASCAL UpdateStatusWindow(LPUIEXTRA lpUIExtra)
  463. {
  464. if (IsWindow(lpUIExtra->uiStatus.hWnd))
  465. SendMessage(lpUIExtra->uiStatus.hWnd,WM_UI_UPDATE,0,0L);
  466. }