Skip to content

Add support for C++ QML Elements in CxxQtBuilder #1146

New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

Open
wants to merge 1 commit into
base: main
Choose a base branch
from

Conversation

akiselev
Copy link
Contributor

@akiselev akiselev commented Dec 19, 2024

This PR is a WIP to add support for registering classes implemented in C++ with a QML module so that they can be included in Cargo-only builds. Instead of just running moc on a header, it also includes the generated metatype information which is needed to register the C++ QML elements.

This first implementation is one I wrote to unblock my own project so I'd appreciate some advice for how to integrate this properly into cxx-qt-build. It should probably be another property on QmlModule like so, but I couldn't figure out how to best implement it that way:

    let module: QmlModule<&str, &str> = QmlModule {
        uri: "Clippo.Theme",
        rust_files: &[
            "src/theme.rs",
        ],
        cpp_files: &[
            ("src/ThemeManager.h", "src/ThemeManager.cpp"),
        ],
        ..Default::default()
    };

With @LeonMatthesKDAB's temporary fix found in #1135, it correctly includes C++ QML elements in modules built with Cargo only.

- Introduce qml_qobjects field to CxxQtBuilder struct
- Implement qml_qobject method for adding QML QObject files
- Process QML QObjects in build method, including moc generation
- Include generated metatypes.json for QML module support
- Update rerun-if-changed cargo instructions for added files
@akiselev akiselev changed the title Add support for C++ QML QObjects in CxxQtBuilder Add support for C++ QML Elements in CxxQtBuilder Dec 19, 2024
Copy link

codecov bot commented Dec 19, 2024

Codecov Report

All modified and coverable lines are covered by tests ✅

Project coverage is 100.00%. Comparing base (f5afefe) to head (82efc03).

Additional details and impacted files
@@            Coverage Diff            @@
##              main     #1146   +/-   ##
=========================================
  Coverage   100.00%   100.00%           
=========================================
  Files           71        71           
  Lines        11967     11967           
=========================================
  Hits         11967     11967           

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link
Contributor

@redstrate redstrate left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this deserves a mention in CHANGELOG.md, can you add it to the MR?

/// Specify a C++ header and source file containing a Q_OBJECT macro to run [moc](https://doc.qt.io/qt-6/moc.html) on.
/// Unlike [CxxQtBuilder::qobject_header], it includes the generated metatypes.json, so that C++ classes can be included
/// in QML modules.
pub fn qml_qobject(
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cpp_qobject ? I guess this could have other applications outside of QML

@LeonMatthesKDAB
Copy link
Collaborator

Hi @akiselev ,
as you mentioned, the best way to integrate this is indeed as a property on QmlModule.
The design of the QmlModule type is unfortunately a bit overly complicated, as it uses two template types, which we really don't want to expand.
My suggestion is to just hijack the existing A type, like we do for qrc_files.

I'm okay with the "list of tuples" approach you have in your initial comment.
We could even consider just a plain list of cpp_files, as we should be able to differentiate between .cpp and .h files by the extension.

Please note that for version 0.8 we are planning a larger refactor of the build system, which will likely end up supporting what you're currently asking anyway due to the nature of the proposed architecture.
See also: #1125
(basically: The qobject_header call should in future take care of registering automatically, if you're buidling a Qml module).

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants