Commit Graph

3530 Commits

Author SHA1 Message Date
Laurent Trinques 1572c23d51 Fix FTBFS https://github.com/qelectrotech/qelectrotech-source-mirror/
pull/477
2026-06-05 10:46:00 +02:00
Laurent Trinques be21604ad0 Merge pull request #477 from Kellermorph/update-german-translation
Fix: Dynamic element text shifting/jumping when duplicating diagrams
2026-06-01 21:10:06 +02:00
Kellermorph e1ccc1e568 Fix: Dynamic element text shifting/jumping when duplicating diagrams 2026-06-01 11:25:25 +02:00
Laurent Trinques 2b7e62f901 [PATCH] print: fix black screen on macOS arm64 after PDF export
On macOS arm64 (Apple Silicon, Sequoia), exporting a PDF via
QPrintPreviewWidget leaves a black screen with only the mouse cursor
visible.  Cmd+Tab restores the display; the exported PDF itself is
correct and clickable cross-reference links work fine.

Root cause
----------
requestPaint() is a slot connected to QPrintPreviewWidget::paintRequested.
Inside this slot the code was calling painter.end() manually, then
pdfConvertUriToGoTo().  On macOS arm64 the Qt5 paint cycle backed by
Metal/CALayer is asynchronous: closing the QPainter from *within* the
paintRequested slot interrupts the compositor before it has flushed the
backing store.  The window goes black and never repaints because the
close() that follows immediately destroys it.

On x86_64 / older macOS (raster/CoreGraphics backend) the paint cycle is
synchronous, so the same code happened to work.

Fix
---
1. Remove the manual painter.end() and pdfConvertUriToGoTo() call from
   requestPaint().  The QPainter is stack-allocated; it destructs normally
   when the slot returns, which is the correct moment to flush the PDF.

2. In print(), capture the output file name before m_preview->print(),
   then defer both pdfConvertUriToGoTo() and this->close() to the next
   event-loop iteration via QTimer::singleShot(0, ...).  This gives the
   Metal compositor one full event-loop turn to finish compositing the
   backing store before the window is torn down.

The fix is a no-op on all other platforms: QTimer::singleShot(0) posts
an event that fires in the very next iteration, so there is no perceptible
delay.

Tested
------
- macOS Sequoia 15.x, Apple M-series, Qt 5.15.x (arm64): black screen gone
- macOS 10.15 x86_64 VM, Qt 5.15.x: no regression
- Linux/Debian Qt 5.15.x: no regression
- PDF cross-reference links and GoTo/FitR destinations: unaffected

Fixes: black screen after PDF export on macOS arm64
2026-05-31 13:01:52 +02:00
Laurent Trinques cd76b6a1d6 This adds native, clickable hyperlinks to PDF exports: cross-references jump
directly to the related component on its folio, framing the target element.

When a project is exported to PDF, every cross-reference becomes an internal
link. Four kinds are covered:

- **Master → contact**: the contact list on a coil/relay (`CrossRefItem`)
- **Folio report → report**: report element labels (`DynamicElementTextItem`)
- **Slave → master**: the `(folio-position)` reference shown on a slave
  (both standalone `DynamicElementTextItem` and grouped `ElementTextItemGroup`)

Clicking a link navigates **inside** the open document (no new viewer
instance) and zooms to frame the target element.

1. **Injection** (`printDiagram`, only when the paint engine is a `QPdfEngine`):
   link rectangles are added with `QPdfEngine::drawHyperlink()`. The scene→page
   mapping is rebuilt to match exactly what `QGraphicsScene::render()` does
   (top-left anchored, `KeepAspectRatio`, **no centering**), and rectangles are
   passed in device pixels — `pageMatrix()` already applies the 72/resolution
   scale and Y-flip internally.

2. Each link URL encodes the target page and the target element's rectangle, in
   PDF points on its own page: `#page=N&fitr=L_B_R_T`.

