⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 im.cpp

📁 WinCE5.0下软键盘LARGEKB源代码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this source code is subject to the terms of the Microsoft end-user
// license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
// If you did not accept the terms of the EULA, you are not authorized to use
// this source code. For a copy of the EULA, please see the LICENSE.RTF on your
// install media.
//
//
//
/*++


Module Name:

    im.cpp

Abstract:

    Sample LSIP Input Method.


Revision History:

--*/


#define INITGUID
#include <windows.h>
#include <coguid.h>
#undef INITGUID
#include <commctrl.h>
#include <sipapi.h>
#include "resource.h"
#include "dllmain.h"
#include "im.h"


#ifdef DEBUG

DBGPARAM dpCurSettings = {
    TEXT("DynamicIM"), {
    TEXT("Init"),TEXT("Keys"),TEXT(""),TEXT(""),
    TEXT(""),TEXT(""),TEXT(""),TEXT(""),
    TEXT(""),TEXT(""),TEXT("Interface"),TEXT("Misc"),
    TEXT("Alloc"),    TEXT("Function"), TEXT("Warning"),  TEXT("Error") },
    0x00000000
};
#else
DWORD   v_dwDebugFlag = 0x0;     // Allow some retail debug zones.
#endif // DEBUG


//
// The KEYENTRY structure describes a single key on the keyboard.
//
typedef struct {
    UINT    bVk;        // If VK then just a byte, -1 for sentinel
    UINT    wcUnshift;
    UINT    wcShift;
    UINT    nCtrl;
    DWORD   fdwFlags;
    int     nLeft;
} KEYENTRY;

