Возвращаемые значения HGLOBAL в UFL Crystal Reports UFL и UF5RestoreState - PullRequest
1 голос
/ 26 ноября 2010

Использование C ++ для написания UFL для отчетов Crystal Я получаю возможность реализовать функции UF5SaveState и UF5RestoreState, которые вы не получаете с интерфейсом COM, что приводит к проблемам, которые эти функции существуют для решения.

Функция UF5SaveState, которую я должен реализовать, имеет следующую подпись: -

HGLOBAL __stdcall UF5SaveState (UFTInt32u jobId)

Моя проблема в том, что я не уверен, как сформировать HGLOBAL, который он должен вернуть.

Документы говорят только это: -

UF5SaveState Эта процедура должна быть реализовано, только если ваш UFL имеет функция с побочными эффектами [Это действительно так] . это вызывается Crystal Reports, чтобы получить состояние от UFL в данный момент точка. Номер задания Crystal Reports передается в функцию. функция возвращает двоичный код состояния UFL поток во втором параметре, и возвращает размер состояния в третий параметр.

Я очень сбит с толку, не в последнюю очередь потому, что он говорит о возврате вещей во втором и даже третьем параметрах. Я на самом деле не человек Windows, поэтому для меня HGLOBAL очень похож на пустой указатель, и поэтому я ожидаю, что он будет более значимым для людей Windows. Я попытался передать обратно результаты GlobalAlloc, попытался создать поток из него (CreateStreamOnHGlobal) и передать его обратно, попробовал просто символ *, и все вылилось в необработанное исключение: -

Необработанное исключение в 0x7c92a978 (ntdll.dll) в crw32.exe: 0xC0000005: Место записи о нарушении прав доступа 0x00030fa4.

Я не сомневаюсь, что это потому, что он ожидает чего-то другого, но что ...

кусок кода, который не работает только для того, чтобы помочь вам начать работу: -

HGLOBAL __stdcall UF5SaveState (UFTInt32u jobId)
{
 ULONG bytesWritten;
 HGLOBAL result = GlobalAlloc(GHND, 2048);
 LPSTREAM stream = LPSTREAM(); 
 CreateStreamOnHGlobal(result, false, &stream);
 stream->Write("ABC", 3, &bytesWritten);
 stream->Release();

 return result;
}

Итак, представьте, что я хочу сохранить состояние, состоящее только из трех символов "ABC", необязательный нулевой терминатор, как мне это сделать?

Ответы [ 2 ]

0 голосов
/ 03 декабря 2010

Обычное место, где по-прежнему используются дескрипторы памяти HGLOBAL, - это настройка буфера обмена Windows. Crystal Reports, вероятно, ожидает тот же тип дескриптора, который вы использовали бы для этого.

Вот соответствующий код для создания HGLOBAL с "ABC" в нем:

const char *szInput = "ABC";
size_t cchBufLen = strlen(szInput) + 1; // +1 for the null-terminator.
size_t cbBufSize = cchBufLen * sizeof(char); // Len==Size, but wouldn't if you were using wchar_t instead of char.

bool bSuccess = false;
HGLOBAL hGlobalClipMem = ::GlobalAlloc(GHND, cbBufSize);

if (hGlobalClipMem != NULL)
{
    // Since the "GHND" flags include GMEM_MOVEABLE we must use GlobalLock to
    // get a pointer to the buffer, and later GlobalFree to get back to normal.
    char *pGlobalBuffer = reinterpret_cast<char *>( ::GlobalLock(hGlobalClipMem) );

    if (pGlobalBuffer != NULL)
    {
        strcpy(pGlobalBuffer, szInput);
        bSuccess = true; // Set false if anything fails here, so you clean-up.

        ::GlobalUnlock(hGlobalClipMem); // You unlock the hGlobal, not the pointer that came out of GlobalLock.
    }

    // Error-handling path.
    if (!bSuccess)
    {
        ::GlobalFree(hGlobalClipMem);
        hGlobalClipMem = NULL;
    }
}

return hGlobalClipMem; // Returns NULL on failure.
0 голосов
/ 26 ноября 2010

Я написал пользовательскую функцию CR миллион лет назад. Заголовочный файл uffuncs.h содержал следующие определения:

HGLOBAL CR_EXPORT UF5SaveState (UFTInt32u jobId);
UFError CR_EXPORT UF5RestoreState (UFTInt32u jobId,
                                   HGLOBAL savedState);

Документация, которую вы нашли, убедительна, но HGLOBAL недостаточно хорош для сохранения в отчете. Это указатель, который не будет восстановлен должным образом при повторной загрузке отчета в другой сессии. Эти загадочные дополнительные аргументы позволили бы это.

Этот заголовочный файл имеет метку времени 1997 года. Я могу только порекомендовать вам попробовать найти более свежую версию файла заголовка uffuncs.h. Где бы это ни было, я не помню, откуда я это взял. Документы и ссылки на веб-сайте совершенно неадекватны. Довольно типичная потеря CR, я решил больше никогда не использовать CR после страданий, через которые я прошел.

...