3. **Post-processing** (`pdfConvertUriToGoTo`, run after the painter is closed):
   the `/S /URI` annotations are rewritten to native `/S /GoTo` actions with a
   `/D [pageObj 0 R /FitR L B R T]` destination, and the xref table is rebuilt.
   Pages are enumerated from the `/Pages /Kids` tree (reliable), not by scanning
   for `/Type /Page` in raw bytes.

- `sources/print/projectprintwindow.{cpp,h}` — injection + post-processing
- `sources/qetgraphicsitem/crossrefitem.{cpp,h}` — `hoveredContactsMap()` accessor; store text rect for hit area
- `sources/qetgraphicsitem/dynamicelementtextitem.h` — `slaveXrefItem()` / `masterElement()` accessors
- `sources/qetgraphicsitem/elementtextitemgroup.h` — `slaveXrefItem()` accessor
- `qelectrotech.pro`, `cmake/qet_compilation_vars.cmake` — enable Qt gui-private headers (`<private/qpdf_p.h>`)

- **Fit-to-page mode only.** Links are not injected in tiled mode (multiple
  pages per folio), which would require a per-tile transform.
- Uses Qt private API (`QPdfEngine::drawHyperlink`), stable since Qt 4 but not
  part of the public API; the build links against `gui-private`.
- Page-tree enumeration assumes the flat `/Kids` array Qt produces (no nested
  page trees).
- The frame zoom is controlled by two constants in `destRectPdf` (`pad`,
  `minSide`) and can be tuned.
- Tested on Qt5; the `/Kids` parsing and `pageMatrix` behaviour are identical on
  Qt6.
2026-05-30 18:48:28 +02:00
Kellermorph 399bc0e897 Feat: Add ability to duplicate diagrams/folios with all metadata and elements 2026-05-29 19:14:36 +02:00
Kellermorph c071e92c58 Feature: Allow excluding specific elements from BOM (Nomenclature) 2026-05-28 12:23:54 +02:00
Kellermorph 19704cf5ca Potential Isolation option for terminals 2026-05-27 21:20:50 +02:00
Kellermorph dc52105868 Fix: Wiring list filter and dynamic text timing 2026-05-26 18:31:37 +02:00
Laurent Trinques 1b8dc5f410 texteditor: set font size spinbox minimum to 4pt to prevent SIGSEGV 2026-05-25 13:14:57 +02:00
Laurent Trinques 26d5d019cc texteditor: fix SIGSEGV caused by font size spinbox reaching 0 2026-05-25 13:04:37 +02:00
Laurent Trinques 6dd7c2d926 crossrefitem: fix SIGSEGV crash + improve double-click navigation + fix PDF/SVG/print rendering
Windows Build / build-windows (push) Has been cancelled
Test Windows VS2026 migration / Build on windows-2025-vs2026 (push) Has been cancelled
Windows Build / deploy-pages (push) Has been cancelled
Fix a use-after-free crash (SIGSEGV in QRegion::begin, Qt5Gui+0x49af60)
confirmed by analysis of 19 coredumps. The crash was triggered when the
scene viewport clip region was freed during zoom/resize events while
QPicture::play() replayed drawPolyline commands through the scene painter.
Qt's raster engine then dereferenced a stale QRegionData pointer.

Root cause: CrossRefItem used three nested QPicture objects (m_drawing,
m_hdr_no_ctc, m_hdr_nc_ctc). The nested drawPicture() calls amplified
the use-after-free risk on any repaint event.

Fix: remove all QPicture from CrossRefItem entirely.
- updateLabel() now uses a QImage-backed dummy painter to compute
  m_bounding_rect, m_shape_path and m_hovered_contacts_map geometry.
  A bool m_update_map flag prevents the map from being overwritten
  during paint().
- paint() calls drawAsCross()/drawAsContacts() directly on the scene
  painter — no QPicture::play() anywhere in the class.
- buildHeaderContact() now draws NO/NC symbols directly onto the painter
  instead of recording them into QPicture members.

Also fix mouseDoubleClickEvent: the element under the click is now found
directly from m_hovered_contacts_map using the event position, rather
than relying on m_hovered_contact which could be reset by hoverMoveEvent
between the two clicks of a double-click.

