출처: http://ikpil.com/507

2008/07/14 10:08

Virtual-Key Codes : Windows 에서 사용 하는 가상키 코드 리스트

The following table shows the symbolic constant names, hexadecimal values, and mouse or keyboard equivalents for the virtual-key codes used by the system. The codes are listed in numeric order.

Constants

VK_LBUTTON (0x01)
Left mouse button
VK_RBUTTON (0x02)
Right mouse button
VK_CANCEL (0x03)
Control-break processing
VK_MBUTTON (0x04)
Middle mouse button (three-button mouse)
VK_XBUTTON1 (0x05)
Windows 2000/XP: X1 mouse button
VK_XBUTTON2 (0x06)
Windows 2000/XP: X2 mouse button
- (0x07)
Undefined
VK_BACK (0x08)
BACKSPACE key
VK_TAB (0x09)
TAB key
- (0x0A-0B)
Reserved
VK_CLEAR (0x0C)
CLEAR key
VK_RETURN (0x0D)
ENTER key
- (0x0E-0F)
Undefined
VK_SHIFT (0x10)
SHIFT key
VK_CONTROL (0x11)
CTRL key
VK_MENU (0x12)
ALT key
VK_PAUSE (0x13)
PAUSE key
VK_CAPITAL (0x14)
CAPS LOCK key
VK_KANA (0x15)
Input Method Editor (IME) Kana mode
VK_HANGUEL (0x15)
IME Hanguel mode (maintained for compatibility; use VK_HANGUL)
VK_HANGUL (0x15)
IME Hangul mode
- (0x16)
Undefined
VK_JUNJA (0x17)
IME Junja mode
VK_FINAL (0x18)
IME final mode
VK_HANJA (0x19)
IME Hanja mode
VK_KANJI (0x19)
IME Kanji mode
- (0x1A)
Undefined
VK_ESCAPE (0x1B)
ESC key
VK_CONVERT (0x1C)
IME convert
VK_NONCONVERT (0x1D)
IME nonconvert
VK_ACCEPT (0x1E)
IME accept
VK_MODECHANGE (0x1F)
IME mode change request
VK_SPACE (0x20)
SPACEBAR
VK_PRIOR (0x21)
PAGE UP key
VK_NEXT (0x22)
PAGE DOWN key
VK_END (0x23)
END key
VK_HOME (0x24)
HOME key
VK_LEFT (0x25)
LEFT ARROW key
VK_UP (0x26)
UP ARROW key
VK_RIGHT (0x27)
RIGHT ARROW key
VK_DOWN (0x28)
DOWN ARROW key
VK_SELECT (0x29)
SELECT key
VK_PRINT (0x2A)
PRINT key
VK_EXECUTE (0x2B)
EXECUTE key
VK_SNAPSHOT (0x2C)
PRINT SCREEN key
VK_INSERT (0x2D)
INS key
VK_DELETE (0x2E)
DEL key
VK_HELP (0x2F)
HELP key
 (0x30)
0 key
 (0x31)
1 key
 (0x32)
2 key
 (0x33)
3 key
 (0x34)
4 key
 (0x35)
5 key
 (0x36)
6 key
 (0x37)
7 key
 (0x38)
8 key
 (0x39)
9 key
- (0x3A-40)
Undefined
 (0x41)
A key
 (0x42)
B key
 (0x43)
C key
 (0x44)
D key
 (0x45)
E key
 (0x46)
F key
 (0x47)
G key
 (0x48)
H key
 (0x49)
I key
 (0x4A)
J key
 (0x4B)
K key
 (0x4C)
L key
 (0x4D)
M key
 (0x4E)
N key
 (0x4F)
O key
 (0x50)
P key
 (0x51)
Q key
 (0x52)
R key
 (0x53)
S key
 (0x54)
T key
 (0x55)
U key
 (0x56)
V key
 (0x57)
W key
 (0x58)
X key
 (0x59)
Y key
 (0x5A)
Z key
VK_LWIN (0x5B)
Left Windows key (Microsoft Natural keyboard)
VK_RWIN (0x5C)
Right Windows key (Natural keyboard)
VK_APPS (0x5D)
Applications key (Natural keyboard)
- (0x5E)
Reserved
VK_SLEEP (0x5F)
Computer Sleep key
VK_NUMPAD0 (0x60)
Numeric keypad 0 key
VK_NUMPAD1 (0x61)
Numeric keypad 1 key
VK_NUMPAD2 (0x62)
Numeric keypad 2 key
VK_NUMPAD3 (0x63)
Numeric keypad 3 key
VK_NUMPAD4 (0x64)
Numeric keypad 4 key
VK_NUMPAD5 (0x65)
Numeric keypad 5 key
VK_NUMPAD6 (0x66)
Numeric keypad 6 key
VK_NUMPAD7 (0x67)
Numeric keypad 7 key
VK_NUMPAD8 (0x68)
Numeric keypad 8 key
VK_NUMPAD9 (0x69)
Numeric keypad 9 key
VK_MULTIPLY (0x6A)
Multiply key
VK_ADD (0x6B)
Add key
VK_SEPARATOR (0x6C)
Separator key
VK_SUBTRACT (0x6D)
Subtract key
VK_DECIMAL (0x6E)
Decimal key
VK_DIVIDE (0x6F)
Divide key
VK_F1 (0x70)
F1 key
VK_F2 (0x71)
F2 key
VK_F3 (0x72)
F3 key
VK_F4 (0x73)
F4 key
VK_F5 (0x74)
F5 key
VK_F6 (0x75)
F6 key
VK_F7 (0x76)
F7 key
VK_F8 (0x77)
F8 key
VK_F9 (0x78)
F9 key
VK_F10 (0x79)
F10 key
VK_F11 (0x7A)
F11 key
VK_F12 (0x7B)
F12 key
VK_F13 (0x7C)
F13 key
VK_F14 (0x7D)
F14 key
VK_F15 (0x7E)
F15 key
VK_F16 (0x7F)
F16 key
VK_F17 (0x80H)
F17 key
VK_F18 (0x81H)
F18 key
VK_F19 (0x82H)
F19 key
VK_F20 (0x83H)
F20 key
VK_F21 (0x84H)
F21 key
VK_F22 (0x85H)
F22 key
VK_F23 (0x86H)
F23 key
VK_F24 (0x87H)
F24 key
- (0x88-8F)
Unassigned
VK_NUMLOCK (0x90)
NUM LOCK key
VK_SCROLL (0x91)
SCROLL LOCK key
 (0x92-96)
OEM specific
- (0x97-9F)
Unassigned
VK_LSHIFT (0xA0)
Left SHIFT key
VK_RSHIFT (0xA1)
Right SHIFT key
VK_LCONTROL (0xA2)
Left CONTROL key
VK_RCONTROL (0xA3)
Right CONTROL key
VK_LMENU (0xA4)
Left MENU key
VK_RMENU (0xA5)
Right MENU key
VK_BROWSER_BACK (0xA6)
Windows 2000/XP: Browser Back key
VK_BROWSER_FORWARD (0xA7)
Windows 2000/XP: Browser Forward key
VK_BROWSER_REFRESH (0xA8)
Windows 2000/XP: Browser Refresh key
VK_BROWSER_STOP (0xA9)
Windows 2000/XP: Browser Stop key
VK_BROWSER_SEARCH (0xAA)
Windows 2000/XP: Browser Search key
VK_BROWSER_FAVORITES (0xAB)
Windows 2000/XP: Browser Favorites key
VK_BROWSER_HOME (0xAC)
Windows 2000/XP: Browser Start and Home key
VK_VOLUME_MUTE (0xAD)
Windows 2000/XP: Volume Mute key
VK_VOLUME_DOWN (0xAE)
Windows 2000/XP: Volume Down key
VK_VOLUME_UP (0xAF)
Windows 2000/XP: Volume Up key
VK_MEDIA_NEXT_TRACK (0xB0)
Windows 2000/XP: Next Track key
VK_MEDIA_PREV_TRACK (0xB1)
Windows 2000/XP: Previous Track key
VK_MEDIA_STOP (0xB2)
Windows 2000/XP: Stop Media key
VK_MEDIA_PLAY_PAUSE (0xB3)
Windows 2000/XP: Play/Pause Media key
VK_LAUNCH_MAIL (0xB4)
Windows 2000/XP: Start Mail key
VK_LAUNCH_MEDIA_SELECT (0xB5)
Windows 2000/XP: Select Media key
VK_LAUNCH_APP1 (0xB6)
Windows 2000/XP: Start Application 1 key
VK_LAUNCH_APP2 (0xB7)
Windows 2000/XP: Start Application 2 key
- (0xB8-B9)
Reserved
VK_OEM_1 (0xBA)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the ';:' key

VK_OEM_PLUS (0xBB)
Windows 2000/XP: For any country/region, the '+' key
VK_OEM_COMMA (0xBC)
Windows 2000/XP: For any country/region, the ',' key
VK_OEM_MINUS (0xBD)
Windows 2000/XP: For any country/region, the '-' key
VK_OEM_PERIOD (0xBE)
Windows 2000/XP: For any country/region, the '.' key
VK_OEM_2 (0xBF)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the '/?' key

VK_OEM_3 (0xC0)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the '`~' key

- (0xC1-D7)
Reserved
- (0xD8-DA)
Unassigned
VK_OEM_4 (0xDB)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the '[{' key

VK_OEM_5 (0xDC)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the '\|' key

VK_OEM_6 (0xDD)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the ']}' key

VK_OEM_7 (0xDE)
Used for miscellaneous characters; it can vary by keyboard.

Windows 2000/XP: For the US standard keyboard, the 'single-quote/double-quote' key

VK_OEM_8 (0xDF)
Used for miscellaneous characters; it can vary by keyboard.
- (0xE0)
Reserved
 (0xE1)
OEM specific
VK_OEM_102 (0xE2)
Windows 2000/XP: Either the angle bracket key or the backslash key on the RT 102-key keyboard
 (0xE3-E4)
OEM specific
VK_PROCESSKEY (0xE5)
Windows 95/98/Me, Windows NT 4.0, Windows 2000/XP: IME PROCESS key
 (0xE6)
OEM specific
VK_PACKET (0xE7)
Windows 2000/XP: Used to pass Unicode characters as if they were keystrokes. The VK_PACKET key is the low word of a 32-bit Virtual Key value used for non-keyboard input methods. For more information, see Remark in KEYBDINPUT, SendInput, WM_KEYDOWN, and WM_KEYUP
- (0xE8)
Unassigned
 (0xE9-F5)
OEM specific
VK_ATTN (0xF6)
Attn key
VK_CRSEL (0xF7)
CrSel key
VK_EXSEL (0xF8)
ExSel key
VK_EREOF (0xF9)
Erase EOF key
VK_PLAY (0xFA)
Play key
VK_ZOOM (0xFB)
Zoom key
VK_NONAME (0xFC)
Reserved
VK_PA1 (0xFD)
PA1 key
VK_OEM_CLEAR (0xFE)
Clear key



AND

출처 : http://blog.naver.com/skycho71?Redirect=Log&logNo=20019748703


베트남어 입력하기(Unikey.exe) 베트남 언어

2005/11/30 15:50

복사 http://blog.naver.com/skycho71/20019748703

이 포스트를 보낸곳 (1) 첨부파일 (1)

베트남어 입력하기

 

베트남어를 사용하기 위해서는 별도의 프로그램이 필요합니다.

1. unikey.zip 파일을 Download 한다. 

2. unikey.zip 파일의 압축을 푼다.


3. UniKey.exe 파일을 실행한다.


 


4. Expand 버튼을 클릭하여 아래 그림과 같이 체크한다.


 


※ Auto-run UniKey at boot time 을 체크하면 부팅될 때 자동 실행된다.

5. Task bar를 클릭하면 오른쪽 밑쪽에(트레이 아이콘) “E"가 표시된다. 

6. 입력창(웹상에서나 문서 편집기)에서 베트남을 입력하고자 할 때는 CTRL + Shift Key를 동시에 눌러서 트레이 아이콘이 “V"로 바꿨고 베트남어를 입력하면 된다. 


 베트남어 성조 입력하기


1. 베트남어에서 사용 되는 성조는 아래와 같이 다양하게 조합할 수 있다.

숫자

1

2

3

4

5

6

7

8

9

영문자

A

Á

À

Ã

Â

 

Ă

 

E

É

È

Ê

 

 

 

I

Í

Ì

Ĩ

 

 

 

 

O

Ó

Ò

Õ

Ô

Ơ

 

 

U

Ú

Ù

Ũ

 

Ư

 

 

