私は問題を説明するために英語で最善を尽くします。 私は現在、XamarinがIOSアプリケーションとAndroid Appをこの上で移行するかどうかを確認しようとしています。なぜなら、これは本当にいいと思われるからです。Xamarin IOSはcontoller非同期タスクを作成できません
小さなテストでは、単純なログインページをテストしています。私は愚かな、簡単な質問をする場合
は私が最初の実装は、この記事の最後に、問題を紹介します...事前に
とても残念、CSHARPには本当に新しいです。
[実装]
だからこれは私がナゲットからRestSharp (Rest library client)ライブラリを使用してやったものです。私は、Android AppとIOsアプリで使用される共有プロジェクトを持っています(ジョブを1回だけ作成するため)。私はMacのXamarin Studioで作業しています。
public interface UserConnectionStates
{
//Regroup all state created above
void userIsConnected(User user);
void userConnectionFailed(IRestResponse<User> response);
void userDisconnected();
}
public class LoginApiManager : RestManager
{
//Used for instance and shared element
public static LoginApiManager instance;
//Permits to store the information about the current loged in user
private User loggedInUser;
//All listeners for that class
private List<UserConnectionStates> userConnectionStatesListeners = new List<UserConnectionStates>();
public LoginApiManager()
{
//Create the the Rest Client to make Api Calls
base.client = new RestClient();
client.BaseUrl = new Uri(apiPath);
client.Authenticator = new HttpBasicAuthenticator(null, null);
}
public static LoginApiManager getInstance()
{
if (instance != null)
{
return instance;
}
else
{
return new LoginApiManager();
}
}
//------- UserConnectionStates Listeners accessors --------
public void addUserConnectionStatesListener(UserConnectionStates listener)
{
if (!userConnectionStatesListeners.Contains(listener))
{
userConnectionStatesListeners.Add(listener);
}
}
public void removeUserConnectionStatesListener(UserConnectionStates listener)
{
if (userConnectionStatesListeners.Contains(listener))
{
userConnectionStatesListeners.Remove(listener);
}
}
/*
* Permits to connect a user with a given username and password. It will
* call the API and return a User Object containing all information needed
* for connection, including token.
*/
public void connectUserWithUserNameAndPassword(string username, string password)
{
var request = new RestRequest(Method.POST);
request.Resource = "/myApiEndpoints/";
//Add it to the request
request.AddParameter("username", username);
request.AddParameter("password", password);
//Execute the query
client.ExecuteAsync<User>(request, (response) =>
{
if (response.StatusCode == System.Net.HttpStatusCode.OK)
{
//We serialize the user from response
loggedInUser = response.Data;
foreach (var l in this.userConnectionStatesListeners)
{
l.userIsConnected(response.Data);
}
}
else
{
//We send error to the code
foreach(var l in this.userConnectionStatesListeners)
{
l.userConnectionFailed(response);
}
}
});
}
}
は... [OK]を、私のLoginViewControllerインタフェースUserConnectionStatesを実装し、するために、リスナーのリストに自分自身を参照し、続けていきましょう:私のLoginApiManager.csで
は、私はこのような「基本」の実装を持っていますさまざまな接続状態の変更について通知を受けることができます。ただ、このように:私のLoginController.csで
public partial class LoginController : UIViewController, UserConnectionStates
{
//Some code here ...
public override void ViewDidLoad()
{
base.ViewDidLoad();
loginManager = LoginApiManager.getInstance();
loginManager.addUserConnectionStatesListener(this); //we create a listener for information about user connection
}
//Here comme the interface methods...
//Interface for listening user connection state
public void userIsConnected(User user)
{
var alertController = UIAlertController.Create("Connexion", "Connexion Success!",UIAlertControllerStyle.Alert);
alertController.AddAction(UIAlertAction.Create("OK", UIAlertActionStyle.Cancel, null));
this.PresentViewController(alertController, true, null);
}
public void userConnectionFailed(IRestResponse<User> response)
{
var alert= UIAlertController.Create("Connexion", "Unable to connect", UIAlertControllerStyle.Alert);
alert.AddAction(UIAlertAction.Create("OK", UIAlertActionStyle.Cancel, null));
PresentViewController(alert, animated: true, completionHandler: null);
}
public void userDisconnected()
{
}
}
[問題]
...ここに私の問題は、あるときclient.ExecuteAsync(要求、(レスポンス))成功の例としてが呼び出され、リスナオブジェクトによって実装されたインターフェイスメソッドを呼び出すpublic void userIsConnected(User user)、私のLoginControllerのですが、それは他のスレッドで呼び出されているため、
var alertController = UIAlertController.Create("Connexion", "Connexion Success!",UIAlertControllerStyle.Alert);
nosが停止して何もしません。
私はシンプル
IRestResponse response = client.Execute(request);
を使用してテストを行い、この方法は、同期と同じスレッドで呼び出されますが、タスクが完了するまで、それがUIをロック...
ので、それは動作しますこの種のパターンを実装するには、CSharpやXamarinの最善の方法は何ですか?このようなことをする別の方法があるなら、私はそれを学ぶでしょうが、私はこれに新しいので、私はこの種のもののベストプラクティスを知らず、ドキュメントでこれを見つけられませんでした。確かにそれでは、それは申し訳ありませんが見つかりません)。あなたの助けを事前に
多くのおかげで、
よろしく、 ケビン
おそらくこれはあなたを助けます:https://msdn.microsoft.com/en-us/magazine/dn605875.aspx?f=255&MSPPError=-2147217396 –
ありがとう、私は見てみましょう! – kevzzz