Skip to content

Commit

Permalink
cxx-qt-lib: Add binding for QQmlApplicationEngine::singletonInstance
Browse files Browse the repository at this point in the history
This allows accessing QObject singleton instances registered in the QML
engine (using #[qml_singleton]) from the Rust side.
  • Loading branch information
redstrate committed Dec 10, 2024
1 parent f5afefe commit 02a5168
Show file tree
Hide file tree
Showing 4 changed files with 30 additions and 1 deletion.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- QObject subclasses can now inherit from other CXX-Qt generated QObject classes
- `BUILD_WASM` CMake option to support WebAssembly builds and a book page for building for WASM
- Add support for cxx_name and rust_name on qproperty attributes which applies to the QProperty generated as well as functions
- Add binding for `singletonInstance` of `QQmlApplicationEngine`, allowing access to singleton instances registered in the QML engine.

### Changed

Expand Down
3 changes: 3 additions & 0 deletions crates/cxx-qt-lib/include/qml/qqmlapplicationengine.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,9 @@ qqmlapplicationengineNew();
QQmlEngine&
qqmlapplicationengineAsQQmlEngine(QQmlApplicationEngine&);

void*
qqmlapplicationengineSingletonInstance(QQmlApplicationEngine& engine, QAnyStringView uri, QAnyStringView typeName);

}
}

Expand Down
6 changes: 6 additions & 0 deletions crates/cxx-qt-lib/src/qml/qqmlapplicationengine.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,5 +22,11 @@ qqmlapplicationengineAsQQmlEngine(QQmlApplicationEngine& engine)
return static_cast<QQmlEngine&>(engine);
}

void*
qqmlapplicationengineSingletonInstance(QQmlApplicationEngine& engine, QAnyStringView uri, QAnyStringView typeName)
{
return reinterpret_cast<void*>(engine.singletonInstance<QObject*>(uri, typeName));
}

}
}
21 changes: 20 additions & 1 deletion crates/cxx-qt-lib/src/qml/qqmlapplicationengine.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ mod ffi {
type QStringList = crate::QStringList;
include!("cxx-qt-lib/qurl.h");
type QUrl = crate::QUrl;
include!("cxx-qt-lib/qanystringview.h");
type QAnyStringView<'a> = crate::QAnyStringView<'a>;

include!("cxx-qt-lib/qqmlapplicationengine.h");
type QQmlApplicationEngine;
Expand Down Expand Up @@ -68,6 +70,9 @@ mod ffi {

#[namespace = "rust::cxxqtlib1"]
unsafe extern "C++" {
include!("cxx-qt-lib/common.h");
type c_void = crate::c_void;

#[doc(hidden)]
#[rust_name = "qqmlapplicationengine_new"]
fn qqmlapplicationengineNew() -> UniquePtr<QQmlApplicationEngine>;
Expand All @@ -77,6 +82,10 @@ mod ffi {
fn qqmlapplicationengineAsQQmlEngine(
ptr: Pin<&mut QQmlApplicationEngine>,
) -> Pin<&mut QQmlEngine>;

#[doc(hidden)]
#[rust_name = "qqmlapplicationengine_singleton_instance"]
fn qqmlapplicationengineSingletonInstance(ptr: Pin<&mut QQmlApplicationEngine>, uri: QAnyStringView, typeName: QAnyStringView) -> *mut c_void;
}

// QQmlApplicationEngine is not a trivial to CXX and is not relocatable in Qt
Expand All @@ -86,7 +95,7 @@ mod ffi {
impl UniquePtr<QQmlApplicationEngine> {}
}

use crate::QQmlEngine;
use crate::{c_void, QAnyStringView, QQmlEngine};
use core::pin::Pin;

pub use ffi::QQmlApplicationEngine;
Expand All @@ -101,4 +110,14 @@ impl QQmlApplicationEngine {
pub fn new() -> cxx::UniquePtr<Self> {
ffi::qqmlapplicationengine_new()
}

pub fn singleton_instance<T>(self: Pin<&mut Self>, uri: QAnyStringView, type_name: QAnyStringView) -> Option<&mut T> {
unsafe {
let ptr = ffi::qqmlapplicationengine_singleton_instance(self, uri, type_name);
if ptr.is_null() {
return None;
}
Some(&mut *(ptr as *mut T))
}
}
}

0 comments on commit 02a5168

Please sign in to comment.