Y

Ý

 

 

 

 

D

 

 

 

 

 

 

 

 

Đ

※ 위의 숫자를 두 개 조합하여 입력 할 수도 있다. 예) Ấ, Ầ, Ẩ, Ậ,…

 

[대한민국대표 베트남 정보채널 브이엔뉴스(WWW.VNNEWS.CO.KR)]



AND

출처: http://blog.naver.com/sunrise7410?Redirect=Log&logNo=10031926353


 
[Tip!]키보드로 베트남어 타이핑하자② 베트남어공부중

2008/06/08 20:56

복사 http://blog.naver.com/sunrise7410/10031926353

이 포스트를 보낸곳 (1)

 

①"1,2,3,4,[,]를 쳤을 때

1

2

3

4

5

6

7

8

9

[

]

ă

â

ê

ô

 

 

 

 

 

ư

ơ

 

 

②a,o,e등의 알파벳을 치고 5,6,7,8,9를 쳤을 때(대소문자상관 없어요^^)

 

1

2

3

4

5

6

7

8

9

[

]

a

 

 

 

 

 

 

o

 

 

 

 

 

 

e

 

 

 

 

 

 

 

 

예를 들면~

 

Tôi là Hee-Ju. 나는 희주입니다.

 

Tôi  나는

는 3을 누르면 됩니다

Là  ~이다

*àa를 누르고 5를 누르면 됩니다

 

 

 

 




AND

출처: http://blog.naver.com/asdq1684/80017478544


베트남어 폰트 키보드 입력 프로그램 베트남언어,사이트

2005/09/17 09:55

복사 http://blog.naver.com/asdq1684/80017478544

베트남어 폰트 키보드입력프로그램 클릭하시면 다운로드 됩니다.

 

 

설치방법

1. 폰트를 다운 받으신후 압축을 풀고 폰트파일들을 windows 폴더안의 fonts폴더에 복사해서 넣습니다.
2.키보드입력프로그램을 다운받아 압축을 푼 후 UniKey.exe를 실행합니다.
영어 베트남어 변환 단축키를 Alt+Z로 설정하고 확인을 누르세요.
그러면 오른쪽 제일 아래 부분에 Alt+Z 누를때 마다 영어 또는 베트남어로 입력상태 표시가 나타날겁니다.
컴터 껐다가 다시 켤 경우에 UniKey.exe프로그램이 자동으로 실행되지 않으므로 베트남어 입력할 경우에는 UniKey.exe를 실행해야 합니다.
3. 이제 웹상에서 베트남어를 보기 위해 설정이 필요합니다.
브라우져를 띠우고 '도구'클릭/'인터넷옵션'/제일아래쪽의 '언어' 클릭/'추가'클릭/베트남어 선택후 확인을 누릅니다.
4.이제 모든 창을 닫고 브라우져를 띠우고 베트남어 표기가 된 사이트에 들어가 보세요.
성조 제대로 표기되면 OK!.

이렇게 해도 안되시는 분은 이렇게도 해보세요.
5. 시작/설정/제어판/키보드/입력로케일/추가/베트남어 추가 하시구요.
6.시작/설정/제어판/국가별옵션/시스템언어설정/ 베트남어가 선택되어져 있는지 확인하세요. 없으면 선택해야 하구요.
7.브라우저에서 보기/인코딩/ 자동선택 하세요.
8 .한.베 까페에서 글쓰기클릭/쓰기선택/ HTML편집기(이미지 삽입)에 체크 하신후
베트남어 입력 하면 되네요.

글자 색깔이나 크기는 강조하고 싶은 부분에서 왼쪽마우스 클릭한체로 죽~~~ 선택한후에
입력부분 제일 위에 있는 글씨색깔이나 크기를 선택 하면 됩니다.

사용방법
*모음글자 a,e,o는 두 번 치면 글자위에 삿갓부호 ^가 조합된다.
*모음글자 a를 치고 W를 누르면 글자 위에 ˇ모양의 부호가 조합된다.
*U를 치고 W를 이어서 치면 자동으로 U와 부호 '가 U'로 된다.
*성조부호는 위의 모음글자와 부호 다음에 이어서 치면 자동으로
조합되서 완전한 글꼴이 구현된다.
*성조부호의 설정키는 다음과 같다.
*、는 F
*´는 S
*작은 물음표 `?'같은 것은 R
*~는 X
*아래점 `.'은 J

 

첨부... unikey.exe파일 바탕화면에 바로가기 만드세요.

  바탕화면에 용량이 큰 파일이 있으면 부팅속도가 늦어진   다.




AND

AND


출처: http://www.osronline.com/ddkx/appendix/imeimes_0h2s.htm


Win32 Multilingual IME Overview for IME Development

This documentation introduces the basics on how to develop an IME for Windows® 95, Windows® 98, and Windows® NT/2000. It is also a supplement to the Win32® Multilingual IME API reference for IME development

The following main topics are discussed:

Overview

IME User Interface

IME Input Context

Generating Messages

ImeSetCompositionString

Soft Keyboard

Reconversion

IME Menu Functions

IME Help File

Windows NT/2000 Issues

IME File Format and Data Structures

Overview

Beginning with Windows 95 and Windows NT® 4.0, Input Method Editors (IMEs) are provided as a dynamic-link library (DLL), in contrast to the IMEs for the Windows 3.1 East Asian Edition. Each IME runs as one of the multilingual keyboard layouts. In comparison to the Windows 3.1 IME, the new Win32 Multilingual Input Method Manager (IMM) and Input Method Editor (IME) architecture provide the following advantages:

  • Run as a component of the multilingual environment
  • Offer multiple Input Contexts for each application task
  • Keep one active IME per each application thread
  • Give information to the application through message looping (no message order broken)
  • Offer strong support for both IME-aware and IME-unaware applications

To fully utilize these advantages, an application needs to support the new Win32 IMM/IME application interface.

In order to maintain maximum compatibility with existing Windows 95 and Windows NT 4.0 IMEs, Windows 98 and Windows 2000 have not changed significantly in design. However, new features have been added in order to provide better system integration and to support more intelligent IMEs.

Note  IME developers must use the immdev.h in DDK, which is a superset of the imm.h in the SDK or other development tools.

Windows 98 and Windows 2000 IMM/IME

The Windows 98 and Windows 2000 IMM/IME architecture retains the Windows 95 and Windows NT 4.0 design. However, some changes have been made in order to support intelligent IME development and integration of the IME with Windows. These changes include:

  • New IME functions that allow applications to communicate with the IMM/IME. These include:

    ImmAssociateContextEx

    ImmDisableIME

    ImmGetImeMenuItems

  • New functions that allow the IME to communicate with IMM and applications. These include:

    ImmRequestMessage

    ImeGetImeMenuItems

  • Supporting reconversion

    This is a new IME feature that allows you to reconvert a string that has already been inserted into the application’s document. This function will help intelligent IMEs to get more information about the converted result and improve conversion accuracy and performance. This feature requires that the application and the IME cooperate.

  • Adding IME menu items to the Context menu of the System Pen icon

    This new feature provides a way for an IME to insert its own menu items into the Context menu of the System Pen icon in the system bar and in applications.

  • New bits and flags for the IME

    The following new bits support new conversion modes:

    IME_CMODE_FIXED

    IME_SMODE_CONVERSATION

    IME_PROP_COMPLETE_ON_UNSELECT

  • Edit control enhancement for the IME

    Through two new edit control messages, EM_SETIMESTATUS and EM_GETIMESTATUS, applications can manage IME status for edit controls.

  • Changing IME Pen Icon and Tooltips

    Through three new messages, INDICM_SETIMEICON, INDICM_SETIMETOOLTIPS, and INDICM_REMOVEDEFAULTMENUITEMS, IME can change the system Pen Icon and Tooltips in the system task bar.

  • Two new IMR messages

    IMR_QUERYCHARPOSITION and IMR_DOCUMENTFEED help the IME and application to communicate position and document information.

  • 64-bit compliant

    Two new structures (TRANSMSG and TRANSMSGLIST) are added into IMM32. They are used by INPUTCONTEXT and ImeToAsciiEx to receive IME translated message.

  • IME_PROP_ACCEPT_WIDE_VKEY

    This new property is added into Windows 2000 so IME can handle the injected Unicode by SendInput API. ImeProcessKey and ImeToAsciiEx APIs are updated to handle injected Unicode as well. The injected Unicode can be used by application and handwriting programs to put Unicode strings into input queue.

Win32 IME Structure

A new Win32 IME has to provide two components. One is the IME Conversion Interface and the other is the IME User Interface. The IME Conversion Interface is provided as a set of functions that are exported from the IME module. These functions are called by the IMM. The IME User Interface is provided in the form of windows. These windows receive messages and provide the user interface for the IME.

IME Aware Applications

One of the main advantages of the new Win32 IME architecture is that it provides better communication logic between the application and the IME. Following is an example of how an application could be involved with the IME:

  • IME Unaware Applications

    These kinds of applications never intend to control the IME. However, as long as it accepts DBCS characters, a user can type any DBCS character to the application using IME.

  • ME Half-aware Applications

    These kinds of applications typically control the various contexts of the IME, such as open and close, and composition form, but it does not display any user interface for the IME.

  • IME Full-aware Applications

    These kinds of applications typically want to be fully responsible for displaying any information given by the IME.

In Windows 95 and Windows NT 4.0 or later, one IME unaware application will be supported with one Default IME window and one Default Input Context.

An IME half-aware application will create its own IME window(s), also called an application IME window, using a predefined system IME class, and may or may not handle its own Input Context given to the application.

An IME fully aware application will handle the Input Context by itself and will display any necessary information given by the Input Context not using the IME window.

IME User Interface

The IME User Interface includes the IME window, the UI window, and the components of the UI window.

Features

An IME class is a predefined global class that carries out any user interface portion of the IME. The normal characteristics of an IME class are the same as with other common controls. Its window instance can be created by CreateWindowEx. As with static controls, the IME class window does not respond to user input by itself, but receives various types of control messages to realize the entire user interface of the IME. An application can create its own IME window(s) by using this IME class or by obtaining the Default IME window through ImmGetDefaultIMEWnd. In comparison to Windows 3.1, an application that wants to control the IME with these window handles (an IME-aware application) can now achieve the following benefits:

  • The new IME includes candidates listing windows. Each application can have its own window instance of the UI so a user can stop in the middle of any operation to switch to another application. In the Windows 3.1 Japanese Edition, the user had to first exit an operation before switching to another application.
  • Since the IME User Interface window is informed about an application’s window handle, it can provide several default behaviors for the application. For example, this can include automatic repositioning of the IME window, automatic tracing of the window caret position, and mode indication for each application.

Even though the system provides only one IME class, there are two kinds of IME window. One is created by the system for the DefWindowProc function especially for an IME unaware program. The IME User Interface for the DefWindowProc function is shared by all IME unaware windows of a thread and is called the default IME window in this documentation. The other windows are created by IME aware applications and are called the application IME window.

Default and Application IME Window

The system creates a default IME window at thread initialization time, which is given to a thread automatically. This window then handles any IME user interface for an IME unaware application.

When the IME or IMM generates WM_IME_xxx messages, an IME unaware application passes them to DefWindowProc. Then, DefWindowProcB sends necessary messages to the default IME window, which provides default behavior of the IME User Interface for an unaware application. An IME aware application also uses this window when it does not hook messages from the IME. An application can use its own application IME window when it is necessary.

IME Class

The Win32 systems provides an IME class in the system. This class is defined by the user just as the predefined Edit class is. The system IME class handles the entire UI of the IME and handles entire control messages from the IME and application, including IMM functions. An application can create its own IME User Interface by using this class. The system IME class, itself, is not replaced by any IME, but is kept as a predefined class.

This class has a window procedure that actually handles the WM_IME_SELECT message. This message has the hKL of the newly selected IME. The system IME class retrieves the name of the class defined by each IME with this hKL. Using this name, the system IME class creates a UI window of the currently active IME.

UI Class from IME

In this design, every IME is expected to register its own UI class for the system. The UI class provided by each IME should be responsible for IME-specific functionality. The IME may register the classes that are used by the IME itself when the IME is attached to the process. This occurs when DllEntry is called with DLL_PROCESS_ATTACH. The IME then has to set the UI class name in the lpszClassName parameter, which is the second parameter of ImeInquire.

The UI class should be registered with CS_IME specified in the style field so every application can use it through the IME class. The UI class name (including the null terminator) can consist of up to 16 characters and may be increased in future versions.

