Unity程序向Web服務器發送數據
- 一、介紹
- 二、HTTP協議
- 三、新建Unity工程,創建腳本
- 1.新建Unity工程,創建腳本WebManager.cs,將其指定給場景中的任意游戲體。
- 2.在WebManager.cs中添加一個m_info屬性和OnGUI函數顯示UI:
- 四、GET請求
- 在WebManager.cs腳本中添加一個IGetData()函數,注意函數的返回類型是
- 在OnGUI函數中添加代碼執行IGetData函數:
- 接下來,我們要創建一個PHP腳本響應WWW的GET請求。新建PHP工程,在Web服務器根目錄創建index.php
- 測試如下
- 五、POST請求
- 在WebManager.cs腳本中添加一個IPostData()函數:
- 在OnGUI函數中添加代碼執行IPostData函數:
- 修改PHP腳本,添加POST請求的響應:
- 測試如下:
一、介紹
本文將演示一個簡單的實例,從Unity程序向Web服務器發送數據,Web服務器收到數據后向Unity程序再返回數據。不附帶HTTP架構設計需要自行動腦設計。
二、HTTP協議
Unity的WWW是基于HTTP協議的網絡傳輸功能,HTTP(hypertext transport protocol)協議即超文本協議,它規定了萬維網數據通信的規則,它是客戶端、服務器模式,客戶端和服務器都必須支持HTTP。HTTP協議的一個重要特點是每次連接只處理一個請求,當服務器處理完客戶端的請求即斷開連接,節省傳輸時間。
使用HTTP協議傳輸數據有多種方式,Unity的WWW主要支持其中的GET和POST方式。GET方式會將請求附加在URL后,POST方式則是通過FORM(表單)的形式提交。GET方式最多只能傳輸1024個字節,POST方式理論上則沒有限制。從安全角度來看POST比GET方式安全性更高,所以在實際使用中更多選擇POST方式。
下面,我們先創建一個簡單的UI界面,提供兩個按鈕,分別用于使用GET和POST方式向服務器提交數據。(這里有不會搭建HTTP服務器的可以看我之前的文章Php與Apache環境配置)
三、新建Unity工程,創建腳本
1.新建Unity工程,創建腳本WebManager.cs,將其指定給場景中的任意游戲體。
2.在WebManager.cs中添加一個m_info屬性和OnGUI函數顯示UI:
string m_info = "Nothing";private void OnGUI(){GUI.BeginGroup(new Rect(Screen.width * 0.5f - 100,Screen.height * 0.5f -100,500,200),"");GUI.Label(new Rect(10,10,400,30),m_info);if (GUI.Button(new Rect (10,50,150,30),"GetData")){}if (GUI.Button(new Rect(10,100,150,30),"Post Data")){}GUI.EndGroup();}
運行程序,在窗口中會出現兩個按鈕,并顯示“Nothing”,如圖所示。我們將使用Get Data和Post Data按鈕分別通過GET 和 POST方式向Web服務器發送數據,然后服務器返回數據,傳遞給m_info屬性顯示在屏幕上。
四、GET請求
接下來我們使用GET方式向服務器提交數據,包括一個用戶名和一個密碼,服務器收到后返回一個字符串。
在WebManager.cs腳本中添加一個IGetData()函數,注意函數的返回類型是
IEnumerator IGetData(){WWW www = new WWW("http://47.101.204.7:8088/index.php?username=get&password=123456");yield return www;if (www.error != null){m_info = www.error;yield return null;}m_info = www.text;}
這個函數中,我們首先創建了一個WWW實例,使其向指定的IP地址發送GET請求,跟隨在IP地址后面的?用于附加數據,這里我們發送了兩個GET數據,一個是username,另一個是password,它們的值分別是get和12345。
WWW實例將在后臺運行,yield return www會等待Web服務器的反映。
如果WWW實例的error屬性不為空,Web服務器返回的數據則會保存在WWW實例的text屬性中。
在OnGUI函數中添加代碼執行IGetData函數:
if (GUI.Button(new Rect (10,50,150,30),"GetData")){StartCoroutine(IGetData());}
接下來,我們要創建一個PHP腳本響應WWW的GET請求。新建PHP工程,在Web服務器根目錄創建index.php
<?php
if ( isset($_GET['username']) && isset($_GET['password']) )echo 'username is '.$_GET['username'].' and password is '.$_GET['password'];
elseecho "error!";
?>
這是一段PHP代碼,isset函數用來判斷是否收到相應的GET請求,如果收到了,則使用echo函數輸出結果,并將其返回到Unity程序中。(在PHP中,連接兩個字符串是使用.而不是+)
測試如下
在Unity中運行程序,按一下Get Data按鈕,然后會收到服務器返回的值,結果如下所示:
五、POST請求
使用POST提交數據的方式與GET類似,但我們將會把字符串轉為byte數組。
在WebManager.cs腳本中添加一個IPostData()函數:
IEnumerator IPostData(){Dictionary<string,string> headers = new Dictionary<string, string>();headers.Add("Content_Type","application/x-www-form-urlencoded");string data = "username=post&password=6789";byte[] bs = System.Text.UTF8Encoding.UTF8.GetBytes(data);WWW www = new WWW("http://47.101.204.7:8088/index.php",bs,headers);yield return www;if (www.error != null){m_info = www.error;yield return null;}m_info = www.text;}
與GET不同的是,在保存數據的字符串中,最前面沒有?符號,但仍使用&符號連接數據,最后我們將字符串轉為一個byte數組。headers在以前版本是一個HashTable現在都改為了Dictionary,它由鍵、值對應,這里我們用它來保存HTTP包頭。
在OnGUI函數中添加代碼執行IPostData函數:
if (GUI.Button(new Rect(10,100,150,30),"Post Data")){StartCoroutine(IPostData());}
修改PHP腳本,添加POST請求的響應:
<?php
if ( isset($_GET['username']) && isset($_GET['password']) )echo 'username is '.$_GET['username'].' and password is '.$_GET['password'];
else if ( isset($_POST['username']) && isset($_POST['password']) )echo 'username is '.$_POST['username'].' and password is '.$_POST['password'];
elseecho "error!";
?>
測試如下:
在Unity中運行程序,按一下Post Data按鈕,然后會收到服務器返回的數據