WindowsXP (SP1以降)でMCE対応リモコンを使う
WindowsXP(SP1以降)では「WindowsXP Media Center Edition」対応のリモコンを使う事ができます。「WindowsXP Media Center Edition」は単体売りされていませんが、リモコンとGUIを用意すれば同等の事が可能となります。簡単に入手できるリモコンとしては
// キーボード入力
procedure Form1.FormKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);
begin
case Key of
// Clear
VK_ESCAPE:
;
// クリア (サイバーリンク・マルチリモコン MultiR.C./CL-RC2)
VK_DELETE:
;
// ↑
VK_UP:
;
// ↓
VK_DOWN:
;
// ←
VK_LEFT:
;
// →
VK_RIGHT:
;
// Enter/OK(決定)
VK_RETURN:
;
// [数字キー]
Ord('0')..Ord('9'):
;
end;
end;
|
procedure WmAppCommand(var Mess: TMessage);message WM_APPCOMMAND;
|
const APPCOMMAND_BROWSER_BACKWARD = 1; APPCOMMAND_BROWSER_FORWARD = 2; APPCOMMAND_BROWSER_REFRESH = 3; APPCOMMAND_BROWSER_STOP = 4; APPCOMMAND_BROWSER_SEARCH = 5; APPCOMMAND_BROWSER_FAVORITES = 6; APPCOMMAND_BROWSER_HOME = 7; APPCOMMAND_VOLUME_MUTE = 8; APPCOMMAND_VOLUME_DOWN = 9; APPCOMMAND_VOLUME_UP = 10; APPCOMMAND_MEDIA_NEXTTRACK = 11; APPCOMMAND_MEDIA_PREVIOUSTRACK = 12; APPCOMMAND_MEDIA_STOP = 13; APPCOMMAND_MEDIA_PLAY_PAUSE = 14; APPCOMMAND_LAUNCH_MAIL = 15; APPCOMMAND_LAUNCH_MEDIA_SELECT = 16; APPCOMMAND_LAUNCH_APP1 = 17; APPCOMMAND_LAUNCH_APP2 = 18; APPCOMMAND_BASS_DOWN = 19; APPCOMMAND_BASS_BOOST = 20; APPCOMMAND_BASS_UP = 21; APPCOMMAND_TREBLE_DOWN = 22; APPCOMMAND_TREBLE_UP = 23; APPCOMMAND_MICROPHONE_VOLUME_MUTE = 24; APPCOMMAND_MICROPHONE_VOLUME_DOWN = 25; APPCOMMAND_MICROPHONE_VOLUME_UP = 26; APPCOMMAND_HELP = 27; APPCOMMAND_FIND = 28; APPCOMMAND_NEW = 29; APPCOMMAND_OPEN = 30; APPCOMMAND_CLOSE = 31; APPCOMMAND_SAVE = 32; APPCOMMAND_PRINT = 33; APPCOMMAND_UNDO = 34; APPCOMMAND_REDO = 35; APPCOMMAND_COPY = 36; APPCOMMAND_CUT = 37; APPCOMMAND_PASTE = 38; APPCOMMAND_REPLY_TO_MAIL = 39; APPCOMMAND_FORWARD_MAIL = 40; APPCOMMAND_SEND_MAIL = 41; APPCOMMAND_SPELL_CHECK = 42; APPCOMMAND_DICTATE_OR_COMMAND_CONTROL_TOGGLE = 43; APPCOMMAND_MIC_ON_OFF_TOGGLE = 44; APPCOMMAND_CORRECTION_LIST = 45; APPCOMMAND_MEDIA_PLAY = 46; APPCOMMAND_MEDIA_PAUSE = 47; APPCOMMAND_MEDIA_RECORD = 48; APPCOMMAND_MEDIA_FAST_FORWARD = 49; APPCOMMAND_MEDIA_REWIND = 50; APPCOMMAND_MEDIA_CHANNEL_UP = 51; APPCOMMAND_MEDIA_CHANNEL_DOWN = 52; APPCOMMAND_DELETE = 53; APPCOMMAND_DWM_FLIP3D = 54; APPCOMMAND_MEDIA_PLAY_PAUSE2 = 4143; APPCOMMAND_MEDIA_PLAY2 = 4142; APPCOMMAND_MEDIA_PAUSE2 = 4143; APPCOMMAND_MEDIA_RECORD2 = 4144; APPCOMMAND_MEDIA_FASTFORWARD2 = 4145; APPCOMMAND_MEDIA_REWIND2 = 4146; APPCOMMAND_MEDIA_CHANNEL_UP2 = 4147; APPCOMMAND_MEDIA_CHANNEL_DOWN2 = 4148; |
// リモコンキー入力
procedure Form1.WmAppCommand(var Mess: TMessage);
begin
case Mess.LParamHi of
APPCOMMAND_BROWSER_BACKWARD:
// (処理)
end;
end;
|
type
TRAWINPUTDEVICE =
packed record
usUsagePage: WORD;
usUsage: WORD;
dwFlags: DWORD;
hwndTarge : HWND;
end;
PRAWINPUTDEVICE = ^TRAWINPUTDEVICE;
const
RI_NUM_DEVICE = 2;
var
Rid: packed array [0..RI_NUM_DEVICE-1] of TRAWInputDevice;
|
function RegisterRawInputDevices(pRawInputDevices: Pointer;uiNumDevices,cbSize: UINT): Boolean;
stdcall;external 'user32.dll';
|
// リモコンデバイスを登録 Rid[0].usUsagePage := $FFBC; Rid[0].usUsage := $88; Rid[0].dwFlags := 0; Rid[0].hwndTarget := 0; Rid[1].usUsagePage := $000C; Rid[1].usUsage := $01; Rid[1].dwFlags := 0; Rid[1].hwndTarget := 0; RegisterRawInputDevices(@Rid, RI_NUM_DEVICE, SizeOf(TRAWInputDevice)); |
| デバイス |
usUsagePage | usUsag |
| キーボード |
0x0001 |
0x06 |
| マウス |
0x0001 |
0x02 |
| ゲームパッド |
0x0001 |
0x05 |
| ジョイスティック |
0x0001 |
0x04 |
| キーボード(Generic desktop) | 0x0001 |
0x80 |
| キーボード(Consumer controls) |
0x000C |
0x01 |
| MCE対応リモコン(Vendor-defined) |
0xFFBC |
0x88 |
procedure WmInput(var Mess: TMessage);message WM_INPUT;
|
const PW_CLIENTONLY = $00000001; RIM_INPUT = $00000000; RIM_INPUTSINK = $00000001; RIM_TYPEMOUSE = $00000000; RIM_TYPEKEYBOARD = $00000001; RIM_TYPEHID = $00000002; MOUSE_MOVE_RELATIVE = $00000000; MOUSE_MOVE_ABSOLUTE = $00000001; MOUSE_VIRTUAL_DESKTOP = $00000002; MOUSE_ATTRIBUTES_CHANGED = $00000004; RI_MOUSE_LEFT_BUTTON_DOWN = $0001; RI_MOUSE_LEFT_BUTTON_UP = $0002; RI_MOUSE_RIGHT_BUTTON_DOWN = $0004; RI_MOUSE_RIGHT_BUTTON_UP = $0008; RI_MOUSE_MIDDLE_BUTTON_DOWN = $0010; RI_MOUSE_MIDDLE_BUTTON_UP = $0020; RI_MOUSE_BUTTON_1_DOWN = RI_MOUSE_LEFT_BUTTON_DOWN; RI_MOUSE_BUTTON_1_UP = RI_MOUSE_LEFT_BUTTON_UP; RI_MOUSE_BUTTON_2_DOWN = RI_MOUSE_RIGHT_BUTTON_DOWN; RI_MOUSE_BUTTON_2_UP = RI_MOUSE_RIGHT_BUTTON_UP; RI_MOUSE_BUTTON_3_DOWN = RI_MOUSE_MIDDLE_BUTTON_DOWN; RI_MOUSE_BUTTON_3_UP = RI_MOUSE_MIDDLE_BUTTON_UP; RI_MOUSE_BUTTON_4_DOWN = $0040; RI_MOUSE_BUTTON_4_UP = $0080; RI_MOUSE_BUTTON_5_DOWN = $0100; RI_MOUSE_BUTTON_5_UP = $0200; RI_MOUSE_WHEEL = $0400; KEYBOARD_OVERRUN_MAKE_CODE = $00ff; RI_KEY_MAKE = $0000; RI_KEY_BREAK = $0001; RI_KEY_E0 = $0002; RI_KEY_E1 = $0004; RI_KEY_TERMSRV_SET_LED = $0008; RI_KEY_TERMSRV_SHADOW = $0010; RID_INPUT = $10000003; RID_HEADER = $10000005; RIDI_PREPARSEDDATA = $20000005; RIDI_DEVICENAME = $20000007; RIDI_DEVICEINFO = $2000000b; RIDEV_REMOVE = $00000001; RIDEV_EXCLUDE = $00000010; RIDEV_PAGEONLY = $00000020; RIDEV_NOLEGACY = $00000030; RIDEV_INPUTSINK = $00000100; RIDEV_CAPTUREMOUSE = $00000200; RIDEV_NOHOTKEYS = $00000200; RIDEV_APPKEYS = $00000400; RIDEV_EXINPUTSINK = $00001000; RIDEV_DEVNOTIFY = $00002000; RIDEV_EXMODEMASK = $000000F0; |
type
TRAWINPUTHEADER =
packed record
dwType : DWORD;
dwSize : DWORD;
hDevice : THANDLE;
wParam : WPARAM;
end;
PRAWINPUTHEADER = ^TRAWINPUTHEADER;
TRMBUTTONS =
packed record
case Integer of
0:(ulButtons: ULONG);
1:(
usButtonFlags : SHORT;
usButtonData : SHORT;
);
end;
TRAWMOUSE =
packed record
usFlags : SHORT;
RMButtons : TRMBUTTONS;
ulRawButtons : ULONG;
lLastX : LongInt;
lLastY : LongInt;
ulExtraInformation : ULONG;
end;
PRAWMOUSE = ^TRAWMOUSE;
TRAWKEYBOARD =
packed record
MakeCode : SHORT;
Flags : SHORT;
Reserved : SHORT;
VKey : SHORT;
Mess : UINT;
ExtraInformation : ULONG;
end;
PRAWKEYBOARD = ^TRAWKEYBOARD;
TRAWHID =
packed record
dwSizeHid : DWORD;
dwCount : DWORD;
bRawData : BYTE;
end;
PTRAWHID = ^TRAWHID;
TRAWINPUTDATA =
packed record
case Integer of
0:(mouse : TRAWMOUSE );
1:(keyboard : TRAWKEYBOARD);
2:(hid : TRAWHID );
end;
TRAWINPUT =
packed record
header : TRAWINPUTHEADER;
data : TRAWINPUTDATA;
end;
PRAWINPUT = ^TRAWINPUT;
|
function GetRawInputData(hRawInput: Pointer; uiCommand:UINT; pData: Pointer; pcbSize: Pointer; cbSizeHeader: UINT): UINT;
stdcall; external 'user32.dll';
|
procedure Tmain_form.WmInput(var Mess: TMessage);
var
i,l:Integer;
RI: PRAWINPUT;
dwSize: UINT;
lpb: PBYTE;
DataSize: DWORD;
HID_DATA:array [0..15] of DWORD;
P:PByte;
begin
GetRawInputData(PRAWINPUT(Mess.LParam), RID_INPUT, nil, @dwSize,SizeOf(TRAWINPUTHEADER));
if dwSize = 0 then
Exit;
DataSize := SizeOf(BYTE) * dwSize;
GetMem(lpb,DataSize);
try
GetRawInputData(PRAWINPUT(Mess.LParam), RID_INPUT, lpb, @dwSize, SizeOf(TRAWINPUTHEADER));
RI := PRAWINPUT(lpb);
case RI.header.dwType of
// マウス
RIM_TYPEMOUSE:
begin
Label1.Caption := Format('Mouse : (%d:%d) %.2x',
[RI.Data.mouse.lLastX,RI.Data.mouse.lLastX,RI.Data
.mouse.RMButtons.usButtonData]);
end;
// キーボード
RIM_TYPEKEYBOARD:
begin
Label1.Caption := Format('KeyBoard : %.2x',[RI.Data.keyboard.VKey]);
end;
// HID準拠デバイス
RIM_TYPEHID:
begin
P := @RI.Data.hid.bRawData;
for i:=0 to RI.Data.hid.dwCount-1 do
begin
HID_DATA[i] := 0;
for l:=1 to RI.Data.hid.dwSizeHid do
begin
HID_DATA[i] := (HID_DATA[i] shl 8) + P^;
Inc(P);
end;
end;
Label1.Caption := '';
for i:=0 to RI.Data.hid.dwCount-1 do
Label1.Caption := Label1.Caption + Format('HID[%d] : %x',[i+1,HID_DATA[i]]);
end;
end;
finally
FreeMem(lpb,DataSize);
end;
end;
|
| ボタン | メッセージ | コマンドまたは「UsagePage/Usag/RawData」 |
| ホーム |
アプリケーションで制御不可 | N/A |
| Power | WM_INPUT | アプリケーションで制御すべきではない |
| DVD/VIDEO CD | WM_INPUT | 0xFFBC / 0x88 / 0x048000 |
| 音楽 | WM_INPUT | 0xFFBC / 0x88 / 0x040800 |
| 写真/静止画 | WM_INPUT | 0xFFBC / 0x88 / 0x041000 |
| ファイル再生 | WM_INPUT | 0xFFBC / 0x88 / 0x042000 |
| テレビ | WM_INPUT | 0xFFBC / 0x88 / 0x040200 |
| 録画 | WM_APPCOMMAND | APPCOMMAND_MEDIA_RECORD |
| ラジオ | WM_INPUT | 0x000C / 0x01 / 0x03040000 |
| 主/副音声 |
WM_INPUT | 0xFFBC / 0x88 / 0x040010 |
| 文字放送/CC | WM_INPUT | 0xFFBC / 0x88 / 0x040020 |
| Last CH | WM_INPUT | 0xFFBC / 0x88 / 0x040040 |
| 字幕切り替え | WM_INPUT | 0xFFBC / 0x88 / 0x040008 |
| 音声切り替え | WM_INPUT | 0xFFBC / 0x88 / 0x040002 |
| アングル切り替え | WM_INPUT | 0xFFBC / 0x88 / 0x040001 |
| BACK | WM_APPCOMMAND | APPCOMMAND_BROWSER_BACKWARD |
| Info/EPG | WM_INPUT | 0x000C / 0x01 / 0x03000002 |
| DVDメニュー | WM_INPUT | 0xFFBC / 0x88 / 0x040004 |
| 音量Up(+) | WM_APPCOMMAND | APPCOMMAND_VOLUME_UP |
| 音量Down(-) | WM_APPCOMMAND | APPCOMMAND_VOLUME_DOWN |
| ミュート | WM_APPCOMMAND | APPCOMMAND_VOLUME_MUTE |
| チャンネルUp | WM_APPCOMMAND | APPCOMMAND_MEDIA_CHANNEL_UP |
| チャンネルDown | WM_APPCOMMAND | APPCOMMAND_MEDIA_CHANNEL_DOWN |
| ↑ | WM_KEYDOWN | VK_UP |
| ↓ | WM_KEYDOWN | VK_DOWN |
| ← | WM_KEYDOWN | VK_LEFT |
| → | WM_KEYDOWN | VK_RIGHT |
| 決定 |
WM_KEYDOWN | VK_RETURN |
| 再生 | WM_APPCOMMAND | APPCOMMAND_MEDIA_PLAY |
| 巻き戻し | WM_APPCOMMAND | APPCOMMAND_MEDIA_REWIND |
| 一時停止 | WM_APPCOMMAND | APPCOMMAND_MEDIA_PAUSE |
| 早送り | WM_APPCOMMAND | APPCOMMAND_MEDIA_FASTFORWARD |
| 前のチャプタ |
WM_APPCOMMAND | APPCOMMAND_MEDIA_PREVIOUSTRACK |
| 停止 | WM_APPCOMMAND | APPCOMMAND_MEDIA_STOP |
| 次のチャプタ | WM_APPCOMMAND | APPCOMMAND_MEDIA_NEXTTRACK |
| 数字キー | WM_KEYDOWN | VK_0...VK_9 |
| クリア | WM_KEYDOWN | VK_DELETE(リファレンスではVK_ESCAPE) |
| BACK |