Merge remote-tracking branch 'upstream/master' into wiring-manager

Conflicts resolved in 24 files. Notable decisions:

- ico/icon-themes.qrc: upstream's icon folder restructure kept; the 36
  cable icon entries re-added under the new qet/qet-dark path scheme
  (XML valid, every referenced file exists).
- Toolbar system: upstream's DiagramToolbarSettings now owns the
  toolbar filling. The cable tool is registered as
  diagrameditor.add_cable (generic group loop) and listed on the
  "diagram" toolbar right after the auto-break conductor action,
  separated by a divider, exactly like before the merge.
- Paste: the cable lines of a copy are handed to
  PasteNumberingImport::push() as extra commands, so paste + cable
  lines + the numbering question stay ONE undo step on both paste
  paths (DiagramView::paste and DiagramEventAddPaste::commit).
- PDF links: upstream's deterministic link sorting kept together with
  the cable cross-reference injector (injectLinkTo -> links list).
- Element renumbering: upstream's ElementAutoNumSchemeCommand::renumber
  replaces the old formula-based body of
  QETProject::renumberElementsBySchemeTitle; the cable numbering rule
  API (cableAutoNum, axis priority, rule name) is kept in full.
- Auto-numbering pages: upstream's scheme management kept, the Câbles
  tab added as index 4 (changeToCableTab), both entry points
  changeToCable() and changeToElement() kept side by side.
- SelectAutonumW: dirty tracking and the contextEdited signal moved
  into upstream's insertPartRow() row API, so single-rule mode, the
  rule-removable button and "confirm without change leaves the project
  alone" keep working.
- xrefpropertieswidget: upstream's offset clamping kept; the cable
  branch (Texte field, Police button, hidden display options) kept;
  the stack-overlapping checkbox is hidden for cables.

