LMMS
Loading...
Searching...
No Matches
juce_Component.cpp
Go to the documentation of this file.
1/*
2 ==============================================================================
3
4 This file is part of the JUCE library.
5 Copyright (c) 2022 - Raw Material Software Limited
6
7 JUCE is an open source library subject to commercial or open-source
8 licensing.
9
10 By using JUCE, you agree to the terms of both the JUCE 7 End-User License
11 Agreement and JUCE Privacy Policy.
12
13 End User License Agreement: www.juce.com/juce-7-licence
14 Privacy Policy: www.juce.com/juce-privacy-policy
15
16 Or: You may also use this code under the terms of the GPL v3 (see
17 www.gnu.org/licenses).
18
19 JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
20 EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
21 DISCLAIMED.
22
23 ==============================================================================
24*/
25
26namespace juce
27{
28
30{
31 if (in == nullptr)
32 return nullptr;
33
34 if (in->isEnabled())
35 return in;
36
37 return findFirstEnabledAncestor (in->getParentComponent());
38}
39
40Component* Component::currentlyFocusedComponent = nullptr;
41
42
43//==============================================================================
45{
46public:
48
49 void addListener (MouseListener* newListener, bool wantsEventsForAllNestedChildComponents)
50 {
51 if (! listeners.contains (newListener))
52 {
53 if (wantsEventsForAllNestedChildComponents)
54 {
55 listeners.insert (0, newListener);
57 }
58 else
59 {
60 listeners.add (newListener);
61 }
62 }
63 }
64
65 void removeListener (MouseListener* listenerToRemove)
66 {
67 auto index = listeners.indexOf (listenerToRemove);
68
69 if (index >= 0)
70 {
71 if (index < numDeepMouseListeners)
73
74 listeners.remove (index);
75 }
76 }
77
78 // g++ 4.8 cannot deduce the parameter pack inside the function pointer when it has more than one element
79 #if defined(__GNUC__) && __GNUC__ < 5 && ! defined(__clang__)
80 template <typename... Params>
81 static void sendMouseEvent (Component& comp, Component::BailOutChecker& checker,
82 void (MouseListener::*eventMethod) (const MouseEvent&),
83 Params... params)
84 {
85 sendMouseEvent <decltype (eventMethod), Params...> (comp, checker, eventMethod, params...);
86 }
87
88 template <typename... Params>
89 static void sendMouseEvent (Component& comp, Component::BailOutChecker& checker,
90 void (MouseListener::*eventMethod) (const MouseEvent&, const MouseWheelDetails&),
91 Params... params)
92 {
93 sendMouseEvent <decltype (eventMethod), Params...> (comp, checker, eventMethod, params...);
94 }
95
96 template <typename... Params>
97 static void sendMouseEvent (Component& comp, Component::BailOutChecker& checker,
98 void (MouseListener::*eventMethod) (const MouseEvent&, float),
99 Params... params)
100 {
101 sendMouseEvent <decltype (eventMethod), Params...> (comp, checker, eventMethod, params...);
102 }
103
104 template <typename EventMethod, typename... Params>
105 static void sendMouseEvent (Component& comp, Component::BailOutChecker& checker,
106 EventMethod eventMethod,
107 Params... params)
108 #else
109 template <typename... Params>
111 void (MouseListener::*eventMethod) (Params...),
112 Params... params)
113 #endif
114 {
115 if (checker.shouldBailOut())
116 return;
117
118 if (auto* list = comp.mouseListeners.get())
119 {
120 for (int i = list->listeners.size(); --i >= 0;)
121 {
122 (list->listeners.getUnchecked(i)->*eventMethod) (params...);
123
124 if (checker.shouldBailOut())
125 return;
126
127 i = jmin (i, list->listeners.size());
128 }
129 }
130
131 for (Component* p = comp.parentComponent; p != nullptr; p = p->parentComponent)
132 {
133 if (auto* list = p->mouseListeners.get())
134 {
135 if (list->numDeepMouseListeners > 0)
136 {
137 BailOutChecker2 checker2 (checker, p);
138
139 for (int i = list->numDeepMouseListeners; --i >= 0;)
140 {
141 (list->listeners.getUnchecked(i)->*eventMethod) (params...);
142
143 if (checker2.shouldBailOut())
144 return;
145
146 i = jmin (i, list->numDeepMouseListeners);
147 }
148 }
149 }
150 }
151 }
152
153private:
156
158 {
163
165 {
166 return checker.shouldBailOut() || safePointer == nullptr;
167 }
168
169 private:
172
174 };
175
177};
178
179//==============================================================================
181{
182 FocusRestorer() : lastFocus (Component::getCurrentlyFocusedComponent()) {}
183
185 {
186 if (lastFocus != nullptr
187 && lastFocus->isShowing()
188 && ! lastFocus->isCurrentlyBlockedByAnotherModalComponent())
189 lastFocus->grabKeyboardFocus();
190 }
191
193
195};
196
197//==============================================================================
199{
200 template <typename PointOrRect>
201 static PointOrRect unscaledScreenPosToScaled (float scale, PointOrRect pos) noexcept
202 {
203 return scale != 1.0f ? pos / scale : pos;
204 }
205
206 template <typename PointOrRect>
207 static PointOrRect scaledScreenPosToUnscaled (float scale, PointOrRect pos) noexcept
208 {
209 return scale != 1.0f ? pos * scale : pos;
210 }
211
212 // For these, we need to avoid getSmallestIntegerContainer being used, which causes
213 // judder when moving windows
214 static Rectangle<int> unscaledScreenPosToScaled (float scale, Rectangle<int> pos) noexcept
215 {
216 return scale != 1.0f ? Rectangle<int> (roundToInt ((float) pos.getX() / scale),
217 roundToInt ((float) pos.getY() / scale),
218 roundToInt ((float) pos.getWidth() / scale),
219 roundToInt ((float) pos.getHeight() / scale)) : pos;
220 }
221
222 static Rectangle<int> scaledScreenPosToUnscaled (float scale, Rectangle<int> pos) noexcept
223 {
224 return scale != 1.0f ? Rectangle<int> (roundToInt ((float) pos.getX() * scale),
225 roundToInt ((float) pos.getY() * scale),
226 roundToInt ((float) pos.getWidth() * scale),
227 roundToInt ((float) pos.getHeight() * scale)) : pos;
228 }
229
231 {
232 return scale != 1.0f ? Rectangle<float> (pos.getX() / scale,
233 pos.getY() / scale,
234 pos.getWidth() / scale,
235 pos.getHeight() / scale) : pos;
236 }
237
239 {
240 return scale != 1.0f ? Rectangle<float> (pos.getX() * scale,
241 pos.getY() * scale,
242 pos.getWidth() * scale,
243 pos.getHeight() * scale) : pos;
244 }
245
246 template <typename PointOrRect>
247 static PointOrRect unscaledScreenPosToScaled (PointOrRect pos) noexcept
248 {
249 return unscaledScreenPosToScaled (Desktop::getInstance().getGlobalScaleFactor(), pos);
250 }
251
252 template <typename PointOrRect>
253 static PointOrRect scaledScreenPosToUnscaled (PointOrRect pos) noexcept
254 {
255 return scaledScreenPosToUnscaled (Desktop::getInstance().getGlobalScaleFactor(), pos);
256 }
257
258 template <typename PointOrRect>
259 static PointOrRect unscaledScreenPosToScaled (const Component& comp, PointOrRect pos) noexcept
260 {
261 return unscaledScreenPosToScaled (comp.getDesktopScaleFactor(), pos);
262 }
263
264 template <typename PointOrRect>
265 static PointOrRect scaledScreenPosToUnscaled (const Component& comp, PointOrRect pos) noexcept
266 {
267 return scaledScreenPosToUnscaled (comp.getDesktopScaleFactor(), pos);
268 }
269
270 static Point<int> addPosition (Point<int> p, const Component& c) noexcept { return p + c.getPosition(); }
271 static Rectangle<int> addPosition (Rectangle<int> p, const Component& c) noexcept { return p + c.getPosition(); }
272 static Point<float> addPosition (Point<float> p, const Component& c) noexcept { return p + c.getPosition().toFloat(); }
273 static Rectangle<float> addPosition (Rectangle<float> p, const Component& c) noexcept { return p + c.getPosition().toFloat(); }
274 static Point<int> subtractPosition (Point<int> p, const Component& c) noexcept { return p - c.getPosition(); }
275 static Rectangle<int> subtractPosition (Rectangle<int> p, const Component& c) noexcept { return p - c.getPosition(); }
276 static Point<float> subtractPosition (Point<float> p, const Component& c) noexcept { return p - c.getPosition().toFloat(); }
277 static Rectangle<float> subtractPosition (Rectangle<float> p, const Component& c) noexcept { return p - c.getPosition().toFloat(); }
278
280 {
281 if (auto* peer = comp.getPeer())
282 {
283 pos = peer->globalToLocal (pos);
284 auto& peerComp = peer->getComponent();
285 return comp.getLocalPoint (&peerComp, unscaledScreenPosToScaled (peerComp, pos));
286 }
287
288 return comp.getLocalPoint (nullptr, unscaledScreenPosToScaled (comp, pos));
289 }
290};
291
292static const char colourPropertyPrefix[] = "jcclr_";
293
294//==============================================================================
296{
297 #if JUCE_MODAL_LOOPS_PERMITTED
298 static void* runModalLoopCallback (void* userData)
299 {
300 return (void*) (pointer_sized_int) static_cast<Component*> (userData)->runModalLoop();
301 }
302 #endif
303
304 static Identifier getColourPropertyID (int colourID)
305 {
306 char buffer[32];
307 auto* end = buffer + numElementsInArray (buffer) - 1;
308 auto* t = end;
309 *t = 0;
310
311 for (auto v = (uint32) colourID;;)
312 {
313 *--t = "0123456789abcdef" [v & 15];
314 v >>= 4;
315
316 if (v == 0)
317 break;
318 }
319
320 for (int i = (int) sizeof (colourPropertyPrefix) - 1; --i >= 0;)
322
323 return t;
324 }
325
326 //==============================================================================
327 static bool hitTest (Component& comp, Point<float> localPoint)
328 {
329 const auto intPoint = localPoint.roundToInt();
330 return Rectangle<int> { comp.getWidth(), comp.getHeight() }.contains (intPoint)
331 && comp.hitTest (intPoint.x, intPoint.y);
332 }
333
334 // converts an unscaled position within a peer to the local position within that peer's component
335 template <typename PointOrRect>
336 static PointOrRect rawPeerPositionToLocal (const Component& comp, PointOrRect pos) noexcept
337 {
338 if (comp.isTransformed())
339 pos = pos.transformedBy (comp.getTransform().inverted());
340
342 }
343
344 // converts a position within a peer's component to the unscaled position within the peer
345 template <typename PointOrRect>
346 static PointOrRect localPositionToRawPeerPos (const Component& comp, PointOrRect pos) noexcept
347 {
348 if (comp.isTransformed())
349 pos = pos.transformedBy (comp.getTransform());
350
352 }
353
354 template <typename PointOrRect>
355 static PointOrRect convertFromParentSpace (const Component& comp, const PointOrRect pointInParentSpace)
356 {
357 const auto transformed = comp.affineTransform != nullptr ? pointInParentSpace.transformedBy (comp.affineTransform->inverted())
358 : pointInParentSpace;
359
360 if (comp.isOnDesktop())
361 {
362 if (auto* peer = comp.getPeer())
364
366 return transformed;
367 }
368
369 if (comp.getParentComponent() == nullptr)
371
372 return ScalingHelpers::subtractPosition (transformed, comp);
373 }
374
375 template <typename PointOrRect>
376 static PointOrRect convertToParentSpace (const Component& comp, const PointOrRect pointInLocalSpace)
377 {
378 const auto preTransform = [&]
379 {
380 if (comp.isOnDesktop())
381 {
382 if (auto* peer = comp.getPeer())
383 return ScalingHelpers::unscaledScreenPosToScaled (peer->localToGlobal (ScalingHelpers::scaledScreenPosToUnscaled (comp, pointInLocalSpace)));
384
386 return pointInLocalSpace;
387 }
388
389 if (comp.getParentComponent() == nullptr)
391
392 return ScalingHelpers::addPosition (pointInLocalSpace, comp);
393 }();
394
395 return comp.affineTransform != nullptr ? preTransform.transformedBy (*comp.affineTransform)
396 : preTransform;
397 }
398
399 template <typename PointOrRect>
400 static PointOrRect convertFromDistantParentSpace (const Component* parent, const Component& target, PointOrRect coordInParent)
401 {
402 auto* directParent = target.getParentComponent();
403 jassert (directParent != nullptr);
404
405 if (directParent == parent)
406 return convertFromParentSpace (target, coordInParent);
407
409 return convertFromParentSpace (target, convertFromDistantParentSpace (parent, *directParent, coordInParent));
411 }
412
413 template <typename PointOrRect>
414 static PointOrRect convertCoordinate (const Component* target, const Component* source, PointOrRect p)
415 {
416 while (source != nullptr)
417 {
418 if (source == target)
419 return p;
420
422
423 if (source->isParentOf (target))
424 return convertFromDistantParentSpace (source, *target, p);
425
427
428 p = convertToParentSpace (*source, p);
429 source = source->getParentComponent();
430 }
431
432 jassert (source == nullptr);
433 if (target == nullptr)
434 return p;
435
436 auto* topLevelComp = target->getTopLevelComponent();
437
438 p = convertFromParentSpace (*topLevelComp, p);
439
440 if (topLevelComp == target)
441 return p;
442
443 return convertFromDistantParentSpace (topLevelComp, *target, p);
444 }
445
447 const Rectangle<int> clipRect, Point<int> delta)
448 {
449 bool wasClipped = false;
450
451 for (int i = comp.childComponentList.size(); --i >= 0;)
452 {
453 auto& child = *comp.childComponentList.getUnchecked(i);
454
455 if (child.isVisible() && ! child.isTransformed())
456 {
457 auto newClip = clipRect.getIntersection (child.boundsRelativeToParent);
458
459 if (! newClip.isEmpty())
460 {
461 if (child.isOpaque() && child.componentTransparency == 0)
462 {
463 g.excludeClipRegion (newClip + delta);
464 wasClipped = true;
465 }
466 else
467 {
468 auto childPos = child.getPosition();
469
470 if (clipObscuredRegions (child, g, newClip - childPos, childPos + delta))
471 wasClipped = true;
472 }
473 }
474 }
475 }
476
477 return wasClipped;
478 }
479
481 {
482 if (auto* p = comp.getParentComponent())
483 return p->getLocalBounds();
484
485 return Desktop::getInstance().getDisplays().getPrimaryDisplay()->userArea;
486 }
487
489 {
490 if (auto* cached = c.getCachedComponentImage())
491 cached->releaseResources();
492
493 for (auto* child : c.childComponentList)
495 }
496
497 //==============================================================================
498 static bool modalWouldBlockComponent (const Component& maybeBlocked, Component* modal)
499 {
500 return modal != nullptr
501 && modal != &maybeBlocked
502 && ! modal->isParentOf (&maybeBlocked)
503 && ! modal->canModalEventBeSentToComponent (&maybeBlocked);
504 }
505
506 template <typename Function>
508 {
509 for (auto& ms : Desktop::getInstance().getMouseSources())
510 if (auto* c = ms.getComponentUnderMouse())
511 if (modalWouldBlockComponent (*c, &modal))
512 (c->*function) (ms, ScalingHelpers::screenPosToLocalPos (*c, ms.getScreenPosition()), Time::getCurrentTime());
513 }
514};
515
516//==============================================================================
521
526
528{
529 static_assert (sizeof (flags) <= sizeof (componentFlags), "componentFlags has too many bits!");
530
531 componentListeners.call ([this] (ComponentListener& l) { l.componentBeingDeleted (*this); });
532
533 while (childComponentList.size() > 0)
534 removeChildComponent (childComponentList.size() - 1, false, true);
535
536 masterReference.clear();
537
538 if (parentComponent != nullptr)
539 parentComponent->removeChildComponent (parentComponent->childComponentList.indexOf (this), true, false);
540 else
542
543 if (flags.hasHeavyweightPeerFlag)
545
546 // Something has added some children to this component during its destructor! Not a smart idea!
547 jassert (childComponentList.size() == 0);
548}
549
550//==============================================================================
552{
553 // if component methods are being called from threads other than the message
554 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
556
557 if (componentName != name)
558 {
560
561 if (flags.hasHeavyweightPeerFlag)
562 if (auto* peer = getPeer())
563 peer->setTitle (name);
564
565 BailOutChecker checker (this);
566 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentNameChanged (*this); });
567 }
568}
569
571{
572 componentID = newID;
573}
574
575void Component::setVisible (bool shouldBeVisible)
576{
577 if (flags.visibleFlag != shouldBeVisible)
578 {
579 // if component methods are being called from threads other than the message
580 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
582
583 const WeakReference<Component> safePointer (this);
584 flags.visibleFlag = shouldBeVisible;
585
586 if (shouldBeVisible)
587 repaint();
588 else
590
592
593 if (! shouldBeVisible)
594 {
596
597 if (hasKeyboardFocus (true))
598 {
599 if (parentComponent != nullptr)
600 parentComponent->grabKeyboardFocus();
601
602 // ensure that keyboard focus is given away if it wasn't taken by parent
604 }
605 }
606
607 if (safePointer != nullptr)
608 {
610
611 if (safePointer != nullptr && flags.hasHeavyweightPeerFlag)
612 {
613 if (auto* peer = getPeer())
614 {
615 peer->setVisible (shouldBeVisible);
617 }
618 }
619 }
620 }
621}
622
624
626{
627 BailOutChecker checker (this);
629
630 if (! checker.shouldBailOut())
631 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentVisibilityChanged (*this); });
632}
633
635{
636 if (! flags.visibleFlag)
637 return false;
638
639 if (parentComponent != nullptr)
640 return parentComponent->isShowing();
641
642 if (auto* peer = getPeer())
643 return ! peer->isMinimised();
644
645 return false;
646}
647
648//==============================================================================
650{
651 if (auto* peer = getPeer())
652 return peer->getNativeHandle();
653
654 return nullptr;
655}
656
657//==============================================================================
658void Component::addToDesktop (int styleWanted, void* nativeWindowToAttachTo)
659{
660 // if component methods are being called from threads other than the message
661 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
663
664 if (isOpaque())
665 styleWanted &= ~ComponentPeer::windowIsSemiTransparent;
666 else
668
669 // don't use getPeer(), so that we only get the peer that's specifically
670 // for this comp, and not for one of its parents.
671 auto* peer = ComponentPeer::getPeerFor (this);
672
673 if (peer == nullptr || styleWanted != peer->getStyleFlags())
674 {
675 const WeakReference<Component> safePointer (this);
676
677 #if JUCE_LINUX || JUCE_BSD
678 // it's wise to give the component a non-zero size before
679 // putting it on the desktop, as X windows get confused by this, and
680 // a (1, 1) minimum size is enforced here.
681 setSize (jmax (1, getWidth()),
682 jmax (1, getHeight()));
683 #endif
684
685 const auto unscaledPosition = ScalingHelpers::scaledScreenPosToUnscaled (getScreenPosition());
686 const auto topLeft = ScalingHelpers::unscaledScreenPosToScaled (*this, unscaledPosition);
687
688 bool wasFullscreen = false;
689 bool wasMinimised = false;
690 ComponentBoundsConstrainer* currentConstrainer = nullptr;
691 Rectangle<int> oldNonFullScreenBounds;
692 int oldRenderingEngine = -1;
693
694 if (peer != nullptr)
695 {
696 std::unique_ptr<ComponentPeer> oldPeerToDelete (peer);
697
698 wasFullscreen = peer->isFullScreen();
699 wasMinimised = peer->isMinimised();
700 currentConstrainer = peer->getConstrainer();
701 oldNonFullScreenBounds = peer->getNonFullScreenBounds();
702 oldRenderingEngine = peer->getCurrentRenderingEngine();
703
704 flags.hasHeavyweightPeerFlag = false;
705 Desktop::getInstance().removeDesktopComponent (this);
706 internalHierarchyChanged(); // give comps a chance to react to the peer change before the old peer is deleted.
707
708 if (safePointer == nullptr)
709 return;
710
711 setTopLeftPosition (topLeft);
712 }
713
714 if (parentComponent != nullptr)
715 parentComponent->removeChildComponent (this);
716
717 if (safePointer != nullptr)
718 {
719 flags.hasHeavyweightPeerFlag = true;
720
721 peer = createNewPeer (styleWanted, nativeWindowToAttachTo);
722
723 Desktop::getInstance().addDesktopComponent (this);
724
725 boundsRelativeToParent.setPosition (topLeft);
726 peer->updateBounds();
727
728 if (oldRenderingEngine >= 0)
729 peer->setCurrentRenderingEngine (oldRenderingEngine);
730
731 peer->setVisible (isVisible());
732
733 peer = ComponentPeer::getPeerFor (this);
734
735 if (peer == nullptr)
736 return;
737
738 if (wasFullscreen)
739 {
740 peer->setFullScreen (true);
741 peer->setNonFullScreenBounds (oldNonFullScreenBounds);
742 }
743
744 if (wasMinimised)
745 peer->setMinimised (true);
746
747 #if JUCE_WINDOWS
748 if (isAlwaysOnTop())
749 peer->setAlwaysOnTop (true);
750 #endif
751
752 peer->setConstrainer (currentConstrainer);
753
754 repaint();
755
756 #if JUCE_LINUX
757 // Creating the peer Image on Linux will change the reported position of the window. If
758 // the Image creation is interleaved with the coming configureNotifyEvents the window
759 // will appear in the wrong position. To avoid this, we force the Image creation here,
760 // before handling any of the configureNotifyEvents. The Linux implementation of
761 // performAnyPendingRepaintsNow() will force update the peer position if necessary.
762 peer->performAnyPendingRepaintsNow();
763 #endif
764
766
767 if (auto* handler = getAccessibilityHandler())
769 }
770 }
771}
772
774{
775 // if component methods are being called from threads other than the message
776 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
778
779 if (flags.hasHeavyweightPeerFlag)
780 {
781 if (auto* handler = getAccessibilityHandler())
783
785
786 auto* peer = ComponentPeer::getPeerFor (this);
787 jassert (peer != nullptr);
788
789 flags.hasHeavyweightPeerFlag = false;
790 delete peer;
791
792 Desktop::getInstance().removeDesktopComponent (this);
793 }
794}
795
797{
798 return flags.hasHeavyweightPeerFlag;
799}
800
802{
803 if (flags.hasHeavyweightPeerFlag)
804 return ComponentPeer::getPeerFor (this);
805
806 if (parentComponent == nullptr)
807 return nullptr;
808
809 return parentComponent->getPeer();
810}
811
813{
814 /* This means that the user's trying to get rid of your window with the 'close window' system
815 menu option (on windows) or possibly the task manager - you should really handle this
816 and delete or hide your component in an appropriate way.
817
818 If you want to ignore the event and don't want to trigger this assertion, just override
819 this method and do nothing.
820 */
822}
823
825
826float Component::getDesktopScaleFactor() const { return Desktop::getInstance().getGlobalScaleFactor(); }
827
828//==============================================================================
829void Component::setOpaque (bool shouldBeOpaque)
830{
831 if (shouldBeOpaque != flags.opaqueFlag)
832 {
833 flags.opaqueFlag = shouldBeOpaque;
834
835 if (flags.hasHeavyweightPeerFlag)
836 if (auto* peer = ComponentPeer::getPeerFor (this))
837 addToDesktop (peer->getStyleFlags()); // recreates the heavyweight window
838
839 repaint();
840 }
841}
842
844{
845 return flags.opaqueFlag;
846}
847
848//==============================================================================
850{
852
853 void paint (Graphics& g) override
854 {
855 scale = g.getInternalContext().getPhysicalPixelScaleFactor();
856 auto compBounds = owner.getLocalBounds();
857 auto imageBounds = compBounds * scale;
858
859 if (image.isNull() || image.getBounds() != imageBounds)
860 {
861 image = Image (owner.isOpaque() ? Image::RGB
862 : Image::ARGB,
863 jmax (1, imageBounds.getWidth()),
864 jmax (1, imageBounds.getHeight()),
865 ! owner.isOpaque());
866
867 validArea.clear();
868 }
869
870 if (! validArea.containsRectangle (compBounds))
871 {
872 Graphics imG (image);
873 auto& lg = imG.getInternalContext();
874
876
877 for (auto& i : validArea)
878 lg.excludeClipRectangle (i);
879
880 if (! owner.isOpaque())
881 {
882 lg.setFill (Colours::transparentBlack);
883 lg.fillRect (compBounds, true);
884 lg.setFill (Colours::black);
885 }
886
887 owner.paintEntireComponent (imG, true);
888 }
889
890 validArea = compBounds;
891
892 g.setColour (Colours::black.withAlpha (owner.getAlpha()));
893 g.drawImageTransformed (image, AffineTransform::scale ((float) compBounds.getWidth() / (float) imageBounds.getWidth(),
894 (float) compBounds.getHeight() / (float) imageBounds.getHeight()), false);
895 }
896
897 bool invalidateAll() override { validArea.clear(); return true; }
898 bool invalidate (const Rectangle<int>& area) override { validArea.subtract (area); return true; }
899 void releaseResources() override { image = Image(); }
900
901private:
905 float scale = 1.0f;
906
908};
909
911{
912 if (cachedImage.get() != newCachedImage)
913 {
914 cachedImage.reset (newCachedImage);
915 repaint();
916 }
917}
918
919void Component::setBufferedToImage (bool shouldBeBuffered)
920{
921 // This assertion means that this component is already using a custom CachedComponentImage,
922 // so by calling setBufferedToImage, you'll be deleting the custom one - this is almost certainly
923 // not what you wanted to happen... If you really do know what you're doing here, and want to
924 // avoid this assertion, just call setCachedComponentImage (nullptr) before setBufferedToImage().
925 jassert (cachedImage == nullptr || dynamic_cast<StandardCachedComponentImage*> (cachedImage.get()) != nullptr);
926
927 if (shouldBeBuffered)
928 {
929 if (cachedImage == nullptr)
930 cachedImage.reset (new StandardCachedComponentImage (*this));
931 }
932 else
933 {
934 cachedImage.reset();
935 }
936}
937
938//==============================================================================
939void Component::reorderChildInternal (int sourceIndex, int destIndex)
940{
941 if (sourceIndex != destIndex)
942 {
943 auto* c = childComponentList.getUnchecked (sourceIndex);
944 jassert (c != nullptr);
945 c->repaintParent();
946
947 childComponentList.move (sourceIndex, destIndex);
948
951 }
952}
953
954void Component::toFront (bool shouldGrabKeyboardFocus)
955{
956 // if component methods are being called from threads other than the message
957 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
959
960 if (flags.hasHeavyweightPeerFlag)
961 {
962 if (auto* peer = getPeer())
963 {
964 peer->toFront (shouldGrabKeyboardFocus);
965
966 if (shouldGrabKeyboardFocus && ! hasKeyboardFocus (true))
968 }
969 }
970 else if (parentComponent != nullptr)
971 {
972 auto& childList = parentComponent->childComponentList;
973
974 if (childList.getLast() != this)
975 {
976 auto index = childList.indexOf (this);
977
978 if (index >= 0)
979 {
980 int insertIndex = -1;
981
982 if (! flags.alwaysOnTopFlag)
983 {
984 insertIndex = childList.size() - 1;
985
986 while (insertIndex > 0 && childList.getUnchecked (insertIndex)->isAlwaysOnTop())
987 --insertIndex;
988 }
989
990 parentComponent->reorderChildInternal (index, insertIndex);
991 }
992 }
993
994 if (shouldGrabKeyboardFocus)
995 {
997
998 if (isShowing())
1000 }
1001 }
1002}
1003
1005{
1006 if (other != nullptr && other != this)
1007 {
1008 // the two components must belong to the same parent..
1010
1011 if (parentComponent != nullptr)
1012 {
1013 auto& childList = parentComponent->childComponentList;
1014 auto index = childList.indexOf (this);
1015
1016 if (index >= 0 && childList [index + 1] != other)
1017 {
1018 auto otherIndex = childList.indexOf (other);
1019
1020 if (otherIndex >= 0)
1021 {
1022 if (index < otherIndex)
1023 --otherIndex;
1024
1025 parentComponent->reorderChildInternal (index, otherIndex);
1026 }
1027 }
1028 }
1029 else if (isOnDesktop())
1030 {
1031 jassert (other->isOnDesktop());
1032
1033 if (other->isOnDesktop())
1034 {
1035 auto* us = getPeer();
1036 auto* them = other->getPeer();
1037 jassert (us != nullptr && them != nullptr);
1038
1039 if (us != nullptr && them != nullptr)
1040 us->toBehind (them);
1041 }
1042 }
1043 }
1044}
1045
1047{
1048 if (isOnDesktop())
1049 {
1050 jassertfalse; //xxx need to add this to native window
1051 }
1052 else if (parentComponent != nullptr)
1053 {
1054 auto& childList = parentComponent->childComponentList;
1055
1056 if (childList.getFirst() != this)
1057 {
1058 auto index = childList.indexOf (this);
1059
1060 if (index > 0)
1061 {
1062 int insertIndex = 0;
1063
1064 if (flags.alwaysOnTopFlag)
1065 while (insertIndex < childList.size() && ! childList.getUnchecked (insertIndex)->isAlwaysOnTop())
1066 ++insertIndex;
1067
1068 parentComponent->reorderChildInternal (index, insertIndex);
1069 }
1070 }
1071 }
1072}
1073
1074void Component::setAlwaysOnTop (bool shouldStayOnTop)
1075{
1076 if (shouldStayOnTop != flags.alwaysOnTopFlag)
1077 {
1078 BailOutChecker checker (this);
1079
1080 flags.alwaysOnTopFlag = shouldStayOnTop;
1081
1082 if (isOnDesktop())
1083 {
1084 if (auto* peer = getPeer())
1085 {
1086 if (! peer->setAlwaysOnTop (shouldStayOnTop))
1087 {
1088 // some kinds of peer can't change their always-on-top status, so
1089 // for these, we'll need to create a new window
1090 auto oldFlags = peer->getStyleFlags();
1092 addToDesktop (oldFlags);
1093 }
1094 }
1095 }
1096
1097 if (shouldStayOnTop && ! checker.shouldBailOut())
1098 toFront (false);
1099
1100 if (! checker.shouldBailOut())
1102 }
1103}
1104
1106{
1107 return flags.alwaysOnTopFlag;
1108}
1109
1110//==============================================================================
1111int Component::proportionOfWidth (float proportion) const noexcept { return roundToInt (proportion * (float) boundsRelativeToParent.getWidth()); }
1112int Component::proportionOfHeight (float proportion) const noexcept { return roundToInt (proportion * (float) boundsRelativeToParent.getHeight()); }
1113
1115{
1116 return parentComponent != nullptr ? parentComponent->getWidth()
1117 : getParentMonitorArea().getWidth();
1118}
1119
1121{
1122 return parentComponent != nullptr ? parentComponent->getHeight()
1123 : getParentMonitorArea().getHeight();
1124}
1125
1127{
1128 return Desktop::getInstance().getDisplays().getDisplayForRect (getScreenBounds())->userArea;
1129}
1130
1131int Component::getScreenX() const { return getScreenPosition().x; }
1132int Component::getScreenY() const { return getScreenPosition().y; }
1135
1136Point<int> Component::getLocalPoint (const Component* source, Point<int> point) const { return ComponentHelpers::convertCoordinate (this, source, point); }
1137Point<float> Component::getLocalPoint (const Component* source, Point<float> point) const { return ComponentHelpers::convertCoordinate (this, source, point); }
1140
1145
1146//==============================================================================
1147void Component::setBounds (int x, int y, int w, int h)
1148{
1149 // if component methods are being called from threads other than the message
1150 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
1152
1153 if (w < 0) w = 0;
1154 if (h < 0) h = 0;
1155
1156 const bool wasResized = (getWidth() != w || getHeight() != h);
1157 const bool wasMoved = (getX() != x || getY() != y);
1158
1159 #if JUCE_DEBUG
1160 // It's a very bad idea to try to resize a window during its paint() method!
1161 jassert (! (flags.isInsidePaintCall && wasResized && isOnDesktop()));
1162 #endif
1163
1164 if (wasMoved || wasResized)
1165 {
1166 const bool showing = isShowing();
1167
1168 if (showing)
1169 {
1170 // send a fake mouse move to trigger enter/exit messages if needed..
1172
1173 if (! flags.hasHeavyweightPeerFlag)
1174 repaintParent();
1175 }
1176
1177 boundsRelativeToParent.setBounds (x, y, w, h);
1178
1179 if (showing)
1180 {
1181 if (wasResized)
1182 repaint();
1183 else if (! flags.hasHeavyweightPeerFlag)
1184 repaintParent();
1185 }
1186 else if (cachedImage != nullptr)
1187 {
1188 cachedImage->invalidateAll();
1189 }
1190
1191 flags.isMoveCallbackPending = wasMoved;
1192 flags.isResizeCallbackPending = wasResized;
1193
1194 if (flags.hasHeavyweightPeerFlag)
1195 if (auto* peer = getPeer())
1196 peer->updateBounds();
1197
1199 }
1200}
1201
1203{
1204 const bool wasMoved = flags.isMoveCallbackPending;
1205 const bool wasResized = flags.isResizeCallbackPending;
1206
1207 if (wasMoved || wasResized)
1208 {
1209 flags.isMoveCallbackPending = false;
1210 flags.isResizeCallbackPending = false;
1211
1212 sendMovedResizedMessages (wasMoved, wasResized);
1213 }
1214}
1215
1216void Component::sendMovedResizedMessages (bool wasMoved, bool wasResized)
1217{
1218 BailOutChecker checker (this);
1219
1220 if (wasMoved)
1221 {
1222 moved();
1223
1224 if (checker.shouldBailOut())
1225 return;
1226 }
1227
1228 if (wasResized)
1229 {
1230 resized();
1231
1232 if (checker.shouldBailOut())
1233 return;
1234
1235 for (int i = childComponentList.size(); --i >= 0;)
1236 {
1237 childComponentList.getUnchecked(i)->parentSizeChanged();
1238
1239 if (checker.shouldBailOut())
1240 return;
1241
1242 i = jmin (i, childComponentList.size());
1243 }
1244 }
1245
1246 if (parentComponent != nullptr)
1247 parentComponent->childBoundsChanged (this);
1248
1249 if (! checker.shouldBailOut())
1250 {
1251 componentListeners.callChecked (checker, [this, wasMoved, wasResized] (ComponentListener& l)
1252 {
1253 l.componentMovedOrResized (*this, wasMoved, wasResized);
1254 });
1255 }
1256
1257 if ((wasMoved || wasResized) && ! checker.shouldBailOut())
1258 if (auto* handler = getAccessibilityHandler())
1260}
1261
1262void Component::setSize (int w, int h) { setBounds (getX(), getY(), w, h); }
1263
1266
1268void Component::setBounds (Rectangle<int> r) { setBounds (r.getX(), r.getY(), r.getWidth(), r.getHeight()); }
1269
1270void Component::setCentrePosition (Point<int> p) { setBounds (getBounds().withCentre (p.transformedBy (getTransform().inverted()))); }
1272
1274{
1276 roundToInt ((float) getParentHeight() * y));
1277}
1278
1280{
1281 setBounds ((target * Point<float> ((float) getParentWidth(),
1282 (float) getParentHeight())).toNearestInt());
1283}
1284
1285void Component::setBoundsRelative (float x, float y, float w, float h)
1286{
1287 setBoundsRelative ({ x, y, w, h });
1288}
1289
1291{
1292 auto parentArea = ComponentHelpers::getParentOrMainMonitorBounds (*this)
1293 .transformedBy (getTransform().inverted());
1294
1295 setBounds (parentArea.getCentreX() - width / 2,
1296 parentArea.getCentreY() - height / 2,
1297 width, height);
1298}
1299
1304
1305void Component::setBoundsToFit (Rectangle<int> targetArea, Justification justification, bool onlyReduceInSize)
1306{
1307 if (getLocalBounds().isEmpty() || targetArea.isEmpty())
1308 {
1309 // it's no good calling this method unless both the component and
1310 // target rectangle have a finite size.
1312 return;
1313 }
1314
1315 auto sourceArea = targetArea.withZeroOrigin();
1316
1317 if (onlyReduceInSize
1318 && getWidth() <= targetArea.getWidth()
1319 && getHeight() <= targetArea.getHeight())
1320 {
1321 sourceArea = getLocalBounds();
1322 }
1323 else
1324 {
1325 auto sourceRatio = getHeight() / (double) getWidth();
1326 auto targetRatio = targetArea.getHeight() / (double) targetArea.getWidth();
1327
1328 if (sourceRatio <= targetRatio)
1329 sourceArea.setHeight (jmin (targetArea.getHeight(),
1330 roundToInt (targetArea.getWidth() * sourceRatio)));
1331 else
1332 sourceArea.setWidth (jmin (targetArea.getWidth(),
1333 roundToInt (targetArea.getHeight() / sourceRatio)));
1334 }
1335
1336 if (! sourceArea.isEmpty())
1337 setBounds (justification.appliedToRectangle (sourceArea, targetArea));
1338}
1339
1340//==============================================================================
1342{
1343 // If you pass in a transform with no inverse, the component will have no dimensions,
1344 // and there will be all sorts of maths errors when converting coordinates.
1345 jassert (! newTransform.isSingularity());
1346
1347 if (newTransform.isIdentity())
1348 {
1349 if (affineTransform != nullptr)
1350 {
1351 repaint();
1352 affineTransform.reset();
1353 repaint();
1354 sendMovedResizedMessages (false, false);
1355 }
1356 }
1357 else if (affineTransform == nullptr)
1358 {
1359 repaint();
1360 affineTransform.reset (new AffineTransform (newTransform));
1361 repaint();
1362 sendMovedResizedMessages (false, false);
1363 }
1364 else if (*affineTransform != newTransform)
1365 {
1366 repaint();
1367 *affineTransform = newTransform;
1368 repaint();
1369 sendMovedResizedMessages (false, false);
1370 }
1371}
1372
1374{
1375 return affineTransform != nullptr;
1376}
1377
1382
1384{
1385 AffineTransform transform;
1386
1387 for (auto* target = targetComponent; target != nullptr; target = target->getParentComponent())
1388 {
1389 transform = transform.followedBy (target->getTransform());
1390
1391 if (target->isOnDesktop())
1392 transform = transform.scaled (target->getDesktopScaleFactor());
1393 }
1394
1395 auto transformScale = std::sqrt (std::abs (transform.getDeterminant()));
1396 return transformScale / Desktop::getInstance().getGlobalScaleFactor();
1397}
1398
1399//==============================================================================
1400bool Component::hitTest (int x, int y)
1401{
1402 if (! flags.ignoresMouseClicksFlag)
1403 return true;
1404
1405 if (flags.allowChildMouseClicksFlag)
1406 {
1407 for (int i = childComponentList.size(); --i >= 0;)
1408 {
1409 auto& child = *childComponentList.getUnchecked (i);
1410
1411 if (child.isVisible()
1413 return true;
1414 }
1415 }
1416
1417 return false;
1418}
1419
1421 bool allowClicksOnChildComponents) noexcept
1422{
1423 flags.ignoresMouseClicksFlag = ! allowClicks;
1424 flags.allowChildMouseClicksFlag = allowClicksOnChildComponents;
1425}
1426
1427void Component::getInterceptsMouseClicks (bool& allowsClicksOnThisComponent,
1428 bool& allowsClicksOnChildComponents) const noexcept
1429{
1430 allowsClicksOnThisComponent = ! flags.ignoresMouseClicksFlag;
1431 allowsClicksOnChildComponents = flags.allowChildMouseClicksFlag;
1432}
1433
1435{
1436 return contains (point.toFloat());
1437}
1438
1440{
1441 if (ComponentHelpers::hitTest (*this, point))
1442 {
1443 if (parentComponent != nullptr)
1444 return parentComponent->contains (ComponentHelpers::convertToParentSpace (*this, point));
1445
1446 if (flags.hasHeavyweightPeerFlag)
1447 if (auto* peer = getPeer())
1448 return peer->contains (ComponentHelpers::localPositionToRawPeerPos (*this, point).roundToInt(), true);
1449 }
1450
1451 return false;
1452}
1453
1454bool Component::reallyContains (Point<int> point, bool returnTrueIfWithinAChild)
1455{
1456 return reallyContains (point.toFloat(), returnTrueIfWithinAChild);
1457}
1458
1459bool Component::reallyContains (Point<float> point, bool returnTrueIfWithinAChild)
1460{
1461 if (! contains (point))
1462 return false;
1463
1464 auto* top = getTopLevelComponent();
1465 auto* compAtPosition = top->getComponentAt (top->getLocalPoint (this, point));
1466
1467 return (compAtPosition == this) || (returnTrueIfWithinAChild && isParentOf (compAtPosition));
1468}
1469
1471{
1472 return getComponentAt (position.toFloat());
1473}
1474
1476{
1477 if (flags.visibleFlag && ComponentHelpers::hitTest (*this, position))
1478 {
1479 for (int i = childComponentList.size(); --i >= 0;)
1480 {
1481 auto* child = childComponentList.getUnchecked (i);
1482
1483 child = child->getComponentAt (ComponentHelpers::convertFromParentSpace (*child, position));
1484
1485 if (child != nullptr)
1486 return child;
1487 }
1488
1489 return this;
1490 }
1491
1492 return nullptr;
1493}
1494
1496{
1497 return getComponentAt (Point<int> { x, y });
1498}
1499
1500//==============================================================================
1502{
1503 // if component methods are being called from threads other than the message
1504 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
1506
1507 jassert (this != &child); // adding a component to itself!?
1508
1509 if (child.parentComponent != this)
1510 {
1511 if (child.parentComponent != nullptr)
1512 child.parentComponent->removeChildComponent (&child);
1513 else
1514 child.removeFromDesktop();
1515
1516 child.parentComponent = this;
1517
1518 if (child.isVisible())
1519 child.repaintParent();
1520
1521 if (! child.isAlwaysOnTop())
1522 {
1523 if (zOrder < 0 || zOrder > childComponentList.size())
1524 zOrder = childComponentList.size();
1525
1526 while (zOrder > 0)
1527 {
1528 if (! childComponentList.getUnchecked (zOrder - 1)->isAlwaysOnTop())
1529 break;
1530
1531 --zOrder;
1532 }
1533 }
1534
1535 childComponentList.insert (zOrder, &child);
1536
1539 }
1540}
1541
1543{
1544 child.setVisible (true);
1545 addChildComponent (child, zOrder);
1546}
1547
1549{
1550 if (child != nullptr)
1551 addChildComponent (*child, zOrder);
1552}
1553
1555{
1556 if (child != nullptr)
1557 addAndMakeVisible (*child, zOrder);
1558}
1559
1560void Component::addChildAndSetID (Component* child, const String& childID)
1561{
1562 if (child != nullptr)
1563 {
1564 child->setComponentID (childID);
1565 addAndMakeVisible (child);
1566 }
1567}
1568
1570{
1571 removeChildComponent (childComponentList.indexOf (child), true, true);
1572}
1573
1575{
1576 return removeChildComponent (index, true, true);
1577}
1578
1579Component* Component::removeChildComponent (int index, bool sendParentEvents, bool sendChildEvents)
1580{
1581 // if component methods are being called from threads other than the message
1582 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
1584
1585 if (auto* child = childComponentList [index])
1586 {
1587 sendParentEvents = sendParentEvents && child->isShowing();
1588
1589 if (sendParentEvents)
1590 {
1592
1593 if (child->isVisible())
1594 child->repaintParent();
1595 }
1596
1597 childComponentList.remove (index);
1598 child->parentComponent = nullptr;
1599
1601
1602 // (NB: there are obscure situations where child->isShowing() = false, but it still has the focus)
1603 if (child->hasKeyboardFocus (true))
1604 {
1605 const WeakReference<Component> safeThis (this);
1606
1607 child->giveAwayKeyboardFocusInternal (sendChildEvents || currentlyFocusedComponent != child);
1608
1609 if (sendParentEvents)
1610 {
1611 if (safeThis == nullptr)
1612 return child;
1613
1615 }
1616 }
1617
1618 if (sendChildEvents)
1619 child->internalHierarchyChanged();
1620
1621 if (sendParentEvents)
1623
1624 return child;
1625 }
1626
1627 return nullptr;
1628}
1629
1630//==============================================================================
1632{
1633 while (! childComponentList.isEmpty())
1635}
1636
1638{
1639 while (! childComponentList.isEmpty())
1640 delete (removeChildComponent (childComponentList.size() - 1));
1641}
1642
1647
1648Component* Component::getChildComponent (int index) const noexcept
1649{
1650 return childComponentList[index];
1651}
1652
1653int Component::getIndexOfChildComponent (const Component* child) const noexcept
1654{
1655 return childComponentList.indexOf (const_cast<Component*> (child));
1656}
1657
1659{
1660 for (auto* c : childComponentList)
1661 if (c->componentID == targetID)
1662 return c;
1663
1664 return nullptr;
1665}
1666
1668{
1669 auto* comp = this;
1670
1671 while (comp->parentComponent != nullptr)
1672 comp = comp->parentComponent;
1673
1674 return const_cast<Component*> (comp);
1675}
1676
1677bool Component::isParentOf (const Component* possibleChild) const noexcept
1678{
1679 while (possibleChild != nullptr)
1680 {
1681 possibleChild = possibleChild->parentComponent;
1682
1683 if (possibleChild == this)
1684 return true;
1685 }
1686
1687 return false;
1688}
1689
1690//==============================================================================
1693
1695{
1696 if (componentListeners.isEmpty())
1697 {
1699 }
1700 else
1701 {
1702 BailOutChecker checker (this);
1703
1705
1706 if (! checker.shouldBailOut())
1707 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentChildrenChanged (*this); });
1708 }
1709}
1710
1712{
1713 BailOutChecker checker (this);
1714
1716
1717 if (checker.shouldBailOut())
1718 return;
1719
1720 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentParentHierarchyChanged (*this); });
1721
1722 if (checker.shouldBailOut())
1723 return;
1724
1725 for (int i = childComponentList.size(); --i >= 0;)
1726 {
1727 childComponentList.getUnchecked (i)->internalHierarchyChanged();
1728
1729 if (checker.shouldBailOut())
1730 {
1731 // you really shouldn't delete the parent component during a callback telling you
1732 // that it's changed..
1734 return;
1735 }
1736
1737 i = jmin (i, childComponentList.size());
1738 }
1739
1740 if (flags.hasHeavyweightPeerFlag)
1741 if (auto* handler = getAccessibilityHandler())
1742 handler->notifyAccessibilityEvent (AccessibilityEvent::structureChanged);
1743}
1744
1745//==============================================================================
1746#if JUCE_MODAL_LOOPS_PERMITTED
1747int Component::runModalLoop()
1748{
1749 if (! MessageManager::getInstance()->isThisTheMessageThread())
1750 {
1751 // use a callback so this can be called from non-gui threads
1753 ->callFunctionOnMessageThread (&ComponentHelpers::runModalLoopCallback, this);
1754 }
1755
1756 if (! isCurrentlyModal (false))
1757 enterModalState (true);
1758
1759 return ModalComponentManager::getInstance()->runEventLoopForCurrentComponent();
1760}
1761#endif
1762
1763//==============================================================================
1764void Component::enterModalState (bool shouldTakeKeyboardFocus,
1766 bool deleteWhenDismissed)
1767{
1768 // if component methods are being called from threads other than the message
1769 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
1771
1772 if (! isCurrentlyModal (false))
1773 {
1774 // While this component is in modal state it may block other components from receiving
1775 // mouseExit events. To keep mouseEnter and mouseExit calls balanced on these components,
1776 // we must manually force the mouse to "leave" blocked components.
1778
1779 auto& mcm = *ModalComponentManager::getInstance();
1780 mcm.startModal (this, deleteWhenDismissed);
1781 mcm.attachCallback (this, callback);
1782
1783 setVisible (true);
1784
1785 if (shouldTakeKeyboardFocus)
1787 }
1788 else
1789 {
1790 // Probably a bad idea to try to make a component modal twice!
1792 }
1793}
1794
1795void Component::exitModalState (int returnValue)
1796{
1797 WeakReference<Component> deletionChecker (this);
1798
1799 if (isCurrentlyModal (false))
1800 {
1801 if (MessageManager::getInstance()->isThisTheMessageThread())
1802 {
1803 auto& mcm = *ModalComponentManager::getInstance();
1804 mcm.endModal (this, returnValue);
1805 mcm.bringModalComponentsToFront();
1806
1807 // While this component is in modal state it may block other components from receiving
1808 // mouseEnter events. To keep mouseEnter and mouseExit calls balanced on these components,
1809 // we must manually force the mouse to "enter" blocked components.
1810 if (deletionChecker != nullptr)
1812 }
1813 else
1814 {
1815 MessageManager::callAsync ([target = WeakReference<Component> { this }, returnValue]
1816 {
1817 if (target != nullptr)
1818 target->exitModalState (returnValue);
1819 });
1820 }
1821 }
1822}
1823
1824bool Component::isCurrentlyModal (bool onlyConsiderForemostModalComponent) const noexcept
1825{
1826 auto& mcm = *ModalComponentManager::getInstance();
1827
1828 return onlyConsiderForemostModalComponent ? mcm.isFrontModalComponent (this)
1829 : mcm.isModal (this);
1830}
1831
1836
1838{
1839 return ModalComponentManager::getInstance()->getNumModalComponents();
1840}
1841
1843{
1844 return ModalComponentManager::getInstance()->getModalComponent (index);
1845}
1846
1847//==============================================================================
1848void Component::setBroughtToFrontOnMouseClick (bool shouldBeBroughtToFront) noexcept
1849{
1850 flags.bringToFrontOnClickFlag = shouldBeBroughtToFront;
1851}
1852
1854{
1855 return flags.bringToFrontOnClickFlag;
1856}
1857
1858//==============================================================================
1860{
1861 if (cursor != newCursor)
1862 {
1863 cursor = newCursor;
1864
1865 if (flags.visibleFlag)
1868}
1869
1874
1876{
1877 Desktop::getInstance().getMainMouseSource().forceMouseCursorUpdate();
1878}
1879
1880//==============================================================================
1881void Component::setRepaintsOnMouseActivity (bool shouldRepaint) noexcept
1882{
1883 flags.repaintOnMouseActivityFlag = shouldRepaint;
1884}
1885
1886//==============================================================================
1888{
1889 return (255 - componentTransparency) / 255.0f;
1890}
1891
1892void Component::setAlpha (float newAlpha)
1893{
1894 auto newIntAlpha = (uint8) (255 - jlimit (0, 255, roundToInt (newAlpha * 255.0)));
1895
1896 if (componentTransparency != newIntAlpha)
1897 {
1898 componentTransparency = newIntAlpha;
1899 alphaChanged();
1900 }
1901}
1902
1904{
1905 if (flags.hasHeavyweightPeerFlag)
1906 {
1907 if (auto* peer = getPeer())
1908 peer->setAlpha (getAlpha());
1909 }
1910 else
1911 {
1912 repaint();
1913 }
1914}
1915
1916//==============================================================================
1921
1922void Component::repaint (int x, int y, int w, int h)
1923{
1924 internalRepaint ({ x, y, w, h });
1925}
1926
1928{
1929 internalRepaint (area);
1930}
1931
1933{
1934 if (parentComponent != nullptr)
1936}
1937
1939{
1940 area = area.getIntersection (getLocalBounds());
1941
1942 if (! area.isEmpty())
1943 internalRepaintUnchecked (area, false);
1944}
1945
1946void Component::internalRepaintUnchecked (Rectangle<int> area, bool isEntireComponent)
1947{
1948 // if component methods are being called from threads other than the message
1949 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
1951
1952 if (flags.visibleFlag)
1953 {
1954 if (cachedImage != nullptr)
1955 if (! (isEntireComponent ? cachedImage->invalidateAll()
1956 : cachedImage->invalidate (area)))
1957 return;
1958
1959 if (area.isEmpty())
1960 return;
1961
1962 if (flags.hasHeavyweightPeerFlag)
1963 {
1964 if (auto* peer = getPeer())
1965 {
1966 // Tweak the scaling so that the component's integer size exactly aligns with the peer's scaled size
1967 auto peerBounds = peer->getBounds();
1968 auto scaled = area * Point<float> ((float) peerBounds.getWidth() / (float) getWidth(),
1969 (float) peerBounds.getHeight() / (float) getHeight());
1970
1971 peer->repaint (affineTransform != nullptr ? scaled.transformedBy (*affineTransform) : scaled);
1972 }
1973 }
1974 else
1975 {
1976 if (parentComponent != nullptr)
1977 parentComponent->internalRepaint (ComponentHelpers::convertToParentSpace (*this, area));
1978 }
1979 }
1980}
1981
1982//==============================================================================
1984{
1985 // if your component is marked as opaque, you must implement a paint
1986 // method and ensure that its entire area is completely painted.
1987 jassert (getBounds().isEmpty() || ! isOpaque());
1988}
1989
1991{
1992 // all painting is done in the subclasses
1993}
1994
1995//==============================================================================
1997{
1998 g.setOrigin (getPosition());
1999
2000 if (cachedImage != nullptr)
2001 cachedImage->paint (g);
2002 else
2003 paintEntireComponent (g, false);
2004}
2005
2007{
2008 auto clipBounds = g.getClipBounds();
2009
2010 if (flags.dontClipGraphicsFlag && getNumChildComponents() == 0)
2011 {
2012 paint (g);
2013 }
2014 else
2015 {
2017
2018 if (! (ComponentHelpers::clipObscuredRegions (*this, g, clipBounds, {}) && g.isClipEmpty()))
2019 paint (g);
2020 }
2021
2022 for (int i = 0; i < childComponentList.size(); ++i)
2023 {
2024 auto& child = *childComponentList.getUnchecked (i);
2025
2026 if (child.isVisible())
2027 {
2028 if (child.affineTransform != nullptr)
2029 {
2031
2032 g.addTransform (*child.affineTransform);
2033
2034 if ((child.flags.dontClipGraphicsFlag && ! g.isClipEmpty()) || g.reduceClipRegion (child.getBounds()))
2035 child.paintWithinParentContext (g);
2036 }
2037 else if (clipBounds.intersects (child.getBounds()))
2038 {
2040
2041 if (child.flags.dontClipGraphicsFlag)
2042 {
2043 child.paintWithinParentContext (g);
2044 }
2045 else if (g.reduceClipRegion (child.getBounds()))
2046 {
2047 bool nothingClipped = true;
2048
2049 for (int j = i + 1; j < childComponentList.size(); ++j)
2050 {
2051 auto& sibling = *childComponentList.getUnchecked (j);
2052
2053 if (sibling.flags.opaqueFlag && sibling.isVisible() && sibling.affineTransform == nullptr)
2054 {
2055 nothingClipped = false;
2056 g.excludeClipRegion (sibling.getBounds());
2057 }
2058 }
2059
2060 if (nothingClipped || ! g.isClipEmpty())
2061 child.paintWithinParentContext (g);
2062 }
2063 }
2064 }
2065 }
2066
2069}
2070
2071void Component::paintEntireComponent (Graphics& g, bool ignoreAlphaLevel)
2072{
2073 // If sizing a top-level-window and the OS paint message is delivered synchronously
2074 // before resized() is called, then we'll invoke the callback here, to make sure
2075 // the components inside have had a chance to sort their sizes out..
2076 #if JUCE_DEBUG
2077 if (! flags.isInsidePaintCall) // (avoids an assertion in plugins hosted in WaveLab)
2078 #endif
2080
2081 #if JUCE_DEBUG
2082 flags.isInsidePaintCall = true;
2083 #endif
2084
2085 if (effect != nullptr)
2086 {
2087 auto scale = g.getInternalContext().getPhysicalPixelScaleFactor();
2088
2089 auto scaledBounds = getLocalBounds() * scale;
2090
2091 Image effectImage (flags.opaqueFlag ? Image::RGB : Image::ARGB,
2092 scaledBounds.getWidth(), scaledBounds.getHeight(), ! flags.opaqueFlag);
2093 {
2094 Graphics g2 (effectImage);
2095 g2.addTransform (AffineTransform::scale ((float) scaledBounds.getWidth() / (float) getWidth(),
2096 (float) scaledBounds.getHeight() / (float) getHeight()));
2098 }
2099
2101
2102 g.addTransform (AffineTransform::scale (1.0f / scale));
2103 effect->applyEffect (effectImage, g, scale, ignoreAlphaLevel ? 1.0f : getAlpha());
2104 }
2105 else if (componentTransparency > 0 && ! ignoreAlphaLevel)
2106 {
2107 if (componentTransparency < 255)
2108 {
2109 g.beginTransparencyLayer (getAlpha());
2111 g.endTransparencyLayer();
2112 }
2113 }
2114 else
2115 {
2117 }
2118
2119 #if JUCE_DEBUG
2120 flags.isInsidePaintCall = false;
2121 #endif
2122}
2123
2124void Component::setPaintingIsUnclipped (bool shouldPaintWithoutClipping) noexcept
2125{
2126 flags.dontClipGraphicsFlag = shouldPaintWithoutClipping;
2127}
2128
2130{
2131 return flags.dontClipGraphicsFlag;
2132}
2133
2134//==============================================================================
2136 bool clipImageToComponentBounds, float scaleFactor)
2137{
2138 auto r = areaToGrab;
2139
2140 if (clipImageToComponentBounds)
2141 r = r.getIntersection (getLocalBounds());
2142
2143 if (r.isEmpty())
2144 return {};
2145
2146 auto w = roundToInt (scaleFactor * (float) r.getWidth());
2147 auto h = roundToInt (scaleFactor * (float) r.getHeight());
2148
2149 Image image (flags.opaqueFlag ? Image::RGB : Image::ARGB, w, h, true);
2150
2151 Graphics g (image);
2152
2153 if (w != getWidth() || h != getHeight())
2154 g.addTransform (AffineTransform::scale ((float) w / (float) r.getWidth(),
2155 (float) h / (float) r.getHeight()));
2156 g.setOrigin (-r.getPosition());
2157
2158 paintEntireComponent (g, true);
2159
2160 return image;
2161}
2162
2164{
2165 if (effect != newEffect)
2166 {
2167 effect = newEffect;
2168 repaint();
2169 }
2170}
2171
2172//==============================================================================
2174{
2175 for (auto* c = this; c != nullptr; c = c->parentComponent)
2176 if (auto lf = c->lookAndFeel.get())
2177 return *lf;
2178
2180}
2181
2183{
2184 if (lookAndFeel != newLookAndFeel)
2185 {
2186 lookAndFeel = newLookAndFeel;
2188 }
2189}
2190
2193
2195{
2196 const WeakReference<Component> safePointer (this);
2197 repaint();
2199
2200 if (safePointer != nullptr)
2201 {
2202 colourChanged();
2203
2204 if (safePointer != nullptr)
2205 {
2206 for (int i = childComponentList.size(); --i >= 0;)
2207 {
2208 childComponentList.getUnchecked (i)->sendLookAndFeelChange();
2209
2210 if (safePointer == nullptr)
2211 return;
2212
2213 i = jmin (i, childComponentList.size());
2214 }
2215 }
2216 }
2217}
2218
2219Colour Component::findColour (int colourID, bool inheritFromParent) const
2220{
2221 if (auto* v = properties.getVarPointer (ComponentHelpers::getColourPropertyID (colourID)))
2222 return Colour ((uint32) static_cast<int> (*v));
2223
2224 if (inheritFromParent && parentComponent != nullptr
2225 && (lookAndFeel == nullptr || ! lookAndFeel->isColourSpecified (colourID)))
2226 return parentComponent->findColour (colourID, true);
2227
2228 return getLookAndFeel().findColour (colourID);
2229}
2230
2231bool Component::isColourSpecified (int colourID) const
2232{
2233 return properties.contains (ComponentHelpers::getColourPropertyID (colourID));
2234}
2235
2236void Component::removeColour (int colourID)
2237{
2238 if (properties.remove (ComponentHelpers::getColourPropertyID (colourID)))
2239 colourChanged();
2240}
2241
2242void Component::setColour (int colourID, Colour colour)
2243{
2244 if (properties.set (ComponentHelpers::getColourPropertyID (colourID), (int) colour.getARGB()))
2245 colourChanged();
2246}
2247
2249{
2250 bool changed = false;
2251
2252 for (int i = properties.size(); --i >= 0;)
2253 {
2254 auto name = properties.getName(i);
2255
2256 if (name.toString().startsWith (colourPropertyPrefix))
2257 if (target.properties.set (name, properties [name]))
2258 changed = true;
2259 }
2260
2261 if (changed)
2262 target.colourChanged();
2263}
2264
2265//==============================================================================
2269
2274
2276{
2277 // You can only assign a positioner to the component that it was created for!
2278 jassert (newPositioner == nullptr || this == &(newPositioner->getComponent()));
2279 positioner.reset (newPositioner);
2280}
2281
2282//==============================================================================
2287
2293
2294//==============================================================================
2302
2304{
2305 // the base class just passes this event up to the nearest enabled ancestor
2306 if (auto* enabledComponent = findFirstEnabledAncestor (getParentComponent()))
2307 enabledComponent->mouseWheelMove (e.getEventRelativeTo (enabledComponent), wheel);
2308}
2309
2310void Component::mouseMagnify (const MouseEvent& e, float magnifyAmount)
2311{
2312 // the base class just passes this event up to the nearest enabled ancestor
2313 if (auto* enabledComponent = findFirstEnabledAncestor (getParentComponent()))
2314 enabledComponent->mouseMagnify (e.getEventRelativeTo (enabledComponent), magnifyAmount);
2315}
2316
2317//==============================================================================
2322
2324{
2325 // if component methods are being called from threads other than the message
2326 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
2327 #if JUCE_DEBUG || JUCE_LOG_ASSERTIONS
2328 if (getParentComponent() != nullptr)
2329 {
2331 }
2332 #endif
2333
2334 componentListeners.add (newListener);
2335}
2336
2338{
2339 componentListeners.remove (listenerToRemove);
2340}
2341
2342//==============================================================================
2344{
2345 ModalComponentManager::getInstance()->bringModalComponentsToFront();
2346 getLookAndFeel().playAlertSound();
2347}
2348
2350{
2351 return false;
2352}
2353
2355{
2356 if (auto* current = getCurrentlyModalComponent())
2357 current->inputAttemptWhenModal();
2358}
2359
2360//==============================================================================
2362{
2363 MessageManager::callAsync ([target = WeakReference<Component> { this }, commandID]
2364 {
2365 if (target != nullptr)
2366 target->handleCommandMessage (commandID);
2367 });
2368}
2369
2371{
2372 // used by subclasses
2373}
2374
2375//==============================================================================
2377 bool wantsEventsForAllNestedChildComponents)
2378{
2379 // if component methods are being called from threads other than the message
2380 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
2382
2383 // If you register a component as a mouselistener for itself, it'll receive all the events
2384 // twice - once via the direct callback that all components get anyway, and then again as a listener!
2385 jassert ((newListener != this) || wantsEventsForAllNestedChildComponents);
2386
2387 if (mouseListeners == nullptr)
2388 mouseListeners.reset (new MouseListenerList());
2389
2390 mouseListeners->addListener (newListener, wantsEventsForAllNestedChildComponents);
2391}
2392
2394{
2395 // if component methods are being called from threads other than the message
2396 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
2398
2399 if (mouseListeners != nullptr)
2400 mouseListeners->removeListener (listenerToRemove);
2401}
2402
2403//==============================================================================
2405{
2407 {
2408 // if something else is modal, always just show a normal mouse cursor
2410 return;
2411 }
2412
2413 if (flags.repaintOnMouseActivityFlag)
2414 repaint();
2415
2416 BailOutChecker checker (this);
2417
2418 const auto me = makeMouseEvent (source,
2419 PointerState().withPosition (relativePos),
2420 source.getCurrentModifiers(),
2421 this,
2422 this,
2423 time,
2424 relativePos,
2425 time,
2426 0,
2427 false);
2428 mouseEnter (me);
2429
2430 flags.cachedMouseInsideComponent = true;
2431
2432 if (checker.shouldBailOut())
2433 return;
2434
2435 Desktop::getInstance().getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseEnter (me); });
2436
2437 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseEnter, me);
2438}
2439
2441{
2443 {
2444 // if something else is modal, always just show a normal mouse cursor
2446 return;
2447 }
2448
2449 if (flags.repaintOnMouseActivityFlag)
2450 repaint();
2451
2452 flags.cachedMouseInsideComponent = false;
2453
2454 BailOutChecker checker (this);
2455
2456 const auto me = makeMouseEvent (source,
2457 PointerState().withPosition (relativePos),
2458 source.getCurrentModifiers(),
2459 this,
2460 this,
2461 time,
2462 relativePos,
2463 time,
2464 0,
2465 false);
2466
2467 mouseExit (me);
2468
2469 if (checker.shouldBailOut())
2470 return;
2471
2472 Desktop::getInstance().getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseExit (me); });
2473
2474 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseExit, me);
2475}
2476
2477void Component::internalMouseDown (MouseInputSource source, const PointerState& relativePointerState, Time time)
2478{
2479 auto& desktop = Desktop::getInstance();
2480 BailOutChecker checker (this);
2481
2483 {
2484 flags.mouseDownWasBlocked = true;
2486
2487 if (checker.shouldBailOut())
2488 return;
2489
2490 // If processing the input attempt has exited the modal loop, we'll allow the event
2491 // to be delivered..
2493 {
2494 // allow blocked mouse-events to go to global listeners..
2495 const auto me = makeMouseEvent (source,
2496 relativePointerState,
2497 source.getCurrentModifiers(),
2498 this,
2499 this,
2500 time,
2501 relativePointerState.position,
2502 time,
2504 false);
2505
2506 desktop.getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseDown (me); });
2507 return;
2508 }
2509 }
2510
2511 flags.mouseDownWasBlocked = false;
2512
2513 for (auto* c = this; c != nullptr; c = c->parentComponent)
2514 {
2515 if (c->isBroughtToFrontOnMouseClick())
2516 {
2517 c->toFront (true);
2518
2519 if (checker.shouldBailOut())
2520 return;
2521 }
2522 }
2523
2524 if (! flags.dontFocusOnMouseClickFlag)
2525 {
2527
2528 if (checker.shouldBailOut())
2529 return;
2530 }
2531
2532 if (flags.repaintOnMouseActivityFlag)
2533 repaint();
2534
2535 const auto me = makeMouseEvent (source,
2536 relativePointerState,
2537 source.getCurrentModifiers(),
2538 this,
2539 this,
2540 time,
2541 relativePointerState.position,
2542 time,
2544 false);
2545 mouseDown (me);
2546
2547 if (checker.shouldBailOut())
2548 return;
2549
2550 desktop.getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseDown (me); });
2551
2552 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseDown, me);
2553}
2554
2555void Component::internalMouseUp (MouseInputSource source, const PointerState& relativePointerState, Time time, const ModifierKeys oldModifiers)
2556{
2557 if (flags.mouseDownWasBlocked && isCurrentlyBlockedByAnotherModalComponent())
2558 return;
2559
2560 BailOutChecker checker (this);
2561
2562 if (flags.repaintOnMouseActivityFlag)
2563 repaint();
2564
2565 const auto me = makeMouseEvent (source,
2566 relativePointerState,
2567 oldModifiers,
2568 this,
2569 this,
2570 time,
2571 getLocalPoint (nullptr, source.getLastMouseDownPosition()),
2572 source.getLastMouseDownTime(),
2574 source.isLongPressOrDrag());
2575 mouseUp (me);
2576
2577 if (checker.shouldBailOut())
2578 return;
2579
2580 auto& desktop = Desktop::getInstance();
2581 desktop.getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseUp (me); });
2582
2583 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseUp, me);
2584
2585 if (checker.shouldBailOut())
2586 return;
2587
2588 // check for double-click
2589 if (me.getNumberOfClicks() >= 2)
2590 {
2591 mouseDoubleClick (me);
2592
2593 if (checker.shouldBailOut())
2594 return;
2595
2596 desktop.mouseListeners.callChecked (checker, [&] (MouseListener& l) { l.mouseDoubleClick (me); });
2597 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseDoubleClick, me);
2598 }
2599}
2600
2601void Component::internalMouseDrag (MouseInputSource source, const PointerState& relativePointerState, Time time)
2602{
2604 {
2605 BailOutChecker checker (this);
2606
2607 const auto me = makeMouseEvent (source,
2608 relativePointerState,
2609 source.getCurrentModifiers(),
2610 this,
2611 this,
2612 time,
2613 getLocalPoint (nullptr, source.getLastMouseDownPosition()),
2614 source.getLastMouseDownTime(),
2616 source.isLongPressOrDrag());
2617 mouseDrag (me);
2618
2619 if (checker.shouldBailOut())
2620 return;
2621
2622 Desktop::getInstance().getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseDrag (me); });
2623
2624 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseDrag, me);
2625 }
2626}
2627
2629{
2630 auto& desktop = Desktop::getInstance();
2631
2633 {
2634 // allow blocked mouse-events to go to global listeners..
2635 desktop.sendMouseMove();
2636 }
2637 else
2638 {
2639 BailOutChecker checker (this);
2640
2641 const auto me = makeMouseEvent (source,
2642 PointerState().withPosition (relativePos),
2643 source.getCurrentModifiers(),
2644 this,
2645 this,
2646 time,
2647 relativePos,
2648 time,
2649 0,
2650 false);
2651 mouseMove (me);
2652
2653 if (checker.shouldBailOut())
2654 return;
2655
2656 desktop.getMouseListeners().callChecked (checker, [&] (MouseListener& l) { l.mouseMove (me); });
2657
2658 MouseListenerList::template sendMouseEvent<const MouseEvent&> (*this, checker, &MouseListener::mouseMove, me);
2659 }
2660}
2661
2663 Time time, const MouseWheelDetails& wheel)
2664{
2665 auto& desktop = Desktop::getInstance();
2666 BailOutChecker checker (this);
2667
2668 const auto me = makeMouseEvent (source,
2669 PointerState().withPosition (relativePos),
2670 source.getCurrentModifiers(),
2671 this,
2672 this,
2673 time,
2674 relativePos,
2675 time,
2676 0,
2677 false);
2678
2680 {
2681 // allow blocked mouse-events to go to global listeners..
2682 desktop.mouseListeners.callChecked (checker, [&] (MouseListener& l) { l.mouseWheelMove (me, wheel); });
2683 }
2684 else
2685 {
2686 mouseWheelMove (me, wheel);
2687
2688 if (checker.shouldBailOut())
2689 return;
2690
2691 desktop.mouseListeners.callChecked (checker, [&] (MouseListener& l) { l.mouseWheelMove (me, wheel); });
2692
2693 if (! checker.shouldBailOut())
2694 MouseListenerList::template sendMouseEvent<const MouseEvent&, const MouseWheelDetails&> (*this, checker, &MouseListener::mouseWheelMove, me, wheel);
2695 }
2696}
2697
2699 Time time, float amount)
2700{
2701 auto& desktop = Desktop::getInstance();
2702 BailOutChecker checker (this);
2703
2704 const auto me = makeMouseEvent (source,
2705 PointerState().withPosition (relativePos),
2706 source.getCurrentModifiers(),
2707 this,
2708 this,
2709 time,
2710 relativePos,
2711 time,
2712 0,
2713 false);
2714
2716 {
2717 // allow blocked mouse-events to go to global listeners..
2718 desktop.mouseListeners.callChecked (checker, [&] (MouseListener& l) { l.mouseMagnify (me, amount); });
2719 }
2720 else
2721 {
2722 mouseMagnify (me, amount);
2723
2724 if (checker.shouldBailOut())
2725 return;
2726
2727 desktop.mouseListeners.callChecked (checker, [&] (MouseListener& l) { l.mouseMagnify (me, amount); });
2728
2729 if (! checker.shouldBailOut())
2730 MouseListenerList::template sendMouseEvent<const MouseEvent&, float> (*this, checker, &MouseListener::mouseMagnify, me, amount);
2731 }
2732}
2733
2735{
2736 if (flags.ignoresMouseClicksFlag && ! flags.allowChildMouseClicksFlag)
2737 return;
2738
2739 auto mainMouse = Desktop::getInstance().getMainMouseSource();
2740
2741 if (! mainMouse.isDragging())
2742 mainMouse.triggerFakeMove();
2743}
2744
2746{
2747 Desktop::getInstance().beginDragAutoRepeat (interval);
2748}
2749
2750//==============================================================================
2752{
2753}
2754
2756{
2757 if (flags.hasHeavyweightPeerFlag)
2758 Desktop::getInstance().componentBroughtToFront (this);
2759
2760 BailOutChecker checker (this);
2762
2763 if (checker.shouldBailOut())
2764 return;
2765
2766 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentBroughtToFront (*this); });
2767
2768 if (checker.shouldBailOut())
2769 return;
2770
2771 // When brought to the front and there's a modal component blocking this one,
2772 // we need to bring the modal one to the front instead..
2773 if (auto* cm = getCurrentlyModalComponent())
2774 if (cm->getTopLevelComponent() != getTopLevelComponent())
2775 ModalComponentManager::getInstance()->bringModalComponentsToFront (false); // very important that this is false, otherwise in Windows,
2776 // non-front components can't get focus when another modal comp is
2777 // active, and therefore can't receive mouse-clicks
2778}
2779
2780//==============================================================================
2784
2789
2791 const WeakReference<Component>& safePointer)
2792{
2793 focusGained (cause);
2794
2795 if (safePointer == nullptr)
2796 return;
2797
2798 if (hasKeyboardFocus (false))
2799 if (auto* handler = getAccessibilityHandler())
2800 handler->grabFocus();
2801
2802 if (safePointer == nullptr)
2803 return;
2804
2805 internalChildKeyboardFocusChange (cause, safePointer);
2806}
2807
2809{
2810 const WeakReference<Component> safePointer (this);
2811
2812 focusLost (cause);
2813
2814 if (safePointer != nullptr)
2815 {
2816 if (auto* handler = getAccessibilityHandler())
2817 handler->giveAwayFocus();
2818
2819 internalChildKeyboardFocusChange (cause, safePointer);
2820 }
2821}
2822
2824 const WeakReference<Component>& safePointer)
2825{
2826 const bool childIsNowKeyboardFocused = hasKeyboardFocus (true);
2827
2828 if (flags.childKeyboardFocusedFlag != childIsNowKeyboardFocused)
2829 {
2830 flags.childKeyboardFocusedFlag = childIsNowKeyboardFocused;
2831
2833
2834 if (safePointer == nullptr)
2835 return;
2836 }
2837
2838 if (parentComponent != nullptr)
2839 parentComponent->internalChildKeyboardFocusChange (cause, parentComponent);
2840}
2841
2842void Component::setWantsKeyboardFocus (bool wantsFocus) noexcept
2843{
2844 flags.wantsKeyboardFocusFlag = wantsFocus;
2845}
2846
2848{
2849 flags.dontFocusOnMouseClickFlag = ! shouldGrabFocus;
2850}
2851
2853{
2854 return ! flags.dontFocusOnMouseClickFlag;
2855}
2856
2858{
2859 return flags.wantsKeyboardFocusFlag && ! flags.isDisabledFlag;
2860}
2861
2863{
2864 flags.isFocusContainerFlag = (containerType == FocusContainerType::focusContainer
2865 || containerType == FocusContainerType::keyboardFocusContainer);
2866
2867 flags.isKeyboardFocusContainerFlag = (containerType == FocusContainerType::keyboardFocusContainer);
2868}
2869
2871{
2872 return flags.isFocusContainerFlag;
2873}
2874
2876{
2877 return flags.isKeyboardFocusContainerFlag;
2878}
2879
2880template <typename FocusContainerFn>
2881static Component* findContainer (const Component* child, FocusContainerFn isFocusContainer)
2882{
2883 if (auto* parent = child->getParentComponent())
2884 {
2885 if ((parent->*isFocusContainer)() || parent->getParentComponent() == nullptr)
2886 return parent;
2887
2888 return findContainer (parent, isFocusContainer);
2889 }
2890
2891 return nullptr;
2892}
2893
2898
2903
2905
2910
2911void Component::setExplicitFocusOrder (int newFocusOrderIndex)
2912{
2913 properties.set (juce_explicitFocusOrderId, newFocusOrderIndex);
2914}
2915
2916std::unique_ptr<ComponentTraverser> Component::createFocusTraverser()
2917{
2918 if (flags.isFocusContainerFlag || parentComponent == nullptr)
2919 return std::make_unique<FocusTraverser>();
2920
2921 return parentComponent->createFocusTraverser();
2922}
2923
2924std::unique_ptr<ComponentTraverser> Component::createKeyboardFocusTraverser()
2925{
2926 if (flags.isKeyboardFocusContainerFlag || parentComponent == nullptr)
2927 return std::make_unique<KeyboardFocusTraverser>();
2928
2929 return parentComponent->createKeyboardFocusTraverser();
2930}
2931
2933{
2934 if (currentlyFocusedComponent == this)
2935 return;
2936
2937 if (auto* peer = getPeer())
2938 {
2939 const WeakReference<Component> safePointer (this);
2940 peer->grabFocus();
2941
2942 if (! peer->isFocused() || currentlyFocusedComponent == this)
2943 return;
2944
2946
2947 if (auto* losingFocus = componentLosingFocus.get())
2948 if (auto* otherPeer = losingFocus->getPeer())
2949 otherPeer->closeInputMethodContext();
2950
2952
2953 Desktop::getInstance().triggerFocusCallback();
2954
2955 // call this after setting currentlyFocusedComponent so that the one that's
2956 // losing it has a chance to see where focus is going
2957 if (componentLosingFocus != nullptr)
2958 componentLosingFocus->internalKeyboardFocusLoss (cause);
2959
2960 if (currentlyFocusedComponent == this)
2961 internalKeyboardFocusGain (cause, safePointer);
2962 }
2963}
2964
2966{
2967 if (! isShowing())
2968 return;
2969
2970 if (flags.wantsKeyboardFocusFlag
2971 && (isEnabled() || parentComponent == nullptr))
2972 {
2973 takeKeyboardFocus (cause);
2974 return;
2975 }
2976
2978 return;
2979
2980 if (auto traverser = createKeyboardFocusTraverser())
2981 {
2982 if (auto* defaultComp = traverser->getDefaultComponent (this))
2983 {
2984 defaultComp->grabKeyboardFocusInternal (cause, false);
2985 return;
2986 }
2987 }
2988
2989 // if no children want it and we're allowed to try our parent comp,
2990 // then pass up to parent, which will try our siblings.
2991 if (canTryParent && parentComponent != nullptr)
2992 parentComponent->grabKeyboardFocusInternal (cause, true);
2993}
2994
2996{
2997 // if component methods are being called from threads other than the message
2998 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
3000
3002
3003 // A component can only be focused when it's actually on the screen!
3004 // If this fails then you're probably trying to grab the focus before you've
3005 // added the component to a parent or made it visible. Or maybe one of its parent
3006 // components isn't yet visible.
3007 jassert (isShowing() || isOnDesktop());
3008}
3009
3010void Component::giveAwayKeyboardFocusInternal (bool sendFocusLossEvent)
3011{
3012 if (hasKeyboardFocus (true))
3013 {
3014 if (auto* componentLosingFocus = currentlyFocusedComponent)
3015 {
3016 if (auto* otherPeer = componentLosingFocus->getPeer())
3017 otherPeer->closeInputMethodContext();
3018
3019 currentlyFocusedComponent = nullptr;
3020
3021 if (sendFocusLossEvent && componentLosingFocus != nullptr)
3022 componentLosingFocus->internalKeyboardFocusLoss (focusChangedDirectly);
3023
3024 Desktop::getInstance().triggerFocusCallback();
3025 }
3026 }
3027}
3028
3030{
3031 // if component methods are being called from threads other than the message
3032 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
3034
3036}
3037
3039{
3040 // if component methods are being called from threads other than the message
3041 // thread, you'll need to use a MessageManagerLock object to make sure it's thread-safe.
3043
3044 if (parentComponent != nullptr)
3045 {
3046 if (auto traverser = createKeyboardFocusTraverser())
3047 {
3048 auto findComponentToFocus = [&]() -> Component*
3049 {
3050 if (auto* comp = (moveToNext ? traverser->getNextComponent (this)
3051 : traverser->getPreviousComponent (this)))
3052 return comp;
3053
3054 if (auto* focusContainer = findKeyboardFocusContainer())
3055 {
3056 auto allFocusableComponents = traverser->getAllComponents (focusContainer);
3057
3058 if (! allFocusableComponents.empty())
3059 return moveToNext ? allFocusableComponents.front()
3060 : allFocusableComponents.back();
3061 }
3062
3063 return nullptr;
3064 };
3065
3066 if (auto* nextComp = findComponentToFocus())
3067 {
3068 if (nextComp->isCurrentlyBlockedByAnotherModalComponent())
3069 {
3070 const WeakReference<Component> nextCompPointer (nextComp);
3072
3073 if (nextCompPointer == nullptr || nextComp->isCurrentlyBlockedByAnotherModalComponent())
3074 return;
3075 }
3076
3077 nextComp->grabKeyboardFocusInternal (focusChangedByTabKey, true);
3078 return;
3079 }
3080 }
3081
3082 parentComponent->moveKeyboardFocusToSibling (moveToNext);
3083 }
3084}
3085
3086bool Component::hasKeyboardFocus (bool trueIfChildIsFocused) const
3087{
3088 return (currentlyFocusedComponent == this)
3089 || (trueIfChildIsFocused && isParentOf (currentlyFocusedComponent));
3090}
3091
3096
3098{
3099 if (currentlyFocusedComponent != nullptr)
3100 currentlyFocusedComponent->giveAwayKeyboardFocus();
3101}
3102
3103//==============================================================================
3105{
3106 return (! flags.isDisabledFlag)
3107 && (parentComponent == nullptr || parentComponent->isEnabled());
3108}
3109
3110void Component::setEnabled (bool shouldBeEnabled)
3111{
3112 if (flags.isDisabledFlag == shouldBeEnabled)
3113 {
3114 flags.isDisabledFlag = ! shouldBeEnabled;
3115
3116 // if any parent components are disabled, setting our flag won't make a difference,
3117 // so no need to send a change message
3118 if (parentComponent == nullptr || parentComponent->isEnabled())
3120
3121 BailOutChecker checker (this);
3122 componentListeners.callChecked (checker, [this] (ComponentListener& l) { l.componentEnablementChanged (*this); });
3123
3124 if (! shouldBeEnabled && hasKeyboardFocus (true))
3125 {
3126 if (parentComponent != nullptr)
3127 parentComponent->grabKeyboardFocus();
3128
3129 // ensure that keyboard focus is given away if it wasn't taken by parent
3131 }
3132 }
3133}
3134
3136
3138{
3139 const WeakReference<Component> safePointer (this);
3140
3142
3143 if (safePointer == nullptr)
3144 return;
3145
3146 for (int i = getNumChildComponents(); --i >= 0;)
3147 {
3148 if (auto* c = getChildComponent (i))
3149 {
3150 c->sendEnablementChangeMessage();
3151
3152 if (safePointer == nullptr)
3153 return;
3154 }
3155 }
3156}
3157
3158//==============================================================================
3159bool Component::isMouseOver (bool includeChildren) const
3160{
3161 if (! MessageManager::getInstance()->isThisTheMessageThread())
3162 return flags.cachedMouseInsideComponent;
3163
3164 for (auto& ms : Desktop::getInstance().getMouseSources())
3165 {
3166 auto* c = ms.getComponentUnderMouse();
3167
3168 if (c != nullptr && (c == this || (includeChildren && isParentOf (c))))
3169 if (ms.isDragging() || ! (ms.isTouch() || ms.isPen()))
3170 if (c->reallyContains (c->getLocalPoint (nullptr, ms.getScreenPosition()), false))
3171 return true;
3172 }
3173
3174 return false;
3175}
3176
3177bool Component::isMouseButtonDown (bool includeChildren) const
3178{
3179 for (auto& ms : Desktop::getInstance().getMouseSources())
3180 {
3181 auto* c = ms.getComponentUnderMouse();
3182
3183 if (c == this || (includeChildren && isParentOf (c)))
3184 if (ms.isDragging())
3185 return true;
3186 }
3187
3188 return false;
3189}
3190
3191bool Component::isMouseOverOrDragging (bool includeChildren) const
3192{
3193 for (auto& ms : Desktop::getInstance().getMouseSources())
3194 {
3195 auto* c = ms.getComponentUnderMouse();
3196
3197 if (c == this || (includeChildren && isParentOf (c)))
3198 if (ms.isDragging() || ! ms.isTouch())
3199 return true;
3200 }
3201
3202 return false;
3203}
3204
3209
3214
3215//==============================================================================
3217{
3218 if (keyListeners == nullptr)
3219 keyListeners.reset (new Array<KeyListener*>());
3220
3221 keyListeners->addIfNotAlreadyThere (newListener);
3222}
3223
3225{
3226 if (keyListeners != nullptr)
3227 keyListeners->removeFirstMatchingValue (listenerToRemove);
3228}
3229
3230bool Component::keyPressed (const KeyPress&) { return false; }
3231bool Component::keyStateChanged (bool /*isKeyDown*/) { return false; }
3232
3234{
3235 if (parentComponent != nullptr)
3236 parentComponent->modifierKeysChanged (modifiers);
3237}
3238
3244
3245//==============================================================================
3247 : safePointer (component)
3248{
3249 jassert (component != nullptr);
3250}
3251
3253{
3254 return safePointer == nullptr;
3255}
3256
3257//==============================================================================
3258void Component::setTitle (const String& newTitle)
3259{
3260 componentTitle = newTitle;
3261}
3262
3263void Component::setDescription (const String& newDescription)
3264{
3265 componentDescription = newDescription;
3266}
3267
3268void Component::setHelpText (const String& newHelpText)
3269{
3270 componentHelpText = newHelpText;
3271}
3272
3273void Component::setAccessible (bool shouldBeAccessible)
3274{
3275 flags.accessibilityIgnoredFlag = ! shouldBeAccessible;
3276
3277 if (flags.accessibilityIgnoredFlag)
3279}
3280
3282{
3283 return (! flags.accessibilityIgnoredFlag
3284 && (parentComponent == nullptr || parentComponent->isAccessible()));
3285}
3286
3287std::unique_ptr<AccessibilityHandler> Component::createAccessibilityHandler()
3288{
3289 return std::make_unique<AccessibilityHandler> (*this, AccessibilityRole::unspecified);
3290}
3291
3292std::unique_ptr<AccessibilityHandler> Component::createIgnoredAccessibilityHandler (Component& comp)
3293{
3294 return std::make_unique<AccessibilityHandler> (comp, AccessibilityRole::ignored);
3295}
3296
3301
3303{
3304 if (! isAccessible() || getWindowHandle() == nullptr)
3305 return nullptr;
3306
3307 if (accessibilityHandler == nullptr
3308 || accessibilityHandler->getTypeIndex() != std::type_index (typeid (*this)))
3309 {
3311
3312 // On Android, notifying that an element was created can cause the system to request
3313 // the accessibility node info for the new element. If we're not careful, this will lead
3314 // to recursive calls, as each time an element is created, new node info will be requested,
3315 // causing an element to be created, causing a new info request...
3316 // By assigning the accessibility handler before notifying the system that an element was
3317 // created, the if() predicate above should evaluate to false on recursive calls,
3318 // terminating the recursion.
3319 if (accessibilityHandler != nullptr)
3321 else
3322 jassertfalse; // createAccessibilityHandler must return non-null
3323 }
3324
3325 return accessibilityHandler.get();
3326}
3327
3328} // namespace juce
Type jmin(const Type a, const Type b)
Definition MathsFunctions.h:60
#define noexcept
Definition DistrhoDefines.h:72
Definition juce_AccessibilityHandler.h:41
Definition juce_AffineTransform.h:43
AffineTransform scaled(float factorX, float factorY) const noexcept
Definition juce_AffineTransform.cpp:129
bool isSingularity() const noexcept
Definition juce_AffineTransform.cpp:208
static AffineTransform scale(float factorX, float factorY) noexcept
Definition juce_AffineTransform.cpp:141
float getDeterminant() const noexcept
Definition juce_AffineTransform.cpp:238
AffineTransform followedBy(const AffineTransform &other) const noexcept
Definition juce_AffineTransform.cpp:65
bool isIdentity() const noexcept
Definition juce_AffineTransform.cpp:52
Definition juce_Array.h:56
Definition juce_BorderSize.h:42
Rectangle< ValueType > subtractedFrom(const Rectangle< ValueType > &original) const noexcept
Definition juce_BorderSize.h:101
Definition juce_CachedComponentImage.h:42
Definition juce_Colour.h:38
uint32 getARGB() const noexcept
Definition juce_Colour.cpp:301
Definition juce_Component.h:2331
bool shouldBailOut() const noexcept
Definition juce_Component.cpp:3252
const WeakReference< Component > safePointer
Definition juce_Component.h:2340
BailOutChecker(Component *component)
Definition juce_Component.cpp:3246
Definition juce_Component.cpp:45
MouseListenerList() noexcept
Definition juce_Component.cpp:47
void addListener(MouseListener *newListener, bool wantsEventsForAllNestedChildComponents)
Definition juce_Component.cpp:49
void removeListener(MouseListener *listenerToRemove)
Definition juce_Component.cpp:65
int numDeepMouseListeners
Definition juce_Component.cpp:155
static void sendMouseEvent(Component &comp, Component::BailOutChecker &checker, void(MouseListener::*eventMethod)(Params...), Params... params)
Definition juce_Component.cpp:110
Array< MouseListener * > listeners
Definition juce_Component.cpp:154
Definition juce_Component.h:2355
Component & component
Definition juce_Component.h:2372
Positioner(Component &component) noexcept
Definition juce_Component.cpp:2266
Component & getComponent() const noexcept
Definition juce_Component.h:2363
Definition juce_ComponentBoundsConstrainer.h:44
Definition juce_Component.h:36
bool contains(Point< int > localPoint)
Definition juce_Component.cpp:1434
virtual void focusLost(FocusChangeType cause)
Definition juce_Component.cpp:2782
void moveKeyboardFocusToSibling(bool moveToNext)
Definition juce_Component.cpp:3038
ImageEffectFilter * effect
Definition juce_Component.h:2542
void mouseMagnify(const MouseEvent &event, float scaleFactor) override
Definition juce_Component.cpp:2310
bool isColourSpecified(int colourID) const
Definition juce_Component.cpp:2231
void paintEntireComponent(Graphics &context, bool ignoreAlphaLevel)
Definition juce_Component.cpp:2071
int proportionOfWidth(float proportion) const noexcept
Definition juce_Component.cpp:1111
static int JUCE_CALLTYPE getNumCurrentlyModalComponents() noexcept
Definition juce_Component.cpp:1837
void setLookAndFeel(LookAndFeel *newLookAndFeel)
Definition juce_Component.cpp:2182
Rectangle< int > getBoundsInParent() const noexcept
Definition juce_Component.cpp:2288
AffineTransform getTransform() const
Definition juce_Component.cpp:1378
virtual ComponentPeer * createNewPeer(int styleFlags, void *nativeWindowToAttachTo)
Definition juce_linux_Windowing.cpp:574
void deleteAllChildren()
Definition juce_Component.cpp:1637
void internalChildrenChanged()
Definition juce_Component.cpp:1694
Component * findChildWithID(StringRef componentID) const noexcept
Definition juce_Component.cpp:1658
void mouseDrag(const MouseEvent &event) override
Definition juce_Component.cpp:2299
void setTransform(const AffineTransform &transform)
Definition juce_Component.cpp:1341
bool isMouseButtonDown(bool includeChildren=false) const
Definition juce_Component.cpp:3177
static void JUCE_CALLTYPE unfocusAllComponents()
Definition juce_Component.cpp:3097
void removeComponentListener(ComponentListener *listenerToRemove)
Definition juce_Component.cpp:2337
void internalChildKeyboardFocusChange(FocusChangeType, const WeakReference< Component > &)
Definition juce_Component.cpp:2823
void setRepaintsOnMouseActivity(bool shouldRepaint) noexcept
Definition juce_Component.cpp:1881
bool isAccessible() const noexcept
Definition juce_Component.cpp:3281
virtual void childBoundsChanged(Component *child)
Definition juce_Component.cpp:2320
void copyAllExplicitColoursTo(Component &target) const
Definition juce_Component.cpp:2248
std::unique_ptr< AffineTransform > affineTransform
Definition juce_Component.h:2538
void setComponentID(const String &newID)
Definition juce_Component.cpp:570
void internalMouseEnter(MouseInputSource, Point< float >, Time)
Definition juce_Component.cpp:2404
void sendVisibilityChangeMessage()
Definition juce_Component.cpp:625
Component * getTopLevelComponent() const noexcept
Definition juce_Component.cpp:1667
String componentTitle
Definition juce_Component.h:2534
virtual void inputAttemptWhenModal()
Definition juce_Component.cpp:2343
WeakReference< LookAndFeel > lookAndFeel
Definition juce_Component.h:2540
virtual void paintOverChildren(Graphics &g)
Definition juce_Component.cpp:1990
void mouseMove(const MouseEvent &event) override
Definition juce_Component.cpp:2300
virtual std::unique_ptr< AccessibilityHandler > createAccessibilityHandler()
Definition juce_Component.cpp:3287
static Component *JUCE_CALLTYPE getCurrentlyModalComponent(int index=0) noexcept
Definition juce_Component.cpp:1842
void setBroughtToFrontOnMouseClick(bool shouldBeBroughtToFront) noexcept
Definition juce_Component.cpp:1848
void giveAwayKeyboardFocus()
Definition juce_Component.cpp:3029
void toBehind(Component *other)
Definition juce_Component.cpp:1004
void setAccessible(bool shouldBeAccessible)
Definition juce_Component.cpp:3273
void setBoundsInset(BorderSize< int > borders)
Definition juce_Component.cpp:1300
void internalMagnifyGesture(MouseInputSource, Point< float >, Time, float)
Definition juce_Component.cpp:2698
void setInterceptsMouseClicks(bool allowClicksOnThisComponent, bool allowClicksOnChildComponents) noexcept
Definition juce_Component.cpp:1420
bool isMouseOverOrDragging(bool includeChildren=false) const
Definition juce_Component.cpp:3191
void internalKeyboardFocusLoss(FocusChangeType)
Definition juce_Component.cpp:2808
void setCentreRelative(float x, float y)
Definition juce_Component.cpp:1273
NamedValueSet properties
Definition juce_Component.h:2549
ComponentFlags flags
Definition juce_Component.h:2589
static bool JUCE_CALLTYPE isMouseButtonDownAnywhere() noexcept
Definition juce_Component.cpp:3205
void grabKeyboardFocusInternal(FocusChangeType, bool canTryParent)
Definition juce_Component.cpp:2965
virtual MouseCursor getMouseCursor()
Definition juce_Component.cpp:1870
bool isVisible() const noexcept
Definition juce_Component.h:122
void removeFromDesktop()
Definition juce_Component.cpp:773
int getScreenY() const
Definition juce_Component.cpp:1132
Component * getParentComponent() const noexcept
Definition juce_Component.h:804
void * getWindowHandle() const
Definition juce_Component.cpp:649
int getNumChildComponents() const noexcept
Definition juce_Component.cpp:1643
uint32 componentFlags
Definition juce_Component.h:2588
void takeKeyboardFocus(FocusChangeType)
Definition juce_Component.cpp:2932
virtual void childrenChanged()
Definition juce_Component.cpp:1692
int proportionOfHeight(float proportion) const noexcept
Definition juce_Component.cpp:1112
String componentDescription
Definition juce_Component.h:2534
std::unique_ptr< MouseListenerList > mouseListeners
Definition juce_Component.h:2546
virtual void parentHierarchyChanged()
Definition juce_Component.cpp:1691
MouseCursor cursor
Definition juce_Component.h:2541
Component * parentComponent
Definition juce_Component.h:2535
Image createComponentSnapshot(Rectangle< int > areaToGrab, bool clipImageToComponentBounds=true, float scaleFactor=1.0f)
Definition juce_Component.cpp:2135
int getScreenX() const
Definition juce_Component.cpp:1131
void setPositioner(Positioner *newPositioner)
Definition juce_Component.cpp:2275
virtual void focusGained(FocusChangeType cause)
Definition juce_Component.cpp:2781
void setTitle(const String &newTitle)
Definition juce_Component.cpp:3258
bool reallyContains(Point< int > localPoint, bool returnTrueIfWithinAChild)
Definition juce_Component.cpp:1454
int getIndexOfChildComponent(const Component *child) const noexcept
Definition juce_Component.cpp:1653
bool isAlwaysOnTop() const noexcept
Definition juce_Component.cpp:1105
bool isOpaque() const noexcept
Definition juce_Component.cpp:843
void setFocusContainerType(FocusContainerType containerType) noexcept
Definition juce_Component.cpp:2862
virtual void minimisationStateChanged(bool isNowMinimised)
Definition juce_Component.cpp:824
Point< int > getPosition() const noexcept
Definition juce_Component.h:286
int getHeight() const noexcept
Definition juce_Component.h:274
void paintComponentAndChildren(Graphics &)
Definition juce_Component.cpp:2006
void grabKeyboardFocus()
Definition juce_Component.cpp:2995
Component * findFocusContainer() const
Definition juce_Component.cpp:2894
ListenerList< ComponentListener > componentListeners
Definition juce_Component.h:2548
Rectangle< int > getLocalArea(const Component *sourceComponent, Rectangle< int > areaRelativeToSourceComponent) const
Definition juce_Component.cpp:1138
void sendFakeMouseMove() const
Definition juce_Component.cpp:2734
bool isTransformed() const noexcept
Definition juce_Component.cpp:1373
virtual void userTriedToCloseWindow()
Definition juce_Component.cpp:812
int getX() const noexcept
Definition juce_Component.h:259
int getExplicitFocusOrder() const
Definition juce_Component.cpp:2906
void toBack()
Definition juce_Component.cpp:1046
void internalMouseUp(MouseInputSource, const PointerState &, Time, const ModifierKeys oldModifiers)
Definition juce_Component.cpp:2555
std::unique_ptr< AccessibilityHandler > accessibilityHandler
Definition juce_Component.h:2554
void toFront(bool shouldAlsoGainKeyboardFocus)
Definition juce_Component.cpp:954
Point< int > getLocalPoint(const Component *sourceComponent, Point< int > pointRelativeToSourceComponent) const
Definition juce_Component.cpp:1136
static Component *JUCE_CALLTYPE getCurrentlyFocusedComponent() noexcept
Definition juce_Component.cpp:3092
bool isShowing() const
Definition juce_Component.cpp:634
virtual std::unique_ptr< ComponentTraverser > createKeyboardFocusTraverser()
Definition juce_Component.cpp:2924
void sendLookAndFeelChange()
Definition juce_Component.cpp:2194
void setTopRightPosition(int x, int y)
Definition juce_Component.cpp:1267
static float JUCE_CALLTYPE getApproximateScaleFactorForComponent(const Component *targetComponent)
Definition juce_Component.cpp:1383
void giveAwayKeyboardFocusInternal(bool sendFocusLossEvent)
Definition juce_Component.cpp:3010
void setAlpha(float newAlpha)
Definition juce_Component.cpp:1892
void addComponentListener(ComponentListener *newListener)
Definition juce_Component.cpp:2323
void mouseUp(const MouseEvent &event) override
Definition juce_Component.cpp:2298
void addAndMakeVisible(Component *child, int zOrder=-1)
Definition juce_Component.cpp:1554
virtual bool canModalEventBeSentToComponent(const Component *targetComponent)
Definition juce_Component.cpp:2349
FocusChangeType
Definition juce_Component.h:1890
@ focusChangedByTabKey
Definition juce_Component.h:1892
@ focusChangedDirectly
Definition juce_Component.h:1893
@ focusChangedByMouseClick
Definition juce_Component.h:1891
void mouseExit(const MouseEvent &event) override
Definition juce_Component.cpp:2296
void setPaintingIsUnclipped(bool shouldPaintWithoutClipping) noexcept
Definition juce_Component.cpp:2124
void setAlwaysOnTop(bool shouldStayOnTop)
Definition juce_Component.cpp:1074
Positioner * getPositioner() const noexcept
Definition juce_Component.cpp:2270
float getAlpha() const noexcept
Definition juce_Component.cpp:1887
uint8 componentTransparency
Definition juce_Component.h:2592
bool hasKeyboardFocus(bool trueIfChildIsFocused) const
Definition juce_Component.cpp:3086
virtual void alphaChanged()
Definition juce_Component.cpp:1903
bool isCurrentlyBlockedByAnotherModalComponent() const
Definition juce_Component.cpp:1832
void addMouseListener(MouseListener *newListener, bool wantsEventsForAllNestedChildComponents)
Definition juce_Component.cpp:2376
void setDescription(const String &newDescription)
Definition juce_Component.cpp:3263
bool isBroughtToFrontOnMouseClick() const noexcept
Definition juce_Component.cpp:1853
String componentName
Definition juce_Component.h:2534
static Component * currentlyFocusedComponent
Definition juce_Component.h:2531
AccessibilityHandler * getAccessibilityHandler()
Definition juce_Component.cpp:3302
void setOpaque(bool shouldBeOpaque)
Definition juce_Component.cpp:829
void setMouseCursor(const MouseCursor &cursorType)
Definition juce_Component.cpp:1859
void setCentrePosition(int x, int y)
Definition juce_Component.cpp:1271
void postCommandMessage(int commandId)
Definition juce_Component.cpp:2361
virtual void enablementChanged()
Definition juce_Component.cpp:3135
virtual void modifierKeysChanged(const ModifierKeys &modifiers)
Definition juce_Component.cpp:3233
void mouseEnter(const MouseEvent &event) override
Definition juce_Component.cpp:2295
void setEnabled(bool shouldBeEnabled)
Definition juce_Component.cpp:3110
Rectangle< int > getBounds() const noexcept
Definition juce_Component.h:304
void repaint()
Definition juce_Component.cpp:1917
void sendMovedResizedMessagesIfPending()
Definition juce_Component.cpp:1202
void addKeyListener(KeyListener *newListener)
Definition juce_Component.cpp:3216
Component() noexcept
Definition juce_Component.cpp:517
FocusContainerType
Definition juce_Component.h:1277
@ focusContainer
Definition juce_Component.h:1295
@ keyboardFocusContainer
Definition juce_Component.h:1307
Rectangle< int > getScreenBounds() const
Definition juce_Component.cpp:1134
std::unique_ptr< Positioner > positioner
Definition juce_Component.h:2537
void getInterceptsMouseClicks(bool &allowsClicksOnThisComponent, bool &allowsClicksOnChildComponents) const noexcept
Definition juce_Component.cpp:1427
WeakReference< Component >::Master masterReference
Definition juce_Component.h:2552
Point< int > getMouseXYRelative() const
Definition juce_Component.cpp:3210
void removeMouseListener(MouseListener *listenerToRemove)
Definition juce_Component.cpp:2393
bool isOnDesktop() const noexcept
Definition juce_Component.cpp:796
void internalHierarchyChanged()
Definition juce_Component.cpp:1711
void internalMouseWheel(MouseInputSource, Point< float >, Time, const MouseWheelDetails &)
Definition juce_Component.cpp:2662
virtual bool hitTest(int x, int y)
Definition juce_Component.cpp:1400
void exitModalState(int returnValue)
Definition juce_Component.cpp:1795
void setBoundsToFit(Rectangle< int > targetArea, Justification justification, bool onlyReduceInSize)
Definition juce_Component.cpp:1305
std::unique_ptr< Array< KeyListener * > > keyListeners
Definition juce_Component.h:2547
bool getMouseClickGrabsKeyboardFocus() const noexcept
Definition juce_Component.cpp:2852
virtual void resized()
Definition juce_Component.cpp:2318
Rectangle< int > localAreaToGlobal(Rectangle< int > localArea) const
Definition juce_Component.cpp:1143
void reorderChildInternal(int sourceIndex, int destIndex)
Definition juce_Component.cpp:939
bool isKeyboardFocusContainer() const noexcept
Definition juce_Component.cpp:2875
int getY() const noexcept
Definition juce_Component.h:268
virtual void setName(const String &newName)
Definition juce_Component.cpp:551
void removeChildComponent(Component *childToRemove)
Definition juce_Component.cpp:1569
std::unique_ptr< CachedComponentImage > cachedImage
Definition juce_Component.h:2543
Component * getChildComponent(int index) const noexcept
Definition juce_Component.cpp:1648
bool isParentOf(const Component *possibleChild) const noexcept
Definition juce_Component.cpp:1677
void removeColour(int colourID)
Definition juce_Component.cpp:2236
void internalMouseDrag(MouseInputSource, const PointerState &, Time)
Definition juce_Component.cpp:2601
void removeAllChildren()
Definition juce_Component.cpp:1631
String componentID
Definition juce_Component.h:2534
virtual void addToDesktop(int windowStyleFlags, void *nativeWindowToAttachTo=nullptr)
Definition juce_Component.cpp:658
void setBufferedToImage(bool shouldBeBuffered)
Definition juce_Component.cpp:919
void setBounds(int x, int y, int width, int height)
Definition juce_Component.cpp:1147
void setSize(int newWidth, int newHeight)
Definition juce_Component.cpp:1262
virtual bool keyStateChanged(bool isKeyDown)
Definition juce_Component.cpp:3231
void setColour(int colourID, Colour newColour)
Definition juce_Component.cpp:2242
void enterModalState(bool takeKeyboardFocus=true, ModalComponentManager::Callback *callback=nullptr, bool deleteWhenDismissed=false)
Definition juce_Component.cpp:1764
bool isPaintingUnclipped() const noexcept
Definition juce_Component.cpp:2129
Array< Component * > childComponentList
Definition juce_Component.h:2539
void setWantsKeyboardFocus(bool wantsFocus) noexcept
Definition juce_Component.cpp:2842
Colour findColour(int colourID, bool inheritFromParent=false) const
Definition juce_Component.cpp:2219
void internalMouseExit(MouseInputSource, Point< float >, Time)
Definition juce_Component.cpp:2440
bool isMouseOver(bool includeChildren=false) const
Definition juce_Component.cpp:3159
void setMouseClickGrabsKeyboardFocus(bool shouldGrabFocus)
Definition juce_Component.cpp:2847
void mouseDoubleClick(const MouseEvent &event) override
Definition juce_Component.cpp:2301
virtual void parentSizeChanged()
Definition juce_Component.cpp:2321
Rectangle< int > getParentMonitorArea() const
Definition juce_Component.cpp:1126
void internalMouseDown(MouseInputSource, const PointerState &, Time)
Definition juce_Component.cpp:2477
static std::unique_ptr< AccessibilityHandler > createIgnoredAccessibilityHandler(Component &)
Definition juce_Component.cpp:3292
int getWidth() const noexcept
Definition juce_Component.h:271
~Component() override
Definition juce_Component.cpp:527
void internalKeyboardFocusGain(FocusChangeType, const WeakReference< Component > &)
Definition juce_Component.cpp:2790
void mouseWheelMove(const MouseEvent &event, const MouseWheelDetails &wheel) override
Definition juce_Component.cpp:2303
bool isFocusContainer() const noexcept
Definition juce_Component.cpp:2870
void internalMouseMove(MouseInputSource, Point< float >, Time)
Definition juce_Component.cpp:2628
static void JUCE_CALLTYPE beginDragAutoRepeat(int millisecondsBetweenCallbacks)
Definition juce_Component.cpp:2745
bool isEnabled() const noexcept
Definition juce_Component.cpp:3104
virtual std::unique_ptr< ComponentTraverser > createFocusTraverser()
Definition juce_Component.cpp:2916
Point< int > localPointToGlobal(Point< int > localPoint) const
Definition juce_Component.cpp:1141
bool getWantsKeyboardFocus() const noexcept
Definition juce_Component.cpp:2857
void updateMouseCursor() const
Definition juce_Component.cpp:1875
void addChildAndSetID(Component *child, const String &componentID)
Definition juce_Component.cpp:1560
ComponentPeer * getPeer() const
Definition juce_Component.cpp:801
virtual void focusOfChildComponentChanged(FocusChangeType cause)
Definition juce_Component.cpp:2783
void internalRepaintUnchecked(Rectangle< int >, bool)
Definition juce_Component.cpp:1946
LookAndFeel & getLookAndFeel() const noexcept
Definition juce_Component.cpp:2173
virtual bool keyPressed(const KeyPress &key)
Definition juce_Component.cpp:3230
void setExplicitFocusOrder(int newFocusOrderIndex)
Definition juce_Component.cpp:2911
void setHelpText(const String &newHelpText)
Definition juce_Component.cpp:3268
Rectangle< int > getLocalBounds() const noexcept
Definition juce_Component.cpp:2283
int getParentWidth() const noexcept
Definition juce_Component.cpp:1114
Point< int > getScreenPosition() const
Definition juce_Component.cpp:1133
void setComponentEffect(ImageEffectFilter *newEffect)
Definition juce_Component.cpp:2163
void internalModalInputAttempt()
Definition juce_Component.cpp:2354
void setTopLeftPosition(int x, int y)
Definition juce_Component.cpp:1264
virtual void broughtToFront()
Definition juce_Component.cpp:2751
void centreWithSize(int width, int height)
Definition juce_Component.cpp:1290
String componentHelpText
Definition juce_Component.h:2534
virtual void lookAndFeelChanged()
Definition juce_Component.cpp:2191
void sendMovedResizedMessages(bool wasMoved, bool wasResized)
Definition juce_Component.cpp:1216
void internalBroughtToFront()
Definition juce_Component.cpp:2755
virtual void colourChanged()
Definition juce_Component.cpp:2192
Component * findKeyboardFocusContainer() const
Definition juce_Component.cpp:2899
void sendEnablementChangeMessage()
Definition juce_Component.cpp:3137
void addChildComponent(Component *child, int zOrder=-1)
Definition juce_Component.cpp:1548
friend class ComponentPeer
Definition juce_Component.h:2527
virtual void paint(Graphics &g)
Definition juce_Component.cpp:1983
void internalRepaint(Rectangle< int >)
Definition juce_Component.cpp:1938
void internalModifierKeysChanged()
Definition juce_Component.cpp:3239
bool isCurrentlyModal(bool onlyConsiderForemostModalComponent=true) const noexcept
Definition juce_Component.cpp:1824
void mouseDown(const MouseEvent &event) override
Definition juce_Component.cpp:2297
virtual void setVisible(bool shouldBeVisible)
Definition juce_Component.cpp:575
void invalidateAccessibilityHandler()
Definition juce_Component.cpp:3297
virtual void visibilityChanged()
Definition juce_Component.cpp:623
void removeKeyListener(KeyListener *listenerToRemove)
Definition juce_Component.cpp:3224
Component * getComponentAt(int x, int y)
Definition juce_Component.cpp:1495
void repaintParent()
Definition juce_Component.cpp:1932
Rectangle< int > boundsRelativeToParent
Definition juce_Component.h:2536
virtual float getDesktopScaleFactor() const
Definition juce_Component.cpp:826
int getParentHeight() const noexcept
Definition juce_Component.cpp:1120
void paintWithinParentContext(Graphics &)
Definition juce_Component.cpp:1996
void setCachedComponentImage(CachedComponentImage *newCachedImage)
Definition juce_Component.cpp:910
virtual void moved()
Definition juce_Component.cpp:2319
void setBoundsRelative(float proportionalX, float proportionalY, float proportionalWidth, float proportionalHeight)
Definition juce_Component.cpp:1285
virtual void handleCommandMessage(int commandId)
Definition juce_Component.cpp:2370
Definition juce_ComponentListener.h:43
@ windowIsSemiTransparent
Definition juce_ComponentPeer.h:78
static ComponentPeer * getPeerFor(const Component *) noexcept
Definition juce_ComponentPeer.cpp:61
static Point< int > getMousePosition()
Definition juce_Desktop.cpp:153
static Desktop &JUCE_CALLTYPE getInstance()
Definition juce_Desktop.cpp:50
Definition juce_GraphicsContext.h:660
Definition juce_GraphicsContext.h:45
void addTransform(const AffineTransform &transform)
Definition juce_GraphicsContext.cpp:255
LowLevelGraphicsContext & getInternalContext() const noexcept
Definition juce_GraphicsContext.h:736
Definition juce_Identifier.h:39
Definition juce_ImageEffectFilter.h:43
Definition juce_Image.h:58
@ ARGB
Definition juce_Image.h:67
@ RGB
Definition juce_Image.h:66
Definition juce_Justification.h:41
const Rectangle< ValueType > appliedToRectangle(const Rectangle< ValueType > &areaToAdjust, const Rectangle< ValueType > &targetSpace) const noexcept
Definition juce_Justification.h:93
Definition juce_KeyListener.h:41
Definition juce_KeyPress.h:40
Definition juce_LookAndFeel.h:108
static LookAndFeel & getDefaultLookAndFeel() noexcept
Definition juce_LookAndFeel.cpp:107
virtual void addTransform(const AffineTransform &)=0
static bool callAsync(std::function< void()> functionToCall)
Definition juce_MessageManager.cpp:192
static MessageManager * getInstance()
Definition juce_MessageManager.cpp:47
Definition juce_ModalComponentManager.h:56
Definition juce_ModifierKeys.h:41
static ModifierKeys currentModifiers
Definition juce_ModifierKeys.h:189
Definition juce_MouseCursor.h:39
@ NormalCursor
Definition juce_MouseCursor.h:48
Definition juce_MouseEvent.h:39
Definition juce_MouseInputSource.h:52
int getNumberOfMultipleClicks() const noexcept
Definition juce_MouseInputSource.cpp:590
ModifierKeys getCurrentModifiers() const noexcept
Definition juce_MouseInputSource.cpp:579
Time getLastMouseDownTime() const noexcept
Definition juce_MouseInputSource.cpp:591
void showMouseCursor(const MouseCursor &cursor)
Definition juce_MouseInputSource.cpp:600
bool isLongPressOrDrag() const noexcept
Definition juce_MouseInputSource.cpp:593
Point< float > getLastMouseDownPosition() const noexcept
Definition juce_MouseInputSource.cpp:592
Definition juce_MouseListener.h:39
virtual void mouseEnter(const MouseEvent &event)
Definition juce_MouseListener.cpp:29
virtual void mouseMagnify(const MouseEvent &event, float scaleFactor)
Definition juce_MouseListener.cpp:37
virtual void mouseMove(const MouseEvent &event)
Definition juce_MouseListener.cpp:34
virtual void mouseUp(const MouseEvent &event)
Definition juce_MouseListener.cpp:32
virtual void mouseDrag(const MouseEvent &event)
Definition juce_MouseListener.cpp:33
virtual void mouseDoubleClick(const MouseEvent &event)
Definition juce_MouseListener.cpp:35
virtual void mouseDown(const MouseEvent &event)
Definition juce_MouseListener.cpp:31
virtual void mouseExit(const MouseEvent &event)
Definition juce_MouseListener.cpp:30
virtual void mouseWheelMove(const MouseEvent &event, const MouseWheelDetails &wheel)
Definition juce_MouseListener.cpp:36
bool set(const Identifier &name, const var &newValue)
Definition juce_NamedValueSet.cpp:183
Definition juce_Point.h:42
constexpr Point< float > toFloat() const noexcept
Definition juce_Point.h:234
constexpr Point< int > roundToInt() const noexcept
Definition juce_Point.h:240
ValueType y
Definition juce_Point.h:247
ValueType x
Definition juce_Point.h:246
Definition juce_PointerState.h:32
Point< float > position
Definition juce_PointerState.h:52
Definition juce_Rectangle.h:67
JUCE_NODISCARD Rectangle withZeroOrigin() const noexcept
Definition juce_Rectangle.h:238
bool contains(ValueType xCoord, ValueType yCoord) const noexcept
Definition juce_Rectangle.h:622
Rectangle getIntersection(Rectangle other) const noexcept
Definition juce_Rectangle.h:664
ValueType getHeight() const noexcept
Definition juce_Rectangle.h:136
ValueType getWidth() const noexcept
Definition juce_Rectangle.h:133
bool isEmpty() const noexcept
Definition juce_Rectangle.h:121
Definition juce_RectangleList.h:43
Definition juce_String.h:53
Definition juce_StringRef.h:62
Definition juce_Time.h:37
static Time JUCE_CALLTYPE getCurrentTime() noexcept
Definition juce_Time.cpp:233
Definition juce_WeakReference.h:78
ObjectType * get() const noexcept
Definition juce_WeakReference.h:102
* e
Definition inflate.c:1404
UINT_D64 w
Definition inflate.c:942
int * l
Definition inflate.c:1579
struct huft * t
Definition inflate.c:943
register unsigned j
Definition inflate.c:1576
int y
Definition inflate.c:1588
unsigned v[N_MAX]
Definition inflate.c:1584
int g
Definition inflate.c:1573
register unsigned i
Definition inflate.c:1575
unsigned x[BMAX+1]
Definition inflate.c:1586
static const char * name
Definition pugl.h:1582
static int int height
Definition pugl.h:1594
static int width
Definition pugl.h:1593
static uintptr_t parent
Definition pugl.h:1644
#define JUCE_BEGIN_IGNORE_WARNINGS_MSVC(warnings)
Definition juce_CompilerWarnings.h:198
#define JUCE_END_IGNORE_WARNINGS_MSVC
Definition juce_CompilerWarnings.h:199
#define JUCE_ASSERT_MESSAGE_MANAGER_IS_LOCKED
Definition juce_MessageManager.h:465
#define jassert(expression)
#define JUCE_DECLARE_NON_COPYABLE(className)
#define JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(className)
#define jassertfalse
#define JUCE_CALLTYPE
#define JUCE_ASSERT_MESSAGE_MANAGER_IS_LOCKED_OR_OFFSCREEN
Definition juce_gui_basics.cpp:102
float in
Definition lilv_test.c:1460
static int JUCE_CDECL comp(const void *a, const void *b)
Definition lsp.c:298
const Colour transparentBlack
Definition juce_Colours.h:40
const Colour black
Definition juce_Colours.h:50
Definition carla_juce.cpp:31
constexpr Type jmin(Type a, Type b)
Definition juce_MathsFunctions.h:106
unsigned int uint32
Definition juce_MathsFunctions.h:45
constexpr Type jmax(Type a, Type b)
Definition juce_MathsFunctions.h:94
RangedDirectoryIterator end(const RangedDirectoryIterator &)
Definition juce_RangedDirectoryIterator.h:184
@ elementCreated
Definition juce_AccessibilityHandler.cpp:33
@ elementMovedOrResized
Definition juce_AccessibilityHandler.cpp:35
@ windowOpened
Definition juce_AccessibilityHandler.cpp:37
@ windowClosed
Definition juce_AccessibilityHandler.cpp:38
void notifyAccessibilityEventInternal(const AccessibilityHandler &, InternalAccessibilityEvent)
Definition juce_gui_basics.cpp:336
Type jlimit(Type lowerLimit, Type upperLimit, Type valueToConstrain) noexcept
Definition juce_MathsFunctions.h:262
auto makeMouseEvent(MouseInputSource source, const PointerState &ps, ModifierKeys modifiers, Component *eventComponent, Component *originator, Time eventTime, Point< float > mouseDownPos, Time mouseDownTime, int numberOfClicks, bool mouseWasDragged)
Definition juce_PointerState.h:78
static const Identifier juce_explicitFocusOrderId("_jexfo")
@ structureChanged
Definition juce_AccessibilityEvent.h:57
jack_client_t client jack_client_t client jack_client_t client jack_client_t JackInfoShutdownCallback function
Definition juce_linux_JackAudio.cpp:63
static Component * findContainer(const Component *child, FocusContainerFn isFocusContainer)
Definition juce_Component.cpp:2881
static const char colourPropertyPrefix[]
Definition juce_Component.cpp:292
int pointer_sized_int
Definition juce_MathsFunctions.h:80
unsigned char uint8
Definition juce_MathsFunctions.h:37
static Component * findFirstEnabledAncestor(Component *in)
Definition juce_Component.cpp:29
int roundToInt(const FloatType value) noexcept
Definition juce_MathsFunctions.h:465
@ list
Definition juce_AccessibilityRole.h:56
@ image
Definition juce_AccessibilityRole.h:42
@ unspecified
Definition juce_AccessibilityRole.h:68
@ ignored
Definition juce_AccessibilityRole.h:67
constexpr int numElementsInArray(Type(&)[N]) noexcept
Definition juce_MathsFunctions.h:344
Definition juce_Component.cpp:296
static PointOrRect rawPeerPositionToLocal(const Component &comp, PointOrRect pos) noexcept
Definition juce_Component.cpp:336
static PointOrRect convertFromDistantParentSpace(const Component *parent, const Component &target, PointOrRect coordInParent)
Definition juce_Component.cpp:400
static PointOrRect convertToParentSpace(const Component &comp, const PointOrRect pointInLocalSpace)
Definition juce_Component.cpp:376
static Identifier getColourPropertyID(int colourID)
Definition juce_Component.cpp:304
static void releaseAllCachedImageResources(Component &c)
Definition juce_Component.cpp:488
static PointOrRect convertFromParentSpace(const Component &comp, const PointOrRect pointInParentSpace)
Definition juce_Component.cpp:355
static PointOrRect convertCoordinate(const Component *target, const Component *source, PointOrRect p)
Definition juce_Component.cpp:414
static bool hitTest(Component &comp, Point< float > localPoint)
Definition juce_Component.cpp:327
static bool modalWouldBlockComponent(const Component &maybeBlocked, Component *modal)
Definition juce_Component.cpp:498
static void sendMouseEventToComponentsThatAreBlockedByModal(Component &modal, Function &&function)
Definition juce_Component.cpp:507
static bool clipObscuredRegions(const Component &comp, Graphics &g, const Rectangle< int > clipRect, Point< int > delta)
Definition juce_Component.cpp:446
static Rectangle< int > getParentOrMainMonitorBounds(const Component &comp)
Definition juce_Component.cpp:480
static PointOrRect localPositionToRawPeerPos(const Component &comp, PointOrRect pos) noexcept
Definition juce_Component.cpp:346
bool shouldBailOut() const noexcept
Definition juce_Component.cpp:164
BailOutChecker2(Component::BailOutChecker &boc, Component *comp)
Definition juce_Component.cpp:159
Component::BailOutChecker & checker
Definition juce_Component.cpp:170
const WeakReference< Component > safePointer
Definition juce_Component.cpp:171
~FocusRestorer()
Definition juce_Component.cpp:184
WeakReference< Component > lastFocus
Definition juce_Component.cpp:192
FocusRestorer()
Definition juce_Component.cpp:182
Definition juce_MouseEvent.h:392
Definition juce_Component.cpp:199
static Point< int > addPosition(Point< int > p, const Component &c) noexcept
Definition juce_Component.cpp:270
static Point< float > subtractPosition(Point< float > p, const Component &c) noexcept
Definition juce_Component.cpp:276
static PointOrRect scaledScreenPosToUnscaled(float scale, PointOrRect pos) noexcept
Definition juce_Component.cpp:207
static Point< float > screenPosToLocalPos(Component &comp, Point< float > pos)
Definition juce_Component.cpp:279
static Rectangle< float > subtractPosition(Rectangle< float > p, const Component &c) noexcept
Definition juce_Component.cpp:277
static Rectangle< float > addPosition(Rectangle< float > p, const Component &c) noexcept
Definition juce_Component.cpp:273
static Rectangle< int > subtractPosition(Rectangle< int > p, const Component &c) noexcept
Definition juce_Component.cpp:275
static Rectangle< int > unscaledScreenPosToScaled(float scale, Rectangle< int > pos) noexcept
Definition juce_Component.cpp:214
static Rectangle< float > unscaledScreenPosToScaled(float scale, Rectangle< float > pos) noexcept
Definition juce_Component.cpp:230
static Rectangle< float > scaledScreenPosToUnscaled(float scale, Rectangle< float > pos) noexcept
Definition juce_Component.cpp:238
static PointOrRect scaledScreenPosToUnscaled(const Component &comp, PointOrRect pos) noexcept
Definition juce_Component.cpp:265
static PointOrRect unscaledScreenPosToScaled(float scale, PointOrRect pos) noexcept
Definition juce_Component.cpp:201
static Point< int > subtractPosition(Point< int > p, const Component &c) noexcept
Definition juce_Component.cpp:274
static Rectangle< int > scaledScreenPosToUnscaled(float scale, Rectangle< int > pos) noexcept
Definition juce_Component.cpp:222
static PointOrRect unscaledScreenPosToScaled(const Component &comp, PointOrRect pos) noexcept
Definition juce_Component.cpp:259
static Point< float > addPosition(Point< float > p, const Component &c) noexcept
Definition juce_Component.cpp:272
static Rectangle< int > addPosition(Rectangle< int > p, const Component &c) noexcept
Definition juce_Component.cpp:271
static PointOrRect unscaledScreenPosToScaled(PointOrRect pos) noexcept
Definition juce_Component.cpp:247
static PointOrRect scaledScreenPosToUnscaled(PointOrRect pos) noexcept
Definition juce_Component.cpp:253
Definition juce_Component.cpp:850
float scale
Definition juce_Component.cpp:905
bool invalidate(const Rectangle< int > &area) override
Definition juce_Component.cpp:898
StandardCachedComponentImage(Component &c) noexcept
Definition juce_Component.cpp:851
Component & owner
Definition juce_Component.cpp:904
void releaseResources() override
Definition juce_Component.cpp:899
bool invalidateAll() override
Definition juce_Component.cpp:897
Image image
Definition juce_Component.cpp:902
void paint(Graphics &g) override
Definition juce_Component.cpp:853
RectangleList< int > validArea
Definition juce_Component.cpp:903
RECT const char void(* callback)(const char *droppath))) SWELL_API_DEFINE(BOOL
Definition swell-functions.h:1004
uch * p
Definition crypt.c:594
return c
Definition crypt.c:175
int r
Definition crypt.c:458
uch h[RAND_HEAD_LEN]
Definition crypt.c:459
void handler(int signal)
Definition fileio.c:1632
ss
Definition zipinfo.c:2292
#define const
Definition zconf.h:137