Also remove setBold(true) on terminal name labels: the Qt PDF/SVG/print
engine rendered bold at 4pt as extremely thick glyphs, making exports
unreadable. Normal weight at 4pt is correct and legible on all backends.

Fixes: SIGSEGV in CrossRefItem::paint() on zoom/resize
Fixes: double-click navigation unreliable on Xref contact symbols
Fixes: terminal name labels unreadable in PDF/SVG/print export
2026-05-24 16:00:45 +02:00
Laurent Trinques ddf5ffcd89 xref: add option to hide terminal names in cross-references
Add a new boolean property 'showTerminalName' (default: true) to
XRefProperties, with full persistence in XML and QSettings.

A new checkbox "Afficher les numéros de bornes dans les Xrefs" is
added to the XRefPropertiesWidget in the main display group (not in
the cross-only group), so it is active in both Cross and Contacts modes.

When unchecked, terminal names are hidden in all three rendering paths:
  - drawContact()            (Contacts mode: NO/NC/SW symbols)
  - fillCrossRef()           (Cross mode: NO and NC columns)
  - setUpCrossBoundingRect() (Cross mode: bounding rect sizing)

Backward compatible: existing project files without the attribute
default to showTerminalName=true (no visual change).

Files changed:
  sources/properties/xrefproperties.h
  sources/properties/xrefproperties.cpp
  sources/ui/xrefpropertieswidget.ui
  sources/ui/xrefpropertieswidget.cpp
  sources/qetgraphicsitem/crossrefitem.cpp
2026-05-23 19:23:43 +02:00
Laurent Trinques 7d718bb9a0 crossrefitem: fix terminal name sorting for power contacts
The previous sort used QString::toInt() to order terminal names,
which returns 0 for any string containing a non-numeric prefix
(e.g. "R1", "R2", "L1", "L2"...). This caused undefined sort order
and incorrect pole pairing in the Xref contact mirror.

Example: a 4-pole NC power contact with terminals R1..R8 was
displaying R1/R3, R5/R7, R2/R4, R6/R8 instead of the correct
R1/R2, R3/R4, R5/R6, R7/R8.

Fix: extract the trailing numeric part of each terminal name and
compare prefixes separately. If both names share the same prefix
and both have a trailing number, sort numerically on that number;
otherwise fall back to full string comparison.

This covers all naming conventions: "1"/"2"/"3", "R1"/"R2"/"R3",
"L1"/"L2"/"L3", etc.

Applied in both drawContact() and setUpCrossBoundingRect().
2026-05-23 15:50:11 +02:00
Laurent Trinques d949e6eb8c crossrefitem: fix SIGSEGV when dropping power NC contact on diagram
Three bugs were causing a crash (SIGSEGV in QRegion::begin) when
a power NC slave element was placed on a folio, even before linking
it to a master element.

1. m_drawing (QPicture) was never reset between updateLabel() calls.
   QPicture accumulates paint commands — calling qp.begin() on an
   existing QPicture appends to it rather than replacing its content.
   After several updates (load, move, hover...) the picture became
   corrupted and crashed on play().
   Fix: reset m_drawing = QPicture() at the start of updateLabel().

2. m_drawed_contacts was only initialized to 0 in drawAsContacts(),
   but not in drawAsCross(). When drawing in Cross mode, fillCrossRef()
   called drawContact() with an uninitialized m_drawed_contacts value,
   producing a garbage offset. The NC contact symbol uses drawPolyline()
   with a sub-pixel Y coordinate (offset+2.5); with a random offset Qt
   generated an invalid QRegion and crashed.
   This explains why NC contacts crashed but NO contacts did not: the
   NO symbol only uses drawLine() which is more tolerant of bad coords.
   Fix: add m_drawed_contacts = 0 at the start of drawAsCross().

3. setUpCrossBoundingRect() used QRectF() (null rect) as the reference
   rect for painter.boundingRect(), which can return invalid dimensions.
   Additionally, height was accumulated incorrectly: united() + setHeight()
   doubled the height at each iteration, causing an exponentially growing
   bounding rect with multiple contacts.
   Fix: use QRectF(0, 0, 500, 20) as reference rect and accumulate
   height and width independently.
