Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Работа с сетью в Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 19.01.2016, 15:30   #1
Shouldercannon
Участник клуба Подтвердите свой е-майл
 
Аватар для Shouldercannon
 
Регистрация: 26.01.2008
Сообщений: 1,893
Вопрос Передача файлов по сети

Доброго времени суток!
Сделал передачу файлов через Socket и столкнулся с проблемами.

Код:
unit frm_ReceivingFile;

procedure TFormReceivingFile.FormCreate(Sender: TObject);
begin
  ProcReceivingFile('Test', 'test.txt', ExtractFilePath(Application.ExeName) + 'Downloads'); //!//

  ClientSocket1.Open; // Открываем сокет
  BReceive := False; // Режим клиента - приём команд
end;

procedure TFormReceivingFile.ProcReceivingFile(Nick, sFile, sFolder: String);
begin
  LUser.Caption := Nick;
  LFile.Caption := ExtractFileName(sFile);
  ReceptionFolder := sFolder;
end;

procedure TFormReceivingFile.ClientSocket1Connect(Sender: TObject;
  Socket: TCustomWinSocket);
begin
  LStatus.Caption := 'Приём...';
end;

procedure TFormReceivingFile.ClientSocket1Disconnect(Sender: TObject;
  Socket: TCustomWinSocket);
begin
  LStatus.Caption := 'Нет соединения';
end;

procedure TFormReceivingFile.ClientSocket1Read(Sender: TObject;
  Socket: TCustomWinSocket);
var
  s: AnsiString; // Принятый текст
begin
  s := Socket.ReceiveText;
  // Если клиент в режиме приёма файла, то...
  if BReceive then Writing(s) // Записываем данные в буфер
  else // Если клиент не в режиме приёма файла, то...
  if Copy(s, 1, Pos('<||>', String(s)) - 1) = '10' then // Если это команда принятия файла "10", то...
  begin
    MS := TMemoryStream.Create; // Создаём буфер для файла
    // Определяем имя файла
    Delete(s, 1, Pos('<||>', String(s)) + 3);
    sName := String(Copy(s, 1, Pos('<||>', String(s)) - 1));
    // Определяем размер файла
    Delete(s, 1, Pos('<||>', String(s)) + 3);
    Size := StrToInt(String(Copy(s, 1, Pos('<||>', String(s)) - 1))); // Определяем размер файла
    Delete(s, 1, Pos('<||>', String(s)) + 3); // Удаляем последний разделитель
    BReceive := True; // Переводим сервер в режим приёма файла
    Writing(s); // Записываем данные в буфер
  end;
end;

procedure TFormReceivingFile.Writing(s: AnsiString);
begin
  // Если принято байт меньше размера файла, то...
  if MS.Size < Size then MS.Write(s[1], Length(s)); // Записываем в буфер
  // Выводим прогресс закачки файла
  ProgressBar1.Position := MS.Size * 100 div Size;
  LReceived.Caption := Format('%s / %s', [GetNormalSize(MS.Size), GetNormalSize(Size)]);
  // Если файл принят, то...
  if MS.Size = Size then
  begin
    BReceive := False; // Переводим клиента в нормальный режим
    MS.Position := 0; // Переводим каретку в начало буфера
    MS.SaveToFile(Format('%s\%s', [ReceptionFolder, ExtractFileName(sName)])); // Сохраняем файл
    ClientSocket1.Socket.SendText('11'); // Посылаем команду "11", то есть файл принят
    FreeAndNil(MS); // Убиваем буфер
    LStatus.Caption := 'Файл принят';
  end;
end;
ProgressBar работает нормально, а в LStatus количество переданных байт выводится только после получения файла

Код:
unit frm_FileTransfer;

procedure TFormFileTransfer.FormCreate(Sender: TObject);
begin
  ServerSocket1.Open; // Открываем сокет
end;

procedure TFormFileTransfer.FormDestroy(Sender: TObject);
begin
  ServerSocket1.Close; // Закрываем сокет
end;

procedure TFormFileTransfer.ProcFileTransfer(Nick, sFile: String);
var
  Size: Integer;
  P: ^Byte;
begin
  LUser.Caption := Nick;
  LFile.Caption := ExtractFileName(sFile);

  Self.Show;

  MS := TMemoryStream.Create; // Создаём буфер для файла
  MS.LoadFromFile(sFile); // Загружаем файл в буфер
  ServerSocket1.Socket.Connections[0].SendText(AnsiString('10<||>' + sFile + '<||>' + IntToStr(MS.Size) + '<||>')); // Посылаем информацию о файле (файл и размер)
  MS.Position := 0; // Переводим каретку в начало файла
  P := MS.Memory; // Загружаем в переменную "P" файл
  Size := ServerSocket1.Socket.Connections[0].SendBuf(P^, MS.Size); // Посылаем файл
  // Выводим прогресс
  ProgressBar1.Position := Size * 100 div MS.Size;
  LReceived.Caption := Format('%s / %s', [GetNormalSize(Size), GetNormalSize(MS.Size)]);
end;

procedure TFormFileTransfer.ServerSocket1ClientConnect(Sender: TObject;
  Socket: TCustomWinSocket);
begin
  LStatus.Caption := 'Передача...';
end;

procedure TFormFileTransfer.ServerSocket1ClientDisconnect(Sender: TObject;
  Socket: TCustomWinSocket);
begin
  LStatus.Caption := 'Нет соединения';
end;

procedure TFormFileTransfer.ServerSocket1ClientRead(Sender: TObject;
  Socket: TCustomWinSocket);
begin
  // Если клиент принял файл, то...
  if Socket.ReceiveText = '11' then
  begin
    LStatus.Caption := 'Файл отправлен';
    FreeAndNil(MS); // Убиваем буфер
  end;
end;
PrograssBar стоит на месте, а в LStatus количество переданных байт сразу на максимуме (10 Кб / 10 Кб)

Последний раз редактировалось Shouldercannon; 19.01.2016 в 15:53.
Shouldercannon вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
C# передача файлов в сети TaTT DoGG Помощь студентам 20 02.04.2017 15:53
передача файлов по сети SPD Общие вопросы Delphi 7 10.06.2011 00:24
С# передача файлов по сети bondik Общие вопросы .NET 4 04.03.2010 10:49
Передача файлов по сети SL1CK Работа с сетью в Delphi 3 05.12.2009 00:08