From 7667932a00ac97e5a78698835cdd512a88f29c9a Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Sun, 10 Aug 2025 16:49:51 +0200 Subject: [PATCH] Some adjustments: * Fixed instance marker when the cell is made from empty ones only * 'fit' will include empty instances --- src/db/db/dbInstances.cc | 13 ++++++++ src/db/db/dbInstances.h | 9 ++++++ src/db/unit_tests/dbCellTests.cc | 1 + src/laybasic/laybasic/layLayerProperties.cc | 31 ++++++++++++++----- src/laybasic/laybasic/layLayerProperties.h | 12 ++++++- src/laybasic/laybasic/layLayoutViewBase.cc | 2 +- src/laybasic/laybasic/layMarker.cc | 11 +++++-- .../laybasic/layRedrawThreadWorker.cc | 2 +- 8 files changed, 68 insertions(+), 13 deletions(-) diff --git a/src/db/db/dbInstances.cc b/src/db/db/dbInstances.cc index 02ca1e743..0e43a2293 100644 --- a/src/db/db/dbInstances.cc +++ b/src/db/db/dbInstances.cc @@ -907,6 +907,19 @@ Instance::bbox () const } } +Instance::box_type +Instance::bbox_with_empty () const +{ + const db::Instances *i = instances (); + const db::Cell *c = i ? i->cell () : 0; + const db::Layout *g = c ? c->layout () : 0; + if (g) { + return bbox (db::box_convert (*g)); + } else { + return db::Instance::box_type (); + } +} + // ------------------------------------------------------------------------------------- // Instances implementation diff --git a/src/db/db/dbInstances.h b/src/db/db/dbInstances.h index 17d71ab28..361f705f2 100644 --- a/src/db/db/dbInstances.h +++ b/src/db/db/dbInstances.h @@ -338,6 +338,15 @@ public: */ cell_inst_array_type::box_type bbox () const; + /** + * @brief Returns the bounding box of this array, including empty instances + * + * This method uses the pointers provided internally to identify container and cell. + * In constrast to normal "bbox", this bounding box considers empty cells as + * point-like with a box of (0,0;0,0). + */ + cell_inst_array_type::box_type bbox_with_empty () const; + /** * @brief Return the iterator for the instances of the array * diff --git a/src/db/unit_tests/dbCellTests.cc b/src/db/unit_tests/dbCellTests.cc index 5e0e8d238..8d6ccd540 100644 --- a/src/db/unit_tests/dbCellTests.cc +++ b/src/db/unit_tests/dbCellTests.cc @@ -723,6 +723,7 @@ TEST(3a) EXPECT_EQ (inst.to_string (), "cell_index=1 r0 100,-100"); EXPECT_EQ (inst.bbox ().to_string (), "()"); EXPECT_EQ (inst.bbox (db::box_convert (g)).to_string (), "(100,-100;100,-100)"); + EXPECT_EQ (inst.bbox_with_empty ().to_string (), "(100,-100;100,-100)"); EXPECT_EQ (c0.bbox ().to_string (), "()"); EXPECT_EQ (c0.bbox_with_empty ().to_string (), "(100,-100;100,-100)"); diff --git a/src/laybasic/laybasic/layLayerProperties.cc b/src/laybasic/laybasic/layLayerProperties.cc index 54d782194..041bdf668 100644 --- a/src/laybasic/laybasic/layLayerProperties.cc +++ b/src/laybasic/laybasic/layLayerProperties.cc @@ -790,7 +790,29 @@ LayerPropertiesNode::set_parent (const LayerPropertiesNode *parent) mp_parent.reset (const_cast(parent)); } -db::DBox +db::DBox +LayerPropertiesNode::overall_bbox () const +{ + tl_assert (mp_view); + lay::CellView cv = mp_view->cellview (cellview_index ()); + + if (! cv.is_valid ()) { + + return db::DBox (); + + } else { + + db::DBox b; + double dbu = cv->layout ().dbu (); + for (std::vector::const_iterator t = trans ().begin (); t != trans ().end (); ++t) { + b += (*t * db::CplxTrans (dbu) * cv.context_trans ()) * cv.cell ()->bbox_with_empty (); + } + return b; + + } +} + +db::DBox LayerPropertiesNode::bbox () const { tl_assert (mp_view); @@ -802,12 +824,7 @@ LayerPropertiesNode::bbox () const } else if (is_cell_box_layer ()) { - db::DBox b; - double dbu = cv->layout ().dbu (); - for (std::vector::const_iterator t = trans ().begin (); t != trans ().end (); ++t) { - b += (*t * db::CplxTrans (dbu) * cv.context_trans ()) * cv.cell ()->bbox (); - } - return b; + return overall_bbox (); } else { diff --git a/src/laybasic/laybasic/layLayerProperties.h b/src/laybasic/laybasic/layLayerProperties.h index 0c902f4ea..2264b7eee 100644 --- a/src/laybasic/laybasic/layLayerProperties.h +++ b/src/laybasic/laybasic/layLayerProperties.h @@ -1182,7 +1182,17 @@ public: * @return A bbox in micron units */ db::DBox bbox () const; - + + /** + * @brief Computes the overall box of this layer + * + * This is not a layer specific box, but an all-layer box, + * including transformations (if specified). + * This box is equivalent to the box delivered by + * a cell frame layer. + */ + db::DBox overall_bbox () const; + /** * @brief Attach to a view * diff --git a/src/laybasic/laybasic/layLayoutViewBase.cc b/src/laybasic/laybasic/layLayoutViewBase.cc index a786e7378..285e1b5c5 100644 --- a/src/laybasic/laybasic/layLayoutViewBase.cc +++ b/src/laybasic/laybasic/layLayoutViewBase.cc @@ -3865,7 +3865,7 @@ LayoutViewBase::full_box () const db::DBox bbox; for (LayerPropertiesConstIterator l = get_properties ().begin_const_recursive (); ! l.at_end (); ++l) { - bbox += l->bbox (); + bbox += l->overall_bbox (); } for (lay::AnnotationShapes::iterator a = annotation_shapes ().begin (); ! a.at_end (); ++a) { diff --git a/src/laybasic/laybasic/layMarker.cc b/src/laybasic/laybasic/layMarker.cc index cab2f5829..d50fe0162 100644 --- a/src/laybasic/laybasic/layMarker.cc +++ b/src/laybasic/laybasic/layMarker.cc @@ -53,7 +53,7 @@ void render_cell_inst (const db::Layout &layout, const db::CellInstArray &inst, const db::Cell &cell = layout.cell (inst.object ().cell_index ()); std::string cell_name = layout.display_name (inst.object ().cell_index ()); - db::Box cell_box = cell.bbox (); + db::Box cell_box = cell.bbox_with_empty (); db::Vector a, b; unsigned long amax = 0, bmax = 0; @@ -589,7 +589,12 @@ InstanceMarker::set_max_shapes (size_t s) db::DBox InstanceMarker::item_bbox () const { - return db::DBox (m_inst.bbox ()); + const db::Layout *ly = layout (); + if (! ly) { + return db::DBox (); + } + + return db::DBox (m_inst.bbox_with_empty ()); } // ------------------------------------------------------------------------ @@ -1059,7 +1064,7 @@ Marker::item_bbox () const } else if (m_type == Instance) { const db::Layout *ly = layout (); if (ly) { - return db::DBox (m_object.inst->bbox (db::box_convert (*ly))); + return db::DBox (m_object.inst->bbox (db::box_convert (*ly))); } } return db::DBox (); diff --git a/src/laybasic/laybasic/layRedrawThreadWorker.cc b/src/laybasic/laybasic/layRedrawThreadWorker.cc index 105daab69..68bf6e700 100644 --- a/src/laybasic/laybasic/layRedrawThreadWorker.cc +++ b/src/laybasic/laybasic/layRedrawThreadWorker.cc @@ -631,7 +631,7 @@ RedrawThreadWorker::draw_cell (bool drawing_context, int level, const db::CplxTr lay::CanvasPlane *vertices = m_planes[3 + plane_group * (planes_per_layer / 3)]; if (empty_cell) { - r.draw (dbox, 0, 0, vertices, 0); + r.draw (dbox, 0, contour, vertices, 0); } else { r.draw (dbox, fill, contour, 0, 0); }