aboutsummaryrefslogtreecommitdiffstats
path: root/tests/manual/helloswift
diff options
context:
space:
mode:
Diffstat (limited to 'tests/manual/helloswift')
-rw-r--r--tests/manual/helloswift/CMakeLists.txt97
-rw-r--r--tests/manual/helloswift/greeter.h43
-rw-r--r--tests/manual/helloswift/hello.swift21
-rw-r--r--tests/manual/helloswift/main.cpp34
-rw-r--r--tests/manual/helloswift/main.qml33
-rw-r--r--tests/manual/helloswift/module.modulemap3
6 files changed, 231 insertions, 0 deletions
diff --git a/tests/manual/helloswift/CMakeLists.txt b/tests/manual/helloswift/CMakeLists.txt
new file mode 100644
index 0000000000..2549577172
--- /dev/null
+++ b/tests/manual/helloswift/CMakeLists.txt
@@ -0,0 +1,97 @@
+# Copyright (C) 2023 The Qt Company Ltd.
+# SPDX-License-Identifier: BSD-3-Clause
+
+cmake_minimum_required(VERSION 3.26)
+project(helloswift LANGUAGES CXX Swift)
+
+# --------------- Qt ----------------
+
+find_package(Qt6 REQUIRED COMPONENTS Core Quick)
+
+qt_standard_project_setup(REQUIRES 6.5)
+
+if(NOT DEFINED INSTALL_EXAMPLESDIR)
+ set(INSTALL_EXAMPLESDIR "examples")
+endif()
+
+set(INSTALL_EXAMPLEDIR "${INSTALL_EXAMPLESDIR}/quick/helloswift")
+
+qt_add_executable(helloswift WIN32 MACOSX_BUNDLE
+ main.cpp
+)
+
+target_include_directories(helloswift PRIVATE
+ ${CMAKE_CURRENT_BINARY_DIR}
+)
+target_link_libraries(helloswift PRIVATE
+ Qt6::Quick
+)
+
+qt_add_qml_module(helloswift
+ URI helloswift
+ QML_FILES
+ "main.qml"
+)
+
+install(TARGETS helloswift
+ RUNTIME DESTINATION "${INSTALL_EXAMPLEDIR}"
+ BUNDLE DESTINATION "${INSTALL_EXAMPLEDIR}"
+ LIBRARY DESTINATION "${INSTALL_EXAMPLEDIR}"
+)
+
+# ------------- Swift ---------------
+
+# Verify that we have a new enough compiler
+if("${CMAKE_Swift_COMPILER_VERSION}" VERSION_LESS 5.9)
+ message(FATAL_ERROR "Swift 5.9 required for C++ interoperability")
+endif()
+
+set(CMAKE_OSX_DEPLOYMENT_TARGET 13.0)
+set(CMAKE_CXX_STANDARD 17)
+
+get_target_property(QT_CORE_INCLUDES Qt6::Core INTERFACE_INCLUDE_DIRECTORIES)
+
+# Swift library
+set(SWIFT_SOURCES "${CMAKE_CURRENT_SOURCE_DIR}/hello.swift")
+add_library(hello-swift STATIC ${SWIFT_SOURCES})
+set_target_properties(hello-swift PROPERTIES Swift_MODULE_NAME "HelloSwift")
+target_include_directories(hello-swift PUBLIC
+ "${CMAKE_CURRENT_SOURCE_DIR}"
+ "${QT_CORE_INCLUDES}"
+)
+target_compile_options(hello-swift PUBLIC
+ $<$<COMPILE_LANGUAGE:Swift>:-cxx-interoperability-mode=default>
+ $<$<COMPILE_LANGUAGE:Swift>:-Xcc -std=c++17>)
+
+# Swift to C++ bridging header
+set(SWIFT_BRIDGING_HEADER "${CMAKE_CURRENT_BINARY_DIR}/hello-swift.h")
+list(TRANSFORM QT_CORE_INCLUDES PREPEND "-I")
+add_custom_command(
+ COMMAND
+ ${CMAKE_Swift_COMPILER} -frontend -typecheck
+ ${SWIFT_SOURCES}
+ -I ${CMAKE_CURRENT_SOURCE_DIR}
+ ${QT_CORE_INCLUDES}
+ -sdk ${CMAKE_OSX_SYSROOT}
+ -module-name HelloSwift
+ -cxx-interoperability-mode=default
+ -Xcc -std=c++17
+ -emit-clang-header-path "${SWIFT_BRIDGING_HEADER}"
+ OUTPUT
+ "${SWIFT_BRIDGING_HEADER}"
+ DEPENDS
+ ${SWIFT_SOURCES}
+ )
+
+add_custom_target(swift-bridging-header
+ DEPENDS
+ "${SWIFT_BRIDGING_HEADER}"
+)
+
+add_dependencies(hello-swift swift-bridging-header)
+
+# Tie everything together
+
+target_link_libraries(helloswift PRIVATE
+ hello-swift
+)
diff --git a/tests/manual/helloswift/greeter.h b/tests/manual/helloswift/greeter.h
new file mode 100644
index 0000000000..722380051c
--- /dev/null
+++ b/tests/manual/helloswift/greeter.h
@@ -0,0 +1,43 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
+
+#ifndef GREETER_H
+#define GREETER_H
+
+#include <QtCore/qobject.h>
+#include <string>
+#include <swift/bridging>
+
+namespace HelloSwift {
+class SwiftGreeter;
+class Test;
+}
+
+template <typename SwiftType, typename QtType>
+class SwiftWrapper
+{
+public:
+ template <typename ...Args>
+ SwiftWrapper(Args && ...args)
+ : swiftImpl(new SwiftType(
+ SwiftType::init(
+ static_cast<QtType*>(this),
+ std::forward<Args>(args)...)))
+ {
+ }
+
+protected:
+ std::unique_ptr<SwiftType> swiftImpl;
+};
+
+class Greeter : public QObject, public SwiftWrapper<HelloSwift::SwiftGreeter, Greeter>
+{
+ Q_OBJECT
+public:
+ Q_PRIVATE_PROPERTY(swiftImpl, std::string greeting READ getGreeting NOTIFY greetingChanged)
+ Q_PRIVATE_SLOT(swiftImpl, void updateGreeting())
+ Q_SIGNAL void greetingChanged();
+} SWIFT_UNSAFE_REFERENCE;
+
+
+#endif // GREETER_H
diff --git a/tests/manual/helloswift/hello.swift b/tests/manual/helloswift/hello.swift
new file mode 100644
index 0000000000..99043c328d
--- /dev/null
+++ b/tests/manual/helloswift/hello.swift
@@ -0,0 +1,21 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
+
+import Greeter
+
+public class SwiftGreeter {
+ private let qtImpl: Greeter
+
+ public init(greeter: Greeter ) {
+ self.qtImpl = greeter;
+ }
+
+ public var greeting: String {
+ let greetings = ["Hello", "Howdy", "Hey", "Hola", "Heisan"]
+ return greetings[Int.random(in: 0..<greetings.count)]
+ }
+
+ public func updateGreeting() {
+ qtImpl.greetingChanged();
+ }
+}
diff --git a/tests/manual/helloswift/main.cpp b/tests/manual/helloswift/main.cpp
new file mode 100644
index 0000000000..264c4cb136
--- /dev/null
+++ b/tests/manual/helloswift/main.cpp
@@ -0,0 +1,34 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
+
+#include <QGuiApplication>
+#include <QStringList>
+
+#include <qqmlengine.h>
+#include <qqmlcontext.h>
+#include <qqml.h>
+#include <QtQuick/qquickitem.h>
+#include <QtQuick/qquickview.h>
+
+#include "greeter.h"
+#include "hello-swift.h"
+
+int main(int argc, char ** argv)
+{
+ QGuiApplication app(argc, argv);
+
+ QMetaType::registerConverter<std::string, QString>(&QString::fromStdString);
+
+ Greeter greeter;
+
+ QQuickView view;
+ view.setResizeMode(QQuickView::SizeRootObjectToView);
+ view.engine()->rootContext()->setContextProperty("greeter", &greeter);
+
+ view.setSource(QUrl("qrc:/qt/qml/helloswift/main.qml"));
+ view.show();
+
+ return app.exec();
+}
+
+#include "moc_greeter.cpp"
diff --git a/tests/manual/helloswift/main.qml b/tests/manual/helloswift/main.qml
new file mode 100644
index 0000000000..3992cde4e4
--- /dev/null
+++ b/tests/manual/helloswift/main.qml
@@ -0,0 +1,33 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
+
+import QtQuick
+
+Rectangle {
+ id: rectangle
+ width: 500; height: 500
+ color: "lightgray"
+
+ Text {
+ id: text;
+ anchors.centerIn: parent
+ anchors.verticalCenterOffset: -50
+ font.pointSize: 40
+ text: greeter.greeting
+ }
+
+ Image {
+ anchors.top: text.bottom
+ anchors.topMargin: 5
+ anchors.horizontalCenter: parent.horizontalCenter
+ anchors.horizontalCenterOffset: -8
+ source: "https://www.swift.org/assets/images/swift.svg"
+ fillMode: Image.PreserveAspectFit
+ sourceSize.width: 150
+
+ MouseArea {
+ anchors.fill: parent
+ onClicked: greeter.updateGreeting();
+ }
+ }
+}
diff --git a/tests/manual/helloswift/module.modulemap b/tests/manual/helloswift/module.modulemap
new file mode 100644
index 0000000000..4cc079abea
--- /dev/null
+++ b/tests/manual/helloswift/module.modulemap
@@ -0,0 +1,3 @@
+module Greeter {
+ header "greeter.h"
+}