mirror of
https://github.com/KLayout/klayout.git
synced 2026-09-03 08:26:27 +02:00
Convenience 'each' for recursive shape iterator / recursive instance iterator
This commit is contained in:
@@ -30,6 +30,31 @@
|
||||
namespace gsi
|
||||
{
|
||||
|
||||
namespace {
|
||||
|
||||
/**
|
||||
* @brief A wrapper that allows using "each" on the iterator
|
||||
*/
|
||||
class IteratorIterator
|
||||
{
|
||||
public:
|
||||
typedef db::RecursiveInstanceIterator value_type;
|
||||
typedef db::RecursiveInstanceIterator &reference;
|
||||
typedef db::RecursiveInstanceIterator *pointer;
|
||||
typedef std::forward_iterator_tag iterator_category;
|
||||
typedef void difference_type;
|
||||
|
||||
IteratorIterator (db::RecursiveInstanceIterator *iter) : mp_iter (iter) { }
|
||||
bool at_end () const { return mp_iter->at_end (); }
|
||||
reference operator* () const { return *mp_iter; }
|
||||
void operator++ () { ++*mp_iter; }
|
||||
|
||||
private:
|
||||
db::RecursiveInstanceIterator *mp_iter;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------
|
||||
// db::RecursiveInstanceIterator binding
|
||||
|
||||
@@ -48,6 +73,11 @@ static db::RecursiveInstanceIterator *new_si2a (const db::Layout &layout, const
|
||||
return new db::RecursiveInstanceIterator (layout, cell, region, overlapping);
|
||||
}
|
||||
|
||||
static IteratorIterator each (db::RecursiveInstanceIterator *r)
|
||||
{
|
||||
return IteratorIterator (r);
|
||||
}
|
||||
|
||||
static db::DCplxTrans si_dtrans (const db::RecursiveInstanceIterator *r)
|
||||
{
|
||||
const db::Layout *ly = r->layout ();
|
||||
@@ -184,6 +214,21 @@ Class<db::RecursiveInstanceIterator> decl_RecursiveInstanceIterator ("db", "Recu
|
||||
"bounding box touches the search region are reported. The bounding box of instances is measured taking all layers "
|
||||
"of the target cell into account.\n"
|
||||
) +
|
||||
gsi::iterator_ext ("each", &each,
|
||||
"@brief Native iteration\n"
|
||||
"This method enables native iteration, e.g.\n"
|
||||
"\n"
|
||||
"@code\n"
|
||||
" iter = ... # RecursiveInstanceIterator\n"
|
||||
" iter.each do |i|\n"
|
||||
" ... i is the iterator itself\n"
|
||||
" end\n"
|
||||
"@/code\n"
|
||||
"\n"
|
||||
"This is slightly more convenient than the 'at_end' .. 'next' loop.\n"
|
||||
"\n"
|
||||
"This feature has been introduced in version 0.28.\n"
|
||||
) +
|
||||
gsi::method ("max_depth=", (void (db::RecursiveInstanceIterator::*) (int)) &db::RecursiveInstanceIterator::max_depth, gsi::arg ("depth"),
|
||||
"@brief Specifies the maximum hierarchy depth to look into\n"
|
||||
"\n"
|
||||
@@ -468,6 +513,12 @@ Class<db::RecursiveInstanceIterator> decl_RecursiveInstanceIterator ("db", "Recu
|
||||
"end\n"
|
||||
"@/code\n"
|
||||
"\n"
|
||||
"# or shorter:\n"
|
||||
"cell.begin_instances_rec.each do |iter|\n"
|
||||
" puts \"Instance of #{iter.inst_cell.name} in #{cell.name}: \" + (iter.dtrans * iter.inst_dtrans).to_s\n"
|
||||
"end\n"
|
||||
"@/code\n"
|
||||
"\n"
|
||||
"Here, a target cell is specified which confines the search to instances of this particular cell.\n"
|
||||
"'iter.dtrans' gives us the accumulated transformation of all parents up to the top cell. "
|
||||
"'iter.inst_dtrans' gives us the transformation from the current instance. "
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
|
||||
#
|
||||
/*
|
||||
|
||||
KLayout Layout Viewer
|
||||
@@ -27,12 +27,39 @@
|
||||
|
||||
#include "tlGlobPattern.h"
|
||||
|
||||
#include <iterator>
|
||||
|
||||
namespace gsi
|
||||
{
|
||||
|
||||
// ---------------------------------------------------------------
|
||||
// db::RecursiveShapeIterator binding
|
||||
|
||||
namespace {
|
||||
|
||||
/**
|
||||
* @brief A wrapper that allows using "each" on the iterator
|
||||
*/
|
||||
class IteratorIterator
|
||||
{
|
||||
public:
|
||||
typedef db::RecursiveShapeIterator value_type;
|
||||
typedef db::RecursiveShapeIterator &reference;
|
||||
typedef db::RecursiveShapeIterator *pointer;
|
||||
typedef std::forward_iterator_tag iterator_category;
|
||||
typedef void difference_type;
|
||||
|
||||
IteratorIterator (db::RecursiveShapeIterator *iter) : mp_iter (iter) { }
|
||||
bool at_end () const { return mp_iter->at_end (); }
|
||||
reference operator* () const { return *mp_iter; }
|
||||
void operator++ () { ++*mp_iter; }
|
||||
|
||||
private:
|
||||
db::RecursiveShapeIterator *mp_iter;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
static db::RecursiveShapeIterator *new_si1 (const db::Layout &layout, const db::Cell &cell, unsigned int layer)
|
||||
{
|
||||
return new db::RecursiveShapeIterator (layout, cell, layer);
|
||||
@@ -63,6 +90,11 @@ static db::RecursiveShapeIterator *new_si4a (const db::Layout &layout, const db:
|
||||
return new db::RecursiveShapeIterator (layout, cell, layers, region, overlapping);
|
||||
}
|
||||
|
||||
static IteratorIterator each (db::RecursiveShapeIterator *r)
|
||||
{
|
||||
return IteratorIterator (r);
|
||||
}
|
||||
|
||||
static db::DCplxTrans si_dtrans (const db::RecursiveShapeIterator *r)
|
||||
{
|
||||
const db::Layout *ly = r->layout ();
|
||||
@@ -236,6 +268,21 @@ Class<db::RecursiveShapeIterator> decl_RecursiveShapeIterator ("db", "RecursiveS
|
||||
"\n"
|
||||
"This constructor has been introduced in version 0.23. The 'overlapping' parameter has been made optional in version 0.27.\n"
|
||||
) +
|
||||
gsi::iterator_ext ("each", &each,
|
||||
"@brief Native iteration\n"
|
||||
"This method enables native iteration, e.g.\n"
|
||||
"\n"
|
||||
"@code\n"
|
||||
" iter = ... # RecursiveShapeIterator\n"
|
||||
" iter.each do |i|\n"
|
||||
" ... i is the iterator itself\n"
|
||||
" end\n"
|
||||
"@/code\n"
|
||||
"\n"
|
||||
"This is slightly more convenient than the 'at_end' .. 'next' loop.\n"
|
||||
"\n"
|
||||
"This feature has been introduced in version 0.28.\n"
|
||||
) +
|
||||
gsi::method ("max_depth=", (void (db::RecursiveShapeIterator::*) (int)) &db::RecursiveShapeIterator::max_depth, gsi::arg ("depth"),
|
||||
"@brief Specifies the maximum hierarchy depth to look into\n"
|
||||
"\n"
|
||||
@@ -560,6 +607,15 @@ Class<db::RecursiveShapeIterator> decl_RecursiveShapeIterator ("db", "RecursiveS
|
||||
" end\n"
|
||||
" iter.next\n"
|
||||
"end\n"
|
||||
"\n"
|
||||
"# or shorter:\n"
|
||||
"iter = cell.begin_shapes_rec(layer)\n"
|
||||
"iter.each do |iter|\n"
|
||||
" if iter.shape.renders_polygon?\n"
|
||||
" polygon = iter.shape.polygon.transformed(iter.itrans)\n"
|
||||
" puts \"In cell #{iter.cell.name}: \" + polygon.to_s\n"
|
||||
" end\n"
|
||||
"end\n"
|
||||
"@/code\n"
|
||||
"\n"
|
||||
"\\Cell offers three methods to get these iterators: begin_shapes_rec, begin_shapes_rec_touching and begin_shapes_rec_overlapping.\n"
|
||||
|
||||
Reference in New Issue
Block a user