SwiftUI中调用UnityAds show方法编译报错,寻求技术解决方案
SwiftUI环境下UnityAds广告展示问题解决
错误原因分析
你遇到的Cannot convert value of type 'UIViewController.Type' to expected argument type 'UIViewController'编译错误,核心原因是UnityAds.show(_:placementId:showDelegate:)方法的第一个参数需要UIViewController的实例,但你传入的是UIViewController类本身(UIViewController.Type),完全不符合参数要求。
SwiftUI环境适配方案
纯SwiftUI项目无默认UIViewController实例,需通过以下方式获取有效顶层视图控制器,同时修正UnityAds的初始化与调用逻辑:
1. 封装顶层VC获取工具
先实现一个全局工具方法,用来获取当前活跃的顶层UIViewController:
import UIKit extension UIApplication { static func getTopViewController() -> UIViewController? { guard let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene, let window = windowScene.windows.first else { return nil } var topViewController = window.rootViewController while let presentedViewController = topViewController?.presentedViewController { topViewController = presentedViewController } return topViewController } }
2. 修正UnityAds初始化与广告逻辑
不要在全局直接调用UnityAds.initialize,应放在App入口初始化时执行,同时修正广告展示方法:
import SwiftUI import UnityAds @main struct YourAppName: App { init() { // 初始化UnityAds,放在App初始化阶段执行更合理 UnityAds.initialize("307659", testMode: true) } var body: some Scene { WindowGroup { ContentView() } } } struct ContentView: View { var body: some View { VStack(spacing: 20) { Button("加载插屏广告") { loadInterstitial_UnityAds() } Button("展示广告") { showAds_Unity() } } } func loadInterstitial_UnityAds(){ guard UnityAds.isInitialized() else { print("UnityAds未初始化") return } // 新增加载回调,便于排查加载状态 UnityAds.load("video") { state, error in if let error = error { print("广告加载失败: \(error.localizedDescription)") } else if state == .ready { print("广告加载完成") } } } func showAds_Unity(){ guard let topVC = UIApplication.getTopViewController() else { print("无法获取顶层视图控制器") return } // 注意:placementId需与Unity后台配置的广告位ID一致,你之前传的307659是AppID,不是广告位ID UnityAds.show(topVC, placementId: "video", showDelegate: self) } } // 可选:实现UnityAdsShowDelegate处理广告回调,便于业务逻辑扩展 extension ContentView: UnityAdsShowDelegate { func unityAdsShowComplete(_ placementId: String, with finishState: UnityAdsShowCompletionState) { print("广告展示完成: \(finishState.rawValue)") } func unityAdsShowFailed(_ placementId: String, with error: UnityAdsShowError, with message: String) { print("广告展示失败: \(message)") } func unityAdsShowStart(_ placementId: String) { print("广告开始展示") } func unityAdsShowClick(_ placementId: String) { print("广告被点击") } }
关键注意事项
- 区分AppID与PlacementId:你之前在展示方法中传入的
307659是UnityAds的AppID,而非广告位ID(placementId),需替换为Unity后台创建的对应广告位ID(比如你加载时用的video)。 - 初始化时机:避免在全局作用域直接初始化UnityAds,放在App结构体的
init方法中更符合SwiftUI的生命周期规范。 - 顶层VC可靠性:通过
UIApplication扩展获取顶层VC是SwiftUI环境下获取UIViewController实例的通用方案,确保广告能正确展示在当前界面之上。
内容的提问来源于stack exchange,提问作者Franklyn Oreben
相关产品推荐
相关产品推荐

