纳金网

标题: Unity3D入门二:Socket初探 [打印本页]

作者: .    时间: 2013-1-16 16:59
标题: Unity3D入门二:Socket初探
这几天研究了下Socket交互。通过网上的资料做了有关Socket的第一个Demo,虽然不是很成熟,但个人感觉已经相对比较完整了。各类型数据的传输接受都有,其中也做了float类型的(因为我感觉做Unity应该用的着)。
功能方面,为了测试多用户交互,我在Demo上开启了4个Socket 4个线程接受数据。实现了服务端通知用户进入 离开功能。

真机上,需要加上字库,要不无法显示中文。
下面上代码:
客户端代码:
using UnityEngine;

using System;

using System.Collections;

using LSocket.Net;

using LSocket.Type;

using LSocket.cmd;
public class SocketDemo : MonoBehaviour

{

public UnitySocket[] socket;

public String[] textAreaString;

public String[] textFieldString;

public GUISkin mySkin;

// Use this for initialization

void Start()

{

socket = new UnitySocket[4];

textAreaString = new String[12];

for (int i = 0; i < 12; i++)

{

textAreaString = "";

}

textFieldString = new String[4];

for(int i=0;i<4;i++){

textFieldString = "";

}

}
// Update is called once per frame

void Update()

{
}
void OnGUI()

{

GUI.skin = mySkin;

for (int i = 0; i < 4; i++)

{

String s = textAreaString[i * 3] + "
" + textAreaString[i * 3 + 1] + "
" + textAreaString[i * 3 + 2];

GUI.TextArea(new Rect(i % 2 * Screen.width / 2, i / 2 * (Screen.height / 2) + 50, 100, 60), s);

textFieldString = GUI.TextField(new Rect(i % 2 * Screen.width / 2+50, i / 2 * (Screen.height / 2), 100, 20), textFieldString);

if (GUI.Button(new Rect(i % 2 * Screen.width / 2, i / 2 * (Screen.height / 2), 40, 20), "连接"))

{

socket = null;

socket = new UnitySocket();

socket.SocketConnection("192.168.0.8", 10000, this, i);

socket.DoLogin(textFieldString);

}

else if (GUI.Button(new Rect(i % 2 * Screen.width / 2, i / 2 *( Screen.height / 2) + 25, 40, 20), "关闭"))

{

if (socket != null)

{

socket.close();

socket = null;

}

}

}
if (GUI.Button(new Rect(Screen.width - 60, Screen.height - 30, 60, 30), "退出")) {

Application.Quit();

}
}

}


namespace LSocket.Net

{ /**

*

* @author feng侠,qq:313785443

* @date 2010-12-23

*

*/
// 描 述:封装c# socket数据传输协议

using UnityEngine;

using System;

using System.Net.Sockets;

using System.Net;

using System.Collections;

using System.Text;

using System.Threading;

using LSocket.Type;

using LSocket.cmd;

class SocketThread

{
UnitySocket socket;

SocketDemo demo;

int idx;
public SocketThread(UnitySocket socket, SocketDemo demo, int idx)

{

this.socket = socket;

this.demo = demo;

this.idx = idx;

}
public void ***n()

{

while (***e)

{

try

{

String s = socket.ReceiveString();

demo.textAreaString[idx * 3] = demo.textAreaString[idx * 3 + 1];

demo.textAreaString[idx * 3 + 1] = demo.textAreaString[idx * 3 + 2];

demo.textAreaString[idx * 3 + 2] = s;

MonoBehaviour.print(s + " " + idx);

}

catch (Exception e)

{

MonoBehaviour.print(e.ToString());

socket.t.Abort();

}

}

}
}
public class UnitySocket

{

public Socket mSocket = null;

public Thread t=null;

private SocketThread st=null;

public SocketDemo demo=null;
public UnitySocket()

{
}

public void SocketConnection(string LocalIP, int LocalPort,SocketDemo demo,int idx)

{

this.demo=demo;

mSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);

try

{
IPAddress ip = IPAddress.Parse(LocalIP);

IPEndPoint ipe = new IPEndPoint(ip, LocalPort);

mSocket.Connect(ipe);

st =new SocketThread(this, demo, idx);

t = new Thread(new ThreadStart(st***n));

t.Start();

}

catch (Exception e)

{

MonoBehaviour.print(e.ToString());

}

}
public void close(){

mSocket.Close(0);

mSocket=null;

}
public void DoLogin(String userName){

try

{

Send(CommandID.LOGIN);

Send(userName);

}catch(Exception e){

MonoBehaviour.print(e.ToString());

}

}

public void Send(float data){

byte[] longth = TypeConvert.getBytes(data, ***e);

mSocket.Send(longth);

}
public float ReceiveFloat()

{

byte[] recvBytes = new byte[4];

mSocket.Receive(recvBytes, 4, 0);//从服务器端接受返回信息

float data = TypeConvert.getFloat(recvBytes, ***e);

return data;

}
public void Send(short data)

{

byte[] longth=TypeConvert.getBytes(data,***e);

mSocket.Send(longth);

}
public void Send(long data)

{

byte[] longth=TypeConvert.getBytes(data,***e);

mSocket.Send(longth);

}
public void Send(int data)

{

byte[] longth=TypeConvert.getBytes(data,***e);

mSocket.Send(longth);
}
public void Send(string data)

{

byte[] longth=Encoding.UTF8.GetBytes(data);

Send(longth.Length);

mSocket.Send(longth);
}
public short ReceiveShort()

{

byte[] recvBytes = new byte[2];

mSocket.Receive(recvBytes,2,0);//从服务器端接受返回信息

short data=TypeConvert.getShort(recvBytes,***e);

return data;

}
public int ReceiveInt()

{

byte[] recvBytes = new byte[4];

mSocket.Receive(recvBytes,4,0);//从服务器端接受返回信息

int data=TypeConvert.getInt(recvBytes,***e);

return data;

}
public long ReceiveLong()

{

byte[] recvBytes = new byte[8];

mSocket.Receive(recvBytes,8,0);//从服务器端接受返回信息

long data=TypeConvert.getLong(recvBytes,***e);

return data;

}
public String ReceiveString()

{

int length = ReceiveInt();

MonoBehaviour.print("Stringlen="+length);

byte[] recvBytes = new byte[length];

mSocket.Receive(recvBytes,length,0);//从服务器端接受返回信息

String data = Encoding.UTF8.GetString(recvBytes);

return data;

}
}

}


