Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Visual C++/MFC/WTL > Как CImage передать по сети?


Автор: yurec 13.1.2009, 14:06
Привет!

Стоит задача передавать по сети изображения ( примерно 30 джпегов  по 200-300кб в секунду ).
Хочеться ето сделать еффективно и красиво.
Вот думаю над таким вариантом:

Код


//Save

{
    CSocket sockSrvr;
    sockSrvr.Create(9999,SOCK_STREAM,_T("127.0.0.1"));
    sockSrvr.Listen();

    CSocket sockRecv; 
    sockSrvr.Accept( sockRecv ); 

    CSocketFile file(&sockRecv);
    CArchive ar(&file,CArchive::store);
    CArchiveStream stream(&ar);
    CImage img;
    HRESULT hr_res = img.Load(_T("D:\\Documents and Settings\\zhacun\\Desktop\\CreateImagesTest\\clock01.jpg"));
    if (S_OK != hr_res)
      {
      DWORD err = GetLastError();
      ASSERT(FALSE);
      }

    hr_res = img.Save(&stream,Gdiplus::ImageFormatJPEG);
    if (S_OK != hr_res)
      {
      DWORD err = GetLastError();
      ASSERT(FALSE);
      }
 }



Код


//Load

{
  CSocket sock;
  sock.Create();
  UINT res = sock.Connect(_T("127.0.0.1"),9999);
  if (0 == res)
    {
    DWORD nError = GetLastError();
    ASSERT(FALSE);
    }

  CSocketFile file(&sock);
  CArchive ar(&file,CArchive::load);
  CArchiveStream stream(&ar);
  CImage img;

  HRESULT hr_res = img.Load(&stream);//go into gdiplusbitmap.h next
  if (E_FAIL == hr_res)
    {
    DWORD err = GetLastError();
    ASSERT(FALSE);
    }
 }

//gdiplusbitmap.h

inline 
Bitmap::Bitmap(
    IN IStream *stream, 
    IN BOOL useEmbeddedColorManagement
    )
{
    GpBitmap *bitmap = NULL;

    if(useEmbeddedColorManagement)
    {
        lastResult = DllExports::GdipCreateBitmapFromStreamICM(stream, &bitmap);
    }
    else
    {
        lastResult = DllExports::GdipCreateBitmapFromStream(stream, &bitmap); 
    //returns invalidParameter here, output tells: "Warning - Attempt made to seek on a CSocketFile"
    }

    SetNativeImage(bitmap);
}




Подскажите в чём проблема, пожалуйста. Или предложите альтернативу. 

Спасибо.

Автор: Rapalex 13.1.2009, 15:22
По моему пересжимать каждый файл перед отправкой както не красиво, и ресурсоёмко, так ещё и с потерями, получится так что посылается один файл а приходит другой, зато очень похожий )))

Автор: yurec 13.1.2009, 16:09
проблема,которую мне нужно решить - CImage::Load  не читает из потока созданого из сокета.

(про какое сжатие Вы говорите не знаю, да ето и не имеет значения в етом случае)

Автор: yurec 13.1.2009, 20:04
Вот так работает! 

Код

// TODO: Add your control notification handler code here
  {
  CSocket sock;
  sock.Create();
  UINT res = sock.Connect(_T("127.0.0.1"),9999);
  if (0 == res)
    {
    DWORD nError = GetLastError();
    ASSERT(FALSE);
    }

  CSocketFile file(&sock);
  CArchive ar(&file,CArchive::load);
  CArchiveStream stream(&ar);

  const ULONG buf_size = 4 * 1024 * 1024;

  COleStreamFile ole_file;
  ole_file.CreateMemoryStream();
  char * p_buf = new char[buf_size];
  ZeroMemory(p_buf,buf_size);

  ULONG read_stream = 0;
  HRESULT hr = stream.Read(p_buf,buf_size,&read_stream);
  ASSERT(S_OK == hr);
  ole_file.Write(p_buf,read_stream);

  HRESULT hr_res = img.Load(ole_file.GetStream());
  VERIFY(S_OK == hr_res);

  delete[] p_buf;
  }


Надеюсь я не ошибаюсь и COleStreamFile выделяет память в оперативке, а не на диске?

Автор: yurec 14.1.2009, 11:17
Я думаю, что я не ошибаюсь )

Автор: Rapalex 14.1.2009, 11:21
Лучше бы ты весь файл передал массивом байт, это было бы правильней.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)