MyGUI  3.2.1
MyGUI_LayerManager.cpp
Go to the documentation of this file.
1 /*
2  * This source file is part of MyGUI. For the latest info, see http://mygui.info/
3  * Distributed under the MIT License
4  * (See accompanying file COPYING.MIT or copy at http://opensource.org/licenses/MIT)
5  */
6 
7 #include "MyGUI_Precompiled.h"
8 #include "MyGUI_LayerManager.h"
9 #include "MyGUI_LayerItem.h"
10 #include "MyGUI_WidgetManager.h"
11 #include "MyGUI_RenderManager.h"
12 #include "MyGUI_Widget.h"
13 #include "MyGUI_FactoryManager.h"
14 
15 #include "MyGUI_SharedLayer.h"
16 #include "MyGUI_OverlappedLayer.h"
17 
18 namespace MyGUI
19 {
20 
21  template <> LayerManager* Singleton<LayerManager>::msInstance = nullptr;
22  template <> const char* Singleton<LayerManager>::mClassTypeName = "LayerManager";
23 
25  mIsInitialise(false),
26  mCategoryName("Layer")
27  {
28  }
29 
31  {
32  MYGUI_ASSERT(!mIsInitialise, getClassTypeName() << " initialised twice");
33  MYGUI_LOG(Info, "* Initialise: " << getClassTypeName());
34 
36  ResourceManager::getInstance().registerLoadXmlDelegate(mCategoryName) = newDelegate(this, &LayerManager::_load);
37 
40 
41  MYGUI_LOG(Info, getClassTypeName() << " successfully initialized");
42  mIsInitialise = true;
43  }
44 
46  {
47  MYGUI_ASSERT(mIsInitialise, getClassTypeName() << " is not initialised");
48  MYGUI_LOG(Info, "* Shutdown: " << getClassTypeName());
49 
52 
53  // удаляем все хранители слоев
54  clear();
55 
58 
59  MYGUI_LOG(Info, getClassTypeName() << " successfully shutdown");
60  mIsInitialise = false;
61  }
62 
63  void LayerManager::clear()
64  {
65  for (VectorLayer::iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
66  {
67  destroy(*iter);
68  }
69  mLayerNodes.clear();
70  }
71 
72  void LayerManager::_load(xml::ElementPtr _node, const std::string& _file, Version _version)
73  {
74  VectorLayer layers;
75  // берем детей и крутимся, основной цикл
76  xml::ElementEnumerator layer = _node->getElementEnumerator();
77  while (layer.next(mCategoryName))
78  {
79 
80  std::string name;
81 
82  if ( !layer->findAttribute("name", name))
83  {
84  MYGUI_LOG(Warning, "Attribute 'name' not found (file : " << _file << ")");
85  continue;
86  }
87 
88  for (VectorLayer::iterator iter = layers.begin(); iter != layers.end(); ++iter)
89  {
90  MYGUI_ASSERT((*iter)->getName() != name, "Layer '" << name << "' already exist (file : " << _file << ")");
91  }
92 
93  std::string type = layer->findAttribute("type");
94  if (type.empty() && _version <= Version(1, 0))
95  {
96  bool overlapped = utility::parseBool(layer->findAttribute("overlapped"));
97  type = overlapped ? "OverlappedLayer" : "SharedLayer";
98  }
99 
100  IObject* object = FactoryManager::getInstance().createObject(mCategoryName, type);
101  MYGUI_ASSERT(object != nullptr, "factory '" << type << "' is not found");
102 
103  ILayer* item = object->castType<ILayer>();
104  item->deserialization(layer.current(), _version);
105 
106  layers.push_back(item);
107  }
108 
109  // теперь мержим новые и старые слои
110  merge(layers);
111  }
112 
113  void LayerManager::_unlinkWidget(Widget* _widget)
114  {
115  detachFromLayer(_widget);
116  }
117 
118  // поправить на виджет и проверять на рутовость
119  void LayerManager::attachToLayerNode(const std::string& _name, Widget* _item)
120  {
121  MYGUI_ASSERT(nullptr != _item, "pointer must be valid");
122  MYGUI_ASSERT(_item->isRootWidget(), "attached widget must be root");
123 
124  // сначала отсоединяем
125  _item->detachFromLayer();
126 
127  // а теперь аттачим
128  for (VectorLayer::iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
129  {
130  if (_name == (*iter)->getName())
131  {
132  ILayerNode* node = (*iter)->createChildItemNode();
133  node->attachLayerItem(_item);
134 
135  return;
136  }
137  }
138  MYGUI_LOG(Error, "Layer '" << _name << "' is not found");
139  //MYGUI_EXCEPT("Layer '" << _name << "' is not found");
140  }
141 
143  {
144  MYGUI_ASSERT(nullptr != _item, "pointer must be valid");
145  _item->detachFromLayer();
146  }
147 
149  {
150  MYGUI_ASSERT(nullptr != _item, "pointer must be valid");
151  _item->upLayerItem();
152  }
153 
154  bool LayerManager::isExist(const std::string& _name) const
155  {
156  return getByName(_name, false) != nullptr;
157  }
158 
159  void LayerManager::merge(VectorLayer& _layers)
160  {
161  for (VectorLayer::iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
162  {
163  if ((*iter) == nullptr) continue;
164  bool find = false;
165  std::string name = (*iter)->getName();
166  for (VectorLayer::iterator iter2 = _layers.begin(); iter2 != _layers.end(); ++iter2)
167  {
168  if (name == (*iter2)->getName())
169  {
170  // заменяем новый слой, на уже существующий
171  delete (*iter2);
172  (*iter2) = (*iter);
173  (*iter) = nullptr;
174  find = true;
175  break;
176  }
177  }
178  if (!find)
179  {
180  destroy(*iter);
181  (*iter) = nullptr;
182  }
183  }
184 
185  // теперь в основной
186  mLayerNodes = _layers;
187  }
188 
189  void LayerManager::destroy(ILayer* _layer)
190  {
191  MYGUI_LOG(Info, "destroy layer '" << _layer->getName() << "'");
192  delete _layer;
193  }
194 
196  {
197  VectorLayer::reverse_iterator iter = mLayerNodes.rbegin();
198  while (iter != mLayerNodes.rend())
199  {
200  ILayerItem* item = (*iter)->getLayerItemByPoint(_left, _top);
201  if (item != nullptr) return static_cast<Widget*>(item);
202  ++iter;
203  }
204  return nullptr;
205  }
206 
207  void LayerManager::renderToTarget(IRenderTarget* _target, bool _update)
208  {
209  for (VectorLayer::iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
210  {
211  (*iter)->renderToTarget(_target, _update);
212  }
213  }
214 
215  ILayer* LayerManager::getByName(const std::string& _name, bool _throw) const
216  {
217  for (VectorLayer::const_iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
218  {
219  if (_name == (*iter)->getName())
220  return (*iter);
221  }
222  MYGUI_ASSERT(!_throw, "Layer '" << _name << "' not found");
223  return nullptr;
224  }
225 
227  {
228  return EnumeratorLayer(mLayerNodes);
229  }
230 
231  void LayerManager::resizeView(const IntSize& _viewSize)
232  {
233  for (VectorLayer::const_iterator iter = mLayerNodes.begin(); iter != mLayerNodes.end(); ++iter)
234  (*iter)->resizeView(_viewSize);
235  }
236 
238  {
239  return mLayerNodes.size();
240  }
241 
243  {
244  MYGUI_ASSERT_RANGE(_index, mLayerNodes.size(), "LayerManager::getLayer");
245  return mLayerNodes[_index];
246  }
247 
248  const std::string& LayerManager::getCategoryName() const
249  {
250  return mCategoryName;
251  }
252 
253 } // namespace MyGUI