You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Xamarin iOS应用中OneSignal NotificationOpened事件失效问题排查

解决Xamarin iOS集成OneSignal推送点击跳转指定ViewController无效问题

我之前做Xamarin iOS项目时也碰到过一模一样的OneSignal推送跳转问题,结合你给出的代码和排查结果,给你理清楚完整的解决逻辑:

问题复盘

你期望用户点击OneSignal推送时直接打开NotificationsViewController,但实际打开的是应用后台时处于活跃的页面,核心问题是HandleNotificationOpened回调函数完全没生效,最后排查出是重复初始化OneSignal导致的。

问题根源

OneSignal在iOS环境中如果被多次调用StartInit+EndInit,会覆盖第一次初始化时绑定的回调配置,包括HandleNotificationOpened的事件监听,这就导致推送点击事件无法触发你自定义的跳转逻辑,只能走系统默认的恢复后台活跃页面的行为。

修正后的完整代码

删除所有重复的OneSignal初始化代码,确保全局只有一次初始化流程,同时优化跳转逻辑(避免重复实例化导航控制器,复用当前窗口的导航栈更合理):

public class AppDelegate : UIApplicationDelegate 
{ 
    public static UIStoryboard Storyboard = UIStoryboard.FromName("Main", null); 
    public override UIWindow Window { get; set; } 
    public override bool FinishedLaunching (UIApplication application, NSDictionary launchOptions) 
    { 
        // 这里是OneSignal唯一的初始化入口,确保项目其他地方没有重复调用StartInit/EndInit
        OneSignal.Current.StartInit("mykey") 
            .InFocusDisplaying(OSInFocusDisplayOption.None) 
            .HandleNotificationOpened(HandleNotificationOpened) 
            .EndInit(); 
        OneSignal.Current.IdsAvailable(IdsAvailable); 
        return true; 
    } 
    void IdsAvailable(string userID, string pushToken) 
    { 
        GlobalUserInfo._token = userID; 
    } 
    private void HandleNotificationOpened(OSNotificationOpenedResult result) 
    { 
        OSNotificationPayload payload = result.notification.payload; 
        Dictionary<string, object> additionalData = payload.additionalData; 
        if (additionalData != null) 
        { 
            // 复用当前窗口的根导航控制器,而非重新实例化
            var currentNavController = Window.RootViewController as UINavigationController;
            if (currentNavController != null)
            {
                NotificationsViewController notificationsController = Storyboard.InstantiateViewController("NotificationsViewController") as NotificationsViewController; 
                currentNavController.PushViewController(notificationsController, true); 
            }
            // 如果根控制器不是导航控制器,可根据项目结构调整(比如先将导航控制器设为根)
            else
            {
                NotificationsViewController notificationsController = Storyboard.InstantiateViewController("NotificationsViewController") as NotificationsViewController; 
                var navController = new UINavigationController(notificationsController);
                Window.RootViewController = navController;
            }
        } 
    } 
}

额外注意点

  • 全局检查所有可能初始化OneSignal的位置(比如某个ViewController的ViewDidLoad、自定义启动服务类等),确保只初始化一次
  • 区分应用冷启动、热启动场景,HandleNotificationOpened在两种场景下都会触发,跳转逻辑要考虑当前页面栈状态,避免重复推入相同页面
  • 确认NotificationsViewController在Storyboard中的Storyboard ID和代码中InstantiateViewController传入的字符串完全一致

内容的提问来源于stack exchange,提问作者Adeptus Mechanicus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 07:55:18