The cbWndExtra of the UI class has to be 2 * sizeof(LONG). The purpose of this WndExtra is defined by the system (for example, IMMGWL_IMC and IMMGWL_PRIVATE).

The IME can register any class and create any window while working in an application.

The following sample shows how to register the IME User Interface Class:

BOOL WINAPI DLLEntry (
    HINSTANCE    hInstDLL,
    DWORD        dwFunction,
    LPVOID       lpNot)
{
switch(dwFunction)
    {
case DLL_PROCESS_ATTACH:
hInst= hInstDLL;
            wc.style          = CS_MYCLASSFLAG | CS_IME;
            wc.lpfnWndProc    = MyUIServerWndProc;
            wc.cbClsExtra     = 0;
            wc.cbWndExtra     = 2 * sizeof(LONG);
            wc.hInstance      = hInst;
            wc.hCursor        = LoadCursor( NULL, IDC_ARROW );
            wc.hIcon          = NULL;
            wc.lpszMenuName   = (LPSTR)NULL;
wc.lpszClassName  = (LPSTR)szUIClassName;
wc.hbrBackground  = NULL;
if( !RegisterClass( (LPWNDCLASS)&wc ) )
return FALSE;
            wc.style          = CS_MYCLASSFLAG | CS_IME;
            wc.lpfnWndProc    = MyCompStringWndProc;
            wc.cbClsExtra     = 0;
            wc.cbWndExtra     = cbMyWndExtra;
            wc.hInstance      = hInst;
            wc.hCursor        = LoadCursor( NULL, IDC_ARROW );
            wc.hIcon          = NULL;
            wc.lpszMenuName   = (LPSTR)NULL;
wc.lpszClassName  = (LPSTR)szUICompStringClassName;
wc.hbrBackground  = NULL;
if( !RegisterClass( (LPWNDCLASS)&wc ) )
return FALSE;
break;
case DLL_PROCESS_DETACH:
UnregisterClass(szUIClassName,hInst);
UnregisterClass(szUICompStringClassName,hInst);
break;
    }
return TRUE;
}

UI Window

The IME windows of the IME class are created by the application or by the system. When the IME window is created, the UI window provided by the IME itself is created and owned by the IME window.

Each UI window contains the current Input Context. This Input Context can be obtained by calling GetWindowLong with IMMGWL_IMC when the UI window receives a WM_IME_xxx message. The UI window can refer to this Input Context and handles the messages. The Input Context from GetWindowLong with IMMGWL_IMC is available at any time during the UI window procedure, except when handling a WM_CREATE message.

The cbWndExtra of the UI windows cannot be enhanced by the IME. When the IME needs to use the extra byte of the window instance, the UI window uses SetWindowLong and GetWindowLong with IMMGWL_PRIVATE. This IMMGWL_PRIVATE provides a LONG value extra of the window instance. When the UI window needs more than one LONG value extra for private use, the UI window can place a handle for a memory block into the IMMGWL_PRIVATE area.The UI window procedure can use DefWindowProc, but the UI window cannot pass a WM_IME_xxx message to DefWindowProc. Even if the message is not handled by the UI window procedure, the UI window does not pass it to DefWindowProc.

The following sample demonstrates how to allocate and use a block of private memory:

LRESULT UIWndProc (HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
HIMC hIMC;
HGLOBAL hMyExtra;
 
switch(msg){
case WM_CREATE:
// Allocate the memory block for the window instance.
hMyExtra = GlobalAlloc(GHND,size_of_MyExtra);
if (!hMyExtra)
MyError();
// Set the memory handle into IMMGWL_PRIVATE
SetWindowLong(hWnd, IMMGWL_PRIVATE, (LONG)hMyExtra);
                :
                :
break;
case WM_IME_xxxx:
// Get IMC;
hIMC = GetWindowLong(hWnd,IMMGWL_IMC);
// Get the memory handle for the window instance.
hMyExtra = GetWindowLong(hWnd, IMMGWL_PRIVATE);
lpMyExtra = GlobalLock(hMyExtra);
                :
                :
GlobalUnlock(hMyExtra);
break;
            :
            :
 
case WM_DESTROY:
// Get the memory handle for the window instance.
hMyExtra = GetWindowLong(hWnd, IMMGWL_PRIVATE);
// Free the memory block for the window instance.
GlobalFree(hMyExtra);
break;
 
default:
return DefWindowProc(hWnd, msg, wParam, lParam);
    }
}

The UI window must perform all tasks by referring to the Input Context that is currently selected. When a window of an application is activated, the UI window receives a message that contains the current Input Context. The UI window then uses that Input Context. Thus, the Input Context must contain all the information needed by the UI window to display the composition window, the status window, and so forth.

The UI window refers to the Input Context, but does not need to update it. However, if the UI window wants to update the Input Context, it should call the IMM functions. Because the Input Context is managed by the IMM, the IMM along with the IME should be notified when the Input Context is changed.

For example, the UI window occasionally needs to change the conversion mode of the Input Context when the user clicks the mouse. At this point, the UI window should call ImmSetConversionMode. The ImmSetConversionMode function creates a notification for NotifyIME and the UI window with WM_IME_NOTIFY. If the UI window wants to change the display of the conversion mode, the UI window should wait for a WM_IME_NOTIFY message.

Components of the UI Window

The UI window can register and show the composition window and the status window by referring to the current Input Context. The class style of the components of the UI window must include the CS_IME bit. A window instance of the UI window gets information about the composition string, font, and position from the current Input Context.

When a window of the application is getting focused, the system gives the Input Context to this window and sets the current Input Context to the UI window. The system then sends a WM_IME_SETCONTEXT message with the handle of its Input Context to the application. The application then passes this message to the UI window. If current Input Context is replaced by another Input Context, the UI window should repaint the composition window. Any time the current Input Context is changed, the UI window displays a correct composition window. Thus, the status of the IME is assured.

A UI window can create a child window or pop-up window to display its status, composition string, or candidate lists. However, these windows have to be owned by the UI window and created as disabled windows. Any windows that are created by the IME should not get the focus.

IME Input Context

Each window is associated with an IME Input Context. The IMM uses the Input Context to maintain IME status, data, and so forth, and communicate with the IME and with applications.

Default Input Context

By default, the system creates a default Input Context for each thread. All IME unaware windows of the thread share this context.

Application-Created Input Context

A window of an application can associate its window handle to an Input Context to maintain any status of the IME, including an intermediate composition string. Once an application associates an Input Context to a window handle, the system automatically selects the context whenever the window is activated. In this way, an application is free from complicated in and out focus processing.

Using the Input Context

When an application or system creates a new Input Context, the system prepares the new Input Context with the components of the IMC (IMCC). These include hCompStr, hCandInfo, hGuideLine, hPrivate, and hMsgBuf. Basically, the IME does not need to create the Input Context and the components of the Input Context. The IME can change the size of them and lock them to get the pointer for them.

Accessing the HIMC

When an IME accesses the Input Context, the IME has to call ImmLockIMC to get the pointer of the Input Context. ImmLockIMC increments the IMM lock count for IMC, while ImmUnlockIMC decrements the IMM lock count for IMC.

Accessing the HIMCC

When an IME accesses a component of the Input Context, the IME has to call ImmLockIMCC to get the pointer of the IMCC. ImmLockIMCC increments the IMM lock count for IMCC, while ImmUnlockIMC decrements the IMM lock count for IMCC. ImmReSizeIMCC can resize the IMCC to the size specified in the input parameter.

On occasion, an IME needs to create a new component in the Input Context. The IME can call ImmCreateIMCC to do so. To destroy a newly created component in the Input Context, the IME can call ImmDestroyIMCC.

The following example shows how to access the IMCC and change the size of a component:

LPINPUTCONTEXT lpIMC;
LPCOMOSITIONSTRING lpCompStr;
HIMCC hMyCompStr;
 
