//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "SendFile_Cpp.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TSendFiles *SendFiles;
//---------------------------------------------------------------------------
__fastcall TSendFiles::TSendFiles(TComponent* Owner)
: TForm(Owner)
{
FullFileName=new TStringList();//要发送的全路经文件名
FSTimeOut=0; //命令超时计数器
BuildTable16(cnCRC_CCITT); //建立CRC校验表
SleepTime=30;
}
//---------------------------------------------------------------------------
//****************设置文件保存路径******************
void __fastcall TSendFiles::Button5Click(TObject *Sender)
{
AnsiString Dir0 = "";
if (SelectDirectory(Dir0, TSelectDirOpts() << sdAllowCreate << sdPerformCreate << sdPrompt,0)) Dir->Text = Dir0;
}
//---------------------------------------------------------------------------
//****************完成设置,返回主画面***************
void __fastcall TSendFiles::Button4Click(TObject *Sender)
{
Notebook1->ActivePage="Main";
}
//---------------------------------------------------------------------------
//****************进入设置画面*******************
void __fastcall TSendFiles::SetUpClick(TObject *Sender)
{
Notebook1->ActivePage="SetUp";
}
//---------------------------------------------------------------------------
//****************添加按钮事件*******************
void __fastcall TSendFiles::AddClick(TObject *Sender)
{
AnsiString FileName,TempName; //文件名
if (OpenDialog1->Execute()) //打开文件对话框
{
for (int i=0;i<OpenDialog1->Files->Count;i++)
{
TempName=OpenDialog1->Files->Strings[i]; //取出全路经文件名
FullFileName->Add(TempName); //保存
FileName=ExtractFileName(TempName); //取出无路经文件名
ListView1->AddItem(FileName,NULL); //在ListView中显示
}
Sent->Enabled=true; //发送按钮
Cancel->Enabled=false; //取消按钮
}
}
//---------------------------------------------------------------------------
void __fastcall TSendFiles::ListView1Resize(TObject *Sender)
{
ListView1->Columns->Items[0]->Width=ListView1->Width-5;
}
//---------------------------------------------------------------------------
//*****************清除**************************
void __fastcall TSendFiles::ClearClick(TObject *Sender)
{
FullFileName->Clear();
ListView1->Clear();
Sent->Enabled=false;
Cancel->Enabled=false;
Add->Enabled=true;
FSCMDS->Lines->Clear();
FRCMDS->Lines->Clear();
FSRepa->Lines->Clear();
FRError->Lines->Clear();
}
//---------------------------------------------------------------------------
//**************************发送数据到UDP控件************************
//**参数:CMD---命令码,Buffer---缓冲去指针,Size---数据长度
//*******************************************************************
void __fastcall TSendFiles::SendData_1(AnsiString CMD,char *Buffer,long Size)
{
SendData_1(CMD,Buffer,Size,0); //无Position方式发送数据
}
void __fastcall TSendFiles::SendData_1(AnsiString CMD,char *Buffer,long Size,long Position)
{
TSendFileData TempData; //临时数据缓冲
Application->ProcessMessages();
memset(&TempData,0,sizeof(TSendFileData)); //清除缓冲区
//**************************分析要发送的数据*********************************
TempData.Ver='1';
if (!(CMD=="FRLast"||CMD=="FSLast")) //执行的不是"重发"命令
{
if (CMD=="FSCrea") TempData.Position=ReadFileSize;//建立文件命令借用Position传送文件长度
if (CMD=="FSFile") TempData.Position=Position; //传送文件时保存文件指针(当前Position已经读了Size字节)
strcpy(TempData.FileFlage,CMD.c_str()); //保存命令码
TempData.Size=Size; //保存数据长度
memmove(&TempData.Data,Buffer,Size); //把要发送的数据保存到临时数据中
TempData.CRC=0;
unsigned short CRC;
CRC=CRC_16(&TempData.FileFlage[0],sizeof(TempData));//计算CRC校验码
TempData.CRC=CRC; //保存CRC
ErrorCount=0; //错误计数器
FSTimeOut=0;
}
else //执行"重发"命令
{
if (CMD=="FSLast") //发送方重发
memmove(&TempData,&LastSendData,sizeof(TSendFileData));//把最后一次的发送方数据取出
else
memmove(&TempData,&LastReciveCMD,sizeof(LastReciveCMD));//把最后一次的接收方数据取出
Size=TempData.Size;
ErrorCount++; //错误计数器+1
if (ErrorCount>10) //重发超过10次
{
FSStatusBar->Panels->Items[1]->Text="传输错误,发送失败";
return;
}
}
//***************准备发送******************************************************
if (CMD.SubString(1,2)=="FS") //保存最后一次发送的数据
{
memmove(&LastSendData,&TempData,sizeof(TSendFileData)); //发送方数据
FSTimer->Enabled=true; //启动超时定时计数器
}
else
{
memmove(&LastReciveCMD,&TempData,sizeof(LastReciveCMD)); //接受方响应数据
}
//WriteToUDF(TempData.FileFlage,sizeof(TSendFileData)-1000+Size); //发送数据包到UDP
WriteToUDF((char *)&TempData,sizeof(TSendFileData)-1000+Size);
}
//******************善后处理***********************
void __fastcall TSendFiles::FormDestroy(TObject *Sender)
{
delete ReadFile;
delete WriteFile;
delete [] WriteList;//删除文件块状态数据
ReadFile=NULL;
WriteFile=NULL;
}
//---------------------------------------------------------------------------
//***************发送UDP数据****************************
//此处为与主程序合并接口内容,奇怪的是如果用SendBuff发送,在2000下没问题,在9X下会出错
//所以这里用MyStream过渡了一下,改用SendStream发送。
//******************************************************
void __fastcall TSendFiles::WriteToUDF(char *Buffer,int Size)
{
NMUDP1->RemoteHost=RemoteIP->Text;
NMUDP1->RemotePort=RemotePort->Text.ToIntDef(6666);
TMemoryStream *MyStream =new TMemoryStream();
try
{
MyStream->WriteBuffer(Buffer,Size);
NMUDP1->SendStream(MyStream);
}
catch (...){}
delete MyStream;
}
//**************接收到的UDP数据******************************
//此处为与主程序的接口部分,判断FileFlag第一个字节为"F",调Proc_Send_F。
//***********************************************************
void __fastcall TSendFiles::NMUDP1DataReceived(TComponent *Sender,
int NumberBytes, AnsiString FromIP, int Port)
{
TSendFileData RecivedData;
memset(&RecivedData,0,sizeof(TSendFileData));
NMUDP1->RemoteHost=FromIP;
RemoteIP->Text=FromIP;
NMUDP1->RemotePort=Port;
RemotePort->Text=IntToStr(Port);
//NMUDP1->ReadBuffer(&RecivedData.FileFlage[0],8192,NumberBytes);//接受数据
NMUDP1->ReadBuffer((char *)&RecivedData,8192,NumberBytes);
AnsiString Flag;
Flag=RecivedData.FileFlage; //数据包类型
if (Flag.SubString(1,1)=="F") //文件传送类数据
{
if (RecivedData.Ver=='1') Proce_Send_F_1(RecivedData); //1版处理文件传送类数据包
}
}
//---------------------------------------------------------------------------
//********************文件传送类数据处理程序******************
void __fastcall TSendFiles::Proce_Send_F_1(TSendFileData FileData)
{
Application->ProcessMessages();
unsigned short CRC1,CRC2; //以下计算CRC校验码
CRC1=FileData.CRC; //传送来的CRC
FileData.CRC=0;
CRC2=CRC_16(&FileData.FileFlage[0],sizeof(TSendFileData));//计算CRC
AnsiString CMD,FileName; //命令码,文件名
CMD=FileData.F
bcb UDP传文件(使用TNMUDP控件)
5星 · 超过95%的资源 需积分: 35 58 浏览量
2011-11-27
14:45:36
上传
评论 1
收藏 1019KB RAR 举报
keyu1711
- 粉丝: 21
- 资源: 89
最新资源
- apk.tw_LineLite_v8a_v.2.17.1_sign.apk
- Elasticsearch实战:构建高效搜索系统的秘诀.zip
- HTML+CSS+JS网页设计:从入门到精通.zip
- 数据库课程设计:从理论到实践的全面指南.zip
- Python闭包:深入理解与应用场景解析.zip
- Win64OpenSSL-3-3-0.exe
- 课高分程设计-基于C++实现的民航飞行与地图简易管理系统-南京航空航天大学
- 航天器遥测数据故障检测系统python源码+文档说明+数据库(课程设计)
- 北京航空航天大学操作系统课设+ppt+实验报告
- 基于Vue+Echarts实现风力发电机中传感器的数据展示监控可视化系统+源代码+文档说明(高分课程设计)
资源上传下载、课程学习等过程中有任何疑问或建议,欢迎提出宝贵意见哦~我们会及时处理!
点击此处反馈