ブログ@kaorun55

HoloLensやKinectなどのDepthセンサーを中心に書いています。

アプリケーションからタッチ入力を発行してみる

ここまでで、タッチ入力をするための準備ができたので、簡単なサンプルアプリケーションを作ってみます(C++ コンソールアプリ)。

Windows 8 のスタート画面をタッチスクロースさせます。すべてのコードはこのエントリの最後に載せています。

タッチ入力のコード自体は、次のようになっています。ポインタのフラグおよびX,Y座標を指定します。

void TouchInput( POINTER_FLAGS pointerFlags, int x, int y )

{

POINTER_TOUCH_INFO contact = { 0 };

contact.pointerInfo.pointerType = PT_TOUCH;

contact.pointerInfo.pointerFlags = pointerFlags;

contact.pointerInfo.ptPixelLocation.x = x;

contact.pointerInfo.ptPixelLocation.y = y;

contact.pointerInfo.pointerId = 0;

BOOL ret = ::InjectTouchInput( 1, &contact );

if ( !ret ) {

throw std::runtime_error( __FUNCTION__ );

}

}

あとは下図のInteractiveの形に沿って、入力を行います。なお、座標は同じ、違う場合にInjectTouchInputがエラーになることが多いようです。たとえば、UpのX,Y座標は直前の座標と同じである必要があります。

void Down( int x, int y ) 

{

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_INCONTACT | POINTER_FLAG_DOWN, x, y );

}

void Drag( int x, int y )

{

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_INCONTACT | POINTER_FLAG_UPDATE, x, y );

}

void Up( int x, int y )

{

// UpのX,Y座標は直前の座標が入っていないと、パラメーターエラーになる模様

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_UP, x, y );

}

最後にタッチ、スクロール、アップを行います。

        Down( 1000, 10 );

for ( int i = 0 ;i < 100; ++i ) {

x = 1000 - (i * 10);

Drag( x, y );

}

Up( x, y );

全体のコードです。

// ConsoleApplication1.cpp : コンソール アプリケーションのエントリ ポイントを定義します。

//

#include "stdafx.h"

#include <Windows.h>

#include <iostream>

void TouchInput( POINTER_FLAGS pointerFlags, int x, int y )

{

POINTER_TOUCH_INFO contact = { 0 };

contact.pointerInfo.pointerType = PT_TOUCH;

contact.pointerInfo.pointerFlags = pointerFlags;

contact.pointerInfo.ptPixelLocation.x = x;

contact.pointerInfo.ptPixelLocation.y = y;

contact.pointerInfo.pointerId = 0;

BOOL ret = ::InjectTouchInput( 1, &contact );

if ( !ret ) {

throw std::runtime_error( __FUNCTION__ );

}

}

void Down( int x, int y )

{

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_INCONTACT | POINTER_FLAG_DOWN, x, y );

}

void Drag( int x, int y )

{

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_INCONTACT | POINTER_FLAG_UPDATE, x, y );

}

void Up( int x, int y )

{

// UpのX,Y座標は直前の座標が入っていないと、パラメーターエラーになる模様

TouchInput( POINTER_FLAG_INRANGE | POINTER_FLAG_UP, x, y );

}

void SendKey( WORD vk, bool down )

{

INPUT input = { 0 };

input.type = INPUT_KEYBOARD;

input.ki.wVk = VK_LWIN;

input.ki.wScan = MapVirtualKey( vk, 0 );

input.ki.dwFlags = (down ? 0 : KEYEVENTF_KEYUP);

input.ki.dwExtraInfo = ::GetMessageExtraInfo();

SendInput( 1, &input, sizeof(INPUT) );

}

void SendWindowsKey()

{

SendKey( VK_LWIN, true );

SendKey( VK_LWIN, false );

}

int _tmain(int argc, _TCHAR* argv[])

{

try {

BOOL ret = ::InitializeTouchInjection( 1, TOUCH_FEEDBACK_NONE );

if ( !ret ) {

throw std::runtime_error( "InitializeTouchInjection" );

}

// Windows キーを押して、スタート画面を出す

SendWindowsKey();

// ちょっとまって右にスクロール

::Sleep( 1000 );

int x = 0;

const int y = 10;

Down( 1000, 10 );

for ( int i = 0 ;i < 100; ++i ) {

x = 1000 - (i * 10);

Drag( x, y );

}

Up( x, y );

// ちょっとまって左にスクロール

::Sleep( 5000 );

Down( 1000, 10 );

for ( int i = 0 ;i < 100; ++i ) {

x = (i * 10);

Drag( x, y );

}

Up( x, y );

// すこしまって終了

::Sleep( 3000 );

// Windows キーを押して、デスクトップ画面に戻す

SendWindowsKey();

}

catch ( std::exception& ex ) {

std::cout << ex.what() << ", " << ::GetLastError() << std::endl;

}

return 0;

}