richedit и EM_STREAMIN

Тема в разделе "WASM.WIN32", создана пользователем cresta, 30 июл 2005.

  1. cresta

    cresta Active Member

    Публикаций:
    0
    Регистрация:
    13 июн 2004
    Сообщения:
    2.257
    Пробую загрузить richedit при помощи SendMessage/EM_STREAMIN с использованием callback.


    Код (Text):
    1. int File_Load(HWND hEdit){
    2.     HANDLE        hFile;
    3.     int           Read;
    4.     EDITSTREAM    est;
    5.  
    6.     if (INVALID_HANDLE_VALUE != (hFile= CreateFile(FileName,
    7.                                         GENERIC_READ | GENERIC_WRITE,
    8.                                         0, (LPSECURITY_ATTRIBUTES) NULL,
    9.                                         OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL,
    10.                                         (HANDLE) NULL)))
    11.                 {
    12.                 est.dwCookie = (DWORD_PTR)hFile;
    13.                 est.dwError = 0;
    14.                 est.pfnCallback = (EDITSTREAMCALLBACK) & Open_Callback;
    15.                 SendMessage (hEdit, EM_STREAMIN, SF_TEXT, (LPARAM) & est);
    16.                 filesize = GetFileSize(hFile, (LPDWORD) &Read);
    17.                 CloseHandle(hFile);
    18.                 SendMessage(hEdit,EM_SETMODIFY,0,0);
    19.                 }
    20.     return 0;
    21.    
    22. }
    23.  
    24. // это callback:
    25.  
    26. int Open_Callback(HANDLE dwCookie, LPVOID pbBuff, int cb, LPDWORD pcb){
    27.     char            buffer[256];
    28.     BOOL            result;
    29.     int             read;
    30.  
    31.     wsprintf(buffer,"dwCookie=%lu, pbBuff=%lu, cb=%lu, pcb=%lu",dwCookie,
    32.         pbBuff,cb,pcb);
    33.     MessageBox(hWnd,buffer,NULL,NULL);
    34.    
    35.     result = ReadFile(dwCookie,pbBuff,cb,pcb,NULL);
    36.  
    37.     read = *((DWORD*)pcb);
    38.     wsprintf(buffer,"dwCookie=%lu, pbBuff=%lu, cb=%lu, read=%lu",dwCookie,
    39.         pbBuff,cb,read);
    40.     MessageBox(hWnd,buffer,NULL,NULL);
    41.    
    42.     return 0;
    43. }




    richedit вызывает дважды callback.

    На первом вызове запрашивается 4094 байта (cb), читается 3508 (*((DWORD*)pcb)) - это размер файла.

    Затем callback вызывается повторно, с запросом тех же 4094 байт. При этом второй раз ReadFile выдаёт, что считано ноль.

    Возврат в *((DWORD*)pcb) нуля означает конец загрузки.

    После второго возвращения из callBack программа падает.



    Сам richedit нормальный, если грузить вручную через EM_REPLACE, то работает. Хотелось бы сделать с callback'ом.
     
  2. SDragon

    SDragon New Member

    Публикаций:
    0
    Регистрация:
    6 июн 2005
    Сообщения:
    133
    Адрес:
    Siberia
    Open_Callback должна возвращать ненулевое значение, если нужно закончить операцию чтения. Попробуй так:


    Код (Text):
    1. DWORD CALLBACK Open_Callback(DWORD dwCookie, LPBYTE pbBuff, LONG cb, LONG* pcb) {
    2.     return !ReadFile(hFile, pbBuff, cb, (LPDWORD)pcb, NULL);
    3. }
     
  3. SDragon

    SDragon New Member

    Публикаций:
    0
    Регистрация:
    6 июн 2005
    Сообщения:
    133
    Адрес:
    Siberia
  4. cresta

    cresta Active Member

    Публикаций:
    0
    Регистрация:
    13 июн 2004
    Сообщения:
    2.257
    SDragon



    Хм, работает, спасибо. Но непонятно, как это (возврат ненулевого значения) стыкуется с этим:



    The control calls the callback function repeatedly, transferring a portion of the data with each call. The control continues to call the callback function until one of the following conditions occurs:



    <ol type=1>The callback function returns a nonzero value.

    The callback function returns zero in the *pcb parameter.

    An error occurs that prevents the rich edit control from transferring data into or out of itself. Examples are out-of-memory situations, failure of a system function, or an invalid character in the read buffer.

    For a stream-in operation, the RTF code contains data specifying the end of an RTF block.

    For a stream-in operation on a single-line edit control, the callback reads in an end-of-paragraph character (CR, LF, VT, LS, or PS). </ol>




    Или вот с таким кодом (заведомо рабочим):


    Код (Text):
    1. invoke ReadFile,dwCookie,pbBuff,cb,pcb,NULL
    2. mov eax, 0
    3. ret