src/video/winrt/SDL_winrtmouse.cpp
changeset 8515 bc6cf9201dab
parent 8514 8ba600edd93f
child 8516 f3e0e381bdcd
     1.1 --- a/src/video/winrt/SDL_winrtmouse.cpp	Sun Sep 01 10:20:17 2013 -0400
     1.2 +++ b/src/video/winrt/SDL_winrtmouse.cpp	Mon Sep 02 15:23:33 2013 -0400
     1.3 @@ -47,9 +47,7 @@
     1.4  #include "SDL_winrtmouse.h"
     1.5  
     1.6  
     1.7 -static SDL_bool WINRT_UseRelativeMouseMode = SDL_FALSE;
     1.8 -static SDL_TouchID WINRT_TouchID = 1;
     1.9 -static unsigned int WINRT_LeftFingerDown = 0;
    1.10 +extern "C" SDL_bool WINRT_UsingRelativeMouseMode = SDL_FALSE;
    1.11  
    1.12  
    1.13  static SDL_Cursor *
    1.14 @@ -131,7 +129,7 @@
    1.15  static int
    1.16  WINRT_SetRelativeMouseMode(SDL_bool enabled)
    1.17  {
    1.18 -    WINRT_UseRelativeMouseMode = enabled;
    1.19 +    WINRT_UsingRelativeMouseMode = enabled;
    1.20      return 0;
    1.21  }
    1.22  
    1.23 @@ -156,9 +154,6 @@
    1.24  
    1.25      SDL_SetDefaultCursor(WINRT_CreateDefaultCursor());
    1.26  #endif
    1.27 -
    1.28 -    /* Init touch: */
    1.29 -    SDL_AddTouch(WINRT_TouchID, "");
    1.30  }
    1.31  
    1.32  void
    1.33 @@ -166,326 +161,6 @@
    1.34  {
    1.35  }
    1.36  
    1.37 -// Applies necessary geometric transformations to raw cursor positions:
    1.38 -Windows::Foundation::Point
    1.39 -WINRT_TransformCursorPosition(SDL_Window * window, Windows::Foundation::Point rawPosition)
    1.40 -{
    1.41 -    using namespace Windows::Graphics::Display;
    1.42 -
    1.43 -    if (!window) {
    1.44 -        return rawPosition;
    1.45 -    }
    1.46 -
    1.47 -    SDL_WindowData * windowData = (SDL_WindowData *) window->driverdata;
    1.48 -    if (windowData->coreWindow == nullptr) {
    1.49 -        // For some reason, the window isn't associated with a CoreWindow.
    1.50 -        // This might end up being the case as XAML support is extended.
    1.51 -        // For now, if there's no CoreWindow attached to the SDL_Window,
    1.52 -        // don't do any transforms.
    1.53 -        return rawPosition;
    1.54 -    }
    1.55 -
    1.56 -    // The CoreWindow can only be accessed on certain thread(s).
    1.57 -    SDL_assert(CoreWindow::GetForCurrentThread() != nullptr);
    1.58 -
    1.59 -    CoreWindow ^ nativeWindow = windowData->coreWindow.Get();
    1.60 -    Windows::Foundation::Point outputPosition;
    1.61 -
    1.62 -#if WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP
    1.63 -    outputPosition.X = rawPosition.X * (((float32)window->w) / nativeWindow->Bounds.Width);
    1.64 -    outputPosition.Y = rawPosition.Y * (((float32)window->h) / nativeWindow->Bounds.Height);
    1.65 -#else
    1.66 -    switch (DisplayProperties::CurrentOrientation)
    1.67 -    {
    1.68 -        case DisplayOrientations::Portrait:
    1.69 -            outputPosition.X = rawPosition.X * (((float32)window->w) / nativeWindow->Bounds.Width);
    1.70 -            outputPosition.Y = rawPosition.Y * (((float32)window->h) / nativeWindow->Bounds.Height);
    1.71 -            break;
    1.72 -        case DisplayOrientations::PortraitFlipped:
    1.73 -            outputPosition.X = (float32)window->w - rawPosition.X * (((float32)window->w) / nativeWindow->Bounds.Width);
    1.74 -            outputPosition.Y = (float32)window->h - rawPosition.Y * (((float32)window->h) / nativeWindow->Bounds.Height);
    1.75 -            break;
    1.76 -        case DisplayOrientations::Landscape:
    1.77 -            outputPosition.X = rawPosition.Y * (((float32)window->w) / nativeWindow->Bounds.Height);
    1.78 -            outputPosition.Y = (float32)window->h - rawPosition.X * (((float32)window->h) / nativeWindow->Bounds.Width);
    1.79 -            break;
    1.80 -        case DisplayOrientations::LandscapeFlipped:
    1.81 -            outputPosition.X = (float32)window->w - rawPosition.Y * (((float32)window->w) / nativeWindow->Bounds.Height);
    1.82 -            outputPosition.Y = rawPosition.X * (((float32)window->h) / nativeWindow->Bounds.Width);
    1.83 -            break;
    1.84 -        default:
    1.85 -            break;
    1.86 -    }
    1.87 -#endif
    1.88 -
    1.89 -    return outputPosition;
    1.90 -}
    1.91 -
    1.92 -static inline int
    1.93 -_lround(float arg)
    1.94 -{
    1.95 -    if (arg >= 0.0f) {
    1.96 -        return (int)floor(arg + 0.5f);
    1.97 -    } else {
    1.98 -        return (int)ceil(arg - 0.5f);
    1.99 -    }
   1.100 -}
   1.101 -
   1.102 -void
   1.103 -WINRT_ProcessMouseMovedEvent(SDL_Window * window, Windows::Devices::Input::MouseEventArgs ^args)
   1.104 -{
   1.105 -    if (!window || !WINRT_UseRelativeMouseMode) {
   1.106 -        return;
   1.107 -    }
   1.108 -
   1.109 -    // DLudwig, 2012-12-28: On some systems, namely Visual Studio's Windows
   1.110 -    // Simulator, as well as Windows 8 in a Parallels 8 VM, MouseEventArgs'
   1.111 -    // MouseDelta field often reports very large values.  More information
   1.112 -    // on this can be found at the following pages on MSDN:
   1.113 -    //  - http://social.msdn.microsoft.com/Forums/en-US/winappswithnativecode/thread/a3c789fa-f1c5-49c4-9c0a-7db88d0f90f8
   1.114 -    //  - https://connect.microsoft.com/VisualStudio/Feedback/details/756515
   1.115 -    //
   1.116 -    // The values do not appear to be as large when running on some systems,
   1.117 -    // most notably a Surface RT.  Furthermore, the values returned by
   1.118 -    // CoreWindow's PointerMoved event, and sent to this class' OnPointerMoved
   1.119 -    // method, do not ever appear to be large, even when MouseEventArgs'
   1.120 -    // MouseDelta is reporting to the contrary.
   1.121 -    //
   1.122 -    // On systems with the large-values behavior, it appears that the values
   1.123 -    // get reported as if the screen's size is 65536 units in both the X and Y
   1.124 -    // dimensions.  This can be viewed by using Windows' now-private, "Raw Input"
   1.125 -    // APIs.  (GetRawInputData, RegisterRawInputDevices, WM_INPUT, etc.)
   1.126 -    //
   1.127 -    // MSDN's documentation on MouseEventArgs' MouseDelta field (at
   1.128 -    // http://msdn.microsoft.com/en-us/library/windows/apps/windows.devices.input.mouseeventargs.mousedelta ),
   1.129 -    // does not seem to indicate (to me) that its values should be so large.  It
   1.130 -    // says that its values should be a "change in screen location".  I could
   1.131 -    // be misinterpreting this, however a post on MSDN from a Microsoft engineer (see: 
   1.132 -    // http://social.msdn.microsoft.com/Forums/en-US/winappswithnativecode/thread/09a9868e-95bb-4858-ba1a-cb4d2c298d62 ),
   1.133 -    // indicates that these values are in DIPs, which is the same unit used
   1.134 -    // by CoreWindow's PointerMoved events (via the Position field in its CurrentPoint
   1.135 -    // property.  See http://msdn.microsoft.com/en-us/library/windows/apps/windows.ui.input.pointerpoint.position.aspx
   1.136 -    // for details.)
   1.137 -    //
   1.138 -    // To note, PointerMoved events are sent a 'RawPosition' value (via the
   1.139 -    // CurrentPoint property in MouseEventArgs), however these do not seem
   1.140 -    // to exhibit the same large-value behavior.
   1.141 -    //
   1.142 -    // The values passed via PointerMoved events can't always be used for relative
   1.143 -    // mouse motion, unfortunately.  Its values are bound to the cursor's position,
   1.144 -    // which stops when it hits one of the screen's edges.  This can be a problem in
   1.145 -    // first person shooters, whereby it is normal for mouse motion to travel far
   1.146 -    // along any one axis for a period of time.  MouseMoved events do not have the
   1.147 -    // screen-bounding limitation, and can be used regardless of where the system's
   1.148 -    // cursor is.
   1.149 -    //
   1.150 -    // One possible workaround would be to programmatically set the cursor's
   1.151 -    // position to the screen's center (when SDL's relative mouse mode is enabled),
   1.152 -    // however WinRT does not yet seem to have the ability to set the cursor's
   1.153 -    // position via a public API.  Win32 did this via an API call, SetCursorPos,
   1.154 -    // however WinRT makes this function be private.  Apps that use it won't get
   1.155 -    // approved for distribution in the Windows Store.  I've yet to be able to find
   1.156 -    // a suitable, store-friendly counterpart for WinRT.
   1.157 -    //
   1.158 -    // There may be some room for a workaround whereby OnPointerMoved's values
   1.159 -    // are compared to the values from OnMouseMoved in order to detect
   1.160 -    // when this bug is active.  A suitable transformation could then be made to
   1.161 -    // OnMouseMoved's values.  For now, however, the system-reported values are sent
   1.162 -    // to SDL with minimal transformation: from native screen coordinates (in DIPs)
   1.163 -    // to SDL window coordinates.
   1.164 -    //
   1.165 -    const Windows::Foundation::Point mouseDeltaInDIPs((float)args->MouseDelta.X, (float)args->MouseDelta.Y);
   1.166 -    const Windows::Foundation::Point mouseDeltaInSDLWindowCoords = WINRT_TransformCursorPosition(window, mouseDeltaInDIPs);
   1.167 -    SDL_SendMouseMotion(
   1.168 -        window,
   1.169 -        0,
   1.170 -        1,
   1.171 -        _lround(mouseDeltaInSDLWindowCoords.X),
   1.172 -        _lround(mouseDeltaInSDLWindowCoords.Y));
   1.173 -}
   1.174 -
   1.175 -Uint8
   1.176 -WINRT_GetSDLButtonForPointerPoint(Windows::UI::Input::PointerPoint ^pt)
   1.177 -{
   1.178 -    using namespace Windows::UI::Input;
   1.179 -
   1.180 -#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
   1.181 -    return SDL_BUTTON_LEFT;
   1.182 -#else
   1.183 -    switch (pt->Properties->PointerUpdateKind)
   1.184 -    {
   1.185 -        case PointerUpdateKind::LeftButtonPressed:
   1.186 -        case PointerUpdateKind::LeftButtonReleased:
   1.187 -            return SDL_BUTTON_LEFT;
   1.188 -
   1.189 -        case PointerUpdateKind::RightButtonPressed:
   1.190 -        case PointerUpdateKind::RightButtonReleased:
   1.191 -            return SDL_BUTTON_RIGHT;
   1.192 -
   1.193 -        case PointerUpdateKind::MiddleButtonPressed:
   1.194 -        case PointerUpdateKind::MiddleButtonReleased:
   1.195 -            return SDL_BUTTON_MIDDLE;
   1.196 -
   1.197 -        case PointerUpdateKind::XButton1Pressed:
   1.198 -        case PointerUpdateKind::XButton1Released:
   1.199 -            return SDL_BUTTON_X1;
   1.200 -
   1.201 -        case PointerUpdateKind::XButton2Pressed:
   1.202 -        case PointerUpdateKind::XButton2Released:
   1.203 -            return SDL_BUTTON_X2;
   1.204 -
   1.205 -        default:
   1.206 -            break;
   1.207 -    }
   1.208 -#endif
   1.209 -
   1.210 -    return 0;
   1.211 -}
   1.212 -
   1.213 -//const char *
   1.214 -//WINRT_ConvertPointerUpdateKindToString(Windows::UI::Input::PointerUpdateKind kind)
   1.215 -//{
   1.216 -//    using namespace Windows::UI::Input;
   1.217 -//
   1.218 -//    switch (kind)
   1.219 -//    {
   1.220 -//        case PointerUpdateKind::Other:
   1.221 -//            return "Other";
   1.222 -//        case PointerUpdateKind::LeftButtonPressed:
   1.223 -//            return "LeftButtonPressed";
   1.224 -//        case PointerUpdateKind::LeftButtonReleased:
   1.225 -//            return "LeftButtonReleased";
   1.226 -//        case PointerUpdateKind::RightButtonPressed:
   1.227 -//            return "RightButtonPressed";
   1.228 -//        case PointerUpdateKind::RightButtonReleased:
   1.229 -//            return "RightButtonReleased";
   1.230 -//        case PointerUpdateKind::MiddleButtonPressed:
   1.231 -//            return "MiddleButtonPressed";
   1.232 -//        case PointerUpdateKind::MiddleButtonReleased:
   1.233 -//            return "MiddleButtonReleased";
   1.234 -//        case PointerUpdateKind::XButton1Pressed:
   1.235 -//            return "XButton1Pressed";
   1.236 -//        case PointerUpdateKind::XButton1Released:
   1.237 -//            return "XButton1Released";
   1.238 -//        case PointerUpdateKind::XButton2Pressed:
   1.239 -//            return "XButton2Pressed";
   1.240 -//        case PointerUpdateKind::XButton2Released:
   1.241 -//            return "XButton2Released";
   1.242 -//    }
   1.243 -//
   1.244 -//    return "";
   1.245 -//}
   1.246 -
   1.247 -static bool
   1.248 -WINRT_IsTouchEvent(Windows::UI::Input::PointerPoint ^pointerPoint)
   1.249 -{
   1.250 -#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
   1.251 -    return true;
   1.252 -#else
   1.253 -    using namespace Windows::Devices::Input;
   1.254 -    switch (pointerPoint->PointerDevice->PointerDeviceType) {
   1.255 -        case PointerDeviceType::Touch:
   1.256 -        case PointerDeviceType::Pen:
   1.257 -            return true;
   1.258 -        default:
   1.259 -            return false;
   1.260 -    }
   1.261 -#endif
   1.262 -}
   1.263 -
   1.264 -void
   1.265 -WINRT_ProcessPointerMovedEvent(SDL_Window *window, Windows::UI::Input::PointerPoint ^pointerPoint)
   1.266 -{
   1.267 -    if (!window || WINRT_UseRelativeMouseMode) {
   1.268 -        return;
   1.269 -    }
   1.270 -
   1.271 -    Windows::Foundation::Point transformedPoint = WINRT_TransformCursorPosition(window, pointerPoint->Position);
   1.272 -
   1.273 -    if (pointerPoint->PointerId == WINRT_LeftFingerDown) {
   1.274 -        SDL_SendMouseMotion(window, 0, 0, (int)transformedPoint.X, (int)transformedPoint.Y);
   1.275 -    }
   1.276 -
   1.277 -    if (WINRT_IsTouchEvent(pointerPoint)) {
   1.278 -        SDL_SendTouchMotion(
   1.279 -            WINRT_TouchID,
   1.280 -            (SDL_FingerID) pointerPoint->PointerId,
   1.281 -            transformedPoint.X,
   1.282 -            transformedPoint.Y,
   1.283 -            pointerPoint->Properties->Pressure);
   1.284 -    }
   1.285 -}
   1.286 -
   1.287 -void
   1.288 -WINRT_ProcessPointerWheelChangedEvent(SDL_Window *window, Windows::UI::Input::PointerPoint ^pointerPoint)
   1.289 -{
   1.290 -    if (!window) {
   1.291 -        return;
   1.292 -    }
   1.293 -
   1.294 -    // FIXME: This may need to accumulate deltas up to WHEEL_DELTA
   1.295 -    short motion = pointerPoint->Properties->MouseWheelDelta / WHEEL_DELTA;
   1.296 -    SDL_SendMouseWheel(window, 0, 0, motion);
   1.297 -}
   1.298 -
   1.299 -void WINRT_ProcessPointerReleasedEvent(SDL_Window *window, Windows::UI::Input::PointerPoint ^pointerPoint)
   1.300 -{
   1.301 -    if (!window) {
   1.302 -        return;
   1.303 -    }
   1.304 -
   1.305 -    Windows::Foundation::Point transformedPoint = WINRT_TransformCursorPosition(window, pointerPoint->Position);
   1.306 -
   1.307 -    if (WINRT_LeftFingerDown == pointerPoint->PointerId) {
   1.308 -        Uint8 button = WINRT_GetSDLButtonForPointerPoint(pointerPoint);
   1.309 -        if (button) {
   1.310 -            SDL_SendMouseButton(window, 0, SDL_RELEASED, button);
   1.311 -        }
   1.312 -        WINRT_LeftFingerDown = 0;
   1.313 -    }
   1.314 -
   1.315 -    if (WINRT_IsTouchEvent(pointerPoint)) {
   1.316 -        SDL_SendTouch(
   1.317 -            WINRT_TouchID,
   1.318 -            (SDL_FingerID) pointerPoint->PointerId,
   1.319 -            SDL_FALSE,
   1.320 -            transformedPoint.X,
   1.321 -            transformedPoint.Y,
   1.322 -            pointerPoint->Properties->Pressure);
   1.323 -    }
   1.324 -}
   1.325 -
   1.326 -void WINRT_ProcessPointerPressedEvent(SDL_Window *window, Windows::UI::Input::PointerPoint ^pointerPoint)
   1.327 -{
   1.328 -    if (!window) {
   1.329 -        return;
   1.330 -    }
   1.331 -
   1.332 -    Windows::Foundation::Point transformedPoint = WINRT_TransformCursorPosition(window, pointerPoint->Position);
   1.333 -
   1.334 -    if (!WINRT_LeftFingerDown) {
   1.335 -        Uint8 button = WINRT_GetSDLButtonForPointerPoint(pointerPoint);
   1.336 -        if (button) {
   1.337 -#if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
   1.338 -            SDL_SendMouseMotion(window, 0, 0, (int)transformedPoint.X, (int)transformedPoint.Y);
   1.339 -#endif
   1.340 -            SDL_SendMouseButton(window, 0, SDL_PRESSED, button);
   1.341 -        }
   1.342 -
   1.343 -        WINRT_LeftFingerDown = pointerPoint->PointerId;
   1.344 -    }
   1.345 -
   1.346 -    if (WINRT_IsTouchEvent(pointerPoint)) {
   1.347 -        SDL_SendTouch(
   1.348 -            WINRT_TouchID,
   1.349 -            (SDL_FingerID) pointerPoint->PointerId,
   1.350 -            SDL_TRUE,
   1.351 -            transformedPoint.X,
   1.352 -            transformedPoint.Y,
   1.353 -            pointerPoint->Properties->Pressure);
   1.354 -    }
   1.355 -}
   1.356 -
   1.357  #endif /* SDL_VIDEO_DRIVER_WINRT */
   1.358  
   1.359  /* vi: set ts=4 sw=4 expandtab: */