Access to Viewer Functions (DW_CALLBACKS)

If a DLL wants access to Viewer internal functions, its LDLLHandler function handles the DW_WHATMSG message by returning a DC_CALLBACKS flag. In DLLDEMO.C, the LDLLHandler function requests access as follows:

case DW_WHATMSG:
           return DC_INITTERM | DC_CALLBACKS;

When it gets this flag, Viewer sends a DW_CALLBACKS message to the DLL. The lParam1 parameter is a long pointer to an array containing pointer to each of the 16 internal Viewer functions. The DLL.H file defines symbolic names for indexing each function in the array.

In processing the DW_CALLBACKS message, the LDLLHandler function calls a function named GetCallBacks to specify which functions it wants to access. GetCallbacks is defined as follows in DLLDEMO:

PUBLIC     BOOL PASCAL EXPORT GetCallBacks(
VPTR     VPtr,
LONG     lVersion)
{

     // hfs level:
     lpfn_HfsOpenSz       = VPtr[HE_HfsOpenSz];
     lpfn_RcCloseHfs      = VPtr[HE_RcCloseHfs];
     lpfn_RcLLInfoFromHfs = VPtr[HE_RcLLInfoFromHfs];

     // bag level routines
     lpfn_FAccessHfs =  VPtr[HE_FAccessHfs];
     lpfn_HfOpenHfs  =  VPtr[HE_HfOpenHfs];
     lpfn_LcbReadHf  =  (LPFN_LCBREADHF) VPtr[HE_LcbReadHf];
     lpfn_RcCloseHf  =  VPtr[HE_RcCloseHf];
     return TRUE;
}

The VPtr parameter in GetCallBacks is the lParam1 pointer passed by the DW_CALLBACKS message from Viewer. The GetCallbacks function gets pointers to the following Viewer internal functions, which it uses later in the example:

Function What It Does

HfsOpenSz Opens the .MVB file system (the compound file containing the files internal to the title)
RcCloseHfs Closes the open .MVB file system
RcLLInfoFromHfs Maps a handle to the open .MVB file system (returned by HfsOpenSz) to low-level file information
FAccessHfs Determines whether or not a file within the .MVB file system is accessible
HfOpenHfs Opens a file within the .MVB file system
LcbReadHf Reads bytes from a file within the .MVB file system

Important:

This sample code does not take multiple instances of Viewer into account. If more than one instance is started, the DLL receives different pointers to these callback functions—one pointer for each instance. You must keep track of which pointer is associated with each Viewer instance. One way to do this is to create an array associating the task with the callback pointer.