Verified after the merge: build green (515/515, no errors), ctest
85/86 (only the pre-existing headless tst_menubarkeyboard failure),
offscreen smoke exit 124.
This commit is contained in:
Kellermorph
2026-10-09 14:09:08 +02:00
1767 changed files with 194544 additions and 72846 deletions
+62 -3
View File
@@ -259,7 +259,18 @@ class QetGraphicsTableItem;
which it does not, are left alone. Changing the project title is not
undoable: the application sets it directly too.
A folio's title block @b template is a seventh, separate case:
A seventh, write-only field, "preset", sizes the frame for a sheet of
paper: "a4-landscape", "tabloid-portrait" and so on (folioPresets()
lists them). It picks the column and row counts and whole-number
sizes that fill the sheet best without going over it, keeping each
size as near the current one as it can, and pushes them as one
ChangeBorderCommand. Whole numbers because the folio properties panel
edits these sizes in whole pixels: a fraction would be rounded off the
first time someone opened it. Two read-only fields, "width" and
"height", are the frame and title block together in scene units --
what an export draws -- so a caller can check the result.
A folio's title block @b template is a separate case again:
Diagram::setTitleBlockTemplate() resolves a name only against
QETProject::embeddedTitleBlockTemplatesCollection() -- the same
copy-into-the-project step addElement() already does for elements,
@@ -283,7 +294,12 @@ class QetGraphicsTableItem;
is -- x, y (its origin), rotation, and the box it occupies on the folio
(left, top, right, bottom) -- so a script can lay one thing out relative
to another instead of only setting absolute coordinates, and can check
that a move landed. insertFolio() puts a new folio at a position
that a move landed. terminalPosition() is where a wire docks on one
terminal and which way it leaves, so a symbol can be placed with a
terminal exactly in line with another one before any wire exists;
conductorPath() is a wire's drawn path by its uuid, for any wire,
where conductorSegments() needs a terminal carrying only that one.
insertFolio() puts a new folio at a position
instead of at the end, which is what reordering is mostly for while
moving an existing folio still needs the application's project view.
- @b Images: place a picture from a file. The pixels are copied into
@@ -359,6 +375,7 @@ class QetScriptApi : public QObject
Q_INVOKABLE QString projectTitle() const;
Q_INVOKABLE QString filePath() const;
Q_INVOKABLE int folioCount() const;
Q_INVOKABLE int currentFolio() const;
Q_INVOKABLE QString folioTitle(int index) const;
Q_INVOKABLE QString folioUuid(int index) const;
Q_INVOKABLE int folioIndex(const QString &uuid) const;
@@ -372,7 +389,8 @@ class QetScriptApi : public QObject
Q_INVOKABLE bool exportDxf(const QString &outDir, bool showTerminals = false);
Q_INVOKABLE bool exportCables(const QString &output);
Q_INVOKABLE bool exportWires(const QString &output);
Q_INVOKABLE bool exportBom(const QString &output);
Q_INVOKABLE bool exportBom(const QString &output, bool noSlaves = false,
bool noJunctions = false);
Q_INVOKABLE bool exportCableList(const QString &output);
Q_INVOKABLE bool exportWiring(const QString &output);
Q_INVOKABLE bool exportNets(const QString &output);
@@ -386,6 +404,8 @@ class QetScriptApi : public QObject
Q_INVOKABLE bool setElementPosition(int folioIndex, const QString &elementUuid, double x, double y);
Q_INVOKABLE bool moveElement(int folioIndex, const QString &elementUuid, double dx, double dy);
Q_INVOKABLE bool rotateElement(int folioIndex, const QString &elementUuid, double angle);
Q_INVOKABLE bool mirrorElement(int folioIndex, const QString &elementUuid, bool vertical = false);
Q_INVOKABLE QString elementMirror(int folioIndex, const QString &elementUuid) const;
Q_INVOKABLE bool deleteElement(int folioIndex, const QString &elementUuid);
// -- address what is already there --
@@ -423,6 +443,11 @@ class QetScriptApi : public QObject
Q_INVOKABLE bool moveConductorSegment(int folioIndex, const QString &elementUuid,
int terminalIndex, int segmentIndex,
double dx, double dy);
Q_INVOKABLE QString routeConductor(int folioIndex, const QString &elementUuid,
int terminalIndex);
Q_INVOKABLE QString routeConductorBetween(int folioIndex,
const QString &elementUuidA, int terminalIndexA,
const QString &elementUuidB, int terminalIndexB);
// -- cross-references: master/slave and report links --
Q_INVOKABLE QString elementLinkType(int folioIndex, const QString &elementUuid) const;
@@ -507,9 +532,15 @@ class QetScriptApi : public QObject
Q_INVOKABLE QStringList autoNums(const QString &kind) const;
Q_INVOKABLE bool addAutoNum(const QString &kind, const QString &name, const QStringList &parts);
Q_INVOKABLE bool removeAutoNum(const QString &kind, const QString &name);
Q_INVOKABLE bool renameAutoNum(const QString &kind, const QString &name, const QString &newName);
Q_INVOKABLE bool useConductorAutoNum(int folioIndex, const QString &name);
Q_INVOKABLE bool useElementAutoNum(const QString &name);
Q_INVOKABLE bool numberElement(int folioIndex, const QString &elementUuid);
Q_INVOKABLE int renumberElementAutoNum(const QString &name);
Q_INVOKABLE QVariantList freeElementNumbers(int folioIndex, const QString &elementUuid);
Q_INVOKABLE bool assignElementNumber(int folioIndex, const QString &elementUuid, int number);
Q_INVOKABLE bool assignElementAutoNum(const QString &name, int folioIndex,
const QString &elementUuid, bool overwrite);
// -- images, embedded in the project --
Q_INVOKABLE QStringList images(int folioIndex) const;
@@ -517,6 +548,8 @@ class QetScriptApi : public QObject
Q_INVOKABLE int addImage(int folioIndex, const QString &filePath, double x, double y);
Q_INVOKABLE bool setImageScale(int folioIndex, int imageIndex, double factor);
Q_INVOKABLE bool setImageRotation(int folioIndex, int imageIndex, double angle);
Q_INVOKABLE bool cropImage(int folioIndex, int imageIndex, int x, int y, int width, int height);
Q_INVOKABLE QVariantMap imageCrop(int folioIndex, int imageIndex) const;
Q_INVOKABLE bool deleteImage(int folioIndex, int imageIndex);
Q_INVOKABLE int addPdfPage(int folioIndex, const QString &pdfPath, int pageNumber,
int dpi, double x, double y);
@@ -534,6 +567,8 @@ class QetScriptApi : public QObject
Q_INVOKABLE QString elementTextProperty(int folioIndex, const QString &elementUuid,
int textIndex, const QString &property) const;
Q_INVOKABLE bool deleteElementText(int folioIndex, const QString &elementUuid, int textIndex);
Q_INVOKABLE QVariantMap elementTextGeometry(int folioIndex, const QString &elementUuid,
int textIndex) const;
// -- copy elements (with the conductors between them) to a position --
Q_INVOKABLE QStringList duplicateElements(int fromFolioIndex, const QStringList &elementUuids,
@@ -543,6 +578,17 @@ class QetScriptApi : public QObject
Q_INVOKABLE bool setProjectTitle(const QString &title);
Q_INVOKABLE QString folioBorder(int folioIndex, const QString &property) const;
Q_INVOKABLE bool setFolioBorder(int folioIndex, const QString &property, const QString &value);
Q_INVOKABLE QStringList folioPresets() const;
// -- this installation's drawing conventions (grid, flow, routing, tagging, --
// -- grouping, ...), free text, for every assistant that connects to read --
Q_INVOKABLE QString houseStyle() const;
Q_INVOKABLE bool setHouseStyle(const QString &text);
// -- the conductor defaults of a folio (Folio properties > Conductors),
// or with folioIndex -1, the project's defaults for new folios --
Q_INVOKABLE QString conductorDefault(int folioIndex, const QString &property) const;
Q_INVOKABLE bool setConductorDefault(int folioIndex, const QString &property, const QString &value);
// -- title block templates: which exist, embedding one into the project --
Q_INVOKABLE QStringList titleBlockTemplates() const;
@@ -550,6 +596,9 @@ class QetScriptApi : public QObject
// -- read an element's geometry --
Q_INVOKABLE QVariantMap elementGeometry(int folioIndex, const QString &elementUuid) const;
Q_INVOKABLE QVariantMap terminalPosition(int folioIndex, const QString &elementUuid,
int terminalIndex) const;
Q_INVOKABLE QVariantList conductorPath(int folioIndex, const QString &conductorUuid) const;
// -- folios --
Q_INVOKABLE int addFolio();
@@ -584,11 +633,19 @@ class QetScriptApi : public QObject
// -- logging: a script has no console of its own --
Q_INVOKABLE void log(const QString &message);
// -- what a script can call, read from this class itself --
Q_INVOKABLE QStringList apiSignatures() const;
static QStringList signatures();
void setUndoGrouped(bool grouped);
void setLive(QStringList *log);
private:
bool runFlag(const QString &flag, const QStringList &args);
Element *findElement(int folioIndex, const QString &elementUuid) const;
Terminal *findTerminal(int folioIndex, const QString &elementUuid, int terminalIndex,
const QString &caller);
QString applyRoute(Conductor *conductor, const QString &caller);
Conductor *findConductor(int folioIndex, const QString &elementUuid, int terminalIndex,
const QString &caller);
QList<IndependentTextItem *> sortedTexts(int folioIndex) const;
@@ -603,6 +660,8 @@ class QetScriptApi : public QObject
QETProject *m_project;
DiagramView *m_view;
bool m_undo_grouped = false;
QStringList *m_live_log = nullptr; ///< set for a live run: log() and showMessage() go here
QString m_query_error;
};