| 624 | } |
| 625 | |
| 626 | bool TranslateMessage(const MSG *lpMsg) |
| 627 | { |
| 628 | if (lpMsg->message == DVL_WM_KEYDOWN) { |
| 629 | int key = lpMsg->wParam; |
| 630 | unsigned mod = (DWORD)lpMsg->lParam >> 16; |
| 631 | |
| 632 | bool shift = (mod & KMOD_SHIFT) != 0; |
| 633 | bool upper = shift != (mod & KMOD_CAPS); |
| 634 | |
| 635 | bool is_alpha = (key >= 'A' && key <= 'Z'); |
| 636 | bool is_numeric = (key >= '0' && key <= '9'); |
| 637 | bool is_control = key == DVL_VK_SPACE || key == DVL_VK_BACK || key == DVL_VK_ESCAPE || key == DVL_VK_TAB || key == DVL_VK_RETURN; |
| 638 | bool is_oem = (key >= DVL_VK_OEM_1 && key <= DVL_VK_OEM_7); |
| 639 | |
| 640 | if (is_control || is_alpha || is_numeric || is_oem) { |
| 641 | if (!upper && is_alpha) { |
| 642 | key = tolower(key); |
| 643 | } else if (shift && is_numeric) { |
| 644 | switch (key) { |
| 645 | case '1': |
| 646 | key = '!'; |
| 647 | break; |
| 648 | case '2': |
| 649 | key = '@'; |
| 650 | break; |
| 651 | case '3': |
| 652 | key = '#'; |
| 653 | break; |
| 654 | case '4': |
| 655 | key = '$'; |
| 656 | break; |
| 657 | case '5': |
| 658 | key = '%'; |
| 659 | break; |
| 660 | case '6': |
| 661 | key = '^'; |
| 662 | break; |
| 663 | case '7': |
| 664 | key = '&'; |
| 665 | break; |
| 666 | case '8': |
| 667 | key = '*'; |
| 668 | break; |
| 669 | case '9': |
| 670 | key = '('; |
| 671 | break; |
| 672 | case '0': |
| 673 | key = ')'; |
| 674 | break; |
| 675 | } |
| 676 | } else if (is_oem) { |
| 677 | // XXX: This probably only supports US keyboard layout |
| 678 | switch (key) { |
| 679 | case DVL_VK_OEM_1: |
| 680 | key = shift ? ':' : ';'; |
| 681 | break; |
| 682 | case DVL_VK_OEM_2: |
| 683 | key = shift ? '?' : '/'; |
no test coverage detected