if (hIMC)    // It is not NULL context.
{
lpIMC = ImmLockIMC(hIMC);
if (!lpIMC)
    {
MyError( “Can not lock hIMC”);
return FALSE;
    }
 
// Use lpIMC->hCompStr.
lpCompStr = (LPCOMPOSITIONSTRING)ImmLockIMCC(lpIMC->hCompStr);
// Access lpCompStr.
ImmUnlockIMCC(lpIMC->hCompStr);
 
// ReSize lpIMC->hCompStr.
if (!(hMyCompStr = ImmReSizeIMCC(lpIMC->hCompStr,dwNewSize))
    {
MyError(“Can not resize hCompStr”);
ImmUnlockIMC(hIMC);
return FALSE;
    }
lpIMC->hCompStr = hMyCompStr;
ImmUnlockIMC(hIMC);
}

Generating Messages

IMEs need to generate IME messages. When an IME initiates the conversion process, the IME has to generate a WM_IME_STARTCOMPOSITION message. If the IME changes the composition string, the IME has to generate a WM_IME_COMPOSITION message.

There are two ways an IME can generate a message: one is by using the lpdwTransKey buffer provided by ImeToAsciiEx, and the other is by calling ImmGenerateMessage.

Using lpTransMsgList to Generate Messages

Events initiated by IMEs are realized as generating messages to the window associated with the Input Context. Basically, IMEs use the lpTransMsgList provided by the parameter of ImeToAsciiEx to generate the message. The IMEs put the messages into the lpTransMsgList buffer when ImeToAsciiEx is called.

The buffer specified by lpTransMsgList in the ImeToAsciiEx function is provided by the system. This function can place messages in this buffer all at one time. The real number of messages that can be placed is given at the first double word of the buffer. However, if the ImeToAsciiEx function wants to generate more messages than the given number, ImeToAsciiEx can put all the messages into hMsgBuf in the Input Context and then return the number of messages.

When the return value of ImeToAsciiEx is larger than the specified value in lpTransMsgList, the system does not pick up the messages from lpTransMsgList. Instead, the system looks up hMsgBuf in the Input Context, which is passed as a parameter of ImeToAsciiEx.

Following is the code sample for ImeToAsciiEx implementation:

UINT
   ImeToAsciiEx(
   uVirKey,
   uScanCode,
   lpbKeyState,
lpTransMsgList,
   fuState,
   hIMC
  )

{
    DWORD dwMyNumMsg = 0;
 
. . .
 
    // Set the messages that the IME wants to generate.
    pTransMsgList->TransMsg[0].message =msg;
    pTransMsgList->TransMsg[0].wParam = wParam;
    pTransMsgList->TransMsg[0].lParam = lParam;
 
    // Count the number of the messages that the IME wants to generate.
    dwMyNumMsg++;

. . .
 
    return dwMyNumMsg;
}

Using the Message Buffer to Generate Messages

Even if ImeToAsciiEx is not called, IMEs can still generate the message to the window associated with the Input Context by using the message buffer of the Input Context. This message buffer operates as a handle of a memory block and the IME puts the messages into this memory block. The IME then calls the ImmGenerateMessage function, which sends the messages stored in the message buffer to the proper window.

Following is the code sample for ImmGenerateMessage implementation.

MyGenerateMesage(HIMC hIMC, UINT msg, WPARAM wParam, LPARAMlParam)
{
    LPINPUTCONTEXT lpIMC;
    HGLOBAL hTemp;
        LPTRANSMSG lpTransMsg;
DWORD dwMyNumMsg = 1;
    
    // Lock the Input Context.
    lpIMC = ImmLockIMC(hIMC);
    if (!lpIMC) ….. // Error!
// re-allocate the memory block for the message buffer.
hTemp = ImmReSizeIMCC(lpIMC->hMsgBuf, (lpIMC->dwNumMsgBuf + dwMyNumMsg) * sizeof(TRANSMSG));
if (!hTemp) ….// Error!
lpIMC->hMsgBuf = hTemp;
// Lock the memory for the message buffer.
lpTransMsg = ImmLockIMCC(lpIMC->hMsgBuf);
if (!lpTransMsg) …. // Error!


// Set the messages that the IME wants to generate.
lpTransMsg[lpIMC->dwNumMsg].message = msg;
lpTransMsg[lpIMC->dwNumMsg].wParam = wParam;
lpTransMsg[lpIMC->dwNumMsg].lParam = lParam;

// Set the number of the messages.
lpIMC->dwNumMsgBuf += dwMyNumMsg;


// Unlock the memory for the message buffer and the Input Context.
ImmUnlockIMCC(lpIMC->hMsgBuf);
ImmLockIMC(hIMC);
 
// Call ImmGenerateMessage function.
ImmGenerateMessage(hIMC);
}

WM_IME_COMPOSITION Message

When an IME generates a WM_IME_COMPOSITION message, the IME specifies lParam as the GCS bits. The GCS bits then inform the available members of the COMPOSITIONSTRING structure. Even if the IME does not update and a member is available, the IME can set the GCS bits.

When an IME generates a WM_IME_COMPOSITION message, the IME can also change the string attribute and clause information all at once.

ImeSetCompositionString

The ImeSetCompositionString function is used by applications to manipulate the IME composition string. By specifying different flags, an application can change composition string, attribute, clause, and so forth.

The second parameter of this function, dwIndex, specifies how the composition string should be adjusted in an IME. It includes values such as SCS_SETSTR ,SCS_CHANGEATTR, SCS_CHANGECLAUSE, SCS_QUERYRECONVERTSTRING. Each value represents a specific feature.

ImeSetCompositionString Capability

When an IME does not have the capability of ImeSetCompositionString, it will not specify any SCS capability in the IMEINFO structure. When an IME can handle ImeSetCompositionString, it sets the SCS_COMPSTR bit. If an IME can generate the reading string from the composition string, it will set the SCS_CAP_MAKEREAD bit.

If an IME has SCS_CAP_COMPSTR capability, ImeSetCompositionString will be called. In response to this call, the IME should use the new composition string generated by an application and then generate a WM_IME_COMPOSITION message.

SCS_SETSTR

If dwIndex of ImeSetCompositionString is SCS_SETSTR, the IME can clean up all the COMPOSITIONSTR structures of hIMC.

If necessary, the IME can also update the candidate information and generate the candidate message WM_IME_NOTIFY with the submessage as IMN_OPENCANDIDATE, CHANGECANDIDATE, or IMN_CLOSECANDIDATE.

An IME needs to respond to the application requirement based on different input parameters as follows:

  • If the lpRead parameter of ImeSetCompositonString is available:

    The IME should create the composition string from the reading string contained in lpRead. The IME then creates the attribute and clause information for both the new composition string and reading string of lpRead. The IME generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD. On occasion, an IME may finalize the conversion automatically. The IME can then generate a WM_IME_COMPOSITION message with either GCS_RESULT or GCS_RESULTREAD instead of GCS_COMPxxx.

  • If the lpComp parameter of ImeSetCompositonString is available:

    The IME should create the composition attribute and clause information from the composition string contained in lpComp. The IME then generates a WM_IME_COMPOSITION message with GCS_COMP. If the IME has the capability of SCS_CAP_MAKEREAD, the IME should also make the new reading string at the same time. The IME then generates a WM_IME_COMPOSITION message with either GCS_COMP orGCS_COMPREAD. On occasion, an IME may finalize the conversion automatically. The IME can then generate a WM_IME_COMPOSITION message with either GCS_RESULT or GCS_RESULTREAD instead of GCS_COMPxxx.

  • If both lpRead and lpComp are available:

    The IME should create the composition string and the reading string accordingly. In this case, the IME does not need to follow lpComp and lpRead completely. If an IME cannot find the relation between lpRead and lpComp specified by the application, it should correct the composition string. The IME can then create the attribute and clause information for both the new composition string and reading string of lpRead. The IME then generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD. On occasion, the IME may finalize the conversion automatically. The IME can then generate a WM_IME_COMPOSITION message with either GCS_RESULT or GCS_RESULTREAD instead of GCS_COMPxxx.

SCS_CHANGEATTR

SCS_CHANGEATTR effects only attribute information. The IME should not update the composition string, the clause information of the composition string, the reading of the composition string, or the clause information of the reading of the composition string.

The IME first has to check whether the new attribute is acceptable or not. It then sets the new attribute in the COMPOSITIONSTRING structure of hIMC. Last, the IME generates a WM_IME_COMPOSITION message.

If necessary, the IME can update the candidate information and generate the candidate messages WM_IME_NOTIFY with the submessage as IMN_OPENCANDIDATE, CHANGECANDIDATE, or IMN_CLOSECANDIDATE of WM_IME_NOTIFY.

For this feature, an IME cannot finalize the composition string.

An IME needs to respond to the application requirement based on different input parameters as follows:

  • If the lpRead parameter of ImeSetCompositonString is available:

    The IME should follow the new attribute in lpRead and then create a new attribute of the composition string for the current composition string. In this case, the clause information does not change.

    The IME generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD. If an IME cannot accept the new attribute contained in lpRead, it does not generate any messages and returns FALSE.

  • If the lpComp parameter of ImeSetCompositonString is available:

    The IME follows the new attribute in lpComp. In this case, the clause information does not change.

    If the capability of the IME has SCS_CAP_MAKEREAD and the reading string is available, the IME should create a new attribute of the reading of the composition string for the current reading of the composition string.

  • If both lpRead and lpComp are available:

    If the IME can accept the new information, it sets the new information in the COMPOSITION structure of hIMC and generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD.

SCS_CHANGECLAUSE

SCS_CHANGECLAUSE effects the string and attribute for both the composition string and the reading of the composition string.

If necessary, an IME can update the candidate information and generate the candidate message WM_IME_NOTIFY with the submessages as IMN_OPENCANDIDATE, CHANGECANDIDATE, or IMN_CLOSECANDIDATE.

An IME needs to respond to the application requirement based on different input parameters. Following are the instances in which an IME cannot finalize the composition string.

  • If the lpRead parameter of ImeSetCompositonString is available:

    The IME follows the new reading clause information of lpRead and has to correct the attribute of the reading of the composition string. The IME can then update the composition string, the attribute, and the clause information of the composition string. The IME generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD.

  • If the lpComp parameter of ImeSetCompositonString is available:

    The IME follows the new clause information and has to correct the composition string and the attribute of the composition string. Then, the IME can update the reading attribute and the clause information of the reading attribute. The IME generates a WM_IME_COMPOSITION message with either GCS_COMPSTR or GCS_COMPREAD.

  • If both lpRead and lpComp are available:

    If the IME can accept the new information, it sets the new information in the COMPOSITION structure of hIMC and generates a WM_IME_COMPOSITION message with either GCS_COMP or GCS_COMPREAD.

Soft Keyboard

Soft Keyboard is a special window displayed by the IME. Because some IMEs have special reading characters, an IME can provide a soft keyboard to display these special reading characters. In this way, the user does not have to remember the reading character for each key. For example, an IME can use bo po mo fo for its reading characters, while another IME can use radicals for its reading characters.

An IME can change the reading characters of keys and notify the user of these key changes, depending on the conversion state. For example, during candidate selection time, an IME can show just the selection keys to the user.

An IME can also create its own user interface for a soft keyboard or use the system predefined soft keyboard. If an IME wants to use the system predefined soft keyboard, it needs to specify UI_CAP_SOFTKBD in the fdwUICaps member of the IMEINFO structure when ImeInquire is called.

An IME needs to call ImmCreateSoftKeyboard to create the soft keyboard window . It can also call ImmShowSoftKeyboard to show or hide the soft keyboard. Because the soft keyboard window is one component of the UI window, the owner should be the UI window as well.

There are different types of soft keyboards. Each one is designed for a specific country/region or special purpose. An IME can change the reading characters on the soft keyboard by using one of two methods: IMC_SETSOFTKBDSUBTYPE or IMC_SETSOFTKBDDATA.

Reconversion

Reconversion is a new IME function for Windows 98 and Windows 2000. It provides the capability to reconvert a string that is already inserted in an application’s document. Specifically, whatever the string is, an IME is instructed to recognize the string, convert it to the reading or typing information, and then display the candidate list.

New and advanced intelligent IMEs are capable of recognizing and interpreting a complete sentence. When an IME is supplied with better information about a string, such as full sentence and string segmentation, it can accomplish better conversion performance and accuracy. For example, by supplying an entire sentence as opposed to just the reconverted strings, the IME can reconvert the string without having to first convert to reading or typing information.

Editing after the determination is harder than before today. This is because determination will discard most of the information undetermined string had, like reading, phrases, and part of speech. Reconversion will get these information back, making editing after the determination as easier as before the determination. Users will be able to choose different homonym words from candidates, change phrase break and let IME analyze again, and so forth.

The RECONVERTSTRING structure can store the entire sentence and point to the string that will be reconverted by dwStartOffset and dwLen. If dwStartOffset is zero and dwLen is the length of the string, the entire string is reconverted by the IME.

Simple Reconversion

The simplest reconversion is when the target string and the composition string are the same as the entire string. In this case, dwCompStrOffset and dwTargetStrOffset are zero, and dwStrLen, dwCompStrLen, and dwTargetStrLen are the same value. An IME will provide the composition string of the entire string that is supplied in the structure, and will set the target clause by its conversion result.

Normal Reconversion

For an efficient conversion result, the application should provide the RECONVERTSTRING structure with the information string. In this case, the composition string is not the entire string, but is identical to the target string. An IME can convert the composition string by referencing the entire string and then setting the target clause by its conversion result.

Enhanced Reconversion

Applications can set a target string that is different from the composition string. The target string (or part of the target string) is then included in a target clause in high priority by the IME. The target string in the RECONVERTSTRING structure must be part of the composition string. When the application does not want to change the user’s focus during the reconversion, the target string should be specified. The IME can then reference it.

IME Cancel Reconversion

When a user cancels the composition string generated by the reconversion, the IME should determine the original reconverted string. Otherwise, the application will loose the string.

SCS_SETRECONVERTSTRING and SCS_QUERYRECONVERTSTRING Flags

Applications can ask an IME to reconvert the string by calling ImmSetCompositionString. They can use either the SCS_SETSTR flag or the SCS_SETRECONVERTSTRING flag to create a new composition string. However, by using SCS_SETRECONVERTSTRING, the application can pass RECONVERTSTRING to the IME for better conversion efficiency.

Initially, the application should call ImmSetCompositionString with SCS_QUERYRECONVERTSTRING. The selected IME can then adjust the given RECONVERTSTRING structure for appropriate reconversion. The application then calls ImmSetCompositionString with SCS_SETRECONVERTSTRING to request that the IME generate a new composition string. If the application asks the IME to adjust the RECONVERTSTRING structure by calling SCS_QUERYRECONVERTSTRING, efficient reconversion can be accomplished.

SCS_SETRECONVERTSTRING or SCS_QUERYRECONVERTSTRING can be used only for IMEs that have an SCS_CAP_SETRECONVERTSTRING property. This property can be retrieved by using the ImmGetProperty function.

IMR_RECONVERTSTRING and IMR_CONFIRMRECONVERTSTRING Messages

When an IME wants to reconvert, it can ask the application to provide the string to be reconverted. For example, when a user presses the Reconversion key or selects the Reconversion button in the IME status window, the IME sends a WM_IME_REQUEST message with IMR_RECONVERTSTRING to get the target string. Initially, the IME needs to send this with NULL lParam in order to get the required size of RECONVERTSTRING. The IME then prepares a buffer to receive the target string and sends the message again with the pointer of the buffer in lParam.

After the application handles IMR_RECONVERTSTRING, the IME may or may not adjust the RECONVERTSTRING structure given by the application. Finally, the IME sends a WM_IME_REQUEST message with IMR_CONFIRMRECONVERTSTRING to confirm the RECONVERTSTRING structure.

If the application returns TRUE for IMR_CONFIRMRECONVERTSTRING, the IME generates a new composition string based on the RECONERTSTRING structure in the IMR_CONFIRMRECONVERTSTRING message. If the application returns FALSE, the IME generates a new composition string based on the original RECONVERTSTRING structure given by the application in the IMR_RECONVERTSTRING message. An IME will not generate a composition string for reconversion before IMR_CONFIRMRECONVERTSTRING.

The given string should not be changed by SCS_QUERYRECONVERTSTRING or IMR_CONFIRMRECONVERTSTRING. An IME can change only CompStrOffset, CompStrLen, TargetStrOffset, and TargetStrLen to re-confirm it.

IME Menu Functions

The purpose of this function set is to reduce the IME-related icon in the system task bar. It is a new feature for Windows 98 and Windows 2000.

The Windows system program installs two icons in the task bar when the current hKL is an IME. One icon is the System ML icon that indicates the current keyboard layout in the system task bar. The other is the System Pen icon that shows the IME status of the focused window.

Usually, an IME places an additional icon in the task bar. The context menu for this icon is completely dependent on the IME. Having IME icons in a task bar is a quick way for a user to access an IME’s special functions. However, there are three icons associated with the IME and these additional icons may be more than a user wants to deal with.

If the system provides a way for an IME to insert IME menu items into the System Pen icon, the IME then does not need to add its extra icons to the task bar.

The IMM calls the IME function ImeGetImeMenuItems to get the IME menu items.

An application can use ImmGetImeMenuItems to get an IME’s special menu items, which it can add to its context menu. By calling ImmNotify, the selected items can be processed by the IME.

IME Menu Notification

When an application wants to handle an IME’s menu items, it can call ImmNotifyIME. When the menu items added by the IME are selected, NotifyIME is called under the focused thread.

IME Help File

The IME help file is a new function added into Windows 98 and Windows NT. The right click menu of the System Pen Icon has two menu items. One is the setting for the IME system and is used to change the setting of the selected IME of the focus thread. The other menu item is an online Help file that has never been enabled. Thus, this menu item is always grayed. The purpose of this menu item was to display an IME’s online Help. However, because the system does not provide the IME with a way to specify the name of the IME help file, the system task bar program is not able to display it.

IME_ESC_GETHELPFILENAME

The IME_ESC_GETHELPFILENAME escape allows an IME to specify its help file name. On return from the function, the (LPTSTR)lpData is the full path file name of an IME’s help file.

If the help content is HTML help format, please make sure the help file extension is .chm so the Windows User knows which help engine to start.

Indicator Manager for IME

By using a set of messages defined in Windows 98 and Windows 2000, an IME can change the icon and ToolTip string for the System Pen icon on the system task bar.

Indicator Window

An IME can get the window handle of the indicator by using FindWindow with INDICATOR_CLASS.

// Get the window handle of Indicator.
hwndIndicator = FindWindow(INDICATOR_CLASS, NULL);
if (!hwndIndicator)
{
// There is no indicator window. Tray does not have System Pen icon.
return FALSE;
}
// Call PostMessage to change Pen icon.
PostMessage(hwndIndicator, INIDCM_SETIMEICON, nIconIndex, hMyKL);

Note  Due to the internal design requirement in the task bar manager, the IME must use PostMessage for INDICM_xxx messages.

Messages

IMEs can send the following messages to the Indicator window to perform different tasks:

INDICM_SETIMEICON

INDICM_SETIMETOOLTIPS

INDICM_REMOVEDEFAULTMENUITEMS

Windows NT and Windows 2000 Issues

The following topics primarily describe the special issues related to Windows NT/2000. However, some of these issues may also apply to Windows 98.

IME and Localized Language Compatibility

Windows 2000 has full-featured IME support in any localized language version. That is, an IME can be installed and used with any Windows 2000 language. IME developers should test their IME on these environments. This new feature also requires IME developers to prepare their IME help content to include correct charset and font information so it shows up correctly on different language operating systems.

Also, IME developers should develop Unicode IME for Windows 2000. Unicode IMEs will work with Unicode applications under any system locale. For non-Unicode IMEs, the user must change the system locale to support the same language that the IME supports in order to use them.

Unicode Interface

Along with the ANSI version of the IMM/IME interface originally supported by Windows 95, Windows NT and Windows 98 support Unicode interface for the IME. To communicate with the system by Unicode interface, an IME should set the IME_PROP_UNICODE bit of the fdwProperty member of the IMEINFO structure, which is the first parameter of the ImeInquire function. Although ImeInquire is called to initialize the IME for every thread of the application process, the IME is expected to return the same IMEINFO structure on a single system. Windows 98 supports all the Unicode functions, except for ImmIsUIMessage.

Security Concerns

There are two primary security concerns for Windows NT. One involves named objects and the other involves Winlogon.

Named Objects

An IME may want to create various named objects that should be accessed from multiple processes on the local system. Such objects may include file, mutex, or event. Since a process might belong to a different user who is interactively logging onto the system, the default security attribute (created by the system when an IME creates an object with the NULL parameter as the pointer to the security attribute) may not be appropriate for all processes on the local system.

On Windows NT, the first client process of the IME may be the Winlogon process that lets a user log onto the system. Since the Winlogon process belongs to the system account during the log-on session and is alive until the system shuts down, named objects created by the IME with the default security attribute during the log-on session cannot be accessed through other processes belonging to a logged-on user.

Winlogon

Since a user in the log-on session has not been granted the access right to the system yet, information provided by an IME’s configuration dialog boxes can create security problems. Even though, the system administrator can configure the system so such an IME cannot be activated on the log-on session. A well-behaved IME should not allow users to open configure dialog boxes if the client process is a Winlogon process. An IME can check if the client process executing a log-on session is a Winlogon process by checking the IME_SYSTEMINFO_WINLOGON bit of the dwSystemInfoFlags parameter of ImeInquire.

IME File Format and Data Structures

The following topics discuss the IME file format and data structures used by the IME.

IME File Format

An IME needs to specify the following fields correctly in the version information resource. This includes the fixed file information part and the variable length information part. Please refer to the Microsoft Platform SDK for detailed information on version information resource.

Following are the specific settings the IME file should include:

dwFileOS
The dwFileOS should be specified in the root block of the version information. The dwFileOS should be VOS__WINDOWS32 for Windows 95 and Windows NT IMEs.
dwFileType
The dwFileType should be specified in the root block of the version information. The value is VFT_DRV.
dwFileSubtype
The dwFileSubtype should be specified in the root block of the version information. The value is VFT2_DRV_INPUTMETHOD.
FileDescription
The FileDescription is specified in the language-specific block of the version information. This should include the IME name and the version. This string is for display purposes only. Currently, the string length is 32 TCHARS, but may be extended in a future version.
ProductName
The ProductName is specified in the language-specific block of the version information.
Charset ID and Language ID
The code page (character set ID) and language ID are specified in the variable information block of the version information resource. If there are many code pages (character set ID) and language IDs are specified in the block, the IME uses the first code page ID to display the text and uses the first language ID for the IME language. The charset ID and language ID must match the IME language instead of the resource language. The file name of IME is 8.3.

IME Registry Contents

The IME HKEY_CURRENT_USER registry contains an Input Method key. The following table describes the contents of this Input Method.

Key Contents
Input Method There are four value names: Perpendicular Distance, Parallel Distance, Perpendicular Tolerance, and Parallel Tolerance. The near caret operation IME refers to these values. If these four value names are not present, a near operation IME can set a default value, depending on the IME
  Value Name Value Data
  Perpendicular Distance Distance is perpendicular to the text escapement. This is the perpendicular distance (pixels) from the caret position to the composition window without the font height and width. The near caret operation IME will adjust the composition window position according to this value and Parallel Distance. It is in REG_DWORD format.
  Parallel Distance Distance (pixels) is parallel to the text escapement. This is the parallel distance from the caret position to the composition window. It is in REG_DWORD format.
  Perpendicular Tolerance Tolerance (pixels) is perpendicular to the text escapement. This is the perpendicular distance from the caret position to the composition window. The near caret operation IME will not refresh its composition window if the caret movement is within this tolerance. It is in REG_DWORD format.
  Parallel Tolerance Tolerance (pixels) is parallel to the text escapement. This is the parallel distance from the caret position to the composition window. It is in REG_DWORD format.

An IME can place the per-user setting into:

Under HKEY_CURRENT_USER\Software\<Company Name>\Windows\CurrentVersion\<IME Name>.

An IME can place the per computer setting into:

Under HKEY_LOCAL_MAACHINE\Software\<Company Name>\Windows\CurrentVersion\<IME Name>.

IMM and IME Data Structures

The following structures are used for IMM and IME communication. IMEs can access these structures directly, but applications cannot.

INPUTCONTEXT

The INPUTCONTEXT structure is an internal data structure that stores Input Context data.

typedef struct tagINPUTCONTEXT {
HWND  hWnd;
BOOL  fOpen;
POINT  ptStatusWndPos;
POINT  ptSoftKbdPos;
DWORD  fdwConversion;
DWORD  fdwSentence;
union {
            LOGFONTA    A;
            LOGFONTW    W;
} lfFont;
COMPOSITIONFORM  cfCompForm;
CANDIDATEFORM  cfCandForm[4];
HIMCC  hCompStr;
HIMCC  hCandInfo;
HIMCC  hGuideLine
HIMCC  hPrivate; 
DWORD  dwNumMsgBuf;
HIMCC  hMsgBuf;
DWORD  fdwInit
DWORD  dwReserve[3];
} INPUTCONTEXT;

Members

hWnd
Window handle that uses this Input Context. If this Input Context has shared windows, this must be the handle of the window that is activated. It can be reset with ImmSetActiveContext.
fopen
Present status of opened or closed IME.
ptStatusWndPos
Position of the status window.
ptSoftKbdPos
Position of the soft keyboard.
fdwConversion
Conversion mode that will be used by the IME composition engine.
fdwSentence
Sentence mode that will be used by the IME composition engine.
lfFont
LogFont structure to be used by the IME User Interface when it draws the composition string.
cfCompForm
COMPOSITIONFORM structure that will be used by the IME User Interface when it creates the composition window.
cfCandForm[4]
CANDIDATEFORM structures that will be used by the IME User Interface when it creates the candidate windows. This IMC supports four candidate forms.
hCompStr
Memory handle that points to the COMPOSITIONSTR structure. This handle is available when there is a composition string.
hCandInfo
Memory handle of the candidate. This memory block has the CANDIDATEINFO structure and some CANDIDATELIST structures. This handle is available when there are candidate strings.
hGuideLine
Memory handle of GuideLine. This memory block has the GUIDELINE structure. This handle is available when there is guideline information.
hPrivate
Memory handle that will be used by the IME for its private data area.
dwNumMsgBuf
Number of messages that are stored in the hMsgBuf.
hMsgBuf
Memory block that stores the messages in TRANSMSG format. The size of the buffer should be able to store the dwNumMsgBuf amount of TRANSMSGs. This buffer was previously defined in Windows 95/98 and Windows NT 4.0 IME document as the format as [Message1] [wParam1] [lParam1] {[Message2] [wParam2] [lParam2]{...{...{...}}}}, andall values are double word for Win32 platforms.
fdwinit
Initialize flag. When an IME initializes the member of the INPUTCONTEXT structure, the IME has to see the bit of this member. The following bits are provided.
Bit Description
INIT_STATUSWNDPOS Initialize ptStatusWndPos.
INIT_CONVERSION Initialize fdwConversion.
INIT_SENTENCE Initialize fdwSentence.
INIT_LOGFONT Initialize lfFont.
INIT_COMPFORM InitializecfCompForm.
INIT_SOFTKBDPOS Initialize ptSoftKbdPos.

dwReserve[3]
Reserved for future use.

Note  During a call to ImeToAsciiEx, an IME can generate the messages into the lpdwTransKey buffer. However, if an IME wants to generate the messages to the application, it can store the messages in hMsgBuf and call ImmGenerateMessage. The ImmGenerateMessage function then sends the messages in hMsgBuf to the application.

COMPOSITIONSTR

The COMPOSITIONSTR structure contains the composition information. During conversion, an IME places conversion information into this structure.

typedef struct tagCOMPOSITIONSTR {
DWORD  dwSize;
DWORD  dwCompReadAttrLen;
DWORD  dwCompReadAttrOffset;
DWORD  dwCompReadClsLen;
DWORD  dwCompReadClsOffset;
DWORD  dwCompReadStrLen;
DWORD  dwCompReadStrOffset;
DWORD  dwCompAttrLen;
DWORD  dwCompAttrOffset;
DWORD  dwCompClsLen;
DWORD  dwCompClsOffset;
DWORD  dwCompStrLen;
DWORD  dwCompStrOffset;
DWORD  dwCursorPos;
DWORD  dwDeltaStart;
DWORD  dwResultReadClsLen;
DWORD  dwResultReadClsOffset;
DWORD  dwResultReadStrLen;
DWORD  dwResultReadStrOffset;
DWORD  dwResultClsLen;
DWORD  dwResultClsOffset;
DWORD  dwResultStrLen;
DWORD  dwResultStrOffset;
DWORD  dwPrivateSize;
DWORD  dwPrivateOffset; 
} COMPOSITIONSTR;

Members

dwSize
Memory block size of this structure.
dwCompReadAttrLen
Length of the attribute information of the reading string of the composition string.
dwCompReadAttrOffset
Offset from the start position of this structure. Attribute information is stored here.
dwCompReadClsLen
Length of the clause information of the reading string of the composition string.
dwCompReadClsOffset
Offset from the start position of this structure. Clause information is stored here.
dwCompReadStrLen
Length of the reading string of the composition string.
dwCompReadStrOffset
Offset from the start position of this structure. Reading string of the composition string is stored here.
dwCompAttrLen
Length of the attribute information of the composition string.
dwCompAttrOffset
Offset from the start position of this structure. Attribute information is stored here.
dwCompClsLen
Length of the clause information of the composition string.
dwCompClsOffset
Offset from the start position of this structure. Clause information is stored here.
dwCompStrLen
Length of the composition string.
dwCompStrOffset
Offset from the start position of this structure. The composition string is stored here.
dwCursorPos
Cursor position in the composition string.
dwDeltaStart
Start position of change in the composition string. If the composition string has changed from the previous state, the first position of such a change is stored here.
dwResultReadClsLen
Length of the clause information of the reading string of the result string.
dwResultReadClsOffset
Offset from the start position of this structure. Clause information is stored here.
dwResultRieadStrLen
Length of the reading string of the result string.
dwResultReadStrOffset
Offset from the start position of this structure. Reading string of the result string is stored at this point.
dwResultClsLen
Length of the clause information of the result string.
dwResultClsOffset
Offset from the start position of this structure. Clause information is stored here.
dwResultStrLen
Length of the result string.
dwResultStrOffset
Offset from the start position of this structure. Result string is stored here.
dwPrivateSize
Private area in this memory block.
dwPrivateOffset
Offset from the start position of this structure. Private area is stored here.

Note  For Unicode: All dw*StrLen members contain the size in Unicode characters of the string in the corresponding buffer. Other dw*Len and dw*Offset members contain the size in bytes of the corresponding buffer.

The format of the attribute information is a single-byte array and specifies the attribute of string. The following values are provided. Those not listed are reserved.

Value Content
ATTR_INPUT Character currently being entered.
ATTR_TERGET_CONVERTED Character currently being converted (already converted).
ATTR_CONVERTED Character given from the conversion.
ATTR_TERGET_NOTCONVERTED Character currently being converted (yet to be converted).
ATTR_FIXEDCONVERTED Characters will not be converted anymore.
ATTR_INPUT_ERROR Character is an error character and cannot be converted by the IME.

Following is a description of the content for the values provided in the preceding table.

Content Description
Character currently being entered. Character that the user is entering. If this is Japanese, this character is a hiragana, katakana, or alphanumeric character that has yet to be converted by the IME.
Character currently being converted (already converted). Character that has been selected for conversion by the user and converted by the IME.
Character given from conversion. Character which the IME has converted.
Character currently being converted (yet to be converted). Character that has been selected for conversion by the user and not yet converted by the IME. If this is Japanese, this character is a hiragana, katakana, or alphanumeric character that the user has entered.
Character is an error character and cannot be converted by the IME. Character is an error character and the IME cannot convert this character. For example, some consonants cannot be combined.

Comments

The length of the attribute information is the same as the length of the string. Each byte corresponds to each byte of the string. Even if the string includes DBCS characters, the attribute information has the information bytes of both the lead byte and the second byte.

For Windows NT Unicode, the length of the attribute information is the same as the length in Unicode character counts. Each attribute byte corresponds to each Unicode character of the string.

The format of the clause information is a double-word array and specifies the numbers that indicate the position of the clause. The position of the clause is the position of the composition string, with the clause starting from this position. At the least, the length of information is two double words. This means the length of the clause information is 8 bytes. The first double word has to be zero and is the start position of the first clause. The last double word has to be the length of this string. For example, if the string has three clauses, the clause information has four double words. The first double word is zero. The second double word specifies the start position of the second clause. The third double word specifies the start position of the third clause. The last double word is the length of this string.

For Windows NT Unicode, the position of each clause and the length of the string is counted in Unicode characters.

The dwCursorPos member specifies the cursor position and indicates where the cursor is located within the composition string, in terms of the count of that character. The counting starts at zero. If the cursor is to be positioned immediately after the composition string, this value should be equal to the length of the composition string. In the event there is no cursor, a value of -1 is specified here. If a composition string does not exist, this member is invalid.

For Windows NT Unicode, the cursor position is counted in Unicode characters.

CANDIDATEINFO

The CANDIDATEINFO structure is a header of the entire candidate information. This structure can contain 32 candidate lists at most, and these candidate lists have to be in the same memory block.

typedef struct tagCANDIDATEINFO {
DWORD  dwSize;
DWORD  dwCount;
DWORD  dwOffset[32];
DWORD  dwPrivateSize;
DWORD  dwPrivateOffset;
} CANDIDATEINFO;

Members

dwSize
Memory block size of this structure.
dwCount
Number of the candidate lists that are included in this memory block.
dwOffset[32]
Contents are the offset from the start position of this structure. Each offset specifies the start position of each candidate list.
dwPrivateSize
Private area in this memory block.
dwPrivateOffset
Offset from the start position of this structure. The private area is stored here.

GUIDELINE

The GUIDELINE structure contains the guideline information that the IME sends out.

typedef struct tagGUIDELINE {
DWORD  dwSize;
DWORD  dwLevel;  // the error level.
// GL_LEVEL_NOGUIDELINE, 
// GL_LEVEL_FATAL, 
// GL_LEVEL_ERROR, 
// GL_LEVEL_WARNNING,
// GL_LEVEL_INFORMATION
    DWORD dwIndex;  // GL_ID_NODICTIONARY and so on.
    DWORD dwStrLen;  // Error Strings, if this is 0, there is no error string.
DWORD  dwStrOffset;
DWORD  dwPrivateSize;
DWORD  dwPrivateOffset;
} GUIDELINE;

Note  For Unicode, the dwStrLen member specifies the size in Unicode characters of the error string. Other size parameters such as dwSize dwStrOffset, dwPrivateSize contain values counted in bytes.

Members

dwLevel
The dwLevel specifies error level. The following values are provided.
Value Description
GL_LEVEL_NOGUIDELINE No guideline present. If the old guideline is shown, the UI should hide the old guideline.
GL_LEVEL_FATAL Fatal error has occurred. Some data may be lost.
GL_LEVEL _ERROR Error has occurred. Handling may not be continued.
GL_LEVEL _WARNING IME warning to user. Something unexpected has occurred, but the IME can continue handling.
GL_LEVEL _INFORMATION Information for the user.

dwIndex
The following values are provided.
Value Description
GL_ID_UNKNOWN Unknown error. The application should refer to the error string.
GL_ID_NOMODULE IME cannot find the module that the IME needs.
GL_ID_NODICTIONARY IME cannot find the dictionary or the dictionary looks strange.
GL_ID_CANNOTSAVE Dictionary or the statistical data cannot be saved.
GL_ID_NOCONVERT IME cannot convert anymore.
GL_ID_TYPINGERROR Typing error. The IME cannot handle this typing.
GL_ID_TOOMANYSTROKE Two many keystrokes for one character or one clause.
GL_ID_READINGCONFLICT Reading conflict has occurred. For example, some vowels cannot be combined.
GL_ID_INPUTREADING IME prompts the user now it is in inputting reading character state.
GL_ID_INPUTRADICAL IME prompts the user now it is in inputting radical character state.
GL_ID_INPUTCODE IME prompts the user to input the character code state.
GL_ID_CHOOSECANIDATE IME prompts the user to select the candidate string state.
GL_ID_REVERSECONVERSION IME prompts the user to provide the information of the reverse conversion. The information of reverse conversion can be obtained through ImmGetGuideLine(hIMC, GGL_PRIVATE. lpBuf, dwBufLen).The information contained in lpBuf is in CANDIDATELIST format.
GL_ID_PRIVATE_FIRST ID located between GL_ID_PRIVATE_FIRST and GL_ID_PRIVATE_LAST is reserved for the IME. The IME can freely use these IDs for its own GUIDELINE.
GL_ID_PRIVATE_LAST ID located between GL_ID_PRIVATE_FIRST and GL_ID_PRIVATE_LAST is reserved for the IME. The IME can freely use these IDs for its own GUIDELINE.

dwPrivateSize
Private area in this memory block.
dwPrivateOffset
Offset from the start position of this structure. The private area is stored here.

IME Management Structures

The following topics describe the structures used to manage IMEs.

IMEINFO

The IMEINFO structure is used internally by IMM and IME interfaces.

typedef struct tagIMEInfo {
    DWORD  dwPrivateDataSize;  // The byte count of private data in an IME context.
    DWORD  fdwProperty;  // The IME property bits. See description below.
    DWORD  fdwConversionCaps;  // The IME conversion mode capability bits.
    DWORD  fdwSentenceCaps;  // The IME sentence mode capability.
    DWORD  fdwUICaps;  // The IME UI capability.
    DWORD  fdwSCSCaps;  // The ImeSetCompositionString capability.
    DWORD  fdwSelectCaps;  // The IME inherit IMC capability.
} IIMEINFO;

Members

dwPrivateDataSize
Byte count of the structure.
fdwProperty
HIWORD of fdwProperty contains the following bits, which are used by the application.
Bit Description
IME_PROP_AT_CARET Bit On indicates that the IME conversion window is at caret position. Bit Off indicates a near caret position operation IME.
IME_PROP_SPECIAL_UI Bit On indicates that the IME has a special UI. The IME should set this bit only when it has an nonstandard UI that an application cannot display. Typically, an IME will not set this flag.
IME_PROP_CANDLIST_START_FROM_1 Bit ON indicates that the UI of the candidate list string starts from zero or 1. An application can draw the candidate list string by adding the 1, 2, 3, and so on in front of the candidate string.
IME_PROP_UNICODE If set, the IME is viewed as Unicode IME. System and IME will communicate through Unicode IME interface. If clear, IME will use ANSI interface to communicate with system.
IME_PROP_COMPLETE_ON_
UNSELECT
New property bit defined for Windows 98 and Windows 2000. If set, the IME will complete the composition string when the IME is deactivated. If clear, the IME will cancel the composition string when the IME is deactivated (such as from a keyboard layout change).

The LOWORD of fdwProperty contains the following bits, which are used by the system.

Bit Description
IME_PROP_END_UNLOAD Bit On indicates that the IME will unload when there is no one using it.
IME_PROP_KBD_CHAR_FIRST Before the IME translates the DBCS character, the system first translates the characters by keyboard. This character is passed to the IME as an information aid. No aid information is provided when this bit is off.
IME_PROP_NEED_ALTKEY IME needs the ALT key passed to ImeProcessKey.
IME_PROP_IGNORE_UPKEYS IME does not need the UP key passed to ImeProcessKey.
IME_PROP_ACCEPT_WIDE_VKEY Windows 2000: If set, the IME processes the injected Unicode that came from the SendInput function by using VK_PACKET. If clear, IME might not process the injected Unicode and the injected Unicode might be sent to application directly.

fdwConversionCaps
Same definition as the conversion mode. If the relative bit is off, the IME does not have the capability to handle the conversion mode no matter whether the corresponding bit of the conversion mode is on or off.
Conversion mode Description
IME_CMODE_KATAKANA Bit On indicates that the IME supports KATAKANA mode. Otherwise, it does not.
IME_CMODE_NATIVE Bit On indicates that the IME supports NATIVE mode. Otherwise, it does not.
IME_CMODE_FULLSHAPE Bit On indicates that the IME supports full shape mode. Otherwise, it does not.
IME_CMODE_ROMAN Bit On indicates that the IME supports ROMAN input mode. Otherwise, it does not.
IME_CMODE_CHARCODE Bit On indicates that the IME supports CODE input mode. Otherwise, it does not.
IME_CMODE_HANJACONVERT Bit On indicates that the IME supports HANJA convert mode. Otherwise, it does not.
IME_CMODE_SOFTKBD Bit On indicates that the IME supports soft keyboard mode. Otherwise, it does not.
IME_CMODE_NOCONVERSION Bit On indicates that the IME supports No-conversion mode. Otherwise, it does not.
IME_CMODE_EUDC Bit On indicates that the IME the IME supports EUDC mode. Otherwise, it does not.
IME_CMODE_SYMBOL Bit On indicates that the IME supports SYMBOL mode. Otherwise, it does not.
IME_CMODE_CHARCODE Set to 1 if the IME supports character code input mode, but zero if it does not.
IME_CMODE_FIXED Set to 1 if the IME supports fixed conversion mode, but zero if not. This mode allows preconversion by the IME, but not full conversion. An example of this is Fixed Conversion Mode with DBCS HIRAGANA ROMAN. Under this mode, the IME can convert key input characters to DBCS HIRAGANA by Roman Conversion. However, it prevents conversion from DBCS HIRAGANA to Kanji characters.

fdwSentenceCaps
Same constant definition as the sentence mode. If the relative bit is off, the IME does not have the capability to handle the sentence mode no matter if the corresponding bit of sentence mode is on or off.
Conversion mode Description
IME_SMODE_PLAURALCLAUSE Bit On indicates that the IME supports plural clause sentence mode.
IME_SMODE_SINGLECONVERT Bit On indicates that the IME supports single character sentence mode.
IME_SMODE_AUTOMETIC Bit On indicates that the IME supports automatic sentence mode.
IME_SMODE_PHRASEPREDICT Bit On indicates that the IME supports phrase predict sentence mode.
IME_SMODE_CONVERSATION IME uses conversation mode. This is useful for chat applications. Chat applications can change the sentence mode of the IME to conversation style. This is a new mode for Windows 98 and Windows 2000.

fdwUICaps
The fdwUICaps bits specify the UI ability of the IME. The following bits are provided.
Bit Description
UI_CAP_2700 UI supported when LogFont escape is zero or 2700.
UI_CAP_ROT90 UI supported when LogFont escape is zero, 900, 1800, or 2700.
UI_CAP_ROTANY UI supported with any escape.
UI_CAP_SOFKBD IME uses soft keyboard provided by the system.

fdwSCSCaps
The fdwSCSCaps bits specify the SetCompositionString capability that the IME has. The following bits are provided.
Bit Description
SCS_CAP_COMPSTR IME can generate the composition string by SCS_SETSTR.
SCS_CAP_MAKEREAD When calling ImmSetCompositionString with SCS_SETSTR, the IME can create the reading of the composition string without lpRead. Under the IME that has this capability, the application does not need to set lpRead for SCS_SETSTR.

fdwSelectCaps
The fdwSelectCaps capability is for the application. When a user changes the IME, the application can determine if the conversion mode will be inherited or not by checking this capability. If the newly selected IME does not have this capability, the application will not receive the new mode and will have to retrieve the mode again. The following bits are provided.
Bit Description
SELECT_CAP_CONVMODE IME has the capability of inheritance of conversion mode at ImeSelect.
SELECT_CAP_SENTENCE IME has the capability of inheritance of sentence mode at ImeSelect.

Structures Used for IME Communication

The following topics describe the structures used for communication with IMEs.

CANDIDATELIST

The CANDIDATELIST structure contains information about a candidate list.

typedef struct tagCANDIDATELIST {
    DWORD  dwSize;  // the size of this data structure.
    DWORD  dwStyle;  // the style of candidate strings.
    DWORD  dwCount;  // the number of the candidate strings.
    DWORD  dwSelection;  // index of a candidate string now selected.
    DWORD  dwPageStart;  // index of the first candidate string show in the candidate window. It maybe varies with page up or page down key.
    DWORD  dwPageSize;  // the preference number of the candidate strings shows in one page.
    DWORD  dwOffset[];  // the start positions of the first candidate strings. Start positions of other (2nd, 3rd, ..) candidate strings are appened after this field. IME can do this by reallocating the hCandInfo memory handle. So IME can access dwOffset[2] (3rd candidate string) or dwOffset[5] (6st candidate string).
// TCHAR  chCandidateStr[];  // the array of the candidate strings.
} CANDIDATELIST;

Members

dwsize
Size, in bytes, of the structure, the offset array, and all candidate strings.
dwStyle
Candidate style values. It can be one or more of the following values.
Value Meaning
IME_CAND_UNKNOWN Candidates are in a style other than listed here.
IME_CAND_READ Candidates have the same reading.
IME_CAND_CODE Candidates are in one code range.
IME_CAND_MEANING Candidates have the same meaning.
IME_CAND_RADICAL Candidates are composed of same radical character.
IME_CAND_STROKES Candidates are composed of same number of strokes.

For the IME_CAND_CODE style, the candidate list has a special structure depending on the value of the dwCount member. If dwCount is 1, the dwOffset member contains a single DBCS character rather than an offset, and no candidate string is provided. If the dwCount member is greater than 1, the dwOffset member contains valid offsets, and the candidate strings are text representations of individual DBCS character values in hexadecimal notation.

dwCount
Number of candidate strings.
dwSelection
Index of the selected candidate string.
dwPageStart
Index of the first candidate string in the candidate window. This varies as the user presses the Page Up and Page Down keys.
dwPageSize
Number of candidate strings to be shown in one page in the candidate window. The user can move to the next page by pressing IME-defined keys, such as the Page Up or Page Down key. If this number is zero, an application can define a proper value by itself.
dwOffset
Offset to the start of the first candidate string, relative to the start of this structure. The offsets for subsequent strings immediately follow this member, forming an array of 32-bit offsets.

Comments

The CANDIDATELIST structure is used for the return of ImmGetCandidateList . The candidate strings immediately follow the last offset in the dwOffset array.

COMPOSITIONFORM

The COMPOSITIONFORM structure is used for IMC_SETCOMPOSITIONWINDOW and IMC_SETCANDIDATEPOS messages.

typedef tagCOMPOSITIONFORM {
DWORD  dwStyle;
POINT  ptCurrentPos;
RECT  rcArea;
}COMPOSITIONFORM;

Members

dwStyle
Position style. The following values are provided.
Value Meaning
CFS_DEFAULT Move the composition window to the default position. The IME window can display the composition window outside the client area, such as in a floating window.
CFS_FORCE_POSITION Display the upper-left corner of the composition window at exactly the position given by ptCurrentPos. The coordinates are relative to the upper-left corner of the window containing the composition window and are not subject to adjustment by the IME.
CFS_POINT Display the upper-left corner of the composition window at the position given by ptCurrentPos. The coordinates are relative to the upper-left corner of the window containing the composition window and are subject to adjustment by the IME.
CFS_RECT Display the composition window at the position given by rcArea. The coordinates are relative to the upper-left of the window containing the composition window.

ptCurrentPos
Coordinates of the upper-left corner of the composition window.
rcArea
Coordinates of the upper-left and lower-right corners of the composition window.

Comments

When the style of the COMPOSITIONFORM structure is CFS_POINT or CFS_FORCE_POINT, the IME will draw the composition string from the position specified by ptCurrentPos of the COMPOSITIONFORM structure that is given by the application. If the style has CFS_RECT, the composition string will be inside the rectangle specified by rcArea. If not, rcArea will be the client rectangle of the application window.

When the application specifies the composition font, the composition window is rotated as the escapement of the composition font. The direction of the composition string follows the escapement of the font in a composition window. The IME then draws the composition string. Following is an example of this process using various values for the escapement of the composition font:

  • Escapement of the composition font is zero

    Typically, the escapement of the composition font is zero. When this is the case, ptCurrentPos of the composition form structure points to the left and top of the string. All IMEs support this type.

  • Escapement of the composition font is 2700

    This is in the case of a vertical writing. When the application provides the vertical writing, the application can set the 2700 escapement in the composition font set by ImmCompositoinFont. The composition string will then be drawn downward. IMEs that have UI_CAP_2700, UI_CAP_ROT90, or UI_CAP_ROTANY capability will support this type of composition window.

  • Escapement of the composition font is 900 or 1800

    IMEs that have UI_CAP_ROT90 or UI_CAP_ROTANY capability will support this type of composition window.

  • Escapement of the composition font is any value

    IMEs that have UI_CAP_ROTANY capability will support this type of composition window.

Note  UI_CAP_ROT90 and UI_CAPS_ANY are the option for the enhancement of the IME. UI_CAP_2700 is recommended.

CANDIDATEFORM

The CANDIDATEFORM structure is used for IMC_GETCANDIDATEPOS and IMC_SETCANDIDATEPOS messages.

typedef tagCANDIDATEFORM {
DWORD  dwIndex;
DWORD  dwStyle;
POINT  ptCurrentPos;
REC  rcArea;
} CANDIDATEFORM;

Members

dwIndex
Specifies the ID of the candidate list. Zero is the first candidate list, 1 is the second one, and so on up to 3.
dwStyle
Specifies CFS_CANDIDATEPOS or CFS_EXCLUDE. For a near-caret IME, the dwStyle also can be CFS_DEFAULT. A near-caret IME will adjust the candidate position according to other UI components, if the dwStyle is CFS_DEFAULT.
ptCurrentPos
Depends on dwStyle. When dwStyle is CFS_CANDIDATEPOS, ptCurrentPos specifies the recommended position where the candidate list window should be displayed. When dwStyle is CFS_EXCLUDE, ptCurrentPos specifies the current position of the point of interest (typically the caret position).
rcArea
Specifies a rectangle where no display is allowed for candidate windows in the case of CFS_EXCLUDE.

STYLEBUF

The STYLEBUF structure contains the identifier and name of a style.

typedef struct tagSTYLEBUF {
DWORD  dwStyle;
TCHAR  szDescription[32]
} STYLEBUF;

Members

dwStyle
Style of register word.
szDescription
Description string of this style.

Note  The style of the register string includes IME_REGWORD_STYLE_EUDC. The string is in EUDC range:

IME_REGWORD_STYLE_USER_FIRST and IME_REGWORD_STYLE_USER_LAST.

The constants range from IME_REGWORD_STYLE_USER_FIRST to IME_REGWORD_STYLE_USER_LAST and are for private IME ISV styles. The IME ISV can freely define its own style.

SOFTKBDDATA

The SOFTKBDDATA defines the DBCS codes for each virtual key.

typedef struct tagSOFTKBDDATA {
UINT  uCount;
WORD  wCode[][256]
} SOFTKBDDATA;

Members

uCount
Number of the 256-word virtual key mapping to the internal code array.
wCode[][256]
256-word virtual key mapping to the internal code array. There may be more than one 256-word arrays.

Note  It is possible for one type of soft keyboard to use two 256-word arrays. One is for the nonshift state and the other is for the shift state. The soft keyboard can use two internal codes for displaying one virtual key.

RECONVERTSTRING

The RECONVERTSTRING structure defines the strings for IME reconversion. It is the first item in a memory block that contains the strings for reconversion.

typedef struct _tagRECONVERTSTRING {
DWOPD  dwSize;
DWORD  dwVersion;
DWORD  dwStrLen;
DWORD  dwStrOffset;
DWORD  dwCompStrLen;
DWORD  dwCompStrOffset;
DWORD  dwTargetStrLen;
DWORD  dwTargetStrOffset;
} RECONVERTSTRING;

Members

dwSize
Memory block size of this structure.
dwVersion
Reserved by the system. This must be zero.
dwStrlen
Length of the string that contains the composition string.
dwStrOffset
Offset from the start position of this structure. The string containing the reconverted words is stored at this point.
dwCompStrLen
Length of the string that will be the composition string.
dwCompStrOffset
Offset of the string that will be the composition string.
dwTargetStrLen
Length of the string that is related to the target clause in the composition string.
dwTargetStrOffset
Offset of the string that is related to the target clause in the composition string.

Note  The RECONVERTSTRING structure is a new structure for Windows 98 and Windows 2000. The dwCompStrOffset and dwTargetOffset members are the relative position of dwStrOffset. For Windows NT Unicode, dwStrLen, dwCompStrLen, and dwTargetStrLen are the TCHAR count, and dwStrOffset, dwCompStrOffset, and dwTargetStrOffset are the byte offset.

Comments

If an application starts the reconversion process by calling ImmSetCompositionString with SCS_SETRECONVERTSTRING and SCS_QUERYRECONVERTSTRING, the application is then responsible for allocating the necessary memory for this structure as well as the composition string buffer. The IME should not use the memory later. If the IME starts the process, it should allocate the necessary memory for the structure and the composition string buffer.

IMEMENUITEMINFO

The IMEMENUITEMINFO structure contains information about IME menu items.

typedef _tagIMEMENUITEMINFO {
UINT  cbSize;
UINT  fType;
UINT  fState;
UINT  wID;
HBITMAP  hbmpChecked;
HBITMAP  hbmpUnchecked;
DWORD  dwItemData;
TCHAR  szString[48];
HBITMAP  hbmpItem;
} IMEMENUITEMINFO;

Members

cbSize
Size of the structure in bytes
fType
Menu item type. This member can be one or more of the following values.
Value Meaning
IMFT_RADIOCHECK Displays checked menu items using a radio-button mark instead of a check mark if the hbmpChecked member is NULL.
IMFT_SEPARATOR Specifies that the menu item is a separator. A menu item separator appears as a horizontal dividing line. The hbmpItem and szString members are ignored.
IMFT_SUBMENU Specifies that the menu item is a submenu.

fState
Menu item state. This member can be one or more of the following values.
Value Meaning
IMFS_CHECKED Checks the menu item. For more information about checked menu items. See the hbmpChecked member.
IMFS_DEFAULT Specifies that the menu item is the default. A menu can contain only one default menu item, which is displayed in bold.
IMFS_DISABLED Disables the menu item so it cannot be selected, but does not gray it out.
IMFS_ENABLED Enables the menu item so it can be selected. This is the default state.
IMFS_GRAYED Disables the menu item and grays it out so it cannot be selected.
IMFS_HILITE Highlights the menu item.
IMFS_UNCHECKED Unchecks the menu item. For more information about unchecked menu items, see the hbmpUnchecked member.
IMFS_UNHILITE Removes the highlight from the menu item. This is the default state.

wID
Application-defined 16-bit value that identifies the menu item.
hbmpChecked
Handle to the bitmap to display next to the item if it is checked. If this member is NULL, a default bitmap is used. If the IMFT_RADIOCHECK type value is specified, the default bitmap is a bullet. Otherwise, it is a check mark.
hbmpUnchecked
Handle to the bitmap to display next to the item if it is not checked. If this member is NULL, no bitmap is used.
dwItemData
Application-defined value associated with the menu item.
szString
Content of the menu item. This member is a null-terminated string.
hbmpItem
Bitmap handle to display.

Note  The IMEMENUITEMINFO structure is a new structure for Windows 98 and Windows 2000. The Unicode version of this structure has the szString member as the WCHAR.

TRANSMSG

The TRANSMSG structure contains transferred message, used by ImeToAsciiEx to receive IME generated message.

typedef _tagTRANSMSG {
UINT  message;
WPARAM  wParam;
LPARAM  lParam;
} TRANSMSG;

Members

message
Specify message identify
wParam
Specify additional information about the message. The exact meaning depends on the value of the message member.
lParam
Specify additional information about the message. The exact meaning depends on the value of the message member.

Note  This structure is added for future 64-bit Windows NT platform. This structure will be used together with TRANSMSGLIST by ImeToAsciiEx to replace the formerly used LPDWORD lpdwTransBuf. Using this structure will still keep the data in memory with the same offset and keep backward compatible.

TRANSMSGLIST

The TRANSMSGLIST structure contains transferred message list returned from ImeToAsciiEx.

typedef _tagTRANSMSGLIST {
UINT  uMsgCount;
TRANSMSG  TransMsg[1];
} TRANSMSGLIST;

Members

uMsgCount
Specify the message number in TransMsg array.
TransMsg
Includes TRANSMSG data array.

Note  This structure is added for future 64-bit Windows NT platform. This structure will be used by ImeToAsciiEx to replace the formerly used LPDWORD lpdwTransBuf. Using this structure will still keep the data in memory with the same offset and keep backward compatible.



AND

출처: http://blog.naver.com/stweed?Redirect=Log&logNo=30013921792

etAsyncKeyState()
함수 와 GetKeyState()함수는 키보드의 키가 눌렸는지를

체크하는 함수들이다.

GetAsyncKeyState() 함수는 비 동기(Asynchronism)로 처리한다.

즉, 호출된 시점에서 키 상태를 조사하여, 메시지 큐를 거치지 않고 바로 리턴을 해 주므로 

키 입력을 바로 처리해 줄 수가 있다.

GetKeyState() 함수는 호출된 시점에서 메시지 큐를 거치며, 메시지 발생 후의 상태를

리턴하게 되므로, 키보드 메시지 처리 루틴내에서 사용해야 한다.

 

게임과 같이 키 입력에 바로 반응을 해 줘야 하는 프로그램에서는 GetAsyncKeyState()함수

를 사용하는 편이 좋다.

 

GetAsyncKeyState()함수의 사용은

 

if( GetAsyncKeyState(VK_RETURN) )  //enter 키가 눌렀다면

//처리        }

 

이렇게 직접 쓰여도 되지만, 아래와 같은 형식으로 많이 사용한다.

 

if(  GetAsyncKeyState(VK_RETURN) & 0x8000 ) //enter 키가 눌렀다면

//처리   }

 

왜??? 0x8000 으로 AND 연산을 통하여 키눌림을 체크할까??

GetAsyncKeyState() 함수는, 키가 눌려진 시점에서  0x8000 값을 리턴해 준다.

그리고 함수가 호출되었을때 키가 눌려져 있었다고 0x0001 값을 리턴해 준다.

즉, 0x8000 은 현재 키가 눌려진 상태를 뜻하고, 0x0001은 지난번 호출과 이번 호출사이에

키가 눌려진 적이 있었다라는 것을 뜻한다.

예를 들어, 아래 방향키가 게임내에서 비행기도 움직이고, 메뉴에서 위아래 선택에도

쓰인다고 가정해 보자.

AND 연산없이 그냥 사용하여 비행기를 움직이다가, F1키를 눌러 메뉴를 띄웠을 때 커서가

자동으로 아래쪽으로 내려갈 위험성이 생긴다.

왜냐하면, F1키를  누르는 시점에서 - if( GetAsyncKeyState(VK_F1) ) - VK_DOWN 은 

눌리지 않았지만 리턴값이 0x0001이 되어 if( GetAsyncKeyState(VK_F1) ) 전에 호출된

if( GetAsyncKeyState(VK_DOWN) )이 참이 되기 때문이다.

하지만, 0x8000으로 AND연산을 하면

 

    1000 0000 0000 0000  (키눌림 0x8000)         0000 0000 0000 0001 (눌려진적이 있음 0x0001)

 & 1000 0000 0000 0000  (AND 연산 0x8000)   &1000 0000 0000 0000  (AND 연산 0x8000) 

----------------------                            ---------------------

    1000 0000 0000 0000  (키눌림 0x8000)         0000 0000 0000 0000  (키 안 눌림)

 

위와 같은 결과가 되어, 정확한 시점에서 키가 눌려진 상태를 체크할 수가 있는 것이다.

즉, 정확한 시점에서 키눌림 상태를 체크하기 위해서 0x8000 으로 AND 연산을

해 주는 것이다.

 

GetKeyState() 함수의 사용 예:

------------------------------------------------------------------------------------------

//키보드 메시지 처리루틴이 있는 콜백함수 내에서...

//char szTemp[256];

case WM_KEYDOWN:
  //Ctrl+ 왼쪽 화살표키가 눌렸는지 조사

  if( (wParam==VK_LEFT) && (GetKeyState(VK_CONTROL)<0) )
  {
     wsprintf(szTemp,"Ctrl
키와 왼쪽화살표키가 눌림");
  }

  return 0;

----------------------------------------------------------------------------

GetKeyState()함수의 리턴값이 음수일 경우는 해당키가 눌린 상태이고, 음수가 아닐 경우는

해당키가 눌리지 않은 상태이다. 


AND

출처 : http://blog.naver.com/silver6688?Redirect=Log&logNo=60051209034

GetAsyncKeyState와 GetKeyState의 차이점
GetAsyncKeyState와 GetKeyState는 둘 다 키의 상태값을 알아내는 함수이다.
하지만 이 둘 사이에는 차이점이 있는데 다음과 같은 것들이다.

GetAsyncKeyState는 "키가 눌렸는가?"와 "언제부터 눌렸는가?"를 알아낼 때 사용한다.
키가 눌렸을 때 GetAsyncKeyState는 0x8000 bit가 1이된다.
그리고, 이전에 GetAsyncKeyState가 호출되었을 때부터 이번에 GetAsyncKeyState가 호출될 때까지
중간에 끊기지 않고 계속 눌려있는 상태라면 0x0001 bit는 0이 되고, 그렇지 않은 경우는 1이 된다.

1) CTRL 키가 눌린 상태이다.
2) GetAsyncKeyState(VK_CONTROL)를 호출하면 0x8001을 리턴한다.
3) GetAsycnKeyState(VK_CONTROL)을 한번 더 호출하면 0x8000을 리턴한다.

