2012-02-29 5 views
7

В MonoTouch, как зарегистрировать неперехваченное обработчик исключений (или аналогичные функции)MonoTouch: uncaughtExceptionHandler?

В Obj-C:

void uncaughtExceptionHandler(NSException *exception) { 
     [FlurryAnalytics logError:@"Uncaught" message:@"Crash!" exception:exception]; 
    } 

- (void)applicationDidFinishLaunching:(UIApplication *)application { 
    NSSetUncaughtExceptionHandler(&uncaughtExceptionHandler); 
    [FlurryAnalytics startSession:@" "]; 
    .... 
} 

ответ

-4

Вы добавить обработчик примерки поймать вокруг кода, который (может) бросить NSExceptions :

try { 
    FlurryAnalytics.StartSession (" "); 
} catch (MonoTouchException ex) { 
    Console.WriteLine ("Could not start flurry analytics: {0}", ex.Message); 
} 

MonoTouch уже устанавливает неперехваченное обработчик исключений, и автоматически преобразует это ObjectiveC исключения управляемых исключений.

+2

Это не касается его первоначального вопроса. –

1
public delegate void NSUncaughtExceptionHandler(IntPtr exception); 

    [DllImport("/System/Library/Frameworks/Foundation.framework/Foundation")] 
    private static extern void NSSetUncaughtExceptionHandler(IntPtr handler); 

    // This is the main entry point of the application. 
    private static void Main(string[] args) 
    { 
      NSSetUncaughtExceptionHandler(
       Marshal.GetFunctionPointerForDelegate(new NSUncaughtExceptionHandler(MyUncaughtExceptionHandler))); 

      ... 
    } 

    [MonoPInvokeCallback(typeof(NSUncaughtExceptionHandler))] 
    private static void MyUncaughtExceptionHandler(IntPtr exception) 
    { 
     var e = new NSException(exception); 
     ... 
    } 
+0

Удивительно, спасибо! Только конструктор для NSException, который берет IntPtr, защищен, поэтому вам нужно подтипировать его и выставить эту версию конструктора. В противном случае это было очень полезно. –

+0

[Здесь] (http://stackoverflow.com/questions/37525472/create-nsexception-from-intptr/37527174#37527174) вы можете видеть, как 'NSException' принимает аргумент' IntPtr'. – testing

0

Это делает свою работу. Вызовите метод SetupExceptionHandling() при запуске приложения. Магия - это часть NSRunLoop. Но приложение будет в странном состоянии в этот момент, с непредсказуемыми последствиями. Поэтому я настоятельно рекомендую убить приложение после того, как пользователь решит, что делать с исключением - например, путем повторного броска.

public static class IOSStartupTasks { 
    private static bool _HaveHandledException; 
    public static void HandleException(object sender, UnhandledExceptionEventArgs e) { 
    if (!(_HaveHandledException)) { 
     _HaveHandledException = true; 
     UIAlertView alert = new UIAlertView("Error", "Bad news", "report", "just crash"); 
     alert.Delegate = whatever; // delegate object should take the exception as an argument and rethrow when it's done handling user input. 
     alert.Show(); 
     NSRunLoop.Current.RunUntil(NSDate.DistantFuture); // keeps the app alive, but likely with weird effects, so make sure you don't let the user back into the main app. 
    } 
    } 

    public static void SetupExceptionHandling() { 
    AppDomain domain = AppDomain.CurrentDomain; 
    domain.UnhandledException += (object sender, UnhandledExceptionEventArgs e) => 
     IOSStartupTasks.HandleException(sender, e); 
    } 
} 
Смежные вопросы