Browse Source

Internal refactoring of mouse-event classes, as the first step towards multi-touch support.

tags/2021-05-28
Julian Storer 15 years ago
parent
commit
9657241c10
35 changed files with 2725 additions and 2624 deletions
  1. +1
    -0
      amalgamation/juce_amalgamated_template.cpp
  2. +8
    -0
      build/macosx/Juce.xcodeproj/project.pbxproj
  3. +8
    -0
      build/win32/vc8/JUCE.vcproj
  4. +1169
    -1239
      juce_amalgamated.cpp
  5. +202
    -117
      juce_amalgamated.h
  6. +1
    -1
      src/containers/juce_Variant.h
  7. +1
    -1
      src/core/juce_StandardHeader.h
  8. +9
    -12
      src/gui/components/controls/juce_Slider.cpp
  9. +3
    -12
      src/gui/components/controls/juce_TreeView.cpp
  10. +73
    -122
      src/gui/components/juce_Component.cpp
  11. +12
    -7
      src/gui/components/juce_Component.h
  12. +10
    -58
      src/gui/components/juce_Desktop.cpp
  13. +13
    -14
      src/gui/components/juce_Desktop.h
  14. +2
    -2
      src/gui/components/keyboard/juce_ModifierKeys.cpp
  15. +15
    -1
      src/gui/components/keyboard/juce_ModifierKeys.h
  16. +26
    -22
      src/gui/components/mouse/juce_MouseEvent.cpp
  17. +32
    -17
      src/gui/components/mouse/juce_MouseEvent.h
  18. +1
    -0
      src/gui/components/mouse/juce_MouseHoverDetector.cpp
  19. +370
    -0
      src/gui/components/mouse/juce_MouseInputSource.cpp
  20. +85
    -0
      src/gui/components/mouse/juce_MouseInputSource.h
  21. +1
    -2
      src/gui/components/mouse/juce_MouseListener.h
  22. +1
    -0
      src/gui/components/special/juce_ActiveXControlComponent.h
  23. +20
    -19
      src/gui/components/special/juce_MagnifierComponent.cpp
  24. +3
    -0
      src/gui/components/special/juce_MagnifierComponent.h
  25. +5
    -194
      src/gui/components/windows/juce_ComponentPeer.cpp
  26. +4
    -15
      src/gui/components/windows/juce_ComponentPeer.h
  27. +3
    -3
      src/gui/graphics/contexts/juce_LowLevelGraphicsSoftwareRenderer.cpp
  28. +4
    -4
      src/io/streams/juce_OutputStream.cpp
  29. +4
    -4
      src/io/streams/juce_OutputStream.h
  30. +1
    -0
      src/native/juce_mac_NativeCode.mm
  31. +179
    -219
      src/native/linux/juce_linux_Windowing.cpp
  32. +21
    -24
      src/native/mac/juce_iphone_UIViewComponentPeer.mm
  33. +50
    -52
      src/native/mac/juce_mac_NSViewComponentPeer.mm
  34. +258
    -267
      src/native/windows/juce_win32_ActiveXComponent.cpp
  35. +130
    -196
      src/native/windows/juce_win32_Windowing.cpp

+ 1
- 0
amalgamation/juce_amalgamated_template.cpp View File

@@ -288,6 +288,7 @@
#include "../src/gui/components/mouse/juce_DragAndDropContainer.cpp"
#include "../src/gui/components/mouse/juce_MouseCursor.cpp"
#include "../src/gui/components/mouse/juce_MouseEvent.cpp"
#include "../src/gui/components/mouse/juce_MouseInputSource.cpp"
#include "../src/gui/components/mouse/juce_MouseHoverDetector.cpp"
#include "../src/gui/components/mouse/juce_MouseListener.cpp"
#include "../src/gui/components/properties/juce_BooleanPropertyComponent.cpp"


+ 8
- 0
build/macosx/Juce.xcodeproj/project.pbxproj View File

@@ -34,6 +34,8 @@
8473E64B11249FD800D74E02 /* juce_TextInputTarget.h in Headers */ = {isa = PBXBuildFile; fileRef = 8473E64911249FD800D74E02 /* juce_TextInputTarget.h */; };
8473E6531125974600D74E02 /* juce_Range.h in Headers */ = {isa = PBXBuildFile; fileRef = 8473E6521125974600D74E02 /* juce_Range.h */; };
8473E6541125974600D74E02 /* juce_Range.h in Headers */ = {isa = PBXBuildFile; fileRef = 8473E6521125974600D74E02 /* juce_Range.h */; };
84751E5B1132EE9E00640F9A /* juce_MouseInputSource.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 84751E591132EE9E00640F9A /* juce_MouseInputSource.cpp */; };
84751E5C1132EE9E00640F9A /* juce_MouseInputSource.h in Headers */ = {isa = PBXBuildFile; fileRef = 84751E5A1132EE9E00640F9A /* juce_MouseInputSource.h */; };
84816E5710809D07008FEC33 /* juce_iphone_Audio.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 84816E5110809D07008FEC33 /* juce_iphone_Audio.cpp */; };
84816E5910809D07008FEC33 /* juce_iphone_MessageManager.mm in Sources */ = {isa = PBXBuildFile; fileRef = 84816E5310809D07008FEC33 /* juce_iphone_MessageManager.mm */; };
84816E5A10809D07008FEC33 /* juce_iphone_MiscUtilities.mm in Sources */ = {isa = PBXBuildFile; fileRef = 84816E5410809D07008FEC33 /* juce_iphone_MiscUtilities.mm */; };
@@ -1243,6 +1245,8 @@
8456EC6908A2A6F00087C412 /* JUCE changelist.txt */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = text; name = "JUCE changelist.txt"; path = "../../docs/JUCE changelist.txt"; sourceTree = SOURCE_ROOT; };
8473E64911249FD800D74E02 /* juce_TextInputTarget.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = juce_TextInputTarget.h; sourceTree = "<group>"; };
8473E6521125974600D74E02 /* juce_Range.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = juce_Range.h; sourceTree = "<group>"; };
84751E591132EE9E00640F9A /* juce_MouseInputSource.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = juce_MouseInputSource.cpp; sourceTree = "<group>"; };
84751E5A1132EE9E00640F9A /* juce_MouseInputSource.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = juce_MouseInputSource.h; sourceTree = "<group>"; };
84816E3510809B4F008FEC33 /* libjucedebug.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libjucedebug.a; sourceTree = BUILT_PRODUCTS_DIR; };
84816E5110809D07008FEC33 /* juce_iphone_Audio.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = juce_iphone_Audio.cpp; sourceTree = "<group>"; };
84816E5310809D07008FEC33 /* juce_iphone_MessageManager.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = juce_iphone_MessageManager.mm; sourceTree = "<group>"; };
@@ -2674,6 +2678,8 @@
84F1EAD810403709006A1807 /* juce_MouseEvent.cpp */,
84F1EAD910403709006A1807 /* juce_MouseHoverDetector.h */,
84F1EADA10403709006A1807 /* juce_MouseHoverDetector.cpp */,
84751E591132EE9E00640F9A /* juce_MouseInputSource.cpp */,
84751E5A1132EE9E00640F9A /* juce_MouseInputSource.h */,
84F1EADB10403709006A1807 /* juce_MouseListener.h */,
84F1EADC10403709006A1807 /* juce_MouseListener.cpp */,
84F1EADD10403709006A1807 /* juce_TooltipClient.h */,
@@ -3584,6 +3590,7 @@
8414DE8511122A8D00DAF75A /* juce_DynamicObject.h in Headers */,
8473E64A11249FD800D74E02 /* juce_TextInputTarget.h in Headers */,
8473E6531125974600D74E02 /* juce_Range.h in Headers */,
84751E5C1132EE9E00640F9A /* juce_MouseInputSource.h in Headers */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -4226,6 +4233,7 @@
84CABF691101292D0088D64D /* juce_TemporaryFile.cpp in Sources */,
8414DE78111229B300DAF75A /* juce_NamedValueSet.cpp in Sources */,
8414DE8411122A8D00DAF75A /* juce_DynamicObject.cpp in Sources */,
84751E5B1132EE9E00640F9A /* juce_MouseInputSource.cpp in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};


+ 8
- 0
build/win32/vc8/JUCE.vcproj View File

@@ -1931,6 +1931,14 @@
RelativePath="..\..\..\src\gui\components\mouse\juce_MouseHoverDetector.h"
>
</File>
<File
RelativePath="..\..\..\src\gui\components\mouse\juce_MouseInputSource.cpp"
>
</File>
<File
RelativePath="..\..\..\src\gui\components\mouse\juce_MouseInputSource.h"
>
</File>
<File
RelativePath="..\..\..\src\gui\components\mouse\juce_MouseListener.cpp"
>


+ 1169
- 1239
juce_amalgamated.cpp
File diff suppressed because it is too large
View File


+ 202
- 117
juce_amalgamated.h View File

@@ -43,7 +43,7 @@

#define JUCE_MAJOR_VERSION 1
#define JUCE_MINOR_VERSION 51
#define JUCE_BUILDNUMBER 2
#define JUCE_BUILDNUMBER 3

#define JUCE_VERSION ((JUCE_MAJOR_VERSION << 16) + (JUCE_MINOR_VERSION << 8) + JUCE_BUILDNUMBER)

@@ -1385,41 +1385,41 @@ private:
void dupeInternalIfMultiplyReferenced() throw();
};

const String JUCE_PUBLIC_FUNCTION operator+ (const char* string1, const String& string2);
const String JUCE_PUBLIC_FUNCTION operator+ (const juce_wchar* string1, const String& string2);
const String JUCE_PUBLIC_FUNCTION operator+ (char string1, const String& string2);
const String JUCE_PUBLIC_FUNCTION operator+ (juce_wchar string1, const String& string2);
const String JUCE_PUBLIC_FUNCTION operator+ (String string1, const String& string2);
const String JUCE_PUBLIC_FUNCTION operator+ (String string1, const char* string2);
const String JUCE_PUBLIC_FUNCTION operator+ (String string1, const juce_wchar* string2);
const String JUCE_PUBLIC_FUNCTION operator+ (String string1, char characterToAppend);
const String JUCE_PUBLIC_FUNCTION operator+ (String string1, juce_wchar characterToAppend);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const char characterToAppend);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const juce_wchar characterToAppend);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const char* const string2);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const juce_wchar* const string2);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const String& string2);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const short number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const int number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const unsigned int number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const long number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const unsigned long number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const float number);
String& JUCE_PUBLIC_FUNCTION operator<< (String& string1, const double number);
bool JUCE_PUBLIC_FUNCTION operator== (const String& string1, const String& string2) throw();
bool JUCE_PUBLIC_FUNCTION operator== (const String& string1, const char* string2) throw();
bool JUCE_PUBLIC_FUNCTION operator== (const String& string1, const juce_wchar* string2) throw();
bool JUCE_PUBLIC_FUNCTION operator!= (const String& string1, const String& string2) throw();
bool JUCE_PUBLIC_FUNCTION operator!= (const String& string1, const char* string2) throw();
bool JUCE_PUBLIC_FUNCTION operator!= (const String& string1, const juce_wchar* string2) throw();
bool JUCE_PUBLIC_FUNCTION operator> (const String& string1, const String& string2) throw();
bool JUCE_PUBLIC_FUNCTION operator< (const String& string1, const String& string2) throw();
bool JUCE_PUBLIC_FUNCTION operator>= (const String& string1, const String& string2) throw();
bool JUCE_PUBLIC_FUNCTION operator<= (const String& string1, const String& string2) throw();
const String operator+ (const char* string1, const String& string2);
const String operator+ (const juce_wchar* string1, const String& string2);
const String operator+ (char string1, const String& string2);
const String operator+ (juce_wchar string1, const String& string2);
const String operator+ (String string1, const String& string2);
const String operator+ (String string1, const char* string2);
const String operator+ (String string1, const juce_wchar* string2);
const String operator+ (String string1, char characterToAppend);
const String operator+ (String string1, juce_wchar characterToAppend);
String& operator<< (String& string1, const char characterToAppend);
String& operator<< (String& string1, const juce_wchar characterToAppend);
String& operator<< (String& string1, const char* const string2);
String& operator<< (String& string1, const juce_wchar* const string2);
String& operator<< (String& string1, const String& string2);
String& operator<< (String& string1, const short number);
String& operator<< (String& string1, const int number);
String& operator<< (String& string1, const unsigned int number);
String& operator<< (String& string1, const long number);
String& operator<< (String& string1, const unsigned long number);
String& operator<< (String& string1, const float number);
String& operator<< (String& string1, const double number);
bool operator== (const String& string1, const String& string2) throw();
bool operator== (const String& string1, const char* string2) throw();
bool operator== (const String& string1, const juce_wchar* string2) throw();
bool operator!= (const String& string1, const String& string2) throw();
bool operator!= (const String& string1, const char* string2) throw();
bool operator!= (const String& string1, const juce_wchar* string2) throw();
bool operator> (const String& string1, const String& string2) throw();
bool operator< (const String& string1, const String& string2) throw();
bool operator>= (const String& string1, const String& string2) throw();
bool operator<= (const String& string1, const String& string2) throw();

template <class charT, class traits>
std::basic_ostream <charT, traits>& operator<< (std::basic_ostream <charT, traits>& stream, const String& stringToWrite)
@@ -1427,7 +1427,7 @@ std::basic_ostream <charT, traits>& operator<< (std::basic_ostream <charT, trait
return stream << stringToWrite.toUTF8();
}

OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const String& text);
OutputStream& operator<< (OutputStream& stream, const String& text);

#endif // __JUCE_STRING_JUCEHEADER__
/*** End of inlined file: juce_String.h ***/
@@ -2850,13 +2850,13 @@ public:
juce_UseDebuggingNewOperator
};

OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const int number);
OutputStream& operator<< (OutputStream& stream, const int number);

OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const double number);
OutputStream& operator<< (OutputStream& stream, const double number);

OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char character);
OutputStream& operator<< (OutputStream& stream, const char character);

OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char* const text);
OutputStream& operator<< (OutputStream& stream, const char* const text);

#endif // __JUCE_OUTPUTSTREAM_JUCEHEADER__
/*** End of inlined file: juce_OutputStream.h ***/
@@ -2913,9 +2913,6 @@ public:
bool isObject() const throw() { return type == objectType; }
bool isMethod() const throw() { return type == methodType; }

bool operator== (const var& other) const throw();
bool operator!= (const var& other) const throw();

void writeToStream (OutputStream& output) const;

static const var readFromStream (InputStream& input);
@@ -2956,6 +2953,8 @@ public:

juce_UseDebuggingNewOperator

bool equals (const var& other) const throw();

private:
enum Type
{
@@ -2982,6 +2981,11 @@ private:
ValueUnion value;
};

bool operator== (const var& v1, const var& v2) throw();
bool operator!= (const var& v1, const var& v2) throw();
bool operator== (const var& v1, const String& v2) throw();
bool operator!= (const var& v1, const String& v2) throw();

#endif // __JUCE_VARIANT_JUCEHEADER__
/*** End of inlined file: juce_Variant.h ***/

@@ -8924,12 +8928,42 @@ private:
#ifndef __JUCE_MOUSELISTENER_JUCEHEADER__
#define __JUCE_MOUSELISTENER_JUCEHEADER__

class MouseEvent;

class JUCE_API MouseListener
{
public:
virtual ~MouseListener() {}

virtual void mouseMove (const MouseEvent& e);

virtual void mouseEnter (const MouseEvent& e);

virtual void mouseExit (const MouseEvent& e);

virtual void mouseDown (const MouseEvent& e);

virtual void mouseDrag (const MouseEvent& e);

virtual void mouseUp (const MouseEvent& e);

virtual void mouseDoubleClick (const MouseEvent& e);

virtual void mouseWheelMove (const MouseEvent& e,
float wheelIncrementX,
float wheelIncrementY);
};

#endif // __JUCE_MOUSELISTENER_JUCEHEADER__
/*** End of inlined file: juce_MouseListener.h ***/


/*** Start of inlined file: juce_MouseEvent.h ***/
#ifndef __JUCE_MOUSEEVENT_JUCEHEADER__
#define __JUCE_MOUSEEVENT_JUCEHEADER__

class Component;
class MouseInputSource;

/*** Start of inlined file: juce_ModifierKeys.h ***/
#ifndef __JUCE_MODIFIERKEYS_JUCEHEADER__
@@ -8994,8 +9028,18 @@ public:
allMouseButtonModifiers = leftButtonModifier | rightButtonModifier | middleButtonModifier,
};

const ModifierKeys withOnlyMouseButtons() const throw() { return ModifierKeys (flags & allMouseButtonModifiers); }

const ModifierKeys withoutMouseButtons() const throw() { return ModifierKeys (flags & ~allMouseButtonModifiers); }

bool operator== (const ModifierKeys& other) const throw() { return flags == other.flags; }
bool operator!= (const ModifierKeys& other) const throw() { return flags != other.flags; }

inline int getRawFlags() const throw() { return flags; }

inline const ModifierKeys withoutFlags (int rawFlagsToClear) const throw() { return ModifierKeys (flags & ~rawFlagsToClear); }
inline const ModifierKeys withFlags (int rawFlagsToSet) const throw() { return ModifierKeys (flags | rawFlagsToSet); }

inline bool testFlags (const int flagsToTest) const throw() { return (flags & flagsToTest) != 0; }

int getNumMouseButtonsDown() const throw();
@@ -9008,9 +9052,11 @@ private:

int flags;

static int currentModifierFlags;
static ModifierKeys currentModifiers;

friend class ComponentPeer;
friend class MouseInputSource;
friend class MouseInputSourceInternal;
static void updateCurrentModifiers() throw();
};

