public static void WndProc(Window window, int msg, IntPtr wParam, IntPtr lParam, ref bool handled) { if (msg == NativeMethods.WM_TOUCH) { var inputCount = wParam.ToInt32() & 0xffff; var inputs = new TOUCHINPUT[inputCount]; if (NativeMethods.GetTouchInputInfo(lParam, inputCount, inputs, NativeMethods.TouchInputSize)) { for (int i = 0; i < inputCount; i++) { var input = inputs[i]; var position = GraphicsHelper.DivideByDpi(new Point(input.x * 0.01, input.y * 0.01)); position.Offset(-(double)_actualLeft.GetValue(window), -(double)_actualTop.GetValue(window)); MessageTouchDevice device; if (!_devices.TryGetValue(input.dwID, out device)) { device = new MessageTouchDevice(input.dwID); _devices.Add(input.dwID, device); } if (!device.IsActive && input.dwFlags.HasFlag(TOUCHEVENTF.TOUCHEVENTF_DOWN)) { device.SetActiveSource(PresentationSource.FromVisual(window)); device.Position = position; device.Activate(); device.ReportDown(); } else if (device.IsActive && input.dwFlags.HasFlag(TOUCHEVENTF.TOUCHEVENTF_UP)) { device.Position = position; device.ReportUp(); device.Deactivate(); _devices.Remove(input.dwID); } else if (device.IsActive && input.dwFlags.HasFlag(TOUCHEVENTF.TOUCHEVENTF_MOVE) && device.Position != position) { device.Position = position; device.ReportMove(); } _lastTouch = DateTime.Now; } } NativeMethods.CloseTouchInputHandle(lParam); handled = true; } }