#define NUM_ROWS    6
KEYENTRY g_keys[NUM_ROWS][16+1] = {
    // First Row
    {
        { VK_ESCAPE,    0,      0,       NO_CTL, F_VK,             0 },
        { VK_F1,        0,      0,       NO_CTL, F_VK,            29 },
        { VK_F2,        0,      0,       NO_CTL, F_VK,            58 },
        { VK_F3,        0,      0,       NO_CTL, F_VK,            87 },
        { VK_F4,        0,      0,       NO_CTL, F_VK,           116 },
        { VK_F5,        0,      0,       NO_CTL, F_VK,           145 },
        { VK_F6,        0,      0,       NO_CTL, F_VK,           174 },
        { VK_F7,        0,      0,       NO_CTL, F_VK,           203 },
        { VK_F8,        0,      0,       NO_CTL, F_VK,           232 },
        { VK_F9,        0,      0,       NO_CTL, F_VK,           261 },
        { VK_F10,       0,      0,       NO_CTL, F_VK,           290 },
        { VK_F11,       0,      0,       NO_CTL, F_VK,           319 },
        { VK_F12,       0,      0,       NO_CTL, F_VK,           348 },
        { VK_HOME,      0,      0,       NO_CTL, F_VK,           377 },
        { VK_END,       0,      0,       NO_CTL, F_VK,           406 },
        { VK_END/*PROP*/,0,     0,       NO_CTL, F_VK,           435 },
        // The above key should eventually be changed to something besides VK_END
        //  as soon as its purpose is clearly determined. */
        { SENTINEL,     0,      0,       NO_CTL, F_VK,           462 }
    },

    // Second row
    {
        { VK_BACKQUOTE, '`',    '~',     NO_CTL, 0,             0 },
        { '1',          '1',    '!',     NO_CTL, 0,               33 },
        { '2',          '2',    '@',     0,      0,               66 },
        { '3',          '3',    '#',     NO_CTL, 0,               99 },
        { '4',          '4',    '$',     NO_CTL, 0,              132 },
        { '5',          '5',    '%',     NO_CTL, 0,              165 },
        { '6',          '6',    '^',     30,     0,              198 },
        { '7',          '7',    '&',     NO_CTL, 0,              231 },
        { '8',          '8',    '*',     NO_CTL, 0,              264 },
        { '9',          '9',    '(',     NO_CTL, 0,              297 },
        { '0',          '0',    ')',     NO_CTL, 0,              330 },
        { VK_HYPHEN,    '-',    '_',     31,     0,              363 },
        { VK_EQUAL,     '=',    '+',     NO_CTL, 0,              396 },
        { VK_BACK,      '\x8',  '\x8',   127,    0,              429 },
        { SENTINEL,     0,      0,       NO_CTL, 0,              462 }
    },

    // Third row
    {
        { VK_TAB,       '\t',   '\t',    '\t',   0,              0   },
        { 'Q',          'q',    'Q',     17,     0,              33  },
        { 'W',          'w',    'W',     23,     0,              66  },
        { 'E',          'e',    'E',     5,      0,              99  },
        { 'R',          'r',    'R',     18,     0,              132 },
        { 'T',          't',    'T',     20,     0,              165 },
        { 'Y',          'y',    'Y',     25,     0,              198 },
        { 'U',          'u',    'U',     21,     0,              231 },
        { 'I',          'i',    'I',     9,      0,              264 },
        { 'O',          'o',    'O',     15,     0,              297 },
        { 'P',          'p',    'P',     16,     0,              330 },
        { VK_LBRACKET,  '[',    '{',     27,     0,              363 },
        { VK_RBRACKET,  ']',    '}',     29,     0,              396 },
        { VK_BACKSLASH, '\\',   '|',     28,     0,              429 },
        { SENTINEL,     0,      0,       NO_CTL, 0,              462 }
    },

    // Forth row
    {
        { VK_CAPITAL,   0,      0,      NO_CTL, F_VK | F_STK | F_REDRAW, 0 },
        { 'A',          'a',    'A',    1,      0,              33  },
        { 'S',          's',    'S',    19,     0,              66  },
        { 'D',          'd',    'D',    4,      0,              99  },
        { 'F',          'f',    'F',    6,      0,              132 },
        { 'G',          'g',    'G',    7,      0,              165 },
        { 'H',          'h',    'H',    8,      0,              198 },
        { 'J',          'j',    'J',    10,     0,              231 },
        { 'K',          'k',    'K',    11,     0,              264 },
        { 'L',          'l',    'L',    12,     0,              297 },
        { VK_SEMICOLON, ';',    ':',    NO_CTL, 0,              330 },
        { VK_APOSTROPHE,'\'',   '\"',   NO_CTL, 0,              363 },
        { VK_RETURN,    '\xD',  '\xD',  10,     0,              396 },
        { SENTINEL,     0,      0,      NO_CTL, 0,              462 }

    },

    // Fifth row
    {
        { VK_SHIFT,     0,      0,       NO_CTL, F_VK | F_STK | F_REDRAW, 0 },
        { 'Z',          'z',    'Z',     26,     0,              33  },
        { 'X',          'x',    'X',     24,     0,              66  },
        { 'C',          'c',    'C',     3,      0,              99  },
        { 'V',          'v',    'V',     22,     0,              132 },
        { 'B',          'b',    'B',     2,      0,              165 },
        { 'N',          'n',    'N',     14,     0,              198 },
        { 'M',          'm',    'M',     13,     0,              231 },
        { VK_COMMA,     ',',    '<',     NO_CTL, 0,              264 },
        { VK_PERIOD,    '.',    '>',     NO_CTL, 0,              297 },
        { VK_SLASH,     '/',    '?',     NO_CTL, 0,              330 },
        { VK_UP,        0,      0,       NO_CTL, 0,              363 },
        { VK_UP /**/,   0,      0,       NO_CTL, 0,              396 },
        { VK_PRIOR,     0,      0,       NO_CTL, 0,              429 },
        { SENTINEL,     0,      0,       NO_CTL, 0,              462 }
    },

    // Sixth row
    {
        { VK_CONTROL,   0,      0,       NO_CTL, F_VK | F_STK,     0 },
        { VK_LWIN,      0,      0,       0,      F_VK,            33 },
        { VK_LMENU,     0,      0,       0,      F_VK | F_STK,    66 },
        { VK_SPACE,     ' ',    ' ',     32,     0,               99 },
        { VK_INSERT,    0,      0,       NO_CTL, 0,              264 },
        { VK_DELETE,    0,      0,       NO_CTL, 0,              297 },
        { VK_LEFT,      0,      0,       NO_CTL, 0,              330 },
        { VK_DOWN,      0,      0,       NO_CTL, 0,              363 },
        { VK_RIGHT,     0,      0,       NO_CTL, 0,              396 },
        { VK_NEXT,      0,      0,       NO_CTL, 0,              429 },
        { SENTINEL,     0,      0,       NO_CTL, 0,              462 }
    },
};

