1*25ea7f45SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*25ea7f45SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*25ea7f45SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*25ea7f45SAndrew Rist  * distributed with this work for additional information
6*25ea7f45SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*25ea7f45SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*25ea7f45SAndrew Rist  * "License"); you may not use this file except in compliance
9*25ea7f45SAndrew Rist  * with the License.  You may obtain a copy of the License at
10*25ea7f45SAndrew Rist  *
11*25ea7f45SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*25ea7f45SAndrew Rist  *
13*25ea7f45SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*25ea7f45SAndrew Rist  * software distributed under the License is distributed on an
15*25ea7f45SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*25ea7f45SAndrew Rist  * KIND, either express or implied.  See the License for the
17*25ea7f45SAndrew Rist  * specific language governing permissions and limitations
18*25ea7f45SAndrew Rist  * under the License.
19*25ea7f45SAndrew Rist  *
20*25ea7f45SAndrew Rist  *************************************************************/
21*25ea7f45SAndrew Rist 
22*25ea7f45SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_canvas.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir #include <canvas/debug.hxx>
28cdf0e10cSrcweir #include <canvas/canvastools.hxx>
29cdf0e10cSrcweir 
30cdf0e10cSrcweir #include <rtl/math.hxx>
31cdf0e10cSrcweir 
32cdf0e10cSrcweir #include <basegfx/matrix/b2dhommatrix.hxx>
33cdf0e10cSrcweir #include <basegfx/polygon/b2dpolygontools.hxx>
34cdf0e10cSrcweir #include <basegfx/point/b2dpoint.hxx>
35cdf0e10cSrcweir #include <basegfx/range/b2drectangle.hxx>
36cdf0e10cSrcweir #include <basegfx/tools/canvastools.hxx>
37cdf0e10cSrcweir #include <basegfx/numeric/ftools.hxx>
38cdf0e10cSrcweir #include <basegfx/tools/tools.hxx>
39cdf0e10cSrcweir 
40cdf0e10cSrcweir #include <limits>
41cdf0e10cSrcweir 
42cdf0e10cSrcweir #include <canvas/parametricpolypolygon.hxx>
43cdf0e10cSrcweir 
44cdf0e10cSrcweir 
45cdf0e10cSrcweir using namespace ::com::sun::star;
46cdf0e10cSrcweir 
47cdf0e10cSrcweir namespace canvas
48cdf0e10cSrcweir {
getAvailableServiceNames()49cdf0e10cSrcweir     uno::Sequence<rtl::OUString> ParametricPolyPolygon::getAvailableServiceNames()
50cdf0e10cSrcweir     {
51cdf0e10cSrcweir         uno::Sequence<rtl::OUString> aRet(3);
52cdf0e10cSrcweir         aRet[0] = rtl::OUString::createFromAscii("LinearGradient");
53cdf0e10cSrcweir         aRet[1] = rtl::OUString::createFromAscii("EllipticalGradient");
54cdf0e10cSrcweir         aRet[2] = rtl::OUString::createFromAscii("RectangularGradient");
55cdf0e10cSrcweir 
56cdf0e10cSrcweir         return aRet;
57cdf0e10cSrcweir     }
58cdf0e10cSrcweir 
create(const uno::Reference<rendering::XGraphicDevice> & rDevice,const::rtl::OUString & rServiceName,const uno::Sequence<uno::Any> & rArgs)59cdf0e10cSrcweir     ParametricPolyPolygon* ParametricPolyPolygon::create(
60cdf0e10cSrcweir         const uno::Reference< rendering::XGraphicDevice >& rDevice,
61cdf0e10cSrcweir         const ::rtl::OUString& rServiceName,
62cdf0e10cSrcweir         const uno::Sequence< uno::Any >& rArgs )
63cdf0e10cSrcweir     {
64cdf0e10cSrcweir         uno::Sequence< uno::Sequence< double > > colorSequence(2);
65cdf0e10cSrcweir         uno::Sequence< double > colorStops(2);
66cdf0e10cSrcweir         double fAspectRatio=1.0;
67cdf0e10cSrcweir 
68cdf0e10cSrcweir         // defaults
69cdf0e10cSrcweir         uno::Sequence< rendering::RGBColor > rgbColors(1);
70cdf0e10cSrcweir         rgbColors[0] = rendering::RGBColor(0,0,0);
71cdf0e10cSrcweir         colorSequence[0] = rDevice->getDeviceColorSpace()->convertFromRGB(rgbColors);
72cdf0e10cSrcweir         rgbColors[0] = rendering::RGBColor(1,1,1);
73cdf0e10cSrcweir         colorSequence[1] = rDevice->getDeviceColorSpace()->convertFromRGB(rgbColors);
74cdf0e10cSrcweir         colorStops[0] = 0;
75cdf0e10cSrcweir         colorStops[1] = 1;
76cdf0e10cSrcweir 
77cdf0e10cSrcweir         // extract args
78cdf0e10cSrcweir         for( sal_Int32 i=0; i<rArgs.getLength(); ++i )
79cdf0e10cSrcweir         {
80cdf0e10cSrcweir             beans::PropertyValue aProp;
81cdf0e10cSrcweir             if( (rArgs[i] >>= aProp) )
82cdf0e10cSrcweir             {
83cdf0e10cSrcweir                 if( aProp.Name.equalsAscii("Colors") )
84cdf0e10cSrcweir                 {
85cdf0e10cSrcweir                     aProp.Value >>= colorSequence;
86cdf0e10cSrcweir                 }
87cdf0e10cSrcweir                 else if( aProp.Name.equalsAscii("Stops") )
88cdf0e10cSrcweir                 {
89cdf0e10cSrcweir                     aProp.Value >>= colorStops;
90cdf0e10cSrcweir                 }
91cdf0e10cSrcweir                 else if( aProp.Name.equalsAscii("AspectRatio") )
92cdf0e10cSrcweir                 {
93cdf0e10cSrcweir                     aProp.Value >>= fAspectRatio;
94cdf0e10cSrcweir                 }
95cdf0e10cSrcweir             }
96cdf0e10cSrcweir         }
97cdf0e10cSrcweir 
98cdf0e10cSrcweir         if( rServiceName.equalsAscii("LinearGradient") )
99cdf0e10cSrcweir         {
100cdf0e10cSrcweir             return createLinearHorizontalGradient(rDevice, colorSequence, colorStops);
101cdf0e10cSrcweir         }
102cdf0e10cSrcweir         else if( rServiceName.equalsAscii("EllipticalGradient") )
103cdf0e10cSrcweir         {
104cdf0e10cSrcweir             return createEllipticalGradient(rDevice, colorSequence, colorStops, fAspectRatio);
105cdf0e10cSrcweir         }
106cdf0e10cSrcweir         else if( rServiceName.equalsAscii("RectangularGradient") )
107cdf0e10cSrcweir         {
108cdf0e10cSrcweir             return createRectangularGradient(rDevice, colorSequence, colorStops, fAspectRatio);
109cdf0e10cSrcweir         }
110cdf0e10cSrcweir         else if( rServiceName.equalsAscii("VerticalLineHatch") )
111cdf0e10cSrcweir         {
112cdf0e10cSrcweir             // TODO: NYI
113cdf0e10cSrcweir         }
114cdf0e10cSrcweir         else if( rServiceName.equalsAscii("OrthogonalLinesHatch") )
115cdf0e10cSrcweir         {
116cdf0e10cSrcweir             // TODO: NYI
117cdf0e10cSrcweir         }
118cdf0e10cSrcweir         else if( rServiceName.equalsAscii("ThreeCrossingLinesHatch") )
119cdf0e10cSrcweir         {
120cdf0e10cSrcweir             // TODO: NYI
121cdf0e10cSrcweir         }
122cdf0e10cSrcweir         else if( rServiceName.equalsAscii("FourCrossingLinesHatch") )
123cdf0e10cSrcweir         {
124cdf0e10cSrcweir             // TODO: NYI
125cdf0e10cSrcweir         }
126cdf0e10cSrcweir 
127cdf0e10cSrcweir         return NULL;
128cdf0e10cSrcweir     }
129cdf0e10cSrcweir 
createLinearHorizontalGradient(const uno::Reference<rendering::XGraphicDevice> & rDevice,const uno::Sequence<uno::Sequence<double>> & colors,const uno::Sequence<double> & stops)130cdf0e10cSrcweir     ParametricPolyPolygon* ParametricPolyPolygon::createLinearHorizontalGradient(
131cdf0e10cSrcweir         const uno::Reference< rendering::XGraphicDevice >& 	rDevice,
132cdf0e10cSrcweir         const uno::Sequence< uno::Sequence< double > >&		colors,
133cdf0e10cSrcweir         const uno::Sequence< double >& 						stops )
134cdf0e10cSrcweir     {
135cdf0e10cSrcweir         // TODO(P2): hold gradient brush statically, and only setup
136cdf0e10cSrcweir         // the colors
137cdf0e10cSrcweir         return new ParametricPolyPolygon( rDevice, GRADIENT_LINEAR, colors, stops );
138cdf0e10cSrcweir     }
139cdf0e10cSrcweir 
createEllipticalGradient(const uno::Reference<rendering::XGraphicDevice> & rDevice,const uno::Sequence<uno::Sequence<double>> & colors,const uno::Sequence<double> & stops,double fAspectRatio)140cdf0e10cSrcweir     ParametricPolyPolygon* ParametricPolyPolygon::createEllipticalGradient(
141cdf0e10cSrcweir         const uno::Reference< rendering::XGraphicDevice >& 	rDevice,
142cdf0e10cSrcweir         const uno::Sequence< uno::Sequence< double > >&		colors,
143cdf0e10cSrcweir         const uno::Sequence< double >& 						stops,
144cdf0e10cSrcweir         double                                              fAspectRatio )
145cdf0e10cSrcweir     {
146cdf0e10cSrcweir         // TODO(P2): hold gradient polygon statically, and only setup
147cdf0e10cSrcweir         // the colors
148cdf0e10cSrcweir         return new ParametricPolyPolygon(
149cdf0e10cSrcweir             rDevice,
150cdf0e10cSrcweir             ::basegfx::tools::createPolygonFromCircle(
151cdf0e10cSrcweir                 ::basegfx::B2DPoint(0,0), 1 ),
152cdf0e10cSrcweir             GRADIENT_ELLIPTICAL,
153cdf0e10cSrcweir             colors, stops, fAspectRatio );
154cdf0e10cSrcweir     }
155cdf0e10cSrcweir 
createRectangularGradient(const uno::Reference<rendering::XGraphicDevice> & rDevice,const uno::Sequence<uno::Sequence<double>> & colors,const uno::Sequence<double> & stops,double fAspectRatio)156cdf0e10cSrcweir     ParametricPolyPolygon* ParametricPolyPolygon::createRectangularGradient( const uno::Reference< rendering::XGraphicDevice >& rDevice,
157cdf0e10cSrcweir                                                                              const uno::Sequence< uno::Sequence< double > >&	colors,
158cdf0e10cSrcweir                                                                              const uno::Sequence< double >& 					stops,
159cdf0e10cSrcweir                                                                              double                                             fAspectRatio )
160cdf0e10cSrcweir     {
161cdf0e10cSrcweir         // TODO(P2): hold gradient polygon statically, and only setup
162cdf0e10cSrcweir         // the colors
163cdf0e10cSrcweir         return new ParametricPolyPolygon(
164cdf0e10cSrcweir             rDevice,
165cdf0e10cSrcweir             ::basegfx::tools::createPolygonFromRect(
166cdf0e10cSrcweir                 ::basegfx::B2DRectangle( -1, -1, 1, 1 ) ),
167cdf0e10cSrcweir             GRADIENT_RECTANGULAR,
168cdf0e10cSrcweir             colors, stops, fAspectRatio );
169cdf0e10cSrcweir     }
170cdf0e10cSrcweir 
disposing()171cdf0e10cSrcweir     void SAL_CALL ParametricPolyPolygon::disposing()
172cdf0e10cSrcweir     {
173cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
174cdf0e10cSrcweir 
175cdf0e10cSrcweir         mxDevice.clear();
176cdf0e10cSrcweir     }
177cdf0e10cSrcweir 
getOutline(double)178cdf0e10cSrcweir     uno::Reference< rendering::XPolyPolygon2D > SAL_CALL ParametricPolyPolygon::getOutline( double /*t*/ ) throw (lang::IllegalArgumentException, uno::RuntimeException)
179cdf0e10cSrcweir     {
180cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
181cdf0e10cSrcweir 
182cdf0e10cSrcweir         // TODO(F1): outline NYI
183cdf0e10cSrcweir         return uno::Reference< rendering::XPolyPolygon2D >();
184cdf0e10cSrcweir     }
185cdf0e10cSrcweir 
getColor(double)186cdf0e10cSrcweir     uno::Sequence< double > SAL_CALL ParametricPolyPolygon::getColor( double /*t*/ ) throw (lang::IllegalArgumentException, uno::RuntimeException)
187cdf0e10cSrcweir     {
188cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
189cdf0e10cSrcweir 
190cdf0e10cSrcweir         // TODO(F1): color NYI
191cdf0e10cSrcweir         return uno::Sequence< double >();
192cdf0e10cSrcweir     }
193cdf0e10cSrcweir 
getPointColor(const geometry::RealPoint2D &)194cdf0e10cSrcweir     uno::Sequence< double > SAL_CALL ParametricPolyPolygon::getPointColor( const geometry::RealPoint2D& /*point*/ ) throw (lang::IllegalArgumentException, uno::RuntimeException)
195cdf0e10cSrcweir     {
196cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
197cdf0e10cSrcweir 
198cdf0e10cSrcweir         // TODO(F1): point color NYI
199cdf0e10cSrcweir         return uno::Sequence< double >();
200cdf0e10cSrcweir     }
201cdf0e10cSrcweir 
getColorSpace()202cdf0e10cSrcweir     uno::Reference< rendering::XColorSpace > SAL_CALL ParametricPolyPolygon::getColorSpace() throw (uno::RuntimeException)
203cdf0e10cSrcweir     {
204cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
205cdf0e10cSrcweir 
206cdf0e10cSrcweir         return mxDevice.is() ? mxDevice->getDeviceColorSpace() : uno::Reference< rendering::XColorSpace >();
207cdf0e10cSrcweir     }
208cdf0e10cSrcweir 
209cdf0e10cSrcweir #define IMPLEMENTATION_NAME "Canvas::ParametricPolyPolygon"
210cdf0e10cSrcweir #define SERVICE_NAME "com.sun.star.rendering.ParametricPolyPolygon"
211cdf0e10cSrcweir 
getImplementationName()212cdf0e10cSrcweir     ::rtl::OUString SAL_CALL ParametricPolyPolygon::getImplementationName(  ) throw (uno::RuntimeException)
213cdf0e10cSrcweir     {
214cdf0e10cSrcweir         return ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( IMPLEMENTATION_NAME ) );
215cdf0e10cSrcweir     }
216cdf0e10cSrcweir 
supportsService(const::rtl::OUString & ServiceName)217cdf0e10cSrcweir     sal_Bool SAL_CALL ParametricPolyPolygon::supportsService( const ::rtl::OUString& ServiceName ) throw (uno::RuntimeException)
218cdf0e10cSrcweir     {
219cdf0e10cSrcweir         return ServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM ( SERVICE_NAME ) );
220cdf0e10cSrcweir     }
221cdf0e10cSrcweir 
getSupportedServiceNames()222cdf0e10cSrcweir     uno::Sequence< ::rtl::OUString > SAL_CALL ParametricPolyPolygon::getSupportedServiceNames(  ) throw (uno::RuntimeException)
223cdf0e10cSrcweir     {
224cdf0e10cSrcweir         uno::Sequence< ::rtl::OUString > aRet(1);
225cdf0e10cSrcweir         aRet[0] = ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( SERVICE_NAME ) );
226cdf0e10cSrcweir 
227cdf0e10cSrcweir         return aRet;
228cdf0e10cSrcweir     }
229cdf0e10cSrcweir 
~ParametricPolyPolygon()230cdf0e10cSrcweir     ParametricPolyPolygon::~ParametricPolyPolygon()
231cdf0e10cSrcweir     {
232cdf0e10cSrcweir     }
233cdf0e10cSrcweir 
ParametricPolyPolygon(const uno::Reference<rendering::XGraphicDevice> & rDevice,const::basegfx::B2DPolygon & rGradientPoly,GradientType eType,const uno::Sequence<uno::Sequence<double>> & rColors,const uno::Sequence<double> & rStops)234cdf0e10cSrcweir     ParametricPolyPolygon::ParametricPolyPolygon( const uno::Reference< rendering::XGraphicDevice >& 	rDevice,
235cdf0e10cSrcweir                                                   const ::basegfx::B2DPolygon&							rGradientPoly,
236cdf0e10cSrcweir                                                   GradientType                                          eType,
237cdf0e10cSrcweir                                                   const uno::Sequence< uno::Sequence< double > >&		rColors,
238cdf0e10cSrcweir                                                   const uno::Sequence< double >& 						rStops ) :
239cdf0e10cSrcweir         ParametricPolyPolygon_Base( m_aMutex ),
240cdf0e10cSrcweir         mxDevice( rDevice ),
241cdf0e10cSrcweir         maValues( rGradientPoly,
242cdf0e10cSrcweir                   rColors,
243cdf0e10cSrcweir                   rStops,
244cdf0e10cSrcweir                   1.0,
245cdf0e10cSrcweir                   eType )
246cdf0e10cSrcweir     {
247cdf0e10cSrcweir     }
248cdf0e10cSrcweir 
ParametricPolyPolygon(const uno::Reference<rendering::XGraphicDevice> & rDevice,const::basegfx::B2DPolygon & rGradientPoly,GradientType eType,const uno::Sequence<uno::Sequence<double>> & rColors,const uno::Sequence<double> & rStops,double nAspectRatio)249cdf0e10cSrcweir     ParametricPolyPolygon::ParametricPolyPolygon( const uno::Reference< rendering::XGraphicDevice >& 	rDevice,
250cdf0e10cSrcweir                                                   const ::basegfx::B2DPolygon&							rGradientPoly,
251cdf0e10cSrcweir                                                   GradientType                                          eType,
252cdf0e10cSrcweir                                                   const uno::Sequence< uno::Sequence< double > >&		rColors,
253cdf0e10cSrcweir                                                   const uno::Sequence< double >& 						rStops,
254cdf0e10cSrcweir                                                   double												nAspectRatio ) :
255cdf0e10cSrcweir         ParametricPolyPolygon_Base( m_aMutex ),
256cdf0e10cSrcweir         mxDevice( rDevice ),
257cdf0e10cSrcweir         maValues( rGradientPoly,
258cdf0e10cSrcweir                   rColors,
259cdf0e10cSrcweir                   rStops,
260cdf0e10cSrcweir                   nAspectRatio,
261cdf0e10cSrcweir                   eType )
262cdf0e10cSrcweir     {
263cdf0e10cSrcweir     }
264cdf0e10cSrcweir 
ParametricPolyPolygon(const uno::Reference<rendering::XGraphicDevice> & rDevice,GradientType eType,const uno::Sequence<uno::Sequence<double>> & rColors,const uno::Sequence<double> & rStops)265cdf0e10cSrcweir     ParametricPolyPolygon::ParametricPolyPolygon( const uno::Reference< rendering::XGraphicDevice >& 	rDevice,
266cdf0e10cSrcweir                                                   GradientType	 										eType,
267cdf0e10cSrcweir                                                   const uno::Sequence< uno::Sequence< double > >&		rColors,
268cdf0e10cSrcweir                                                   const uno::Sequence< double >& 						rStops ) :
269cdf0e10cSrcweir         ParametricPolyPolygon_Base( m_aMutex ),
270cdf0e10cSrcweir         mxDevice( rDevice ),
271cdf0e10cSrcweir         maValues( ::basegfx::B2DPolygon(),
272cdf0e10cSrcweir                   rColors,
273cdf0e10cSrcweir                   rStops,
274cdf0e10cSrcweir                   1.0,
275cdf0e10cSrcweir                   eType )
276cdf0e10cSrcweir     {
277cdf0e10cSrcweir     }
278cdf0e10cSrcweir 
getValues() const279cdf0e10cSrcweir     ParametricPolyPolygon::Values ParametricPolyPolygon::getValues() const
280cdf0e10cSrcweir     {
281cdf0e10cSrcweir         ::osl::MutexGuard aGuard( m_aMutex );
282cdf0e10cSrcweir 
283cdf0e10cSrcweir         return maValues;
284cdf0e10cSrcweir     }
285cdf0e10cSrcweir 
286cdf0e10cSrcweir }
287