【发布时间】:2016-05-11 20:04:39
【问题描述】:
我有一个 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 应该是正确的?
【问题讨论】:
-
您的网络操作将在后台线程上完成。您需要在主/UI 线程中显式执行您的 UI 操作。
-
@Paulw11 谢谢,用
InvokeOnMainThread包围了这个技巧 -
@user3470987 如果您发布一个显示您如何使用
InvokeOnMainThread的答案,它可能会帮助一些人。
标签: c# ios view xamarin uialertview