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.

256 lines
10KB

  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. #ifndef __JUCE_DRAWABLE_JUCEHEADER__
  19. #define __JUCE_DRAWABLE_JUCEHEADER__
  20. #include "../components/juce_Component.h"
  21. #include "../positioning/juce_RelativeCoordinate.h"
  22. #include "../positioning/juce_RelativeCoordinatePositioner.h"
  23. #include "../layout/juce_ComponentBuilder.h"
  24. class DrawableComposite;
  25. //==============================================================================
  26. /**
  27. The base class for objects which can draw themselves, e.g. polygons, images, etc.
  28. @see DrawableComposite, DrawableImage, DrawablePath, DrawableText
  29. */
  30. class JUCE_API Drawable : public Component
  31. {
  32. protected:
  33. //==============================================================================
  34. /** The base class can't be instantiated directly.
  35. @see DrawableComposite, DrawableImage, DrawablePath, DrawableText
  36. */
  37. Drawable();
  38. public:
  39. /** Destructor. */
  40. virtual ~Drawable();
  41. //==============================================================================
  42. /** Creates a deep copy of this Drawable object.
  43. Use this to create a new copy of this and any sub-objects in the tree.
  44. */
  45. virtual Drawable* createCopy() const = 0;
  46. //==============================================================================
  47. /** Renders this Drawable object.
  48. Note that the preferred way to render a drawable in future is by using it
  49. as a component and adding it to a parent, so you might want to consider that
  50. before using this method.
  51. @see drawWithin
  52. */
  53. void draw (Graphics& g, float opacity,
  54. const AffineTransform& transform = AffineTransform::identity) const;
  55. /** Renders the Drawable at a given offset within the Graphics context.
  56. The co-ordinates passed-in are used to translate the object relative to its own
  57. origin before drawing it - this is basically a quick way of saying:
  58. @code
  59. draw (g, AffineTransform::translation (x, y)).
  60. @endcode
  61. Note that the preferred way to render a drawable in future is by using it
  62. as a component and adding it to a parent, so you might want to consider that
  63. before using this method.
  64. */
  65. void drawAt (Graphics& g, float x, float y, float opacity) const;
  66. /** Renders the Drawable within a rectangle, scaling it to fit neatly inside without
  67. changing its aspect-ratio.
  68. The object can placed arbitrarily within the rectangle based on a Justification type,
  69. and can either be made as big as possible, or just reduced to fit.
  70. Note that the preferred way to render a drawable in future is by using it
  71. as a component and adding it to a parent, so you might want to consider that
  72. before using this method.
  73. @param g the graphics context to render onto
  74. @param destArea the target rectangle to fit the drawable into
  75. @param placement defines the alignment and rescaling to use to fit
  76. this object within the target rectangle.
  77. @param opacity the opacity to use, in the range 0 to 1.0
  78. */
  79. void drawWithin (Graphics& g,
  80. const Rectangle<float>& destArea,
  81. const RectanglePlacement& placement,
  82. float opacity) const;
  83. //==============================================================================
  84. /** Resets any transformations on this drawable, and positions its origin within
  85. its parent component.
  86. */
  87. void setOriginWithOriginalSize (const Point<float>& originWithinParent);
  88. /** Sets a transform for this drawable that will position it within the specified
  89. area of its parent component.
  90. */
  91. void setTransformToFit (const Rectangle<float>& areaInParent, const RectanglePlacement& placement);
  92. /** Returns the DrawableComposite that contains this object, if there is one. */
  93. DrawableComposite* getParent() const;
  94. //==============================================================================
  95. /** Tries to turn some kind of image file into a drawable.
  96. The data could be an image that the ImageFileFormat class understands, or it
  97. could be SVG.
  98. */
  99. static Drawable* createFromImageData (const void* data, size_t numBytes);
  100. /** Tries to turn a stream containing some kind of image data into a drawable.
  101. The data could be an image that the ImageFileFormat class understands, or it
  102. could be SVG.
  103. */
  104. static Drawable* createFromImageDataStream (InputStream& dataSource);
  105. /** Tries to turn a file containing some kind of image data into a drawable.
  106. The data could be an image that the ImageFileFormat class understands, or it
  107. could be SVG.
  108. */
  109. static Drawable* createFromImageFile (const File& file);
  110. /** Attempts to parse an SVG (Scalable Vector Graphics) document, and to turn this
  111. into a Drawable tree.
  112. The object returned must be deleted by the caller. If something goes wrong
  113. while parsing, it may return 0.
  114. SVG is a pretty large and complex spec, and this doesn't aim to be a full
  115. implementation, but it can return the basic vector objects.
  116. */
  117. static Drawable* createFromSVG (const XmlElement& svgDocument);
  118. //==============================================================================
  119. /** Tries to create a Drawable from a previously-saved ValueTree.
  120. The ValueTree must have been created by the createValueTree() method.
  121. If there are any images used within the drawable, you'll need to provide a valid
  122. ImageProvider object that can be used to retrieve these images from whatever type
  123. of identifier is used to represent them.
  124. Internally, this uses a ComponentBuilder, and registerDrawableTypeHandlers().
  125. */
  126. static Drawable* createFromValueTree (const ValueTree& tree, ComponentBuilder::ImageProvider* imageProvider);
  127. /** Creates a ValueTree to represent this Drawable.
  128. The ValueTree that is returned can be turned back into a Drawable with createFromValueTree().
  129. If there are any images used in this drawable, you'll need to provide a valid ImageProvider
  130. object that can be used to create storable representations of them.
  131. */
  132. virtual ValueTree createValueTree (ComponentBuilder::ImageProvider* imageProvider) const = 0;
  133. /** Returns the area that this drawble covers.
  134. The result is expressed in this drawable's own coordinate space, and does not take
  135. into account any transforms that may be applied to the component.
  136. */
  137. virtual Rectangle<float> getDrawableBounds() const = 0;
  138. //==============================================================================
  139. /** Internal class used to manage ValueTrees that represent Drawables. */
  140. class ValueTreeWrapperBase
  141. {
  142. public:
  143. ValueTreeWrapperBase (const ValueTree& state);
  144. ValueTree& getState() noexcept { return state; }
  145. String getID() const;
  146. void setID (const String& newID);
  147. ValueTree state;
  148. };
  149. //==============================================================================
  150. /** Registers a set of ComponentBuilder::TypeHandler objects that can be used to
  151. load all the different Drawable types from a saved state.
  152. @see ComponentBuilder::registerTypeHandler()
  153. */
  154. static void registerDrawableTypeHandlers (ComponentBuilder& componentBuilder);
  155. protected:
  156. //==============================================================================
  157. friend class DrawableComposite;
  158. friend class DrawableShape;
  159. /** @internal */
  160. void transformContextToCorrectOrigin (Graphics& g);
  161. /** @internal */
  162. void parentHierarchyChanged();
  163. /** @internal */
  164. void setBoundsToEnclose (const Rectangle<float>& area);
  165. Point<int> originRelativeToComponent;
  166. #ifndef DOXYGEN
  167. /** Internal utility class used by Drawables. */
  168. template <class DrawableType>
  169. class Positioner : public RelativeCoordinatePositionerBase
  170. {
  171. public:
  172. Positioner (DrawableType& component_)
  173. : RelativeCoordinatePositionerBase (component_),
  174. owner (component_)
  175. {}
  176. bool registerCoordinates() { return owner.registerCoordinates (*this); }
  177. void applyToComponentBounds()
  178. {
  179. ComponentScope scope (getComponent());
  180. owner.recalculateCoordinates (&scope);
  181. }
  182. void applyNewBounds (const Rectangle<int>&)
  183. {
  184. jassertfalse; // drawables can't be resized directly!
  185. }
  186. private:
  187. DrawableType& owner;
  188. JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Positioner);
  189. };
  190. #endif
  191. private:
  192. void nonConstDraw (Graphics& g, float opacity, const AffineTransform& transform);
  193. JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (Drawable);
  194. };
  195. #endif // __JUCE_DRAWABLE_JUCEHEADER__