2026-05-23 15:32:28 +02:00
Laurent Trinques dbda958261 terminaldata: add No, Nc, Common types for SW contacts
Extend TerminalData::Type enum with three new semantic values:
- No     : Normally Open terminal of a switch (SW) contact
- Nc     : Normally Closed terminal of a switch (SW) contact
- Common : Common terminal of a switch (SW) contact

Update typeToString() and typeFromString() accordingly.
Fully backward compatible: existing Generic/Inner/Outer types
are unchanged. Elements without typed terminals fall back
to the previous behavior (first 2 named terminals).

terminal: expose terminalType() as public accessor

Add Terminal::terminalType() returning the TerminalData::Type
of this terminal. This allows crossrefitem and other consumers
to filter terminals by semantic role (No, Nc, Common) without
accessing TerminalData internals directly.

terminaleditor: add No, Nc, Common entries to type combobox

Expose the three new TerminalData types (No, Nc, Common) in
the element editor UI so users can assign a semantic role to
each terminal of a SW contact element.

Also fix a pre-existing bug in updateForm() where m_type_cb
was incorrectly using m_orientation_cb->findData() instead
of m_type_cb->findData(), preventing the type from being
restored correctly when selecting a terminal.

terminaleditor: add No, Nc, Common entries to type combobox

Expose the three new TerminalData types (No, Nc, Common) in
the element editor UI so users can assign a semantic role to
each terminal of a SW contact element.

Also fix a pre-existing bug in updateForm() where m_type_cb
was incorrectly using m_orientation_cb->findData() instead
of m_type_cb->findData(), preventing the type from being
restored correctly when selecting a terminal.
2026-05-23 02:09:32 +02:00
Kellermorph 86dafcb576 Merge branch 'master' into makro-fix 2026-05-21 20:52:18 +02:00
Kellermorph f416c2a97e New element: Line definition 2026-05-21 20:47:44 +02:00
Laurent Trinques 7426fedba3 crossrefitem: display terminal names on contact symbols in Xref
When a slave element has named terminals in its element definition
(.elmt), the terminal names (e.g. 13/14 for NO, 11/12 for NC,
12/13/14 for SW) are now displayed on each side of the contact
symbol in the cross-reference view.

- NO/NC contacts: name[0] on the left, name[1] on the right
- SW contacts: name[0] (NO) top-left, name[1] (common) top-right,
  name[2] (NC) bottom-left

Terminal names are read from Terminal::name() which is populated
from TerminalData::m_name during element parsing. If terminals are
not named, nothing is displayed (fully backward compatible).

Users are expected to name their own terminals in the element
editor to avoid duplicating elements in the official collection.
2026-05-21 17:10:44 +02:00
Kellermorph 8c557a7f29 follow up: wiring list 2026-05-18 21:31:11 +02:00
Kellermorph 0b79dfd149 Fix and Improve Multi-selection for Diagram Operations 2026-05-13 19:42:11 +02:00
Kellermorph a2b6516eb3 Fixed: Prevented the selection in the project tree from jumping to the last page when saving. 2026-04-30 07:54:53 +02:00
Kellermorph 946aa37e78 delete german notes 2026-04-29 16:17:49 +02:00
Kellermorph b8c85f9e96 Fix placing Template 2026-04-29 16:15:58 +02:00
Kellermorph ee8114d42c Fix Thumbnail in Makrotree 2026-04-29 15:56:00 +02:00
Laurent Trinques fc7d8f5f6f Merge pull request #451 from Kellermorph/makro
Auto-build doxygen docs / doxygen (push) Failing after 2m31s
Auto-build doxygen docs / deploy (push) Has been skipped
Draft: Feature - Introduce User Templates Collection and Dedicated UI Tab
2026-04-26 14:10:07 +02:00
Kellermorph 1d451a6490 Fix include paths for NameList header 2026-04-26 13:01:19 +02:00
Kellermorph 0118d94d4e makro 2026-04-26 10:48:47 +02:00
Laurent Trinques 416ec501fe GenerateSvg: Corrected view:
Auto-build doxygen docs / doxygen (push) Failing after 2m28s
Auto-build doxygen docs / deploy (push) Has been skipped
The contents of svg export is not correctly centered within the exported
area, thanks Tom
https://qelectrotech.org/forum/viewtopic.php?pid=22781#p22781
2026-04-23 09:49:42 +02:00
ChuckNr11 f60acad3b3 Fix losing Focus on moving diagram position with keyboard
Due to the changes made in the commit "Add highlight current page in
ProjectView", there is a problem when moving diagrams in the ProjectView
using the keyboard. The diagrams lose focus after being moved.
The cause is: The DiagramItem loses its selection before the move
function is executed.

