diff --git a/modules/juce_gui_basics/native/accessibility/juce_Accessibility_mac.mm b/modules/juce_gui_basics/native/accessibility/juce_Accessibility_mac.mm index 93d7f47584..ec2a6897a0 100644 --- a/modules/juce_gui_basics/native/accessibility/juce_Accessibility_mac.mm +++ b/modules/juce_gui_basics/native/accessibility/juce_Accessibility_mac.mm @@ -784,6 +784,9 @@ private: for (auto* childHandler : children) [accessibleChildren addObject: static_cast (childHandler->getNativeImplementation())]; + if (auto* nativeChild = AccessibilityHandler::getNativeChildForComponent (handler->getComponent())) + [accessibleChildren addObject: static_cast (nativeChild)]; + return accessibleChildren; } diff --git a/modules/juce_gui_extra/embedding/juce_NSViewComponent.h b/modules/juce_gui_extra/embedding/juce_NSViewComponent.h index a935de7503..d9344cc042 100644 --- a/modules/juce_gui_extra/embedding/juce_NSViewComponent.h +++ b/modules/juce_gui_extra/embedding/juce_NSViewComponent.h @@ -84,6 +84,8 @@ public: void alphaChanged() override; /** @internal */ static ReferenceCountedObject* attachViewToComponent (Component&, void*); + /** @internal */ + std::unique_ptr createAccessibilityHandler() override; private: ReferenceCountedObjectPtr attachment; diff --git a/modules/juce_gui_extra/native/juce_NSViewComponent_mac.mm b/modules/juce_gui_extra/native/juce_NSViewComponent_mac.mm index 762e747c46..4124df4e04 100644 --- a/modules/juce_gui_extra/native/juce_NSViewComponent_mac.mm +++ b/modules/juce_gui_extra/native/juce_NSViewComponent_mac.mm @@ -32,8 +32,7 @@ class NSViewAttachment : public ReferenceCountedObject, public: NSViewAttachment (NSView* v, Component& comp) : ComponentMovementWatcher (&comp), - view (v), owner (comp), - currentPeer (nullptr) + view (v), owner (comp) { [view retain]; [view setPostsFrameChangedNotifications: YES]; @@ -75,14 +74,19 @@ public: { auto* peer = owner.getPeer(); - if (currentPeer != peer) + if (std::exchange (currentPeer, peer) != peer) { - currentPeer = peer; - if (peer != nullptr) { auto peerView = (NSView*) peer->getNativeHandle(); [peerView addSubview: view]; + + if (@available (macOS 10.10, *)) + { + previousAccessibilityParent = [view accessibilityParent]; + [view setAccessibilityParent:static_cast (owner.getAccessibilityHandler()->getNativeImplementation())]; + } + componentMovedOrResized (false, false); } else @@ -110,11 +114,16 @@ public: private: Component& owner; - ComponentPeer* currentPeer; + ComponentPeer* currentPeer = nullptr; NSViewFrameWatcher frameWatcher { view, [this] { owner.childBoundsChanged (nullptr); } }; + id previousAccessibilityParent = nil; void removeFromParent() { + if (@available (macOS 10.10, *)) + if (previousAccessibilityParent != nil) + [view setAccessibilityParent: previousAccessibilityParent]; + if ([view superview] != nil) [view removeFromSuperview]; // Must be careful not to call this unless it's required - e.g. some Apple AU views // override the call and use it as a sign that they're being deleted, which breaks everything.. @@ -125,7 +134,10 @@ private: //============================================================================== NSViewComponent::NSViewComponent() = default; -NSViewComponent::~NSViewComponent() = default; +NSViewComponent::~NSViewComponent() +{ + AccessibilityHandler::setNativeChildForComponent (*this, nullptr); +} void NSViewComponent::setView (void* view) { @@ -139,6 +151,8 @@ void NSViewComponent::setView (void* view) attachment = attachViewToComponent (*this, view); old = nullptr; + + AccessibilityHandler::setNativeChildForComponent (*this, getView()); } } @@ -183,4 +197,9 @@ ReferenceCountedObject* NSViewComponent::attachViewToComponent (Component& comp, return new NSViewAttachment ((NSView*) view, comp); } +std::unique_ptr NSViewComponent::createAccessibilityHandler() +{ + return std::make_unique (*this, AccessibilityRole::group); +} + } // namespace juce