LibreOffice Module sfx2 (master) 1
msgpool.cxx
Go to the documentation of this file.
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
20#include <sal/log.hxx>
21#include <osl/diagnose.h>
22
23// due to pSlotPool
24#include <appdata.hxx>
25#include <sfx2/msgpool.hxx>
26#include <sfx2/msg.hxx>
27#include <sfx2/app.hxx>
28#include <sfx2/objface.hxx>
29#include <sfx2/sfxresid.hxx>
30#include <sfx2/module.hxx>
31
32#include <sfx2/strings.hrc>
33
35 : _pParentPool( pParent )
36 , _nCurGroup(0)
37 , _nCurInterface(0)
38 , _nCurMsg(0)
39{
40}
41
43{
44 _pParentPool = nullptr;
45 // swap out _vInterfaces because ~SfxInterface() might call ReleaseInterface()
46 std::vector<SfxInterface*> tmpInterfaces;
47 tmpInterfaces.swap(_vInterfaces);
48 for ( SfxInterface *pIF : tmpInterfaces )
49 delete pIF;
50}
51
52namespace
53{
54 TranslateId getGidResId(SfxGroupId nId)
55 {
56 if (nId == SfxGroupId::Intern)
57 return STR_GID_INTERN;
58 else if (nId == SfxGroupId::Application)
59 return STR_GID_APPLICATION;
60 else if (nId == SfxGroupId::View)
61 return STR_GID_VIEW;
62 else if (nId == SfxGroupId::Document)
63 return STR_GID_DOCUMENT;
64 else if (nId == SfxGroupId::Edit)
65 return STR_GID_EDIT;
66 else if (nId == SfxGroupId::Macro)
67 return STR_GID_MACRO;
68 else if (nId == SfxGroupId::Options)
69 return STR_GID_OPTIONS;
70 else if (nId == SfxGroupId::Math)
71 return STR_GID_MATH;
72 else if (nId == SfxGroupId::Navigator)
73 return STR_GID_NAVIGATOR;
74 else if (nId == SfxGroupId::Insert)
75 return STR_GID_INSERT;
76 else if (nId == SfxGroupId::Format)
77 return STR_GID_FORMAT;
78 else if (nId == SfxGroupId::Template)
79 return STR_GID_TEMPLATE;
80 else if (nId == SfxGroupId::Text)
81 return STR_GID_TEXT;
82 else if (nId == SfxGroupId::Frame)
83 return STR_GID_FRAME;
84 else if (nId == SfxGroupId::Graphic)
85 return STR_GID_GRAPHIC;
86 else if (nId == SfxGroupId::Table)
87 return STR_GID_TABLE;
88 else if (nId == SfxGroupId::Enumeration)
89 return STR_GID_ENUMERATION;
90 else if (nId == SfxGroupId::Data)
91 return STR_GID_DATA;
92 else if (nId == SfxGroupId::Special)
93 return STR_GID_SPECIAL;
94 else if (nId == SfxGroupId::Image)
95 return STR_GID_IMAGE;
96 else if (nId == SfxGroupId::Chart)
97 return STR_GID_CHART;
98 else if (nId == SfxGroupId::Explorer)
99 return STR_GID_EXPLORER;
100 else if (nId == SfxGroupId::Connector)
101 return STR_GID_CONNECTOR;
102 else if (nId == SfxGroupId::Modify)
103 return STR_GID_MODIFY;
104 else if (nId == SfxGroupId::Drawing)
105 return STR_GID_DRAWING;
106 else if (nId == SfxGroupId::Controls)
107 return STR_GID_CONTROLS;
108 return {};
109 }
110}
111
112// registers the availability of the Interface of functions
113
115{
116 // add to the list of SfxObjectInterface instances
117 _vInterfaces.push_back(&rInterface);
118
119 // Stop at a (single) Null-slot (for syntactic reasons the interfaces
120 // always contain at least one slot)
121 if ( rInterface.Count() != 0 && !rInterface.pSlots[0].nSlotId )
122 return;
123
124 // possibly add Interface-id and group-ids of funcs to the list of groups
125 if ( _pParentPool )
126 {
127 // The Groups in parent Slotpool are also known here
128 _vGroups.insert( _vGroups.end(), _pParentPool->_vGroups.begin(), _pParentPool->_vGroups.end() );
129 }
130
131 for ( size_t nFunc = 0; nFunc < rInterface.Count(); ++nFunc )
132 {
133 SfxSlot &rDef = rInterface.pSlots[nFunc];
134 if ( rDef.GetGroupId() != SfxGroupId::NONE &&
135 std::find(_vGroups.begin(), _vGroups.end(), rDef.GetGroupId()) == _vGroups.end() )
136 {
137 if (rDef.GetGroupId() == SfxGroupId::Intern)
138 _vGroups.insert(_vGroups.begin(), rDef.GetGroupId());
139 else
140 _vGroups.push_back(rDef.GetGroupId());
141 }
142 }
143}
144
145
146const std::type_info* SfxSlotPool::GetSlotType( sal_uInt16 nId ) const
147{
148 const SfxSlot* pSlot = GetSlot( nId );
149 return pSlot ? pSlot->GetType()->Type() : nullptr;
150}
151
152
153// get the first SfxMessage for a special Id (e.g. for getting check-mode)
154
155const SfxSlot* SfxSlotPool::GetSlot( sal_uInt16 nId ) const
156{
157 // First, search their own interfaces
158 for (SfxInterface* _pInterface : _vInterfaces)
159 {
160 const SfxSlot *pDef = _pInterface->GetSlot(nId);
161 if ( pDef )
162 return pDef;
163 }
164
165 // Then try any of the possible existing parent
166 return _pParentPool ? _pParentPool->GetSlot( nId ) : nullptr;
167}
168
169
170// skips to the next group
171
172OUString SfxSlotPool::SeekGroup( sal_uInt16 nNo )
173{
174 // if the group exists, use it
175 if ( nNo < _vGroups.size() )
176 {
177 _nCurGroup = nNo;
178 if ( _pParentPool )
179 {
180 // In most cases, the order of the IDs agree
181 sal_uInt16 nParentCount = _pParentPool->_vGroups.size();
182 if ( nNo < nParentCount && _vGroups[nNo] == _pParentPool->_vGroups[nNo] )
184 else
185 {
186 // Otherwise search. If the group is not found in the parent
187 // pool, _nCurGroup is set outside the valid range
188 sal_uInt16 i;
189 for ( i=1; i<nParentCount; i++ )
190 if ( _vGroups[nNo] == _pParentPool->_vGroups[i] )
191 break;
193 }
194 }
195
196 TranslateId pResId = getGidResId(_vGroups[_nCurGroup]);
197 if (!pResId)
198 {
199 OSL_FAIL( "GroupId-Name not defined in SFX!" );
200 return OUString();
201 }
202
203 return SfxResId(pResId);
204 }
205
206 return OUString();
207}
208
209
211{
212 return _vGroups.size();
213}
214
215
216// internal search loop
217
218const SfxSlot* SfxSlotPool::SeekSlot( sal_uInt16 nStartInterface )
219{
220 // The numbering starts at the interfaces of the parent pool
221 sal_uInt16 nFirstInterface = _pParentPool ? _pParentPool->_vInterfaces.size() : 0;
222
223 // have reached the end of the Parent-Pools?
224 if ( nStartInterface < nFirstInterface &&
226 nStartInterface = nFirstInterface;
227
228 // Is the Interface still in the Parent-Pool?
229 if ( nStartInterface < nFirstInterface )
230 {
231 SAL_WARN_IF(!_pParentPool, "sfx.control", "No parent pool!");
232 _nCurInterface = nStartInterface;
233 return _pParentPool->SeekSlot( nStartInterface );
234 }
235
236 // find the first func-def with the current group id
237 sal_uInt16 nCount = _vInterfaces.size() + nFirstInterface;
238 for ( _nCurInterface = nStartInterface;
241 {
242 SfxInterface* pInterface = _vInterfaces[_nCurInterface-nFirstInterface];
243 for ( _nCurMsg = 0;
244 _nCurMsg < pInterface->Count();
245 ++_nCurMsg )
246 {
247 const SfxSlot& rMsg = pInterface->pSlots[_nCurMsg];
248 if (rMsg.GetGroupId() == _vGroups.at(_nCurGroup))
249 return &rMsg;
250 }
251 }
252
253 return nullptr;
254}
255
256
257// skips to the next func in the current group
258
260{
261 // The numbering starts at the interfaces of the parent pool
262 sal_uInt16 nFirstInterface = _pParentPool ? _pParentPool->_vInterfaces.size() : 0;
263
264 if ( _nCurInterface < nFirstInterface && _nCurGroup >= _pParentPool->_vGroups.size() )
265 _nCurInterface = nFirstInterface;
266
267 if ( _nCurInterface < nFirstInterface )
268 {
269 SAL_WARN_IF(!_pParentPool, "sfx.control", "No parent pool!");
270 const SfxSlot *pSlot = _pParentPool->NextSlot();
272 if ( pSlot )
273 return pSlot;
274 if ( _nCurInterface == nFirstInterface )
275 // parent pool is ready
276 return SeekSlot( nFirstInterface );
277 }
278
279 sal_uInt16 nInterface = _nCurInterface - nFirstInterface;
280 // possibly we are already at the end
281 if ( nInterface >= _vInterfaces.size() )
282 return nullptr;
283
284 // look for further matching func-defs within the same Interface
285 SfxInterface* pInterface = _vInterfaces[nInterface];
286 while ( ++_nCurMsg < pInterface->Count() )
287 {
288 SfxSlot& rMsg = pInterface->pSlots[_nCurMsg];
289 if (rMsg.GetGroupId() == _vGroups.at(_nCurGroup))
290 return &rMsg;
291 }
292
293 return SeekSlot(++_nCurInterface );
294}
295
296
297// Query SlotName with help text
298
299
300const SfxSlot* SfxSlotPool::GetUnoSlot( const OUString& rName ) const
301{
302 const SfxSlot *pSlot = nullptr;
303 for (auto const & nInterface: _vInterfaces)
304 {
305 pSlot = nInterface->GetSlot( rName );
306 if ( pSlot )
307 break;
308 }
309
310 if ( !pSlot && _pParentPool )
311 pSlot = _pParentPool->GetUnoSlot( rName );
312
313 return pSlot;
314}
315
317{
318 SfxModule *pMod = SfxModule::GetActiveModule( pFrame );
319 if ( pMod && pMod->GetSlotPool() )
320 return *pMod->GetSlotPool();
321 else
322 return *SfxGetpApp()->Get_Impl()->pSlotPool;
323}
324
325
326/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
SfxApplication * SfxGetpApp()
Definition: app.hxx:231
std::optional< SfxSlotPool > pSlotPool
Definition: appdata.hxx:110
SAL_DLLPRIVATE SfxAppData_Impl * Get_Impl() const
Definition: app.hxx:169
SfxSlot * pSlots
Definition: objface.hxx:61
sal_uInt16 Count() const
Definition: objface.hxx:114
static SfxModule * GetActiveModule(SfxViewFrame *pFrame=nullptr)
Definition: module.cxx:208
SfxSlotPool * GetSlotPool() const
Definition: module.cxx:102
static SfxSlotPool & GetSlotPool(SfxViewFrame *pFrame=nullptr)
Definition: msgpool.cxx:316
sal_uInt16 _nCurMsg
Definition: msgpool.hxx:40
OUString SeekGroup(sal_uInt16 nNo)
Definition: msgpool.cxx:172
~SfxSlotPool()
Definition: msgpool.cxx:42
void RegisterInterface(SfxInterface &rFace)
Definition: msgpool.cxx:114
const std::type_info * GetSlotType(sal_uInt16 nSlotId) const
Definition: msgpool.cxx:146
const SfxSlot * SeekSlot(sal_uInt16 nObject)
Definition: msgpool.cxx:218
sal_uInt16 _nCurInterface
Definition: msgpool.hxx:39
SfxSlotPool(SfxSlotPool *pParent=nullptr)
Definition: msgpool.cxx:34
sal_uInt16 _nCurGroup
Definition: msgpool.hxx:38
const SfxSlot * GetSlot(sal_uInt16 nId) const
Definition: msgpool.cxx:155
const SfxSlot * GetUnoSlot(const OUString &rUnoName) const
Definition: msgpool.cxx:300
std::vector< SfxInterface * > _vInterfaces
Definition: msgpool.hxx:37
const SfxSlot * NextSlot()
Definition: msgpool.cxx:259
sal_uInt16 GetGroupCount() const
Definition: msgpool.cxx:210
SfxSlotPool * _pParentPool
Definition: msgpool.hxx:36
std::vector< SfxGroupId > _vGroups
Definition: msgpool.hxx:35
Definition: msg.hxx:184
const SfxType * GetType() const
Definition: msg.hxx:236
SfxGroupId GetGroupId() const
Definition: msg.hxx:276
sal_uInt16 nSlotId
Definition: msg.hxx:186
int nCount
SfxGroupId
Definition: groupid.hxx:30
#define SAL_WARN_IF(condition, area, stream)
int i
sal_Int16 nId
OUString SfxResId(TranslateId aId)
Definition: sfxresid.cxx:22
const std::type_info * Type() const
Definition: msg.hxx:110
Count