WSF
WsfComponentList.hpp
Go to the documentation of this file.
1// ****************************************************************************
2// CUI
3//
4// The Advanced Framework for Simulation, Integration, and Modeling (AFSIM)
5//
6// Copyright 2003-2015 The Boeing Company. All rights reserved.
7//
8// The use, dissemination or disclosure of data in this file is subject to
9// limitation or restriction. See accompanying README and LICENSE for details.
10// ****************************************************************************
11
12#ifndef WSFCOMPONENTLIST_HPP
13#define WSFCOMPONENTLIST_HPP
14
15#include "wsf_export.h"
16
17#include <algorithm>
18#include <stdexcept>
19#include <utility>
20#include <vector>
21
22#include "WsfComponent.hpp"
23
24// *************************************************************************************************
25// PROGRAMMING NOTE:
26//
27// Most of the methods within WsfComponent and WsfComponentList include the word 'Component' in the
28// name to avoid name conflicts if this class is derived from by another class (e.g.: WsfPlatform).
29// Also, some classes derive from both WsfComponent and WsfComponentList (i.e. they are a component,
30// but they also support sub-components). Thus, there may be no name conflicts between them.
31// *************************************************************************************************
32
36//
37// PROGRAMMING NOTE: This must be exported so these methods are available to all dynamic libraries.
38//
39// PROGRAMMING NOTE: The base class should not include the AddComponent method. This is a requirement
40// to ensure type-safety of derived component lists. Otherwise it would be possible
41// to inject components of the wrong type into a typed component list.
43{
44public:
45 using NameAndComponent = std::pair<WsfStringId, WsfComponent*>;
46 using ComponentList = std::vector<NameAndComponent>;
47
51 virtual ~WsfComponentList();
52
55
57 bool HasComponents() const { return (!mComponentsByName.empty()); }
58
59 void DeleteAllComponents();
60
61 bool DeleteComponent(WsfStringId aName, int aRole);
62
63 unsigned int GetComponentCount(int aRole) const;
64
70
71
79 template<class T>
81 {
82 return DeleteComponent(aName, cCOMPONENT_ROLE<T>());
83 }
84
94 template<class T>
96 {
97 bool deleted(false);
98 T* componentPtr = static_cast<T*>(FindComponentByRoleP(cCOMPONENT_ROLE<T>()));
99 if (componentPtr != nullptr)
100 {
101 deleted = DeleteComponent(componentPtr->GetComponentName(), cCOMPONENT_ROLE<T>());
102 }
103 return deleted;
104 }
105
115 template<class T>
116 T* GetComponent() const
117 {
118 return static_cast<T*>(FindComponentByRoleP(cCOMPONENT_ROLE<T>()));
119 }
120
126 template<class T>
127 T* GetComponent(WsfStringId aName) const
128 {
129 return static_cast<T*>(FindComponentP(aName, cCOMPONENT_ROLE<T>()));
130 }
131
137 template<class T>
138 unsigned int GetComponentCount() const
139 {
141 }
142
153 template<class T>
154 T* GetComponentEntry(unsigned int aEntry) const
155 {
156 return static_cast<T*>(GetComponentEntryByRoleP(cCOMPONENT_ROLE<T>(), aEntry));
157 }
158
159
169 template<class T>
170 bool FindByRole(T*& aPtr) const
171 {
172 for (const auto& component : mComponentsByName)
173 {
174 if (component.second->QueryInterfaceT(aPtr))
175 {
176 return true;
177 }
178 }
179 return false;
180 }
181
182 template<class T>
183 class RoleRange;
184
195 template<class T>
197 {
198 public:
199 RoleIterator(const WsfComponentList& aComponentList)
200 : RoleIterator(aComponentList.mComponentsByName.begin(), aComponentList.mComponentsByName.end())
201 {
202 }
203
204 RoleIterator(const RoleIterator&) = default;
205 RoleIterator& operator=(const RoleIterator& aRhs) = default;
206
208 T* operator*() const
209 {
210 T* componentPtr(nullptr);
211 mIter->second->QueryInterfaceT(componentPtr);
212 return componentPtr;
213 }
214
216 T* operator->() const
217 {
218 T* componentPtr(nullptr);
219 if (!mIter->second->QueryInterfaceT(componentPtr))
220 {
221 throw std::out_of_range("Dereference of nullptr");
222 }
223 return componentPtr;
224 }
225
227 bool operator==(const RoleIterator& aOther) const { return mIter == aOther.mIter; }
228
230 bool operator!=(const RoleIterator& aOther) const { return mIter != aOther.mIter; }
231
234 {
235 AdvanceP();
236 return *this;
237 }
238
240 bool AtEnd() const { return mIter == mEndIter; }
241
242 protected:
243 friend class RoleRange<T>;
244
245 // Invariant: aIter and aEndIter must be from the same list.
246 RoleIterator(ComponentList::const_iterator aIter, ComponentList::const_iterator aEndIter)
247 : mIter(aIter)
248 , mEndIter(aEndIter)
249 {
251
252 if ((mIter != mEndIter) && !mIter->second->ComponentHasRole(mRole))
253 {
254 AdvanceP();
255 }
256 }
257
258 void AdvanceP()
259 {
260 ++mIter;
261 while (mIter != mEndIter)
262 {
263 if (mIter->second->ComponentHasRole(mRole))
264 {
265 break;
266 }
267 ++mIter;
268 }
269 }
270
271 int mRole;
272 ComponentList::const_iterator mIter;
273 ComponentList::const_iterator mEndIter;
274 };
275
279 template<class T>
281 {
282 public:
283 RoleRange(const WsfComponentList& aComponentList)
284 : mComponentList(&aComponentList)
285 {
286 }
287
288 RoleIterator<T> begin() { return RoleIterator<T>(*mComponentList); }
289
291 {
292 return RoleIterator<T>(mComponentList->mComponentsByName.end(), mComponentList->mComponentsByName.end());
293 }
294
295 private:
296 const WsfComponentList* mComponentList;
297 };
298
309 template<typename T>
311 {
312 return RoleRange<T>(*this);
313 }
314
315protected:
316 virtual void ComponentAdded(WsfComponent* aComponentPtr);
317 virtual void ComponentDeleted(WsfComponent* aComponentPtr);
318
319 bool AddComponentP(WsfComponent* aComponentPtr, bool aDoNotify);
320
321 void CopyAllP(const WsfComponentList& aSrc, bool aDoNotify);
322
323 void DeleteAllP(bool aDoNotify);
324
325 bool DeleteComponentP(WsfStringId aName, int aRole, bool aDoNotify);
326
327 WsfComponent* FindComponentP(WsfStringId aName, int aRole) const;
328
329 WsfComponent* FindComponentP(WsfStringId aName) const;
330
331 WsfComponent* FindComponentByRoleP(int aRole) const;
332
333 WsfComponent* GetComponentEntryByRoleP(int aRole, unsigned int aEntry) const;
334
335 bool RemoveComponentP(WsfStringId aName, int aRole, bool aDelete, bool aDoNotify);
336
338};
339
341template<class COMPONENT_TYPE>
343{
344public:
345 using ComponentType = COMPONENT_TYPE;
346 using ParentType = typename COMPONENT_TYPE::ParentType;
347
350
351
363 {
364 public:
365 Iterator(const ComponentList::const_iterator& aSrc)
366 : mIterator(aSrc)
367 {
368 }
369
372 {
373 ++mIterator;
374 return *this;
375 }
376
378 bool operator!=(const Iterator& aRhs) const { return mIterator != aRhs.mIterator; }
379
381 ComponentType* operator*() const { return static_cast<ComponentType*>(mIterator->second); }
382
384 ComponentType* operator->() const { return static_cast<ComponentType*>(mIterator->second); }
385
386 private:
387 ComponentList::const_iterator mIterator;
388 };
389
390
392 Iterator Begin() const { return Iterator(mComponentsByName.begin()); }
393
395 Iterator End() const { return Iterator(mComponentsByName.end()); }
396
399 , mParentOfComponentsPtr(nullptr)
400 {
401 }
402
403 // ===========================================================================================
404 // PROGRAMMING NOTE: Do NOT be tempted to put in copy constructor that includes the new parent.
405 // In most cases the initializer for this list would be something like: "mComponents(aSrc, this)".
406 // and ANYTHING that refers to 'this' (directly or indirectly) is VERY dangerous.
407 // ===========================================================================================
408
410 : WsfComponentList(aSrc)
411 , mParentOfComponentsPtr(nullptr)
412 {
413 }
414
416
417 ~WsfComponentListT() override {}
418
420 {
421 if (this != &aRhs)
422 {
423 DeleteAllP(true);
424 CopyAllP(aRhs, false);
425 SetParentOfComponents(mParentOfComponentsPtr);
426 }
427 return *this;
428 }
429
431 {
432 if (this != &aRhs)
433 {
434 this->WsfComponentList::operator=(std::move(aRhs));
435 SetParentOfComponents(mParentOfComponentsPtr);
436 }
437 return *this;
438 }
439
442 ParentType* GetParentOfComponents() const { return mParentOfComponentsPtr; }
443
451 void SetParentOfComponents(ParentType* aComponentParentPtr)
452 {
453 mParentOfComponentsPtr = aComponentParentPtr;
454 for (const auto& component : mComponentsByName)
455 {
456 ComponentType* componentPtr(static_cast<ComponentType*>(component.second));
457 componentPtr->SetComponentParent(mParentOfComponentsPtr);
458 // The component isn't actually being added to the list here, but it is logically being
459 // added to list because this has been deferred to from the copy construction.
460 ComponentAdded(componentPtr);
461 }
462 }
463
464 bool AddComponent(ComponentType* aComponentPtr)
465 {
466 bool added = AddComponentP(aComponentPtr, true);
467 if (added)
468 {
469 aComponentPtr->SetComponentParent(mParentOfComponentsPtr);
470 }
471 return added;
472 }
473
474 ComponentType* FindComponent(WsfStringId aName) const { return static_cast<ComponentType*>(FindComponentP(aName)); }
475
476 ComponentType* FindComponent(WsfStringId aName, int aRole) const
477 {
478 return static_cast<ComponentType*>(FindComponentP(aName, aRole));
479 }
480
482 {
483 return static_cast<ComponentType*>(FindComponentByRoleP(aRole));
484 }
485
486 ComponentType* GetComponentEntryByRole(int aRole, unsigned int aEntry) const
487 {
488 return static_cast<ComponentType*>(GetComponentEntryByRoleP(aRole, aEntry));
489 }
490
492 std::vector<ComponentType*> GetComponentsByInitializationOrder() const
493 {
494 std::vector<ComponentType*> components;
495 for (const auto& component : mComponentsByName)
496 {
497 components.push_back(static_cast<ComponentType*>(component.second));
498 }
499
500 auto compare = [](const WsfComponent* aLhs, const WsfComponent* aRhs)
501 { return aLhs->GetComponentInitializationOrder() < aRhs->GetComponentInitializationOrder(); };
502 std::stable_sort(components.begin(), components.end(), compare);
503 return components;
504 }
505
506 bool RemoveComponent(ComponentType* aComponentPtr)
507 {
508 bool removed =
509 RemoveComponentP(aComponentPtr->GetComponentName(), aComponentPtr->GetComponentRoles()[0], false, true);
510 if (removed)
511 {
512 aComponentPtr->SetComponentParent(nullptr);
513 }
514 return removed;
515 }
516
517 bool ProcessComponentInput(UtInput& aInput)
518 {
519 bool myCommand{false};
520 for (ComponentType* componentPtr : *this)
521 {
522 if (componentPtr->ProcessInput(aInput))
523 {
524 myCommand = true;
525 break;
526 }
527 }
528 return myCommand;
529 }
530
531private:
533 ParentType* mParentOfComponentsPtr;
534};
535
538
539template<class T>
541{
542 return aList.Begin();
543}
544
545template<class T>
547{
548 return aList.End();
549}
550
551template<class T>
553{
554 return aList.Begin();
555}
556
557template<class T>
559{
560 return aList.End();
561}
562
563#endif
WsfComponentListT< T >::Iterator end(const WsfComponentListT< T > &aList)
Definition WsfComponentList.hpp:546
WsfComponentListT< T >::Iterator begin(const WsfComponentListT< T > &aList)
Definition WsfComponentList.hpp:540
WsfComponentListT< WsfPlatformComponent > WsfPlatformComponentList
A convenience definition for the frequently used component list containing platform components.
Definition WsfComponentList.hpp:537
UtStringId WsfStringId
WsfStringId – the same thing as UtStringId.
Definition WsfStringId.hpp:23
#define WSF_EXPORT
Definition WsfXIO_Export.hpp:35
Definition WsfComponentList.hpp:363
ComponentType * operator->() const
Return the pointer to the component.
Definition WsfComponentList.hpp:384
bool operator!=(const Iterator &aRhs) const
Test for operator inequality.
Definition WsfComponentList.hpp:378
Iterator & operator++()
Prefix increment.
Definition WsfComponentList.hpp:371
ComponentType * operator*() const
Return the pointer to the component.
Definition WsfComponentList.hpp:381
Iterator(const ComponentList::const_iterator &aSrc)
Definition WsfComponentList.hpp:365
A component list that stores only components of a specified type.
Definition WsfComponentList.hpp:343
WsfComponentListT(const WsfComponentListT &aSrc)
Definition WsfComponentList.hpp:409
typename WsfComponentT< Comm >::ParentType ParentType
Definition WsfComponentList.hpp:346
void SetParentOfComponents(ParentType *aComponentParentPtr)
Definition WsfComponentList.hpp:451
WsfComponentT< Comm > ComponentType
Definition WsfComponentList.hpp:345
std::vector< ComponentType * > GetComponentsByInitializationOrder() const
Return a vector of components in the order in which they should be initialized.
Definition WsfComponentList.hpp:492
Iterator Begin() const
Return an iterator for the beginning of the component list.
Definition WsfComponentList.hpp:392
bool ProcessComponentInput(UtInput &aInput)
Definition WsfComponentList.hpp:517
ParentType * GetParentOfComponents() const
Definition WsfComponentList.hpp:442
bool RemoveComponent(ComponentType *aComponentPtr)
Definition WsfComponentList.hpp:506
ComponentType * FindComponent(WsfStringId aName) const
Definition WsfComponentList.hpp:474
ComponentType * FindComponentByRole(int aRole) const
Definition WsfComponentList.hpp:481
Iterator End() const
Return an iterator for the end of the component list.
Definition WsfComponentList.hpp:395
ComponentType * GetComponentEntryByRole(int aRole, unsigned int aEntry) const
Definition WsfComponentList.hpp:486
bool AddComponent(ComponentType *aComponentPtr)
Definition WsfComponentList.hpp:464
~WsfComponentListT() override
Definition WsfComponentList.hpp:417
WsfComponentListT()
Definition WsfComponentList.hpp:397
WsfComponentListT(WsfComponentListT &&)=default
WsfComponentListT & operator=(WsfComponentListT &&aRhs)
Definition WsfComponentList.hpp:430
ComponentType * FindComponent(WsfStringId aName, int aRole) const
Definition WsfComponentList.hpp:476
WsfComponentListT & operator=(const WsfComponentListT &aRhs)
Definition WsfComponentList.hpp:419
Definition WsfComponentList.hpp:197
RoleIterator(const WsfComponentList &aComponentList)
Definition WsfComponentList.hpp:199
bool operator==(const RoleIterator &aOther) const
Compares two iterators for equality.
Definition WsfComponentList.hpp:227
RoleIterator & operator=(const RoleIterator &aRhs)=default
ComponentList::const_iterator mIter
Definition WsfComponentList.hpp:272
ComponentList::const_iterator mEndIter
Definition WsfComponentList.hpp:273
RoleIterator(ComponentList::const_iterator aIter, ComponentList::const_iterator aEndIter)
Definition WsfComponentList.hpp:246
T * operator*() const
Return the pointer to the component.
Definition WsfComponentList.hpp:208
RoleIterator & operator++()
Prefix increment.
Definition WsfComponentList.hpp:233
RoleIterator(const RoleIterator &)=default
T * operator->() const
Return the pointer to the component.
Definition WsfComponentList.hpp:216
bool operator!=(const RoleIterator &aOther) const
Compares two iterators for inequality.
Definition WsfComponentList.hpp:230
int mRole
Definition WsfComponentList.hpp:271
void AdvanceP()
Definition WsfComponentList.hpp:258
bool AtEnd() const
Return true if positioned at the end of the list.
Definition WsfComponentList.hpp:240
Definition WsfComponentList.hpp:281
RoleIterator< T > end()
Definition WsfComponentList.hpp:290
RoleIterator< T > begin()
Definition WsfComponentList.hpp:288
RoleRange(const WsfComponentList &aComponentList)
Definition WsfComponentList.hpp:283
Definition WsfComponentList.hpp:43
bool HasComponents() const
Returns true if the component list has at least one component.
Definition WsfComponentList.hpp:57
std::vector< NameAndComponent > ComponentList
Definition WsfComponentList.hpp:46
bool DeleteComponent(WsfStringId aName, int aRole)
Definition WsfComponentList.cpp:62
bool DeleteComponent()
Definition WsfComponentList.hpp:95
WsfComponentList(WsfComponentList &&)=default
WsfComponent * GetComponentEntryByRoleP(int aRole, unsigned int aEntry) const
Definition WsfComponentList.cpp:235
T * GetComponentEntry(unsigned int aEntry) const
Definition WsfComponentList.hpp:154
T * GetComponent(WsfStringId aName) const
Definition WsfComponentList.hpp:127
RoleRange< T > GetComponentRange()
Definition WsfComponentList.hpp:310
WsfComponentList()
Definition WsfComponentList.cpp:15
ComponentList mComponentsByName
Definition WsfComponentList.hpp:337
bool DeleteComponent(WsfStringId aName)
Definition WsfComponentList.hpp:80
unsigned int GetComponentCount(int aRole) const
Definition WsfComponentList.cpp:71
T * GetComponent() const
Definition WsfComponentList.hpp:116
std::pair< WsfStringId, WsfComponent * > NameAndComponent
Definition WsfComponentList.hpp:45
WsfComponent * FindComponentP(WsfStringId aName, int aRole) const
Definition WsfComponentList.cpp:204
WsfComponentList & operator=(const WsfComponentList &aRhs)
Definition WsfComponentList.cpp:30
bool AddComponentP(WsfComponent *aComponentPtr, bool aDoNotify)
Definition WsfComponentList.cpp:147
unsigned int GetComponentCount() const
Definition WsfComponentList.hpp:138
void CopyAllP(const WsfComponentList &aSrc, bool aDoNotify)
Base class implementation of copying a component list.
Definition WsfComponentList.cpp:101
void DeleteAllP(bool aDoNotify)
Base class implementation of deleting all components in the list.
Definition WsfComponentList.cpp:117
bool RemoveComponentP(WsfStringId aName, int aRole, bool aDelete, bool aDoNotify)
Definition WsfComponentList.cpp:253
virtual void ComponentAdded(WsfComponent *aComponentPtr)
Definition WsfComponentList.cpp:89
WsfComponent * FindComponentByRoleP(int aRole) const
Definition WsfComponentList.cpp:222
bool FindByRole(T *&aPtr) const
Definition WsfComponentList.hpp:170
Definition WsfComponent.hpp:119
void SetComponentParent(ParentType *aParentPtr)
Definition WsfComponent.hpp:159
Definition WsfComponent.hpp:39
virtual const int * GetComponentRoles() const =0
virtual WsfStringId GetComponentName() const =0
virtual int GetComponentInitializationOrder() const
Definition WsfComponent.hpp:79
virtual bool ProcessInput(UtInput &aInput)
Definition WsfComponent.cpp:100
Definition WsfComponentRoles.hpp:60
Copyrights Multiple, All Rights Reserved