UE5 C++的TCP服务器与客户端
创始人
2024-09-26 05:47:24
0

 客户端.h

需要在Build.cs中加入模块:"Networking","Sockets","Json","JsonUtilities"

// Fill out your copyright notice in the Description page of Project Settings.  #pragma once  #include "CoreMinimal.h" #include "GameFramework/Actor.h" #include "ClientActorClass.generated.h"  UCLASS() class TCPSERVERANDCLIENT_API AClientActorClass : public AActor { 	GENERATED_BODY()  public: 	// Sets default values for this actor's properties 	AClientActorClass();  protected: 	// Called when the game starts or when spawned 	virtual void BeginPlay() override;  public: 	// Called every frame 	virtual void Tick(float DeltaTime) override;  	static FSocket* Socket;  	//"Networking","Sockets" 	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static bool ClientConnectToTCPServer(const FString& IP,int32 Port = 8888);  	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static bool SendDataFormClicentToServer(TArray SendData);  	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static bool DisConnectFormClientToServer();  	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static TArray ReceiveDataFromTCPServer();  	//"Json","JsonUtilities" 	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static void StringToBytes(FString InString,bool& OutBool,TArray& OutBytesArray);  	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static void DataTypeToJSON(int32 Int,bool Inbool,FString String,FVector Vector,TArray Array,bool& OutBool,TArray& OutBytesArray);  	UFUNCTION(BlueprintCallable,Category = "TCPServerAndClient") 	static void BytesToString(TArray InBytesArray,FString& OutString); }; 

 客户端.cpp

// Fill out your copyright notice in the Description page of Project Settings.   #include "ClientActorClass.h"  #include "Sockets.h" #include "Internationalization/Text.h" #include "Misc/OutputDevice.h" #include "Internationalization/Internationalization.h" #include "Common/TcpSocketBuilder.h"  FSocket* AClientActorClass::Socket = nullptr; // Sets default values AClientActorClass::AClientActorClass() { 	// Set this actor to call Tick() every frame.  You can turn this off to improve performance if you don't need it. 	PrimaryActorTick.bCanEverTick = true; }  // Called when the game starts or when spawned void AClientActorClass::BeginPlay() { 	Super::BeginPlay(); 	 }  // Called every frame void AClientActorClass::Tick(float DeltaTime) { 	Super::Tick(DeltaTime); }  bool AClientActorClass::ClientConnectToTCPServer(const FString& IP, int32 Port) { 	if (Socket) 	{ 		Socket->Close(); 		ISocketSubsystem::Get(PLATFORM_SOCKETSUBSYSTEM)->DestroySocket(Socket); 		Socket = nullptr; 	}  	TSharedPtr Addr = ISocketSubsystem::Get(PLATFORM_SOCKETSUBSYSTEM)->CreateInternetAddr(); 	bool bIsValid; 	Addr->SetIp(*IP,bIsValid); 	Addr->SetPort(Port);  	if (!bIsValid) 	{ 		UE_LOG(LogTemp,Log,TEXT("InValid IP Address")); 		GEngine->AddOnScreenDebugMessage(-1,5.0f,FColor::Red,TEXT("InValid IP Address")); 		return false; 	} 	Socket = FTcpSocketBuilder(TEXT("TcpClient")).AsBlocking().WithReceiveBufferSize(2*1024*1024);  	bool bConnected = Socket->Connect(*Addr); 	if (!bConnected) 	{ 		UE_LOG(LogTemp,Log,TEXT("Failed Connect To Server")); 		GEngine->AddOnScreenDebugMessage(-1,5.0,FColor::Green,TEXT("Failed Connect To Server")); 		return false; 	} 	UE_LOG(LogTemp,Log,TEXT("Success Connect To Server")); 	GEngine->AddOnScreenDebugMessage(-1,5.0,FColor::Green,TEXT("Success Connect To Server"));  	return true; 	 }  bool AClientActorClass::SendDataFormClicentToServer(TArray SendData) { 	if (!Socket) 	{ 		UE_LOG(LogTemp, Log, TEXT("Socket is not connected!")); 		return false; 	}  	// 发送数据部分 	int32 SentBytes = 0; 	bool bSuccess = Socket->Send(SendData.GetData(), SendData.Num(), SentBytes);  	if (!bSuccess || SentBytes != SendData.Num()) 	{ 		UE_LOG(LogTemp, Log, TEXT("Failed to send data!")); 		return false; 	} 	GEngine->AddOnScreenDebugMessage(-1,5.0,FColor::Green,TEXT("Success to send data!")); 	UE_LOG(LogTemp, Log, TEXT("Success to send data!")); 	return true; }  bool AClientActorClass::DisConnectFormClientToServer() { 	if (Socket) 	{ 		Socket->Close(); 		ISocketSubsystem::Get(PLATFORM_SOCKETSUBSYSTEM)->DestroySocket(Socket); 		Socket = nullptr; 		return true; 	} 	return false; }  TArray AClientActorClass::ReceiveDataFromTCPServer() { 	TArray Bytes;  	if (Socket) 	{ 		uint32 Size; 		while (Socket->HasPendingData(Size)) 		{ 			Bytes.SetNumUninitialized(FMath::Min(Size, 65507u));  			int32 ReadBytes = 0; 			// 读取数据到字节流中 			Socket->Recv(Bytes.GetData(), Bytes.Num(), ReadBytes);  			// 将实际读取的部分截取出来 			Bytes.SetNum(ReadBytes);  			// 如果需要等待接收完整数据再返回,可以设置一个条件,比如接收到特定结束标志 			// 如果已经接收到完整数据,可以直接返回 			return Bytes; 		} 	}  	// 如果没有接收到数据,返回空字节流 	return TArray(); }  void AClientActorClass::StringToBytes(FString InString, bool& OutBool, TArray& OutBytesArray) { 	OutBytesArray.Empty(); 	 	if (!InString.IsEmpty()) 	{ 		FTCHARToUTF8 Converter(*InString); 		int32 NumBytes = Converter.Length(); 		if (NumBytes > 0) 		{ 			OutBytesArray.Append((uint8*)Converter.Get(), NumBytes); 			OutBool = true; 		} 		else 		{ 			OutBool = false; 		} 	} 	else 	{ 		OutBool = false; 	} }  void AClientActorClass::DataTypeToJSON(int32 Int, bool Inbool, FString String, FVector Vector, TArray Array, 	bool& OutBool, TArray& OutBytesArray) { 	OutBytesArray.Empty(); 	 	TSharedPtr JsonObject = MakeShareable(new FJsonObject);  	JsonObject->SetNumberField("MyInteger",Int); 	JsonObject->SetBoolField("MyBool",Inbool); 	JsonObject->SetStringField("MyString",String);  	TSharedPtr VectorObject = MakeShareable(new FJsonObject); 	JsonObject->SetNumberField("MyVector",Vector.X); 	JsonObject->SetNumberField("MyVector",Vector.Y); 	JsonObject->SetNumberField("MyVector",Vector.Z);  	JsonObject->SetObjectField("MyVector",VectorObject); 	 	TArray> JsonArray; 	for (auto& value : Array) 	{ 		JsonArray.Add(MakeShareable(new FJsonValueNumber(value)));		 	} 	JsonObject->SetArrayField("Array",JsonArray);  	// 将 JSON 对象转换为字符串   	FString OutputString; 	TSharedRef> Writer = TJsonWriterFactory<>::Create(&OutputString); 	if (FJsonSerializer::Serialize(JsonObject.ToSharedRef(), Writer)) 	{ 		Writer->Close();  		// 将字符串转换为字节数组   		FTCHARToUTF8 Converter(*OutputString); 		int32 NumBytes = Converter.Length(); 		if (NumBytes > 0) 		{ 			OutBytesArray.Append((uint8*)Converter.Get(), NumBytes); 			OutBool = true; 		} 		else 		{ 			OutBool = false; 		} 	} 	else 	{ 		OutBool = false; 	} }  void AClientActorClass::BytesToString(TArray InBytesArray, FString& OutString) { 	// 检查字节数组是否为空 	if (InBytesArray.Num() == 0) 	{ 		OutString.Empty(); 		GEngine->AddOnScreenDebugMessage(-1, 2.0, FColor::Blue, TEXT("data = null")); 		UE_LOG(LogTemp, Log, TEXT("data = null")); 		return; 	}  	// 将字节流转换为UTF-8字符串 	FString Utf8String = FUTF8ToTCHAR(reinterpret_cast(InBytesArray.GetData()), InBytesArray.Num()).Get();  	// 在这里你可以使用Utf8String进行其他操作,例如将其转换为JSON对象 	// 注意:在UE5中,你可能需要使用FJsonSerializer的Deserialize方法 	TSharedPtr JsonObject; 	TSharedRef> Reader = TJsonReaderFactory<>::Create(Utf8String);  	// Deserialize JSON 	if (FJsonSerializer::Deserialize(Reader, JsonObject)) 	{ 		// 在这里可以使用JsonObject进行其他操作 	} 	else 	{ 		// JSON解析失败的处理 		UE_LOG(LogTemp, Error, TEXT("Failed to parse JSON from string")); 	}  	// 将最终的JSON字符串赋值给输出参数 	OutString = Utf8String; }  