static int g_RowCoord[8] = { 0, 29, 62, 95, 128, 161, 194, 0xFFFF };


//
// Globals.
//
static TCHAR const g_pwszClassName[] = TEXT("A523DFC7-1A7E-4af6-991A-510E75847828 - MicrosoftIMWndClass");
static HWND g_hwndMain;
static HDC  g_hdcKeybd;
static HBITMAP g_hbmKeybd, g_hbmOld;
static IIMCallback *g_pIMCallback;
static int g_nDown;				//普通按键是否被按下
static BOOL g_fControlDown;		//Control键是否按下
static BOOL g_fCapsLockDown;	//CapsLock键是否按下
static BOOL g_fShiftDown;		//Shift键是否按下
static BOOL g_fAltDown;			//Alt键是否按下



//
// Draw the key in the up/down position based on fPress 根据弹起或按下处的fPress值,绘制此处的按键
//
void IM_DrawKey(KEYENTRY *pKey, RECT *prc, BOOL fPress)
{
    HDC hdc;
    RECT rc;
    int Offset = 0;			//绘制键盘需要绘制BMP的上半部分还是下半部分键盘

    hdc = GetDC(g_hwndMain);

    rc = *prc;

    InflateRect(&rc, -1, -1);

    if (g_fShiftDown ^ g_fCapsLockDown) {
        Offset = 195;
    }

    BitBlt(hdc, rc.left, rc.top, rc.right - rc.left + 1, rc.bottom - rc.top + 1,
           g_hdcKeybd,  rc.left, rc.top + Offset, fPress ? NOTSRCCOPY : SRCCOPY);

    ReleaseDC(g_hwndMain, hdc);
}

//
// Paint an area of the keyboard. 绘制键盘的区域
// 
static
void WINAPI
IM_DrawArea( HDC hdc, RECT *prcUpdate )
{
    int Offset = 0;

    RETAILMSG (ZONE_FUNCTION, (TEXT("+IM_DrawArea(0x%08X, 0x%08X(%d,%d,%d,%d))\r\n"), hdc, prcUpdate,
                              prcUpdate->left, prcUpdate->top, prcUpdate->right, prcUpdate->bottom));

    // Draw the keys.
    if (g_fShiftDown ^ g_fCapsLockDown) {
        Offset = 195;	//绘制BMP下半部分,大写字母
    }

    BitBlt(hdc, prcUpdate->left, prcUpdate->top, prcUpdate->right - prcUpdate->left,
           prcUpdate->bottom - prcUpdate->top, g_hdcKeybd,  prcUpdate->left,
           prcUpdate->top + Offset, SRCCOPY );

    // Now draw any keys that are down 现在绘制某一个被按下的键
	//
    if (g_nDown) {
        int nRow, nCol;
        KEYENTRY *pKey;
        RECT    rc;
        for (nRow = 0; nRow < NUM_ROWS; nRow++) {
            for (nCol = 0; SENTINEL != g_keys[nRow][nCol].bVk; nCol++) {
                pKey = &(g_keys[nRow][nCol]);
                if (pKey->fdwFlags & F_DOWN) {
                    rc.left   = pKey->nLeft;
                    rc.right  = (pKey + 1)->nLeft;
                    rc.top    = g_RowCoord[nRow];
                    rc.bottom = g_RowCoord[nRow + 1];
                    IM_DrawKey(pKey, &rc, TRUE);
                }
            }
        }
    }

    return;
}

