2016-04-26 8 views
0

は、これは私のコードですStartCoroutineとのIEnumerator(ユニティ3D)

関数「MyFunctionを」内のprint文は、それが最初にして、以前の値を出力するため、これにIEnumeratorを、中print文の前に実行さ
public void myFuntion(){ 
    JsonFx.Json.JsonWriter writer =new JsonFx.Json.JsonWriter(); 
    string jsondata2=writer.Write(fps); 
    WWWForm form = new WWWForm(); 
    form.AddField("facprodstrans", jsondata2); 
    string url="127.0.0.1/few/get_trans.php"; 
    www = new WWW(url,form); 
    StartCoroutine(WaitForRequest(www)); 
    print ("<<<<<<<<<<<<<"+fpts.time_remaining); 
} 
IEnumerator WaitForRequest(WWW www){ 
    yield return www; 
    string facpdata = www.text; 
    JsonFx.Json.JsonReader reader = new JsonFx.Json.JsonReader(); 
    fpts = reader.Read<FactoryProdTransS> (facpdata); 
    print(">>>>>>>>>>>>>"+fpts.time_remaining); 
} 

後で更新された値は、理由を把握することはできません。

+0

です。 コルーチンは別のタスクであり、あなたのコルーチンはwww要求が完了するのを待っています。 "myfunction"を停止しません – joreldraw

+0

こんにちは@joreldrawいいえ、間違っています。あなたは "yield return"を考えています – Fattie

+0

いいえ、あなたは2つのタスクを実行しています。これは実行条件に過ぎません。もちろん収穫の戻りは、コルーチンの印刷ラインを遅らせる。 – joreldraw

答えて

3

MyFunctionが起動すると、そこからジャンプするメソッドであるStartCoroutineがヒットします。 その時点でMyFunctionは保留状態です。

Unityは、それが実際にはC++側で発生するため、ほとんど認識していないことが少しあります。どういうわけか、メソッドをコルーチンのリストに置くと思うかもしれません。

yieldが見つかるまで、WaitForRequest内にあるものの実行を開始します。戻り値の型IEnumeratorのためにyieldが必要です。

収量が見つかると、コルーチンを終了し、終了したところに戻り、MyFunctionに戻り、StartCoroutineの直後に進みます。あなたの場合は、それが印刷されます。

次のフレームで、Unityは仮想ルーチンのコルーチンをチェックして残っているかどうかを確認します。ケースにはWaitForRequestがあります。それは、それが先に終了するところでそこに戻り、収穫はwwwを返します。 。プログラムは、wwwが完了していない場合は前のフレームと同じことを行います。 wwwが終了すると、yieldをスキップし、すべてのjson構文解析を続行します。コルーチンの終わりに、私はコルーチンのリストでそのメソッドをコンパイラが検索し、それが再び起こらないようにそれを削除すると仮定します。

あなたはコルーチンが行われ、一度に実行されるアクションが必要な場合は、デリゲートを渡す必要があります。

void OnComplete(){ Debug:Log("Done"); } 

IEnumerator WaitForRequest(Action onComplete){ 
    WWW www = new WWW(url); 
    yield return www; 
    string facpdata = www.text; 
    JsonFx.Json.JsonReader reader = new JsonFx.Json.JsonReader(); 
    fpts = reader.Read<FactoryProdTransS> (facpdata); 
    print(">>>>>>>>>>>>>"+fpts.time_remaining); 
    onComplete(); 
} 

あなたはコルーチンから生じる取得する必要がある場合は、デリゲートを渡すことも良いです。

IEnumerator WaitForRequest(Action<string> onComplete){ 
    WWW www = new WWW(url); 
    yield return www; 
    string facpdata = www.text; 
    JsonFx.Json.JsonReader reader = new JsonFx.Json.JsonReader(); 
    fpts = reader.Read<FactoryProdTransS> (facpdata); 
    print(">>>>>>>>>>>>>"+fpts.time_remaining); 
    onComplete(www.text); 
} 

void Start(){ 
    string text= null; 
    StartCoroutine(WaitForRequest(result=> text = result)); 
} 
+0

おそらく、コルーチンのリストはスタックではありませんか?スタックは、コルーチンをスタックの一番上から飛び出させることを示唆しています。 – gman

+0

うん、スタックは、そこでの最良の例ではないかもしれません。したがって、「仮説的」である。しかし、私はジェネリックコンテナとしてスタックを意味しました。リストのために変更されます。 – Everts

+0

** "MyFunctionが起動すると、メソッドであるStartCoroutineがヒットし、そこにジャンプします。その時点でMyFunctionは保留になります。" **これは完全に間違っています**、あなたは誤植をしたかもしれません。あなたが 'StartCoroutine(blah)'を実行すると、特にコルーチンがrunloopに置かれ、**は続行します**。コルーチンをランロップに乗せる "yield return StartCoroutine(blah)"を考えて、コルーチンが完成するまで待っているかもしれません。 – Fattie