Line data Source code
1 : /* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 : * This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this
4 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : #ifndef _MOZILLA_GFX_PATTERNHELPERS_H
7 : #define _MOZILLA_GFX_PATTERNHELPERS_H
8 :
9 : #include "mozilla/Alignment.h"
10 : #include "mozilla/gfx/2D.h"
11 :
12 : namespace mozilla {
13 : namespace gfx {
14 :
15 : /**
16 : * This class is used to allow general pattern creation functions to return
17 : * any type of pattern via an out-paramater without allocating a pattern
18 : * instance on the free-store (an instance of this class being created on the
19 : * stack before passing it in to the creation function). Without this class
20 : * writing pattern creation functions would be a pain since Pattern objects are
21 : * not reference counted, making lifetime management of instances created on
22 : * the free-store and returned from a creation function hazardous. Besides
23 : * that, in the case that ColorPattern's are expected to be common, it is
24 : * particularly desirable to avoid the overhead of allocating on the
25 : * free-store.
26 : */
27 : class GeneralPattern
28 : {
29 : public:
30 76 : explicit GeneralPattern()
31 76 : : mPattern(nullptr)
32 76 : {}
33 :
34 : GeneralPattern(const GeneralPattern& aOther)
35 : : mPattern(nullptr)
36 : {}
37 :
38 152 : ~GeneralPattern() {
39 76 : if (mPattern) {
40 74 : mPattern->~Pattern();
41 : }
42 76 : }
43 :
44 14 : Pattern* Init(const Pattern& aPattern) {
45 14 : MOZ_ASSERT(!mPattern);
46 14 : switch (aPattern.GetType()) {
47 : case PatternType::COLOR:
48 42 : mPattern = new (mColorPattern.addr())
49 28 : ColorPattern(static_cast<const ColorPattern&>(aPattern));
50 14 : break;
51 : case PatternType::LINEAR_GRADIENT:
52 0 : mPattern = new (mLinearGradientPattern.addr())
53 0 : LinearGradientPattern(static_cast<const LinearGradientPattern&>(aPattern));
54 0 : break;
55 : case PatternType::RADIAL_GRADIENT:
56 0 : mPattern = new (mRadialGradientPattern.addr())
57 0 : RadialGradientPattern(static_cast<const RadialGradientPattern&>(aPattern));
58 0 : break;
59 : case PatternType::SURFACE:
60 0 : mPattern = new (mSurfacePattern.addr())
61 0 : SurfacePattern(static_cast<const SurfacePattern&>(aPattern));
62 0 : break;
63 : default:
64 0 : MOZ_MAKE_COMPILER_ASSUME_IS_UNREACHABLE("Unknown pattern type");
65 : }
66 14 : return mPattern;
67 : }
68 :
69 34 : ColorPattern* InitColorPattern(const Color &aColor) {
70 34 : MOZ_ASSERT(!mPattern);
71 34 : mPattern = new (mColorPattern.addr()) ColorPattern(aColor);
72 34 : return mColorPattern.addr();
73 : }
74 :
75 26 : LinearGradientPattern* InitLinearGradientPattern(const Point &aBegin,
76 : const Point &aEnd,
77 : GradientStops *aStops,
78 : const Matrix &aMatrix = Matrix()) {
79 26 : MOZ_ASSERT(!mPattern);
80 78 : mPattern = new (mLinearGradientPattern.addr())
81 52 : LinearGradientPattern(aBegin, aEnd, aStops, aMatrix);
82 26 : return mLinearGradientPattern.addr();
83 : }
84 :
85 0 : RadialGradientPattern* InitRadialGradientPattern(const Point &aCenter1,
86 : const Point &aCenter2,
87 : Float aRadius1,
88 : Float aRadius2,
89 : GradientStops *aStops,
90 : const Matrix &aMatrix = Matrix()) {
91 0 : MOZ_ASSERT(!mPattern);
92 0 : mPattern = new (mRadialGradientPattern.addr())
93 0 : RadialGradientPattern(aCenter1, aCenter2, aRadius1, aRadius2, aStops, aMatrix);
94 0 : return mRadialGradientPattern.addr();
95 : }
96 :
97 0 : SurfacePattern* InitSurfacePattern(SourceSurface *aSourceSurface,
98 : ExtendMode aExtendMode,
99 : const Matrix &aMatrix = Matrix(),
100 : SamplingFilter aSamplingFilter = SamplingFilter::GOOD,
101 : const IntRect &aSamplingRect = IntRect()) {
102 0 : MOZ_ASSERT(!mPattern);
103 0 : mPattern = new (mSurfacePattern.addr())
104 0 : SurfacePattern(aSourceSurface, aExtendMode, aMatrix, aSamplingFilter, aSamplingRect);
105 0 : return mSurfacePattern.addr();
106 : }
107 :
108 139 : Pattern* GetPattern() {
109 139 : return mPattern;
110 : }
111 :
112 0 : const Pattern* GetPattern() const {
113 0 : return mPattern;
114 : }
115 :
116 34 : operator Pattern&() {
117 34 : if (!mPattern) {
118 0 : MOZ_CRASH("GFX: GeneralPattern not initialized");
119 : }
120 34 : return *mPattern;
121 : }
122 :
123 : private:
124 : union {
125 : AlignedStorage2<ColorPattern> mColorPattern;
126 : AlignedStorage2<LinearGradientPattern> mLinearGradientPattern;
127 : AlignedStorage2<RadialGradientPattern> mRadialGradientPattern;
128 : AlignedStorage2<SurfacePattern> mSurfacePattern;
129 : };
130 : Pattern *mPattern;
131 : };
132 :
133 : } // namespace gfx
134 : } // namespace mozilla
135 :
136 : #endif // _MOZILLA_GFX_PATTERNHELPERS_H
137 :
|