00001 #region --- License ---
00002
00003
00004
00005 #endregion
00006
00007 #region --- Using directives ---
00008
00009 using System;
00010 using System.Collections.Generic;
00011 using System.Text;
00012 using System.Runtime.InteropServices;
00013 using System.Diagnostics;
00014 using System.Windows.Forms;
00015 using OpenTK.Input;
00016
00017 #endregion
00018
00019 namespace OpenTK.Platform.Windows
00020 {
00021
00022 sealed class WinRawInput : System.Windows.Forms.NativeWindow, IInputDriver
00023 {
00024
00025 RawInput data = new RawInput();
00026
00027 static int deviceCount;
00028 int rawInputStructSize = API.RawInputSize;
00029
00030 private WinRawKeyboard keyboardDriver;
00031 private WinRawMouse mouseDriver;
00032
00033 #region --- Constructors ---
00034
00035 internal WinRawInput(WinWindowInfo parent)
00036 {
00037 Debug.WriteLine("Initalizing windows raw input driver.");
00038 Debug.Indent();
00039
00040 AssignHandle(parent.WindowHandle);
00041 Debug.Print("Input window attached to parent {0}", parent);
00042 keyboardDriver = new WinRawKeyboard(this.Handle);
00043 mouseDriver = new WinRawMouse(this.Handle);
00044
00045 Debug.Unindent();
00046
00047
00048 }
00049
00050 #endregion
00051
00052 #region internal static int DeviceCount
00053
00054 internal static int DeviceCount
00055 {
00056 get
00057 {
00058 Functions.GetRawInputDeviceList(null, ref deviceCount, API.RawInputDeviceListSize);
00059 return deviceCount;
00060 }
00061 }
00062
00063 #endregion
00064
00065 #region protected override void WndProc(ref Message msg)
00066
00071 protected override void WndProc(ref Message msg)
00072 {
00073 switch ((WindowMessage)msg.Msg)
00074 {
00075 case WindowMessage.INPUT:
00076 int size = 0;
00077
00078 Functions.GetRawInputData(msg.LParam, GetRawInputDataEnum.INPUT,
00079 IntPtr.Zero, ref size, API.RawInputHeaderSize);
00080
00081
00082
00083
00084
00085 if (size == Functions.GetRawInputData(msg.LParam, GetRawInputDataEnum.INPUT,
00086 out data, ref size, API.RawInputHeaderSize))
00087 {
00088 switch (data.Header.Type)
00089 {
00090 case RawInputDeviceType.KEYBOARD:
00091 if (!keyboardDriver.ProcessKeyboardEvent(data))
00092 Functions.DefRawInputProc(ref data, 1, (uint)API.RawInputHeaderSize);
00093 return;
00094
00095 case RawInputDeviceType.MOUSE:
00096 if (!mouseDriver.ProcessEvent(data))
00097 Functions.DefRawInputProc(ref data, 1, (uint)API.RawInputHeaderSize);
00098 return;
00099
00100 case RawInputDeviceType.HID:
00101 Functions.DefRawInputProc(ref data, 1, (uint)API.RawInputHeaderSize);
00102 return;
00103
00104 default:
00105 break;
00106 }
00107 }
00108 else
00109 {
00110 throw new ApplicationException(String.Format(
00111 "GetRawInputData returned invalid buffer. Windows error {0}. Please file a bug at http://opentk.sourceforge.net",
00112 Marshal.GetLastWin32Error()));
00113 }
00114 break;
00115
00116 case WindowMessage.DESTROY:
00117 Debug.Print("Input window detached from parent {0}.", Handle);
00118 ReleaseHandle();
00119 break;
00120
00121 case WindowMessage.QUIT:
00122 Debug.WriteLine("Input window quit.");
00123 this.Dispose();
00124 break;
00125 }
00126
00127 base.WndProc(ref msg);
00128 }
00129
00130 #endregion
00131
00132 #region --- IInputDriver Members ---
00133
00134 #region IInputDriver Members
00135
00136 public void Poll()
00137 {
00138 return;
00139 #if false
00140
00141
00142
00143
00144
00145 int size = 0;
00146 Functions.GetRawInputBuffer(IntPtr.Zero, ref size, API.RawInputHeaderSize);
00147 size *= 256;
00148 IntPtr rin_data = Marshal.AllocHGlobal(size);
00149
00150 while (true)
00151 {
00152
00153
00154 int num = Functions.GetRawInputBuffer(rin_data, ref size, API.RawInputHeaderSize);
00155 if (num == 0)
00156 break;
00157 else if (num < 0)
00158 {
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170 Debug.Print("GetRawInputBuffer failed with code: {0}", Marshal.GetLastWin32Error());
00171
00172 break;
00173 }
00174
00175 RawInput[] rin_structs = new RawInput[num];
00176 IntPtr next_rin = rin_data;
00177 for (int i = 0; i < num; i++)
00178 {
00179 rin_structs[i] = (RawInput)Marshal.PtrToStructure(next_rin, typeof(RawInput));
00180
00181 switch (rin_structs[i].Header.Type)
00182 {
00183 case RawInputDeviceType.KEYBOARD:
00184 keyboardDriver.ProcessKeyboardEvent(rin_structs[i]);
00185 break;
00186
00187 case RawInputDeviceType.MOUSE:
00188 mouseDriver.ProcessEvent(rin_structs[i]);
00189 break;
00190 }
00191
00192 next_rin = Functions.NextRawInputStructure(next_rin);
00193 }
00194 Functions.DefRawInputProc(rin_structs, num, (uint)API.RawInputHeaderSize);
00195 }
00196
00197 Marshal.FreeHGlobal(rin_data);
00198 #endif
00199 }
00200
00201 #endregion
00202
00203 #region IKeyboardDriver Members
00204
00205 public IList<KeyboardDevice> Keyboard
00206 {
00207 get { return keyboardDriver.Keyboard; }
00208 }
00209
00210 #endregion
00211
00212 #region IMouseDriver Members
00213
00214 public IList<MouseDevice> Mouse
00215 {
00216 get { return mouseDriver.Mouse; }
00217 }
00218
00219 #endregion
00220
00221 #region IJoystickDriver Members
00222
00223 public IList<JoystickDevice> Joysticks
00224 {
00225 get { throw new NotImplementedException(); }
00226 }
00227
00228 #endregion
00229
00230 #endregion
00231
00232 #region --- IDisposable Members ---
00233
00234 private bool disposed;
00235
00236 public void Dispose()
00237 {
00238 Dispose(true);
00239 GC.SuppressFinalize(this);
00240 }
00241
00242 private void Dispose(bool manual)
00243 {
00244 if (!disposed)
00245 {
00246 if (manual)
00247 {
00248 keyboardDriver.Dispose();
00249 this.ReleaseHandle();
00250 }
00251
00252 disposed = true;
00253 }
00254 }
00255
00256 ~WinRawInput()
00257 {
00258 Dispose(false);
00259 }
00260
00261 #endregion
00262 }
00263 }