diff --git a/modules/juce_gui_basics/components/juce_Desktop.cpp b/modules/juce_gui_basics/components/juce_Desktop.cpp index 5f59846391..f4966372e5 100644 --- a/modules/juce_gui_basics/components/juce_Desktop.cpp +++ b/modules/juce_gui_basics/components/juce_Desktop.cpp @@ -158,6 +158,11 @@ Point Desktop::getMousePosition() return getInstance().getMainMouseSource().getScreenPosition(); } +void Desktop::setMousePosition (Point newPosition) +{ + getInstance().getMainMouseSource().setScreenPosition (newPosition); +} + Point Desktop::getLastMouseDownPosition() { return getInstance().getMainMouseSource().getLastMouseDownPosition(); diff --git a/modules/juce_gui_basics/components/juce_Desktop.h b/modules/juce_gui_basics/components/juce_Desktop.h index 4517ca850f..dce55fe9da 100644 --- a/modules/juce_gui_basics/components/juce_Desktop.h +++ b/modules/juce_gui_basics/components/juce_Desktop.h @@ -61,8 +61,7 @@ class JUCE_API Desktop : private DeletedAtShutdown, { public: //============================================================================== - /** There's only one dektop object, and this method will return it. - */ + /** There's only one desktop object, and this method will return it. */ static Desktop& JUCE_CALLTYPE getInstance(); //============================================================================== @@ -425,6 +424,8 @@ private: ComponentAnimator animator; + AffineTransform masterTransform; + void timerCallback() override; void resetTimer(); ListenerList & getMouseListeners(); diff --git a/modules/juce_gui_basics/mouse/juce_MouseInputSource.cpp b/modules/juce_gui_basics/mouse/juce_MouseInputSource.cpp index 373224748a..c1102ef6de 100644 --- a/modules/juce_gui_basics/mouse/juce_MouseInputSource.cpp +++ b/modules/juce_gui_basics/mouse/juce_MouseInputSource.cpp @@ -26,8 +26,8 @@ class MouseInputSourceInternal : private AsyncUpdater { public: //============================================================================== - MouseInputSourceInternal (MouseInputSource& source_, const int index_, const bool isMouseDevice_) - : index (index_), isMouseDevice (isMouseDevice_), source (source_), lastPeer (nullptr), + MouseInputSourceInternal (MouseInputSource& s, const int i, const bool isMouse) + : index (i), isMouseDevice (isMouse), source (s), lastPeer (nullptr), isUnboundedMouseModeOn (false), isCursorVisibleUntilOffscreen (false), currentCursorHandle (nullptr), mouseEventCounter (0), mouseMovedSignificantlySincePressed (false) { @@ -76,10 +76,15 @@ public: { // This needs to return the live position if possible, but it mustn't update the lastScreenPos // value, because that can cause continuity problems. - return unboundedMouseOffset + (isMouseDevice ? MouseInputSource::getCurrentMousePosition() + return unboundedMouseOffset + (isMouseDevice ? MouseInputSource::getCurrentRawMousePosition() : lastScreenPos); } + void setScreenPosition (Point p) + { + MouseInputSource::setRawMousePosition (p); + } + //============================================================================== #if JUCE_DUMP_MOUSE_EVENTS #define JUCE_MOUSE_EVENT_DBG(desc) DBG ("Mouse " desc << " #" << source.getIndex() \ @@ -89,52 +94,52 @@ public: #define JUCE_MOUSE_EVENT_DBG(desc) #endif - void sendMouseEnter (Component* const comp, Point screenPos, Time time) + void sendMouseEnter (Component& comp, Point screenPos, Time time) { JUCE_MOUSE_EVENT_DBG ("enter") - comp->internalMouseEnter (source, comp->getLocalPoint (nullptr, screenPos), time); + comp.internalMouseEnter (source, comp.getLocalPoint (nullptr, screenPos), time); } - void sendMouseExit (Component* const comp, Point screenPos, Time time) + void sendMouseExit (Component& comp, Point screenPos, Time time) { JUCE_MOUSE_EVENT_DBG ("exit") - comp->internalMouseExit (source, comp->getLocalPoint (nullptr, screenPos), time); + comp.internalMouseExit (source, comp.getLocalPoint (nullptr, screenPos), time); } - void sendMouseMove (Component* const comp, Point screenPos, Time time) + void sendMouseMove (Component& comp, Point screenPos, Time time) { JUCE_MOUSE_EVENT_DBG ("move") - comp->internalMouseMove (source, comp->getLocalPoint (nullptr, screenPos), time); + comp.internalMouseMove (source, comp.getLocalPoint (nullptr, screenPos), time); } - void sendMouseDown (Component* const comp, Point screenPos, Time time) + void sendMouseDown (Component& comp, Point screenPos, Time time) { JUCE_MOUSE_EVENT_DBG ("down") - comp->internalMouseDown (source, comp->getLocalPoint (nullptr, screenPos), time); + comp.internalMouseDown (source, comp.getLocalPoint (nullptr, screenPos), time); } - void sendMouseDrag (Component* const comp, Point screenPos, Time time) + void sendMouseDrag (Component& comp, Point screenPos, Time time) { JUCE_MOUSE_EVENT_DBG ("drag") - comp->internalMouseDrag (source, comp->getLocalPoint (nullptr, screenPos), time); + comp.internalMouseDrag (source, comp.getLocalPoint (nullptr, screenPos), time); } - void sendMouseUp (Component* const comp, Point screenPos, Time time, const ModifierKeys oldMods) + void sendMouseUp (Component& comp, Point screenPos, Time time, const ModifierKeys oldMods) { JUCE_MOUSE_EVENT_DBG ("up") - comp->internalMouseUp (source, comp->getLocalPoint (nullptr, screenPos), time, oldMods); + comp.internalMouseUp (source, comp.getLocalPoint (nullptr, screenPos), time, oldMods); } - void sendMouseWheel (Component* const comp, Point screenPos, Time time, const MouseWheelDetails& wheel) + void sendMouseWheel (Component& comp, Point screenPos, Time time, const MouseWheelDetails& wheel) { JUCE_MOUSE_EVENT_DBG ("wheel") - comp->internalMouseWheel (source, comp->getLocalPoint (nullptr, screenPos), time, wheel); + comp.internalMouseWheel (source, comp.getLocalPoint (nullptr, screenPos), time, wheel); } - void sendMagnifyGesture (Component* const comp, Point screenPos, Time time, const float amount) + void sendMagnifyGesture (Component& comp, Point screenPos, Time time, const float amount) { JUCE_MOUSE_EVENT_DBG ("magnify") - comp->internalMagnifyGesture (source, comp->getLocalPoint (nullptr, screenPos), time, amount); + comp.internalMagnifyGesture (source, comp.getLocalPoint (nullptr, screenPos), time, amount); } //============================================================================== @@ -164,7 +169,7 @@ public: const ModifierKeys oldMods (getCurrentModifiers()); buttonState = newButtonState; // must change this before calling sendMouseUp, in case it runs a modal loop - sendMouseUp (current, screenPos + unboundedMouseOffset, time, oldMods); + sendMouseUp (*current, screenPos + unboundedMouseOffset, time, oldMods); if (lastCounter != mouseEventCounter) return true; // if a modal loop happened, then newButtonState is no longer valid. @@ -182,7 +187,7 @@ public: if (Component* const current = getComponentUnderMouse()) { registerMouseDown (screenPos, time, *current, buttonState); - sendMouseDown (current, screenPos, time); + sendMouseDown (*current, screenPos, time); } } @@ -206,7 +211,7 @@ public: if (safeOldComp != nullptr) { componentUnderMouse = safeNewComp; - sendMouseExit (safeOldComp, screenPos, time); + sendMouseExit (*safeOldComp, screenPos, time); } buttonState = originalButtonState; @@ -215,21 +220,21 @@ public: current = componentUnderMouse = safeNewComp; if (current != nullptr) - sendMouseEnter (current, screenPos, time); + sendMouseEnter (*current, screenPos, time); revealCursor (false); setButtons (screenPos, time, originalButtonState); } } - void setPeer (ComponentPeer* const newPeer, Point screenPos, Time time) + void setPeer (ComponentPeer& newPeer, Point screenPos, Time time) { ModifierKeys::updateCurrentModifiers(); - if (newPeer != lastPeer) + if (&newPeer != lastPeer) { setComponentUnderMouse (nullptr, screenPos, time); - lastPeer = newPeer; + lastPeer = &newPeer; setComponentUnderMouse (findComponentAt (screenPos), screenPos, time); } } @@ -249,14 +254,14 @@ public: if (isDragging()) { registerMouseDrag (newScreenPos); - sendMouseDrag (current, newScreenPos + unboundedMouseOffset, time); + sendMouseDrag (*current, newScreenPos + unboundedMouseOffset, time); if (isUnboundedMouseModeOn) handleUnboundedDrag (current); } else { - sendMouseMove (current, newScreenPos, time); + sendMouseMove (*current, newScreenPos, time); } } @@ -265,12 +270,11 @@ public: } //============================================================================== - void handleEvent (ComponentPeer* const newPeer, Point positionWithinPeer, Time time, const ModifierKeys newMods) + void handleEvent (ComponentPeer& newPeer, Point positionWithinPeer, Time time, const ModifierKeys newMods) { - jassert (newPeer != nullptr); lastTime = time; ++mouseEventCounter; - const Point screenPos (newPeer->localToGlobal (positionWithinPeer)); + const Point screenPos (newPeer.localToGlobal (positionWithinPeer)); if (isDragging() && newMods.isAnyMouseButtonDown()) { @@ -292,14 +296,13 @@ public: } } - Component* getTargetForGesture (ComponentPeer* const peer, Point positionWithinPeer, + Component* getTargetForGesture (ComponentPeer& peer, Point positionWithinPeer, Time time, Point& screenPos) { - jassert (peer != nullptr); lastTime = time; ++mouseEventCounter; - screenPos = peer->localToGlobal (positionWithinPeer); + screenPos = peer.localToGlobal (positionWithinPeer); setPeer (peer, screenPos, time); setScreenPos (screenPos, time, false); triggerFakeMove(); @@ -307,22 +310,22 @@ public: return isDragging() ? nullptr : getComponentUnderMouse(); } - void handleWheel (ComponentPeer* const peer, Point positionWithinPeer, + void handleWheel (ComponentPeer& peer, Point positionWithinPeer, Time time, const MouseWheelDetails& wheel) { Desktop::getInstance().incrementMouseWheelCounter(); Point screenPos; if (Component* current = getTargetForGesture (peer, positionWithinPeer, time, screenPos)) - sendMouseWheel (current, screenPos, time, wheel); + sendMouseWheel (*current, screenPos, time, wheel); } - void handleMagnifyGesture (ComponentPeer* const peer, Point positionWithinPeer, + void handleMagnifyGesture (ComponentPeer& peer, Point positionWithinPeer, Time time, const float scaleFactor) { Point screenPos; if (Component* current = getTargetForGesture (peer, positionWithinPeer, time, screenPos)) - sendMagnifyGesture (current, screenPos, time, scaleFactor); + sendMagnifyGesture (*current, screenPos, time, scaleFactor); } //============================================================================== @@ -535,20 +538,21 @@ void MouseInputSource::showMouseCursor (const MouseCursor& cursor) { pimpl- void MouseInputSource::hideCursor() { pimpl->hideCursor(); } void MouseInputSource::revealCursor() { pimpl->revealCursor (false); } void MouseInputSource::forceMouseCursorUpdate() { pimpl->revealCursor (true); } +void MouseInputSource::setScreenPosition (Point p) { pimpl->setScreenPosition (p); } -void MouseInputSource::handleEvent (ComponentPeer* peer, Point positionWithinPeer, +void MouseInputSource::handleEvent (ComponentPeer& peer, Point positionWithinPeer, const int64 time, const ModifierKeys mods) { pimpl->handleEvent (peer, positionWithinPeer, Time (time), mods.withOnlyMouseButtons()); } -void MouseInputSource::handleWheel (ComponentPeer* const peer, Point positionWithinPeer, +void MouseInputSource::handleWheel (ComponentPeer& peer, Point positionWithinPeer, const int64 time, const MouseWheelDetails& wheel) { pimpl->handleWheel (peer, positionWithinPeer, Time (time), wheel); } -void MouseInputSource::handleMagnifyGesture (ComponentPeer* const peer, Point positionWithinPeer, +void MouseInputSource::handleMagnifyGesture (ComponentPeer& peer, Point positionWithinPeer, const int64 time, const float scaleFactor) { pimpl->handleMagnifyGesture (peer, positionWithinPeer, Time (time), scaleFactor); diff --git a/modules/juce_gui_basics/mouse/juce_MouseInputSource.h b/modules/juce_gui_basics/mouse/juce_MouseInputSource.h index 6a77cde240..84901e63dc 100644 --- a/modules/juce_gui_basics/mouse/juce_MouseInputSource.h +++ b/modules/juce_gui_basics/mouse/juce_MouseInputSource.h @@ -163,22 +163,21 @@ public: */ void enableUnboundedMouseMovement (bool isEnabled, bool keepCursorVisibleUntilOffscreen = false); - //============================================================================== - /** @internal */ - void handleEvent (ComponentPeer*, Point, int64 time, const ModifierKeys); - /** @internal */ - void handleWheel (ComponentPeer*, Point, int64 time, const MouseWheelDetails&); - /** @internal */ - void handleMagnifyGesture (ComponentPeer*, Point, int64 time, float scaleFactor); + /** Attempts to set this mouse pointer's screen position. */ + void setScreenPosition (Point newPosition); private: //============================================================================== - friend class Desktop; friend class ComponentPeer; friend class MouseInputSourceInternal; ScopedPointer pimpl; - static Point getCurrentMousePosition(); + void handleEvent (ComponentPeer&, Point, int64 time, const ModifierKeys); + void handleWheel (ComponentPeer&, Point, int64 time, const MouseWheelDetails&); + void handleMagnifyGesture (ComponentPeer&, Point, int64 time, float scaleFactor); + + static Point getCurrentRawMousePosition(); + static void setRawMousePosition (Point); JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MouseInputSource) }; diff --git a/modules/juce_gui_basics/native/juce_android_Windowing.cpp b/modules/juce_gui_basics/native/juce_android_Windowing.cpp index 54605b790a..10e8c05bd1 100644 --- a/modules/juce_gui_basics/native/juce_android_Windowing.cpp +++ b/modules/juce_gui_basics/native/juce_android_Windowing.cpp @@ -584,12 +584,12 @@ bool Desktop::addMouseInputSource() return true; } -Point MouseInputSource::getCurrentMousePosition() +Point MouseInputSource::getCurrentRawMousePosition() { return AndroidComponentPeer::lastMousePos; } -void Desktop::setMousePosition (Point newPosition) +void MouseInputSource::setRawMousePosition (Point) { // not needed } diff --git a/modules/juce_gui_basics/native/juce_ios_Windowing.mm b/modules/juce_gui_basics/native/juce_ios_Windowing.mm index 8f9eb1374a..2c4c85f1a2 100644 --- a/modules/juce_gui_basics/native/juce_ios_Windowing.mm +++ b/modules/juce_gui_basics/native/juce_ios_Windowing.mm @@ -288,12 +288,12 @@ bool Desktop::canUseSemiTransparentWindows() noexcept return true; } -Point MouseInputSource::getCurrentMousePosition() +Point MouseInputSource::getCurrentRawMousePosition() { return juce_lastMousePos; } -void Desktop::setMousePosition (Point) +void MouseInputSource::setRawMousePosition (Point) { } diff --git a/modules/juce_gui_basics/native/juce_linux_Windowing.cpp b/modules/juce_gui_basics/native/juce_linux_Windowing.cpp index d995500428..bbcd4473e2 100644 --- a/modules/juce_gui_basics/native/juce_linux_Windowing.cpp +++ b/modules/juce_gui_basics/native/juce_linux_Windowing.cpp @@ -3104,7 +3104,7 @@ bool Desktop::canUseSemiTransparentWindows() noexcept && (matchedDepth == desiredDepth); } -Point MouseInputSource::getCurrentMousePosition() +Point MouseInputSource::getCurrentRawMousePosition() { Window root, child; int x, y, winx, winy; @@ -3124,7 +3124,7 @@ Point MouseInputSource::getCurrentMousePosition() return Point (x, y); } -void Desktop::setMousePosition (Point newPosition) +void MouseInputSource::setRawMousePosition (Point newPosition) { ScopedXLock xlock; Window root = RootWindow (display, DefaultScreen (display)); diff --git a/modules/juce_gui_basics/native/juce_mac_Windowing.mm b/modules/juce_gui_basics/native/juce_mac_Windowing.mm index 786f3751a7..60155eedb0 100644 --- a/modules/juce_gui_basics/native/juce_mac_Windowing.mm +++ b/modules/juce_gui_basics/native/juce_mac_Windowing.mm @@ -208,7 +208,7 @@ bool Desktop::canUseSemiTransparentWindows() noexcept return true; } -Point MouseInputSource::getCurrentMousePosition() +Point MouseInputSource::getCurrentRawMousePosition() { JUCE_AUTORELEASEPOOL { @@ -217,7 +217,7 @@ Point MouseInputSource::getCurrentMousePosition() } } -void Desktop::setMousePosition (Point newPosition) +void MouseInputSource::setRawMousePosition (Point newPosition) { // this rubbish needs to be done around the warp call, to avoid causing a // bizarre glitch.. diff --git a/modules/juce_gui_basics/native/juce_win32_Windowing.cpp b/modules/juce_gui_basics/native/juce_win32_Windowing.cpp index 10c320ac82..d83a6679fa 100644 --- a/modules/juce_gui_basics/native/juce_win32_Windowing.cpp +++ b/modules/juce_gui_basics/native/juce_win32_Windowing.cpp @@ -3021,14 +3021,14 @@ bool Desktop::addMouseInputSource() return false; } -Point MouseInputSource::getCurrentMousePosition() +Point MouseInputSource::getCurrentRawMousePosition() { POINT mousePos; GetCursorPos (&mousePos); return Point (mousePos.x, mousePos.y); } -void Desktop::setMousePosition (Point newPosition) +void MouseInputSource::setRawMousePosition (Point newPosition) { SetCursorPos (newPosition.x, newPosition.y); } diff --git a/modules/juce_gui_basics/windows/juce_ComponentPeer.cpp b/modules/juce_gui_basics/windows/juce_ComponentPeer.cpp index a10732bc77..b01d4d5593 100644 --- a/modules/juce_gui_basics/windows/juce_ComponentPeer.cpp +++ b/modules/juce_gui_basics/windows/juce_ComponentPeer.cpp @@ -78,21 +78,21 @@ void ComponentPeer::handleMouseEvent (const int touchIndex, const Point pos const ModifierKeys newMods, const int64 time) { if (MouseInputSource* mouse = Desktop::getInstance().getOrCreateMouseInputSource (touchIndex)) - mouse->handleEvent (this, positionWithinPeer, time, newMods); + mouse->handleEvent (*this, positionWithinPeer, time, newMods); } void ComponentPeer::handleMouseWheel (const int touchIndex, const Point positionWithinPeer, const int64 time, const MouseWheelDetails& wheel) { if (MouseInputSource* mouse = Desktop::getInstance().getOrCreateMouseInputSource (touchIndex)) - mouse->handleWheel (this, positionWithinPeer, time, wheel); + mouse->handleWheel (*this, positionWithinPeer, time, wheel); } void ComponentPeer::handleMagnifyGesture (const int touchIndex, const Point positionWithinPeer, const int64 time, const float scaleFactor) { if (MouseInputSource* mouse = Desktop::getInstance().getOrCreateMouseInputSource (touchIndex)) - mouse->handleMagnifyGesture (this, positionWithinPeer, time, scaleFactor); + mouse->handleMagnifyGesture (*this, positionWithinPeer, time, scaleFactor); } //==============================================================================