mirror of
https://github.com/SFML/SFML.git
synced 2024-11-25 12:51:05 +08:00
2f524481c1
git-svn-id: https://sfml.svn.sourceforge.net/svnroot/sfml/trunk@1002 4e206d99-4929-0410-ac5d-dfc041789085
414 lines
14 KiB
D
414 lines
14 KiB
D
/*
|
|
* DSFML - SFML Library binding in D language.
|
|
* Copyright (C) 2008 Julien Dagorn (sirjulio13@gmail.com)
|
|
*
|
|
* This software is provided 'as-is', without any express or
|
|
* implied warranty. In no event will the authors be held
|
|
* liable for any damages arising from the use of this software.
|
|
*
|
|
* Permission is granted to anyone to use this software for any purpose,
|
|
* including commercial applications, and to alter it and redistribute
|
|
* it freely, subject to the following restrictions:
|
|
*
|
|
* 1. The origin of this software must not be misrepresented;
|
|
* you must not claim that you wrote the original software.
|
|
* If you use this software in a product, an acknowledgment
|
|
* in the product documentation would be appreciated but
|
|
* is not required.
|
|
*
|
|
* 2. Altered source versions must be plainly marked as such,
|
|
* and must not be misrepresented as being the original software.
|
|
*
|
|
* 3. This notice may not be removed or altered from any
|
|
* source distribution.
|
|
*/
|
|
|
|
module dsfml.network.packet;
|
|
|
|
import dsfml.system.common;
|
|
import dsfml.system.stringutil;
|
|
|
|
/**
|
|
* Packet wraps data to send / to receive through the network
|
|
*
|
|
* The order of insertion and extraction must be the same.
|
|
*
|
|
* You can derive from Packet and override onSend and onReceive to do custom operations before send or after reception.
|
|
*
|
|
* Litterals integer are promoted to int.
|
|
* Litterals floating point are promoted to float.
|
|
*
|
|
* Extraction or insertion can be specified with explicit template.
|
|
* Examples:
|
|
* ------------------------------------------------------------
|
|
* Packet p = new Packet();
|
|
*
|
|
* int i = 32, j = 42;
|
|
* char[] k = hello;
|
|
*
|
|
* p.set(i, k, j); //Set the data in the packet
|
|
*
|
|
* int a, b;
|
|
* char[] c;
|
|
* p.get(a, c, b); //Get data from the packet
|
|
*
|
|
* //...
|
|
*
|
|
* Packet p = new Packet();
|
|
* p.set!(byte)(5); // Litteral are inserted with byte type
|
|
* ------------------------------------------------------------
|
|
*
|
|
* See_Also:
|
|
* $(LINK2 http://www.digitalmars.com/d/1.0/lex.html, D litterals Specification) for more informations.
|
|
*/
|
|
class Packet : DSFMLObject
|
|
{
|
|
/**
|
|
* Default constructor
|
|
*
|
|
*/
|
|
this()
|
|
{
|
|
super(sfPacket_Create());
|
|
}
|
|
|
|
override void dispose()
|
|
{
|
|
sfPacket_Destroy(m_ptr);
|
|
}
|
|
|
|
/**
|
|
* Append data to the end of the packet.
|
|
*
|
|
* Params:
|
|
* data = Array of data to append
|
|
*
|
|
*/
|
|
void append(byte[] data)
|
|
{
|
|
if (data !is null)
|
|
sfPacket_Append(m_ptr, data.ptr, data.length);
|
|
}
|
|
|
|
/**
|
|
* Clear the packet data
|
|
*
|
|
*/
|
|
void clear()
|
|
{
|
|
sfPacket_Clear(m_ptr);
|
|
}
|
|
|
|
/**
|
|
* Get an array to the data contained in the packet
|
|
* $(B the returned array may be invalid after you
|
|
* append data to the packet)
|
|
*
|
|
* Returns:
|
|
* array of data
|
|
*
|
|
* Remarks:
|
|
* return an array of $(B all) data in the packet.
|
|
*
|
|
* ----------
|
|
* Packet p = new Packet();
|
|
*
|
|
* char[] str1 = "Hi";
|
|
* char[] str2 = "Hello";
|
|
*
|
|
* p.set(str1, str2);
|
|
*
|
|
* // Retrieve str1 from packet
|
|
* char[] str3;
|
|
* p.get(str3);
|
|
*
|
|
* // Returns an array containing str1 and str2.
|
|
* byte[] ptr = p.getData();
|
|
* ----------
|
|
*/
|
|
byte[] getData()
|
|
{
|
|
if (canRead)
|
|
return sfPacket_GetData(m_ptr)[0..getDataSize];
|
|
}
|
|
|
|
|
|
/**
|
|
* Get the size of the data contained in the packet
|
|
*
|
|
* Returns:
|
|
* Data size, in bytes
|
|
*/
|
|
uint getDataSize()
|
|
{
|
|
return sfPacket_GetDataSize(m_ptr);
|
|
}
|
|
|
|
/**
|
|
* Tell if the reading position has reached the end of the packet
|
|
*
|
|
* Returns:
|
|
* true if all data have been read.
|
|
*/
|
|
bool endOfPacket()
|
|
{
|
|
return cast(bool)sfPacket_EndOfPacket(m_ptr);
|
|
}
|
|
/**
|
|
* Tell if the packet is valid for reading
|
|
*
|
|
* Returns:
|
|
* True if data can be extracted from the packet
|
|
*
|
|
*/
|
|
bool canRead()
|
|
{
|
|
return cast(bool)sfPacket_CanRead(m_ptr);
|
|
}
|
|
|
|
|
|
/**
|
|
* Add new variables to the packet
|
|
* Accept (u)byte, (u)short, (u)int, float, double, char[] and wchar[] types
|
|
*/
|
|
Packet set(T...)(T t)
|
|
{
|
|
foreach (v; t)
|
|
internalSet(t);
|
|
return this;
|
|
}
|
|
|
|
/**
|
|
* Retrieve data from the packet
|
|
* Accept (u)byte, (u)short, (u)int, float, double, char[] and wchar[] types
|
|
*/
|
|
Packet get(T...)(ref T t)
|
|
{
|
|
foreach (v; t)
|
|
internalGet(t);
|
|
return this;
|
|
}
|
|
|
|
/**
|
|
* Called before packet is send
|
|
*
|
|
* Params:
|
|
* size = Variable to fill with the size of the data to send
|
|
* Returns:
|
|
* Array of byte to send
|
|
*/
|
|
byte[] onSend()
|
|
{
|
|
return getData();
|
|
}
|
|
|
|
/**
|
|
* Called after a packet has been received
|
|
*
|
|
* Params:
|
|
* data = Array of byte received
|
|
*/
|
|
void onReceive(byte[] data)
|
|
{
|
|
append(data);
|
|
}
|
|
|
|
private:
|
|
void internalGet(ref bool data)
|
|
{
|
|
data = cast(bool)sfPacket_ReadInt32(m_ptr);
|
|
}
|
|
void internalGet(ref byte data)
|
|
{
|
|
data = sfPacket_ReadInt8(m_ptr);
|
|
}
|
|
void internalGet(ref ubyte data)
|
|
{
|
|
data = sfPacket_ReadUint8(m_ptr);
|
|
}
|
|
void internalGet(ref short data)
|
|
{
|
|
data = sfPacket_ReadInt16(m_ptr);
|
|
}
|
|
void internalGet(ref ushort data)
|
|
{
|
|
data = sfPacket_ReadUint16(m_ptr);
|
|
}
|
|
void internalGet(ref int data)
|
|
{
|
|
data = sfPacket_ReadInt32(m_ptr);
|
|
}
|
|
void internalGet(ref uint data)
|
|
{
|
|
data = sfPacket_ReadUint32(m_ptr);
|
|
}
|
|
void internalGet(ref float data)
|
|
{
|
|
data = sfPacket_ReadFloat(m_ptr);
|
|
}
|
|
void internalGet(ref double data)
|
|
{
|
|
data = sfPacket_ReadDouble(m_ptr);
|
|
}
|
|
void internalGet(ref char[] data)
|
|
{
|
|
scope char[] temp = new char[sfPacket_GetDataSize(m_ptr)];
|
|
sfPacket_ReadString(m_ptr, temp.ptr);
|
|
size_t l = fromStringz(temp.ptr).length;
|
|
data = new char[l];
|
|
data[] = temp[0 .. l];
|
|
}
|
|
|
|
void internalGet(ref wchar[] data)
|
|
{
|
|
scope wchar[] temp = new wchar[sfPacket_GetDataSize(m_ptr)];
|
|
sfPacket_ReadWideString(m_ptr, temp.ptr);
|
|
size_t l = fromStringz(temp.ptr).length;
|
|
data = new wchar[l];
|
|
data[] = temp[0 .. l];
|
|
}
|
|
|
|
void internalSet(bool data)
|
|
{
|
|
sfPacket_WriteInt32(m_ptr, cast(int)data);
|
|
}
|
|
void internalSet(byte data)
|
|
{
|
|
sfPacket_WriteInt8(m_ptr, data);
|
|
}
|
|
void internalSet(ubyte data)
|
|
{
|
|
sfPacket_WriteUint8(m_ptr, data);
|
|
}
|
|
void internalSet(short data)
|
|
{
|
|
sfPacket_WriteInt16(m_ptr, data);
|
|
}
|
|
void internalSet(ushort data)
|
|
{
|
|
sfPacket_WriteUint16(m_ptr, data);
|
|
}
|
|
void internalSet(int data)
|
|
{
|
|
sfPacket_WriteInt32(m_ptr, data);
|
|
}
|
|
void internalSet(uint data)
|
|
{
|
|
sfPacket_WriteUint32(m_ptr, data);
|
|
}
|
|
void internalSet(float data)
|
|
{
|
|
sfPacket_WriteFloat(m_ptr, data);
|
|
}
|
|
void internalSet(double data)
|
|
{
|
|
sfPacket_WriteDouble(m_ptr, data);
|
|
}
|
|
void internalSet(char[] data)
|
|
{
|
|
sfPacket_WriteString(m_ptr, toStringz(data));
|
|
}
|
|
|
|
void internalSet(wchar[] data)
|
|
{
|
|
sfPacket_WriteWideString(m_ptr, toStringz(data));
|
|
}
|
|
|
|
// External ====================================================================
|
|
|
|
extern (C)
|
|
{
|
|
typedef void* function() pf_sfPacket_Create;
|
|
typedef void function(void*) pf_sfPacket_Destroy;
|
|
typedef void function(void*, void*, size_t) pf_sfPacket_Append;
|
|
typedef void function(void*) pf_sfPacket_Clear;
|
|
typedef byte* function(void*) pf_sfPacket_GetData;
|
|
typedef uint function(void*) pf_sfPacket_GetDataSize;
|
|
typedef int function(void*) pf_sfPacket_EndOfPacket;
|
|
typedef int function(void*) pf_sfPacket_CanRead;
|
|
typedef byte function(void*) pf_sfPacket_ReadInt8;
|
|
typedef ubyte function(void*) pf_sfPacket_ReadUint8;
|
|
typedef short function(void*) pf_sfPacket_ReadInt16;
|
|
typedef ushort function(void*) pf_sfPacket_ReadUint16;
|
|
typedef int function(void*) pf_sfPacket_ReadInt32;
|
|
typedef uint function(void*) pf_sfPacket_ReadUint32;
|
|
typedef float function(void*) pf_sfPacket_ReadFloat;
|
|
typedef double function(void*) pf_sfPacket_ReadDouble;
|
|
typedef void function(void*, char*) pf_sfPacket_ReadString;
|
|
typedef void function(void*, wchar*) pf_sfPacket_ReadWideString;
|
|
typedef void function(void*, byte) pf_sfPacket_WriteInt8;
|
|
typedef void function(void*, ubyte) pf_sfPacket_WriteUint8;
|
|
typedef void function(void*, short) pf_sfPacket_WriteInt16;
|
|
typedef void function(void*, ushort) pf_sfPacket_WriteUint16;
|
|
typedef void function(void*, int) pf_sfPacket_WriteInt32;
|
|
typedef void function(void*, uint) pf_sfPacket_WriteUint32;
|
|
typedef void function(void*, float) pf_sfPacket_WriteFloat;
|
|
typedef void function(void*, double) pf_sfPacket_WriteDouble;
|
|
typedef void function(void*, char*) pf_sfPacket_WriteString;
|
|
typedef void function(void*, wchar*) pf_sfPacket_WriteWideString;
|
|
|
|
static pf_sfPacket_Create sfPacket_Create;
|
|
static pf_sfPacket_Destroy sfPacket_Destroy;
|
|
static pf_sfPacket_Append sfPacket_Append;
|
|
static pf_sfPacket_Clear sfPacket_Clear;
|
|
static pf_sfPacket_GetData sfPacket_GetData;
|
|
static pf_sfPacket_GetDataSize sfPacket_GetDataSize;
|
|
static pf_sfPacket_EndOfPacket sfPacket_EndOfPacket;
|
|
static pf_sfPacket_CanRead sfPacket_CanRead;
|
|
static pf_sfPacket_ReadInt8 sfPacket_ReadInt8;
|
|
static pf_sfPacket_ReadUint8 sfPacket_ReadUint8;
|
|
static pf_sfPacket_ReadInt16 sfPacket_ReadInt16;
|
|
static pf_sfPacket_ReadUint16 sfPacket_ReadUint16;
|
|
static pf_sfPacket_ReadInt32 sfPacket_ReadInt32;
|
|
static pf_sfPacket_ReadUint32 sfPacket_ReadUint32;
|
|
static pf_sfPacket_ReadFloat sfPacket_ReadFloat;
|
|
static pf_sfPacket_ReadDouble sfPacket_ReadDouble;
|
|
static pf_sfPacket_ReadString sfPacket_ReadString;
|
|
static pf_sfPacket_ReadWideString sfPacket_ReadWideString;
|
|
static pf_sfPacket_WriteInt8 sfPacket_WriteInt8;
|
|
static pf_sfPacket_WriteUint8 sfPacket_WriteUint8;
|
|
static pf_sfPacket_WriteInt16 sfPacket_WriteInt16;
|
|
static pf_sfPacket_WriteUint16 sfPacket_WriteUint16;
|
|
static pf_sfPacket_WriteInt32 sfPacket_WriteInt32;
|
|
static pf_sfPacket_WriteUint32 sfPacket_WriteUint32;
|
|
static pf_sfPacket_WriteFloat sfPacket_WriteFloat;
|
|
static pf_sfPacket_WriteDouble sfPacket_WriteDouble;
|
|
static pf_sfPacket_WriteString sfPacket_WriteString;
|
|
static pf_sfPacket_WriteWideString sfPacket_WriteWideString;
|
|
}
|
|
|
|
static this()
|
|
{
|
|
DllLoader dll = DllLoader.load("csfml-network");
|
|
|
|
sfPacket_Append = cast(pf_sfPacket_Append)dll.getSymbol("sfPacket_Append");
|
|
sfPacket_CanRead = cast(pf_sfPacket_CanRead)dll.getSymbol("sfPacket_CanRead");
|
|
sfPacket_Clear = cast(pf_sfPacket_Clear)dll.getSymbol("sfPacket_Clear");
|
|
sfPacket_Create = cast(pf_sfPacket_Create)dll.getSymbol("sfPacket_Create");
|
|
sfPacket_Destroy = cast(pf_sfPacket_Destroy)dll.getSymbol("sfPacket_Destroy");
|
|
sfPacket_EndOfPacket = cast(pf_sfPacket_EndOfPacket)dll.getSymbol("sfPacket_EndOfPacket");
|
|
sfPacket_GetData = cast(pf_sfPacket_GetData)dll.getSymbol("sfPacket_GetData");
|
|
sfPacket_GetDataSize = cast(pf_sfPacket_GetDataSize)dll.getSymbol("sfPacket_GetDataSize");
|
|
sfPacket_ReadDouble = cast(pf_sfPacket_ReadDouble)dll.getSymbol("sfPacket_ReadDouble");
|
|
sfPacket_ReadFloat = cast(pf_sfPacket_ReadFloat)dll.getSymbol("sfPacket_ReadFloat");
|
|
sfPacket_ReadInt16 = cast(pf_sfPacket_ReadInt16)dll.getSymbol("sfPacket_ReadInt16");
|
|
sfPacket_ReadInt32 = cast(pf_sfPacket_ReadInt32)dll.getSymbol("sfPacket_ReadInt32");
|
|
sfPacket_ReadInt8 = cast(pf_sfPacket_ReadInt8)dll.getSymbol("sfPacket_ReadInt8");
|
|
sfPacket_ReadString = cast(pf_sfPacket_ReadString)dll.getSymbol("sfPacket_ReadString");
|
|
sfPacket_ReadWideString = cast(pf_sfPacket_ReadWideString)dll.getSymbol("sfPacket_ReadWideString");
|
|
sfPacket_ReadUint16 = cast(pf_sfPacket_ReadUint16)dll.getSymbol("sfPacket_ReadUint16");
|
|
sfPacket_ReadUint32 = cast(pf_sfPacket_ReadUint32)dll.getSymbol("sfPacket_ReadUint32");
|
|
sfPacket_ReadUint8 = cast(pf_sfPacket_ReadUint8)dll.getSymbol("sfPacket_ReadUint8");
|
|
sfPacket_WriteDouble = cast(pf_sfPacket_WriteDouble)dll.getSymbol("sfPacket_WriteDouble");
|
|
sfPacket_WriteFloat = cast(pf_sfPacket_WriteFloat)dll.getSymbol("sfPacket_WriteFloat");
|
|
sfPacket_WriteInt16 = cast(pf_sfPacket_WriteInt16)dll.getSymbol("sfPacket_WriteInt16");
|
|
sfPacket_WriteInt32 = cast(pf_sfPacket_WriteInt32)dll.getSymbol("sfPacket_WriteInt32");
|
|
sfPacket_WriteInt8 = cast(pf_sfPacket_WriteInt8)dll.getSymbol("sfPacket_WriteInt8");
|
|
sfPacket_WriteString = cast(pf_sfPacket_WriteString)dll.getSymbol("sfPacket_WriteString");
|
|
sfPacket_WriteWideString = cast(pf_sfPacket_WriteWideString)dll.getSymbol("sfPacket_WriteWideString");
|
|
sfPacket_WriteUint16 = cast(pf_sfPacket_WriteUint16)dll.getSymbol("sfPacket_WriteUint16");
|
|
sfPacket_WriteUint32 = cast(pf_sfPacket_WriteUint32)dll.getSymbol("sfPacket_WriteUint32");
|
|
sfPacket_WriteUint8 = cast(pf_sfPacket_WriteUint8)dll.getSymbol("sfPacket_WriteUint8");
|
|
}
|
|
}
|