1) CTRL 키가 눌린 상태이다.
2) GetAsyncKeyState(VK_CONTROL)를 호출하면 0x8001을 리턴한다.
3) CTRL 키를 뗬다가 다시 눌렸다.
4) GetAsycnKeyState(VK_CONTROL)을 한번 더 호출해도 0x8001을 리턴한다.

키가 눌리지 않았을 때, GetAsyncKeyState는 항상 0x0000을 리턴한다.

SHORT GetKeyState(      
    int nVirtKey
);

Return Value

The return value specifies the status of the specified virtual key, as follows:

  • If the high-order bit is 1, the key is down; otherwise, it is up.
  • If the low-order bit is 1, the key is toggled. A key, such as the CAPS LOCK key, is toggled if it is turned on.
  • The key is off and untoggled if the low-order bit is 0. A toggle key's indicator light (if any) on the keyboard will be on
  • when the key is toggled, and off when the key is untoggled.

GetKeyState는 "키가 눌렸는가?"와 "키의 토글상태가 무엇인가?"를 알아낼 때 사용한다.
키의 토글 상태란 Caps Lock, Num Lock의 키가 한번 누르면 불이 켜지고
다시 한번 누르면 불이 꺼지는 것을 생각하면 이해가 빠를것 같다.
키보드 상에는 위에서 말한 키만 불이 켜졌다 꺼졌다하면서 토글상태를 알려주고 있지만
다른 키들도 토글 상태를 갖고 있으며 단지 우리 눈에 보이지 않을 뿐이다.
이 토글 상태를 GetKeyState 함수로 알아낼 수 있다.

