From 26028cdeb94c0a04361d09086a7a0e2f2981e1c9 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Sat, 26 Sep 2020 23:41:39 +0200 Subject: [PATCH] WIP: refactoring, unify shape iterator --- src/db/db/db.pro | 4 + src/db/db/dbDeepRegion.cc | 17 ++ src/db/db/dbFlatRegion.cc | 4 +- src/db/db/dbFlatRegion.h | 39 +--- src/db/db/dbGenericShapeIterator.cc | 23 ++ src/db/db/dbGenericShapeIterator.h | 322 ++++++++++++++++++++++++++++ src/db/db/dbHierProcessor.cc | 31 +-- src/db/db/dbHierProcessor.h | 287 +------------------------ src/db/db/dbOriginalLayerRegion.cc | 27 ++- src/db/db/dbRegion.h | 62 +----- src/db/db/dbRegionDelegate.h | 15 +- src/db/db/dbShapeFlags.cc | 23 ++ src/db/db/dbShapeFlags.h | 79 +++++++ 13 files changed, 522 insertions(+), 411 deletions(-) create mode 100644 src/db/db/dbGenericShapeIterator.cc create mode 100644 src/db/db/dbGenericShapeIterator.h create mode 100644 src/db/db/dbShapeFlags.cc create mode 100644 src/db/db/dbShapeFlags.h diff --git a/src/db/db/db.pro b/src/db/db/db.pro index 512094c23..91ae32572 100644 --- a/src/db/db/db.pro +++ b/src/db/db/db.pro @@ -28,6 +28,7 @@ SOURCES = \ dbEdges.cc \ dbFillTool.cc \ dbFuzzyCellMapping.cc \ + dbGenericShapeIterator.cc \ dbGlyphs.cc \ dbHershey.cc \ dbInstances.cc \ @@ -63,6 +64,7 @@ SOURCES = \ dbRegionLocalOperations.cc \ dbSaveLayoutOptions.cc \ dbShape.cc \ + dbShapeFlags.cc \ dbShapes2.cc \ dbShapes3.cc \ dbShapes.cc \ @@ -224,6 +226,7 @@ HEADERS = \ dbEdgesToContours.h \ dbFillTool.h \ dbFuzzyCellMapping.h \ + dbGenericShapeIterator.h \ dbHash.h \ dbHersheyFont.h \ dbHershey.h \ @@ -263,6 +266,7 @@ HEADERS = \ dbRegionLocalOperations.h \ dbSaveLayoutOptions.h \ dbShape.h \ + dbShapeFlags.h \ dbShapeRepository.h \ dbShapes2.h \ dbShapeProcessor.h \ diff --git a/src/db/db/dbDeepRegion.cc b/src/db/db/dbDeepRegion.cc index 925e5a6c6..e311b42b2 100644 --- a/src/db/db/dbDeepRegion.cc +++ b/src/db/db/dbDeepRegion.cc @@ -79,11 +79,28 @@ public: return &m_polygon; } + virtual bool equals (const generic_shape_iterator_delegate_base *other) const + { + const DeepRegionIterator *o = dynamic_cast (other); + return o && o->m_iter == m_iter; + } + virtual RegionIteratorDelegate *clone () const { return new DeepRegionIterator (*this); } + virtual void do_reset (const db::Box ®ion, bool overlapping) + { + m_iter.set_region (region); + m_iter.set_overlapping (overlapping); + } + + virtual db::Box bbox () const + { + return m_iter.bbox (); + } + private: friend class Region; diff --git a/src/db/db/dbFlatRegion.cc b/src/db/db/dbFlatRegion.cc index 1468ed533..9c0249a72 100644 --- a/src/db/db/dbFlatRegion.cc +++ b/src/db/db/dbFlatRegion.cc @@ -142,7 +142,7 @@ FlatRegion::ensure_merged_polygons_valid () const RegionIteratorDelegate *FlatRegion::begin () const { - return new FlatRegionIterator (m_polygons.get_layer ().begin (), m_polygons.get_layer ().end ()); + return new FlatRegionIterator (&m_polygons); } RegionIteratorDelegate *FlatRegion::begin_merged () const @@ -151,7 +151,7 @@ RegionIteratorDelegate *FlatRegion::begin_merged () const return begin (); } else { ensure_merged_polygons_valid (); - return new FlatRegionIterator (m_merged_polygons.get_layer ().begin (), m_merged_polygons.get_layer ().end ()); + return new FlatRegionIterator (&m_merged_polygons); } } diff --git a/src/db/db/dbFlatRegion.h b/src/db/db/dbFlatRegion.h index 383d96872..915df4a97 100644 --- a/src/db/db/dbFlatRegion.h +++ b/src/db/db/dbFlatRegion.h @@ -35,44 +35,7 @@ namespace db { /** * @brief An iterator delegate for the flat region */ -class DB_PUBLIC FlatRegionIterator - : public RegionIteratorDelegate -{ -public: - typedef db::layer polygon_layer_type; - typedef polygon_layer_type::iterator iterator_type; - - FlatRegionIterator (iterator_type from, iterator_type to) - : m_from (from), m_to (to) - { - // .. nothing yet .. - } - - virtual bool at_end () const - { - return m_from == m_to; - } - - virtual void increment () - { - ++m_from; - } - - virtual const value_type *get () const - { - return m_from.operator-> (); - } - - virtual RegionIteratorDelegate *clone () const - { - return new FlatRegionIterator (*this); - } - -private: - friend class Region; - - iterator_type m_from, m_to; -}; +typedef generic_shapes_iterator_delegate FlatRegionIterator; /** * @brief A flat, polygon-set delegate diff --git a/src/db/db/dbGenericShapeIterator.cc b/src/db/db/dbGenericShapeIterator.cc new file mode 100644 index 000000000..5b262b217 --- /dev/null +++ b/src/db/db/dbGenericShapeIterator.cc @@ -0,0 +1,23 @@ + +/* + + KLayout Layout Viewer + Copyright (C) 2006-2020 Matthias Koefferlein + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +*/ + +#include "dbGenericShapeIterator.h" diff --git a/src/db/db/dbGenericShapeIterator.h b/src/db/db/dbGenericShapeIterator.h new file mode 100644 index 000000000..cbe10dce2 --- /dev/null +++ b/src/db/db/dbGenericShapeIterator.h @@ -0,0 +1,322 @@ + +/* + + KLayout Layout Viewer + Copyright (C) 2006-2020 Matthias Koefferlein + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +*/ + +#ifndef HDR_dbGenericShapeIterator +#define HDR_dbGenericShapeIterator + +#include "dbCommon.h" +#include "dbShapes.h" +#include "dbShapeFlags.h" + +namespace db +{ + +template +class DB_PUBLIC generic_shape_iterator_delegate_base +{ +public: + typedef T value_type; + + generic_shape_iterator_delegate_base () { } + virtual ~generic_shape_iterator_delegate_base () { } + + virtual void do_reset (const db::Box & /*region*/, bool /*overlapping*/) { } + virtual db::Box bbox () const { return db::Box::world (); } + virtual bool at_end () const = 0; + virtual void increment () = 0; + virtual const T *get () const = 0; + virtual generic_shape_iterator_delegate_base *clone () const = 0; + virtual bool equals (const generic_shape_iterator_delegate_base *other) const = 0; +}; + +template +class DB_PUBLIC generic_shape_iterator_delegate2 + : public generic_shape_iterator_delegate_base +{ +public: + typedef typename Iter::value_type value_type; + + generic_shape_iterator_delegate2 (const Iter &from, const Iter &to) + : m_iter (from), m_from (from), m_to (to) + { } + + virtual void do_reset (const db::Box &, bool) + { + m_iter = m_from; + } + + virtual bool at_end () const + { + return m_iter == m_to; + } + + virtual void increment () + { + ++m_iter; + } + + virtual const value_type *get () const + { + return m_iter.operator-> (); + } + + generic_shape_iterator_delegate_base *clone () const + { + return new generic_shape_iterator_delegate2 (*this); + } + + virtual bool equals (const generic_shape_iterator_delegate_base *other) const + { + const generic_shape_iterator_delegate2 *o = dynamic_cast *> (other); + return o && o->m_iter == m_iter; + } + +private: + Iter m_iter, m_from, m_to; +}; + +template +class DB_PUBLIC generic_shape_iterator_delegate1 + : public generic_shape_iterator_delegate_base +{ +public: + typedef typename Iter::value_type value_type; + + generic_shape_iterator_delegate1 (const Iter &from) + : m_iter (from), m_from (from) + { } + + virtual void do_reset (const db::Box &, bool) + { + m_iter = m_from; + } + + virtual bool at_end () const + { + return m_iter.at_end (); + } + + virtual void increment () + { + ++m_iter; + } + + virtual const value_type *get () const + { + return m_iter.operator-> (); + } + + generic_shape_iterator_delegate_base *clone () const + { + return new generic_shape_iterator_delegate1 (*this); + } + + virtual bool equals (const generic_shape_iterator_delegate_base *other) const + { + const generic_shape_iterator_delegate1 *o = dynamic_cast *> (other); + return o && o->m_iter == m_iter; + } + +private: + Iter m_iter, m_from; +}; + +template +class DB_PUBLIC generic_shapes_iterator_delegate + : public generic_shape_iterator_delegate_base +{ +public: + generic_shapes_iterator_delegate (const db::Shapes *shapes) + : mp_shapes (shapes), m_iter (mp_shapes->begin (shape_flags ())) + { + // .. nothing yet .. + } + + virtual void do_reset (const db::Box &box, bool overlapping) + { + if (box == db::Box::world ()) { + m_iter = mp_shapes->begin (shape_flags ()); + } else { + if (mp_shapes->is_bbox_dirty ()) { + const_cast (mp_shapes)->update (); + } + if (overlapping) { + m_iter = mp_shapes->begin_overlapping (box, shape_flags ()); + } else { + m_iter = mp_shapes->begin_touching (box, shape_flags ()); + } + } + } + + virtual bool at_end () const + { + return m_iter.at_end (); + } + + virtual void increment () + { + ++m_iter; + } + + virtual const T *get () const + { + return m_iter->basic_ptr (typename T::tag ()); + } + + generic_shape_iterator_delegate_base *clone () const + { + return new generic_shapes_iterator_delegate (*this); + } + + virtual db::Box bbox () const + { + if (mp_shapes->is_bbox_dirty ()) { + const_cast (mp_shapes)->update (); + } + return mp_shapes->bbox (); + } + + virtual bool equals (const generic_shape_iterator_delegate_base *other) const + { + const generic_shapes_iterator_delegate *o = dynamic_cast *> (other); + return o && o->mp_shapes == mp_shapes && o->m_iter.at_end () == m_iter.at_end () && (m_iter.at_end () || o->m_iter->basic_ptr (typename T::tag ()) == m_iter->basic_ptr (typename T::tag ())); + } + +private: + const db::Shapes *mp_shapes; + db::Shapes::shape_iterator m_iter; + + generic_shapes_iterator_delegate (const generic_shapes_iterator_delegate &other) + : mp_shapes (other.mp_shapes), m_iter (other.m_iter) + { + // .. nothing yet .. + } +}; + +template +class DB_PUBLIC generic_shape_iterator +{ +public: + typedef T value_type; + typedef const value_type &reference; + typedef const value_type *pointer; + typedef std::forward_iterator_tag iterator_category; + typedef void difference_type; + + template + generic_shape_iterator (const Iter &from, const Iter &to) + : mp_delegate (new generic_shape_iterator_delegate2 (from, to)) + { } + + template + generic_shape_iterator (const Iter &from) + : mp_delegate (new generic_shape_iterator_delegate1 (from)) + { } + + generic_shape_iterator () + : mp_delegate (0) + { } + + generic_shape_iterator (generic_shape_iterator_delegate_base *delegate) + : mp_delegate (delegate) + { } + + generic_shape_iterator (const db::Shapes *shapes) + : mp_delegate (new generic_shapes_iterator_delegate (shapes)) + { } + + generic_shape_iterator (const generic_shape_iterator &other) + : mp_delegate (other.mp_delegate ? other.mp_delegate->clone () : 0) + { } + + ~generic_shape_iterator () + { + delete mp_delegate; + } + + generic_shape_iterator &operator= (const generic_shape_iterator &other) + { + if (this != &other) { + delete mp_delegate; + mp_delegate = other.mp_delegate ? other.mp_delegate->clone () : 0; + } + return *this; + } + + bool operator== (const generic_shape_iterator &other) const + { + return mp_delegate && other.mp_delegate && mp_delegate->equals (other.mp_delegate); + } + + template + bool operator== (const generic_shape_iterator &) const + { + return false; + } + + reference operator* () const + { + return *mp_delegate->get (); + } + + pointer operator-> () const + { + return mp_delegate->get (); + } + + generic_shape_iterator &operator++ () + { + mp_delegate->increment (); + return *this; + } + + bool at_end () const + { + return !mp_delegate || mp_delegate->at_end (); + } + + void reset () + { + if (mp_delegate) { + mp_delegate->do_reset (db::Box::world (), false); + } + } + + void reset (const db::Box &box, bool overlapping) + { + if (mp_delegate) { + mp_delegate->do_reset (box, overlapping); + } + } + + db::Box bbox () const + { + return mp_delegate ? mp_delegate->bbox () : db::Box (); + } + +public: + generic_shape_iterator_delegate_base *mp_delegate; +}; + +} + +#endif diff --git a/src/db/db/dbHierProcessor.cc b/src/db/db/dbHierProcessor.cc index 62f35a489..7d59c58dd 100644 --- a/src/db/db/dbHierProcessor.cc +++ b/src/db/db/dbHierProcessor.cc @@ -28,6 +28,7 @@ #include "dbEdgeProcessor.h" #include "dbPolygonGenerators.h" #include "dbLocalOperationUtils.h" +#include "dbShapeFlags.h" #include "tlLog.h" #include "tlTimer.h" #include "tlInternational.h" @@ -1637,7 +1638,7 @@ struct scan_shape2shape_same_layer } void - operator () (const shapes_iterator &, unsigned int, unsigned int, shape_interactions &, db::Coord) const + operator () (const generic_shape_iterator &, unsigned int, unsigned int, shape_interactions &, db::Coord) const { // cannot have different types on the same layer tl_assert (false); @@ -1668,13 +1669,13 @@ struct scan_shape2shape_same_layer } void - operator () (const shapes_iterator &subjects, unsigned int subject_id0, unsigned int intruder_layer, shape_interactions &interactions, db::Coord dist) const + operator () (const generic_shape_iterator &subjects, unsigned int subject_id0, unsigned int intruder_layer, shape_interactions &interactions, db::Coord dist) const { db::box_scanner scanner; interaction_registration_shape1 rec (&interactions, intruder_layer); unsigned int id = subject_id0; - for (shapes_iterator i = subjects; !i.at_end (); ++i) { + for (generic_shape_iterator i = subjects; !i.at_end (); ++i) { scanner.insert (i.operator-> (), id++); } @@ -1715,7 +1716,7 @@ struct scan_shape2shape_different_layers } void - operator () (db::Layout *layout, const shapes_iterator &subjects, const shapes_iterator &intruders, unsigned int subject_id0, unsigned int intruder_layer, shape_interactions &interactions, db::Coord dist) const + operator () (db::Layout *layout, const generic_shape_iterator &subjects, const generic_shape_iterator &intruders, unsigned int subject_id0, unsigned int intruder_layer, shape_interactions &interactions, db::Coord dist) const { db::box_scanner2 scanner; interaction_registration_shape2shape rec (layout, &interactions, intruder_layer); @@ -1737,13 +1738,13 @@ struct scan_shape2shape_different_layers unsigned int id = subject_id0; - shapes_iterator is = subjects; + generic_shape_iterator is = subjects; is.reset (common_box, true); for ( ; !is.at_end (); ++is) { scanner.insert1 (is.operator-> (), id++); } - shapes_iterator ii = intruders; + generic_shape_iterator ii = intruders; ii.reset (common_box, true); for (; !ii.at_end (); ++ii) { scanner.insert2 (ii.operator-> (), interactions.next_id ()); @@ -1870,43 +1871,43 @@ template void local_processor::run_flat (const db::Shapes *subject_shapes, const db::Shapes *intruders, const local_operation *op, db::Shapes *result_shapes) const { - std::vector > is; - is.push_back (shapes_iterator (intruders)); + std::vector > is; + is.push_back (generic_shape_iterator (intruders)); std::vector os; os.push_back (result_shapes); - run_flat (shapes_iterator (subject_shapes), is, op, os); + run_flat (generic_shape_iterator (subject_shapes), is, op, os); } template void local_processor::run_flat (const db::Shapes *subject_shapes, const std::vector &intruders, const local_operation *op, const std::vector &result_shapes) const { - std::vector > is; + std::vector > is; is.reserve (intruders.size ()); for (std::vector::const_iterator i = intruders.begin (); i != intruders.end (); ++i) { - is.push_back (shapes_iterator (*i)); + is.push_back (generic_shape_iterator (*i)); } - run_flat (shapes_iterator (subject_shapes), is, op, result_shapes); + run_flat (generic_shape_iterator (subject_shapes), is, op, result_shapes); } template void -local_processor::run_flat (const shapes_iterator &subjects, const std::vector > &intruders, const local_operation *op, const std::vector &result_shapes) const +local_processor::run_flat (const generic_shape_iterator &subjects, const std::vector > &intruders, const local_operation *op, const std::vector &result_shapes) const { tl_assert (mp_subject_top == 0); tl_assert (mp_intruder_top == 0); shape_interactions interactions; - for (typename std::vector >::const_iterator il = intruders.begin (); il != intruders.end (); ++il) { + for (typename std::vector >::const_iterator il = intruders.begin (); il != intruders.end (); ++il) { // insert dummy interactions to accommodate subject vs. nothing and assign an ID // range for the subject shapes. unsigned int subject_id0 = 0; - for (shapes_iterator i = subjects; !i.at_end (); ++i) { + for (generic_shape_iterator i = subjects; !i.at_end (); ++i) { unsigned int id = interactions.next_id (); if (subject_id0 == 0) { diff --git a/src/db/db/dbHierProcessor.h b/src/db/db/dbHierProcessor.h index 72e5f5525..6832a95db 100644 --- a/src/db/db/dbHierProcessor.h +++ b/src/db/db/dbHierProcessor.h @@ -29,6 +29,7 @@ #include "dbLayout.h" #include "dbLocalOperation.h" +#include "dbGenericShapeIterator.h" #include "tlThreadedWorkers.h" #include "tlProgress.h" @@ -371,290 +372,6 @@ public: } }; -template unsigned int shape_flags (); - -template <> -inline unsigned int shape_flags () -{ - return 1 << db::ShapeIterator::PolygonRef; -} - -template <> -inline unsigned int shape_flags () -{ - return db::ShapeIterator::Edges; -} - -template <> -inline unsigned int shape_flags () -{ - return db::ShapeIterator::Texts; -} - -template -class DB_PUBLIC iterator_delegate_base -{ -public: - iterator_delegate_base () { } - virtual ~iterator_delegate_base () { } - - virtual void do_reset (const db::Box ®ion, bool overlapping) = 0; - virtual db::Box bbox () const { return db::Box::world (); } - virtual bool at_end () const = 0; - virtual void inc () = 0; - virtual const T *get () const = 0; - virtual iterator_delegate_base *clone () const = 0; - virtual bool equals (const iterator_delegate_base *other) const = 0; -}; - -template -class DB_PUBLIC iterator_delegate2 - : public iterator_delegate_base -{ -public: - typedef typename Iter::value_type value_type; - - iterator_delegate2 (const Iter &from, const Iter &to) - : m_iter (from), m_from (from), m_to (to) - { } - - virtual void do_reset (const db::Box &, bool) - { - m_iter = m_from; - } - - virtual bool at_end () const - { - return m_iter == m_to; - } - - virtual void inc () - { - ++m_iter; - } - - virtual const value_type *get () const - { - return m_iter.operator-> (); - } - - iterator_delegate_base *clone () const - { - return new iterator_delegate2 (*this); - } - - virtual bool equals (const iterator_delegate_base *other) const - { - const iterator_delegate2 *o = dynamic_cast *> (other); - return o && o->m_iter == m_iter; - } - -private: - Iter m_iter, m_from, m_to; -}; - -template -class DB_PUBLIC iterator_delegate1 - : public iterator_delegate_base -{ -public: - typedef typename Iter::value_type value_type; - - iterator_delegate1 (const Iter &from) - : m_iter (from), m_from (from) - { } - - virtual void do_reset (const db::Box &, bool) - { - m_iter = m_from; - } - - virtual bool at_end () const - { - return m_iter.at_end (); - } - - virtual void inc () - { - ++m_iter; - } - - virtual const value_type &get () const - { - return *m_iter; - } - - iterator_delegate_base *clone () const - { - return new iterator_delegate1 (*this); - } - - virtual bool equals (const iterator_delegate_base *other) const - { - const iterator_delegate1 *o = dynamic_cast *> (other); - return o && o->m_iter == m_iter; - } - -private: - Iter m_iter, m_from; -}; - -template -class DB_PUBLIC shapes_iterator_delegate - : public iterator_delegate_base -{ -public: - shapes_iterator_delegate (const db::Shapes *shapes) - : mp_shapes (shapes), m_iter (mp_shapes->begin (shape_flags ())) - { - // .. nothing yet .. - } - - virtual void do_reset (const db::Box &box, bool overlapping) - { - if (box == db::Box::world ()) { - m_iter = mp_shapes->begin (shape_flags ()); - } else { - if (mp_shapes->is_bbox_dirty ()) { - const_cast (mp_shapes)->update (); - } - if (overlapping) { - m_iter = mp_shapes->begin_overlapping (box, shape_flags ()); - } else { - m_iter = mp_shapes->begin_touching (box, shape_flags ()); - } - } - } - - virtual bool at_end () const - { - return m_iter.at_end (); - } - - virtual void inc () - { - ++m_iter; - } - - virtual const T *get () const - { - return m_iter->basic_ptr (typename T::tag ()); - } - - iterator_delegate_base *clone () const - { - return new shapes_iterator_delegate (*this); - } - - virtual db::Box bbox () const - { - if (mp_shapes->is_bbox_dirty ()) { - const_cast (mp_shapes)->update (); - } - return mp_shapes->bbox (); - } - - virtual bool equals (const iterator_delegate_base *other) const - { - const shapes_iterator_delegate *o = dynamic_cast *> (other); - return o && o->mp_shapes == mp_shapes && o->m_iter.at_end () == m_iter.at_end () && (m_iter.at_end () || o->m_iter->basic_ptr (typename T::tag ()) == m_iter->basic_ptr (typename T::tag ())); - } - -private: - const db::Shapes *mp_shapes; - db::Shapes::shape_iterator m_iter; - - shapes_iterator_delegate (const shapes_iterator_delegate &other) - : mp_shapes (other.mp_shapes), m_iter (other.m_iter) - { - // .. nothing yet .. - } -}; - -template -class DB_PUBLIC shapes_iterator -{ -public: - template - shapes_iterator (const Iter &from, const Iter &to) - : mp_delegate (new iterator_delegate2 (from, to)) - { } - - template - shapes_iterator (const Iter &from) - : mp_delegate (new iterator_delegate1 (from)) - { } - - shapes_iterator (const db::Shapes *shapes) - : mp_delegate (new shapes_iterator_delegate (shapes)) - { } - - shapes_iterator (const shapes_iterator &other) - : mp_delegate (other.mp_delegate->clone ()) - { } - - shapes_iterator &operator= (const shapes_iterator &other) - { - delete mp_delegate; - mp_delegate = other.mp_delegate->clone (); - } - - bool operator== (const shapes_iterator &other) const - { - return mp_delegate->equals (other.mp_delegate); - } - - template - bool operator== (const shapes_iterator &) const - { - return false; - } - - ~shapes_iterator () - { - delete mp_delegate; - } - - const T &operator* () const - { - return *mp_delegate->get (); - } - - const T *operator-> () const - { - return mp_delegate->get (); - } - - shapes_iterator &operator++ () - { - mp_delegate->inc (); - return *this; - } - - bool at_end () const - { - return mp_delegate->at_end (); - } - - void reset () - { - mp_delegate->do_reset (db::Box::world (), false); - } - - void reset (const db::Box &box, bool overlapping) - { - mp_delegate->do_reset (box, overlapping); - } - - db::Box bbox () const - { - return mp_delegate->bbox (); - } - -public: - iterator_delegate_base *mp_delegate; -}; - template class DB_PUBLIC local_processor { @@ -669,7 +386,7 @@ public: void run_flat (const db::Shapes *subject_shapes, const db::Shapes *intruders, const local_operation *op, db::Shapes *result_shapes) const; void run_flat (const db::Shapes *subjects, const std::vector &intruders, const local_operation *op, const std::vector &result_shapes) const; - void run_flat (const shapes_iterator &subjects, const std::vector > &intruders, const local_operation *op, const std::vector &result_shapes) const; + void run_flat (const generic_shape_iterator &subjects, const std::vector > &intruders, const local_operation *op, const std::vector &result_shapes) const; void set_description (const std::string &d) { diff --git a/src/db/db/dbOriginalLayerRegion.cc b/src/db/db/dbOriginalLayerRegion.cc index 39700e04e..b788141af 100644 --- a/src/db/db/dbOriginalLayerRegion.cc +++ b/src/db/db/dbOriginalLayerRegion.cc @@ -57,7 +57,7 @@ namespace virtual void increment () { - inc (); + do_increment (); set (); } @@ -71,6 +71,27 @@ namespace return new OriginalLayerRegionIterator (*this); } + virtual bool equals (const generic_shape_iterator_delegate_base *other) const + { + const OriginalLayerRegionIterator *o = dynamic_cast (other); + return o && o->m_rec_iter == m_rec_iter && o->m_iter_trans.equal (m_iter_trans); + } + + virtual void do_reset (const db::Box ®ion, bool overlapping) + { + if (region == db::Box::world ()) { + m_rec_iter.set_region (region); + } else { + m_rec_iter.set_region (m_iter_trans.inverted () * region); + } + m_rec_iter.set_overlapping (overlapping); + } + + virtual db::Box bbox () const + { + return m_iter_trans * m_rec_iter.bbox (); + } + private: friend class Region; @@ -89,7 +110,7 @@ namespace } } - void inc () + void do_increment () { if (! m_rec_iter.at_end ()) { ++m_rec_iter; @@ -172,7 +193,7 @@ OriginalLayerRegion::begin_merged () const return begin (); } else { ensure_merged_polygons_valid (); - return new FlatRegionIterator (m_merged_polygons.get_layer ().begin (), m_merged_polygons.get_layer ().end ()); + return new FlatRegionIterator (& m_merged_polygons); } } diff --git a/src/db/db/dbRegion.h b/src/db/db/dbRegion.h index 0278ed4c5..aea98e015 100644 --- a/src/db/db/dbRegion.h +++ b/src/db/db/dbRegion.h @@ -47,19 +47,14 @@ class TransformationReducer; * The iterator delivers the polygons of the region */ class DB_PUBLIC RegionIterator + : public generic_shape_iterator { public: - typedef RegionIteratorDelegate::value_type value_type; - typedef const value_type &reference; - typedef const value_type *pointer; - typedef std::forward_iterator_tag iterator_category; - typedef void difference_type; - /** * @brief Default constructor */ RegionIterator () - : mp_delegate (0) + : generic_shape_iterator () { // .. nothing yet .. } @@ -69,27 +64,18 @@ public: * The iterator will take ownership over the delegate */ RegionIterator (RegionIteratorDelegate *delegate) - : mp_delegate (delegate) + : generic_shape_iterator (delegate) { // .. nothing yet .. } - /** - * @brief Destructor - */ - ~RegionIterator () - { - delete mp_delegate; - mp_delegate = 0; - } - /** * @brief Copy constructor and assignment */ RegionIterator (const RegionIterator &other) - : mp_delegate (0) + : generic_shape_iterator (static_cast &> (other)) { - operator= (other); + // .. nothing yet .. } /** @@ -97,52 +83,18 @@ public: */ RegionIterator &operator= (const RegionIterator &other) { - if (this != &other) { - delete mp_delegate; - mp_delegate = other.mp_delegate ? other.mp_delegate->clone () : 0; - } + generic_shape_iterator::operator= (other); return *this; } - /** - * @Returns true, if the iterator is at the end - */ - bool at_end () const - { - return mp_delegate == 0 || mp_delegate->at_end (); - } - /** * @brief Increment */ RegionIterator &operator++ () { - if (mp_delegate) { - mp_delegate->increment (); - } + generic_shape_iterator::operator++ (); return *this; } - - /** - * @brief Access - */ - reference operator* () const - { - const value_type *value = operator-> (); - tl_assert (value != 0); - return *value; - } - - /** - * @brief Access - */ - pointer operator-> () const - { - return mp_delegate ? mp_delegate->get () : 0; - } - -private: - RegionIteratorDelegate *mp_delegate; }; /** diff --git a/src/db/db/dbRegionDelegate.h b/src/db/db/dbRegionDelegate.h index 928bbe114..c9e346ec6 100644 --- a/src/db/db/dbRegionDelegate.h +++ b/src/db/db/dbRegionDelegate.h @@ -32,6 +32,7 @@ #include "dbEdgePairs.h" #include "dbEdgePairRelations.h" #include "dbShapeCollection.h" +#include "dbGenericShapeIterator.h" #include @@ -142,19 +143,7 @@ typedef shape_collection_processor PolygonToEdgePairP /** * @brief The region iterator delegate */ -class DB_PUBLIC RegionIteratorDelegate -{ -public: - RegionIteratorDelegate () { } - virtual ~RegionIteratorDelegate () { } - - typedef db::Polygon value_type; - - virtual bool at_end () const = 0; - virtual void increment () = 0; - virtual const value_type *get () const = 0; - virtual RegionIteratorDelegate *clone () const = 0; -}; +typedef db::generic_shape_iterator_delegate_base RegionIteratorDelegate; /** * @brief The delegate for the actual region implementation diff --git a/src/db/db/dbShapeFlags.cc b/src/db/db/dbShapeFlags.cc new file mode 100644 index 000000000..2cd5b5f47 --- /dev/null +++ b/src/db/db/dbShapeFlags.cc @@ -0,0 +1,23 @@ + +/* + + KLayout Layout Viewer + Copyright (C) 2006-2020 Matthias Koefferlein + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +*/ + +#include "dbShapeFlags.h" diff --git a/src/db/db/dbShapeFlags.h b/src/db/db/dbShapeFlags.h new file mode 100644 index 000000000..fe6a5e5bb --- /dev/null +++ b/src/db/db/dbShapeFlags.h @@ -0,0 +1,79 @@ + +/* + + KLayout Layout Viewer + Copyright (C) 2006-2020 Matthias Koefferlein + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +*/ + + +#ifndef HDR_dbShapeFlags +#define HDR_dbShapeFlags + +#include "dbCommon.h" +#include "dbShapes.h" + +namespace db +{ + +template unsigned int shape_flags (); + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::PolygonRef; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::Box; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::Path; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::Polygon; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::Edge; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::Text; +} + +template <> +inline unsigned int shape_flags () +{ + return 1 << db::ShapeIterator::TextRef; +} + +} + +#endif