The code has been adjusted.
2026-04-19 10:44:52 +02:00
Kellermorph ee65142b65 makro 2026-04-16 12:47:02 +02:00
Kellermorph eb8f859038 Terminal numbering 2026-04-09 08:36:54 +02:00
Laurent Trinques 54e19f4074 Merge pull request #448 from ChuckNr11/master
Supplement to pull request #444 by Kellermorph
2026-04-06 05:50:03 +02:00
Laurent Trinques 8af1fd708f Merge pull request #447 from Kellermorph/feature-verdrahtungsplan
Add RAM-based wiring list export
2026-04-06 05:47:24 +02:00
ChuckNr11 a64e414d63 Fix: incorrect display after deleting a diagram in elements panel 2026-04-05 22:44:35 +02:00
ChuckNr11 2ed8d76e2d add buttons 'one page left/right' to projectView tab bar
Disable the QTabWidget internal scroll buttons and add own buttons for
scroll 'one page left' and scroll 'one page right'. The scrolled
diagrams will be activated.
2026-04-05 22:39:53 +02:00
ChuckNr11 679647f52a Change operation of elementsPanel
corresponding to operation of project and diagram tabs
- click on the item activates the corresponding diagram or project.
- double click opens the corresponding properties editor.
- selecting with the up and down arrow keys has the same effect.
2026-04-05 22:21:34 +02:00
ChuckNr11 a82f6de23b Add highlight current page in ProjectView
- on clicking project tab
- on moving diagram tab
- on adding project
- on adding diagram
2026-04-05 22:11:38 +02:00
ChuckNr11 6452e03cdc refactor: move code to other place for cleaner code
connections for projectviews are made in "addProjectView"
2026-04-05 21:56:33 +02:00
Kellermorph a45a7d4e4d Remove comments about live RAM capture
Removed commented-out code explaining live RAM capture.
2026-04-05 09:09:51 +02:00
Kellermorph bc9173d726 Add RAM-based wiring list export 2026-04-05 08:33:37 +02:00
Laurent Trinques 19712d72ef TYpo
Auto-build doxygen docs / doxygen (push) Failing after 35s
Auto-build doxygen docs / deploy (push) Has been skipped
2026-04-03 14:14:29 +02:00
Laurent Trinques f23ec620dc Typo
Auto-build doxygen docs / doxygen (push) Failing after 35s
Auto-build doxygen docs / deploy (push) Has been skipped
2026-04-02 20:51:19 +02:00
Laurent Trinques 0a4c3f4601 Improve comment! 2026-04-02 17:05:06 +02:00
Laurent Trinques ab24b74c72 Now, elementproperties widget: add MAX contact slave, and count slave
contacts linked to this master, show these informations only when
element type is master.
2026-04-02 15:46:56 +02:00
Laurent Trinques 380d12e675 Typo 2026-04-02 15:35:04 +02:00
Laurent Trinques d0d3194afa On elementpropertieswidget add MAX conctact slave contact and count
slave contacts linked to this master
2026-04-02 15:07:50 +02:00
Kellermorph 9b77b4d4fa Update rectangle height and add QLabel for hidden masters 2026-04-01 16:51:41 +02:00
Kellermorph 225edec091 Translate warning message to French 2026-03-31 20:33:44 +02:00
Kellermorph 62dbaddab2 Update checkbox text for max slaves setting 2026-03-31 20:21:03 +02:00