GetKeyState의 리턴값은 SHORT가 아닌 CHAR로 생각된다.
리턴값을 살펴보면 0xffffff81, 0xffffff80, 0x00000001, 0x00000000이
되는 것을 볼 수 있기 때문이다.
참고로 같은 SHORT형을 리턴하는 GetAsyncKeyState의 리턴값은 다음과 같다.
0xffff8001, 0xffff8000, 0x00000000 셋 중 하나

** MSDN에는 현재 하드웨어(키보드)의 상태값을 알아내길 원한다면
GetAsyncKeyState를 사용하라고 나와있다. GetKeyState는
메시지큐에 저장된 메시지에 따라 값이 변하기 때문이다.
메시지큐에 처리되지 않은 CTRL키가 눌렸다는 메시지가 쌓여있을 때,
사용자가 CTRL키를 더이상 누르지 않고 있다면.
GetAsyncKeyState는 "키가 눌리지 않았음"을,
GetKeyState는 "키가 눌렸음"을 리턴할 것이다.
////////////////////////////////////////////////////////////////////
ex)
 
if( ( ::GetKeyState( VK_MENU ) & 0x8000 ) > 0 )
{
     ::MessageBox( NULL, _T("ALT 키다 눌렷다~"), NULL, NULL );
}

////////////////////////////////////////////////////////////////////////////////////

