我是想获取游戏手柄的状态信息。。然后想通过编程修改游戏手柄状态信息(不知道如何实现)。。具体步骤如下
我先是建立设备
Device dev;
设备初始化需要GUID,
所有枚举所有设备,由于我的游戏手柄只有1个,所有只取一个GUID
Guid id = new Guid();
foreach (DeviceInstance di in Manager.GetDevices(DeviceClass.GameControl, EnumDevicesFlags.AttachedOnly))
{
id=di.ProductGuid;
}
dev = new Device(id);
JoystickState joy = new JoystickState();
这里都正确,到了下面:
joy = dev.CurrentJoystickState;
出现了异常
提示:Microsoft.DirectX.DirectInput.NotAcquiredException
希望高人指点!!
不过我google一下,出来日本人的程序。。
自分用に改造したところは、他のクラスとのやり取りの時に、使いやすそうなメソッドを追加したくらいです。
// DirectX Inputでコントローラを管理するクラス
// http://wonderrabbitproject.or.tp/diarypro/archives/123.html
// をほぼ参考
using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.DirectX.DirectInput;
namespace TeamYMI
{
class DirectXGameController
{
// DirectInputジョイスティック検索
List<Microsoft.DirectX.DirectInput.Device> joysticks;
List<Microsoft.DirectX.DirectInput.JoystickState[]> jsStates;
public DirectXGameController()
{
joysticks = new List<Microsoft.DirectX.DirectInput.Device>();
jsStates = new List<JoystickState[]>();
Initialize();
}
/// <summary>
/// デバイスの数を返す
/// </summary>
public int DeviceCount
{
get
{
return joysticks.Count;
}
}
/// <summary>
/// デバイスの初期化
/// </summary>
private void Initialize()
{
// DirectInputデバイスのリストを取得
Microsoft.DirectX.DirectInput.DeviceList controllers =
Microsoft.DirectX.DirectInput.Manager.GetDevices(
Microsoft.DirectX.DirectInput.DeviceClass.GameControl,
Microsoft.DirectX.DirectInput.EnumDevicesFlags.AllDevices);
//Joystickのデバイスを作る器
Microsoft.DirectX.DirectInput.Device d;
//取得したデバイスのリストをforeachして1つづつjoysticksに登録
foreach (Microsoft.DirectX.DirectInput.DeviceInstance i in controllers)
{
//デバイスの生成
d = new Microsoft.DirectX.DirectInput.Device(i.InstanceGuid);
//各種フラグの設定。Backgroundだと第一引数のFormはnullでいい
d.SetCooperativeLevel(null,
Microsoft.DirectX.DirectInput.CooperativeLevelFlags.NonExclusive
| Microsoft.DirectX.DirectInput.CooperativeLevelFlags.NoWindowsKey
| Microsoft.DirectX.DirectInput.CooperativeLevelFlags.Background
);
//Joystickタイプのデータフォーマットを設定
d.SetDataFormat(Microsoft.DirectX.DirectInput.DeviceDataFormat.Joystick);
//アナログスティックなどのAxis要素を持つDeviceObjectInstanceの出力レンジを設定
foreach (Microsoft.DirectX.DirectInput.DeviceObjectInstance oi in d.Objects)
{
if ((oi.ObjectId & (int)Microsoft.DirectX.DirectInput.DeviceObjectTypeFlags.Axis) != 0)
{
d.Properties.SetRange(
Microsoft.DirectX.DirectInput.ParameterHow.ById,
oi.ObjectId,
new Microsoft.DirectX.DirectInput.InputRange(-1000, 1000));
}
}
//Axisの絶対位置モードを設定
d.Properties.AxisModeAbsolute = true;
//とりあえずデバイスを動かす
try { d.Acquire(); }
catch (Microsoft.DirectX.DirectXException) { }
//作ったJoystickのDeviceをJoystickリストに追加
joysticks.Add(d);
//Joystickの状態を保持させる為のjsstatesを用意、とりあえず現在と以前の状態で2つ用意してみる
jsStates.Add(new Microsoft.DirectX.DirectInput.JoystickState[2]
{
new Microsoft.DirectX.DirectInput.JoystickState(),
new Microsoft.DirectX.DirectInput.JoystickState()
});
}
}
/// <summary>
/// デバイスIDの状態を取得する
/// </summary>
/// <param name="deviceID"></param>
private void AcquireDeviceState(int deviceID)
{
jsStates[deviceID][1] = jsStates[deviceID][0];
//最新情報を取得
try
{
//デバイスから最新情報を掘り出す
joysticks[deviceID].Poll();
}
catch (Microsoft.DirectX.DirectInput.NotAcquiredException e1)
{
//ここに来た時はAcquireできていないので試してみる
System.Diagnostics.Trace.WriteLine(e1.ToString());
//Poll
try
{
joysticks[deviceID].Acquire();
joysticks[deviceID].Poll();
}
catch (Microsoft.DirectX.DirectInput.InputException e2)
{
System.Diagnostics.Trace.WriteLine(e2.ToString());
}
}
catch (Microsoft.DirectX.DirectInput.InputException e1)
{
System.Diagnostics.Trace.WriteLine(e1.ToString());
}
jsStates[deviceID][0] = joysticks[deviceID].CurrentJoystickState;
}
/// <summary>
/// デバイスIDのボタンIDが押されているかどうか
/// </summary>
/// <param name="buttonID"></param>
/// <param name="deviceID"></param>
/// <returns></returns>
public bool IsButtonPush(int buttonID, int deviceID)
{
AcquireDeviceState(deviceID);
return jsStates[deviceID][0].GetButtons()[buttonID].Equals(128);
}
/// <summary>
/// デバイスIDのアナログの十字の状態、未入力で-1、上が0で時計回りに増加)
/// </summary>
/// <param name="deviceID"></param>
/// <returns></returns>
public int GetAnalogKey(int deviceID)
{
AcquireDeviceState(deviceID);
return jsStates[deviceID][0].GetPointOfView()[0];
}
}
}
================
在进入极品飞车(其他DirectX.DirectInput游戏也的)一直按着游戏杆左键不放,然后,在设备管理中禁用,回到极品飞车游戏,画面出现不停的左方向抖动,就是不停的发左键消息,应该是主动方式
游戏程序主动查询游戏杆的状态,发现状态一直是←方向,所以不停的有左键的抖动。。。
本人也试了进入游戏的时候一直按着键盘的左键,(记住,左键一直按着不放),突然拔掉键盘的ps/2接口。极品游戏出现类似的不停左方向抖动!!!
本人做了个USB禁用、开启程序,就是为了想在需要的时候禁用,开启游戏杆。
希望博客园的师哥们给点建议,。。谢谢!
希望知道的高手,指导一下!!!