//
// Refresh the entire keyboard bitmap. 刷新整个键盘的BMP图
// 
static
void WINAPI
IM_SwitchBitmap( void )
{
    HDC hdc;
    RECT rc;

    GetClientRect( g_hwndMain, &rc );
    hdc = GetDC( g_hwndMain );
    IM_DrawArea( hdc, &rc );
    ReleaseDC( g_hwndMain, hdc );

    return;
}



//
// Determine the left edge of nKey + 1
//
#define KeyLeftCoord(nRow,nKey) (g_keys[nRow][nKey+1].nLeft)

//
// Determine what key contains the point specified in rcKey.left,rcKey.top.
// Fill in the full coordinates for the key and return the keyentry.
//
// Assumptions: we will not get a down event outside of our window, and every
// point in the window maps to a key.
//
__inline static
KEYENTRY* WINAPI
IM_GetKeyFromCoord( RECT *prcKey )
{
    int nRow = 0, nKey = 0, nLeft;
    POINT pt;

    pt.x = prcKey->left;
    pt.y = prcKey->top;

    //
    // Row
    //

    while( prcKey->top > g_RowCoord[nRow + 1] ) {
        nRow++;
    }

    if (nRow > 5) {
        nRow = 5;
    }

    //
    // Key
    //

    while (prcKey->left > (nLeft = KeyLeftCoord(nRow, nKey))) {
        nKey++;
    }

    RETAILMSG (ZONE_KEYS, (TEXT("%d,%d -> %d,%d\r\n"), prcKey->top, prcKey->left, nRow, nKey));

    //
    // Set up rect and return the key.
    //
    prcKey->left   = g_keys[nRow][nKey].nLeft;
    prcKey->right  = nLeft;
    prcKey->top    = g_RowCoord[nRow];
    prcKey->bottom = g_RowCoord[nRow + 1];

    return g_keys[nRow] + nKey;
}

//按键动作

static
BOOL WINAPI
IM_PressKey( BOOL fPress, KEYENTRY *pKey, RECT *prcKey )
{
    DWORD dwVkFlags;
    KEY_STATE_FLAGS nShiftState;
    HRESULT hRes;
    UINT *pnChar = NULL;

    if( fPress )
		{
        pKey->fdwFlags |= F_DOWN;
        dwVkFlags = KEYEVENTF_SILENT;
        nShiftState = KeyStateDownFlag;
		}
	else
		{
        pKey->fdwFlags &= ~F_DOWN;
        dwVkFlags = KEYEVENTF_KEYUP | KEYEVENTF_SILENT;
        nShiftState = KeyShiftNoCharacterFlag;
		}


    //
    // Adjust down count (an optimization for redraw and searching).
    //

    g_nDown += fPress ? 1 : -1;
    ASSERT(g_nDown >= 0);

    if ( pKey->fdwFlags & F_VK )
		{
        hRes = g_pIMCallback->SendVirtualKey( pKey->bVk, dwVkFlags );
		}
	else
		{
#define ISNOCHARACTERKEY(pKey) (pKey->wcUnshift == 0 && pKey->wcShift == 0)

        if (ISNOCHARACTERKEY(pKey))
			{
            nShiftState |= KeyShiftNoCharacterFlag;
			}
		if(g_fAltDown)
			{
			nShiftState |= KeyShiftAnyAltFlag | KeyShiftLeftAltFlag;
			}
        if (g_fControlDown)
			{
            nShiftState |= KeyShiftAnyCtrlFlag;
            if (NO_CTL == pKey->nCtrl)
				{
                nShiftState |= KeyShiftNoCharacterFlag;
				}
            pnChar = &pKey->nCtrl;
			}
		else if (g_fShiftDown ^ g_fCapsLockDown)
			{
            nShiftState |= KeyShiftAnyShiftFlag;
            pnChar = &pKey->wcShift;
			}
		else
			{
            pnChar = &pKey->wcUnshift;
			}

        if (pnChar)
			{
            hRes = g_pIMCallback->SendCharEvents(pKey->bVk, nShiftState, 1, &nShiftState, pnChar);
			}
		}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -