From 2bc913140d71d4dfa3ebba093f9035a57f1c1313 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 19:42:12 +0100 Subject: [PATCH 1/6] Refined solution for partial mode snap, so grid does not have priority over edge or vertex snapping for 'snap to objects' --- src/edt/edt/edtPartialService.cc | 29 ++++++++++++++++++++++++++++- 1 file changed, 28 insertions(+), 1 deletion(-) diff --git a/src/edt/edt/edtPartialService.cc b/src/edt/edt/edtPartialService.cc index b57e5a3cd..4c35f62df 100644 --- a/src/edt/edt/edtPartialService.cc +++ b/src/edt/edt/edtPartialService.cc @@ -1808,11 +1808,38 @@ PartialService::mouse_move_event (const db::DPoint &p, unsigned int buttons, boo // for a single selected point or edge, m_start is the original position and we snap the target - // thus, we can bring the point on grid or to an object's edge or vertex snap_details = snap2 (p); + if (snap_details.object_snap == lay::PointSnapToObjectResult::NoObject) { + m_current = m_start + snap_move (p - m_start); + } else { - m_current = m_start + snap_move (snap_details.snapped_point - m_start); + + auto snapped_to_object = snap_details.snapped_point; + m_current = snapped_to_object; + + if (snap_details.object_snap != lay::PointSnapToObjectResult::ObjectVertex) { + // snap to grid on longer side of reference edge and to object on shorter + auto snapped_to_object_and_grid = m_start + snap_move (snapped_to_object - m_start); + if (std::abs (snap_details.object_ref.dx ()) > std::abs (snap_details.object_ref.dy ())) { + m_current.set_x (snapped_to_object_and_grid.x ()); + // project to edge, so we always hit it + auto cp = snap_details.object_ref.cut_point (db::DEdge (m_current, m_current + db::DVector (0, 1.0))); + if (cp.first) { + m_current.set_y (cp.second.y ()); + } + } else if (std::abs (snap_details.object_ref.dy ()) > std::abs (snap_details.object_ref.dx ())) { + m_current.set_y (snapped_to_object_and_grid.y ()); + // project to edge, so we always hit it + auto cp = snap_details.object_ref.cut_point (db::DEdge (m_current, m_current + db::DVector (1.0, 0))); + if (cp.first) { + m_current.set_x (cp.second.x ()); + } + } + } + mouse_cursor_from_snap_details (snap_details); + } } else { From f53658ea4c73479bd63fb799bf3fa6df45427781 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 21:29:05 +0100 Subject: [PATCH 2/6] Handling problem of redundant key bindings For example, @toolbar.ruler and edit_menu.modes.ruler was redundant in a sense that they point to the same action, hence, each entry in the key_binding config was overriding the other one. To solve this, there now is a primary entry, which is the edit_menu one. Only that entry is effective and listed in key_bindings. --- src/lay/lay/layMacroController.cc | 23 +++---------------- src/lay/lay/layMacroController.h | 2 -- src/lay/lay/layMainWindow.cc | 26 +++++++++++++--------- src/lay/lay/layMainWindow.h | 13 +++++++++-- src/laybasic/laybasic/layAbstractMenu.cc | 28 ++++++++++++++---------- src/laybasic/laybasic/layAbstractMenu.h | 20 ++++++++++++++--- 6 files changed, 64 insertions(+), 48 deletions(-) diff --git a/src/lay/lay/layMacroController.cc b/src/lay/lay/layMacroController.cc index 0b11f3215..1b4a5f52e 100644 --- a/src/lay/lay/layMacroController.cc +++ b/src/lay/lay/layMacroController.cc @@ -208,11 +208,6 @@ MacroController::uninitialize (lay::Dispatcher * /*root*/) bool MacroController::configure (const std::string &key, const std::string &value) { - if (key == cfg_key_bindings) { - m_key_bindings = unpack_key_binding (value); - } else if (key == cfg_menu_items_hidden) { - m_menu_items_hidden = unpack_menu_items_hidden (value); - } return false; } @@ -810,21 +805,9 @@ MacroController::do_update_menu_with_macros () add_macro_items_to_menu (m_temp_macros, used_names, groups, tech); add_macro_items_to_menu (lym::MacroCollection::root (), used_names, groups, tech); - // apply the custom keyboard shortcuts - for (std::vector >::const_iterator kb = m_key_bindings.begin (); kb != m_key_bindings.end (); ++kb) { - if (mp_mw->menu ()->is_valid (kb->first)) { - lay::Action *a = mp_mw->menu ()->action (kb->first); - a->set_shortcut (kb->second); - } - } - - // apply the custom hidden flags - for (std::vector >::const_iterator hf = m_menu_items_hidden.begin (); hf != m_menu_items_hidden.end (); ++hf) { - if (mp_mw->menu ()->is_valid (hf->first)) { - lay::Action *a = mp_mw->menu ()->action (hf->first); - a->set_hidden (hf->second); - } - } + // apply the custom keyboard shortcuts and hidden flags + mp_mw->apply_key_bindings (); + mp_mw->apply_hidden (); } void diff --git a/src/lay/lay/layMacroController.h b/src/lay/lay/layMacroController.h index ad8517f2f..76ee94868 100644 --- a/src/lay/lay/layMacroController.h +++ b/src/lay/lay/layMacroController.h @@ -249,8 +249,6 @@ private slots: tl::DeferredMethod dm_do_sync_with_external_sources; tl::DeferredMethod dm_sync_file_watcher; tl::DeferredMethod dm_sync_files; - std::vector > m_key_bindings; - std::vector > m_menu_items_hidden; void sync_implicit_macros (bool ask_before_autorun); void add_macro_items_to_menu (lym::MacroCollection &collection, std::set &used_names, std::set &groups, const db::Technology *tech); diff --git a/src/lay/lay/layMainWindow.cc b/src/lay/lay/layMainWindow.cc index f7444453c..33814584a 100644 --- a/src/lay/lay/layMainWindow.cc +++ b/src/lay/lay/layMainWindow.cc @@ -1192,8 +1192,8 @@ MainWindow::configure (const std::string &name, const std::string &value) } else if (name == cfg_menu_items_hidden) { - std::vector > hidden = unpack_menu_items_hidden (value); - apply_hidden (hidden); + m_hidden = unpack_menu_items_hidden (value); + apply_hidden (); return true; } else if (name == cfg_initial_technology) { @@ -1213,12 +1213,15 @@ MainWindow::configure (const std::string &name, const std::string &value) } void -MainWindow::apply_hidden (const std::vector > &hidden) +MainWindow::apply_hidden () { - for (std::vector >::const_iterator hf = hidden.begin (); hf != hidden.end (); ++hf) { - if (menu ()->is_valid (hf->first)) { - lay::Action *a = menu ()->action (hf->first); - a->set_hidden (hf->second); + for (std::vector >::const_iterator hf = m_hidden.begin (); hf != m_hidden.end (); ++hf) { + lay::AbstractMenuItem *item = menu ()->find_item_exact (hf->first); + if (item && item->primary ()) { + lay::Action *a = item->action (); + if (a) { + a->set_hidden (hf->second); + } } } } @@ -1227,9 +1230,12 @@ void MainWindow::apply_key_bindings () { for (std::vector >::const_iterator kb = m_key_bindings.begin (); kb != m_key_bindings.end (); ++kb) { - if (menu ()->is_valid (kb->first)) { - lay::Action *a = menu ()->action (kb->first); - a->set_shortcut (kb->second); + lay::AbstractMenuItem *item = menu ()->find_item_exact (kb->first); + if (item && item->primary ()) { + lay::Action *a = item->action (); + if (a) { + a->set_shortcut (kb->second); + } } } } diff --git a/src/lay/lay/layMainWindow.h b/src/lay/lay/layMainWindow.h index 90e3f2693..f2f43d591 100644 --- a/src/lay/lay/layMainWindow.h +++ b/src/lay/lay/layMainWindow.h @@ -534,6 +534,16 @@ Q_OBJECT */ static std::vector menu_symbols (); + /** + * @brief For internal use: apply current key bindings + */ + void apply_key_bindings (); + + /** + * @brief For internal use: apply hidden menu flags + */ + void apply_hidden (); + /** * @brief Open a new layout in mode 'mode' * @@ -770,6 +780,7 @@ protected slots: double m_default_grid; bool m_default_grids_updated; std::vector > m_key_bindings; + std::vector > m_hidden; bool m_new_layout_current_panel; bool m_synchronized_views; bool m_synchronous; @@ -864,8 +875,6 @@ protected slots: void plugin_removed (lay::PluginDeclaration *cls); void libraries_changed (); - void apply_key_bindings (); - void apply_hidden (const std::vector > &hidden); }; } diff --git a/src/laybasic/laybasic/layAbstractMenu.cc b/src/laybasic/laybasic/layAbstractMenu.cc index 44de01ab0..a97e45e7c 100644 --- a/src/laybasic/laybasic/layAbstractMenu.cc +++ b/src/laybasic/laybasic/layAbstractMenu.cc @@ -220,20 +220,22 @@ parse_menu_title (const std::string &s, std::string &title, std::string &shortcu // AbstractMenuItem implementation AbstractMenuItem::AbstractMenuItem (Dispatcher *dispatcher) - : mp_action (new Action ()), mp_dispatcher (dispatcher), m_has_submenu (false), m_remove_on_empty (false) + : mp_action (new Action ()), mp_dispatcher (dispatcher), m_has_submenu (false), m_remove_on_empty (false), m_primary (false) { // ... nothing yet .. } AbstractMenuItem::AbstractMenuItem (const AbstractMenuItem &item) - : mp_action (new Action ()), mp_dispatcher (item.dispatcher ()), m_has_submenu (false), m_remove_on_empty (false) + : mp_action (new Action ()), mp_dispatcher (item.dispatcher ()), m_has_submenu (false), m_remove_on_empty (false), m_primary (false) { // ... nothing yet .. } void -AbstractMenuItem::setup_item (const std::string &pn, const std::string &s, Action *a) +AbstractMenuItem::setup_item (const std::string &pn, const std::string &s, Action *a, bool primary) { + m_primary = primary; + m_basename.clear (); tl::Extractor ex (s.c_str ()); @@ -1587,6 +1589,8 @@ AbstractMenu::items (const std::string &path) const void AbstractMenu::insert_item (const std::string &p, const std::string &name, Action *action) { + bool primary = true; + tl::Extractor extr (p.c_str ()); while (! extr.at_end ()) { @@ -1601,7 +1605,8 @@ AbstractMenu::insert_item (const std::string &p, const std::string &name, Action parent->children.insert (iter, AbstractMenuItem (mp_dispatcher)); --iter; - iter->setup_item (parent->name (), name, action); + iter->setup_item (parent->name (), name, action, primary); + primary = false; // find any items with the same name and remove them for (std::list::iterator existing = parent->children.begin (); existing != parent->children.end (); ) { @@ -1635,7 +1640,7 @@ AbstractMenu::insert_separator (const std::string &p, const std::string &name) --iter; Action *action = new Action (); action->set_separator (true); - iter->setup_item (parent->name (), name, action); + iter->setup_item (parent->name (), name, action, true); } @@ -1655,7 +1660,7 @@ AbstractMenu::insert_menu (const std::string &p, const std::string &name, Action parent->children.insert (iter, AbstractMenuItem (mp_dispatcher)); --iter; - iter->setup_item (parent->name (), name, action); + iter->setup_item (parent->name (), name, action, true); iter->set_has_submenu (); // find any items with the same name and remove them @@ -1945,7 +1950,7 @@ AbstractMenu::find_item (tl::Extractor &extr) if (parent) { parent->children.insert (iter, AbstractMenuItem (mp_dispatcher)); --iter; - iter->setup_item (parent->name (), n, new Action ()); + iter->setup_item (parent->name (), n, new Action (), true); iter->set_has_submenu (); iter->set_remove_on_empty (); iter->set_action_title (ndesc.empty () ? n : ndesc); @@ -2055,16 +2060,17 @@ AbstractMenu::get_shortcuts (const std::string &root, std::map items = this->items (root); for (std::vector::const_iterator i = items.begin (); i != items.end (); ++i) { if (i->size () > 0) { - if (is_valid (*i) && action (*i)->is_visible ()) { - if (is_menu (*i)) { + const AbstractMenuItem *item = find_item_exact (*i); + if (item && item->action () && item->action ()->is_visible ()) { + if (item->has_submenu ()) { // a menu must be listed (so it can be hidden), but does not have a shortcut // but we don't include special menus if (i->at (0) != '@') { bindings.insert (std::make_pair (*i, std::string ())); } get_shortcuts (*i, bindings, with_defaults); - } else if (! is_separator (*i)) { - bindings.insert (std::make_pair (*i, with_defaults ? action (*i)->get_default_shortcut () : action (*i)->get_effective_shortcut ())); + } else if (! item->action ()->is_separator () && item->primary ()) { + bindings.insert (std::make_pair (*i, with_defaults ? item->action ()->get_default_shortcut () : item->action ()->get_effective_shortcut ())); } } } diff --git a/src/laybasic/laybasic/layAbstractMenu.h b/src/laybasic/laybasic/layAbstractMenu.h index aec72ac7a..d7908f5b7 100644 --- a/src/laybasic/laybasic/layAbstractMenu.h +++ b/src/laybasic/laybasic/layAbstractMenu.h @@ -559,7 +559,7 @@ struct LAYBASIC_PUBLIC AbstractMenuItem /** * @brief Internal method used to set up the item */ - void setup_item (const std::string &pn, const std::string &n, Action *a); + void setup_item (const std::string &pn, const std::string &n, Action *a, bool primary); Dispatcher *dispatcher () const { @@ -616,6 +616,11 @@ struct LAYBASIC_PUBLIC AbstractMenuItem return m_remove_on_empty; } + bool primary () const + { + return m_primary; + } + std::list children; private: @@ -623,6 +628,7 @@ struct LAYBASIC_PUBLIC AbstractMenuItem Dispatcher *mp_dispatcher; bool m_has_submenu; bool m_remove_on_empty; + bool m_primary; std::string m_name; std::string m_basename; std::set m_groups; @@ -906,6 +912,16 @@ Q_OBJECT return m_root; } + /** + * @brief For internal use: gets the AbstractMenuItem for a given path or 0 if the path is not valid (const version) + */ + const AbstractMenuItem *find_item_exact (const std::string &path) const; + + /** + * @brief For internal use: gets the AbstractMenuItem for a given path or 0 if the path is not valid + */ + AbstractMenuItem *find_item_exact (const std::string &path); + #if defined(HAVE_QT) signals: /** @@ -918,8 +934,6 @@ Q_OBJECT friend class Action; std::vector::iterator> > find_item (tl::Extractor &extr); - const AbstractMenuItem *find_item_exact (const std::string &path) const; - AbstractMenuItem *find_item_exact (const std::string &path); const AbstractMenuItem *find_item_for_action (const Action *action, const AbstractMenuItem *from = 0) const; AbstractMenuItem *find_item_for_action (const Action *action, AbstractMenuItem *from = 0); #if defined(HAVE_QT) From 998a780676a765ff96802f75ee49fbf964ad6595 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 21:44:18 +0100 Subject: [PATCH 3/6] Fixing bug #1941 (crash with navigator open) --- src/laybasic/laybasic/layLayoutViewBase.cc | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/laybasic/laybasic/layLayoutViewBase.cc b/src/laybasic/laybasic/layLayoutViewBase.cc index 19e6ab7b0..9731df590 100644 --- a/src/laybasic/laybasic/layLayoutViewBase.cc +++ b/src/laybasic/laybasic/layLayoutViewBase.cc @@ -4084,7 +4084,9 @@ LayoutViewBase::cancel_edits () // the move service takes a special role here as it manages the // transaction for the collective move operation. - mp_move_service->cancel (); + if (mp_move_service) { + mp_move_service->cancel (); + } // cancel all drag and pending edit operations such as move operations. mp_canvas->drag_cancel (); @@ -4099,7 +4101,9 @@ LayoutViewBase::finish_edits () { // the move service takes a special role here as it manages the // transaction for the collective move operation. - mp_move_service->finish (); + if (mp_move_service) { + mp_move_service->finish (); + } // cancel all drag operations mp_canvas->drag_cancel (); @@ -5460,7 +5464,7 @@ LayoutViewBase::paste_interactive (bool transient_mode) // operations. trans->close (); - if (mp_move_service->begin_move (trans.release (), transient_mode)) { + if (mp_move_service && mp_move_service->begin_move (trans.release (), transient_mode)) { switch_mode (-1); // move mode } } From dd5214dc6ef2f3c2899eb52338dd43f0abed245e Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 22:01:51 +0100 Subject: [PATCH 4/6] Fixing issue #1942 (PythonStandalone Package stubs errors), adding defaults for Box#enlarge and Box#enlarged (bonus) --- src/db/db/gsiDeclDbBox.cc | 6 +++--- testdata/ruby/dbBoxTest.rb | 9 +++++++++ 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/src/db/db/gsiDeclDbBox.cc b/src/db/db/gsiDeclDbBox.cc index 6bf0601da..697cbb2a1 100644 --- a/src/db/db/gsiDeclDbBox.cc +++ b/src/db/db/gsiDeclDbBox.cc @@ -388,7 +388,7 @@ struct box_defs "\n" "@return A reference to this box.\n" ) + - method_ext ("moved", &box_defs::moved, gsi::arg ("dx, 0"), gsi::arg ("dy", 0), + method_ext ("moved", &box_defs::moved, gsi::arg ("dx", 0), gsi::arg ("dy", 0), "@brief Moves the box by a certain distance\n" "\n" "This is a convenience method which takes two values instead of a Point object.\n" @@ -419,7 +419,7 @@ struct box_defs "\n" "@return The moved box.\n" ) + - method_ext ("enlarge", &box_defs::enlarge, gsi::arg ("dx"), gsi::arg ("dy"), + method_ext ("enlarge", &box_defs::enlarge, gsi::arg ("dx", 0), gsi::arg ("dy", 0), "@brief Enlarges the box by a certain amount.\n" "\n" "\n" @@ -436,7 +436,7 @@ struct box_defs "\n" "@return A reference to this box.\n" ) + - method_ext ("enlarged", &box_defs::enlarged, gsi::arg ("dx"), gsi::arg ("dy"), + method_ext ("enlarged", &box_defs::enlarged, gsi::arg ("dx", 0), gsi::arg ("dy", 0), "@brief Enlarges the box by a certain amount.\n" "\n" "\n" diff --git a/testdata/ruby/dbBoxTest.rb b/testdata/ruby/dbBoxTest.rb index 1a207ef81..b86c5f2f2 100644 --- a/testdata/ruby/dbBoxTest.rb +++ b/testdata/ruby/dbBoxTest.rb @@ -271,6 +271,10 @@ def test_1_Box assert_equal( a.to_s, "(-9,18;12,22)" ) a = b.moved( 1, -1 ) assert_equal( a.to_s, "(-9,16;12,20)" ) + a = b.moved( dy: 1 ) + assert_equal( a.to_s, "(-10,18;11,22)" ) + a = b.moved( dx: 1 ) + assert_equal( a.to_s, "(-9,17;12,21)" ) a = b.dup a.move( 1, -1 ) @@ -304,7 +308,12 @@ def test_1_Box aa = a.dup a.enlarge( -1, 1 ) assert_equal( a.to_s, "(-10,21;11,25)" ) + a.enlarge( 1, -1 ) + a.enlarge( dy: 1 ) + a.enlarge( dx: -1 ) + assert_equal( a.to_s, "(-10,21;11,25)" ) assert_equal( aa.enlarged( -1, 1 ).to_s, "(-10,21;11,25)" ) + assert_equal( aa.enlarged( :dy => 1, :dx => -1 ).to_s, "(-10,21;11,25)" ) a = a.enlarged( RBA::Point::new(1, -1) ) assert_equal( a.to_s, "(-11,22;12,24)" ) From bb635c3c5926f8e76529efa1f3337008a338b1a6 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 22:23:14 +0100 Subject: [PATCH 5/6] Fixing pyi stubs for Box#moved and added defaults for Box#enlarge/enlarged --- scripts/regenerate_stubs.sh | 1 + src/pymod/distutils_src/klayout/dbcore.pyi | 78 +++++++++++----------- 2 files changed, 39 insertions(+), 40 deletions(-) diff --git a/scripts/regenerate_stubs.sh b/scripts/regenerate_stubs.sh index 644f594c8..65f441ab7 100755 --- a/scripts/regenerate_stubs.sh +++ b/scripts/regenerate_stubs.sh @@ -4,6 +4,7 @@ # clean up rm -rf build dist +rm -rf python3-venv-make_stubs python3 setup.py build python3 setup.py bdist_wheel diff --git a/src/pymod/distutils_src/klayout/dbcore.pyi b/src/pymod/distutils_src/klayout/dbcore.pyi index 05e196ac5..b9c72d03c 100644 --- a/src/pymod/distutils_src/klayout/dbcore.pyi +++ b/src/pymod/distutils_src/klayout/dbcore.pyi @@ -553,7 +553,7 @@ class Box: """ ... @overload - def enlarge(self, dx: int, dy: int) -> Box: + def enlarge(self, dx: Optional[int] = ..., dy: Optional[int] = ...) -> Box: r""" @brief Enlarges the box by a certain amount. @@ -596,7 +596,7 @@ class Box: """ ... @overload - def enlarged(self, dx: int, dy: int) -> Box: + def enlarged(self, dx: Optional[int] = ..., dy: Optional[int] = ...) -> Box: r""" @brief Enlarges the box by a certain amount. @@ -701,7 +701,7 @@ class Box: """ ... @overload - def moved(self, dx, 0: int, dy: Optional[int] = ...) -> Box: + def moved(self, dx: Optional[int] = ..., dy: Optional[int] = ...) -> Box: r""" @brief Moves the box by a certain distance @@ -7407,7 +7407,7 @@ class DBox: """ ... @overload - def enlarge(self, dx: float, dy: float) -> DBox: + def enlarge(self, dx: Optional[float] = ..., dy: Optional[float] = ...) -> DBox: r""" @brief Enlarges the box by a certain amount. @@ -7450,7 +7450,7 @@ class DBox: """ ... @overload - def enlarged(self, dx: float, dy: float) -> DBox: + def enlarged(self, dx: Optional[float] = ..., dy: Optional[float] = ...) -> DBox: r""" @brief Enlarges the box by a certain amount. @@ -7555,7 +7555,7 @@ class DBox: """ ... @overload - def moved(self, dx, 0: float, dy: Optional[float] = ...) -> DBox: + def moved(self, dx: Optional[float] = ..., dy: Optional[float] = ...) -> DBox: r""" @brief Moves the box by a certain distance @@ -30277,10 +30277,9 @@ class Instance: @brief Gets the complex transformation of the instance or the first instance in the array This method is always valid compared to \trans, since simple transformations can be expressed as complex transformations as well. Setter: - @brief Sets the complex transformation of the instance or the first instance in the array (in micrometer units) - This method sets the transformation the same way as \cplx_trans=, but the displacement of this transformation is given in micrometer units. It is internally translated into database units. + @brief Sets the complex transformation of the instance or the first instance in the array - This method has been introduced in version 0.25. + This method has been introduced in version 0.23. """ da: DVector r""" @@ -41368,15 +41367,15 @@ class NetPinRef: @overload def net(self) -> Net: r""" - @brief Gets the net this pin reference is attached to (non-const version). - - This constness variant has been introduced in version 0.26.8 + @brief Gets the net this pin reference is attached to. """ ... @overload def net(self) -> Net: r""" - @brief Gets the net this pin reference is attached to. + @brief Gets the net this pin reference is attached to (non-const version). + + This constness variant has been introduced in version 0.26.8 """ ... def pin(self) -> Pin: @@ -41666,17 +41665,17 @@ class NetTerminalRef: @overload def device(self) -> Device: r""" - @brief Gets the device reference. + @brief Gets the device reference (non-const version). Gets the device object that this connection is made to. + + This constness variant has been introduced in version 0.26.8 """ ... @overload def device(self) -> Device: r""" - @brief Gets the device reference (non-const version). + @brief Gets the device reference. Gets the device object that this connection is made to. - - This constness variant has been introduced in version 0.26.8 """ ... def device_class(self) -> DeviceClass: @@ -42688,36 +42687,36 @@ class Netlist: @overload def circuit_by_name(self, name: str) -> Circuit: r""" - @brief Gets the circuit object for a given name (const version). + @brief Gets the circuit object for a given name. If the name is not a valid circuit name, nil is returned. - - This constness variant has been introduced in version 0.26.8. """ ... @overload def circuit_by_name(self, name: str) -> Circuit: r""" - @brief Gets the circuit object for a given name. + @brief Gets the circuit object for a given name (const version). If the name is not a valid circuit name, nil is returned. + + This constness variant has been introduced in version 0.26.8. """ ... @overload def circuits_by_name(self, name_pattern: str) -> List[Circuit]: r""" - @brief Gets the circuit objects for a given name filter. + @brief Gets the circuit objects for a given name filter (const version). The name filter is a glob pattern. This method will return all \Circuit objects matching the glob pattern. - This method has been introduced in version 0.26.4. + + This constness variant has been introduced in version 0.26.8. """ ... @overload def circuits_by_name(self, name_pattern: str) -> List[Circuit]: r""" - @brief Gets the circuit objects for a given name filter (const version). + @brief Gets the circuit objects for a given name filter. The name filter is a glob pattern. This method will return all \Circuit objects matching the glob pattern. - - This constness variant has been introduced in version 0.26.8. + This method has been introduced in version 0.26.4. """ ... def combine_devices(self) -> None: @@ -56566,10 +56565,11 @@ class Shape: Starting with version 0.23, this method returns nil, if the shape does not represent a box. Setter: - @brief Replaces the shape by the given box (in micrometer units) - This method replaces the shape by the given box, like \box= with a \Box argument does. This version translates the box from micrometer units to database units internally. + @brief Replaces the shape by the given box + This method replaces the shape by the given box. This method can only be called for editable layouts. It does not change the user properties of the shape. + Calling this method will invalidate any iterators. It should not be called inside a loop iterating over shapes. - This method has been introduced in version 0.25. + This method has been introduced in version 0.22. """ box_center: Point r""" @@ -57238,10 +57238,10 @@ class Shape: Applies to texts only. Will throw an exception if the object is not a text. Setter: - @brief Sets the text transformation in micrometer units + @brief Sets the text transformation Applies to texts only. Will throw an exception if the object is not a text. - This method has been introduced in version 0.25. + This method has been introduced in version 0.23. """ text_valign: int r""" @@ -60854,16 +60854,16 @@ class SubCircuit(NetlistObject): @overload def circuit_ref(self) -> Circuit: r""" - @brief Gets the circuit referenced by the subcircuit (non-const version). - - - This constness variant has been introduced in version 0.26.8 + @brief Gets the circuit referenced by the subcircuit. """ ... @overload def circuit_ref(self) -> Circuit: r""" - @brief Gets the circuit referenced by the subcircuit. + @brief Gets the circuit referenced by the subcircuit (non-const version). + + + This constness variant has been introduced in version 0.26.8 """ ... @overload @@ -61533,8 +61533,7 @@ class Text: Setter: @brief Sets the horizontal alignment - This property specifies how the text is aligned relative to the anchor point. - This property has been introduced in version 0.22 and extended to enums in 0.28. + This is the version accepting integer values. It's provided for backward compatibility. """ size: int r""" @@ -61570,8 +61569,7 @@ class Text: Setter: @brief Sets the vertical alignment - This property specifies how the text is aligned relative to the anchor point. - This property has been introduced in version 0.22 and extended to enums in 0.28. + This is the version accepting integer values. It's provided for backward compatibility. """ x: int r""" From d9957be07f3373879ecadd5a880888dbe41e9ab0 Mon Sep 17 00:00:00 2001 From: Matthias Koefferlein Date: Mon, 2 Dec 2024 22:27:18 +0100 Subject: [PATCH 6/6] Preparations for release --- Changelog | 10 ++++++++++ Changelog.Debian | 7 +++++++ version.sh | 4 ++-- 3 files changed, 19 insertions(+), 2 deletions(-) diff --git a/Changelog b/Changelog index 53c1953ad..210a64829 100644 --- a/Changelog +++ b/Changelog @@ -1,3 +1,13 @@ +0.29.10 (2024-12-03): +* Bug: %GITHUB%/issues/1941 Crash with the navigator open +* Bug: %GITHUB%/issues/1942 Syntax error in pyi stubs + As a bonus, added defaults for Box#enlarge and Box#enlarged (dx, dy) +* Bugfix: Partial mode snapping now is object first, then grid +* Bugfix: Key bindings have not been properly read from the configuration file + The change in the configuration string structure triggered an old bug: + Toolbar buttons had a twofold configuration and only the last one was + considered. Changing the order of the entries could spoil the configuration. + 0.29.9 (2024-12-01): * Bug: %GITHUB%/issues/1907 Locking layouts against modification during recursive iteration of instances and shapes This prevents crashes in write-white-iterating scenarios diff --git a/Changelog.Debian b/Changelog.Debian index 33fc15d0b..34f59cf70 100644 --- a/Changelog.Debian +++ b/Changelog.Debian @@ -1,3 +1,10 @@ +klayout (0.29.10-1) unstable; urgency=low + + * New features and bugfixes + - See changelog + + -- Matthias Köfferlein Mon, 02 Dec 2024 22:23:47 +0100 + klayout (0.29.9-1) unstable; urgency=low * New features and bugfixes diff --git a/version.sh b/version.sh index 18d074c60..51fecf2ff 100644 --- a/version.sh +++ b/version.sh @@ -2,10 +2,10 @@ # This script is sourced to define the main version parameters # The main version -KLAYOUT_VERSION="0.29.9" +KLAYOUT_VERSION="0.29.10" # The version used for PyPI (don't use variables here!) -KLAYOUT_PYPI_VERSION="0.29.9" +KLAYOUT_PYPI_VERSION="0.29.10" # The build date KLAYOUT_VERSION_DATE=$(date "+%Y-%m-%d")