MyGUI
3.2.1
|
00001 /* 00002 * This source file is part of MyGUI. For the latest info, see http://mygui.info/ 00003 * Distributed under the MIT License 00004 * (See accompanying file COPYING.MIT or copy at http://opensource.org/licenses/MIT) 00005 */ 00006 00007 #include "MyGUI_Precompiled.h" 00008 #include "MyGUI_LayerNode.h" 00009 #include "MyGUI_ILayerItem.h" 00010 #include "MyGUI_ITexture.h" 00011 #include "MyGUI_ISubWidget.h" 00012 #include "MyGUI_ISubWidgetText.h" 00013 00014 namespace MyGUI 00015 { 00016 00017 LayerNode::LayerNode(ILayer* _layer, ILayerNode* _parent) : 00018 mParent(_parent), 00019 mLayer(_layer), 00020 mOutOfDate(false), 00021 mDepth(0.0f) 00022 { 00023 } 00024 00025 LayerNode::~LayerNode() 00026 { 00027 for (VectorRenderItem::iterator iter = mFirstRenderItems.begin(); iter != mFirstRenderItems.end(); ++iter) 00028 delete (*iter); 00029 mFirstRenderItems.clear(); 00030 00031 for (VectorRenderItem::iterator iter = mSecondRenderItems.begin(); iter != mSecondRenderItems.end(); ++iter) 00032 delete (*iter); 00033 mSecondRenderItems.clear(); 00034 00035 for (VectorILayerNode::iterator iter = mChildItems.begin(); iter != mChildItems.end(); ++iter) 00036 delete (*iter); 00037 mChildItems.clear(); 00038 } 00039 00040 ILayerNode* LayerNode::createChildItemNode() 00041 { 00042 LayerNode* layer = new LayerNode(mLayer, this); 00043 mChildItems.push_back(layer); 00044 00045 mOutOfDate = true; 00046 00047 return layer; 00048 } 00049 00050 void LayerNode::destroyChildItemNode(ILayerNode* _node) 00051 { 00052 for (VectorILayerNode::iterator iter = mChildItems.begin(); iter != mChildItems.end(); ++iter) 00053 { 00054 if ((*iter) == _node) 00055 { 00056 delete _node; 00057 mChildItems.erase(iter); 00058 00059 mOutOfDate = true; 00060 00061 return; 00062 } 00063 } 00064 MYGUI_EXCEPT("item node not found"); 00065 } 00066 00067 void LayerNode::upChildItemNode(ILayerNode* _item) 00068 { 00069 for (VectorILayerNode::iterator iter = mChildItems.begin(); iter != mChildItems.end(); ++iter) 00070 { 00071 if ((*iter) == _item) 00072 { 00073 mChildItems.erase(iter); 00074 mChildItems.push_back(_item); 00075 00076 mOutOfDate = true; 00077 00078 return; 00079 } 00080 } 00081 MYGUI_EXCEPT("item node not found"); 00082 } 00083 00084 void LayerNode::renderToTarget(IRenderTarget* _target, bool _update) 00085 { 00086 mDepth = _target->getInfo().maximumDepth; 00087 00088 // сначала отрисовываем свое 00089 for (VectorRenderItem::iterator iter = mFirstRenderItems.begin(); iter != mFirstRenderItems.end(); ++iter) 00090 (*iter)->renderToTarget(_target, _update); 00091 00092 for (VectorRenderItem::iterator iter = mSecondRenderItems.begin(); iter != mSecondRenderItems.end(); ++iter) 00093 (*iter)->renderToTarget(_target, _update); 00094 00095 // теперь отрисовываем дочерние узлы 00096 for (VectorILayerNode::iterator iter = mChildItems.begin(); iter != mChildItems.end(); ++iter) 00097 (*iter)->renderToTarget(_target, _update); 00098 00099 mOutOfDate = false; 00100 } 00101 00102 void LayerNode::resizeView(const IntSize& _viewSize) 00103 { 00104 IntSize oldSize = mLayer->getSize(); 00105 00106 for (VectorLayerItem::const_iterator iter = mLayerItems.begin(); iter != mLayerItems.end(); ++iter) 00107 (*iter)->resizeLayerItemView(oldSize, _viewSize); 00108 } 00109 00110 ILayerItem* LayerNode::getLayerItemByPoint(int _left, int _top) const 00111 { 00112 // сначала пикаем детей 00113 for (VectorILayerNode::const_iterator iter = mChildItems.begin(); iter != mChildItems.end(); ++iter) 00114 { 00115 ILayerItem* item = (*iter)->getLayerItemByPoint(_left, _top); 00116 if (nullptr != item) 00117 return item; 00118 } 00119 00120 for (VectorLayerItem::const_iterator iter = mLayerItems.begin(); iter != mLayerItems.end(); ++iter) 00121 { 00122 ILayerItem* item = (*iter)->getLayerItemByPoint(_left, _top); 00123 if (nullptr != item) 00124 return item; 00125 } 00126 00127 return nullptr; 00128 } 00129 00130 RenderItem* LayerNode::addToRenderItem(ITexture* _texture, bool _firstQueue, bool _manualRender) 00131 { 00132 RenderItem* item = nullptr; 00133 if (_firstQueue) 00134 item = addToRenderItemFirstQueue(_texture, _manualRender); 00135 else 00136 item = addToRenderItemSecondQueue(_texture, _manualRender); 00137 00138 mOutOfDate = false; 00139 return item; 00140 } 00141 00142 RenderItem* LayerNode::addToRenderItemFirstQueue(ITexture* _texture, bool _manualRender) 00143 { 00144 if (mFirstRenderItems.empty() || _manualRender) 00145 { 00146 RenderItem* item = new RenderItem(); 00147 item->setTexture(_texture); 00148 item->setManualRender(_manualRender); 00149 mFirstRenderItems.push_back(item); 00150 00151 return item; 00152 } 00153 00154 updateCompression(); 00155 00156 // first queue keep order 00157 00158 // use either first empty buffer 00159 // or last non-empty buffer if it have same texture 00160 VectorRenderItem::reverse_iterator iter = mFirstRenderItems.rbegin(); 00161 bool itemFound = false; 00162 while (iter != mFirstRenderItems.rend()) 00163 { 00164 if ((*iter)->getNeedVertexCount() == 0) 00165 { 00166 iter++; 00167 itemFound = true; 00168 continue; 00169 } 00170 else if (!(*iter)->getManualRender() && (*iter)->getTexture() == _texture) 00171 { 00172 iter++; 00173 itemFound = true; 00174 break; 00175 } 00176 00177 break; 00178 } 00179 00180 if (itemFound) 00181 { 00182 iter--; 00183 (*iter)->setTexture(_texture); 00184 00185 return (*iter); 00186 } 00187 00188 // not found, create new 00189 RenderItem* item = new RenderItem(); 00190 item->setTexture(_texture); 00191 item->setManualRender(_manualRender); 00192 mFirstRenderItems.push_back(item); 00193 00194 return item; 00195 } 00196 00197 RenderItem* LayerNode::addToRenderItemSecondQueue(ITexture* _texture, bool _manualRender) 00198 { 00199 // order is not important in second queue 00200 // use first buffer with same texture or empty buffer 00201 for (VectorRenderItem::iterator iter = mSecondRenderItems.begin(); iter != mSecondRenderItems.end(); ++iter) 00202 { 00203 if ((*iter)->getTexture() == _texture) 00204 { 00205 return (*iter); 00206 } 00207 else if ((*iter)->getNeedVertexCount() == 0) 00208 { 00209 (*iter)->setTexture(_texture); 00210 00211 return (*iter); 00212 } 00213 } 00214 00215 // not found, create new 00216 RenderItem* item = new RenderItem(); 00217 item->setTexture(_texture); 00218 item->setManualRender(_manualRender); 00219 mSecondRenderItems.push_back(item); 00220 00221 return item; 00222 } 00223 00224 void LayerNode::attachLayerItem(ILayerItem* _item) 00225 { 00226 mLayerItems.push_back(_item); 00227 _item->attachItemToNode(mLayer, this); 00228 00229 mOutOfDate = true; 00230 } 00231 00232 void LayerNode::detachLayerItem(ILayerItem* _item) 00233 { 00234 for (VectorLayerItem::iterator iter = mLayerItems.begin(); iter != mLayerItems.end(); ++iter) 00235 { 00236 if ((*iter) == _item) 00237 { 00238 mLayerItems.erase(iter); 00239 00240 mOutOfDate = true; 00241 00242 return; 00243 } 00244 } 00245 MYGUI_EXCEPT("layer item not found"); 00246 } 00247 00248 void LayerNode::outOfDate(RenderItem* _item) 00249 { 00250 mOutOfDate = true; 00251 if (_item) 00252 _item->outOfDate(); 00253 } 00254 00255 EnumeratorILayerNode LayerNode::getEnumerator() const 00256 { 00257 return EnumeratorILayerNode(mChildItems); 00258 } 00259 00260 size_t LayerNode::getLayerNodeCount() const 00261 { 00262 return mChildItems.size(); 00263 } 00264 00265 ILayerNode* LayerNode::getLayerNodeAt(size_t _index) const 00266 { 00267 MYGUI_ASSERT_RANGE(_index, mChildItems.size(), "LayerNode::getLayerNodeAt"); 00268 00269 return mChildItems[_index]; 00270 } 00271 00272 void LayerNode::updateCompression() 00273 { 00274 if (mFirstRenderItems.size() <= 1) 00275 return; 00276 00277 bool need_compression = false; 00278 for (VectorRenderItem::iterator iter = mFirstRenderItems.begin(); iter != mFirstRenderItems.end(); ++iter) 00279 { 00280 if ((*iter)->getNeedCompression()) 00281 { 00282 need_compression = true; 00283 break; 00284 } 00285 } 00286 00287 // pushing all empty buffers to the end of buffers list 00288 if (need_compression) 00289 { 00290 VectorRenderItem nonEmptyItems; 00291 VectorRenderItem emptyItems; 00292 00293 for (VectorRenderItem::iterator iter = mFirstRenderItems.begin(); iter != mFirstRenderItems.end(); ++iter) 00294 { 00295 (*iter)->setNeedCompression(false); 00296 00297 if ((*iter)->getNeedVertexCount() == 0 && !(*iter)->getManualRender()) 00298 emptyItems.push_back(*iter); 00299 else 00300 nonEmptyItems.push_back(*iter); 00301 } 00302 nonEmptyItems.insert(nonEmptyItems.end(), emptyItems.begin(), emptyItems.end()); 00303 std::swap(mFirstRenderItems, nonEmptyItems); 00304 } 00305 00306 mOutOfDate = true; 00307 } 00308 00309 ILayer* LayerNode::getLayer() const 00310 { 00311 return mLayer; 00312 } 00313 00314 ILayerNode* LayerNode::getParent() const 00315 { 00316 return mParent; 00317 } 00318 00319 bool LayerNode::isOutOfDate() const 00320 { 00321 for (VectorRenderItem::const_iterator item = mFirstRenderItems.begin(); item != mFirstRenderItems.end(); ++item) 00322 { 00323 if ((*item)->isOutOfDate()) 00324 return true; 00325 } 00326 00327 for (VectorRenderItem::const_iterator item = mSecondRenderItems.begin(); item != mSecondRenderItems.end(); ++item) 00328 { 00329 if ((*item)->isOutOfDate()) 00330 return true; 00331 } 00332 00333 for (VectorILayerNode::const_iterator item = mChildItems.begin(); item != mChildItems.end(); ++item) 00334 { 00335 if (static_cast<const LayerNode*>(*item)->isOutOfDate()) 00336 return true; 00337 } 00338 00339 return mOutOfDate; 00340 } 00341 00342 float LayerNode::getNodeDepth() 00343 { 00344 return mDepth; 00345 } 00346 00347 } // namespace MyGUI