2015-06-12 42 views
3

在我們正在製作的應用程序中,我們希望在應用程序掛起時嘗試​​遠程用戶保存數據。在Unity的編輯器,在Android上,這很簡單,只要Unity3D在iOS上的主線程上的WWW調用

WWW www = new WWW(_URL); 
while(!www.isDone) 
{ 
    Thread.Sleep(100); 
} 
Debug.Log(www.text); 

(全樣本:https://github.com/SixMinute/iOSWWWGet

但在iOS上,www.isDone而我們阻止從未值爲true,那麼整個事情只是掛起。

這是一個錯誤,或通過設計?然後,如果是設計,那麼這樣做的正確方法是什麼,因爲如果我們把它放在StartCoroutine之後,它在主線程中不正確,並且在暫停時,發生什麼事情會在應用程序恢復時推送到它(這完全擊敗了我們正在努力的目的)。

編輯:在與IRC上的一些Unity開發人員交談後,他們接受這實際上是代碼中的錯誤,瞭解我需要這個的原因,並且接受需要有一種方法來同步激發WWW請求,或者在iOS的OnApplicationPause(true)流程中調用時啓用此功能的其他方式,因爲否則(儘管能夠輕鬆地在本地執行),但當時無法啓動WWW請求,唯一的選擇是將它們排隊,直到簡歷,這是完全不切實際的。

回答

1

在這一刻團結不啓動一個新的線程WWW行動,至少在一些平臺(iOS,webplayer)。或者如果是這樣,它會在主線程上設置WWW.isDone。所以這段代碼:

while(!www.isDone) 
    Thread.Sleep(500); 

不起作用。

+0

是的,我添加了來自Unity iOS開發者的響應。雖然在這種情況下這是平臺的一個限制,但在掛起流程期間,仍然有一種方法可以從「OnApplicationPause(true)」調用中觸發WWW請求。在目前最簡單的形式中,你的回答是正確的,我會將其標記爲這樣,但希望Unity修復該錯誤/允許在iOS上執行此操作的方法,然後將該方法作爲答案添加。 – seaders

-1

入住這對Unity Documentation

使用協程,while循環將被阻止在網絡播放器:

void SaveDate() 
{ 
StartCoroutine("SaveWebData"); 
} 

IEnumerator SaveWebData() 
{ 
// Start a download of the given URL 
WWW www = new WWW(_URL); 

// Wait for download to complete 
yield return www; 

// Completed! 
Debug.Log(www.text); 
} 
+1

你能提供一些代碼,因爲該頁面是非常缺乏信息和*正如我所說的*,使用'StartCoroutine'推動任何東西'yield'當應用程序恢復後出現這種情況。我需要在編輯器和Android上的主線程上下載。 – seaders

+0

_ [你的回答是在另一座城堡:何時答案不是答案?](http://meta.stackexchange.com/questions/225370/your-answer-is-in-another-castle-when-is-的回答 - 不的回答)_。考慮編輯您的答案以包含鏈接指向的文章摘要。 – MickyD

+0

對不起,編輯。現在好多了? – joreldraw

1

以任何你想要的方法開始你的www電話。在更新期間,請檢查www.isDone ...如果返回true,則對其執行操作...否則,請通過。

private WWW myRequest = null; 

void Update() 
{ 
    if (myRequest != null) 
    { 
     if (myRequest.isDone) 
     { 
      // process request here 

      myRequest = null;// reset it 
     } 
    } 
} 

如果你想支持發射一個以上的WWW請求一次,把你的WWW請求中的數組列表myRequests =新名單()和遍歷那些在更新,而不是和檢查每個人的狀態。在使用它時,您無法從myRequests中刪除,因此請記下臨時刪除列表。

private List<WWW> myRequests = new List<WWW>() 

void Update() 
{ 
    if (myRequests.Count > 0) 
    { 
     List<WWW> removeList = null; 

     foreach (WWW myRequest in myRequests) 
     { 
      if (myRequest.isDone) 
      { 
       // process request here 

       if (removeList == null) 
       { 
        removeList = new List<WWW>(); 
       } 
       removeList.Add(myRequest); 
      } 
     } 
     if (removeList != null) 
     { 
      foreach (WWW oldReq in removeList) 
      { 
       myRequests.Remove(oldReq); 
      } 
     } 
    } 
}