GetAsyncKeyState는 윈도우즈 메시지 루프를 사용하지 않는 곳 (예를 들면 쓰레드, PeekMessage의 Idle 처리 등)에서 사용하죠




AND

출처: http://cafe.naver.com/sg0101.cafe?iframe_url=/ArticleRead.nhn%3Farticleid=36

GetForegroundWindow - 현재 활성화된 윈도 핸들 얻기
 keybd_event - 키값 보내기

 

사용 예

 

 HWND hwnd = GetForegroundWindow(); // 현재 활성화 된 윈도우의 핸들 얻기
 unsigned char a = VK_LWIN ; // 윈도 메뉴창 키 값
 keybd_event(a, 0, KEYEVENTF_EXTENDEDKEY, 0); // 키 누름
 keybd_event(a, 0, KEYEVENTF_EXTENDEDKEY | KEYEVENTF_KEYUP, 0); // 키 뗌

 

키 값은 평소에 쉽게 쓰는 WM_CHAR나 WM_KEYDOWN, WM_KEYUP과 동일한 키 값 사용

 

예를 들어 a의 키값은 0x41, b의 키값은 0x42.......


AND

출처: http://cafe.naver.com/ssua.cafe?iframe_url=/ArticleRead.nhn%3Farticleid=66

VC++ Virual KeyValue | MFC
전체공개 2006.06.06 18:37

출처 : http://cafe.naver.com/trisquare.cafe

 


 

 
- 사용함수 예 : BOOL GetKeyboardState(PBYTE lpKeyState);
               *** 이 함수는 한번에 키보드의 모든 자판의 눌림 상태를 검사하는 함수 이다.
 
   BYTE   byKeyState[256];
 
   if(GetKeyboardState(byKeyState))   // 인자로 256개의 Byte 배열을 요구한다.
   {
      if(byKeyState[13] & 0x80)         // Enter키가 눌려저 있는지 검사
      {
      }
   }


상위 4비트는 물리적인 키눌림여부를 알려주고 ( 최상위비트 1: 키눌림, 0: 키 안눌림)
하위 4비트는 토글 여부를 알려준다. (최하위비트 1: toggle, 0: untoggle) (불들어오면 toggle, 꺼지면 untoggle)
참고로 capslock과같은 toggle키 외 다른키도 이 토글 여부 비트가 설정되지만
         무시해주세염




AND