相关内容

热门资讯

透视好牌!aapoker透视脚... 透视好牌!aapoker透视脚本,aapoker辅助插件工具,wpk教程(有挂方法);进入游戏-大厅...
透视计算!hhpoker辅助靠... 透视计算!hhpoker辅助靠谱吗,hh poker辅助有用吗,必赢方法(有挂介绍);1、玩家可以在...
透视好牌!wepoker私局代... 透视好牌!wepoker私局代打,wepoker分析(一直是有挂)1、进入到wepoker私局代打黑...
透视挂透视!aapoker怎么... 透视挂透视!aapoker怎么开辅助器,aapoker真的假的,解密教程(有挂方法)在进入aapok...
透视有挂!hhpoker破解工... 透视有挂!hhpoker破解工具,hhpoker德州作弊,攻略教程(有挂揭秘)暗藏猫腻,小编详细说明...
透视神器!wepoker私人局... 透视神器!wepoker私人局有透视吗,we poker辅助器下载(切实真的有挂);1)wepoke...
透视神器!aa poker透视... 透视神器!aa poker透视软件,aapoker怎么选牌,教你教程(有挂规律)aa poker透视...
透视新版!hhpoker脚本下... 透视新版!hhpoker脚本下载,hhpoker是真的假的,wpk教程(有挂解说)小薇(透视辅助)致...
辅助透视!wepoker轻量版... 辅助透视!wepoker轻量版有透视吗,wepoker辅助器如何使用(竟然真的有挂);1、每一步都需...
透视教程!aapoker透视脚... 透视教程!aapoker透视脚本入口,aapoker免费透视脚本,辅助教程(有挂详情)1、构建自己的...