1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
4 *
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 *
9 * This file incorporates work covered by the following license notice:
10 *
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 */
19 #include <Functions.hxx>
20 #include <Function.hxx>
21 #include <core_resource.hxx>
22 #include <strings.hrc>
23 #include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
24 #include <com/sun/star/lang/NoSupportException.hpp>
25
26 namespace reportdesign
27 {
28
29 using namespace com::sun::star;
30
OFunctions(const uno::Reference<report::XFunctionsSupplier> & _xParent,const uno::Reference<uno::XComponentContext> & context)31 OFunctions::OFunctions(const uno::Reference< report::XFunctionsSupplier >& _xParent,const uno::Reference< uno::XComponentContext >& context)
32 :FunctionsBase(m_aMutex)
33 ,m_aContainerListeners(m_aMutex)
34 ,m_xContext(context)
35 ,m_xParent(_xParent)
36 {
37 }
38
39 // TODO: VirtualFunctionFinder: This is virtual function!
40
~OFunctions()41 OFunctions::~OFunctions()
42 {
43 }
44
dispose()45 void SAL_CALL OFunctions::dispose()
46 {
47 cppu::WeakComponentImplHelperBase::dispose();
48 }
49
50 // TODO: VirtualFunctionFinder: This is virtual function!
51
disposing()52 void SAL_CALL OFunctions::disposing()
53 {
54 for (auto& rFunction : m_aFunctions)
55 rFunction->dispose();
56 m_aFunctions.clear();
57 lang::EventObject aDisposeEvent( static_cast< ::cppu::OWeakObject* >( this ) );
58 m_aContainerListeners.disposeAndClear( aDisposeEvent );
59 m_xContext.clear();
60 }
61
62 // XFunctionsSupplier
63
createFunction()64 uno::Reference< report::XFunction > SAL_CALL OFunctions::createFunction( )
65 {
66 return new OFunction(m_xContext);
67 }
68
69 // XIndexContainer
insertByIndex(::sal_Int32 Index,const uno::Any & aElement)70 void SAL_CALL OFunctions::insertByIndex( ::sal_Int32 Index, const uno::Any& aElement )
71 {
72 {
73 ::osl::MutexGuard aGuard(m_aMutex);
74 bool bAdd = (Index == static_cast<sal_Int32>(m_aFunctions.size()));
75 if ( !bAdd )
76 checkIndex(Index);
77 uno::Reference< report::XFunction > xFunction(aElement,uno::UNO_QUERY);
78 if ( !xFunction.is() )
79 throw lang::IllegalArgumentException(RptResId(RID_STR_ARGUMENT_IS_NULL),*this,2);
80
81 if ( bAdd )
82 m_aFunctions.push_back(xFunction);
83 else
84 {
85 TFunctions::iterator aPos = m_aFunctions.begin();
86 ::std::advance(aPos,Index);
87 m_aFunctions.insert(aPos, xFunction);
88 }
89 xFunction->setParent(*this);
90 }
91 // notify our container listeners
92 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::makeAny(Index), aElement, uno::Any());
93 m_aContainerListeners.notifyEach(&container::XContainerListener::elementInserted,aEvent);
94 }
95
96
removeByIndex(::sal_Int32 Index)97 void SAL_CALL OFunctions::removeByIndex( ::sal_Int32 Index )
98 {
99 uno::Reference< report::XFunction > xFunction;
100 {
101 ::osl::MutexGuard aGuard(m_aMutex);
102 checkIndex(Index);
103 TFunctions::iterator aPos = m_aFunctions.begin();
104 ::std::advance(aPos,Index);
105 xFunction = *aPos;
106 m_aFunctions.erase(aPos);
107 xFunction->setParent(nullptr);
108 }
109 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::makeAny(Index), uno::makeAny(xFunction), uno::Any());
110 m_aContainerListeners.notifyEach(&container::XContainerListener::elementRemoved,aEvent);
111 }
112
113 // XIndexReplace
replaceByIndex(::sal_Int32 Index,const uno::Any & Element)114 void SAL_CALL OFunctions::replaceByIndex( ::sal_Int32 Index, const uno::Any& Element )
115 {
116 uno::Any aOldElement;
117 {
118 ::osl::MutexGuard aGuard(m_aMutex);
119 checkIndex(Index);
120 uno::Reference< report::XFunction > xFunction(Element,uno::UNO_QUERY);
121 if ( !xFunction.is() )
122 throw lang::IllegalArgumentException(RptResId(RID_STR_ARGUMENT_IS_NULL),*this,2);
123 TFunctions::iterator aPos = m_aFunctions.begin();
124 ::std::advance(aPos,Index);
125 aOldElement <<= *aPos;
126 *aPos = xFunction;
127 }
128
129 container::ContainerEvent aEvent(static_cast<container::XContainer*>(this), uno::makeAny(Index), Element, aOldElement);
130 m_aContainerListeners.notifyEach(&container::XContainerListener::elementReplaced,aEvent);
131 }
132
133 // XIndexAccess
getCount()134 ::sal_Int32 SAL_CALL OFunctions::getCount( )
135 {
136 ::osl::MutexGuard aGuard(m_aMutex);
137 return m_aFunctions.size();
138 }
139
getByIndex(::sal_Int32 Index)140 uno::Any SAL_CALL OFunctions::getByIndex( ::sal_Int32 Index )
141 {
142 ::osl::MutexGuard aGuard(m_aMutex);
143 checkIndex(Index);
144 TFunctions::const_iterator aPos = m_aFunctions.begin();
145 ::std::advance(aPos,Index);
146 return uno::makeAny(*aPos);
147 }
148
149 // XElementAccess
getElementType()150 uno::Type SAL_CALL OFunctions::getElementType( )
151 {
152 return cppu::UnoType<report::XFunction>::get();
153 }
154
hasElements()155 sal_Bool SAL_CALL OFunctions::hasElements( )
156 {
157 ::osl::MutexGuard aGuard(m_aMutex);
158 return !m_aFunctions.empty();
159 }
160
161 // XChild
getParent()162 uno::Reference< uno::XInterface > SAL_CALL OFunctions::getParent( )
163 {
164 return m_xParent;
165 }
166
setParent(const uno::Reference<uno::XInterface> &)167 void SAL_CALL OFunctions::setParent( const uno::Reference< uno::XInterface >& /*Parent*/ )
168 {
169 throw lang::NoSupportException();
170 }
171
172 // XContainer
addContainerListener(const uno::Reference<container::XContainerListener> & xListener)173 void SAL_CALL OFunctions::addContainerListener( const uno::Reference< container::XContainerListener >& xListener )
174 {
175 m_aContainerListeners.addInterface(xListener);
176 }
177
removeContainerListener(const uno::Reference<container::XContainerListener> & xListener)178 void SAL_CALL OFunctions::removeContainerListener( const uno::Reference< container::XContainerListener >& xListener )
179 {
180 m_aContainerListeners.removeInterface(xListener);
181 }
182
checkIndex(sal_Int32 _nIndex)183 void OFunctions::checkIndex(sal_Int32 _nIndex)
184 {
185 if ( _nIndex < 0 || static_cast<sal_Int32>(m_aFunctions.size()) <= _nIndex )
186 throw lang::IndexOutOfBoundsException();
187 }
188
189 }
190
191
192 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
193