namespace LSocket.Type

{

using UnityEngine;

using System.Collections;
public class TypeConvert

{
public TypeConvert()

{

}
public static byte[] getBytes(float s,bool asc){

int buf = (int)(s * 100);

return getBytes(buf,asc);

}
public static float getFloat(byte[] buf,bool asc){

int i=getInt(buf,asc);

float s=(float)i;

return s/100;

}
public static byte[] getBytes(short s, bool asc)

{

byte[] buf = new byte[2];

if (asc)

{

for (int i = buf.Length - 1; i >= 0; i--)

{

buf = (byte)(s & 0x00ff);

s >>= 8;

}

}

else

{

for (int i = 0; i < buf.Length; i++)

{
buf = (byte)(s & 0x00ff);

s >>= 8;

}

}

return buf;

}

public static byte[] getBytes(int s, bool asc)

{

byte[] buf = new byte[4];

if (asc)

for (int i = buf.Length - 1; i >= 0; i--)

{

buf = (byte)(s & 0x000000ff);

s >>= 8;

}

else

for (int i = 0; i < buf.Length; i++)

{

buf = (byte)(s & 0x000000ff);

s >>= 8;

}

return buf;

}
public static byte[] getBytes(long s, bool asc)

{

byte[] buf = new byte[8];

if (asc)

for (int i = buf.Length - 1; i >= 0; i--)

{

buf = (byte)(s & 0x00000000000000ff);

s >>= 8;

}

else

for (int i = 0; i < buf.Length; i++)

{

buf = (byte)(s & 0x00000000000000ff);

s >>= 8;

}

return buf;

}

public static short getShort(byte[] buf, bool asc)

{

if (buf == null)

{

//throw new IllegalArgumentException("byte array is null!");

}

if (buf.Length > 2)

{

//throw new IllegalArgumentException("byte array size > 2 !");

}

short r = 0;

if (!asc)

for (int i = buf.Length - 1; i >= 0; i--)

{

r <<= 8;

r |= (short)(buf & 0x00ff);

}

else

for (int i = 0; i < buf.Length; i++)

{

r <<= 8;

r |= (short)(buf & 0x00ff);

}

return r;

}

public static int getInt(byte[] buf, bool asc)

{

if (buf == null)

{

// throw new IllegalArgumentException("byte array is null!");

}

if (buf.Length > 4)

{

//throw new IllegalArgumentException("byte array size > 4 !");

}

int r = 0;

if (!asc)

for (int i = buf.Length - 1; i >= 0; i--)

{

r <<= 8;

r |= (buf & 0x000000ff);

}

else

for (int i = 0; i < buf.Length; i++)

{

r <<= 8;

r |= (buf & 0x000000ff);

}

return r;

}

public static long getLong(byte[] buf, bool asc)

{

if (buf == null)

{

//throw new IllegalArgumentException("byte array is null!");

}

if (buf.Length >

{

//throw new IllegalArgumentException("byte array size > 8 !");

}

long r = 0;

if (!asc)

for (int i = buf.Length - 1; i >= 0; i--)

{

r <<= 8;

r |= (buf & 0x00000000000000ff);

}

else

for (int i = 0; i < buf.Length; i++)

{

r <<= 8;

r |= (buf & 0x00000000000000ff);

}

return r;

}
namespace LSocket.cmd

{

public class CommandID

{

/** 登陆消息命令 **/

public static int LOGIN = 1001;
}

}


很简单的demo,有一定的可扩展性,需要工程的可以下载来看,下载链接
http://download.csdn.net/detail/genius840215/4187126


【来源:互联网】

更多精彩教程,尽在web3D纳金网http://www.narkii.com/college/




欢迎光临 纳金网 (http://rs.narkii.com/club/) Powered by Discuz! X2.5