簡體   English   中英

調用 iOS Alert 時出現 UI 一致性錯誤

[英]UI consistency error when calling iOS Alert

我有一個 iOS Xamarin 項目,但出現以下錯誤:

    UIKit Consistency error: you are calling a UIKit method that 
    can only be invoked from the UI thread.

此錯誤發生在以下代碼中:

在我的歡迎視圖頁面中,我有一個名為SyncButton的按鈕被點擊。 單擊該按鈕應該使用 REST 將數據與服務器同步。

在我的 WelcomeController 中,我有:

....
SyncButton.TouchUpInside += async (object sender, EventArgs e) => {
            SyncButton.Enabled = false;

            await welcomeDelegate.syncButtonCore (cred, iOSErrorAlert);

            SyncButton.Enabled = true;
        };
 ....

public void iOSErrorAlert(string LoginErrorTitle, string LoginErrorMessage){
        var Alert = UIAlertController.Create (LoginErrorTitle, LoginErrorMessage, UIAlertControllerStyle.Alert);
        Alert.AddAction (UIAlertAction.Create ("OK", UIAlertActionStyle.Cancel, null));
        PresentViewController (Alert, animated: true, completionHandler: null);

    }

當確實出現超時或其他一些錯誤時,應該發生警報。

SyncButtonCore()包含在如下所示的委托類中:

public async Task syncButtonCore(UserCredentials cred, RequestWithAlertDelegate.ErrorAlert NativeAlert){
        await Task.Run (async ()=>{
            RequestWithAlertDelegate requestWithAlert = new RequestWithAlertDelegate();
            string URL = URLs.BASE_URL + URLs.CASELOAD + "/" + cred.PID;
            await requestWithAlert.RequestWithRetry(URL, cred.UserID, cred.Password, NativeAlert, null, async delegate (string Response1){...}, 1);

我的RequestWithAlert類在哪里:

public async Task RequestWithRetry (string URL, string UserID, string Password, ErrorAlert NativeAlert, SyncAction Action, AsyncAction Action2, int times)
    {
        ...make sure legit credentials...
        if (LoginError) {
            NativeAlert (LoginErrorTitle, LoginErrorMessage);
        } 

在最后一段代碼中,我在 NativeAlert() 函數中遇到錯誤的地方。 這最終拋出了在我的代碼開頭提到的 UIKit 錯誤

var Alert = UIAlertController.Create (LoginErrorTitle, LoginErrorMessage, UIAlertControllerStyle.Alert);

我不確定我在這里做錯了什么,為什么我不允許創建這個警報,因為我在我的WelcomeController定義了它,我的 UIThread 應該是正確的?

問題出在我的iOSErrorAlert()函數中。 我需要用InvokeOnMainThread()包圍它,因為 UI 操作應該在主線程中執行(我沒有這樣做,因為我將它傳遞給其他類/線程)。 謝謝@Paulw11 的評論。

不得不更換這個:

public void iOSErrorAlert(string LoginErrorTitle, string LoginErrorMessage){
    var Alert = UIAlertController.Create (LoginErrorTitle, LoginErrorMessage, UIAlertControllerStyle.Alert);
    Alert.AddAction (UIAlertAction.Create ("OK", UIAlertActionStyle.Cancel, null));
    PresentViewController (Alert, animated: true, completionHandler: null);
}

有了這個:

public void iOSErrorAlert(string LoginErrorTitle, string LoginErrorMessage){
    InvokeOnMainThread (() => {
        var Alert = UIAlertController.Create (LoginErrorTitle, LoginErrorMessage, UIAlertControllerStyle.Alert);
        Alert.AddAction (UIAlertAction.Create ("OK", UIAlertActionStyle.Cancel, null));
        PresentViewController (Alert, animated: true, completionHandler: null);
    });
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM