1. 首先下载Raknet的源代码,我用的是4.0的,不是最新的,解压后编译DLL工程,编译完成后进入解压的根目录下,进入Lib文件夹下找到RakNet_DLL_Debug_Win32.dll,  RakNet_DLL_Debug_Win32.lib这两个库文件,并将其关联到工程中。

2. 将解压目录下Source文件夹下的资源也管理到你的工程中

进行完上面两步就将网络库配置完成,下面便开始服务器端与客户端的程序编写

// 服务器端程序

#include <string>
#include <sstream>
#include <iostream>
#include "raknet/RakPeerInterface.h"
#include "raknet/RakNetTypes.h"
#include "raknet/MessageIdentifiers.h" // RakNet自定义消息枚举定义处
#include "raknet/BitStream.h" // RakNet消息包的Bit数据流 #define MAX_CLIENTS 10
#define SERVER_PORT 60000
enum ChatMessagesDefine
{// 自定义消息枚举值,消息ID
MSG_CHATWORD = ID_USER_PACKET_ENUM + , // 消息ID从RakNet定义的最后一个枚举开始
}; // 服务器端程序
int _tmain(int argc, _TCHAR* argv[])
{
// 给服务器端创建一个实例
RakNet::RakPeerInterface* pPeer = RakNet::RakPeerInterface::GetInstance();
if ( NULL == pPeer )
{
std::cout << "RakNet::RakPeerInterface::GetInstance() Error!" << std::endl << std::endl;
return -;
}
else
{
std::cout << "--------- MyServer Init Success -----------" << std::endl << std::endl;
} RakNet::Packet* pPacket;
std::cout << "Start Server ......" << std::endl << std::endl;
//启动服务器
pPeer->Startup( MAX_CLIENTS, &RakNet::SocketDescriptor( SERVER_PORT, ), ); //设置最大链接数
pPeer->SetMaximumIncomingConnections( MAX_CLIENTS ); //////////////////////////////////////////////////////////////////////////
while ( )
{
for ( pPacket = pPeer->Receive(); pPacket; pPeer->DeallocatePacket( pPacket ), pPacket = pPeer->Receive() )
{
switch ( pPacket->data[] )
{
case ID_REMOTE_DISCONNECTION_NOTIFICATION:
std::cout << "Another client has disconnected !" << std::endl;
break;
case ID_REMOTE_CONNECTION_LOST:
std::cout << "Another client has lost the connection !" << std::endl;
break;
case ID_REMOTE_NEW_INCOMING_CONNECTION:
std::cout << "Another client has connected !" << std::endl;
break; case ID_CONNECTION_REQUEST_ACCEPTED: //
//{
// std::cout << "Our connection request has been accepted !" << std::endl; // RakNet::BitStream bsOut;
// bsOut.Write( ( RakNet::MessageID )MSG_CHATWORD );
// bsOut.Write("Hello world");
// pPeer->Send( &bsOut, HIGH_PRIORITY, RELIABLE_ORDERED, 0, pPacket->systemAddress, false );
//}
break; case ID_NEW_INCOMING_CONNECTION:
{
std::cout << "Our connection request has been accepted !" << std::endl; RakNet::BitStream bsOut;
bsOut.Write( ( RakNet::MessageID )MSG_CHATWORD );
bsOut.Write("Hello world ! I'm successed ! Congratulations !");
pPeer->Send( &bsOut, HIGH_PRIORITY, RELIABLE_ORDERED, , pPacket->systemAddress, false );
}
std::cout << "A connection is incoming !" << std::endl;
break;
case ID_NO_FREE_INCOMING_CONNECTIONS:
std::cout << "The server is full !" << std::endl;
break;
case ID_DISCONNECTION_NOTIFICATION:
std::cout << "A client has disconnected !" << std::endl;
break;
case ID_CONNECTION_LOST:
std::cout << "A client lost the connection !" << std::endl;
break; //用户自定义数据包
case MSG_CHATWORD:
{
RakNet::RakString rs;
RakNet::BitStream bsIn( pPacket->data, pPacket->length, false );
bsIn.IgnoreBytes( sizeof(RakNet::MessageID) );
bsIn.Read( rs ); //提取字符串
std::istringstream input_str(rs.C_String()); //存入字符串流
double v, h;
input_str >> v >> h; //提取想要的变量
std::cout << v << " " << h << std::endl; //打印结果
}
break; default:
std::cout << "Message with identifier %i has arrived !" << pPacket->data[ ] << std::endl;
break;
}
}
} //////////////////////////////////////////////////////////////////////////
RakNet::RakPeerInterface::DestroyInstance( pPeer ); /*
//创建一个实例
RakNet::RakPeerInterface *server = RakNet::RakPeerInterface::GetInstance(); //创建套接字描述,也就是指定一个通信端口(UDP无监听)
RakNet::SocketDescriptor socketDescriptor;
socketDescriptor.port = 30050; //启动服务器端
bool b = server->Startup(2, &socketDescriptor, 1 )== RakNet::RAKNET_STARTED; //如果没有报错,服务端启动成功了。
RakAssert(b); if ( b )
{
printf( "服务器启动成功!\n\n等待客户端的请求......\n\n" );
}
else
{
printf( "服务器启动失败!\n\n请重新启动服务器!\n\n" );
} //设置最大连接数(此连接并不等同TCP的连接!),这一步必须设置,否则会出现客户端调用Connect失败
server->SetMaximumIncomingConnections(2); //接下来就是处理数据发送接收的部分了
while( 1 )
{
RakNet::Packet * packet = server->Receive();
if( packet )
{
switch( packet->data[0] )
{
//用户自定义数据包的接收处理,此处显示接到的数据包内容。其他消息的处理可以同样用case语句
case ID_USER_PACKET_ENUM:
printf("接收到自定义数据,内容: %s\n\n", packet->data );
break;
default:
break;
}
}
}
*/
return ;
}

// 客户端程序

#include <string>
#include <sstream>
#include <iostream> #include "raknet/RakPeerInterface.h"
#include "raknet/RakNetTypes.h"
#include "raknet/MessageIdentifiers.h"
#include "raknet/BitStream.h" #define MAX_CLIENTS 10
#define SERVER_PORT 60000 enum ChatMessagesDefine
{// 自定义消息枚举值,消息ID
MSG_CHATWORD = ID_USER_PACKET_ENUM + , // 消息ID从RakNet定义的最后一个枚举开始
}; // 客户端程序
int _tmain(int argc, _TCHAR* argv[])
{
double v = 1000.023;
double h = 10023.23;
RakNet::RakPeerInterface *peer = RakNet::RakPeerInterface::GetInstance(); RakNet::SocketDescriptor sd;
peer->Startup(, &sd, ); // 作为客户端连接,连接到主机ip地址和端口号
peer->Connect("127.0.0.1", SERVER_PORT, , ); float k = ;
int i = ;
for ( i = ; i < ; i++ )
{
// 给主机发送数据
RakNet::BitStream bsOut;
bsOut.Write( (RakNet::MessageID)MSG_CHATWORD );
std::ostringstream format_messege;
format_messege << v++ << " " << h++; // 输入信息到字符串流,用空格隔开,此处为飞行器速度高度V, h为double型
// bsOut.Write("hello");
std::string ss = format_messege.str(); // str()返回的是临时对象
bsOut.Write( ss.c_str() );
peer->Send( &bsOut, HIGH_PRIORITY, RELIABLE_ORDERED, , RakNet::UNASSIGNED_SYSTEM_ADDRESS, true );
Sleep( );
} RakNet::Packet * packet;
while( )
{
packet = peer->Receive();
if( packet )
{
// 当接收到的消息的第一个字节的数据为 ID_CONNECTION_REQUEST_ACCEPTED 才表示服务端接受了连接请求!!!
if( packet->data[] == MSG_CHATWORD )
{
RakNet::RakString rs;
RakNet::BitStream bsIn( packet->data, packet->length, false );
bsIn.IgnoreBytes(sizeof(RakNet::MessageID));
bsIn.Read( rs );
printf("server return = %s", rs.C_String() );
}
}
} //断开连接,这个会给对方发送一个消息,告诉它要断开连接了。
peer->Shutdown( ); RakNet::RakPeerInterface::DestroyInstance(peer); /*
RakNet::RakPeerInterface *client = RakNet::RakPeerInterface::GetInstance(); RakNet::SocketDescriptor socketDescriptor;
socketDescriptor.port = 0; client->Startup(1, &socketDescriptor, 1 ); // 客户端连接服务端,判断返回值和RakNet::CONNECTION_ATTEMPT_STARTED是否相等,
// 相等只是代表请求投递成功,并不意味着服务端接收了连接请求
bool rs = ( client->Connect("127.0.0.1", 30050, NULL, 0, 0) == RakNet::CONNECTION_ATTEMPT_STARTED ); // 数据包
RakNet::Packet *packet; bool bIsConn = false; // 循环接收来自服务端的消息
while(1)
{
packet = client->Receive();
if( packet )
{
// 当接收到的消息的第一个字节的数据为 ID_CONNECTION_REQUEST_ACCEPTED 才表示服务端接受了连接请求!!!
if( packet->data[0] == ID_CONNECTION_REQUEST_ACCEPTED )
{
bIsConn = true;
printf("服务器端受理了客户端的请求!\n\n"); char flag = (char)ID_USER_PACKET_ENUM;
char buffer[ ] = "这是来自客户端的消息";
buffer[ 0 ] = flag; //连接ok后发送一个字符串到服务端
uint32_t sendrs = client->Send( (const char*)buffer,
strlen(buffer)+1,
HIGH_PRIORITY,
RELIABLE_ORDERED,
0,
RakNet::UNASSIGNED_SYSTEM_ADDRESS,
true );
printf("服务器端返回来的消息: %d\n",sendrs);
} //如果没有连接成功,则继续连接,直到服务端返回的信息告诉我们连接成功了
if( !bIsConn )
{
printf("连接服务器失败!\n");
client->Connect("127.0.0.1", 30050, NULL, 0, 0);
}
}
}
*/
system( "pause");
return ;
}

ps: 下面是将网络库关联到你的工程中

1.右键工程--》属性--》c/c++ --》常规--》"附加包含目录",将源文件和上面的两个文件包含进去

2.右键工程--》属性--》链接器 --》常规--》"附加包含目录",将源文件和上面的两个文件包含进去

3.右键工程--》属性--》链接器 --》输入--》"附加依赖项",添加 RakNet_DLL_Debug_Win32.lib 库

Raknet实现的简单服务器与客户端的交互的更多相关文章

  1. Socket创建简单服务器和客户端程序

    使用Socket编程创建简单服务器和客户端 要知道的 Socket-AddressFamily, SocketType, ProtocolType https://blog.csdn.net/weix ...

  2. 实现服务器和客户端数据交互,Java Socket有妙招

    摘要:在Java SDK中,对于Socket原生提供了支持,它分为ServerSocket和Socket. 本文分享自华为云社区<Java Socket 如何实现服务器和客户端数据交互>, ...

  3. python3实现UDP协议的简单服务器和客户端

    利用python中的socket模块中的来实现UDP协议,这里写一个简单的服务器和客户端.为了说明网络编程中UDP的应用,这里就不写图形化了,在两台电脑上分别打开UDP的客户端和服务端就可以了. UD ...

  4. python3实现TCP协议的简单服务器和客户端

    利用python3来实现TCP协议,和UDP类似.UDP应用于及时通信,而TCP协议用来传送文件.命令等操作,因为这些数据不允许丢失,否则会造成文件错误或命令混乱.下面代码就是模拟客户端通过命令行操作 ...

  5. 基于asp.net MVC 的服务器和客户端的交互(一)

    架构思想 三层架构 提出了一种基于ASP.NET开发方式的三层架构的Web应用系统构造思想.其基本内容是:将面向对象的UML建模与Web应用系统开发 相结合,将整个系统分成适合ASP.NET开发方式的 ...

  6. 基于asp.net MVC 的服务器和客户端的交互(三)之客户端请求响应

    一.分析 WEB API 中HTTP 请求方式的四个主要方法 (GET, PUT, POST, DELETE), 按照下列方式映射为 CURD 操作: GET 用于获取 URI 资源的进行展示,GET ...

  7. 基于asp.net MVC 的服务器和客户端的交互(二)之获取Oauth 2.0认证权限

    基本Web API的ASP.NET的Oauth2认证 增加Token额外字段 增加Scope授权字段 持久化Token 设计Token的时间间隔 刷新Token后失效老的Token 自定义验证[重启I ...

  8. Linux系统编程(34)—— socket编程之TCP服务器与客户端的交互

    前面几篇中实现的client每次运行只能从命令行读取一个字符串发给服务器,再从服务器收回来,现在我们把它改成交互式的,不断从终端接受用户输入并和server交互. /* client.c */ #in ...

  9. Socket实现服务器与客户端的交互

       连接过程:   根据连接启动的方式以及本地套接字要连接的目标,套接字之间的连接过程可以分为三个步骤:服务器监听,客户端请求,连接确认. (1)服务器监听:是服务器端套接字并不定位具体的客户端套接 ...

随机推荐

  1. Tomcat学习笔记 - 错误日志 - Tomcat安装版安装后第二次启动后闪退(转)-- javac不是内部或外部命令 -- 配置java环境教程

    如果安装成功并且安装完成第一次启动是成功的,第二次就闪退的话,原因之一是没有配置java的环境.在网上找的配制方法有很多错误,测试javac命令时候会提示不是内部或外部命令,找到一个正确的教程.如下, ...

  2. js 函数声明与函数表达式

      1,变量包括全局变量和局部变量,局部变量只能在函数内部访问.如果函数传参和全局变量一样的话,即使是给全局变量赋值,这里会把全局变量当成局部变量的. 如: 1: var x='x'; 2:   3: ...

  3. [C++程序设计]内置函数

    注意: 可以在声明函数和定义函数时同时写 inline,也可以只在其中一处声明inline,效果相同,都能按内置函数处理. 使用内置函数可以节省运行时间,但却增加了目标 程序的长度.因此一般只将规模很 ...

  4. Web框架-Django基础

    一.django简介 Django是一个开放源代码的Web应用框架,由Python写成.采用了MVC的软件设计模式,即模型M,视图V和控制器C.它最初是被开发来用于管理劳伦斯出版集团旗下的一些以新闻内 ...

  5. java类中的static成员变量和static方法简单介绍,持续补充

    一.静态成员变量 1.属于整个类而不是某个对象实例,所以可以直接通过类名和对象名去调用. 2.静态成员属于整个类,当系统第一次使用该类时,就会为其分配内存空间直到该类被卸载才会进行资源回收 二.静态方 ...

  6. linux开启mysql远程登录

    Mysql默认root用户只能本地访问,不能远程连接管理mysql数据库,Linux如何开启mysql远程连接?设置步骤如下:1.GRANT命令创建远程连接mysql授权用户itloggermysql ...

  7. ASP.NET用户自定义控件配置

    一直以来开发中碰到要写自定义控件的时候总是习惯性的找度娘,而没有自己记住,结果今天就悲剧了,找了半天才找到,想想还是自己积累起来吧! 第一种配置方式: 配置写在webconfig文件中,位置如下: w ...

  8. 用JSON 和 Google 实现全文翻译

    unit Unit1; interface uses Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms ...

  9. 瑞柏匡丞:App对新媒体的影响

    当下App的迅猛发展是媒体进入开放平台时代的折射,作为最具新媒体特质的代表,App充满了社交性与交互性,并有效整合了传统媒体和新媒体的内容和服务.“什么是新媒体”——这个新媒体时代最为核心的命题,实际 ...

  10. web前端设计:JQuery MINI UI

    JQuery MINIUI 个人感觉用起来很爽,所以在此记录之,以后开发过程可能作为备选项.它能缩短开发时间,减少代码量,使开发者更专注于业务和服务端,轻松实现界面开发,带来绝佳的用户体验.在线下载地 ...