@@ -9163,7 +9209,8 @@ class JUCE_API MouseEvent
{
public:

MouseEvent (const Point<int>& position,
MouseEvent (MouseInputSource& source,
const Point<int>& position,
const ModifierKeys& modifiers,
Component* const originator,
const Time& eventTime,
@@ -9174,17 +9221,19 @@ public:

~MouseEvent() throw();

int x;
const int x;

int y;
const int y;

ModifierKeys mods;
const ModifierKeys mods;

Component* const eventComponent;

Component* eventComponent;
Component* const originalComponent;

Component* originalComponent;
const Time eventTime;

Time eventTime;
MouseInputSource& source;

int getMouseDownX() const throw();

@@ -9220,6 +9269,8 @@ public:

const MouseEvent getEventRelativeTo (Component* const otherComponent) const throw();

const MouseEvent withNewPosition (const Point<int>& newPosition) const throw();

static void setDoubleClickTimeout (const int timeOutMilliseconds) throw();

static int getDoubleClickTimeout() throw();
@@ -9227,42 +9278,17 @@ public:
juce_UseDebuggingNewOperator

private:
Point<int> mouseDownPos;
Time mouseDownTime;
int numberOfClicks;
bool wasMovedSinceMouseDown;
const Point<int> mouseDownPos;
const Time mouseDownTime;
const int numberOfClicks;
const bool wasMovedSinceMouseDown;

MouseEvent& operator= (const MouseEvent&);
};

#endif // __JUCE_MOUSEEVENT_JUCEHEADER__
/*** End of inlined file: juce_MouseEvent.h ***/

class JUCE_API MouseListener
{
public:
virtual ~MouseListener() {}

virtual void mouseMove (const MouseEvent& e);

virtual void mouseEnter (const MouseEvent& e);

virtual void mouseExit (const MouseEvent& e);

virtual void mouseDown (const MouseEvent& e);

virtual void mouseDrag (const MouseEvent& e);

virtual void mouseUp (const MouseEvent& e);

virtual void mouseDoubleClick (const MouseEvent& e);

virtual void mouseWheelMove (const MouseEvent& e,
float wheelIncrementX,
float wheelIncrementY);
};

#endif // __JUCE_MOUSELISTENER_JUCEHEADER__
/*** End of inlined file: juce_MouseListener.h ***/


/*** Start of inlined file: juce_ComponentListener.h ***/
#ifndef __JUCE_COMPONENTLISTENER_JUCEHEADER__
@@ -11966,7 +11992,7 @@ public:
class ComponentBoundsConstrainer;
class ComponentDeletionWatcher;

class JUCE_API ComponentPeer : public MessageListener
class JUCE_API ComponentPeer
{
public:

@@ -12047,7 +12073,7 @@ public:

ComponentBoundsConstrainer* getConstrainer() const throw() { return constrainer; }

virtual bool contains (int x, int y, bool trueIfInAChildWindow) const = 0;
virtual bool contains (const Point<int>& position, bool trueIfInAChildWindow) const = 0;

virtual const BorderSize getFrameSize() const = 0;

@@ -12089,15 +12115,8 @@ public:

virtual void performAnyPendingRepaintsNow() = 0;

void handleMouseEnter (const Point<int>& position, const int64 time);
void handleMouseMove (const Point<int>& position, const int64 time);
void handleMouseDown (const Point<int>& position, const int64 time);
void handleMouseDrag (const Point<int>& position, const int64 time);
void handleMouseUp (const int oldModifiers, const Point<int>& position, const int64 time);
void handleMouseExit (const Point<int>& position, const int64 time);
void handleMouseWheel (const int amountX, const int amountY, const int64 time);

void sendFakeMouseMove() throw();
void handleMouseEvent (const Point<int>& positionWithinPeer, const ModifierKeys& newMods, const int64 time);
void handleMouseWheel (const Point<int>& positionWithinPeer, const int64 time, float x, float y);

void handleUserClosingWindow();

@@ -12133,8 +12152,6 @@ protected:

static void updateCurrentModifiers() throw();

void handleMessage (const Message& message);

private:

Component* lastFocusedComponent;
@@ -12155,6 +12172,8 @@ private:
/*** End of inlined file: juce_ComponentPeer.h ***/

class LookAndFeel;
class MouseInputSource;
class MouseInputSourceInternal;

class JUCE_API Component : public MouseListener,
protected MessageListener
@@ -12545,6 +12564,8 @@ private:

friend class ComponentPeer;
friend class InternalDragRepeater;
friend class MouseInputSource;
friend class MouseInputSourceInternal;

static Component* currentlyFocusedComponent;
static Component* componentUnderMouse;
@@ -12595,13 +12616,13 @@ private:
ComponentFlags flags;
};

void internalMouseEnter (int x, int y, const int64 time);
void internalMouseExit (int x, int y, const int64 time);
void internalMouseDown (int x, int y, const int64 time);
void internalMouseUp (const int oldModifiers, int x, int y, const int64 time);
void internalMouseDrag (int x, int y, const int64 time);
void internalMouseMove (int x, int y, const int64 time);
void internalMouseWheel (const int intAmountX, const int intAmountY, const int64 time);
void internalMouseEnter (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseExit (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseDown (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseUp (MouseInputSource& source, const Point<int>& relativePos, const Time& time, const ModifierKeys& oldModifiers);
void internalMouseDrag (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseMove (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseWheel (MouseInputSource& source, const Point<int>& relativePos, const Time& time, const float amountX, const float amountY);
void internalBroughtToFront();
void internalFocusGain (const FocusChangeType cause);
void internalFocusLoss (const FocusChangeType cause);
@@ -12998,6 +13019,10 @@ private:
#endif // __JUCE_TIMER_JUCEHEADER__
/*** End of inlined file: juce_Timer.h ***/

class MouseInputSource;
class MouseInputSourceInternal;
class MouseListener;

class JUCE_API FocusChangeListener
{
public:
@@ -13057,12 +13082,18 @@ public:

static bool canUseSemiTransparentWindows() throw();

int getNumMouseInputSources() const throw() { return mouseSources.size(); }
MouseInputSource* getMouseSource (int index) const throw() { return mouseSources [index]; }
MouseInputSource& getMainMouseSource() const throw() { return *mouseSources.getUnchecked(0); }

private:

static Desktop* instance;

friend class Component;
friend class ComponentPeer;
friend class MouseInputSource;
friend class MouseInputSourceInternal;
SortedSet <void*> mouseListeners, focusListeners;
Array <Component*> desktopComponents;

@@ -13073,24 +13104,12 @@ private:

Array <Rectangle<int> > monitorCoordsClipped, monitorCoordsUnclipped;

OwnedArray <MouseInputSource> mouseSources;

Point<int> lastFakeMouseMove;
int mouseClickCounter;
bool mouseMovedSignificantlySincePressed;

struct RecentMouseDown
{
Point<int> position;
int64 time;
Component* component;
};

RecentMouseDown mouseDowns[4];

void incrementMouseClickCounter() throw();
void registerMouseDown (const Point<int>& position, int64 time, Component* component) throw();
void registerMouseDrag (const Point<int>& position) throw();
const Time getLastMouseDownTime() const throw();
int getNumberOfMultipleClicks() const throw();

Component* kioskModeComponent;
Rectangle<int> kioskComponentOriginalBounds;
@@ -25899,6 +25918,7 @@ public:
juce_UseDebuggingNewOperator

private:
class ActiveXControlData;
friend class ActiveXControlData;
void* control;
bool mouseEventsAllowed;
@@ -26176,6 +26196,69 @@ private:
#ifndef __JUCE_MAGNIFIERCOMPONENT_JUCEHEADER__
#define __JUCE_MAGNIFIERCOMPONENT_JUCEHEADER__


/*** Start of inlined file: juce_MouseInputSource.h ***/
#ifndef __JUCE_MOUSEEVENT_JUCEHEADER__x
#define __JUCE_MOUSEEVENT_JUCEHEADER__x

class Component;
class ComponentPeer;
class MouseInputSourceInternal;

class JUCE_API MouseInputSource
{
public:

MouseInputSource (int index, bool isMouseDevice);

~MouseInputSource();

bool isMouse() const;

bool isTouch() const;

bool canHover() const;

bool hasMouseWheel() const;

int getIndex() const;

bool isDragging() const;

const Point<int> getScreenPosition() const;

const ModifierKeys getCurrentModifiers() const;

Component* getComponentUnderMouse() const;

void triggerFakeMove() const;

int getNumberOfMultipleClicks() const throw();

const Time getLastMouseDownTime() const throw();

const Point<int> getLastMouseDownPosition() const throw();

bool hasMouseMovedSignificantlySincePressed() const throw();

juce_UseDebuggingNewOperator

void handleEvent (ComponentPeer* peer, const Point<int>& positionWithinPeer, int64 time, const ModifierKeys& mods);
void handleWheel (ComponentPeer* peer, const Point<int>& positionWithinPeer, int64 time, float x, float y);

private:
friend class Desktop;
friend class ComponentPeer;
friend class MouseInputSourceInternal;
ScopedPointer<MouseInputSourceInternal> pimpl;

MouseInputSource (const MouseInputSource&);
MouseInputSource& operator= (const MouseInputSource&);
};

#endif // __JUCE_MOUSEEVENT_JUCEHEADER__
/*** End of inlined file: juce_MouseInputSource.h ***/

class JUCE_API MagnifierComponent : public Component
{
public:
@@ -26204,6 +26287,7 @@ private:
ComponentPeer* peer;
bool deleteContent;
Graphics::ResamplingQuality quality;
MouseInputSource mouseSource;

void paint (Graphics& g);
void mouseDown (const MouseEvent& e);
@@ -26214,6 +26298,7 @@ private:
void mouseExit (const MouseEvent& e);
void mouseWheelMove (const MouseEvent& e, float, float);

void passOnMouseEventToPeer (const MouseEvent& e);
int scaleInt (const int n) const;

MagnifierComponent (const MagnifierComponent&);


+ 1
- 1
src/containers/juce_Variant.h View File

@@ -169,7 +169,7 @@ public:
/** Returns true if this var has the same value as the one supplied. */
bool equals (const var& other) const throw();
private:
enum Type
{


+ 1
- 1
src/core/juce_StandardHeader.h View File

@@ -33,7 +33,7 @@
*/
#define JUCE_MAJOR_VERSION 1
#define JUCE_MINOR_VERSION 51
#define JUCE_BUILDNUMBER 2
#define JUCE_BUILDNUMBER 3
/** Current Juce version number.


+ 9
- 12
src/gui/components/controls/juce_Slider.cpp View File

@@ -1148,35 +1148,32 @@ void Slider::restoreMouseIfHidden()
: ((sliderBeingDragged == 1) ? getMinValue()
: (double) currentValue.getValue());
Point<int> mousePos;
if (style == RotaryHorizontalDrag || style == RotaryVerticalDrag)
{
Point<int> mousePos (Desktop::getMousePosition());
const Point<int> lastMouseDown (Desktop::getLastMouseDownPosition());
mousePos = Desktop::getLastMouseDownPosition();
if (style == RotaryHorizontalDrag)
{
const double posDiff = valueToProportionOfLength (pos) - valueToProportionOfLength (valueOnMouseDown);
mousePos = Point<int> (roundToInt (pixelsForFullDragExtent * posDiff + lastMouseDown.getX()),
lastMouseDown.getY());
mousePos += Point<int> (roundToInt (pixelsForFullDragExtent * posDiff), 0);
}
else
{
const double posDiff = valueToProportionOfLength (valueOnMouseDown) - valueToProportionOfLength (pos);
mousePos = Point<int> (lastMouseDown.getX(),
roundToInt (pixelsForFullDragExtent * posDiff + lastMouseDown.getY()));
mousePos += Point<int> (0, roundToInt (pixelsForFullDragExtent * posDiff));
}
Desktop::setMousePosition (mousePos);
}
else
{
const int pixelPos = (int) getLinearSliderPos (pos);
const Point<int> pos (isHorizontal() ? pixelPos : (getWidth() / 2),
isVertical() ? pixelPos : (getHeight() / 2));
Desktop::setMousePosition (relativePositionToGlobal (pos));
mousePos = relativePositionToGlobal (Point<int> (isHorizontal() ? pixelPos : (getWidth() / 2),
isVertical() ? pixelPos : (getHeight() / 2)));
}
Desktop::setMousePosition (mousePos);
}
}


+ 3
- 12
src/gui/components/controls/juce_TreeView.cpp View File

@@ -83,12 +83,8 @@ public:
else
selectBasedOnModifiers (item, e.mods);
MouseEvent e2 (e);
e2.x -= pos.getX();
e2.y -= pos.getY();
if (e2.x >= 0)
item->itemClicked (e2);
if (e.x >= pos.getX())
item->itemClicked (e.withNewPosition (e.getPosition() - pos.getPosition()));
}
}
@@ -114,12 +110,7 @@ public:
TreeViewItem* const item = findItemAt (e.y, pos);
if (item != 0 && (e.x >= pos.getX() || ! owner->openCloseButtonsVisible))
{
MouseEvent e2 (e);
e2.x -= pos.getX();
e2.y -= pos.getY();
item->itemDoubleClicked (e2);
}
item->itemDoubleClicked (e.withNewPosition (e.getPosition() - pos.getPosition()));
}
}


+ 73
- 122
src/gui/components/juce_Component.cpp View File

@@ -39,8 +39,9 @@ BEGIN_JUCE_NAMESPACE
#include "../../events/juce_MessageManager.h"
#include "../../events/juce_Timer.h"
#include "../../core/juce_Time.h"
#include "../../core/juce_Singleton.h"
#include "../../core/juce_PlatformUtilities.h"
#include "mouse/juce_MouseInputSource.h"
//==============================================================================
Component* Component::componentUnderMouse = 0;
@@ -1084,7 +1085,7 @@ bool Component::contains (const int x, const int y)
const ComponentPeer* const peer = getPeer();
if (peer != 0)
return peer->contains (x, y, true);
return peer->contains (Point<int> (x, y), true);
}
}
@@ -2226,7 +2227,7 @@ void Component::removeMouseListener (MouseListener* const listenerToRemove) thro
}
//==============================================================================
void Component::internalMouseEnter (int x, int y, int64 time)
void Component::internalMouseEnter (MouseInputSource& source, const Point<int>& relativePos, const Time& time)
{
if (isCurrentlyBlockedByAnotherModalComponent())
{
@@ -2256,13 +2257,9 @@ void Component::internalMouseEnter (int x, int y, int64 time)
if (flags.repaintOnMouseActivityFlag)
repaint();
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
Point<int> (x, y),
Time (time),
0, false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos,
time, 0, false);
mouseEnter (me);
@@ -2318,13 +2315,13 @@ void Component::internalMouseEnter (int x, int y, int64 time)
internalUpdateMouseCursor (true);
}
void Component::internalMouseExit (int x, int y, int64 time)
void Component::internalMouseExit (MouseInputSource& source, const Point<int>& relativePos, const Time& time)
{
const ComponentDeletionWatcher deletionChecker (this);
if (flags.draggingFlag)
{
internalMouseUp (ModifierKeys::getCurrentModifiers().getRawFlags(), x, y, time);
internalMouseUp (source, relativePos, time, source.getCurrentModifiers().getRawFlags());
if (deletionChecker.hasBeenDeleted())
return;
@@ -2341,13 +2338,9 @@ void Component::internalMouseExit (int x, int y, int64 time)
if (flags.repaintOnMouseActivityFlag)
repaint();
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
Point<int> (x, y),
Time (time),
0, false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos,
time, 0, false);
mouseExit (me);
if (deletionChecker.hasBeenDeleted())
@@ -2403,23 +2396,33 @@ void Component::internalMouseExit (int x, int y, int64 time)
class InternalDragRepeater : public Timer
{
public:
InternalDragRepeater() {}
~InternalDragRepeater() {}
InternalDragRepeater()
{}
~InternalDragRepeater()
{
clearSingletonInstance();
}
juce_DeclareSingleton_SingleThreaded_Minimal (InternalDragRepeater)
void timerCallback()
{
Component* const c = Component::getComponentUnderMouse();
Desktop& desktop = Desktop::getInstance();
int numMiceDown = 0;
if (c != 0 && c->isMouseButtonDown())
for (int i = desktop.getNumMouseInputSources(); --i >= 0;)
{
const Point<int> mousePos (c->getMouseXYRelative());
// the offsets have been added on, so must be taken off before calling the
// drag.. otherwise they'll be added twice
c->internalMouseDrag (mousePos.getX() - unboundedMouseOffset.getX(),
mousePos.getY() - unboundedMouseOffset.getY(),
Time::currentTimeMillis());
MouseInputSource* const source = desktop.getMouseSource(i);
if (source->isDragging())
{
source->triggerFakeMove();
++numMiceDown;
}
}
if (numMiceDown == 0)
deleteInstance();
}
juce_UseDebuggingNewOperator
@@ -2429,31 +2432,27 @@ private:
InternalDragRepeater& operator= (const InternalDragRepeater&);
};
static InternalDragRepeater* dragRepeater = 0;
juce_ImplementSingleton_SingleThreaded (InternalDragRepeater)
void Component::beginDragAutoRepeat (const int interval)
{
if (interval > 0)
{
if (dragRepeater == 0)
dragRepeater = new InternalDragRepeater();
if (dragRepeater->getTimerInterval() != interval)
dragRepeater->startTimer (interval);
if (InternalDragRepeater::getInstance()->getTimerInterval() != interval)
InternalDragRepeater::getInstance()->startTimer (interval);
}
else
{
deleteAndZero (dragRepeater);
InternalDragRepeater::deleteInstance();
}
}
//==============================================================================
void Component::internalMouseDown (const int x, const int y, const int64 time)
void Component::internalMouseDown (MouseInputSource& source, const Point<int>& relativePos, const Time& time)
{
Desktop& desktop = Desktop::getInstance();
desktop.registerMouseDown (relativePositionToGlobal (Point<int> (x, y)), time, this);
const ComponentDeletionWatcher deletionChecker (this);
if (isCurrentlyBlockedByAnotherModalComponent())
@@ -2468,14 +2467,9 @@ void Component::internalMouseDown (const int x, const int y, const int64 time)
if (isCurrentlyBlockedByAnotherModalComponent())
{
// allow blocked mouse-events to go to global listeners..
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
Point<int> (x, y),
desktop.getLastMouseDownTime(),
desktop.getNumberOfMultipleClicks(),
false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos, time,
source.getNumberOfMultipleClicks(), false);
desktop.resetTimer();
@@ -2521,14 +2515,9 @@ void Component::internalMouseDown (const int x, const int y, const int64 time)
if (flags.repaintOnMouseActivityFlag)
repaint();
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
desktop.getLastMouseDownTime(),
Point<int> (x, y),
desktop.getLastMouseDownTime(),
desktop.getNumberOfMultipleClicks(),
false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos, time,
source.getNumberOfMultipleClicks(), false);
mouseDown (me);
if (deletionChecker.hasBeenDeleted())
@@ -2581,37 +2570,25 @@ void Component::internalMouseDown (const int x, const int y, const int64 time)
}
//==============================================================================
void Component::internalMouseUp (const int oldModifiers, int x, int y, const int64 time)
void Component::internalMouseUp (MouseInputSource& source, const Point<int>& relativePos, const Time& time, const ModifierKeys& oldModifiers)
{
if (isValidComponent() && flags.draggingFlag)
{
Desktop& desktop = Desktop::getInstance();
flags.draggingFlag = false;
deleteAndZero (dragRepeater);
x += unboundedMouseOffset.getX();
y += unboundedMouseOffset.getY();
desktop.registerMouseDrag (relativePositionToGlobal (Point<int> (x, y)));
const ComponentDeletionWatcher deletionChecker (this);
if (flags.repaintOnMouseActivityFlag)
repaint();
const Point<int> mouseDownPos (globalPositionToRelative (Desktop::getLastMouseDownPosition()));
const Time lastMouseDownTime (desktop.getLastMouseDownTime());
const MouseEvent me (Point<int> (x, y),
oldModifiers,
this,
Time (time),
mouseDownPos,
lastMouseDownTime,
desktop.getNumberOfMultipleClicks(),
desktop.mouseMovedSignificantlySincePressed
|| time > lastMouseDownTime.toMilliseconds() + 300);
const MouseEvent me (source, relativePos + unboundedMouseOffset,
oldModifiers, this, time,
globalPositionToRelative (source.getLastMouseDownPosition()),
source.getLastMouseDownTime(),
source.getNumberOfMultipleClicks(),
source.hasMouseMovedSignificantlySincePressed());
mouseUp (me);
@@ -2719,33 +2696,22 @@ void Component::internalMouseUp (const int oldModifiers, int x, int y, const int
enableUnboundedMouseMovement (false);
}
void Component::internalMouseDrag (int x, int y, const int64 time)
void Component::internalMouseDrag (MouseInputSource& source, const Point<int>& relativePos, const Time& time)
{
if (isValidComponent() && flags.draggingFlag)
{
Desktop& desktop = Desktop::getInstance();
flags.mouseOverFlag = reallyContains (x, y, false);
x += unboundedMouseOffset.getX();
y += unboundedMouseOffset.getY();
desktop.registerMouseDrag (relativePositionToGlobal (Point<int> (x, y)));
flags.mouseOverFlag = reallyContains (relativePos.getX(), relativePos.getY(), false);
const ComponentDeletionWatcher deletionChecker (this);
const Point<int> mouseDownPos (globalPositionToRelative (Desktop::getLastMouseDownPosition()));
const Time lastMouseDownTime (desktop.getLastMouseDownTime());
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
mouseDownPos,
lastMouseDownTime,
desktop.getNumberOfMultipleClicks(),
desktop.mouseMovedSignificantlySincePressed
|| time > lastMouseDownTime.toMilliseconds() + 300);
const MouseEvent me (source, relativePos + unboundedMouseOffset,
source.getCurrentModifiers(), this, time,
globalPositionToRelative (source.getLastMouseDownPosition()),
source.getLastMouseDownTime(),
source.getNumberOfMultipleClicks(),
source.hasMouseMovedSignificantlySincePressed());
mouseDrag (me);
@@ -2800,8 +2766,8 @@ void Component::internalMouseDrag (int x, int y, const int64 time)
{
if (isUnboundedMouseModeOn)
{
Rectangle<int> screenArea (getParentMonitorArea().expanded (-2, -2));
Point<int> mousePos (Desktop::getMousePosition());
const Rectangle<int> screenArea (getParentMonitorArea().expanded (-2, -2));
Point<int> mousePos (source.getScreenPosition());
if (! screenArea.contains (mousePos))
{
@@ -2833,7 +2799,7 @@ void Component::internalMouseDrag (int x, int y, const int64 time)
}
}
void Component::internalMouseMove (const int x, const int y, const int64 time)
void Component::internalMouseMove (MouseInputSource& source, const Point<int>& relativePos, const Time& time)
{
const ComponentDeletionWatcher deletionChecker (this);
@@ -2841,13 +2807,9 @@ void Component::internalMouseMove (const int x, const int y, const int64 time)
{
Desktop& desktop = Desktop::getInstance();
const MouseEvent me (Point<int> (x, y),
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
Point<int> (x, y),
Time (time),
0, false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos,
time, 0, false);
if (isCurrentlyBlockedByAnotherModalComponent())
{
@@ -2913,23 +2875,17 @@ void Component::internalMouseMove (const int x, const int y, const int64 time)
}
}
void Component::internalMouseWheel (const int intAmountX, const int intAmountY, const int64 time)
void Component::internalMouseWheel (MouseInputSource& source, const Point<int>& relativePos,
const Time& time, const float amountX, const float amountY)
{
Desktop& desktop = Desktop::getInstance();
const ComponentDeletionWatcher deletionChecker (this);
const float wheelIncrementX = intAmountX * (1.0f / 256.0f);
const float wheelIncrementY = intAmountY * (1.0f / 256.0f);
const float wheelIncrementX = amountX * (1.0f / 256.0f);
const float wheelIncrementY = amountY * (1.0f / 256.0f);
const Point<int> mousePos (getMouseXYRelative());
const MouseEvent me (mousePos,
ModifierKeys::getCurrentModifiers(),
this,
Time (time),
mousePos,
Time (time),
0, false);
const MouseEvent me (source, relativePos, source.getCurrentModifiers(),
this, time, relativePos, time, 0, false);
if (isCurrentlyBlockedByAnotherModalComponent())
{
@@ -2992,17 +2948,12 @@ void Component::internalMouseWheel (const int intAmountX, const int intAmountY,
p = p->parentComponent_;
}
sendFakeMouseMove();
}
}
void Component::sendFakeMouseMove() const
{
ComponentPeer* const peer = getPeer();
if (peer != 0)
peer->sendFakeMouseMove();
Desktop::getInstance().getMainMouseSource().triggerFakeMove();
}
void Component::broughtToFront()


+ 12
- 7
src/gui/components/juce_Component.h View File

@@ -28,6 +28,7 @@
#include "mouse/juce_MouseCursor.h"
#include "mouse/juce_MouseListener.h"
#include "mouse/juce_MouseEvent.h"
#include "juce_ComponentListener.h"
#include "keyboard/juce_KeyListener.h"
#include "keyboard/juce_KeyboardFocusTraverser.h"
@@ -40,6 +41,8 @@
#include "../../containers/juce_VoidArray.h"
#include "../../containers/juce_NamedValueSet.h"
class LookAndFeel;
class MouseInputSource;
class MouseInputSourceInternal;
//==============================================================================
@@ -1921,6 +1924,8 @@ private:
//==============================================================================
friend class ComponentPeer;
friend class InternalDragRepeater;
friend class MouseInputSource;
friend class MouseInputSourceInternal;
static Component* currentlyFocusedComponent;
static Component* componentUnderMouse;
@@ -1973,13 +1978,13 @@ private:
};
//==============================================================================
void internalMouseEnter (int x, int y, const int64 time);
void internalMouseExit (int x, int y, const int64 time);
void internalMouseDown (int x, int y, const int64 time);
void internalMouseUp (const int oldModifiers, int x, int y, const int64 time);
void internalMouseDrag (int x, int y, const int64 time);
void internalMouseMove (int x, int y, const int64 time);
void internalMouseWheel (const int intAmountX, const int intAmountY, const int64 time);
void internalMouseEnter (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseExit (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseDown (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseUp (MouseInputSource& source, const Point<int>& relativePos, const Time& time, const ModifierKeys& oldModifiers);
void internalMouseDrag (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseMove (MouseInputSource& source, const Point<int>& relativePos, const Time& time);
void internalMouseWheel (MouseInputSource& source, const Point<int>& relativePos, const Time& time, const float amountX, const float amountY);
void internalBroughtToFront();
void internalFocusGain (const FocusChangeType cause);
void internalFocusLoss (const FocusChangeType cause);


+ 10
- 58
src/gui/components/juce_Desktop.cpp View File

@@ -30,15 +30,20 @@ BEGIN_JUCE_NAMESPACE
#include "juce_Desktop.h"
#include "juce_ComponentDeletionWatcher.h"
#include "../graphics/geometry/juce_RectangleList.h"
#include "mouse/juce_MouseInputSource.h"
#include "mouse/juce_MouseListener.h"
#include "mouse/juce_MouseEvent.h"
//==============================================================================
Desktop::Desktop() throw()
: mouseClickCounter (0),
mouseMovedSignificantlySincePressed (false),
kioskModeComponent (0)
{
zerostruct (mouseDowns);
const int maxNumMice = 1;
for (int i = maxNumMice; --i >= 0;)
mouseSources.add (new MouseInputSource (i, true));
refreshMonitorSizes();
}
@@ -204,7 +209,7 @@ void Desktop::componentBroughtToFront (Component* const c) throw()
//==============================================================================
const Point<int> Desktop::getLastMouseDownPosition() throw()
{
return getInstance().mouseDowns[0].position;
return getInstance().getMainMouseSource().getLastMouseDownPosition();
}
int Desktop::getMouseButtonClickCounter() throw()
@@ -217,59 +222,6 @@ void Desktop::incrementMouseClickCounter() throw()
++mouseClickCounter;
}
const Time Desktop::getLastMouseDownTime() const throw()
{
return Time (mouseDowns[0].time);
}
void Desktop::registerMouseDown (const Point<int>& position, int64 time, Component* component) throw()
{
for (int i = numElementsInArray (mouseDowns); --i > 0;)
mouseDowns[i] = mouseDowns[i - 1];
mouseDowns[0].position = position;
mouseDowns[0].time = time;
mouseDowns[0].component = component;
mouseMovedSignificantlySincePressed = false;
}
void Desktop::registerMouseDrag (const Point<int>& position) throw()
{
mouseMovedSignificantlySincePressed
= mouseMovedSignificantlySincePressed
|| abs (mouseDowns[0].position.getX() - position.getX()) >= 4
|| abs (mouseDowns[0].position.getY() - position.getY()) >= 4;
}
int Desktop::getNumberOfMultipleClicks() const throw()
{
int numClicks = 0;
if (mouseDowns[0].time != 0)
{
if (! mouseMovedSignificantlySincePressed)
++numClicks;
for (int i = 1; i < numElementsInArray (mouseDowns); ++i)
{
if (mouseDowns[0].time - mouseDowns[i].time
< (int) (MouseEvent::getDoubleClickTimeout() * (1.0 + 0.25 * (i - 1)))
&& abs (mouseDowns[0].position.getX() - mouseDowns[i].position.getX()) < 8
&& abs (mouseDowns[0].position.getY() - mouseDowns[i].position.getY()) < 8
&& mouseDowns[0].component == mouseDowns[i].component)
{
++numClicks;
}
else
{
break;
}
}
}
return numClicks;
}
//==============================================================================
void Desktop::addGlobalMouseListener (MouseListener* const listener) throw()
{
@@ -339,7 +291,7 @@ void Desktop::sendMouseMove()
const Point<int> pos (target->globalPositionToRelative (lastFakeMouseMove));
const Time now (Time::getCurrentTime());
const MouseEvent me (pos, ModifierKeys::getCurrentModifiers(),
const MouseEvent me (getMainMouseSource(), pos, ModifierKeys::getCurrentModifiers(),
target, now, pos, now, 0, false);
for (int i = mouseListeners.size(); --i >= 0;)


+ 13
- 14
src/gui/components/juce_Desktop.h View File

@@ -27,10 +27,16 @@
#define __JUCE_DESKTOP_JUCEHEADER__
#include "juce_Component.h"
#include "../../core/juce_Time.h"
#include "../../utilities/juce_DeletedAtShutdown.h"
#include "../../events/juce_Timer.h"
#include "../../events/juce_AsyncUpdater.h"
#include "../../containers/juce_SortedSet.h"
#include "../../containers/juce_OwnedArray.h"
#include "../graphics/geometry/juce_RectangleList.h"
class MouseInputSource;
class MouseInputSourceInternal;
class MouseListener;
//==============================================================================
@@ -233,6 +239,9 @@ public:
/** True if the OS supports semitransparent windows */
static bool canUseSemiTransparentWindows() throw();
int getNumMouseInputSources() const throw() { return mouseSources.size(); }
MouseInputSource* getMouseSource (int index) const throw() { return mouseSources [index]; }
MouseInputSource& getMainMouseSource() const throw() { return *mouseSources.getUnchecked(0); }
private:
//==============================================================================
@@ -240,6 +249,8 @@ private:
friend class Component;
friend class ComponentPeer;
friend class MouseInputSource;
friend class MouseInputSourceInternal;
SortedSet <void*> mouseListeners, focusListeners;
Array <Component*> desktopComponents;
@@ -250,24 +261,12 @@ private:
Array <Rectangle<int> > monitorCoordsClipped, monitorCoordsUnclipped;
OwnedArray <MouseInputSource> mouseSources;
Point<int> lastFakeMouseMove;
int mouseClickCounter;
bool mouseMovedSignificantlySincePressed;
struct RecentMouseDown
{
Point<int> position;
int64 time;
Component* component;
};
RecentMouseDown mouseDowns[4];
void incrementMouseClickCounter() throw();
void registerMouseDown (const Point<int>& position, int64 time, Component* component) throw();
void registerMouseDrag (const Point<int>& position) throw();
const Time getLastMouseDownTime() const throw();
int getNumberOfMultipleClicks() const throw();
Component* kioskModeComponent;
Rectangle<int> kioskComponentOriginalBounds;


+ 2
- 2
src/gui/components/keyboard/juce_ModifierKeys.cpp View File

@@ -47,11 +47,11 @@ ModifierKeys& ModifierKeys::operator= (const ModifierKeys& other) throw()
return *this;
}
int ModifierKeys::currentModifierFlags = 0;
ModifierKeys ModifierKeys::currentModifiers;
const ModifierKeys ModifierKeys::getCurrentModifiers() throw()
{
return ModifierKeys (currentModifierFlags);
return currentModifiers;
}
int ModifierKeys::getNumMouseButtonsDown() const throw()


+ 15
- 1
src/gui/components/keyboard/juce_ModifierKeys.h View File

@@ -151,11 +151,23 @@ public:
allMouseButtonModifiers = leftButtonModifier | rightButtonModifier | middleButtonModifier,
};
//==============================================================================
/** Returns a copy of only the mouse-button flags */
const ModifierKeys withOnlyMouseButtons() const throw() { return ModifierKeys (flags & allMouseButtonModifiers); }
/** Returns a copy of only the non-mouse flags */
const ModifierKeys withoutMouseButtons() const throw() { return ModifierKeys (flags & ~allMouseButtonModifiers); }
bool operator== (const ModifierKeys& other) const throw() { return flags == other.flags; }
bool operator!= (const ModifierKeys& other) const throw() { return flags != other.flags; }
//==============================================================================
/** Returns the raw flags for direct testing. */
inline int getRawFlags() const throw() { return flags; }
inline const ModifierKeys withoutFlags (int rawFlagsToClear) const throw() { return ModifierKeys (flags & ~rawFlagsToClear); }
inline const ModifierKeys withFlags (int rawFlagsToSet) const throw() { return ModifierKeys (flags | rawFlagsToSet); }
/** Tests a combination of flags and returns true if any of them are set. */
inline bool testFlags (const int flagsToTest) const throw() { return (flags & flagsToTest) != 0; }
@@ -187,9 +199,11 @@ private:
//==============================================================================
int flags;
static int currentModifierFlags;
static ModifierKeys currentModifiers;
friend class ComponentPeer;
friend class MouseInputSource;
friend class MouseInputSourceInternal;
static void updateCurrentModifiers() throw();
};


+ 26
- 22
src/gui/components/mouse/juce_MouseEvent.cpp View File

@@ -32,7 +32,8 @@ BEGIN_JUCE_NAMESPACE
//==============================================================================
MouseEvent::MouseEvent (const Point<int>& position,
MouseEvent::MouseEvent (MouseInputSource& source_,
const Point<int>& position,
const ModifierKeys& mods_,
Component* const originator,
const Time& eventTime_,
@@ -46,6 +47,7 @@ MouseEvent::MouseEvent (const Point<int>& position,
eventComponent (originator),
originalComponent (originator),
eventTime (eventTime_),
source (source_),
mouseDownPos (mouseDownPos_),
mouseDownTime (mouseDownTime_),
numberOfClicks (numberOfClicks_),
@@ -57,6 +59,28 @@ MouseEvent::~MouseEvent() throw()
{
}
//==============================================================================
const MouseEvent MouseEvent::getEventRelativeTo (Component* const otherComponent) const throw()
{
if (otherComponent == 0)
{
jassertfalse
return *this;
}
return MouseEvent (source, eventComponent->relativePositionToOtherComponent (otherComponent, getPosition()),
mods, originalComponent, eventTime,
eventComponent->relativePositionToOtherComponent (otherComponent, mouseDownPos),
mouseDownTime, numberOfClicks, wasMovedSinceMouseDown);
}
const MouseEvent MouseEvent::withNewPosition (const Point<int>& newPosition) const throw()
{
return MouseEvent (source, newPosition, mods, originalComponent,
eventTime, mouseDownPos, mouseDownTime,
numberOfClicks, wasMovedSinceMouseDown);
}
//==============================================================================
bool MouseEvent::mouseWasClicked() const throw()
{
@@ -90,8 +114,7 @@ int MouseEvent::getDistanceFromDragStartY() const throw()
int MouseEvent::getDistanceFromDragStart() const throw()
{
return roundToInt (juce_hypot (getDistanceFromDragStartX(),
getDistanceFromDragStartY()));
return mouseDownPos.getDistanceFrom (getPosition());
}
int MouseEvent::getLengthOfMousePress() const throw()
@@ -138,25 +161,6 @@ const Point<int> MouseEvent::getMouseDownScreenPosition() const
return eventComponent->relativePositionToGlobal (mouseDownPos);
}
//==============================================================================
const MouseEvent MouseEvent::getEventRelativeTo (Component* const otherComponent) const throw()
{
if (otherComponent == 0)
{
jassertfalse
return *this;
}
return MouseEvent (eventComponent->relativePositionToOtherComponent (otherComponent, Point<int> (x, y)),
mods,
originalComponent,
eventTime,
eventComponent->relativePositionToOtherComponent (otherComponent, mouseDownPos),
mouseDownTime,
numberOfClicks,
wasMovedSinceMouseDown);
}
//==============================================================================
static int doubleClickTimeOutMs = 400;


+ 32
- 17
src/gui/components/mouse/juce_MouseEvent.h View File

@@ -27,6 +27,7 @@
#define __JUCE_MOUSEEVENT_JUCEHEADER__
class Component;
class MouseInputSource;
#include "../keyboard/juce_ModifierKeys.h"
#include "../../../core/juce_Time.h"
#include "../../graphics/geometry/juce_Point.h"
@@ -47,6 +48,7 @@ public:
Normally an application will never need to use this.
@param source the source that's invoking the event
@param position the position of the mouse, relative to the component that is passed-in
@param modifiers the key modifiers at the time of the event
@param originator the component that the mouse event applies to
@@ -60,7 +62,8 @@ public:
@param numberOfClicks how many clicks, e.g. a double-click event will be 2, a triple-click will be 3, etc
@param mouseWasDragged whether the mouse has been dragged significantly since the previous mouse-down
*/
MouseEvent (const Point<int>& position,
MouseEvent (MouseInputSource& source,
const Point<int>& position,
const ModifierKeys& modifiers,
Component* const originator,
const Time& eventTime,
@@ -78,14 +81,14 @@ public:
This value is relative to the top-left of the component to which the
event applies (as indicated by the MouseEvent::eventComponent field).
*/
int x;
const int x;
/** The y-position of the mouse when the event occurred.
This value is relative to the top-left of the component to which the
event applies (as indicated by the MouseEvent::eventComponent field).
*/
int y;
const int y;
/** The key modifiers associated with the event.
@@ -95,7 +98,7 @@ public:
When used for mouse-up events, this will indicate the state of the mouse buttons
just before they were released, so that you can tell which button they let go of.
*/
ModifierKeys mods;
const ModifierKeys mods;
/** The component that this event applies to.
@@ -110,7 +113,7 @@ public:
@see originalComponent
*/
Component* eventComponent;
Component* const eventComponent;
/** The component that the event first occurred on.
@@ -119,11 +122,15 @@ public:
@see eventComponent
*/
Component* originalComponent;
Component* const originalComponent;
/** The time that this mouse-event occurred.
*/
Time eventTime;
const Time eventTime;
/** The source device that generated this event.
*/
MouseInputSource& source;
//==============================================================================
/** Returns the x co-ordinate of the last place that a mouse was pressed.
@@ -218,7 +225,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getMouseDownScreenX, Desktop::getMousePosition
@see getScreenPosition
*/
int getScreenX() const;
@@ -226,7 +233,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getMouseDownScreenY, Desktop::getMousePosition
@see getScreenPosition
*/
int getScreenY() const;
@@ -234,7 +241,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getMouseDownScreenY, Desktop::getMousePosition
@see getMouseDownScreenPosition
*/
const Point<int> getScreenPosition() const;
@@ -242,7 +249,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getScreenX, Desktop::getMousePosition
@see getMouseDownScreenPosition
*/
int getMouseDownScreenX() const;
@@ -250,7 +257,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getScreenY, Desktop::getMousePosition
@see getMouseDownScreenPosition
*/
int getMouseDownScreenY() const;
@@ -258,7 +265,7 @@ public:
The co-ordinates are relative to the top-left of the main monitor.
@see getScreenY, Desktop::getMousePosition
@see getScreenPosition
*/
const Point<int> getMouseDownScreenPosition() const;
@@ -270,6 +277,12 @@ public:
*/
const MouseEvent getEventRelativeTo (Component* const otherComponent) const throw();
/** Creates a copy of this event with a different position.
All other members of the event object are the same, but the x and y are
replaced with these new values.
*/
const MouseEvent withNewPosition (const Point<int>& newPosition) const throw();
//==============================================================================
/** Changes the application-wide setting for the double-click time limit.
@@ -294,10 +307,12 @@ public:
juce_UseDebuggingNewOperator
private:
Point<int> mouseDownPos;
Time mouseDownTime;
int numberOfClicks;
bool wasMovedSinceMouseDown;
const Point<int> mouseDownPos;
const Time mouseDownTime;
const int numberOfClicks;
const bool wasMovedSinceMouseDown;
MouseEvent& operator= (const MouseEvent&);
};


+ 1
- 0
src/gui/components/mouse/juce_MouseHoverDetector.cpp View File

@@ -29,6 +29,7 @@ BEGIN_JUCE_NAMESPACE
#include "../juce_Component.h"
#include "juce_MouseHoverDetector.h"
#include "juce_MouseEvent.h"
//==============================================================================


+ 370
- 0
src/gui/components/mouse/juce_MouseInputSource.cpp View File

@@ -0,0 +1,370 @@
/*
==============================================================================
This file is part of the JUCE library - "Jules' Utility Class Extensions"
Copyright 2004-9 by Raw Material Software Ltd.
------------------------------------------------------------------------------
JUCE can be redistributed and/or modified under the terms of the GNU General
Public License (Version 2), as published by the Free Software Foundation.
A copy of the license is included in the JUCE distribution, or can be found
online at www.gnu.org/licenses.
JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
------------------------------------------------------------------------------
To release a closed-source product which uses JUCE, commercial licenses are
available: visit www.rawmaterialsoftware.com/juce for more information.
==============================================================================
*/
#include "../../../core/juce_StandardHeader.h"
BEGIN_JUCE_NAMESPACE
#include "juce_MouseInputSource.h"
#include "juce_MouseEvent.h"
#include "../juce_Component.h"
#include "../juce_ComponentDeletionWatcher.h"
#include "../../../events/juce_AsyncUpdater.h"
//==============================================================================
class MouseInputSourceInternal : public AsyncUpdater
{
public:
MouseInputSourceInternal (MouseInputSource& source_, const int index_, const bool isMouseDevice_)
: source (source_), index (index_), isMouseDevice (isMouseDevice_), lastPeer (0), lastTime (0)
{
zerostruct (mouseDowns);
}
~MouseInputSourceInternal()
{
}
bool isDragging() const throw()
{
return buttonState.isAnyMouseButtonDown();
}
Component* getComponentUnderMouse() const
{
return componentUnderMouse != 0 ? const_cast<Component*> (componentUnderMouse->getComponent()) : 0;
}
const ModifierKeys getCurrentModifiers() const
{
return ModifierKeys::getCurrentModifiers().withoutMouseButtons().withFlags (buttonState.getRawFlags());
}
ComponentPeer* getPeer()
{
if (! ComponentPeer::isValidPeer (lastPeer))
lastPeer = 0;
return lastPeer;
}
Component* findComponentAt (const Point<int>& screenPos)
{
ComponentPeer* const peer = getPeer();
if (peer != 0)
{
Component* const comp = peer->getComponent();
const Point<int> relativePos (comp->globalPositionToRelative (screenPos));
// (the contains() call is needed to test for overlapping desktop windows)
if (comp->contains (relativePos.getX(), relativePos.getY()))
return comp->getComponentAt (relativePos);
}
return 0;
}
void setButtons (const Point<int>& screenPos, const int64 time, const ModifierKeys& newButtonState)
{
if (buttonState != newButtonState)
{
// (ignore secondary clicks when there's already a button down)
if (buttonState.isAnyMouseButtonDown() == newButtonState.isAnyMouseButtonDown())
{
buttonState = newButtonState;
return;
}
if (buttonState.isAnyMouseButtonDown())
{
Component* const current = getComponentUnderMouse();
if (current != 0)
current->internalMouseUp (source, current->globalPositionToRelative (screenPos),
time, getCurrentModifiers());
}
buttonState = newButtonState;
if (buttonState.isAnyMouseButtonDown())
{
Desktop::getInstance().incrementMouseClickCounter();
Component* const current = getComponentUnderMouse();
if (current != 0)
{
registerMouseDown (screenPos, time, current);
current->internalMouseDown (source, current->globalPositionToRelative (screenPos), time);
}
}
}
}
void setComponentUnderMouse (Component* const newComponent, const Point<int>& screenPos, const int64 time)
{
Component* current = getComponentUnderMouse();
if (newComponent != current)
{
ScopedPointer<ComponentDeletionWatcher> newCompWatcher (newComponent != 0 ? new ComponentDeletionWatcher (newComponent) : 0);
const ModifierKeys originalButtonState (buttonState);
if (current != 0)
{
setButtons (screenPos, time, ModifierKeys());
current->internalMouseExit (source, current->globalPositionToRelative (screenPos), time);
buttonState = originalButtonState;
}
componentUnderMouse = newCompWatcher;
current = getComponentUnderMouse();
Component::componentUnderMouse = current;
if (current != 0)
current->internalMouseEnter (source, current->globalPositionToRelative (screenPos), time);
setButtons (screenPos, time, originalButtonState);
}
}
void setPeer (ComponentPeer* const newPeer, const Point<int>& screenPos, const int64 time)
{
ModifierKeys::updateCurrentModifiers();
if (newPeer != lastPeer)
{
setComponentUnderMouse (0, screenPos, time);
lastPeer = newPeer;
setComponentUnderMouse (findComponentAt (screenPos), screenPos, time);
}
}
void setScreenPos (const Point<int>& newScreenPos, const int64 time, const bool forceUpdate)
{
if (! isDragging())
setComponentUnderMouse (findComponentAt (newScreenPos), newScreenPos, time);
if (newScreenPos != lastScreenPos || forceUpdate)
{
cancelPendingUpdate();
lastScreenPos = newScreenPos;
Component* const current = getComponentUnderMouse();
if (current != 0)
{
const Point<int> pos (current->globalPositionToRelative (lastScreenPos));
if (isDragging())
{
registerMouseDrag (newScreenPos);
current->internalMouseDrag (source, pos, time);
}
else
{
current->internalMouseMove (source, pos, time);
}
}
}
}
void handleEvent (ComponentPeer* const newPeer, const Point<int>& positionWithinPeer, const int64 time, const ModifierKeys& newMods)
{
jassert (newPeer != 0);
lastTime = time;
const Point<int> screenPos (newPeer->relativePositionToGlobal (positionWithinPeer));
if (isDragging() && newMods.isAnyMouseButtonDown())
{
setScreenPos (screenPos, time, false);
}
else
{
setPeer (newPeer, screenPos, time);
ComponentPeer* peer = getPeer();
if (peer != 0)
{
setButtons (screenPos, time, newMods);
peer = getPeer();
if (peer != 0)
setScreenPos (peer->relativePositionToGlobal (positionWithinPeer), time, false);
}
}
}
void handleWheel (ComponentPeer* const peer, const Point<int>& positionWithinPeer, int64 time, float x, float y)
{
jassert (peer != 0);
lastTime = time;
const Point<int> screenPos (peer->relativePositionToGlobal (positionWithinPeer));
setPeer (peer, screenPos, time);
setScreenPos (screenPos, time, false);
triggerFakeMove();
if (! isDragging())
{
Component* current = getComponentUnderMouse();
if (current != 0)
current->internalMouseWheel (source, current->globalPositionToRelative (screenPos), time, x, y);
}
}
const Time getLastMouseDownTime() const throw()
{
return Time (mouseDowns[0].time);
}
const Point<int> getLastMouseDownPosition() const throw()
{
return mouseDowns[0].position;
}
int getNumberOfMultipleClicks() const throw()
{
int numClicks = 0;
if (mouseDowns[0].time != 0)
{
if (! mouseMovedSignificantlySincePressed)
++numClicks;
for (int i = 1; i < numElementsInArray (mouseDowns); ++i)
{
if (mouseDowns[0].time - mouseDowns[i].time < (int) (MouseEvent::getDoubleClickTimeout() * (1.0 + 0.25 * (i - 1)))
&& abs (mouseDowns[0].position.getX() - mouseDowns[i].position.getX()) < 8
&& abs (mouseDowns[0].position.getY() - mouseDowns[i].position.getY()) < 8
&& mouseDowns[0].component == mouseDowns[i].component)
{
++numClicks;
}
else
{
break;
}
}
}
return numClicks;
}
bool hasMouseMovedSignificantlySincePressed() const throw()
{
return mouseMovedSignificantlySincePressed
|| lastTime > mouseDowns[0].time + 300;
}
void triggerFakeMove()
{
triggerAsyncUpdate();
}
void handleAsyncUpdate()
{
setScreenPos (Desktop::getMousePosition(), Time::currentTimeMillis(), true);
}
int index;
bool isMouseDevice;
Point<int> lastScreenPos;
ModifierKeys buttonState;
private:
MouseInputSource& source;
ScopedPointer<ComponentDeletionWatcher> componentUnderMouse;
ComponentPeer* lastPeer;
struct RecentMouseDown
{
Point<int> position;
int64 time;
Component* component;
};
RecentMouseDown mouseDowns[4];
bool mouseMovedSignificantlySincePressed;
int64 lastTime;
void registerMouseDown (const Point<int>& screenPos, const int64 time, Component* const component) throw()
{
for (int i = numElementsInArray (mouseDowns); --i > 0;)
mouseDowns[i] = mouseDowns[i - 1];
mouseDowns[0].position = screenPos;
mouseDowns[0].time = time;
mouseDowns[0].component = component;
mouseMovedSignificantlySincePressed = false;
}
void registerMouseDrag (const Point<int>& screenPos) throw()
{
mouseMovedSignificantlySincePressed = mouseMovedSignificantlySincePressed
|| mouseDowns[0].position.getDistanceFrom (screenPos) >= 4;
}
};
//==============================================================================
MouseInputSource::MouseInputSource (const int index, const bool isMouseDevice)
{
pimpl = new MouseInputSourceInternal (*this, index, isMouseDevice);
}
MouseInputSource::~MouseInputSource()
{
}
bool MouseInputSource::isMouse() const { return pimpl->isMouseDevice; }
bool MouseInputSource::isTouch() const { return ! pimpl->isMouseDevice; }
bool MouseInputSource::canHover() const { return pimpl->isMouseDevice; }
bool MouseInputSource::hasMouseWheel() const { return pimpl->isMouseDevice; }
int MouseInputSource::getIndex() const { return pimpl->index; }
bool MouseInputSource::isDragging() const { return pimpl->isDragging(); }
const Point<int> MouseInputSource::getScreenPosition() const { return pimpl->lastScreenPos; }
const ModifierKeys MouseInputSource::getCurrentModifiers() const { return pimpl->getCurrentModifiers(); }
Component* MouseInputSource::getComponentUnderMouse() const { return pimpl->getComponentUnderMouse(); }
void MouseInputSource::triggerFakeMove() const { pimpl->triggerFakeMove(); }
int MouseInputSource::getNumberOfMultipleClicks() const throw() { return pimpl->getNumberOfMultipleClicks(); }
const Time MouseInputSource::getLastMouseDownTime() const throw() { return pimpl->getLastMouseDownTime(); }
const Point<int> MouseInputSource::getLastMouseDownPosition() const throw() { return pimpl->getLastMouseDownPosition(); }
bool MouseInputSource::hasMouseMovedSignificantlySincePressed() const throw() { return pimpl->hasMouseMovedSignificantlySincePressed(); }
void MouseInputSource::handleEvent (ComponentPeer* peer, const Point<int>& positionWithinPeer, const int64 time, const ModifierKeys& mods)
{
pimpl->handleEvent (peer, positionWithinPeer, time, mods.withOnlyMouseButtons());
}
void MouseInputSource::handleWheel (ComponentPeer* const peer, const Point<int>& positionWithinPeer, const int64 time, const float x, const float y)
{
pimpl->handleWheel (peer, positionWithinPeer, time, x, y);
}
END_JUCE_NAMESPACE

+ 85
- 0
src/gui/components/mouse/juce_MouseInputSource.h View File

@@ -0,0 +1,85 @@
/*
==============================================================================
This file is part of the JUCE library - "Jules' Utility Class Extensions"
Copyright 2004-9 by Raw Material Software Ltd.
------------------------------------------------------------------------------
JUCE can be redistributed and/or modified under the terms of the GNU General
Public License (Version 2), as published by the Free Software Foundation.
A copy of the license is included in the JUCE distribution, or can be found
online at www.gnu.org/licenses.
JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
------------------------------------------------------------------------------
To release a closed-source product which uses JUCE, commercial licenses are
available: visit www.rawmaterialsoftware.com/juce for more information.
==============================================================================
*/
#ifndef __JUCE_MOUSEEVENT_JUCEHEADER__x
#define __JUCE_MOUSEEVENT_JUCEHEADER__x
class Component;
class ComponentPeer;
class MouseInputSourceInternal;
#include "../keyboard/juce_ModifierKeys.h"
#include "../../../core/juce_Time.h"
#include "../../../containers/juce_ScopedPointer.h"
#include "../../graphics/geometry/juce_Point.h"
#include "../juce_Desktop.h"
//==============================================================================
/**
*/
class JUCE_API MouseInputSource
{
public:
//==============================================================================
MouseInputSource (int index, bool isMouseDevice);
~MouseInputSource();
//==============================================================================
bool isMouse() const;
bool isTouch() const;
bool canHover() const;
bool hasMouseWheel() const;
int getIndex() const;
bool isDragging() const;
const Point<int> getScreenPosition() const;
const ModifierKeys getCurrentModifiers() const;
Component* getComponentUnderMouse() const;
void triggerFakeMove() const;
int getNumberOfMultipleClicks() const throw();
const Time getLastMouseDownTime() const throw();
const Point<int> getLastMouseDownPosition() const throw();
bool hasMouseMovedSignificantlySincePressed() const throw();
//==============================================================================
juce_UseDebuggingNewOperator
void handleEvent (ComponentPeer* peer, const Point<int>& positionWithinPeer, int64 time, const ModifierKeys& mods);
void handleWheel (ComponentPeer* peer, const Point<int>& positionWithinPeer, int64 time, float x, float y);
private:
friend class MouseInputSourceInternal;
ScopedPointer<MouseInputSourceInternal> pimpl;
friend class Desktop;
friend class ComponentPeer;
MouseInputSource (const MouseInputSource&);
MouseInputSource& operator= (const MouseInputSource&);
};
#endif // __JUCE_MOUSEEVENT_JUCEHEADER__

+ 1
- 2
src/gui/components/mouse/juce_MouseListener.h View File

@@ -26,8 +26,7 @@
#ifndef __JUCE_MOUSELISTENER_JUCEHEADER__
#define __JUCE_MOUSELISTENER_JUCEHEADER__
#include "juce_MouseEvent.h"
class MouseEvent;
//==============================================================================
/**


+ 1
- 0
src/gui/components/special/juce_ActiveXControlComponent.h View File

@@ -116,6 +116,7 @@ public:
juce_UseDebuggingNewOperator
private:
class ActiveXControlData;
friend class ActiveXControlData;
void* control;
bool mouseEventsAllowed;


+ 20
- 19
src/gui/components/special/juce_MagnifierComponent.cpp View File

@@ -110,10 +110,10 @@ public:
roundToInt (p.getY() / zoom));
}
bool contains (int x, int y, bool) const
bool contains (const Point<int>& position, bool) const
{
return ((unsigned int) x) < (unsigned int) magnifierComp->getWidth()
&& ((unsigned int) y) < (unsigned int) magnifierComp->getHeight();
return ((unsigned int) position.getX()) < (unsigned int) magnifierComp->getWidth()
&& ((unsigned int) position.getY()) < (unsigned int) magnifierComp->getHeight();
}
void repaint (int x, int y, int w, int h)
@@ -193,7 +193,8 @@ MagnifierComponent::MagnifierComponent (Component* const content_,
scaleFactor (0.0),
peer (0),
deleteContent (deleteContentCompWhenNoLongerNeeded),
quality (Graphics::lowResamplingQuality)
quality (Graphics::lowResamplingQuality),
mouseSource (0, true)
{
holderComp = new PeerHolderComp (this);
setScaleFactor (1.0);
@@ -285,48 +286,48 @@ void MagnifierComponent::childBoundsChanged (Component* c)
roundToInt (c->getHeight() * scaleFactor));
}
void MagnifierComponent::mouseDown (const MouseEvent& e)
void MagnifierComponent::passOnMouseEventToPeer (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseDown (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
mouseSource.handleEvent (peer, Point<int> (scaleInt (e.x), scaleInt (e.y)),
e.eventTime.toMilliseconds(), ModifierKeys::getCurrentModifiers());
}
void MagnifierComponent::mouseDown (const MouseEvent& e)
{
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseUp (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseUp (e.mods.getRawFlags(), Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseDrag (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseDrag (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseMove (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseMove (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseEnter (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseEnter (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseExit (const MouseEvent& e)
{
if (peer != 0)
peer->handleMouseExit (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds());
passOnMouseEventToPeer (e);
}
void MagnifierComponent::mouseWheelMove (const MouseEvent& e, float ix, float iy)
{
if (peer != 0)
peer->handleMouseWheel (roundToInt (ix * 256.0f),
roundToInt (iy * 256.0f),
e.eventTime.toMilliseconds());
peer->handleMouseWheel (Point<int> (scaleInt (e.x), scaleInt (e.y)), e.eventTime.toMilliseconds(),
ix * 256.0f, iy * 256.0f);
else
Component::mouseWheelMove (e, ix, iy);
}


+ 3
- 0
src/gui/components/special/juce_MagnifierComponent.h View File

@@ -27,6 +27,7 @@
#define __JUCE_MAGNIFIERCOMPONENT_JUCEHEADER__
#include "../juce_Component.h"
#include "../mouse/juce_MouseInputSource.h"
//==============================================================================
@@ -100,6 +101,7 @@ private:
ComponentPeer* peer;
bool deleteContent;
Graphics::ResamplingQuality quality;
MouseInputSource mouseSource;
//==============================================================================
void paint (Graphics& g);
@@ -111,6 +113,7 @@ private:
void mouseExit (const MouseEvent& e);
void mouseWheelMove (const MouseEvent& e, float, float);
void passOnMouseEventToPeer (const MouseEvent& e);
int scaleInt (const int n) const;
MagnifierComponent (const MagnifierComponent&);


+ 5
- 194
src/gui/components/windows/juce_ComponentPeer.cpp View File

@@ -36,12 +36,12 @@ BEGIN_JUCE_NAMESPACE
#include "../../../core/juce_Random.h"
#include "../layout/juce_ComponentBoundsConstrainer.h"
#include "../mouse/juce_FileDragAndDropTarget.h"
#include "../mouse/juce_MouseInputSource.h"
//#define JUCE_ENABLE_REPAINT_DEBUGGING 1
//==============================================================================
static const int fakeMouseMoveMessage = 0x7fff00ff;
static VoidArray heavyweightPeers;
@@ -102,203 +102,14 @@ void ComponentPeer::updateCurrentModifiers() throw()
}
//==============================================================================
void ComponentPeer::handleMouseEnter (const Point<int>& position, const int64 time)
void ComponentPeer::handleMouseEvent (const Point<int>& positionWithinPeer, const ModifierKeys& newMods, const int64 time)
{
jassert (component->isValidComponent());
updateCurrentModifiers();
Component* c = component->getComponentAt (position);
const ComponentDeletionWatcher deletionChecker (component);
if (c != Component::componentUnderMouse && Component::componentUnderMouse != 0)
{
jassert (Component::componentUnderMouse->isValidComponent());
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseExit (relPos.getX(), relPos.getY(), time);
Component::componentUnderMouse = 0;
if (deletionChecker.hasBeenDeleted())
return;
c = component->getComponentAt (position);
}
Component::componentUnderMouse = c;
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseEnter (relPos.getX(), relPos.getY(), time);
}
Desktop::getInstance().getMainMouseSource().handleEvent (this, positionWithinPeer, time, newMods);
}
void ComponentPeer::handleMouseMove (const Point<int>& position, const int64 time)
void ComponentPeer::handleMouseWheel (const Point<int>& positionWithinPeer, const int64 time, float x, float y)
{
jassert (component->isValidComponent());
updateCurrentModifiers();
fakeMouseMessageSent = false;
const ComponentDeletionWatcher deletionChecker (component);
Component* c = component->getComponentAt (position);
if (c != Component::componentUnderMouse)
{
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseExit (relPos.getX(), relPos.getY(), time);
Component::componentUnderMouse = 0;
if (deletionChecker.hasBeenDeleted())
return; // if this window has just been deleted..
c = component->getComponentAt (position);
}
Component::componentUnderMouse = c;
if (c != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (c, position));
c->internalMouseEnter (relPos.getX(), relPos.getY(), time);
if (deletionChecker.hasBeenDeleted())
return; // if this window has just been deleted..
}
}
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseMove (relPos.getX(), relPos.getY(), time);
}
}
void ComponentPeer::handleMouseDown (const Point<int>& position, const int64 time)
{
Desktop::getInstance().incrementMouseClickCounter();
updateCurrentModifiers();
if (ModifierKeys::getCurrentModifiers().getNumMouseButtonsDown() == 1)
{
Component::componentUnderMouse = component->getComponentAt (position);
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseDown (relPos.getX(), relPos.getY(), time);
}
}
}
void ComponentPeer::handleMouseDrag (const Point<int>& position, const int64 time)
{
updateCurrentModifiers();
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseDrag (relPos.getX(), relPos.getY(), time);
}
}
void ComponentPeer::handleMouseUp (const int oldModifiers, const Point<int>& position, const int64 time)
{
updateCurrentModifiers();
if (ModifierKeys (oldModifiers).getNumMouseButtonsDown() == 1)
{
const ComponentDeletionWatcher deletionChecker (component);
Component* c = component->getComponentAt (position);
if (c != Component::componentUnderMouse)
{
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseUp (oldModifiers, relPos.getX(), relPos.getY(), time);
if (Component::componentUnderMouse != 0)
Component::componentUnderMouse->internalMouseExit (relPos.getX(), relPos.getY(), time);
if (deletionChecker.hasBeenDeleted())
return;
c = component->getComponentAt (position);
}
Component::componentUnderMouse = c;
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseEnter (relPos.getX(), relPos.getY(), time);
}
}
else
{
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseUp (oldModifiers, relPos.getX(), relPos.getY(), time);
}
}
}
}
void ComponentPeer::handleMouseExit (const Point<int>& position, const int64 time)
{
jassert (component->isValidComponent());
updateCurrentModifiers();
if (Component::componentUnderMouse != 0)
{
const Point<int> relPos (component->relativePositionToOtherComponent (Component::componentUnderMouse, position));
Component::componentUnderMouse->internalMouseExit (relPos.getX(), relPos.getY(), time);
Component::componentUnderMouse = 0;
}
}
void ComponentPeer::handleMouseWheel (const int amountX, const int amountY, const int64 time)
{
updateCurrentModifiers();
if (Component::componentUnderMouse != 0)
Component::componentUnderMouse->internalMouseWheel (amountX, amountY, time);
}
void ComponentPeer::sendFakeMouseMove() throw()
{
if ((! fakeMouseMessageSent)
&& component->flags.hasHeavyweightPeerFlag
&& ! ModifierKeys::getCurrentModifiers().isAnyMouseButtonDown())
{
if (! isMinimised())
component->bounds_ = getBounds();
const Point<int> pos (component->getMouseXYRelative());
if (((unsigned int) pos.getX()) < (unsigned int) component->getWidth()
&& ((unsigned int) pos.getY()) < (unsigned int) component->getHeight()
&& contains (pos.getX(), pos.getY(), false))
{
postMessage (new Message (fakeMouseMoveMessage, pos.getX(), pos.getY(), 0));
}
fakeMouseMessageSent = true;
}
}
void ComponentPeer::handleMessage (const Message& message)
{
if (message.intParameter1 == fakeMouseMoveMessage)
{
if (! ModifierKeys::getCurrentModifiers().isAnyMouseButtonDown())
handleMouseMove (Point<int> (message.intParameter2, message.intParameter3),
Time::currentTimeMillis());
}
Desktop::getInstance().getMainMouseSource().handleWheel (this, positionWithinPeer, time, x, y);
}
//==============================================================================


+ 4
- 15
src/gui/components/windows/juce_ComponentPeer.h View File

@@ -48,7 +48,7 @@ class ComponentDeletionWatcher;
@see Component::createNewPeer
*/
class JUCE_API ComponentPeer : public MessageListener
class JUCE_API ComponentPeer
{
public:
//==============================================================================
@@ -197,7 +197,7 @@ public:
is false, then this returns false if the point is actually inside a child of this
window.
*/
virtual bool contains (int x, int y, bool trueIfInAChildWindow) const = 0;
virtual bool contains (const Point<int>& position, bool trueIfInAChildWindow) const = 0;
/** Returns the size of the window frame that's around this window.
@@ -295,16 +295,8 @@ public:
virtual void performAnyPendingRepaintsNow() = 0;
//==============================================================================
void handleMouseEnter (const Point<int>& position, const int64 time);
void handleMouseMove (const Point<int>& position, const int64 time);
void handleMouseDown (const Point<int>& position, const int64 time);
void handleMouseDrag (const Point<int>& position, const int64 time);
void handleMouseUp (const int oldModifiers, const Point<int>& position, const int64 time);
void handleMouseExit (const Point<int>& position, const int64 time);
void handleMouseWheel (const int amountX, const int amountY, const int64 time);
/** Causes a mouse-move callback to be made asynchronously. */
void sendFakeMouseMove() throw();
void handleMouseEvent (const Point<int>& positionWithinPeer, const ModifierKeys& newMods, const int64 time);
void handleMouseWheel (const Point<int>& positionWithinPeer, const int64 time, float x, float y);
void handleUserClosingWindow();
@@ -373,9 +365,6 @@ protected:
static void updateCurrentModifiers() throw();
/** @internal */
void handleMessage (const Message& message);
private:
//==============================================================================
Component* lastFocusedComponent;


+ 3
- 3
src/gui/graphics/contexts/juce_LowLevelGraphicsSoftwareRenderer.cpp View File

@@ -230,7 +230,7 @@ public:
start = roundToInt ((y - yTerm) * grad);
}
forcedinline const PixelARGB getPixel (const int x) const throw()
inline const PixelARGB getPixel (const int x) const throw()
{
return vertical ? linePix
: lookupTable [jlimit (0, numEntries, (x * scale - start) >> (int) numScaleBits)];
@@ -274,7 +274,7 @@ public:
dy *= dy;
}
forcedinline const PixelARGB getPixel (const int px) const throw()
inline const PixelARGB getPixel (const int px) const throw()
{
double x = px - gx1;
x *= x;
@@ -312,7 +312,7 @@ public:
lineYM11 = inverseTransform.mat11 * y + inverseTransform.mat12 - gy1;
}
forcedinline const PixelARGB getPixel (const int px) const throw()
inline const PixelARGB getPixel (const int px) const throw()
{
double x = px;
const double y = tM10 * x + lineYM11;


+ 4
- 4
src/io/streams/juce_OutputStream.cpp View File

@@ -254,23 +254,23 @@ int OutputStream::writeFromInputStream (InputStream& source, int numBytesToWrite
}
//==============================================================================
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const int number)
OutputStream& operator<< (OutputStream& stream, const int number)
{
return stream << String (number);
}
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const double number)
OutputStream& operator<< (OutputStream& stream, const double number)
{
return stream << String (number);
}
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char character)
OutputStream& operator<< (OutputStream& stream, const char character)
{
stream.writeByte (character);
return stream;
}
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char* const text)
OutputStream& operator<< (OutputStream& stream, const char* const text)
{
stream.write (text, (int) strlen (text));
return stream;


+ 4
- 4
src/io/streams/juce_OutputStream.h View File

@@ -207,16 +207,16 @@ public:
//==============================================================================
/** Writes a number to a stream as 8-bit characters in the default system encoding. */
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const int number);
OutputStream& operator<< (OutputStream& stream, const int number);
/** Writes a number to a stream as 8-bit characters in the default system encoding. */
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const double number);
OutputStream& operator<< (OutputStream& stream, const double number);
/** Writes a character to a stream. */
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char character);
OutputStream& operator<< (OutputStream& stream, const char character);
/** Writes a null-terminated text string to a stream. */
OutputStream& JUCE_PUBLIC_FUNCTION operator<< (OutputStream& stream, const char* const text);
OutputStream& operator<< (OutputStream& stream, const char* const text);


+ 1
- 0
src/native/juce_mac_NativeCode.mm View File

@@ -59,6 +59,7 @@ BEGIN_JUCE_NAMESPACE
#include "../gui/components/special/juce_OpenGLComponent.h"
#include "../gui/components/special/juce_QuickTimeMovieComponent.h"
#include "../gui/components/mouse/juce_DragAndDropContainer.h"
#include "../gui/components/mouse/juce_MouseEvent.h"
#include "../gui/components/keyboard/juce_KeyPressMappingSet.h"
#include "../gui/components/special/juce_NSViewComponent.h"
#include "../gui/components/layout/juce_ComponentMovementWatcher.h"


+ 179
- 219
src/native/linux/juce_linux_Windowing.cpp View File

@@ -120,33 +120,6 @@ enum MouseButtons
WheelDown = 5
};
static const Point<int> getMousePos (int& mouseMods) throw()
{
Window root, child;
int x, y, winx, winy;
unsigned int mask;
mouseMods = 0;
ScopedXLock xlock;
if (XQueryPointer (display,
RootWindow (display, DefaultScreen (display)),
&root, &child,
&x, &y, &winx, &winy, &mask) == False)
{
// Pointer not on the default screen
x = y = -1;
}
else
{
if ((mask & Button1Mask) != 0) mouseMods |= ModifierKeys::leftButtonModifier;
if ((mask & Button2Mask) != 0) mouseMods |= ModifierKeys::middleButtonModifier;
if ((mask & Button3Mask) != 0) mouseMods |= ModifierKeys::rightButtonModifier;
}
return Point<int> (x, y);
}
//==============================================================================
static int AltMask = 0;
static int NumLockMask = 0;
@@ -200,124 +173,6 @@ bool KeyPress::isKeyCurrentlyDown (const int keyCode) throw()
return keyDown (XKeysymToKeycode (display, keysym));
}
//==============================================================================
// Alt and Num lock are not defined by standard X
// modifier constants: check what they're mapped to
static void getModifierMapping() throw()
{
ScopedXLock xlock;
const int altLeftCode = XKeysymToKeycode (display, XK_Alt_L);
const int numLockCode = XKeysymToKeycode (display, XK_Num_Lock);
AltMask = 0;
NumLockMask = 0;
XModifierKeymap* mapping = XGetModifierMapping (display);
if (mapping)
{
for (int i = 0; i < 8; i++)
{
if (mapping->modifiermap [i << 1] == altLeftCode)
AltMask = 1 << i;
else if (mapping->modifiermap [i << 1] == numLockCode)
NumLockMask = 1 << i;
}
XFreeModifiermap (mapping);
}
}
static int currentModifiers = 0;
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifierFlags = currentModifiers;
}
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
int mouseMods;
getMousePos (mouseMods);
currentModifiers &= ~ModifierKeys::allMouseButtonModifiers;
currentModifiers |= mouseMods;
return ModifierKeys (currentModifiers);
}
static void updateKeyModifiers (const int status) throw()
{
currentModifiers &= ~(ModifierKeys::shiftModifier
| ModifierKeys::ctrlModifier
| ModifierKeys::altModifier);
if (status & ShiftMask)
currentModifiers |= ModifierKeys::shiftModifier;
if (status & ControlMask)
currentModifiers |= ModifierKeys::ctrlModifier;
if (status & AltMask)
currentModifiers |= ModifierKeys::altModifier;
numLock = ((status & NumLockMask) != 0);
capsLock = ((status & LockMask) != 0);
}
static bool updateKeyModifiersFromSym (KeySym sym, const bool press) throw()
{
int modifier = 0;
bool isModifier = true;
switch (sym)
{
case XK_Shift_L:
case XK_Shift_R:
modifier = ModifierKeys::shiftModifier;
break;
case XK_Control_L:
case XK_Control_R:
modifier = ModifierKeys::ctrlModifier;
break;
case XK_Alt_L:
case XK_Alt_R:
modifier = ModifierKeys::altModifier;
break;
case XK_Num_Lock:
if (press)
numLock = ! numLock;
break;
case XK_Caps_Lock:
if (press)
capsLock = ! capsLock;
break;
case XK_Scroll_Lock:
break;
default:
isModifier = false;
break;
}
if (modifier != 0)
{
if (press)
currentModifiers |= modifier;
else
currentModifiers &= ~modifier;
}
return isModifier;
}
//==============================================================================
#if JUCE_USE_XSHM
static bool isShmAvailable() throw()
@@ -605,7 +460,6 @@ public:
wh (0),
taskbarImage (0),
fullScreen (false),
entered (false),
mapped (false)
{
// it's dangerous to create a window on a thread other than the message thread..
@@ -644,7 +498,7 @@ public:
ScopedXLock xlock;
if (! XFindContext (display, (XID) windowHandle, improbableNumber, &peer))
{
if (peer != 0 && ! ((LinuxComponentPeer*) peer)->isValidMessageListener())
if (peer != 0 && ! ComponentPeer::isValidPeer ((LinuxComponentPeer*) peer))
peer = 0;
}
@@ -854,9 +708,10 @@ public:
return result;
}
bool contains (int x, int y, bool trueIfInAChildWindow) const
bool contains (const Point<int>& position, bool trueIfInAChildWindow) const
{
jassert (x >= 0 && y >= 0 && x < ww && y < wh); // should only be called for points that are actually inside the bounds
int x = position.getX();
int y = position.getY();
if (((unsigned int) x) >= (unsigned int) ww
|| ((unsigned int) y) >= (unsigned int) wh)
@@ -1166,10 +1021,9 @@ public:
int keyCode = (int) unicodeChar;
if (keyCode < 0x20)
keyCode = XKeycodeToKeysym (display, keyEvent->keycode,
(currentModifiers & ModifierKeys::shiftModifier) != 0 ? 1 : 0);
keyCode = XKeycodeToKeysym (display, keyEvent->keycode, currentModifiers.isShiftDown() ? 1 : 0);
const int oldMods = currentModifiers;
const ModifierKeys oldMods (currentModifiers);
bool keyPressed = false;
const bool keyDownChange = (sym != NoSymbol) && ! updateKeyModifiersFromSym (sym, true);
@@ -1267,7 +1121,7 @@ public:
ScopedXLock xlock;
KeySym sym = XKeycodeToKeysym (display, keyEvent->keycode, 0);
const int oldMods = currentModifiers;
const ModifierKeys oldMods (currentModifiers);
const bool keyDownChange = (sym != NoSymbol) && ! updateKeyModifiersFromSym (sym, false);
if (oldMods != currentModifiers)
@@ -1282,48 +1136,37 @@ public:
case ButtonPress:
{
const XButtonPressedEvent* const buttonPressEvent = (const XButtonPressedEvent*) &event->xbutton;
updateKeyModifiers (buttonPressEvent->state);
bool buttonMsg = false;
bool wheelUpMsg = false;
bool wheelDownMsg = false;
const int map = pointerMap [buttonPressEvent->button - Button1];
if (map == WheelUp || map == WheelDown)
{
handleMouseWheel (Point<int> (buttonPressEvent->x, buttonPressEvent->y),
getEventTime (buttonPressEvent->time), 0, map == WheelDown ? -84.0f : 84.0f);
}
if (map == LeftButton)
{
currentModifiers |= ModifierKeys::leftButtonModifier;
currentModifiers = currentModifiers.withFlags (ModifierKeys::leftButtonModifier);
buttonMsg = true;
}
else if (map == RightButton)
{
currentModifiers |= ModifierKeys::rightButtonModifier;
currentModifiers = currentModifiers.withFlags (ModifierKeys::rightButtonModifier);
buttonMsg = true;
}
else if (map == MiddleButton)
{
currentModifiers |= ModifierKeys::middleButtonModifier;
currentModifiers = currentModifiers.withFlags (ModifierKeys::middleButtonModifier);
buttonMsg = true;
}
else if (map == WheelUp)
{
wheelUpMsg = true;
}
else if (map == WheelDown)
{
wheelDownMsg = true;
}
updateKeyModifiers (buttonPressEvent->state);
if (buttonMsg)
{
toFront (true);
handleMouseDown (Point<int> (buttonPressEvent->x, buttonPressEvent->y),
getEventTime (buttonPressEvent->time));
}
else if (wheelUpMsg || wheelDownMsg)
{
handleMouseWheel (0, wheelDownMsg ? -84 : 84,
handleMouseEvent (Point<int> (buttonPressEvent->x, buttonPressEvent->y), currentModifiers,
getEventTime (buttonPressEvent->time));
}
@@ -1334,22 +1177,19 @@ public:
case ButtonRelease:
{
const XButtonReleasedEvent* const buttonRelEvent = (const XButtonReleasedEvent*) &event->xbutton;
updateKeyModifiers (buttonRelEvent->state);
const int oldModifiers = currentModifiers;
const int map = pointerMap [buttonRelEvent->button - Button1];
if (map == LeftButton)
currentModifiers &= ~ModifierKeys::leftButtonModifier;
currentModifiers = currentModifiers.withoutFlags (ModifierKeys::leftButtonModifier);
else if (map == RightButton)
currentModifiers &= ~ModifierKeys::rightButtonModifier;
currentModifiers = currentModifiers.withoutFlags (ModifierKeys::rightButtonModifier);
else if (map == MiddleButton)
currentModifiers &= ~ModifierKeys::middleButtonModifier;
updateKeyModifiers (buttonRelEvent->state);
currentModifiers = currentModifiers.withoutFlags (ModifierKeys::middleButtonModifier);
handleMouseUp (oldModifiers,
Point<int> (buttonRelEvent->x, buttonRelEvent->y),
getEventTime (buttonRelEvent->time));
handleMouseEvent (Point<int> (buttonRelEvent->x, buttonRelEvent->y), currentModifiers,
getEventTime (buttonRelEvent->time));
clearLastMousePos();
break;
@@ -1358,10 +1198,9 @@ public:
case MotionNotify:
{
const XPointerMovedEvent* const movedEvent = (const XPointerMovedEvent*) &event->xmotion;
updateKeyModifiers (movedEvent->state);
Point<int> mousePos (Desktop::getMousePosition());
const Point<int> mousePos (Desktop::getMousePosition());
if (lastMousePos != mousePos)
{
@@ -1370,37 +1209,28 @@ public:
if (parentWindow != 0 && (styleFlags & windowHasTitleBar) == 0)
{
Window wRoot = 0, wParent = 0;
Window* wChild = 0;
unsigned int numChildren;
{
ScopedXLock xlock;
unsigned int numChildren;
Window* wChild = 0;
XQueryTree (display, windowH, &wRoot, &wParent, &wChild, &numChildren);
}
if (wParent != 0
&& wParent != windowH
&& wParent != wRoot)
&& wParent != windowH
&& wParent != wRoot)
{
parentWindow = wParent;
updateBounds();
mousePos -= getScreenPosition();
}
else
{
parentWindow = 0;
mousePos -= getScreenPosition();
}
}
else
{
mousePos -= getScreenPosition();
}
if ((currentModifiers & ModifierKeys::allMouseButtonModifiers) == 0)
handleMouseMove (mousePos, getEventTime (movedEvent->time));
else
handleMouseDrag (mousePos, getEventTime (movedEvent->time));
handleMouseEvent (mousePos - getScreenPosition(), currentModifiers, getEventTime (movedEvent->time));
}
break;
@@ -1411,14 +1241,10 @@ public:
clearLastMousePos();
const XEnterWindowEvent* const enterEvent = (const XEnterWindowEvent*) &event->xcrossing;
if ((currentModifiers & ModifierKeys::allMouseButtonModifiers) == 0
&& ! entered)
if (! currentModifiers.isAnyMouseButtonDown())
{
updateKeyModifiers (enterEvent->state);
handleMouseEnter (Point<int> (enterEvent->x, enterEvent->y), getEventTime (enterEvent->time));
entered = true;
handleMouseEvent (Point<int> (enterEvent->x, enterEvent->y), currentModifiers, getEventTime (enterEvent->time));
}
break;
@@ -1431,15 +1257,11 @@ public:
// Suppress the normal leave if we've got a pointer grab, or if
// it's a bogus one caused by clicking a mouse button when running
// in a Window manager
if (((currentModifiers & ModifierKeys::allMouseButtonModifiers) == 0
&& leaveEvent->mode == NotifyNormal)
|| leaveEvent->mode == NotifyUngrab)
if (((! currentModifiers.isAnyMouseButtonDown()) && leaveEvent->mode == NotifyNormal)
|| leaveEvent->mode == NotifyUngrab)
{
updateKeyModifiers (leaveEvent->state);
handleMouseExit (Point<int> (leaveEvent->x, leaveEvent->y), getEventTime (leaveEvent->time));
entered = false;
handleMouseEvent (Point<int> (leaveEvent->x, leaveEvent->y), currentModifiers, getEventTime (leaveEvent->time));
}
break;
@@ -1570,7 +1392,7 @@ public:
// Deal with modifier/keyboard mapping
ScopedXLock xlock;
XRefreshKeyboardMapping (mappingEvent);
getModifierMapping();
updateModifierMappings();
}
break;
@@ -1726,6 +1548,8 @@ public:
bool dontRepaint;
static ModifierKeys currentModifiers;
private:
//==============================================================================
class LinuxRepaintManager : public Timer
@@ -1870,7 +1694,7 @@ private:
Window windowH, parentWindow;
int wx, wy, ww, wh;
Image* taskbarImage;
bool fullScreen, entered, mapped, depthIs16Bit;
bool fullScreen, mapped, depthIs16Bit;
BorderSize windowBorder;
struct MotifWmHints
@@ -1882,6 +1706,100 @@ private:
unsigned long status;
};
static void updateKeyModifiers (const int status) throw()
{
int keyMods = 0;
if (status & ShiftMask) keyMods |= ModifierKeys::shiftModifier;
if (status & ControlMask) keyMods |= ModifierKeys::ctrlModifier;
if (status & AltMask) keyMods |= ModifierKeys::altModifier;
currentModifiers = currentModifiers.withOnlyMouseButtons().withFlags (keyMods);
numLock = ((status & NumLockMask) != 0);
capsLock = ((status & LockMask) != 0);
}
static bool updateKeyModifiersFromSym (KeySym sym, const bool press) throw()
{
int modifier = 0;
bool isModifier = true;
switch (sym)
{
case XK_Shift_L:
case XK_Shift_R:
modifier = ModifierKeys::shiftModifier;
break;
case XK_Control_L:
case XK_Control_R:
modifier = ModifierKeys::ctrlModifier;
break;
case XK_Alt_L:
case XK_Alt_R:
modifier = ModifierKeys::altModifier;
break;
case XK_Num_Lock:
if (press)
numLock = ! numLock;
break;
case XK_Caps_Lock:
if (press)
capsLock = ! capsLock;
break;
case XK_Scroll_Lock:
break;
default:
isModifier = false;
break;
}
if (modifier != 0)
{
if (press)
currentModifiers = currentModifiers.withFlags (modifier);
else
currentModifiers = currentModifiers.withoutFlags (modifier);
}
return isModifier;
}
// Alt and Num lock are not defined by standard X
// modifier constants: check what they're mapped to
static void updateModifierMappings() throw()
{
ScopedXLock xlock;
const int altLeftCode = XKeysymToKeycode (display, XK_Alt_L);
const int numLockCode = XKeysymToKeycode (display, XK_Num_Lock);
AltMask = 0;
NumLockMask = 0;
XModifierKeymap* mapping = XGetModifierMapping (display);
if (mapping)
{
for (int i = 0; i < 8; i++)
{
if (mapping->modifiermap [i << 1] == altLeftCode)
AltMask = 1 << i;
else if (mapping->modifiermap [i << 1] == numLockCode)
NumLockMask = 1 << i;
}
XFreeModifiermap (mapping);
}
}
//==============================================================================
void removeWindowDecorations (Window wndH)
{
@@ -2195,7 +2113,7 @@ private:
}
}
getModifierMapping();
updateModifierMappings();
}
windowH = wndH;
@@ -2220,7 +2138,7 @@ private:
{}
}
static int64 getEventTime (::Time t) throw()
static int64 getEventTime (::Time t)
{
static int64 eventTimeOffset = 0x12345678;
const int64 thisMessageTime = t;
@@ -2566,9 +2484,37 @@ private:
}
};
ModifierKeys LinuxComponentPeer::currentModifiers;
int LinuxComponentPeer::pointerMap[5];
Point<int> LinuxComponentPeer::lastMousePos;
//==============================================================================
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifiers = LinuxComponentPeer::currentModifiers;
}
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
Window root, child;
int x, y, winx, winy;
unsigned int mask;
int mouseMods = 0;
ScopedXLock xlock;
if (XQueryPointer (display, RootWindow (display, DefaultScreen (display)),
&root, &child, &x, &y, &winx, &winy, &mask) != False)
{
if ((mask & Button1Mask) != 0) mouseMods |= ModifierKeys::leftButtonModifier;
if ((mask & Button2Mask) != 0) mouseMods |= ModifierKeys::middleButtonModifier;
if ((mask & Button3Mask) != 0) mouseMods |= ModifierKeys::rightButtonModifier;
}
LinuxComponentPeer::currentModifiers = LinuxComponentPeer::currentModifiers.withoutMouseButtons().withFlags (mouseMods);
return LinuxComponentPeer::currentModifiers;
}
//==============================================================================
void juce_setKioskComponent (Component* kioskModeComponent, bool enableOrDisable, bool allowMenusAndBars)
@@ -2721,8 +2667,22 @@ bool Desktop::canUseSemiTransparentWindows() throw()
const Point<int> Desktop::getMousePosition()
{
int mouseMods;
return getMousePos (mouseMods);
Window root, child;
int x, y, winx, winy;
unsigned int mask;
ScopedXLock xlock;
if (XQueryPointer (display,
RootWindow (display, DefaultScreen (display)),
&root, &child,
&x, &y, &winx, &winy, &mask) == False)
{
// Pointer not on the default screen
x = y = -1;
}
return Point<int> (x, y);
}
void Desktop::setMousePosition (const Point<int>& newPosition)


