You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

226 lines
5.6 KiB

9 years ago
9 years ago
9 years ago
9 years ago
  1. /*
  2. * This program source code file is part of KiCad, a free EDA CAD application.
  3. *
  4. * Copyright (C) 2013 CERN
  5. * Copyright (C) 2024 KiCad Developers, see AUTHORS.txt for contributors.
  6. * @author Maciej Suminski <maciej.suminski@cern.ch>
  7. *
  8. * This program is free software; you can redistribute it and/or
  9. * modify it under the terms of the GNU General Public License
  10. * as published by the Free Software Foundation; either version 2
  11. * of the License, or (at your option) any later version.
  12. *
  13. * This program is distributed in the hope that it will be useful,
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. * GNU General Public License for more details.
  17. *
  18. * You should have received a copy of the GNU General Public License
  19. * along with this program; if not, you may find one here:
  20. * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
  21. * or you may search the http://www.gnu.org website for the version 2 license,
  22. * or you may write to the Free Software Foundation, Inc.,
  23. * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
  24. *
  25. */
  26. /**
  27. * @file view_group.cpp
  28. * @brief VIEW_GROUP extends VIEW_ITEM by possibility of grouping items into a single object.
  29. * VIEW_GROUP does not take over ownership of the held items. The main purpose of this class is
  30. * to group items and draw them on a single layer (in particular the overlay).
  31. */
  32. #include <set>
  33. #include <core/kicad_algo.h>
  34. #include <view/view_group.h>
  35. #include <view/view.h>
  36. #include <view/view_item.h>
  37. #include <gal/painter.h>
  38. #include <gal/graphics_abstraction_layer.h>
  39. #include <layer_ids.h>
  40. using namespace KIGFX;
  41. VIEW_GROUP::VIEW_GROUP( VIEW* aView ) :
  42. VIEW_ITEM(),
  43. m_layer( LAYER_SELECT_OVERLAY )
  44. {
  45. }
  46. VIEW_GROUP::~VIEW_GROUP()
  47. {
  48. // VIEW_ITEM destructor removes the object from its parent view
  49. }
  50. void VIEW_GROUP::Add( VIEW_ITEM* aItem )
  51. {
  52. m_groupItems.push_back( aItem );
  53. }
  54. void VIEW_GROUP::Remove( VIEW_ITEM* aItem )
  55. {
  56. alg::delete_matching( m_groupItems, aItem );
  57. }
  58. void VIEW_GROUP::Clear()
  59. {
  60. m_groupItems.clear();
  61. }
  62. unsigned int VIEW_GROUP::GetSize() const
  63. {
  64. return m_groupItems.size();
  65. }
  66. VIEW_ITEM *VIEW_GROUP::GetItem( unsigned int idx ) const
  67. {
  68. return m_groupItems[idx];
  69. }
  70. const BOX2I VIEW_GROUP::ViewBBox() const
  71. {
  72. BOX2I bb;
  73. if( !m_groupItems.size() )
  74. {
  75. bb.SetMaximum();
  76. }
  77. else
  78. {
  79. bb = m_groupItems[0]->ViewBBox();
  80. for( VIEW_ITEM* item : m_groupItems )
  81. bb.Merge( item->ViewBBox() );
  82. }
  83. return bb;
  84. }
  85. void VIEW_GROUP::ViewDraw( int aLayer, VIEW* aView ) const
  86. {
  87. KIGFX::GAL* gal = aView->GetGAL();
  88. PAINTER* painter = aView->GetPainter();
  89. bool isSelection = m_layer == LAYER_SELECT_OVERLAY;
  90. const std::vector<VIEW_ITEM*> drawList = updateDrawList();
  91. constexpr double HIDE = std::numeric_limits<double>::max();
  92. std::map<int, std::vector<VIEW_ITEM*>> layer_item_map;
  93. // Build a list of layers used by the items in the group
  94. for( VIEW_ITEM* item : drawList )
  95. {
  96. if( aView->IsHiddenOnOverlay( item ) )
  97. continue;
  98. std::vector<int> layers = item->ViewGetLayers();
  99. for( auto layer : layers )
  100. {
  101. wxCHECK2_MSG( layer <= LAYER_ID_COUNT, continue, wxT( "Invalid item layer" ) );
  102. layer_item_map[ layer ].push_back( item );
  103. }
  104. }
  105. if( layer_item_map.empty() )
  106. return;
  107. std::vector<int> layers;
  108. layers.reserve( layer_item_map.size() );
  109. for( const std::pair<const int, std::vector<VIEW_ITEM*>>& entry : layer_item_map )
  110. layers.push_back( entry.first );
  111. aView->SortLayers( layers );
  112. // Now draw the layers in sorted order
  113. GAL_SCOPED_ATTRS scopedAttrs( *gal, GAL_SCOPED_ATTRS::LAYER_DEPTH );
  114. for( int layer : layers )
  115. {
  116. bool draw = aView->IsLayerVisible( layer );
  117. if( IsZoneFillLayer( layer ) )
  118. {
  119. // The visibility of solid areas must follow the visiblility of the zone layer
  120. int zone_main_layer = layer - LAYER_ZONE_START;
  121. draw = aView->IsLayerVisible( zone_main_layer );
  122. }
  123. if( isSelection )
  124. {
  125. switch( layer )
  126. {
  127. case LAYER_PAD_PLATEDHOLES:
  128. case LAYER_PAD_HOLEWALLS:
  129. draw = true;
  130. break;
  131. default:
  132. break;
  133. }
  134. }
  135. if( draw )
  136. {
  137. gal->AdvanceDepth();
  138. for( VIEW_ITEM* item : layer_item_map[ layer ] )
  139. {
  140. // Ignore LOD scale for selected items, but don't ignore things explicitly
  141. // hidden.
  142. if( item->ViewGetLOD( layer, aView ) == HIDE )
  143. continue;
  144. if( !painter->Draw( item, layer ) )
  145. item->ViewDraw( layer, aView ); // Alternative drawing method
  146. }
  147. }
  148. }
  149. }
  150. std::vector<int> VIEW_GROUP::ViewGetLayers() const
  151. {
  152. // Everything is displayed on a single layer
  153. return { m_layer };
  154. }
  155. void VIEW_GROUP::FreeItems()
  156. {
  157. for( unsigned int i = 0 ; i < GetSize(); i++ )
  158. delete GetItem( i );
  159. Clear();
  160. }
  161. const std::vector<VIEW_ITEM*> VIEW_GROUP::updateDrawList() const
  162. {
  163. return m_groupItems;
  164. }
  165. /*void VIEW_GROUP::ItemsSetVisibility( bool aVisible )
  166. {
  167. for(unsigned int i = 0 ; i < GetSize(); i++)
  168. GetItem(i)->ViewSetVisible( aVisible );
  169. }
  170. void VIEW_GROUP::ItemsViewUpdate( VIEW_ITEM::VIEW_UPDATE_FLAGS aFlags )
  171. {
  172. for(unsigned int i = 0 ; i < GetSize(); i++)
  173. GetItem(i)->ViewUpdate( aFlags );
  174. }*/