diff --git a/.gitignore b/.gitignore
index 316d436..c600db7 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,11 +1,18 @@
*.iml
-.gradle
+**/.gradle/
/local.properties
/.idea
.DS_Store
-/build
+build/
/captures
.externalNativeBuild
-.cxx
+**/.cxx/
local.properties
jniLibs
+
+# C++ build artifacts
+**/prebuilt/
+
+# Swift build artifacts
+**/.build/
+**/Package.resolved
diff --git a/README.md b/README.md
index 795ccf3..c5e3acb 100644
--- a/README.md
+++ b/README.md
@@ -29,6 +29,16 @@ This approach is ideal for production Android applications where you want to wri
business logic, algorithms, or libraries in Swift, while maintaining a standard
Kotlin/Java frontend.
+## C++ Integration Example
+
+The **[hello-cpp-swift](hello-cpp-swift/)** example demonstrates how to integrate
+C++ libraries into Android applications through Swift. This example packages a C++
+library as an artifactbundle, imports it as a Swift binary target, and exposes it
+to Android using swift-java for automatic JNI generation.
+
+This pattern is useful when you have existing C++ code and want to leverage Swift's
+type safety and swift-java's automatic bridging to create Android-compatible libraries.
+
## Other Examples
For those who want to explore alternative integration patterns or understand
diff --git a/hello-cpp-swift/README.md b/hello-cpp-swift/README.md
new file mode 100644
index 0000000..4e5a0cb
--- /dev/null
+++ b/hello-cpp-swift/README.md
@@ -0,0 +1,89 @@
+# C++ to Swift to Android Integration
+
+This example demonstrates how to call C++ code from Android through Swift. The app uses a C++ library that provides basic calculator functions (add and multiply), wraps them in Swift, and calls them from an Android Kotlin app.
+
+## Overview
+
+The project is structured into three main parts:
+
+1. **`cpp-lib`**: A C++ library with basic calculator functions (`add` and `multiply`). This is built using CMake and packaged as an artifactbundle for consumption by Swift.
+
+2. **`swift-lib`**: A Swift package that wraps the C++ functions and exposes them to Android using [swift-java](https://github.com/swiftlang/swift-java). The Swift code calls the C++ functions and provides JNI bindings automatically.
+
+3. **`app`**: A standard Android application written in Kotlin that calls the Swift-wrapped C++ functions and displays the results.
+
+## Prerequisites
+
+Before you can build and run this project, you need to have the following installed:
+
+* **Basic setup**: Follow the Prerequisites and Setup instructions in [hello-swift-java/README.md](../hello-swift-java/README.md) to install JDK, Swiftly, Swift SDK for Android, and publish the swift-java packages locally.
+* **Android NDK**: Required to build the C++ library. Set the `ANDROID_NDK_HOME` environment variable to your NDK installation path.
+
+## Setup and Configuration
+
+### 1. Build the C++ Library
+
+Before building the Android app, you need to build the C++ library:
+
+```bash
+cd hello-cpp-swift/cpp-lib
+./build-android-static.sh
+```
+
+This will create the `prebuilt/HelloWorldCpp.artifactbundle` directory containing the compiled C++ static libraries for all Android architectures (arm64-v8a, armeabi-v7a, x86_64).
+
+## Running the example
+
+1. Open the `swift-android-examples` project in Android Studio.
+
+2. Select the `hello-cpp-swift:app` Gradle target.
+
+3. Run the app on an Android emulator or a physical device.
+
+4. The app will display the results of C++ calculations (10 + 5 and 10 × 5) called through Swift.
+
+## Building from command line
+
+```bash
+# From the project root directory
+./gradlew :hello-cpp-swift:app:assembleDebug
+
+# Install on device/emulator
+./gradlew :hello-cpp-swift:app:installDebug
+```
+
+## How it works
+
+1. **C++ Layer** (`cpp-lib/src/calculator.cpp`):
+ ```cpp
+ int add(int a, int b) {
+ return a + b;
+ }
+ ```
+
+2. **Swift Layer** (`swift-lib/Sources/HelloCppSwift/Calculator.swift`):
+ ```swift
+ import HelloWorldCpp
+
+ public func addNumbers(_ a: Int32, _ b: Int32) -> Int32 {
+ return add(a, b)
+ }
+ ```
+
+3. **Android/Kotlin Layer** (`app/MainActivity.kt`):
+ ```kotlin
+ val sum = com.example.hellocppswift.HelloCppSwift.addNumbers(10, 5)
+ ```
+
+The Swift code is automatically wrapped with JNI bindings using the `swift-java` JExtract plugin, making it callable from Kotlin/Java code.
+
+## Rebuilding the C++ Library
+
+If you make changes to the C++ code, you need to rebuild the artifactbundle:
+
+```bash
+cd hello-cpp-swift/cpp-lib
+./build-android-static.sh
+```
+
+Then rebuild the Android app to pick up the changes.
diff --git a/hello-cpp-swift/app/build.gradle.kts b/hello-cpp-swift/app/build.gradle.kts
new file mode 100644
index 0000000..ec92bcb
--- /dev/null
+++ b/hello-cpp-swift/app/build.gradle.kts
@@ -0,0 +1,47 @@
+plugins {
+ alias(libs.plugins.android.application)
+ alias(libs.plugins.kotlin.android)
+}
+
+android {
+ namespace = "com.example.hellocppswift"
+ compileSdk = 36
+
+ defaultConfig {
+ applicationId = "com.example.hellocppswift"
+ minSdk = 28
+ targetSdk = 36
+ versionCode = 1
+ versionName = "1.0"
+ }
+
+ buildTypes {
+ release {
+ isMinifyEnabled = false
+ proguardFiles(
+ getDefaultProguardFile("proguard-android-optimize.txt"),
+ "proguard-rules.pro"
+ )
+ }
+ }
+
+ compileOptions {
+ sourceCompatibility = JavaVersion.VERSION_11
+ targetCompatibility = JavaVersion.VERSION_11
+ }
+}
+
+kotlin {
+ compilerOptions {
+ jvmTarget.set(org.jetbrains.kotlin.gradle.dsl.JvmTarget.JVM_11)
+ }
+}
+
+dependencies {
+ implementation(libs.androidx.core.ktx)
+ implementation(libs.androidx.appcompat)
+ implementation(libs.material)
+ implementation(libs.androidx.constraintlayout)
+ implementation("org.swift.swiftkit:swiftkit-core:1.0-SNAPSHOT")
+ implementation(project(":hello-cpp-swift:swift-lib"))
+}
diff --git a/hello-cpp-swift/app/src/main/AndroidManifest.xml b/hello-cpp-swift/app/src/main/AndroidManifest.xml
new file mode 100644
index 0000000..7541bda
--- /dev/null
+++ b/hello-cpp-swift/app/src/main/AndroidManifest.xml
@@ -0,0 +1,19 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/hello-cpp-swift/app/src/main/java/com/example/hellocppswift/MainActivity.kt b/hello-cpp-swift/app/src/main/java/com/example/hellocppswift/MainActivity.kt
new file mode 100644
index 0000000..63d5356
--- /dev/null
+++ b/hello-cpp-swift/app/src/main/java/com/example/hellocppswift/MainActivity.kt
@@ -0,0 +1,32 @@
+package com.example.hellocppswift
+
+import android.os.Bundle
+import android.view.Gravity
+import android.widget.FrameLayout
+import android.widget.TextView
+import androidx.appcompat.app.AppCompatActivity
+
+class MainActivity : AppCompatActivity() {
+ override fun onCreate(savedInstanceState: Bundle?) {
+ super.onCreate(savedInstanceState)
+
+ val textView = TextView(this).apply {
+ textSize = 24f
+ textAlignment = TextView.TEXT_ALIGNMENT_CENTER
+ setPadding(32, 32, 32, 32)
+ gravity = Gravity.CENTER
+ }
+
+ val sum = com.example.hellocppswift.HelloCppSwift.addNumbers(10, 5)
+ val product = com.example.hellocppswift.HelloCppSwift.multiplyNumbers(10, 5)
+
+ textView.text = "C++ via Swift Calculations:\n\n10 + 5 = $sum\n10 × 5 = $product"
+
+ val container = FrameLayout(this).apply {
+ setPadding(0, 200, 0, 0)
+ addView(textView)
+ }
+
+ setContentView(container)
+ }
+}
diff --git a/hello-cpp-swift/app/src/main/res/values/strings.xml b/hello-cpp-swift/app/src/main/res/values/strings.xml
new file mode 100644
index 0000000..0aa30d0
--- /dev/null
+++ b/hello-cpp-swift/app/src/main/res/values/strings.xml
@@ -0,0 +1,4 @@
+
+
+ Hello C++ Swift
+
diff --git a/hello-cpp-swift/cpp-lib/CMakeLists.txt b/hello-cpp-swift/cpp-lib/CMakeLists.txt
new file mode 100644
index 0000000..9eb9864
--- /dev/null
+++ b/hello-cpp-swift/cpp-lib/CMakeLists.txt
@@ -0,0 +1,21 @@
+cmake_minimum_required(VERSION 3.18)
+project(HelloWorldCpp VERSION 1.0.0 LANGUAGES CXX)
+
+set(CMAKE_CXX_STANDARD 17)
+set(CMAKE_CXX_STANDARD_REQUIRED ON)
+
+set(SOURCES
+ src/calculator.cpp
+)
+
+set(HEADERS
+ include/calculator.h
+)
+
+add_library(${PROJECT_NAME} STATIC ${SOURCES} ${HEADERS})
+
+target_include_directories(${PROJECT_NAME}
+ PUBLIC
+ $
+ $
+)
diff --git a/hello-cpp-swift/cpp-lib/build-android-static.sh b/hello-cpp-swift/cpp-lib/build-android-static.sh
new file mode 100755
index 0000000..cb75c4a
--- /dev/null
+++ b/hello-cpp-swift/cpp-lib/build-android-static.sh
@@ -0,0 +1,115 @@
+#!/bin/bash
+
+set -e
+
+SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
+cd "$SCRIPT_DIR"
+
+if [ -z "$ANDROID_NDK_HOME" ]; then
+ echo "Error: ANDROID_NDK_HOME environment variable is not set"
+ echo "Please set it to your Android NDK installation path"
+ exit 1
+fi
+
+if [ ! -d "$ANDROID_NDK_HOME" ]; then
+ echo "Error: ANDROID_NDK_HOME points to non-existent directory: $ANDROID_NDK_HOME"
+ exit 1
+fi
+
+ANDROID_TOOLCHAIN="$ANDROID_NDK_HOME/build/cmake/android.toolchain.cmake"
+
+if [ ! -f "$ANDROID_TOOLCHAIN" ]; then
+ echo "Error: Android toolchain file not found at: $ANDROID_TOOLCHAIN"
+ exit 1
+fi
+
+ANDROID_API=28
+
+ABIS=(
+ "arm64-v8a:android-aarch64"
+ "armeabi-v7a:android-armv7"
+ "x86_64:android-x86_64"
+)
+
+echo "Building HelloWorldCpp static libraries for Android..."
+
+for ABI_ENTRY in "${ABIS[@]}"; do
+ ABI="${ABI_ENTRY%%:*}"
+ echo "Building for $ABI..."
+
+ BUILD_DIR="build/android-static/$ABI"
+ mkdir -p "$BUILD_DIR"
+
+ cmake -S . -B "$BUILD_DIR" \
+ -DCMAKE_TOOLCHAIN_FILE="$ANDROID_TOOLCHAIN" \
+ -DANDROID_ABI="$ABI" \
+ -DANDROID_PLATFORM="android-$ANDROID_API" \
+ -DCMAKE_BUILD_TYPE=Release \
+ -DCMAKE_CXX_STANDARD=17
+
+ cmake --build "$BUILD_DIR" --config Release
+
+ echo "✓ Built $ABI"
+done
+
+echo ""
+echo "Creating artifactbundle..."
+
+ARTIFACTBUNDLE_DIR="prebuilt/HelloWorldCpp.artifactbundle"
+
+for ABI_ENTRY in "${ABIS[@]}"; do
+ ABI="${ABI_ENTRY%%:*}"
+ BUNDLE_DIR="${ABI_ENTRY##*:}"
+
+ mkdir -p "$ARTIFACTBUNDLE_DIR/$BUNDLE_DIR/Headers"
+
+ cp "build/android-static/$ABI/libHelloWorldCpp.a" "$ARTIFACTBUNDLE_DIR/$BUNDLE_DIR/"
+
+ cp include/calculator.h "$ARTIFACTBUNDLE_DIR/$BUNDLE_DIR/Headers/"
+ cp include/module.modulemap "$ARTIFACTBUNDLE_DIR/$BUNDLE_DIR/Headers/"
+
+ echo "✓ Created artifactbundle for $BUNDLE_DIR"
+done
+
+cat > "$ARTIFACTBUNDLE_DIR/info.json" << 'EOF'
+{
+ "schemaVersion": "1.0",
+ "artifacts": {
+ "HelloWorldCpp": {
+ "version": "1.0.0",
+ "type": "staticLibrary",
+ "variants": [
+ {
+ "path": "android-aarch64/libHelloWorldCpp.a",
+ "supportedTriples": ["aarch64-unknown-linux-android"],
+ "staticLibraryMetadata": {
+ "headerPaths": ["android-aarch64/Headers"],
+ "moduleMapPath": "android-aarch64/Headers/module.modulemap"
+ }
+ },
+ {
+ "path": "android-armv7/libHelloWorldCpp.a",
+ "supportedTriples": ["armv7-unknown-linux-android"],
+ "staticLibraryMetadata": {
+ "headerPaths": ["android-armv7/Headers"],
+ "moduleMapPath": "android-armv7/Headers/module.modulemap"
+ }
+ },
+ {
+ "path": "android-x86_64/libHelloWorldCpp.a",
+ "supportedTriples": ["x86_64-unknown-linux-android"],
+ "staticLibraryMetadata": {
+ "headerPaths": ["android-x86_64/Headers"],
+ "moduleMapPath": "android-x86_64/Headers/module.modulemap"
+ }
+ }
+ ]
+ }
+ }
+}
+EOF
+
+echo "✓ Generated info.json"
+echo ""
+echo "All Android static libraries built successfully!"
+echo "Artifactbundle created at: $ARTIFACTBUNDLE_DIR"
diff --git a/hello-cpp-swift/cpp-lib/include/calculator.h b/hello-cpp-swift/cpp-lib/include/calculator.h
new file mode 100644
index 0000000..c84b9ae
--- /dev/null
+++ b/hello-cpp-swift/cpp-lib/include/calculator.h
@@ -0,0 +1,15 @@
+#ifndef CALCULATOR_H
+#define CALCULATOR_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int add(int a, int b);
+int multiply(int a, int b);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/hello-cpp-swift/cpp-lib/include/module.modulemap b/hello-cpp-swift/cpp-lib/include/module.modulemap
new file mode 100644
index 0000000..b79c670
--- /dev/null
+++ b/hello-cpp-swift/cpp-lib/include/module.modulemap
@@ -0,0 +1,4 @@
+module HelloWorldCpp {
+ header "calculator.h"
+ export *
+}
diff --git a/hello-cpp-swift/cpp-lib/src/calculator.cpp b/hello-cpp-swift/cpp-lib/src/calculator.cpp
new file mode 100644
index 0000000..ec000c3
--- /dev/null
+++ b/hello-cpp-swift/cpp-lib/src/calculator.cpp
@@ -0,0 +1,9 @@
+#include "calculator.h"
+
+int add(int a, int b) {
+ return a + b;
+}
+
+int multiply(int a, int b) {
+ return a * b;
+}
diff --git a/hello-cpp-swift/swift-lib/Package.swift b/hello-cpp-swift/swift-lib/Package.swift
new file mode 100644
index 0000000..384d60a
--- /dev/null
+++ b/hello-cpp-swift/swift-lib/Package.swift
@@ -0,0 +1,70 @@
+// swift-tools-version: 6.2
+
+import CompilerPluginSupport
+import PackageDescription
+
+import class Foundation.FileManager
+import class Foundation.ProcessInfo
+
+func findJavaHome() -> String {
+ if let home = ProcessInfo.processInfo.environment["JAVA_HOME"] {
+ return home
+ }
+
+ let path = "\(FileManager.default.homeDirectoryForCurrentUser.path()).java_home"
+ if let home = try? String(contentsOfFile: path, encoding: .utf8) {
+ if let lastChar = home.last, lastChar.isNewline {
+ return String(home.dropLast())
+ }
+
+ return home
+ }
+
+ fatalError("Please set the JAVA_HOME environment variable to point to where Java is installed.")
+}
+let javaHome = findJavaHome()
+
+let javaIncludePath = "\(javaHome)/include"
+#if os(Linux)
+ let javaPlatformIncludePath = "\(javaIncludePath)/linux"
+#elseif os(macOS)
+ let javaPlatformIncludePath = "\(javaIncludePath)/darwin"
+#else
+ #error("Currently only macOS and Linux platforms are supported, this may change in the future.")
+#endif
+
+let package = Package(
+ name: "HelloCppSwift",
+ platforms: [.macOS(.v15)],
+ products: [
+ .library(
+ name: "HelloCppSwift",
+ type: .dynamic,
+ targets: ["HelloCppSwift"])
+ ],
+ dependencies: [
+ .package(url: "https://github.com/swiftlang/swift-java", branch: "main"),
+ ],
+ targets: [
+ .binaryTarget(
+ name: "HelloWorldCpp",
+ path: "../cpp-lib/prebuilt/HelloWorldCpp.artifactbundle"
+ ),
+ .target(
+ name: "HelloCppSwift",
+ dependencies: [
+ .target(name: "HelloWorldCpp"),
+ .product(name: "SwiftJava", package: "swift-java"),
+ .product(name: "CSwiftJavaJNI", package: "swift-java"),
+ .product(name: "SwiftJavaRuntimeSupport", package: "swift-java"),
+ ],
+ swiftSettings: [
+ .swiftLanguageMode(.v5),
+ .unsafeFlags(["-I\(javaIncludePath)", "-I\(javaPlatformIncludePath)"], .when(platforms: [.macOS, .linux, .windows]))
+ ],
+ plugins: [
+ .plugin(name: "JExtractSwiftPlugin", package: "swift-java")
+ ]
+ ),
+ ]
+)
diff --git a/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/Calculator.swift b/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/Calculator.swift
new file mode 100644
index 0000000..494ad99
--- /dev/null
+++ b/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/Calculator.swift
@@ -0,0 +1,14 @@
+#if canImport(FoundationEssentials)
+import FoundationEssentials
+#else
+import Foundation
+#endif
+import HelloWorldCpp
+
+public func addNumbers(_ a: Int32, _ b: Int32) -> Int32 {
+ return add(a, b)
+}
+
+public func multiplyNumbers(_ a: Int32, _ b: Int32) -> Int32 {
+ return multiply(a, b)
+}
diff --git a/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/swift-java.config b/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/swift-java.config
new file mode 100644
index 0000000..6068c54
--- /dev/null
+++ b/hello-cpp-swift/swift-lib/Sources/HelloCppSwift/swift-java.config
@@ -0,0 +1,4 @@
+{
+ "javaPackage": "com.example.hellocppswift",
+ "mode": "jni"
+}
diff --git a/hello-cpp-swift/swift-lib/build.gradle b/hello-cpp-swift/swift-lib/build.gradle
new file mode 100644
index 0000000..673a061
--- /dev/null
+++ b/hello-cpp-swift/swift-lib/build.gradle
@@ -0,0 +1,185 @@
+import java.nio.file.*
+
+plugins {
+ alias(libs.plugins.android.library)
+}
+
+android {
+ namespace "com.example.hellocppswift.lib"
+ compileSdkVersion 34
+
+ defaultConfig {
+ minSdkVersion 28
+ }
+
+ compileOptions {
+ sourceCompatibility = JavaVersion.VERSION_11
+ targetCompatibility = JavaVersion.VERSION_11
+ }
+}
+
+dependencies {
+ implementation('org.swift.swiftkit:swiftkit-core:1.0-SNAPSHOT')
+}
+
+def getSwiftlyPath() {
+ def fromConfig = project.findProperty("swiftly.path") ?: System.getenv("SWIFTLY_PATH")
+ if (fromConfig) {
+ return file(fromConfig)
+ }
+
+ def homeDir = System.getProperty("user.home")
+ def possiblePaths = [
+ "$homeDir/.swiftly/bin/swiftly",
+ "$homeDir/.local/share/swiftly/bin/swiftly",
+ "$homeDir/.local/bin/swiftly",
+ "/usr/local/bin/swiftly",
+ "/opt/homebrew/bin/swiftly",
+ "/root/.local/share/swiftly/bin/swiftly"
+ ]
+
+ for (path in possiblePaths) {
+ if (file(path).exists()) {
+ return path
+ }
+ }
+
+ throw new GradleException("Swift SDK path not found. Please set swiftly.path in the gradle.properties file or set SWIFTLY_PATH environment variable.")
+}
+
+def getSwiftSDKPath() {
+ def fromConfig = project.findProperty("swift.sdk.path") ?: System.getenv("SWIFT_SDK_PATH")
+ if (fromConfig) {
+ return file(fromConfig)
+ }
+
+ def homeDir = System.getProperty("user.home")
+ def possiblePaths = [
+ "${homeDir}/Library/org.swift.swiftpm/swift-sdks/",
+ "${homeDir}/.config/swiftpm/swift-sdks/",
+ "${homeDir}/.swiftpm/swift-sdks/",
+ "/root/.swiftpm/swift-sdks/"
+ ]
+
+ for (path in possiblePaths) {
+ if (file(path).exists()) {
+ return file(path)
+ }
+ }
+
+ throw new GradleException("Swift SDK path not found. Please set swift.sdk.path in the gradle.properties file or set SWIFT_SDK_PATH environment variable.")
+}
+
+def swiftRuntimeLibs = [
+ "swiftCore",
+ "swift_Concurrency",
+ "swift_StringProcessing",
+ "swift_RegexParser",
+ "swift_Builtin_float",
+ "swift_math",
+ "swiftAndroid",
+ "dispatch",
+ "BlocksRuntime",
+ "swiftSwiftOnoneSupport",
+ "swiftDispatch",
+ "Foundation",
+ "FoundationEssentials",
+ "FoundationInternationalization",
+ "_FoundationICU",
+ "swiftSynchronization"
+]
+
+def sdkName = "swift-DEVELOPMENT-SNAPSHOT-2025-10-16-a-android-0.1.artifactbundle"
+def swiftVersion = "main-snapshot-2025-10-16"
+def minSdk = android.defaultConfig.minSdkVersion.apiLevel
+
+def abis = [
+ "arm64-v8a" : [triple: "aarch64-unknown-linux-android${minSdk}", androidSdkLibDirectory: "swift-aarch64", ndkDirectory: "aarch64-linux-android"],
+ "armeabi-v7a" : [triple: "armv7-unknown-linux-android${minSdk}", androidSdkLibDirectory: "swift-armv7", ndkDirectory: "arm-linux-android"],
+ "x86_64" : [triple: "x86_64-unknown-linux-android${minSdk}", androidSdkLibDirectory: "swift-x86_64", ndkDirectory: "x86_64-linux-android"]
+]
+
+def generatedJniLibsDir = layout.buildDirectory.dir("generated/jniLibs")
+def swiftSdkPath = "${getSwiftSDKPath().absolutePath}/${sdkName}"
+
+def buildSwiftAll = tasks.register("buildSwiftAll") {
+ group = "build"
+ description = "Builds the Swift code for all Android ABIs."
+
+ inputs.file(new File(projectDir, "Package.swift"))
+ inputs.dir(new File(layout.projectDirectory.asFile, "Sources/HelloCppSwift".toString()))
+
+ outputs.dir(layout.buildDirectory.dir("../.build/plugins/outputs/${layout.projectDirectory.asFile.getName().toLowerCase()}"))
+
+ File baseSwiftPluginOutputsDir = layout.buildDirectory.dir("../.build/plugins/outputs/").get().asFile
+ if (!baseSwiftPluginOutputsDir.exists()) {
+ baseSwiftPluginOutputsDir.mkdirs()
+ }
+ Files.walk(layout.buildDirectory.dir("../.build/plugins/outputs/").get().asFile.toPath()).each {
+ if (it.endsWith("JExtractSwiftPlugin/src/generated/java")) {
+ outputs.dir(it)
+ }
+ }
+}
+
+abis.each { abi, info ->
+ def task = tasks.register("buildSwift${abi.capitalize()}", Exec) {
+ group = "build"
+ description = "Builds the Swift code for the ${abi} ABI."
+
+ doFirst {
+ println("Building Swift for ${abi} (${info.triple})...")
+ }
+
+ outputs.dir(layout.projectDirectory.dir(".build/${info.triple}/debug"))
+
+ workingDir = layout.projectDirectory
+ executable(getSwiftlyPath())
+ args("run", "swift", "build", "+${swiftVersion}", "--swift-sdk", info.triple)
+ }
+
+ buildSwiftAll.configure { dependsOn(task) }
+}
+
+def copyJniLibs = tasks.register("copyJniLibs", Copy) {
+ dependsOn(buildSwiftAll)
+
+ abis.each { abi, info ->
+ from(layout.projectDirectory.dir(".build/${info.triple}/debug")) {
+ include("*.so")
+ into(abi)
+ }
+
+ from(file("${swiftSdkPath}/swift-android/ndk-sysroot/usr/lib/${info.ndkDirectory}/libc++_shared.so")) {
+ into(abi)
+ }
+
+ doFirst {
+ println("Copying Swift runtime libraries for ${abi}...")
+ }
+
+ from(swiftRuntimeLibs.collect { libName ->
+ "${swiftSdkPath}/swift-android/swift-resources/usr/lib/${info.androidSdkLibDirectory}/android/lib${libName}.so"
+ }) {
+ into(abi)
+ }
+ }
+
+ into(generatedJniLibsDir)
+}
+
+android {
+ sourceSets {
+ main {
+ java {
+ srcDir(buildSwiftAll)
+ }
+
+ jniLibs {
+ srcDir(generatedJniLibsDir)
+ }
+ }
+ }
+}
+
+preBuild.dependsOn(copyJniLibs)
diff --git a/settings.gradle.kts b/settings.gradle.kts
index 0be2778..0ded51f 100644
--- a/settings.gradle.kts
+++ b/settings.gradle.kts
@@ -36,3 +36,7 @@ include(":hello-swift-raw-jni-library")
// native-only examples
include(":native-activity")
+
+// cpp-swift example
+include(":hello-cpp-swift:swift-lib")
+include(":hello-cpp-swift:app")