+ 21
- 24
src/native/mac/juce_iphone_UIViewComponentPeer.mm View File

@@ -101,7 +101,7 @@ public:
bool isMinimised() const;
void setFullScreen (bool shouldBeFullScreen);
bool isFullScreen() const;
bool contains (int x, int y, bool trueIfInAChildWindow) const;
bool contains (const Point<int>& position, bool trueIfInAChildWindow) const;
const BorderSize getFrameSize() const;
bool setAlwaysOnTop (bool alwaysOnTop);
void toFront (bool makeActiveWindow);
@@ -133,6 +133,7 @@ public:
UIWindow* window;
JuceUIView* view;
bool isSharedWindow, fullScreen, insideDrawRect;
static ModifierKeys currentModifiers;
};
//==============================================================================
@@ -167,23 +168,16 @@ bool KeyPress::isKeyCurrentlyDown (const int keyCode) throw()
return false;
}
static int currentModifiers = 0;
ModifierKeys UIViewComponentPeer::currentModifiers;
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
return ModifierKeys (currentModifiers);
return UIViewComponentPeer::currentModifiers;
}
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifierFlags = currentModifiers;
}
static int getModifierForButtonNumber (const int num)
{
return num == 0 ? ModifierKeys::leftButtonModifier
: (num == 1 ? ModifierKeys::rightButtonModifier
: (num == 2 ? ModifierKeys::middleButtonModifier : 0));
currentModifiers = UIViewComponentPeer::currentModifiers;
}
static int64 getMouseTime (UIEvent* e)
@@ -208,13 +202,15 @@ JUCE_NAMESPACE::Point<int> juce_lastMousePos;
{
CGPoint p = [[t objectAtIndex: 0] locationInView: self];
const JUCE_NAMESPACE::Point<int> pos ((int) p.x, (int) p.y);
currentModifiers |= getModifierForButtonNumber (0);
juce_lastMousePos = pos + owner->getScreenPosition();
owner->handleMouseMove (pos, getMouseTime (event));
owner->handleMouseEvent (pos, JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers, getMouseTime (event));
if (owner != 0)
owner->handleMouseDown (pos, getMouseTime (event));
JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers
= JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers.withoutMouseButtons()
.withFlags (JUCE_NAMESPACE::ModifierKeys::leftButtonModifier);
owner->handleMouseEvent (pos, JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers, getMouseTime (event));
}
default:
@@ -238,7 +234,7 @@ JUCE_NAMESPACE::Point<int> juce_lastMousePos;
const JUCE_NAMESPACE::Point<int> pos ((int) p.x, (int) p.y);
juce_lastMousePos = pos + owner->getScreenPosition();
owner->handleMouseDrag (pos, getMouseTime (event));
owner->handleMouseEvent (pos, JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers, getMouseTime (event));
}
default:
@@ -262,9 +258,10 @@ JUCE_NAMESPACE::Point<int> juce_lastMousePos;
const JUCE_NAMESPACE::Point<int> pos ((int) p.x, (int) p.y);
juce_lastMousePos = pos + owner->getScreenPosition();
const int oldMods = currentModifiers;
currentModifiers &= ~getModifierForButtonNumber (0);
owner->handleMouseUp (oldMods, pos, getMouseTime (event));
JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers
= JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers.withoutMouseButtons();
owner->handleMouseEvent (pos, JUCE_NAMESPACE::UIViewComponentPeer::currentModifiers, getMouseTime (event));
}
default:
@@ -559,15 +556,15 @@ bool UIViewComponentPeer::isFullScreen() const
return fullScreen;
}
bool UIViewComponentPeer::contains (int x, int y, bool trueIfInAChildWindow) const
bool UIViewComponentPeer::contains (const Point<int>& position, bool trueIfInAChildWindow) const
{
if (((unsigned int) x) >= (unsigned int) component->getWidth()
|| ((unsigned int) y) >= (unsigned int) component->getHeight())
if (((unsigned int) position.getX()) >= (unsigned int) component->getWidth()
|| ((unsigned int) position.getY()) >= (unsigned int) component->getHeight())
return false;
CGPoint p;
p.x = (float) x;
p.y = (float) y;
p.x = (float) position.getX();
p.y = (float) position.getY();
UIView* v = [view hitTest: p withEvent: nil];


+ 50
- 52
src/native/mac/juce_mac_NSViewComponentPeer.mm View File

@@ -159,7 +159,7 @@ public:
bool isMinimised() const;
void setFullScreen (bool shouldBeFullScreen);
bool isFullScreen() const;
bool contains (int x, int y, bool trueIfInAChildWindow) const;
bool contains (const Point<int>& position, bool trueIfInAChildWindow) const;
const BorderSize getFrameSize() const;
bool setAlwaysOnTop (bool alwaysOnTop);
void toFront (bool makeActiveWindow);
@@ -186,6 +186,7 @@ public:
virtual void redirectMouseEnter (NSEvent* ev);
virtual void redirectMouseExit (NSEvent* ev);
virtual void redirectMouseWheel (NSEvent* ev);
void sendMouseEvent (NSEvent* ev);
bool handleKeyEvent (NSEvent* ev, bool isKeyDown);
virtual bool redirectKeyDown (NSEvent* ev);
@@ -261,6 +262,10 @@ public:
NSWindow* window;
JuceNSView* view;
bool isSharedWindow, fullScreen, insideDrawRect, usingCoreGraphics, recursiveToFrontCall;
static ModifierKeys currentModifiers;
static ComponentPeer* currentlyFocusedPeer;
static VoidArray keysCurrentlyDown;
};
//==============================================================================
@@ -748,45 +753,37 @@ END_JUCE_NAMESPACE
BEGIN_JUCE_NAMESPACE
//==============================================================================
static ComponentPeer* currentlyFocusedPeer = 0;
static VoidArray keysCurrentlyDown;
ModifierKeys NSViewComponentPeer::currentModifiers;
ComponentPeer* NSViewComponentPeer::currentlyFocusedPeer = 0;
VoidArray NSViewComponentPeer::keysCurrentlyDown;
//==============================================================================
bool KeyPress::isKeyCurrentlyDown (const int keyCode) throw()
{
if (keysCurrentlyDown.contains ((void*) keyCode))
if (NSViewComponentPeer::keysCurrentlyDown.contains ((void*) keyCode))
return true;
if (keyCode >= 'A' && keyCode <= 'Z'
&& keysCurrentlyDown.contains ((void*) (int) CharacterFunctions::toLowerCase ((tchar) keyCode)))
&& NSViewComponentPeer::keysCurrentlyDown.contains ((void*) (int) CharacterFunctions::toLowerCase ((tchar) keyCode)))
return true;
if (keyCode >= 'a' && keyCode <= 'z'
&& keysCurrentlyDown.contains ((void*) (int) CharacterFunctions::toUpperCase ((tchar) keyCode)))
&& NSViewComponentPeer::keysCurrentlyDown.contains ((void*) (int) CharacterFunctions::toUpperCase ((tchar) keyCode)))
return true;
return false;
}
static int currentModifiers = 0;
void NSViewComponentPeer::updateModifiers (NSEvent* e)
{
int m = currentModifiers & ~(ModifierKeys::shiftModifier | ModifierKeys::ctrlModifier
| ModifierKeys::altModifier | ModifierKeys::commandModifier);
if (([e modifierFlags] & NSShiftKeyMask) != 0)
m |= ModifierKeys::shiftModifier;
if (([e modifierFlags] & NSControlKeyMask) != 0)
m |= ModifierKeys::ctrlModifier;
int m = 0;
if (([e modifierFlags] & NSAlternateKeyMask) != 0)
m |= ModifierKeys::altModifier;
if (([e modifierFlags] & NSShiftKeyMask) != 0) m |= ModifierKeys::shiftModifier;
if (([e modifierFlags] & NSControlKeyMask) != 0) m |= ModifierKeys::ctrlModifier;
if (([e modifierFlags] & NSAlternateKeyMask) != 0) m |= ModifierKeys::altModifier;
if (([e modifierFlags] & NSCommandKeyMask) != 0) m |= ModifierKeys::commandModifier;
if (([e modifierFlags] & NSCommandKeyMask) != 0)
m |= ModifierKeys::commandModifier;
currentModifiers = m;
currentModifiers = currentModifiers.withOnlyMouseButtons().withFlags (m);
}
void NSViewComponentPeer::updateKeysDown (NSEvent* ev, bool isKeyDown)
@@ -805,12 +802,12 @@ void NSViewComponentPeer::updateKeysDown (NSEvent* ev, bool isKeyDown)
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
return ModifierKeys (currentModifiers);
return NSViewComponentPeer::currentModifiers;
}
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifierFlags = currentModifiers;
currentModifiers = NSViewComponentPeer::currentModifiers;
}
//==============================================================================
@@ -1106,15 +1103,15 @@ bool NSViewComponentPeer::isFullScreen() const
return fullScreen;
}
bool NSViewComponentPeer::contains (int x, int y, bool trueIfInAChildWindow) const
bool NSViewComponentPeer::contains (const Point<int>& position, bool trueIfInAChildWindow) const
{
if (((unsigned int) x) >= (unsigned int) component->getWidth()
|| ((unsigned int) y) >= (unsigned int) component->getHeight())
if (((unsigned int) position.getX()) >= (unsigned int) component->getWidth()
|| ((unsigned int) position.getY()) >= (unsigned int) component->getHeight())
return false;
NSPoint p;
p.x = (float) x;
p.y = (float) y;
p.x = (float) position.getX();
p.y = (float) position.getY();
NSView* v = [view hitTest: p];
@@ -1226,19 +1223,19 @@ void NSViewComponentPeer::viewFocusLoss()
void juce_HandleProcessFocusChange()
{
keysCurrentlyDown.clear();
NSViewComponentPeer::keysCurrentlyDown.clear();
if (NSViewComponentPeer::isValidPeer (currentlyFocusedPeer))
if (NSViewComponentPeer::isValidPeer (NSViewComponentPeer::currentlyFocusedPeer))
{
if (Process::isForegroundProcess())
{
currentlyFocusedPeer->handleFocusGain();
NSViewComponentPeer::currentlyFocusedPeer->handleFocusGain();
ComponentPeer::bringModalComponentToFront();
}
else
{
currentlyFocusedPeer->handleFocusLoss();
NSViewComponentPeer::currentlyFocusedPeer->handleFocusLoss();
// turn kiosk mode off if we lose focus..
Desktop::getInstance().setKioskModeComponent (0);
@@ -1355,55 +1352,56 @@ bool NSViewComponentPeer::redirectPerformKeyEquivalent (NSEvent* ev)
#endif
//==============================================================================
void NSViewComponentPeer::redirectMouseDown (NSEvent* ev)
void NSViewComponentPeer::sendMouseEvent (NSEvent* ev)
{
updateModifiers (ev);
currentModifiers |= getModifierForButtonNumber ([ev buttonNumber]);
handleMouseDown (getMousePos (ev, view), getMouseTime (ev));
handleMouseEvent (getMousePos (ev, view), currentModifiers, getMouseTime (ev));
}
void NSViewComponentPeer::redirectMouseDown (NSEvent* ev)
{
currentModifiers = currentModifiers.withFlags (getModifierForButtonNumber ([ev buttonNumber]));
sendMouseEvent (ev);
}
void NSViewComponentPeer::redirectMouseUp (NSEvent* ev)
{
const int oldMods = currentModifiers;
updateModifiers (ev);
currentModifiers &= ~getModifierForButtonNumber ([ev buttonNumber]);
handleMouseUp (oldMods, getMousePos (ev, view), getMouseTime (ev));
currentModifiers = currentModifiers.withoutFlags (getModifierForButtonNumber ([ev buttonNumber]));
sendMouseEvent (ev);
showArrowCursorIfNeeded();
}
void NSViewComponentPeer::redirectMouseDrag (NSEvent* ev)
{
updateModifiers (ev);
currentModifiers |= getModifierForButtonNumber ([ev buttonNumber]);
handleMouseDrag (getMousePos (ev, view), getMouseTime (ev));
currentModifiers = currentModifiers.withFlags (getModifierForButtonNumber ([ev buttonNumber]));
sendMouseEvent (ev);
}
void NSViewComponentPeer::redirectMouseMove (NSEvent* ev)
{
updateModifiers (ev);
handleMouseMove (getMousePos (ev, view), getMouseTime (ev));
currentModifiers = currentModifiers.withoutMouseButtons();
sendMouseEvent (ev);
showArrowCursorIfNeeded();
}
void NSViewComponentPeer::redirectMouseEnter (NSEvent* ev)
{
updateModifiers (ev);
handleMouseEnter (getMousePos (ev, view), getMouseTime (ev));
currentModifiers = currentModifiers.withoutMouseButtons();
sendMouseEvent (ev);
}
void NSViewComponentPeer::redirectMouseExit (NSEvent* ev)
{
updateModifiers (ev);
handleMouseExit (getMousePos (ev, view), getMouseTime (ev));
currentModifiers = currentModifiers.withoutMouseButtons();
sendMouseEvent (ev);
}
void NSViewComponentPeer::redirectMouseWheel (NSEvent* ev)
{
updateModifiers (ev);
handleMouseWheel (roundToInt ([ev deltaX] * 10.0f),
roundToInt ([ev deltaY] * 10.0f),
getMouseTime (ev));
handleMouseWheel (getMousePos (ev, view), getMouseTime (ev),
[ev deltaX] * 10.0f, [ev deltaY] * 10.0f);
}
void NSViewComponentPeer::showArrowCursorIfNeeded()


+ 258
- 267
src/native/windows/juce_win32_ActiveXComponent.cpp View File

@@ -27,223 +27,272 @@
// compiled on its own).
#if JUCE_INCLUDED_FILE
//==============================================================================
class JuceIStorage : public IStorage
namespace ActiveXHelpers
{
int refCount;
class JuceIStorage : public IStorage
{
int refCount;
public:
JuceIStorage() : refCount (1) {}
public:
JuceIStorage() : refCount (1) {}
virtual ~JuceIStorage()
{
jassert (refCount == 0);
}
virtual ~JuceIStorage()
{
jassert (refCount == 0);
}
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
{
if (id == IID_IUnknown || id == IID_IStorage)
{
AddRef();
*result = this;
return S_OK;
}
*result = 0;
return E_NOINTERFACE;
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
HRESULT __stdcall CreateStream (const WCHAR*, DWORD, DWORD, DWORD, IStream**) { return E_NOTIMPL; }
HRESULT __stdcall OpenStream (const WCHAR*, void*, DWORD, DWORD, IStream**) { return E_NOTIMPL; }
HRESULT __stdcall CreateStorage (const WCHAR*, DWORD, DWORD, DWORD, IStorage**) { return E_NOTIMPL; }
HRESULT __stdcall OpenStorage (const WCHAR*, IStorage*, DWORD, SNB, DWORD, IStorage**) { return E_NOTIMPL; }
HRESULT __stdcall CopyTo (DWORD, IID const*, SNB, IStorage*) { return E_NOTIMPL; }
HRESULT __stdcall MoveElementTo (const OLECHAR*,IStorage*, const OLECHAR*, DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Commit (DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Revert() { return E_NOTIMPL; }
HRESULT __stdcall EnumElements (DWORD, void*, DWORD, IEnumSTATSTG**) { return E_NOTIMPL; }
HRESULT __stdcall DestroyElement (const OLECHAR*) { return E_NOTIMPL; }
HRESULT __stdcall RenameElement (const WCHAR*, const WCHAR*) { return E_NOTIMPL; }
HRESULT __stdcall SetElementTimes (const WCHAR*, FILETIME const*, FILETIME const*, FILETIME const*) { return E_NOTIMPL; }
HRESULT __stdcall SetClass (REFCLSID) { return S_OK; }
HRESULT __stdcall SetStateBits (DWORD, DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Stat (STATSTG*, DWORD) { return E_NOTIMPL; }
juce_UseDebuggingNewOperator
};
class JuceOleInPlaceFrame : public IOleInPlaceFrame
{
if (id == IID_IUnknown || id == IID_IStorage)
int refCount;
HWND window;
public:
JuceOleInPlaceFrame (HWND window_)
: refCount (1),
window (window_)
{
AddRef();
*result = this;
return S_OK;
}
*result = 0;
return E_NOINTERFACE;
}
virtual ~JuceOleInPlaceFrame()
{
jassert (refCount == 0);
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
HRESULT __stdcall CreateStream (const WCHAR*, DWORD, DWORD, DWORD, IStream**) { return E_NOTIMPL; }
HRESULT __stdcall OpenStream (const WCHAR*, void*, DWORD, DWORD, IStream**) { return E_NOTIMPL; }
HRESULT __stdcall CreateStorage (const WCHAR*, DWORD, DWORD, DWORD, IStorage**) { return E_NOTIMPL; }
HRESULT __stdcall OpenStorage (const WCHAR*, IStorage*, DWORD, SNB, DWORD, IStorage**) { return E_NOTIMPL; }
HRESULT __stdcall CopyTo (DWORD, IID const*, SNB, IStorage*) { return E_NOTIMPL; }
HRESULT __stdcall MoveElementTo (const OLECHAR*,IStorage*, const OLECHAR*, DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Commit (DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Revert() { return E_NOTIMPL; }
HRESULT __stdcall EnumElements (DWORD, void*, DWORD, IEnumSTATSTG**) { return E_NOTIMPL; }
HRESULT __stdcall DestroyElement (const OLECHAR*) { return E_NOTIMPL; }
HRESULT __stdcall RenameElement (const WCHAR*, const WCHAR*) { return E_NOTIMPL; }
HRESULT __stdcall SetElementTimes (const WCHAR*, FILETIME const*, FILETIME const*, FILETIME const*) { return E_NOTIMPL; }
HRESULT __stdcall SetClass (REFCLSID) { return S_OK; }
HRESULT __stdcall SetStateBits (DWORD, DWORD) { return E_NOTIMPL; }
HRESULT __stdcall Stat (STATSTG*, DWORD) { return E_NOTIMPL; }
juce_UseDebuggingNewOperator
};
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
{
if (id == IID_IUnknown || id == IID_IOleInPlaceFrame)
{
AddRef();
*result = this;
return S_OK;
}
*result = 0;
return E_NOINTERFACE;
}
class JuceOleInPlaceFrame : public IOleInPlaceFrame
{
int refCount;
HWND window;
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
public:
JuceOleInPlaceFrame (HWND window_)
: refCount (1),
window (window_)
{
}
HRESULT __stdcall GetWindow (HWND* lphwnd) { *lphwnd = window; return S_OK; }
HRESULT __stdcall ContextSensitiveHelp (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall GetBorder (LPRECT) { return E_NOTIMPL; }
HRESULT __stdcall RequestBorderSpace (LPCBORDERWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetBorderSpace (LPCBORDERWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetActiveObject (IOleInPlaceActiveObject*, LPCOLESTR) { return S_OK; }
HRESULT __stdcall InsertMenus (HMENU, LPOLEMENUGROUPWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetMenu (HMENU, HOLEMENU, HWND) { return S_OK; }
HRESULT __stdcall RemoveMenus (HMENU) { return E_NOTIMPL; }
HRESULT __stdcall SetStatusText (LPCOLESTR) { return S_OK; }
HRESULT __stdcall EnableModeless (BOOL) { return S_OK; }
HRESULT __stdcall TranslateAccelerator(LPMSG, WORD) { return E_NOTIMPL; }
juce_UseDebuggingNewOperator
};
virtual ~JuceOleInPlaceFrame()
{
jassert (refCount == 0);
}
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
class JuceIOleInPlaceSite : public IOleInPlaceSite
{
if (id == IID_IUnknown || id == IID_IOleInPlaceFrame)
int refCount;
HWND window;
JuceOleInPlaceFrame* frame;
public:
JuceIOleInPlaceSite (HWND window_)
: refCount (1),
window (window_)
{
AddRef();
*result = this;
return S_OK;
frame = new JuceOleInPlaceFrame (window);
}
*result = 0;
return E_NOINTERFACE;
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
HRESULT __stdcall GetWindow (HWND* lphwnd) { *lphwnd = window; return S_OK; }
HRESULT __stdcall ContextSensitiveHelp (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall GetBorder (LPRECT) { return E_NOTIMPL; }
HRESULT __stdcall RequestBorderSpace (LPCBORDERWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetBorderSpace (LPCBORDERWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetActiveObject (IOleInPlaceActiveObject*, LPCOLESTR) { return S_OK; }
HRESULT __stdcall InsertMenus (HMENU, LPOLEMENUGROUPWIDTHS) { return E_NOTIMPL; }
HRESULT __stdcall SetMenu (HMENU, HOLEMENU, HWND) { return S_OK; }
HRESULT __stdcall RemoveMenus (HMENU) { return E_NOTIMPL; }
HRESULT __stdcall SetStatusText (LPCOLESTR) { return S_OK; }
HRESULT __stdcall EnableModeless (BOOL) { return S_OK; }
HRESULT __stdcall TranslateAccelerator(LPMSG, WORD) { return E_NOTIMPL; }
juce_UseDebuggingNewOperator
};
virtual ~JuceIOleInPlaceSite()
{
jassert (refCount == 0);
frame->Release();
}
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
{
if (id == IID_IUnknown || id == IID_IOleInPlaceSite)
{
AddRef();
*result = this;
return S_OK;
}
class JuceIOleInPlaceSite : public IOleInPlaceSite
{
int refCount;
HWND window;
JuceOleInPlaceFrame* frame;
*result = 0;
return E_NOINTERFACE;
}
public:
JuceIOleInPlaceSite (HWND window_)
: refCount (1),
window (window_)
{
frame = new JuceOleInPlaceFrame (window);
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
virtual ~JuceIOleInPlaceSite()
{
jassert (refCount == 0);
frame->Release();
}
HRESULT __stdcall GetWindow (HWND* lphwnd) { *lphwnd = window; return S_OK; }
HRESULT __stdcall ContextSensitiveHelp (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall CanInPlaceActivate() { return S_OK; }
HRESULT __stdcall OnInPlaceActivate() { return S_OK; }
HRESULT __stdcall OnUIActivate() { return S_OK; }
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
{
if (id == IID_IUnknown || id == IID_IOleInPlaceSite)
HRESULT __stdcall GetWindowContext (LPOLEINPLACEFRAME* lplpFrame, LPOLEINPLACEUIWINDOW* lplpDoc, LPRECT, LPRECT, LPOLEINPLACEFRAMEINFO lpFrameInfo)
{
AddRef();
*result = this;
// frame->AddRef(); // MS docs are unclear about whether this is needed, but it seems to lead to a memory leak..
*lplpFrame = frame;
*lplpDoc = 0;
lpFrameInfo->fMDIApp = FALSE;
lpFrameInfo->hwndFrame = window;
lpFrameInfo->haccel = 0;
lpFrameInfo->cAccelEntries = 0;
return S_OK;
}
*result = 0;
return E_NOINTERFACE;
}
HRESULT __stdcall Scroll (SIZE) { return E_NOTIMPL; }
HRESULT __stdcall OnUIDeactivate (BOOL) { return S_OK; }
HRESULT __stdcall OnInPlaceDeactivate() { return S_OK; }
HRESULT __stdcall DiscardUndoState() { return E_NOTIMPL; }
HRESULT __stdcall DeactivateAndUndo() { return E_NOTIMPL; }
HRESULT __stdcall OnPosRectChange (LPCRECT) { return S_OK; }
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
juce_UseDebuggingNewOperator
};
HRESULT __stdcall GetWindow (HWND* lphwnd) { *lphwnd = window; return S_OK; }
HRESULT __stdcall ContextSensitiveHelp (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall CanInPlaceActivate() { return S_OK; }
HRESULT __stdcall OnInPlaceActivate() { return S_OK; }
HRESULT __stdcall OnUIActivate() { return S_OK; }
HRESULT __stdcall GetWindowContext (LPOLEINPLACEFRAME* lplpFrame, LPOLEINPLACEUIWINDOW* lplpDoc, LPRECT, LPRECT, LPOLEINPLACEFRAMEINFO lpFrameInfo)
class JuceIOleClientSite : public IOleClientSite
{
// frame->AddRef(); // MS docs are unclear about whether this is needed, but it seems to lead to a memory leak..
*lplpFrame = frame;
*lplpDoc = 0;
lpFrameInfo->fMDIApp = FALSE;
lpFrameInfo->hwndFrame = window;
lpFrameInfo->haccel = 0;
lpFrameInfo->cAccelEntries = 0;
return S_OK;
}
int refCount;
JuceIOleInPlaceSite* inplaceSite;
HRESULT __stdcall Scroll (SIZE) { return E_NOTIMPL; }
HRESULT __stdcall OnUIDeactivate (BOOL) { return S_OK; }
HRESULT __stdcall OnInPlaceDeactivate() { return S_OK; }
HRESULT __stdcall DiscardUndoState() { return E_NOTIMPL; }
HRESULT __stdcall DeactivateAndUndo() { return E_NOTIMPL; }
HRESULT __stdcall OnPosRectChange (LPCRECT) { return S_OK; }
public:
JuceIOleClientSite (HWND window)
: refCount (1)
{
inplaceSite = new JuceIOleInPlaceSite (window);
}
juce_UseDebuggingNewOperator
};
virtual ~JuceIOleClientSite()
{
jassert (refCount == 0);
inplaceSite->Release();
}
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
{
if (id == IID_IUnknown || id == IID_IOleClientSite)
{
AddRef();
*result = this;
return S_OK;
}
else if (id == IID_IOleInPlaceSite)
{
inplaceSite->AddRef();
*result = inplaceSite;
return S_OK;
}
class JuceIOleClientSite : public IOleClientSite
{
int refCount;
JuceIOleInPlaceSite* inplaceSite;
*result = 0;
return E_NOINTERFACE;
}
public:
JuceIOleClientSite (HWND window)
: refCount (1)
{
inplaceSite = new JuceIOleInPlaceSite (window);
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
virtual ~JuceIOleClientSite()
{
jassert (refCount == 0);
inplaceSite->Release();
}
HRESULT __stdcall SaveObject() { return E_NOTIMPL; }
HRESULT __stdcall GetMoniker (DWORD, DWORD, IMoniker**) { return E_NOTIMPL; }
HRESULT __stdcall GetContainer (LPOLECONTAINER* ppContainer) { *ppContainer = 0; return E_NOINTERFACE; }
HRESULT __stdcall ShowObject() { return S_OK; }
HRESULT __stdcall OnShowWindow (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall RequestNewObjectLayout() { return E_NOTIMPL; }
juce_UseDebuggingNewOperator
};
HRESULT __stdcall QueryInterface (REFIID id, void __RPC_FAR* __RPC_FAR* result)
//==============================================================================
static VoidArray activeXComps;
static HWND getHWND (const ActiveXControlComponent* const component)
{
if (id == IID_IUnknown || id == IID_IOleClientSite)
{
AddRef();
*result = this;
return S_OK;
}
else if (id == IID_IOleInPlaceSite)
HWND hwnd = 0;
const IID iid = IID_IOleWindow;
IOleWindow* const window = (IOleWindow*) component->queryInterface (&iid);
if (window != 0)
{
inplaceSite->AddRef();
*result = inplaceSite;
return S_OK;
window->GetWindow (&hwnd);
window->Release();
}
*result = 0;
return E_NOINTERFACE;
return hwnd;
}
ULONG __stdcall AddRef() { return ++refCount; }
ULONG __stdcall Release() { const int r = --refCount; if (r == 0) delete this; return r; }
static void offerActiveXMouseEventToPeer (ComponentPeer* const peer, HWND hwnd, UINT message, LPARAM lParam)
{
RECT activeXRect, peerRect;
GetWindowRect (hwnd, &activeXRect);
GetWindowRect ((HWND) peer->getNativeHandle(), &peerRect);
HRESULT __stdcall SaveObject() { return E_NOTIMPL; }
HRESULT __stdcall GetMoniker (DWORD, DWORD, IMoniker**) { return E_NOTIMPL; }
HRESULT __stdcall GetContainer (LPOLECONTAINER* ppContainer) { *ppContainer = 0; return E_NOINTERFACE; }
HRESULT __stdcall ShowObject() { return S_OK; }
HRESULT __stdcall OnShowWindow (BOOL) { return E_NOTIMPL; }
HRESULT __stdcall RequestNewObjectLayout() { return E_NOTIMPL; }
const Point<int> mousePos (GET_X_LPARAM (lParam) + activeXRect.left - peerRect.left,
GET_Y_LPARAM (lParam) + activeXRect.top - peerRect.top);
const int64 mouseEventTime = Win32ComponentPeer::getMouseEventTime();
juce_UseDebuggingNewOperator
};
ModifierKeys::getCurrentModifiersRealtime(); // to update the mouse button flags
switch (message)
{
case WM_MOUSEMOVE:
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
peer->handleMouseEvent (mousePos, Win32ComponentPeer::currentModifiers, mouseEventTime);
break;
default:
break;
}
}
}
//==============================================================================
class ActiveXControlData : public ComponentMovementWatcher
class ActiveXControlComponent::ActiveXControlData : public ComponentMovementWatcher
{
ActiveXControlComponent* const owner;
bool wasShowing;
@@ -261,8 +310,8 @@ public:
owner (owner_),
wasShowing (owner_ != 0 && owner_->isShowing()),
controlHWND (0),
storage (new JuceIStorage()),
clientSite (new JuceIOleClientSite (hwnd)),
storage (new ActiveXHelpers::JuceIStorage()),
clientSite (new ActiveXHelpers::JuceIOleClientSite (hwnd)),
control (0)
{
}
@@ -315,124 +364,66 @@ public:
return ((ActiveXControlData*) ax->control) != 0
&& ((ActiveXControlData*) ax->control)->controlHWND == hwnd;
}
};
//==============================================================================
static VoidArray activeXComps;
static HWND getHWND (const ActiveXControlComponent* const component)
{
HWND hwnd = 0;
const IID iid = IID_IOleWindow;
IOleWindow* const window = (IOleWindow*) component->queryInterface (&iid);
if (window != 0)
{
window->GetWindow (&hwnd);
window->Release();
}
return hwnd;
}
static void offerActiveXMouseEventToPeer (ComponentPeer* const peer, HWND hwnd, UINT message, LPARAM lParam)
{
RECT activeXRect, peerRect;
GetWindowRect (hwnd, &activeXRect);
GetWindowRect ((HWND) peer->getNativeHandle(), &peerRect);
const Point<int> mousePos (GET_X_LPARAM (lParam) + activeXRect.left - peerRect.left,
GET_Y_LPARAM (lParam) + activeXRect.top - peerRect.top);
const int64 mouseEventTime = getMouseEventTime();
const int oldModifiers = currentModifiers;
ModifierKeys::getCurrentModifiersRealtime(); // to update the mouse button flags
switch (message)
{
case WM_MOUSEMOVE:
if (ModifierKeys (currentModifiers).isAnyMouseButtonDown())
peer->handleMouseDrag (mousePos, mouseEventTime);
else
peer->handleMouseMove (mousePos, mouseEventTime);
break;
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
peer->handleMouseDown (mousePos, mouseEventTime);
break;
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
peer->handleMouseUp (oldModifiers, mousePos, mouseEventTime);
break;
default:
break;
}
}
// intercepts events going to an activeX control, so we can sneakily use the mouse events
static LRESULT CALLBACK activeXHookWndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
for (int i = activeXComps.size(); --i >= 0;)
// intercepts events going to an activeX control, so we can sneakily use the mouse events
static LRESULT CALLBACK activeXHookWndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
const ActiveXControlComponent* const ax = (const ActiveXControlComponent*) activeXComps.getUnchecked(i);
if (ActiveXControlData::doesWindowMatch (ax, hwnd))
for (int i = ActiveXHelpers::activeXComps.size(); --i >= 0;)
{
switch (message)
const ActiveXControlComponent* const ax = (const ActiveXControlComponent*) ActiveXHelpers::activeXComps.getUnchecked(i);
if (doesWindowMatch (ax, hwnd))
{
case WM_MOUSEMOVE:
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
case WM_LBUTTONDBLCLK:
case WM_MBUTTONDBLCLK:
case WM_RBUTTONDBLCLK:
if (ax->isShowing())
switch (message)
{
ComponentPeer* const peer = ax->getPeer();
if (peer != 0)
case WM_MOUSEMOVE:
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
case WM_LBUTTONDBLCLK:
case WM_MBUTTONDBLCLK:
case WM_RBUTTONDBLCLK:
if (ax->isShowing())
{
offerActiveXMouseEventToPeer (peer, hwnd, message, lParam);
ComponentPeer* const peer = ax->getPeer();
if (! ax->areMouseEventsAllowed())
return 0;
if (peer != 0)
{
ActiveXHelpers::offerActiveXMouseEventToPeer (peer, hwnd, message, lParam);
if (! ax->areMouseEventsAllowed())
return 0;
}
}
break;
default:
break;
}
break;
default:
break;
return CallWindowProc ((WNDPROC) (ax->originalWndProc), hwnd, message, wParam, lParam);
}
return CallWindowProc ((WNDPROC) (ax->originalWndProc), hwnd, message, wParam, lParam);
}
}
return DefWindowProc (hwnd, message, wParam, lParam);
}
return DefWindowProc (hwnd, message, wParam, lParam);
}
};
ActiveXControlComponent::ActiveXControlComponent()
: originalWndProc (0),
control (0),
mouseEventsAllowed (true)
{
activeXComps.add (this);
ActiveXHelpers::activeXComps.add (this);
}
ActiveXControlComponent::~ActiveXControlComponent()
{
deleteControl();
activeXComps.removeValue (this);
ActiveXHelpers::activeXComps.removeValue (this);
}
void ActiveXControlComponent::paint (Graphics& g)
@@ -476,12 +467,12 @@ bool ActiveXControlComponent::createControl (const void* controlIID)
control = info.release();
setControlBounds (Rectangle<int> (pos.getX(), pos.getY(), getWidth(), getHeight()));
((ActiveXControlData*) control)->controlHWND = getHWND (this);
((ActiveXControlData*) control)->controlHWND = ActiveXHelpers::getHWND (this);
if (((ActiveXControlData*) control)->controlHWND != 0)
{
originalWndProc = (void*) (pointer_sized_int) GetWindowLongPtr ((HWND) ((ActiveXControlData*) control)->controlHWND, GWLP_WNDPROC);
SetWindowLongPtr ((HWND) ((ActiveXControlData*) control)->controlHWND, GWLP_WNDPROC, (LONG_PTR) activeXHookWndProc);
SetWindowLongPtr ((HWND) ((ActiveXControlData*) control)->controlHWND, GWLP_WNDPROC, (LONG_PTR) ActiveXControlData::activeXHookWndProc);
}
return true;


+ 130
- 196
src/native/windows/juce_win32_Windowing.cpp View File

@@ -336,33 +336,6 @@ long improbableWindowNumber = 0xf965aa01; // also referenced by messaging.cpp
//==============================================================================
static int currentModifiers = 0;
static int modifiersAtLastCallback = 0;
static void updateKeyModifiers() throw()
{
currentModifiers &= ~(ModifierKeys::shiftModifier
| ModifierKeys::ctrlModifier
| ModifierKeys::altModifier);
if ((GetKeyState (VK_SHIFT) & 0x8000) != 0)
currentModifiers |= ModifierKeys::shiftModifier;
if ((GetKeyState (VK_CONTROL) & 0x8000) != 0)
currentModifiers |= ModifierKeys::ctrlModifier;
if ((GetKeyState (VK_MENU) & 0x8000) != 0)
currentModifiers |= ModifierKeys::altModifier;
if ((GetKeyState (VK_RMENU) & 0x8000) != 0)
currentModifiers &= ~(ModifierKeys::ctrlModifier | ModifierKeys::altModifier);
}
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifierFlags = currentModifiers;
}
bool KeyPress::isKeyCurrentlyDown (const int keyCode) throw()
{
SHORT k = (SHORT) keyCode;
@@ -389,39 +362,6 @@ bool KeyPress::isKeyCurrentlyDown (const int keyCode) throw()
return (GetKeyState (k) & 0x8000) != 0;
}
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
updateKeyModifiers();
currentModifiers &= ~ModifierKeys::allMouseButtonModifiers;
if ((GetKeyState (VK_LBUTTON) & 0x8000) != 0)
currentModifiers |= ModifierKeys::leftButtonModifier;
if ((GetKeyState (VK_RBUTTON) & 0x8000) != 0)
currentModifiers |= ModifierKeys::rightButtonModifier;
if ((GetKeyState (VK_MBUTTON) & 0x8000) != 0)
currentModifiers |= ModifierKeys::middleButtonModifier;
return ModifierKeys (currentModifiers);
}
static int64 getMouseEventTime() throw()
{
static int64 eventTimeOffset = 0;
static DWORD lastMessageTime = 0;
const DWORD thisMessageTime = GetMessageTime();
if (thisMessageTime < lastMessageTime || lastMessageTime == 0)
{
lastMessageTime = thisMessageTime;
eventTimeOffset = Time::currentTimeMillis() - thisMessageTime;
}
return eventTimeOffset + thisMessageTime;
}
static void* callFunctionIfNotLocked (MessageCallbackFunction* callback, void* userData)
{
if (MessageManager::getInstance()->currentThreadHasLockedMessageManager())
@@ -666,17 +606,20 @@ public:
return wp.showCmd == SW_SHOWMAXIMIZED;
}
bool contains (int x, int y, bool trueIfInAChildWindow) const
bool contains (const Point<int>& position, bool trueIfInAChildWindow) const
{
if (((unsigned int) position.getX()) >= (unsigned int) component->getWidth()
|| ((unsigned int) position.getY()) >= (unsigned int) component->getHeight())
return false;
RECT r;
GetWindowRect (hwnd, &r);
POINT p;
p.x = x + r.left + windowBorder.getLeft();
p.y = y + r.top + windowBorder.getTop();
p.x = position.getX() + r.left + windowBorder.getLeft();
p.y = position.getY() + r.top + windowBorder.getTop();
HWND w = WindowFromPoint (p);
return w == hwnd || (trueIfInAChildWindow && (IsChild (hwnd, w) != 0));
}
@@ -849,11 +792,52 @@ public:
return GetAncestor (hwnd, GA_ROOT) == h;
}
//==============================================================================
static void updateKeyModifiers() throw()
{
int keyMods = 0;
if (GetKeyState (VK_SHIFT) & 0x8000) keyMods |= ModifierKeys::shiftModifier;
if (GetKeyState (VK_CONTROL) & 0x8000) keyMods |= ModifierKeys::ctrlModifier;
if (GetKeyState (VK_MENU) & 0x8000) keyMods |= ModifierKeys::altModifier;
if (GetKeyState (VK_RMENU) & 0x8000) keyMods &= ~(ModifierKeys::ctrlModifier | ModifierKeys::altModifier);
currentModifiers = currentModifiers.withOnlyMouseButtons().withFlags (keyMods);
}
static void updateModifiersFromWParam (const WPARAM wParam)
{
int mouseMods = 0;
if (wParam & MK_LBUTTON) mouseMods |= ModifierKeys::leftButtonModifier;
if (wParam & MK_RBUTTON) mouseMods |= ModifierKeys::rightButtonModifier;
if (wParam & MK_MBUTTON) mouseMods |= ModifierKeys::middleButtonModifier;
currentModifiers = currentModifiers.withoutMouseButtons().withFlags (mouseMods);
updateKeyModifiers();
}
static int64 getMouseEventTime()
{
static int64 eventTimeOffset = 0;
static DWORD lastMessageTime = 0;
const DWORD thisMessageTime = GetMessageTime();
if (thisMessageTime < lastMessageTime || lastMessageTime == 0)
{
lastMessageTime = thisMessageTime;
eventTimeOffset = Time::currentTimeMillis() - thisMessageTime;
}
return eventTimeOffset + thisMessageTime;
}
//==============================================================================
juce_UseDebuggingNewOperator
bool dontRepaint;
static ModifierKeys currentModifiers;
static ModifierKeys modifiersAtLastCallback;
private:
HWND hwnd;
DropShadower* shadower;
@@ -1257,19 +1241,17 @@ private:
}
//==============================================================================
void doMouseMove (const int x, const int y)
void doMouseEvent (const Point<int>& position)
{
static uint32 lastMouseTime = 0;
// this can be set to throttle the mouse-messages to less than a
// certain number per second, as things can get unresponsive
// if each drag or move callback has to do a lot of work.
const int maxMouseMovesPerSecond = 60;
const int64 mouseEventTime = getMouseEventTime();
handleMouseEvent (position, currentModifiers, getMouseEventTime());
}
void doMouseMove (const Point<int>& position)
{
if (! isMouseOver)
{
isMouseOver = true;
updateKeyModifiers();
TRACKMOUSEEVENT tme;
tme.cbSize = sizeof (tme);
@@ -1278,151 +1260,63 @@ private:
tme.dwHoverTime = 0;
if (! TrackMouseEvent (&tme))
{
jassertfalse;
}
updateKeyModifiers();
handleMouseEnter (Point<int> (x, y), mouseEventTime);
}
else if (! isDragging)
{
if (((unsigned int) x) < (unsigned int) component->getWidth()
&& ((unsigned int) y) < (unsigned int) component->getHeight())
{
RECT r;
GetWindowRect (hwnd, &r);
POINT p;
p.x = x + r.left + windowBorder.getLeft();
p.y = y + r.top + windowBorder.getTop();
if (WindowFromPoint (p) == hwnd)
{
const uint32 now = Time::getMillisecondCounter();
if (now > lastMouseTime + 1000 / maxMouseMovesPerSecond)
{
lastMouseTime = now;
handleMouseMove (Point<int> (x, y), mouseEventTime);
}
}
}
if (! contains (position, false))
return;
}
else
{
const uint32 now = Time::getMillisecondCounter();
if (now > lastMouseTime + 1000 / maxMouseMovesPerSecond)
{
lastMouseTime = now;
handleMouseDrag (Point<int> (x, y), mouseEventTime);
}
}
doMouseEvent (position);
}
void doMouseDown (const int x, const int y, const WPARAM wParam)
void doMouseDown (const Point<int>& position, const WPARAM wParam)
{
if (GetCapture() != hwnd)
SetCapture (hwnd);
doMouseMove (x, y);
currentModifiers &= ~ModifierKeys::allMouseButtonModifiers;
if ((wParam & MK_LBUTTON) != 0)
currentModifiers |= ModifierKeys::leftButtonModifier;
if ((wParam & MK_RBUTTON) != 0)
currentModifiers |= ModifierKeys::rightButtonModifier;
if ((wParam & MK_MBUTTON) != 0)
currentModifiers |= ModifierKeys::middleButtonModifier;
doMouseMove (position);
updateKeyModifiers();
updateModifiersFromWParam (wParam);
isDragging = true;
handleMouseDown (Point<int> (x, y), getMouseEventTime());
doMouseEvent (position);
}
void doMouseUp (const int x, const int y, const WPARAM wParam)
void doMouseUp (const Point<int>& position, const WPARAM wParam)
{
int numButtons = 0;
if ((wParam & MK_LBUTTON) != 0)
++numButtons;
if ((wParam & MK_RBUTTON) != 0)
++numButtons;
if ((wParam & MK_MBUTTON) != 0)
++numButtons;
const int oldModifiers = currentModifiers;
// update the currentmodifiers only after the callback, so the callback
// knows which button was released.
currentModifiers &= ~ModifierKeys::allMouseButtonModifiers;
if ((wParam & MK_LBUTTON) != 0)
currentModifiers |= ModifierKeys::leftButtonModifier;
if ((wParam & MK_RBUTTON) != 0)
currentModifiers |= ModifierKeys::rightButtonModifier;
if ((wParam & MK_MBUTTON) != 0)
currentModifiers |= ModifierKeys::middleButtonModifier;
updateKeyModifiers();
updateModifiersFromWParam (wParam);
isDragging = false;
// release the mouse capture if the user's not still got a button down
if (numButtons == 0 && hwnd == GetCapture())
// release the mouse capture if the user has released all buttons
if ((wParam & (MK_LBUTTON | MK_RBUTTON | MK_MBUTTON)) == 0 && hwnd == GetCapture())
ReleaseCapture();
handleMouseUp (oldModifiers, Point<int> (x, y), getMouseEventTime());
doMouseEvent (position);
}
void doCaptureChanged()
{
if (isDragging)
{
RECT wr;
GetWindowRect (hwnd, &wr);
const DWORD mp = GetMessagePos();
doMouseUp (GET_X_LPARAM (mp) - wr.left - windowBorder.getLeft(),
GET_Y_LPARAM (mp) - wr.top - windowBorder.getTop(),
(WPARAM) getMouseEventTime());
}
doMouseUp (getCurrentMousePos(), (WPARAM) 0);
}
void doMouseExit()
{
if (isMouseOver)
{
isMouseOver = false;
RECT wr;
GetWindowRect (hwnd, &wr);
const DWORD mp = GetMessagePos();
handleMouseExit (Point<int> (GET_X_LPARAM (mp) - wr.left - windowBorder.getLeft(),
GET_Y_LPARAM (mp) - wr.top - windowBorder.getTop()),
getMouseEventTime());
}
isMouseOver = false;
doMouseEvent (getCurrentMousePos());
}
void doMouseWheel (const WPARAM wParam, const bool isVertical)
void doMouseWheel (const Point<int>& position, const WPARAM wParam, const bool isVertical)
{
updateKeyModifiers();
const int amount = jlimit (-1000, 1000, (int) (0.75f * (short) HIWORD (wParam)));
const float amount = jlimit (-1000.0f, 1000.0f, 0.75f * HIWORD (wParam));
handleMouseWheel (isVertical ? 0 : amount,
isVertical ? amount : 0,
getMouseEventTime());
handleMouseWheel (position, getMouseEventTime(),
isVertical ? 0.0f : amount,
isVertical ? amount : 0.0f);
}
//==============================================================================
@@ -1592,7 +1486,7 @@ private:
key = (int) keyChar;
// avoid sending junk text characters for some control-key combinations
if (textChar < ' ' && (currentModifiers & (ModifierKeys::ctrlModifier | ModifierKeys::altModifier)) != 0)
if (textChar < ' ' && currentModifiers.testFlags (ModifierKeys::ctrlModifier | ModifierKeys::altModifier))
textChar = 0;
}
@@ -1784,6 +1678,21 @@ public:
}
private:
static const Point<int> getPointFromLParam (LPARAM lParam) throw()
{
return Point<int> (GET_X_LPARAM (lParam), GET_Y_LPARAM (lParam));
}
const Point<int> getCurrentMousePos() throw()
{
RECT wr;
GetWindowRect (hwnd, &wr);
const DWORD mp = GetMessagePos();
return Point<int> (GET_X_LPARAM (mp) - wr.left - windowBorder.getLeft(),
GET_Y_LPARAM (mp) - wr.top - windowBorder.getTop());
}
LRESULT peerWindowProc (HWND h, UINT message, WPARAM wParam, LPARAM lParam)
{
if (isValidPeer (this))
@@ -1823,7 +1732,7 @@ private:
//==============================================================================
case WM_MOUSEMOVE:
doMouseMove (GET_X_LPARAM (lParam), GET_Y_LPARAM (lParam));
doMouseMove (getPointFromLParam (lParam));
return 0;
case WM_MOUSELEAVE:
@@ -1833,13 +1742,13 @@ private:
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
doMouseDown (GET_X_LPARAM (lParam), GET_Y_LPARAM (lParam), wParam);
doMouseDown (getPointFromLParam (lParam), wParam);
return 0;
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
doMouseUp (GET_X_LPARAM (lParam), GET_Y_LPARAM (lParam), wParam);
doMouseUp (getPointFromLParam (lParam), wParam);
return 0;
case WM_CAPTURECHANGED:
@@ -1853,11 +1762,11 @@ private:
return 0;
case 0x020A: /* WM_MOUSEWHEEL */
doMouseWheel (wParam, true);
doMouseWheel (getCurrentMousePos(), wParam, true);
return 0;
case 0x020E: /* WM_MOUSEHWHEEL */
doMouseWheel (wParam, false);
doMouseWheel (getCurrentMousePos(), wParam, false);
return 0;
//==============================================================================
@@ -1967,7 +1876,7 @@ private:
component->repaint();
handleMovedOrResized();
if (! isValidMessageListener())
if (! ComponentPeer::isValidPeer (this))
return 0;
}
@@ -2042,31 +1951,31 @@ private:
}
else
{
const int oldModifiers = currentModifiers;
MouseEvent e (Point<int>(), ModifierKeys::getCurrentModifiersRealtime(), component,
getMouseEventTime(), Point<int>(), getMouseEventTime(), 1, false);
ModifierKeys eventMods (ModifierKeys::getCurrentModifiersRealtime());
if (lParam == WM_LBUTTONDOWN || lParam == WM_LBUTTONDBLCLK)
e.mods = ModifierKeys (e.mods.getRawFlags() | ModifierKeys::leftButtonModifier);
eventMods = eventMods.withFlags (ModifierKeys::leftButtonModifier);
else if (lParam == WM_RBUTTONDOWN || lParam == WM_RBUTTONDBLCLK)
e.mods = ModifierKeys (e.mods.getRawFlags() | ModifierKeys::rightButtonModifier);
eventMods = eventMods.withFlags (ModifierKeys::rightButtonModifier);
else if (lParam == WM_LBUTTONUP || lParam == WM_RBUTTONUP)
eventMods = eventMods.withoutMouseButtons();
const MouseEvent e (Desktop::getInstance().getMainMouseSource(),
Point<int>(), eventMods, component, getMouseEventTime(),
Point<int>(), getMouseEventTime(), 1, false);
if (lParam == WM_LBUTTONDOWN || lParam == WM_RBUTTONDOWN)
{
SetFocus (hwnd);
SetForegroundWindow (hwnd);
component->mouseDown (e);
}
else if (lParam == WM_LBUTTONUP || lParam == WM_RBUTTONUP)
{
e.mods = ModifierKeys (oldModifiers);
component->mouseUp (e);
}
else if (lParam == WM_LBUTTONDBLCLK || lParam == WM_LBUTTONDBLCLK)
{
e.mods = ModifierKeys (oldModifiers);
component->mouseDoubleClick (e);
}
else if (lParam == WM_MOUSEMOVE)
@@ -2216,6 +2125,9 @@ private:
Win32ComponentPeer& operator= (const Win32ComponentPeer&);
};
ModifierKeys Win32ComponentPeer::currentModifiers;
ModifierKeys Win32ComponentPeer::modifiersAtLastCallback;
ComponentPeer* Component::createNewPeer (int styleFlags, void* /*nativeWindowToAttachTo*/)
{
return new Win32ComponentPeer (this, styleFlags);
@@ -2223,6 +2135,28 @@ ComponentPeer* Component::createNewPeer (int styleFlags, void* /*nativeWindowToA
juce_ImplementSingleton_SingleThreaded (Win32ComponentPeer::WindowClassHolder);
//==============================================================================
void ModifierKeys::updateCurrentModifiers() throw()
{
currentModifiers = Win32ComponentPeer::currentModifiers;
}
const ModifierKeys ModifierKeys::getCurrentModifiersRealtime() throw()
{
Win32ComponentPeer::updateKeyModifiers();
int keyMods = 0;
if ((GetKeyState (VK_LBUTTON) & 0x8000) != 0) keyMods |= ModifierKeys::leftButtonModifier;
if ((GetKeyState (VK_RBUTTON) & 0x8000) != 0) keyMods |= ModifierKeys::rightButtonModifier;
if ((GetKeyState (VK_MBUTTON) & 0x8000) != 0) keyMods |= ModifierKeys::middleButtonModifier;
Win32ComponentPeer::currentModifiers
= Win32ComponentPeer::currentModifiers.withOnlyMouseButtons().withFlags (keyMods);
return Win32ComponentPeer::currentModifiers;
}
//==============================================================================
void SystemTrayIconComponent::setIconImage (const Image& newImage)
{


Loading…
Cancel
Save