The JUCE cross-platform C++ framework, with DISTRHO/KXStudio specific changes
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

151 lines
4.9KB

  1. /*
  2. ==============================================================================
  3. This file is part of the JUCE library - "Jules' Utility Class Extensions"
  4. Copyright 2004-11 by Raw Material Software Ltd.
  5. ------------------------------------------------------------------------------
  6. JUCE can be redistributed and/or modified under the terms of the GNU General
  7. Public License (Version 2), as published by the Free Software Foundation.
  8. A copy of the license is included in the JUCE distribution, or can be found
  9. online at www.gnu.org/licenses.
  10. JUCE is distributed in the hope that it will be useful, but WITHOUT ANY
  11. WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
  12. A PARTICULAR PURPOSE. See the GNU General Public License for more details.
  13. ------------------------------------------------------------------------------
  14. To release a closed-source product which uses JUCE, commercial licenses are
  15. available: visit www.rawmaterialsoftware.com/juce for more information.
  16. ==============================================================================
  17. */
  18. class NSViewAttachment : public ReferenceCountedObject,
  19. public ComponentMovementWatcher
  20. {
  21. public:
  22. NSViewAttachment (NSView* const view_, Component& owner_)
  23. : ComponentMovementWatcher (&owner_),
  24. view (view_),
  25. owner (owner_),
  26. currentPeer (nullptr)
  27. {
  28. [view_ retain];
  29. if (owner.isShowing())
  30. componentPeerChanged();
  31. }
  32. ~NSViewAttachment()
  33. {
  34. removeFromParent();
  35. [view release];
  36. }
  37. void componentMovedOrResized (Component& comp, bool wasMoved, bool wasResized)
  38. {
  39. ComponentMovementWatcher::componentMovedOrResized (comp, wasMoved, wasResized);
  40. // The ComponentMovementWatcher version of this method avoids calling
  41. // us when the top-level comp is resized, but for an NSView we need to know this
  42. // because with inverted co-ords, we need to update the position even if the
  43. // top-left pos hasn't changed
  44. if (comp.isOnDesktop() && wasResized)
  45. componentMovedOrResized (wasMoved, wasResized);
  46. }
  47. void componentMovedOrResized (bool /*wasMoved*/, bool /*wasResized*/)
  48. {
  49. Component* const topComp = owner.getTopLevelComponent();
  50. if (topComp->getPeer() != nullptr)
  51. {
  52. const Rectangle<int> area (topComp->getLocalArea (&owner, owner.getLocalBounds()));
  53. NSRect r = NSMakeRect ((float) area.getX(), (float) area.getY(), (float) area.getWidth(), (float) area.getHeight());
  54. r.origin.y = [[view superview] frame].size.height - (r.origin.y + r.size.height);
  55. [view setFrame: r];
  56. }
  57. }
  58. void componentPeerChanged()
  59. {
  60. ComponentPeer* const peer = owner.getPeer();
  61. if (currentPeer != peer)
  62. {
  63. removeFromParent();
  64. currentPeer = peer;
  65. if (peer != nullptr)
  66. {
  67. NSView* const peerView = (NSView*) peer->getNativeHandle();
  68. [peerView addSubview: view];
  69. componentMovedOrResized (false, false);
  70. }
  71. }
  72. [view setHidden: ! owner.isShowing()];
  73. }
  74. void componentVisibilityChanged()
  75. {
  76. componentPeerChanged();
  77. }
  78. NSView* const view;
  79. private:
  80. Component& owner;
  81. ComponentPeer* currentPeer;
  82. void removeFromParent()
  83. {
  84. if ([view superview] != nil)
  85. [view removeFromSuperview]; // Must be careful not to call this unless it's required - e.g. some Apple AU views
  86. // override the call and use it as a sign that they're being deleted, which breaks everything..
  87. }
  88. JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (NSViewAttachment);
  89. };
  90. //==============================================================================
  91. NSViewComponent::NSViewComponent() {}
  92. NSViewComponent::~NSViewComponent() {}
  93. void NSViewComponent::setView (void* const view)
  94. {
  95. if (view != getView())
  96. {
  97. attachment = nullptr;
  98. if (view != nullptr)
  99. attachment = attachViewToComponent (*this, view);
  100. }
  101. }
  102. void* NSViewComponent::getView() const
  103. {
  104. return attachment != nullptr ? static_cast <NSViewAttachment*> (attachment.getObject())->view
  105. : nullptr;
  106. }
  107. void NSViewComponent::resizeToFitView()
  108. {
  109. if (attachment != nullptr)
  110. {
  111. NSRect r = [static_cast <NSViewAttachment*> (attachment.getObject())->view frame];
  112. setBounds (Rectangle<int> ((int) r.size.width, (int) r.size.height));
  113. }
  114. }
  115. void NSViewComponent::paint (Graphics&) {}
  116. ReferenceCountedObject* NSViewComponent::attachViewToComponent (Component& comp, void* const view)
  117. {
  118. return new NSViewAttachment ((NSView*) view, comp);
  119. }