2567 lines
95 KiB
C
2567 lines
95 KiB
C
|
/****************************************************************************
|
|||
|
CACHE.C
|
|||
|
|
|||
|
$Log: S:\products\msprods\oiwh\display\cache.c_v $
|
|||
|
*
|
|||
|
* Rev 1.104 24 Apr 1996 14:38:34 BEG06016
|
|||
|
* Added horizontal differencing.
|
|||
|
*
|
|||
|
* Rev 1.104 24 Apr 1996 14:27:40 BEG06016
|
|||
|
* Added horizontal differencing.
|
|||
|
*
|
|||
|
* Rev 1.103 19 Apr 1996 09:02:26 BEG06016
|
|||
|
* Added CheckError2 for error handling.
|
|||
|
*
|
|||
|
* Rev 1.102 18 Apr 1996 13:47:04 BEG06016
|
|||
|
* Added CheckError2 for error handling.
|
|||
|
*
|
|||
|
* Rev 1.101 15 Apr 1996 15:54:00 BEG06016
|
|||
|
* Fixed reading of 16 bit annotations.
|
|||
|
*
|
|||
|
* Rev 1.100 15 Apr 1996 09:50:12 BEG06016
|
|||
|
* Fixed reading of 16 bit annotations.
|
|||
|
*
|
|||
|
* Rev 1.99 12 Apr 1996 09:38:56 BEG06016
|
|||
|
* Ficed the initialization of some variables.
|
|||
|
*
|
|||
|
* Rev 1.98 12 Apr 1996 08:47:18 BEG06016
|
|||
|
* Ficed the initialization of some variables.
|
|||
|
*
|
|||
|
* Rev 1.97 12 Apr 1996 08:18:14 BEG06016
|
|||
|
* Ficed the initialization of some variables.
|
|||
|
*
|
|||
|
* Rev 1.96 11 Apr 1996 15:12:52 BEG06016
|
|||
|
* Optimized named block access some.
|
|||
|
*
|
|||
|
* Rev 1.95 27 Feb 1996 11:08:42 BEG06016
|
|||
|
* Misc fixes.
|
|||
|
*
|
|||
|
* Rev 1.94 10 Jan 1996 16:09:26 RC
|
|||
|
* Fixed dib size calculation in ReadAnnotations
|
|||
|
*
|
|||
|
* Rev 1.93 10 Jan 1996 15:18:04 BLJ
|
|||
|
* Fixed some error handling.
|
|||
|
*
|
|||
|
* Rev 1.92 05 Jan 1996 14:07:52 RC
|
|||
|
* Propagated previous change
|
|||
|
*
|
|||
|
* Rev 1.91 05 Jan 1996 11:03:50 BLJ
|
|||
|
* Fixed some error handling.
|
|||
|
*
|
|||
|
* Rev 1.90 04 Jan 1996 17:43:40 RC
|
|||
|
* Changed cache line upper bound from -1 to 0xfffffff to account for uints
|
|||
|
* changing to ints
|
|||
|
*
|
|||
|
* Rev 1.89 02 Jan 1996 09:58:14 BLJ
|
|||
|
* Changed alot of UINTs to ints.
|
|||
|
* Changed IMG structure to include the image data.
|
|||
|
* Changed lp prefix to p.
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
#include "privdisp.h"
|
|||
|
|
|||
|
#define CACHE_PAGE 0
|
|||
|
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: IMGCacheFile
|
|||
|
|
|||
|
PURPOSE: Send cacheing request to BACKCAP
|
|||
|
|
|||
|
INPUT: pCacheFileParms - The cache parameters given by the caller.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI IMGCacheFile(LP_CACHE_FILE_PARMS pCacheFileParms){
|
|||
|
|
|||
|
int nStatus;
|
|||
|
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2(IntSeqfileInit())
|
|||
|
|
|||
|
// Prevent Multiprocessing in this code.
|
|||
|
CheckError2(LockMutex())
|
|||
|
|
|||
|
if (!pCacheFileParms){
|
|||
|
nStatus = Error(DISPLAY_NULLPOINTERINVALID);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
if (!pCacheFileParms->file_name){
|
|||
|
nStatus = Error(DISPLAY_INVALIDFILENAME);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
CheckError2(CacheFileAno(pCacheFileParms->hWnd, pCacheFileParms->file_name,
|
|||
|
pCacheFileParms->wPage_number, &pAnoImage))
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
// Allow Multiprocessing again.
|
|||
|
UnlockMutex();
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: IMGCacheDiscard
|
|||
|
|
|||
|
PURPOSE: Discard files from the cache
|
|||
|
|
|||
|
INPUT: hWnd - callers window handle
|
|||
|
option
|
|||
|
CACHE_DISCARD_SYSOLD - discard oldest image regardless of window
|
|||
|
CACHE_DISCARD_WINOLD - discard oldest image belonging to this window
|
|||
|
CACHE_DISCARD_WINALL - discard all images belonging to this window
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI IMGCacheDiscard(HWND hWnd, UINT option){
|
|||
|
|
|||
|
int nStatus;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2(IntSeqfileInit())
|
|||
|
|
|||
|
// Prevent Multiprocessing in this code.
|
|||
|
CheckError2(LockMutex())
|
|||
|
|
|||
|
switch (option){
|
|||
|
case CACHE_DISCARD_WINOLD:
|
|||
|
case CACHE_DISCARD_SYSOLD:
|
|||
|
// Find the oldest file in the cache.
|
|||
|
pAnoImage = 0;
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]->nLockCount
|
|||
|
&& pSubSegMemory->ppCachedAnoImage[nLoop]->nAge > pAnoImage->nAge){
|
|||
|
pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop];
|
|||
|
}
|
|||
|
}
|
|||
|
// Delete the oldest file in the cache.
|
|||
|
if (pAnoImage){
|
|||
|
CheckError2(CacheClearAno(&pAnoImage))
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case CACHE_DISCARD_WINALL:
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop];
|
|||
|
if (!pAnoImage->nLockCount){
|
|||
|
CheckError2(CacheClearAno(&pAnoImage))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
nStatus = Error(DISPLAY_INVALID_OPTIONS);
|
|||
|
}
|
|||
|
|
|||
|
Exit:
|
|||
|
// Allow Multiprocessing again.
|
|||
|
UnlockMutex();
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
Function: IMGCacheDiscardFileCgbw
|
|||
|
|
|||
|
Description: Discard a given file from the cache for a given window.
|
|||
|
Although this API is not documented, it is public.
|
|||
|
|
|||
|
Inputs: hWnd - handle of window for which the file is cached.
|
|||
|
pFileName - file name string.
|
|||
|
nPage - The page number to cache.
|
|||
|
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI IMGCacheDiscardFileCgbw(HWND hWnd, PSTR pFileName, int nPage){
|
|||
|
|
|||
|
int nStatus;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
BOOL bFileFound = FALSE;
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
PIMAGE pImage;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2(IntSeqfileInit())
|
|||
|
|
|||
|
// Prevent Multiprocessing in this code.
|
|||
|
CheckError2(LockMutex())
|
|||
|
|
|||
|
if (!pFileName){
|
|||
|
nStatus = Error(DISPLAY_INVALIDFILENAME);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (nPage == -1 || pImage->nFilePageNum == nPage){
|
|||
|
bFileFound = TRUE;
|
|||
|
if (!pAnoImage->nLockCount){
|
|||
|
CheckError2(CacheClearAno(&pAnoImage))
|
|||
|
}else{
|
|||
|
nStatus = Error2(DISPLAY_CACHEFILEINUSE);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
if (nPage < -1){
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (pImage = pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (nPage == -1 || pImage->nFilePageNum == nPage){
|
|||
|
bFileFound = TRUE;
|
|||
|
if (!pImage->nLockCount){
|
|||
|
CheckError2(CacheClear(&pImage))
|
|||
|
}else{
|
|||
|
nStatus = Error2(DISPLAY_CACHEFILEINUSE);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
if (nPage < -1){
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (!bFileFound){
|
|||
|
nStatus = Error2(DISPLAY_CACHENOTFOUND);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
// Allow Multiprocessing again.
|
|||
|
UnlockMutex();
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: IMGCacheFilesInCache
|
|||
|
|
|||
|
PURPOSE: Returns a list of files that are in the cache.
|
|||
|
|
|||
|
INPUTS: hWnd - This is the window handle whose cache entries are
|
|||
|
being checked.
|
|||
|
pFiles - The caller allocated array where the information will
|
|||
|
be stored.
|
|||
|
pNumberOfFiles
|
|||
|
- At entry this is the maximum number of entries
|
|||
|
the array can hold.
|
|||
|
- At return this is the exact number of entries being
|
|||
|
returned.
|
|||
|
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI IMGCacheFilesInCache(HWND hWnd, LPCACHE_FILES_IN_CACHE_STRUCT pFiles,
|
|||
|
UINT *puNumberOfFiles){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
int nNumberOfFiles = 0;
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
PIMAGE pImage;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2(IntSeqfileInit())
|
|||
|
|
|||
|
// Prevent Multiprocessing in this code.
|
|||
|
CheckError2(LockMutex())
|
|||
|
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (nNumberOfFiles >= (int) *puNumberOfFiles){
|
|||
|
break;
|
|||
|
}
|
|||
|
strcpy(pFiles->File[nLoop].szFilename, pImage->szFileName);
|
|||
|
pFiles->File[nLoop].uPageNumber = pImage->nFilePageNum;
|
|||
|
nNumberOfFiles++;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
*puNumberOfFiles = nNumberOfFiles;
|
|||
|
|
|||
|
Exit:
|
|||
|
// Allow Multiprocessing again.
|
|||
|
UnlockMutex();
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: ValidateCache
|
|||
|
|
|||
|
PURPOSE: Makes sure all data has been read from cache.
|
|||
|
|
|||
|
INPUT: hWnd - Handle to window where image is to be displayed.
|
|||
|
HANDLE - Handle to image structure.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI ValidateCache(HWND hWnd, PANO_IMAGE pAnoImage){
|
|||
|
|
|||
|
int nStatus;
|
|||
|
|
|||
|
CheckError2(ValidateCacheLines(hWnd, pAnoImage, 0xffffff))
|
|||
|
|
|||
|
Exit:
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: ValidateCacheLines
|
|||
|
|
|||
|
PURPOSE: Makes sure the specified lines of data have been read from cache.
|
|||
|
|
|||
|
INPUT: hWnd - Handle to window where image is to be displayed.
|
|||
|
HANDLE - Handle to image structure.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI ValidateCacheLines(HWND hWnd, PANO_IMAGE pAnoImage, int nValidationLine){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PIMAGE pBaseImage;
|
|||
|
PIMAGE pFormImage;
|
|||
|
PIMG pBasePlusFormImg = 0;
|
|||
|
PBYTE pDestLine;
|
|||
|
PBYTE pSourceLine;
|
|||
|
int nWidthInBytes;
|
|||
|
RECT rSrceImageRect;
|
|||
|
RECT rDestMergeRect;
|
|||
|
LRECT lrSourceRect;
|
|||
|
LRECT lrDestRect;
|
|||
|
int nAdjHScale;
|
|||
|
int nAdjVScale;
|
|||
|
int nMarkIndex;
|
|||
|
PMARK pMark=0;
|
|||
|
PAN_NEW_ROTATE_STRUCT pAnRotation = 0;
|
|||
|
PSTR pFileName;
|
|||
|
char FileName[256];
|
|||
|
PAN_NAME_STRUCT pAnName;
|
|||
|
int nEarlyBPFValidLines; // keeps track of how many base image lines
|
|||
|
// are valid coming into validate cache
|
|||
|
|
|||
|
|
|||
|
pBaseImage = pAnoImage->pBaseImage;
|
|||
|
if (!pBaseImage->pImg){
|
|||
|
nStatus = Error(DISPLAY_IMAGETYPENOTSUPPORTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (!pBaseImage->bFileRotationDone){
|
|||
|
nValidationLine = 0xffffff;
|
|||
|
}
|
|||
|
nValidationLine = min(pBaseImage->nHeight, nValidationLine);
|
|||
|
nEarlyBPFValidLines = pAnoImage->nBPFValidLines;
|
|||
|
|
|||
|
if (!pAnoImage->bAnnotationsAlreadyRead && pBaseImage->bAnnotationsPresent){
|
|||
|
CheckError2(ReadAnnotationsFromFile(hWnd, pAnoImage,
|
|||
|
&pAnoImage->Annotations.ppMarks,
|
|||
|
&pAnoImage->Annotations.nMarks))
|
|||
|
}
|
|||
|
|
|||
|
// Read the base image.
|
|||
|
if (pBaseImage->bUsingCache && !pBaseImage->bCacheValid
|
|||
|
&& pBaseImage->nLinesRead < nValidationLine){
|
|||
|
CheckError2(CacheRead(hWnd, pBaseImage, nValidationLine - pBaseImage->nLinesRead))
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
// check to see if there is a form mark
|
|||
|
for (nMarkIndex = 0; nMarkIndex < pAnoImage->Annotations.nMarks; nMarkIndex++){
|
|||
|
pMark = pAnoImage->Annotations.ppMarks[nMarkIndex];
|
|||
|
if ((int) pMark->Attributes.uType == OIOP_AN_FORM){
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// if the form has been thrown away or doesnt exist, get it
|
|||
|
if (pMark && ((int) pMark->Attributes.uType == OIOP_AN_FORM) && (!pAnoImage->pFormImage)){
|
|||
|
pAnName = 0;
|
|||
|
CheckError2(GetAMarkNamedBlock(pMark, szOiFilNam, (PPSTR) &pAnName))
|
|||
|
if (pAnName == 0){
|
|||
|
nStatus = Error (DISPLAY_DATACORRUPTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
pFileName = FileName;
|
|||
|
GetFileName (pFileName, (PSTR) pAnName->name);
|
|||
|
|
|||
|
pAnRotation = 0;
|
|||
|
CheckError2( GetAMarkNamedBlock(pMark, szOiAnoDat, (PPSTR) &pAnRotation))
|
|||
|
if (pAnRotation == 0){
|
|||
|
nStatus = Error (DISPLAY_DATACORRUPTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
CheckError2( CacheFile(hWnd, pFileName, 1, &pAnoImage->pFormImage))
|
|||
|
|
|||
|
pAnRotation->nHRes = pBaseImage->nHRes;
|
|||
|
pAnRotation->nVRes = pBaseImage->nVRes;
|
|||
|
pAnoImage->pFormImage->nLockCount++;
|
|||
|
pAnoImage->pFormMark = pMark;
|
|||
|
pAnoImage->nBPFValidLines = 0;
|
|||
|
pAnoImage->pBasePlusFormImg = 0;
|
|||
|
pAnoImage->pDisplayFormImage = 0;
|
|||
|
}
|
|||
|
|
|||
|
if ((!(pFormImage = pAnoImage->pFormImage)) || (pMark && !pMark->Attributes.bVisible)){
|
|||
|
pAnoImage->pBasePlusFormImg = pBaseImage->pImg;
|
|||
|
pAnoImage->nBPFValidLines = pBaseImage->nLinesRead;
|
|||
|
}else{
|
|||
|
// Read the form image.
|
|||
|
if (pFormImage->bUsingCache && !pFormImage->bCacheValid
|
|||
|
&& pFormImage->nLinesRead < nValidationLine){
|
|||
|
CheckError2( CacheRead(hWnd, pFormImage, pFormImage->nHeight))
|
|||
|
}
|
|||
|
|
|||
|
// Generate the BasePlusForm image.
|
|||
|
pMark = pAnoImage->Annotations.ppMarks[0];
|
|||
|
if (!pAnoImage->nBPFValidLines){
|
|||
|
CheckError2( AllocateMemory(sizeof(IMG), (PPSTR) &pAnoImage->pBasePlusFormImg, ZERO_INIT))
|
|||
|
CheckError2( CreateAnyImgBuf(&pAnoImage->pBasePlusFormImg, pBaseImage->nWidth,
|
|||
|
pBaseImage->nHeight, pBaseImage->pImg->nType))
|
|||
|
}
|
|||
|
pBasePlusFormImg = pAnoImage->pBasePlusFormImg;
|
|||
|
|
|||
|
// Copy the base image to BasePlusForm.
|
|||
|
switch (pBaseImage->pImg->nType){
|
|||
|
case ITYPE_BI_LEVEL:
|
|||
|
nWidthInBytes = (pBaseImage->nWidth + 7) / 8;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY4:
|
|||
|
case ITYPE_PAL4:
|
|||
|
nWidthInBytes = (pBaseImage->nWidth + 1) / 2;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY7:
|
|||
|
case ITYPE_GRAY8:
|
|||
|
case ITYPE_COMPAL8:
|
|||
|
case ITYPE_CUSPAL8:
|
|||
|
nWidthInBytes = pBaseImage->nWidth;
|
|||
|
break;
|
|||
|
case ITYPE_RGB24:
|
|||
|
case ITYPE_BGR24:
|
|||
|
nWidthInBytes = pBaseImage->nWidth * 3;
|
|||
|
break;
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
if (pAnoImage->nBPFValidLines < nValidationLine){
|
|||
|
pSourceLine = &pBaseImage->pImg->bImageData[0]
|
|||
|
+ (pAnoImage->nBPFValidLines * pBaseImage->pImg->nBytesPerLine);
|
|||
|
pDestLine = &pBasePlusFormImg->bImageData[0]
|
|||
|
+ (pAnoImage->nBPFValidLines * pBasePlusFormImg->nBytesPerLine);
|
|||
|
memcpy(pDestLine, pSourceLine,
|
|||
|
nWidthInBytes * (nValidationLine - pAnoImage->nBPFValidLines));
|
|||
|
pAnoImage->nBPFValidLines = nValidationLine;
|
|||
|
}
|
|||
|
|
|||
|
pAnRotation = 0;
|
|||
|
CheckError2(GetAMarkNamedBlock(pMark, szOiAnoDat, (PPSTR) &pAnRotation))
|
|||
|
if (pAnRotation == 0){
|
|||
|
nStatus = Error (DISPLAY_DATACORRUPTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
// adjust the resolution of the form image to the base image
|
|||
|
// Only do this if any scaling is necessary
|
|||
|
if (!pAnoImage->pDisplayFormImage){
|
|||
|
CheckError2( AllocateMemory(sizeof(IMAGE),
|
|||
|
(PPSTR) &pAnoImage->pDisplayFormImage, ZERO_INIT))
|
|||
|
|
|||
|
SetLRect (lrSourceRect, 0, 0, pAnoImage->pFormImage->nWidth,
|
|||
|
pAnoImage->pFormImage->nHeight);
|
|||
|
|
|||
|
nAdjHScale = ((pAnRotation->scale * pBaseImage->nHRes)/ pFormImage->nHRes);
|
|||
|
nAdjVScale = ((pAnRotation->scale * pBaseImage->nVRes)/ pFormImage->nVRes);
|
|||
|
|
|||
|
CopyRect (lrDestRect, lrSourceRect);
|
|||
|
ConvertRect2(&lrDestRect, CONV_FULLSIZE_TO_SCALED, nAdjHScale, nAdjVScale, 0, 0);
|
|||
|
|
|||
|
CheckError2( CreateAnyImgBuf(&pAnoImage->pDisplayFormImage->pImg,
|
|||
|
(lrDestRect.right - lrDestRect.left),
|
|||
|
(lrDestRect.bottom - lrDestRect.top), ITYPE_BI_LEVEL))
|
|||
|
|
|||
|
CheckError2( ScaleBits(pAnoImage->pFormImage->pImg,
|
|||
|
pAnoImage->pDisplayFormImage->pImg, OI_SCALE_ALG_BW_KEEP_BLACK,
|
|||
|
nAdjHScale, nAdjVScale, lrSourceRect, lrDestRect, NULL))
|
|||
|
pAnoImage->pDisplayFormImage->nHeight = pAnoImage->pDisplayFormImage->pImg->nHeight;
|
|||
|
pAnoImage->pDisplayFormImage->nWidth = pAnoImage->pDisplayFormImage->pImg->nWidth;
|
|||
|
|
|||
|
CheckError2( RotateImage (pMark, pAnoImage->pDisplayFormImage,
|
|||
|
pAnRotation->rotation))
|
|||
|
|
|||
|
}
|
|||
|
// Merge form image into BasePlusForm.
|
|||
|
|
|||
|
CopyRectLtoR(rSrceImageRect, pAnoImage->pFormMark->Attributes.lrBounds);
|
|||
|
SetRect(&rDestMergeRect,
|
|||
|
max(0, rSrceImageRect.left),
|
|||
|
max(0, rSrceImageRect.top),
|
|||
|
min((int) pBaseImage->nWidth, rSrceImageRect.right),
|
|||
|
min((int)min(nValidationLine, pBaseImage->nHeight),
|
|||
|
rSrceImageRect.bottom));
|
|||
|
|
|||
|
//do the merge only if needed
|
|||
|
if ((rDestMergeRect.left < rDestMergeRect.right
|
|||
|
&& rDestMergeRect.top < rDestMergeRect.bottom) &&
|
|||
|
(rSrceImageRect.top <= (int)nValidationLine) &&
|
|||
|
(rSrceImageRect.bottom >= (int)nEarlyBPFValidLines)){
|
|||
|
CheckError2( MergeImgs(pAnoImage->pDisplayFormImage->pImg, pBasePlusFormImg,
|
|||
|
rDestMergeRect, rSrceImageRect))
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: MakeCacheAnoImage
|
|||
|
|
|||
|
PURPOSE: Add an Ano Image to the cache.
|
|||
|
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI MakeCacheAnoImage(PANO_IMAGE *ppAnoImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PANO_IMAGE pAnoImage = 0;
|
|||
|
int nLoop;
|
|||
|
|
|||
|
|
|||
|
// If there is no room for the new entry then increase the number of file entries possible.
|
|||
|
if (!pSubSegMemory->nMaxAnoCachedEntries || pSubSegMemory->ppCachedAnoImage[pSubSegMemory->nMaxAnoCachedEntries - 1]){
|
|||
|
CheckError2( ReAllocateMemory(sizeof(PANO_IMAGE) * (pSubSegMemory->nMaxAnoCachedEntries + 1),
|
|||
|
(PPSTR) &pSubSegMemory->ppCachedAnoImage, ZERO_INIT))
|
|||
|
pSubSegMemory->nMaxAnoCachedEntries++;
|
|||
|
}
|
|||
|
|
|||
|
CheckError2( AllocateMemory(sizeof(ANO_IMAGE), (PPSTR) &pAnoImage, ZERO_INIT))
|
|||
|
|
|||
|
// Allocate the default mark.
|
|||
|
CheckError2( AllocateMemory(sizeof(MARK), (PPSTR) &pAnoImage->Annotations.pDefMark, ZERO_INIT))
|
|||
|
|
|||
|
// Save it in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
pSubSegMemory->ppCachedAnoImage[nLoop] = pAnoImage;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
if (nStatus && pAnoImage){
|
|||
|
if (pAnoImage->Annotations.pDefMark){
|
|||
|
FreeMemory((PPSTR) &pAnoImage->Annotations.pDefMark);
|
|||
|
}
|
|||
|
FreeMemory((PPSTR) &pAnoImage);
|
|||
|
}
|
|||
|
*ppAnoImage = pAnoImage;
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheFileAno
|
|||
|
|
|||
|
PURPOSE: Add a file to the cache.
|
|||
|
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheFileAno(HWND hWnd, PSTR pFileName, int nPage, PANO_IMAGE *ppAnoImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PIMAGE pImage;
|
|||
|
PANO_IMAGE pAnoImage = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
//int nOldestIndex;
|
|||
|
|
|||
|
|
|||
|
// Age all files in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
pSubSegMemory->ppCachedAnoImage[nLoop]->nAge = min(32000, pSubSegMemory->ppCachedAnoImage[nLoop]->nAge +1);
|
|||
|
}
|
|||
|
|
|||
|
// If this file is already in the cache, then return the pointer to it.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!(pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)
|
|||
|
&& pImage->nFilePageNum == nPage){
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
CheckError2( CacheFile(hWnd, pFileName, nPage, &pImage))
|
|||
|
CheckError2( MakeCacheAnoImage(&pAnoImage))
|
|||
|
|
|||
|
pImage->nLockCount++;
|
|||
|
pAnoImage->pBaseImage = pImage;
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
*ppAnoImage = pAnoImage;
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: MakeCacheImage
|
|||
|
|
|||
|
PURPOSE: Add an Image to the cache.
|
|||
|
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI MakeCacheImage(HWND hWnd, FIO_INFORMATION FioInfo, FIO_INFO_CGBW FioInfoCgbw,
|
|||
|
PIMAGE *ppImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PIMAGE pImage = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
int nOldestIndex;
|
|||
|
int nOldestAge;
|
|||
|
long lSizeOfThisImage;
|
|||
|
PSTR pTemp;
|
|||
|
int nSize;
|
|||
|
|
|||
|
|
|||
|
// Free np room in the cache.
|
|||
|
lSizeOfThisImage = ((( FioInfo.vertical_pixels * FioInfo.bits_per_sample
|
|||
|
* FioInfo.samples_per_pix) + 7) / 8) * FioInfo.horizontal_pixels;
|
|||
|
lCurrentCacheSize += lSizeOfThisImage;
|
|||
|
if (!lMaxCacheSize){
|
|||
|
LoadString((HANDLE) hInst, ID_MAX_CACHE_SIZE, Buff2, 80);
|
|||
|
nSize = 20;
|
|||
|
if (nStatus = OiGetStringfromReg(szIniSectionOi, Buff2, "6000000", Buff1, &nSize)){
|
|||
|
Error(nStatus);
|
|||
|
}
|
|||
|
lMaxCacheSize = 0;
|
|||
|
pTemp = Buff1;
|
|||
|
while(pTemp[0]){
|
|||
|
lMaxCacheSize *= 10;
|
|||
|
lMaxCacheSize += pTemp[0] - '0';
|
|||
|
pTemp++;
|
|||
|
}
|
|||
|
if (!lMaxCacheSize){
|
|||
|
lMaxCacheSize = 1; // Prevent this code from being executed again.
|
|||
|
}
|
|||
|
}
|
|||
|
while(lCurrentCacheSize >= lMaxCacheSize){
|
|||
|
// Delete the oldest ano file from the cache.
|
|||
|
if (pSubSegMemory->ppCachedImage){
|
|||
|
nOldestIndex = 0;
|
|||
|
nOldestAge = 0;
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]->nLockCount &&
|
|||
|
pSubSegMemory->ppCachedImage[nLoop]->nAge > nOldestAge){
|
|||
|
nOldestIndex = nLoop;
|
|||
|
nOldestAge = pSubSegMemory->ppCachedImage[nLoop]->nAge;
|
|||
|
}
|
|||
|
}
|
|||
|
if (pSubSegMemory->ppCachedImage[nOldestIndex]){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nOldestIndex]->nLockCount){
|
|||
|
CacheClear(&pSubSegMemory->ppCachedImage[nOldestIndex]);
|
|||
|
continue;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Delete the oldest ano file from the cache.
|
|||
|
if (pSubSegMemory->ppCachedAnoImage){
|
|||
|
nOldestIndex = 0;
|
|||
|
nOldestAge = 0;
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]->nLockCount &&
|
|||
|
pSubSegMemory->ppCachedAnoImage[nLoop]->nAge > nOldestAge){
|
|||
|
nOldestIndex = nLoop;
|
|||
|
nOldestAge = pSubSegMemory->ppCachedAnoImage[nLoop]->nAge;
|
|||
|
}
|
|||
|
}
|
|||
|
if (pSubSegMemory->ppCachedAnoImage[nOldestIndex]){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nOldestIndex]->nLockCount){
|
|||
|
CacheClearAno(&pSubSegMemory->ppCachedAnoImage[nOldestIndex]);
|
|||
|
continue;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
// No more to discard.
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
// If there is no room for the new entry then increase the number of file entries possible.
|
|||
|
if (!pSubSegMemory->nMaxCachedEntries || pSubSegMemory->ppCachedImage[pSubSegMemory->nMaxCachedEntries - 1]){
|
|||
|
CheckError2( ReAllocateMemory(sizeof(PIMAGE) * (pSubSegMemory->nMaxCachedEntries + 1),
|
|||
|
(PPSTR) &pSubSegMemory->ppCachedImage, ZERO_INIT))
|
|||
|
pSubSegMemory->nMaxCachedEntries++;
|
|||
|
}
|
|||
|
|
|||
|
CheckError2(OpenViaHandleCgbw(&pImage, 0, &FioInfo, &FioInfoCgbw))
|
|||
|
|
|||
|
// Save it in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
pSubSegMemory->ppCachedImage[nLoop] = pImage;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (FioInfoCgbw.fio_flags & FIO_ANNO_DATA){
|
|||
|
pImage->bAnnotationsPresent = TRUE;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
*ppImage = pImage;
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheFile
|
|||
|
|
|||
|
PURPOSE: Add a file to the cache.
|
|||
|
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheFile(HWND hWnd, PSTR pFileName, int nPage, PIMAGE *ppImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PIMAGE pImage = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
FIO_INFORMATION FioInfo;
|
|||
|
FIO_INFO_CGBW FioInfoCgbw;
|
|||
|
RGBQUAD PaletteTable[256];
|
|||
|
BOOL bCloseFileOnError = FALSE;
|
|||
|
HANDLE hFileProp;
|
|||
|
FIO_INFO_MISC FioInfoMisc;
|
|||
|
PIMG pImg = 0;
|
|||
|
int nTemp;
|
|||
|
|
|||
|
|
|||
|
// Age all files in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
pSubSegMemory->ppCachedImage[nLoop]->nAge = min(32000, pSubSegMemory->ppCachedImage[nLoop]->nAge +1);
|
|||
|
}
|
|||
|
|
|||
|
// If this file is already in the cache, then return the pointer to it.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pSubSegMemory->ppCachedImage[nLoop]->szFileName){
|
|||
|
if (!_stricmp(pSubSegMemory->ppCachedImage[nLoop]->szFileName, pFileName)
|
|||
|
&& pSubSegMemory->ppCachedImage[nLoop]->nFilePageNum == nPage){
|
|||
|
pImage = pSubSegMemory->ppCachedImage[nLoop];
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Open the new file.
|
|||
|
memset(&FioInfo, 0, sizeof(FIO_INFORMATION));
|
|||
|
memset(&FioInfoCgbw, 0, sizeof(FIO_INFO_CGBW));
|
|||
|
FioInfo.filename = pFileName;
|
|||
|
FioInfo.page_number = nPage;
|
|||
|
FioInfoCgbw.fio_flags = FIO_IMAGE_DATA | FIO_ANNO_DATA | FIO_HITIFF_DATA;
|
|||
|
CheckError( IMGFileOpenForRead(&hFileProp, hWnd,
|
|||
|
&FioInfo, &FioInfoCgbw, &FioInfoMisc, ALIGN_BYTE))
|
|||
|
bCloseFileOnError = TRUE;
|
|||
|
|
|||
|
FioInfo.filename = 0; // This is NULL to avoid reopening the file.
|
|||
|
FioInfo.page_number = nPage;
|
|||
|
FioInfoCgbw.lppalette_table = PaletteTable;
|
|||
|
CheckError( IMGFileGetInfo(hFileProp, hWnd, &FioInfo, &FioInfoCgbw, &FioInfoMisc))
|
|||
|
|
|||
|
FioInfo.filename = pFileName;
|
|||
|
CheckError2( MakeCacheImage(hWnd, FioInfo, FioInfoCgbw, &pImage))
|
|||
|
pImage->hWnd = hWnd;
|
|||
|
pImage->nCompressionType = FioInfoCgbw.compress_type;
|
|||
|
pImage->nFileType = FioInfo.file_type;
|
|||
|
pImage->nMaxStripSize = FioInfoCgbw.max_strip_size;
|
|||
|
|
|||
|
pImage->bUsingCache = TRUE;
|
|||
|
pImage->hFileProp = hFileProp;
|
|||
|
pImage->nStripIndex = 1;
|
|||
|
pImage->nLinesPerStrip = FioInfo.rows_strip;
|
|||
|
|
|||
|
// Setup last view info.
|
|||
|
pImage->bFileScaleValid = FioInfoMisc.bLastInfoValid;
|
|||
|
if (FioInfoMisc.bLastInfoValid){
|
|||
|
if (FioInfo.horizontal_dpi >= FioInfo.vertical_dpi){
|
|||
|
pImage->nFileScale = max(20, min(65535, FioInfoMisc.LastInfo.ScaleX * 10));
|
|||
|
}else{
|
|||
|
pImage->nFileScale = max(20, min(65535, FioInfoMisc.LastInfo.ScaleY * 10));
|
|||
|
}
|
|||
|
pImage->nFileScaleFlags = FioInfoMisc.LastInfo.Flags;
|
|||
|
pImage->nFileRotation = FioInfoMisc.LastInfo.Rotation;
|
|||
|
if (!(FioInfoMisc.LastInfo.Flags & FIO_LASTINFO_INVERT)){
|
|||
|
// This is being commented out by request of Rita.
|
|||
|
// Not setting this bit will cause all subsequent displays to be slowwer.
|
|||
|
// pImage->bArchive |= ARCHIVE_PASTED_INTO_IMAGE;
|
|||
|
}
|
|||
|
}
|
|||
|
while(pImage->nFileRotation < 0){
|
|||
|
pImage->nFileRotation += 360;
|
|||
|
}
|
|||
|
while(pImage->nFileRotation >= 360){
|
|||
|
pImage->nFileRotation -= 360;
|
|||
|
}
|
|||
|
if (!pImage->nFileRotation){
|
|||
|
pImage->bFileRotationDone = TRUE;
|
|||
|
}
|
|||
|
|
|||
|
pImage->nCompFlags = 0;
|
|||
|
if (FioInfo.compression_type & FIO_HORZ_PREDICTOR){
|
|||
|
pImage->nCompFlags |= COMPRESS_HORZ_PREDICTOR;
|
|||
|
}
|
|||
|
if (FioInfo.compression_type & FIO_PREFIXED_EOL){
|
|||
|
pImage->nCompFlags |= COMPRESS_BEGINNING_EOLS;
|
|||
|
}else if (FioInfo.compression_type & FIO_EOL){
|
|||
|
pImage->nCompFlags |= COMPRESS_ENDING_EOLS;
|
|||
|
}
|
|||
|
// A001, B001 = Byte align lines.
|
|||
|
// B901, BB01 = not byte aligned.
|
|||
|
if (((FioInfo.compression_type & 0x0fff) == 0x001)){
|
|||
|
pImage->nCompFlags |= COMPRESS_BYTE_ALIGN_LINES;
|
|||
|
}
|
|||
|
if ((FioInfo.compression_type & FIO_COMPRESSED_LTR)){
|
|||
|
pImage->nCompFlags |= COMPRESS_COMPRESSED_IS_LTR;
|
|||
|
}
|
|||
|
if ((FioInfo.compression_type & FIO_EXPAND_LTR)){
|
|||
|
pImage->nCompFlags |= COMPRESS_EXPANDED_IS_LTR;
|
|||
|
}
|
|||
|
if ((FioInfo.compression_type & FIO_NEGATE)){
|
|||
|
pImage->nCompFlags |= COMPRESS_NEGATE_BITS;
|
|||
|
}
|
|||
|
|
|||
|
if (((FioInfoCgbw.compress_type == FIO_1D) || (FioInfoCgbw.compress_type == FIO_2D))){
|
|||
|
pImage->nCompFlags &= ~COMPRESS_NEGATE_BITS;
|
|||
|
}
|
|||
|
if ((FioInfoCgbw.compress_type == FIO_PACKED)){
|
|||
|
pImage->nCompFlags ^= COMPRESS_EXPANDED_IS_LTR;
|
|||
|
}
|
|||
|
|
|||
|
// Start the background cache timer.
|
|||
|
if (pImage->nFileType == FIO_AWD){
|
|||
|
CheckError2( CacheRead(hWnd, pImage, 0xffffff))
|
|||
|
if (!pImage->bFileRotationDone){
|
|||
|
// bFileRotationDone must be set to TRUE before orientation to avoid endless recursion.
|
|||
|
pImage->bFileRotationDone = TRUE;
|
|||
|
if (pImage->nFileRotation == 90){
|
|||
|
CheckError2( CreateAnyImgBuf(&pImg, pImage->nHeight, pImage->nWidth, pImage->pImg->nType))
|
|||
|
CheckError2( RotateRight90(pImage->pImg, pImg, pImage->nWidth, pImage->nHeight))
|
|||
|
FreeImgBuf(&pImage->pImg);
|
|||
|
MoveImage(&pImg, &pImage->pImg);
|
|||
|
nTemp = pImage->nHRes;
|
|||
|
pImage->nHRes = pImage->nVRes;
|
|||
|
pImage->nVRes = nTemp;
|
|||
|
nTemp = pImage->nHeight;
|
|||
|
pImage->nHeight = pImage->nWidth;
|
|||
|
pImage->nWidth = nTemp;
|
|||
|
}else if (pImage->nFileRotation == 180){
|
|||
|
CheckError2( Flip(pImage->pImg, pImage->nWidth, pImage->nHeight))
|
|||
|
}else if (pImage->nFileRotation == 270){
|
|||
|
CheckError2( CreateAnyImgBuf(&pImg, pImage->nHeight, pImage->nWidth, pImage->pImg->nType))
|
|||
|
CheckError2( RotateRight270(pImage->pImg, pImg, pImage->nWidth, pImage->nHeight))
|
|||
|
CheckError2( FreeImgBuf(&pImage->pImg))
|
|||
|
MoveImage(&pImg, &pImage->pImg);
|
|||
|
nTemp = pImage->nHRes;
|
|||
|
pImage->nHRes = pImage->nVRes;
|
|||
|
pImage->nVRes = nTemp;
|
|||
|
nTemp = pImage->nHeight;
|
|||
|
pImage->nHeight = pImage->nWidth;
|
|||
|
pImage->nWidth = nTemp;
|
|||
|
}else{
|
|||
|
nStatus = Error(DISPLAY_INVALIDORIENTATION);
|
|||
|
pImage->bFileRotationDone = FALSE;
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}else{
|
|||
|
CacheStartTimer(hWnd);
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
FreeImgBuf(&pImg);
|
|||
|
if (nStatus && bCloseFileOnError){
|
|||
|
// This takes hWnd, not pImage->hWnd, on purpose to work in error conditions
|
|||
|
IMGFileClose(hFileProp, hWnd);
|
|||
|
if (pImage){
|
|||
|
pImage->hFileProp = 0;
|
|||
|
}
|
|||
|
}
|
|||
|
*ppImage = pImage;
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheReadOld
|
|||
|
|
|||
|
PURPOSE: Reads a number of lines from the cache.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheReadOld(HWND hWnd, PIMAGE pImage, int nLinesToRead){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
|
|||
|
int nLines;
|
|||
|
DWORD dwLines;
|
|||
|
DWORD dwLine;
|
|||
|
PSTR pAddress;
|
|||
|
int nLineWidth;
|
|||
|
int nBufferSize;
|
|||
|
FIO_INFORMATION FioInfo;
|
|||
|
FIO_INFO_CGBW FioInfoCgbw;
|
|||
|
|
|||
|
|
|||
|
if (!pImage->pImg){
|
|||
|
nStatus = Error(DISPLAY_IMAGETYPENOTSUPPORTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (nLinesToRead + pImage->nLinesRead + 10 >= pImage->nHeight){
|
|||
|
nLinesToRead = pImage->nHeight - pImage->nLinesRead;
|
|||
|
}
|
|||
|
|
|||
|
if (!pImage->hFileProp){
|
|||
|
memset(&FioInfo, 0, sizeof(FIO_INFORMATION));
|
|||
|
memset(&FioInfoCgbw, 0, sizeof(FIO_INFO_CGBW));
|
|||
|
FioInfo.filename = pImage->szFileName;
|
|||
|
FioInfo.page_number = pImage->nFilePageNum;
|
|||
|
CheckError( IMGFileOpenForRead(&pImage->hFileProp, hWnd,
|
|||
|
&FioInfo, &FioInfoCgbw, NULL, ALIGN_BYTE))
|
|||
|
pImage->hWnd = hWnd;
|
|||
|
}
|
|||
|
|
|||
|
switch (pImage->pImg->nType){
|
|||
|
case ITYPE_BI_LEVEL:
|
|||
|
nLineWidth = (pImage->nWidth + 7) / 8;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY4:
|
|||
|
case ITYPE_PAL4:
|
|||
|
nLineWidth = (pImage->nWidth + 1) / 2;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY8:
|
|||
|
case ITYPE_PAL8:
|
|||
|
case ITYPE_COMPAL8:
|
|||
|
case ITYPE_CUSPAL8:
|
|||
|
nLineWidth = pImage->nWidth;
|
|||
|
break;
|
|||
|
case ITYPE_RGB24:
|
|||
|
case ITYPE_BGR24:
|
|||
|
default:
|
|||
|
nLineWidth = pImage->nWidth * 3;
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
while (nLinesToRead){
|
|||
|
pAddress = &pImage->pImg->bImageData[0]
|
|||
|
+ (pImage->nLinesRead * pImage->pImg->nBytesPerLine);
|
|||
|
|
|||
|
nLines = max(1, min(pImage->nHeight - pImage->nLinesRead, (32767 / nLineWidth)));
|
|||
|
nBufferSize = nLines * nLineWidth;
|
|||
|
dwLine = pImage->nLinesRead;
|
|||
|
dwLines = nLines;
|
|||
|
if (nStatus = IMGFileReadData(pImage->hFileProp, pImage->hWnd, &dwLine, &dwLines,
|
|||
|
pAddress, FIO_IMAGE_DATA)){
|
|||
|
|
|||
|
// The check for "lpImage->nLinesRead < pImage->nHeight - 1" below
|
|||
|
// is caused by the fact that some of the tiff files gotten from
|
|||
|
// elsewhere (from VS WIIS) actually have 1 less line than specified.
|
|||
|
|
|||
|
if (nStatus != FIO_EOF){
|
|||
|
nStatus = Error(nStatus);
|
|||
|
goto Exit;
|
|||
|
}else{
|
|||
|
// if (nStatus == FIO_EOF && pImage->nLinesRead >= pImage->nHeight - 1){
|
|||
|
nStatus = 0;
|
|||
|
|
|||
|
// This is for AWD files where we dont know the exact height of each page beforehand.
|
|||
|
pImage->nLinesRead = dwLine;
|
|||
|
lCurrentCacheSize -= (pImage->nHeight - pImage->nLinesRead) * nLineWidth;
|
|||
|
pImage->nHeight = pImage->nLinesRead;
|
|||
|
pImage->pImg->nHeight = pImage->nHeight;
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
nLines = (int)dwLines;
|
|||
|
pImage->nLinesRead = dwLine;
|
|||
|
if (((int)nLinesToRead) >= 0){
|
|||
|
nLinesToRead -= min((int) nLinesToRead, nLines);
|
|||
|
}else{
|
|||
|
nLinesToRead -= nLines;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
if (pImage->nLinesRead >= pImage->nHeight){
|
|||
|
pImage->nLinesRead = pImage->nHeight;
|
|||
|
pImage->bCacheValid = TRUE;
|
|||
|
}
|
|||
|
|
|||
|
if (nStatus || pImage->bCacheValid){
|
|||
|
IMGFileClose(pImage->hFileProp, pImage->hWnd);
|
|||
|
pImage->hFileProp = 0;
|
|||
|
pImage->hWnd = 0;
|
|||
|
}
|
|||
|
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
int PASCAL IMGFileReadRawm (HWND window_handle, int strip_index,
|
|||
|
PINT this_many_bytes, PSTR buffer_address,
|
|||
|
long *bytes_remain, HANDLE hprop);
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheReadNew
|
|||
|
|
|||
|
PURPOSE: Reads a number of lines from the cache.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheReadNew(HWND hWnd, PIMAGE pImage, int nLinesToRead){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
|
|||
|
int nLines;
|
|||
|
PSTR pAddress;
|
|||
|
int nLineWidth;
|
|||
|
int nBufferSize;
|
|||
|
FIO_INFORMATION FioInfo;
|
|||
|
FIO_INFO_CGBW FioInfoCgbw;
|
|||
|
PBYTE pCompressedBuffer = 0;
|
|||
|
long lSize;
|
|||
|
long lRemaining;
|
|||
|
int nCompressedBufferSize;
|
|||
|
|
|||
|
|
|||
|
if (!pImage->pImg){
|
|||
|
nStatus = Error(DISPLAY_IMAGETYPENOTSUPPORTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (nLinesToRead + pImage->nLinesRead + 10 >= pImage->nHeight){
|
|||
|
nLinesToRead = pImage->nHeight - pImage->nLinesRead;
|
|||
|
}
|
|||
|
|
|||
|
if (!pImage->hFileProp){
|
|||
|
memset(&FioInfo, 0, sizeof(FIO_INFORMATION));
|
|||
|
memset(&FioInfoCgbw, 0, sizeof(FIO_INFO_CGBW));
|
|||
|
FioInfo.filename = pImage->szFileName;
|
|||
|
FioInfo.page_number = pImage->nFilePageNum;
|
|||
|
CheckError( IMGFileOpenForRead(&pImage->hFileProp, hWnd,
|
|||
|
&FioInfo, &FioInfoCgbw, NULL, ALIGN_BYTE))
|
|||
|
pImage->hWnd = hWnd;
|
|||
|
}
|
|||
|
|
|||
|
switch (pImage->pImg->nType){
|
|||
|
case ITYPE_BI_LEVEL:
|
|||
|
nLineWidth = (pImage->nWidth + 7) / 8;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY4:
|
|||
|
case ITYPE_PAL4:
|
|||
|
nLineWidth = (pImage->nWidth + 1) / 2;
|
|||
|
break;
|
|||
|
case ITYPE_GRAY8:
|
|||
|
case ITYPE_PAL8:
|
|||
|
case ITYPE_COMPAL8:
|
|||
|
case ITYPE_CUSPAL8:
|
|||
|
nLineWidth = pImage->nWidth;
|
|||
|
break;
|
|||
|
case ITYPE_RGB24:
|
|||
|
case ITYPE_BGR24:
|
|||
|
default:
|
|||
|
nLineWidth = pImage->nWidth * 3;
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
nCompressedBufferSize = pImage->nMaxStripSize + 4;
|
|||
|
CheckError2( AllocateMemory(nCompressedBufferSize, &pCompressedBuffer, NO_INIT))
|
|||
|
|
|||
|
if (pImage->nLinesRead == 0){
|
|||
|
pImage->nStripIndex = 1;
|
|||
|
}
|
|||
|
|
|||
|
while (nLinesToRead){
|
|||
|
pAddress = &pImage->pImg->bImageData[0] + (pImage->nLinesRead * pImage->pImg->nBytesPerLine);
|
|||
|
|
|||
|
nLines = max(1, min(pImage->nHeight - pImage->nLinesRead, (32767 / nLineWidth)));
|
|||
|
nBufferSize = nLines * nLineWidth;
|
|||
|
|
|||
|
lSize = nCompressedBufferSize;
|
|||
|
if (nStatus = IMGFileReadRawm(pImage->hWnd, pImage->nStripIndex,
|
|||
|
&lSize, pCompressedBuffer, &lRemaining, pImage->hFileProp)){
|
|||
|
|
|||
|
// The check for "lpImage->nLinesRead < pImage->nHeight - 1" below
|
|||
|
// is caused by the fact that some of the tiff files gotten from
|
|||
|
// elsewhere (from VS WIIS) actually have 1 less line than specified.
|
|||
|
|
|||
|
if (nStatus != FIO_EOF || pImage->nLinesRead < pImage->nHeight - 1){
|
|||
|
nStatus = Error(nStatus);
|
|||
|
goto Exit;
|
|||
|
}else{
|
|||
|
// if (nStatus == FIO_EOF && pImage->nLinesRead >= pImage->nHeight - 1){
|
|||
|
nStatus = 0;
|
|||
|
pImage->nLinesRead = pImage->nHeight;
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
if (lRemaining){
|
|||
|
nStatus = Error(DISPLAY_DATACORRUPTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
CheckError2( DecompressImage(pImage->nWidth, pImage->pImg->nBytesPerLine,
|
|||
|
min( pImage->nLinesPerStrip, pImage->nHeight - pImage->nLinesRead),
|
|||
|
pAddress, pImage->pImg->nType, pCompressedBuffer, lSize,
|
|||
|
pImage->nCompressionType & FIO_TYPES_MASK, pImage->nCompFlags))
|
|||
|
|
|||
|
pImage->nStripIndex++;
|
|||
|
pImage->nLinesRead += pImage->nLinesPerStrip;
|
|||
|
|
|||
|
nLinesToRead -= min((int) nLinesToRead, pImage->nLinesPerStrip);
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
if (pCompressedBuffer){
|
|||
|
FreeMemory(&pCompressedBuffer);
|
|||
|
}
|
|||
|
if (pImage->nLinesRead >= pImage->nHeight){
|
|||
|
pImage->nLinesRead = pImage->nHeight;
|
|||
|
pImage->bCacheValid = TRUE;
|
|||
|
}
|
|||
|
|
|||
|
if (nStatus || pImage->bCacheValid){
|
|||
|
IMGFileClose(pImage->hFileProp, pImage->hWnd);
|
|||
|
pImage->hFileProp = 0;
|
|||
|
pImage->hWnd = 0;
|
|||
|
}
|
|||
|
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheRead
|
|||
|
|
|||
|
PURPOSE: Reads a number of lines from the cache.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheRead(HWND hWnd, PIMAGE pImage, int nLinesToRead){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
FIO_INFORMATION FioInfo;
|
|||
|
FIO_INFO_CGBW FioInfoCgbw;
|
|||
|
BOOL bRead = FALSE;
|
|||
|
|
|||
|
|
|||
|
if (pImage->bCacheValid){
|
|||
|
goto Exit; // This is not an error.
|
|||
|
}
|
|||
|
|
|||
|
if (!pImage->hFileProp){
|
|||
|
memset(&FioInfo, 0, sizeof(FIO_INFORMATION));
|
|||
|
memset(&FioInfoCgbw, 0, sizeof(FIO_INFO_CGBW));
|
|||
|
FioInfo.filename = pImage->szFileName;
|
|||
|
FioInfo.page_number = pImage->nFilePageNum;
|
|||
|
CheckError( IMGFileOpenForRead(&pImage->hFileProp, hWnd,
|
|||
|
&FioInfo, &FioInfoCgbw, NULL, ALIGN_BYTE))
|
|||
|
pImage->hWnd = hWnd;
|
|||
|
}
|
|||
|
|
|||
|
if (pImage->nFileType == FIO_TIF){
|
|||
|
switch (pImage->nCompressionType){
|
|||
|
case FIO_0D:
|
|||
|
case FIO_1D:
|
|||
|
case FIO_2D:
|
|||
|
case FIO_PACKED:
|
|||
|
case FIO_LZW:
|
|||
|
CheckError2( CacheReadNew(hWnd, pImage, nLinesToRead))
|
|||
|
bRead = TRUE;
|
|||
|
break;
|
|||
|
|
|||
|
case FIO_GLZW:
|
|||
|
case FIO_TJPEG:
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (!bRead){
|
|||
|
CheckError2( CacheReadOld(hWnd, pImage, nLinesToRead))
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheClearAno
|
|||
|
|
|||
|
PURPOSE: Discard annotated files from the cache.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheClearAno(PANO_IMAGE *ppAnoImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
PIMAGE pImage;
|
|||
|
PMARK pMark;
|
|||
|
int nMarkIndex;
|
|||
|
|
|||
|
|
|||
|
pAnoImage = *ppAnoImage;
|
|||
|
|
|||
|
if (pAnoImage->nLockCount){
|
|||
|
nStatus = Error(DISPLAY_CACHEFILEINUSE);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
pImage->nLockCount = max(0, pImage->nLockCount -1);
|
|||
|
if (!pImage->nLockCount && (!pImage->bUsingCache || pImage->bArchive
|
|||
|
|| (pImage->szFileName[0] == '\0'))){
|
|||
|
// If not nsing the cache or the image has been modified
|
|||
|
// and not saved yet, then throw it away.
|
|||
|
CheckError2( CacheClear(&pImage))
|
|||
|
pAnoImage->pBaseImage = 0;
|
|||
|
}
|
|||
|
}
|
|||
|
// DON'T free the FormImage or the DisplayFormImage.
|
|||
|
// Freeing the mark will free the form image.
|
|||
|
|
|||
|
// Delete all annotations.
|
|||
|
for (nMarkIndex = 0; nMarkIndex < pAnoImage->Annotations.nMarks; nMarkIndex++){
|
|||
|
pMark = pAnoImage->Annotations.ppMarks[nMarkIndex];
|
|||
|
pMark->Attributes.dwPermissions = ACL_ALL;
|
|||
|
}
|
|||
|
CheckError2( DeleteAnnotations(pAnoImage))
|
|||
|
|
|||
|
// Free the default mark.
|
|||
|
pMark = pAnoImage->Annotations.pDefMark;
|
|||
|
CheckError2( DeleteMarkNamedBlocks(pMark))
|
|||
|
CheckError2( FreeMemory((PPSTR) &pMark))
|
|||
|
pAnoImage->Annotations.pDefMark = NULL;
|
|||
|
|
|||
|
// Find the entry in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (pSubSegMemory->ppCachedAnoImage[nLoop] == pAnoImage){
|
|||
|
FreeMemory((PPSTR) &pSubSegMemory->ppCachedAnoImage[nLoop]);
|
|||
|
// Compress the cache.
|
|||
|
for (nLoop += 1; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
pSubSegMemory->ppCachedAnoImage[nLoop - 1] = pSubSegMemory->ppCachedAnoImage[nLoop];
|
|||
|
pSubSegMemory->ppCachedAnoImage[nLoop] = 0;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheClear
|
|||
|
|
|||
|
PURPOSE: Discard files from the cache
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheClear(PIMAGE *ppImage){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
int nLoop;
|
|||
|
PIMAGE pImage = *ppImage;
|
|||
|
long lSizeOfThisImage;
|
|||
|
|
|||
|
|
|||
|
if (!pImage->pImg){
|
|||
|
nStatus = Error(DISPLAY_IMAGETYPENOTSUPPORTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (pImage->nLockCount){
|
|||
|
nStatus = Error(DISPLAY_CACHEFILEINUSE);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
switch (pImage->pImg->nType){
|
|||
|
case ITYPE_BI_LEVEL: lSizeOfThisImage = 1; break;
|
|||
|
case ITYPE_GRAY4: lSizeOfThisImage = 4; break;
|
|||
|
case ITYPE_GRAY8: lSizeOfThisImage = 8; break;
|
|||
|
case ITYPE_PAL4: lSizeOfThisImage = 4; break;
|
|||
|
case ITYPE_CUSPAL8: lSizeOfThisImage = 8; break;
|
|||
|
case ITYPE_COMPAL8: lSizeOfThisImage = 8; break;
|
|||
|
case ITYPE_RGB24: lSizeOfThisImage = 24; break;
|
|||
|
case ITYPE_BGR24: lSizeOfThisImage = 24; break;
|
|||
|
default:
|
|||
|
nStatus = Error(DISPLAY_INTERNALDATAERROR);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
lSizeOfThisImage = ((lSizeOfThisImage * pImage->nWidth) + 7) / 8;
|
|||
|
lSizeOfThisImage *= pImage->nHeight;
|
|||
|
|
|||
|
lCurrentCacheSize -= lSizeOfThisImage;
|
|||
|
|
|||
|
if (pImage->hFileProp){
|
|||
|
IMGFileClose(pImage->hFileProp, pImage->hWnd);
|
|||
|
pImage->hFileProp = 0;
|
|||
|
pImage->hWnd = 0;
|
|||
|
}
|
|||
|
|
|||
|
FreeImgBuf(&pImage->pImg);
|
|||
|
|
|||
|
if (pImage->hCusPal){
|
|||
|
DeleteObject(pImage->hCusPal);
|
|||
|
}
|
|||
|
|
|||
|
// Find the entry in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (pSubSegMemory->ppCachedImage[nLoop] == pImage){
|
|||
|
FreeMemory((PPSTR) &pSubSegMemory->ppCachedImage[nLoop]);
|
|||
|
// Compress the cache.
|
|||
|
for (nLoop++; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
pSubSegMemory->ppCachedImage[nLoop - 1] = pSubSegMemory->ppCachedImage[nLoop];
|
|||
|
pSubSegMemory->ppCachedImage[nLoop] = 0;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheStartTimer
|
|||
|
|
|||
|
PURPOSE: Causes the cache to be activated for processing in the background.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheStartTimer(HWND hWnd){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
TIMERPROC pfnTimer;
|
|||
|
|
|||
|
if (!bTimerRunning){
|
|||
|
hTimerWnd = hWnd;
|
|||
|
pfnTimer = (TIMERPROC) GetProcAddress(hInst, "CacheTimerProc");
|
|||
|
if (SetTimer(hTimerWnd, CACHE_TIMER_ID, CACHE_TIMER_CYCLE, pfnTimer)){
|
|||
|
bTimerRunning = TRUE;
|
|||
|
}else{
|
|||
|
nStatus = Error(DISPLAY_DATACORRUPTED);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return nStatus;
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheStopTimer
|
|||
|
|
|||
|
PURPOSE: Stops the cache from being activated.
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheStopTimer(HWND hWnd){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
if (bTimerRunning){
|
|||
|
KillTimer(hTimerWnd, CACHE_TIMER_ID);
|
|||
|
bTimerRunning = FALSE;
|
|||
|
}
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/*****************************************************************************
|
|||
|
|
|||
|
FUNCTION: CacheTimerProc
|
|||
|
|
|||
|
PURPOSE: Discard files from the cache
|
|||
|
|
|||
|
*****************************************************************************/
|
|||
|
|
|||
|
int WINAPI CacheTimerProc(HWND hWnd, int Msg, int nTimerId, DWORD dwCurrentTime){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
PIMAGE pImage;
|
|||
|
int nLoop;
|
|||
|
|
|||
|
|
|||
|
// Prevent Multiprocessing in this code.
|
|||
|
CheckError2( LockMutex())
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!pSubSegMemory->ppCachedAnoImage[nLoop]){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pSubSegMemory->ppCachedAnoImage[nLoop]->pBaseImage->bAnnotationsPresent
|
|||
|
&& !pSubSegMemory->ppCachedAnoImage[nLoop]->bAnnotationsAlreadyRead){
|
|||
|
ReadAnnotationsFromFile(hWnd, pSubSegMemory->ppCachedAnoImage[nLoop],
|
|||
|
&pSubSegMemory->ppCachedAnoImage[nLoop]->Annotations.ppMarks,
|
|||
|
&pSubSegMemory->ppCachedAnoImage[nLoop]->Annotations.nMarks);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (pImage = pSubSegMemory->ppCachedImage[nLoop]){
|
|||
|
if (!pImage->bCacheValid && pImage->bUsingCache){
|
|||
|
CheckError2( CacheRead(hWnd, pImage, 1))
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
if (pImage->bCacheValid && pImage->hFileProp){
|
|||
|
if (nStatus || pImage->bCacheValid){
|
|||
|
IMGFileClose(pImage->hFileProp, pImage->hWnd);
|
|||
|
pImage->hFileProp = 0;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// If we get here, it means that there are currently no images needing cache.
|
|||
|
CacheStopTimer(hWnd);
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
// Allow Multiprocessing again.
|
|||
|
UnlockMutex();
|
|||
|
if (nStatus){
|
|||
|
CacheStopTimer(hWnd);
|
|||
|
}
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: BlockedAnoReadChar
|
|||
|
|
|||
|
PURPOSE: Reads a char.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
char WINAPI BlockedAnoReadChar(HWND hWnd, PANO_IMAGE pAnoImage, PINT pnStatus){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
char cTemp;
|
|||
|
|
|||
|
nStatus = BlockedAnoRead(hWnd, pAnoImage, 1, (PSTR) &cTemp);
|
|||
|
|
|||
|
if (!*pnStatus){
|
|||
|
*pnStatus = nStatus;
|
|||
|
}
|
|||
|
return(cTemp);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: BlockedAnoReadShort
|
|||
|
|
|||
|
PURPOSE: Reads a short.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
short WINAPI BlockedAnoReadShort(HWND hWnd, PANO_IMAGE pAnoImage, PINT pnStatus){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
short shTemp;
|
|||
|
|
|||
|
nStatus = BlockedAnoRead(hWnd, pAnoImage, 2, (PSTR) &shTemp);
|
|||
|
|
|||
|
if (!*pnStatus){
|
|||
|
*pnStatus = nStatus;
|
|||
|
}
|
|||
|
return(shTemp);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: BlockedAnoReadLong
|
|||
|
|
|||
|
PURPOSE: Reads a long.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
long WINAPI BlockedAnoReadLong(HWND hWnd, PANO_IMAGE pAnoImage, PINT pnStatus){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
long lTemp;
|
|||
|
|
|||
|
nStatus = BlockedAnoRead(hWnd, pAnoImage, 4, (PSTR) &lTemp);
|
|||
|
|
|||
|
if (!*pnStatus){
|
|||
|
*pnStatus = nStatus;
|
|||
|
}
|
|||
|
return(lTemp);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: BlockedAnoReadStr
|
|||
|
|
|||
|
PURPOSE: Reads a string.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
void WINAPI BlockedAnoReadStr(HWND hWnd, PANO_IMAGE pAnoImage, PINT pnStatus, int nSize, PSTR pBuffer){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
nStatus = BlockedAnoRead(hWnd, pAnoImage, nSize, pBuffer);
|
|||
|
|
|||
|
if (!*pnStatus){
|
|||
|
*pnStatus = nStatus;
|
|||
|
}
|
|||
|
return;
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: ReadMarkAttributes16
|
|||
|
|
|||
|
PURPOSE: Reads mark attributes structure.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI ReadMarkAttributes16(HWND hWnd, PANO_IMAGE pAnoImage, PMARK pMark){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
(int) pMark->Attributes.uType = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lrBounds.left = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lrBounds.top = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lrBounds.right = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lrBounds.bottom = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor1.rgbBlue = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor1.rgbGreen = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor1.rgbRed = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor1.rgbReserved = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor2.rgbBlue = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor2.rgbGreen = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor2.rgbRed = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.rgbColor2.rgbReserved = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.bHighlighting = (BOOL) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.bTransparent = (BOOL) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
(int) pMark->Attributes.uLineSize = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.uStartingPoint = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.uEndPoint = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfHeight = (int) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfWidth = (int) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfEscapement = (int) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfOrientation = (int) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfWeight = (int) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfItalic = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfUnderline = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfStrikeOut = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfCharSet = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfOutPrecision = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfClipPrecision = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfQuality = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lfFont.lfPitchAndFamily = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
BlockedAnoReadStr(hWnd, pAnoImage, &nStatus, 32, (PSTR) &pMark->Attributes.lfFont.lfFaceName[0]);
|
|||
|
pMark->Attributes.bMinimizable = (BOOL) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.Time = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.bVisible = (BOOL) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.dwPermissions = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[0] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[1] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[2] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[3] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[4] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[5] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[6] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[7] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[8] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pMark->Attributes.lReserved[9] = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: ReadAnnotationsFromFile
|
|||
|
|
|||
|
PURPOSE: Reads all annotations from a file.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI ReadAnnotationsFromFile(HWND hWnd, PANO_IMAGE pAnoImage,
|
|||
|
PMARK **pppMarks, int *pnMarks){
|
|||
|
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
FIO_INFO_CGBW FioInfoCgbw;
|
|||
|
FIO_INFORMATION FioInfo;
|
|||
|
PIMAGE pImage;
|
|||
|
PSTR pTemp;
|
|||
|
PMARK pMark=0;
|
|||
|
BOOL bFileOpenedHere = FALSE;
|
|||
|
|
|||
|
pAnoImage->lAnoStart = 0;
|
|||
|
pImage = pAnoImage->pBaseImage;
|
|||
|
|
|||
|
if (!pImage->szFileName[0]){
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
if (!pImage->hFileProp){
|
|||
|
memset(&FioInfoCgbw, 0, sizeof(FIO_INFO_CGBW));
|
|||
|
memset(&FioInfo, 0, sizeof(FIO_INFORMATION));
|
|||
|
FioInfo.filename = pImage->szFileName;
|
|||
|
FioInfo.page_number = pImage->nFilePageNum;
|
|||
|
FioInfoCgbw.fio_flags = FIO_IMAGE_DATA | FIO_ANNO_DATA | FIO_HITIFF_DATA;
|
|||
|
CheckError( IMGFileOpenForRead(&pImage->hFileProp, hWnd,
|
|||
|
&FioInfo, &FioInfoCgbw, NULL, ALIGN_BYTE))
|
|||
|
pImage->hWnd = hWnd;
|
|||
|
bFileOpenedHere = TRUE;
|
|||
|
}
|
|||
|
|
|||
|
CheckError2( ReadAnnotations(pImage->hWnd, pAnoImage, pppMarks, pnMarks))
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
// add the default mark stuff
|
|||
|
if (!nStatus){
|
|||
|
// add default group and index
|
|||
|
pMark = pAnoImage->Annotations.pDefMark;
|
|||
|
pTemp = 0;
|
|||
|
GetAMarkNamedBlock(pMark, szOiGroup, (PPSTR) &pTemp);
|
|||
|
if (!pTemp){
|
|||
|
LoadString(hInst, ID_UNTITLED, Buff1, 16);
|
|||
|
AddAMarkNamedBlock(pMark, szOiGroup, (PPSTR) &pTemp, lstrlen(Buff1) + 1);
|
|||
|
memcpy(pTemp, Buff1, lstrlen(Buff1) + 1);
|
|||
|
}
|
|||
|
// Update file with index# info.
|
|||
|
pTemp = 0;
|
|||
|
GetAMarkNamedBlock(pMark, szOiIndex, (PPSTR) &pTemp);
|
|||
|
if (!pTemp){
|
|||
|
AddAMarkNamedBlock(pMark, szOiIndex, (PPSTR) &pTemp, 10);
|
|||
|
strcpy(pTemp, "0");
|
|||
|
}
|
|||
|
}
|
|||
|
if (bFileOpenedHere){
|
|||
|
IMGFileClose(pImage->hFileProp, pImage->hWnd);
|
|||
|
pImage->hFileProp = 0;
|
|||
|
pImage->hWnd = 0;
|
|||
|
}
|
|||
|
pAnoImage->bAnnotationsAlreadyRead = TRUE;
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
//
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: ReadAnnotations
|
|||
|
|
|||
|
PURPOSE: Reads all annotations.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI ReadAnnotations(HWND hWnd, PANO_IMAGE pAnoImage,
|
|||
|
PMARK **pppMarks, int *pnMarks){
|
|||
|
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
int nNamedBlockIndex;
|
|||
|
|
|||
|
PMARK pDefMark;
|
|||
|
int nIndex;
|
|||
|
PMARK pMark = 0;
|
|||
|
long lTemp[2];
|
|||
|
int nIntSize = 2;
|
|||
|
PSTR pTemp = 0;
|
|||
|
BOOL bDone;
|
|||
|
BOOL bThrowItAway;
|
|||
|
BOOL bDontRead;
|
|||
|
PAN_NEW_ROTATE_STRUCT pAnRotation = NULL;
|
|||
|
int nMarkIndex;
|
|||
|
PAN_POINTS pPoints;
|
|||
|
LPLRECT plrRect;
|
|||
|
int nIDs;
|
|||
|
LPOI_ACL_BLOCK pAclBlock;
|
|||
|
BITMAPINFOHEADER *pDib;
|
|||
|
RGBQUAD *pRGBQuad;
|
|||
|
int nMaxPoints;
|
|||
|
int nPoints;
|
|||
|
int nLoop;
|
|||
|
NAMED_BLOCK NamedBlock;
|
|||
|
PSTR pBlock;
|
|||
|
LPOIAN_TEXTPRIVDATA pTextPrivData = NULL;
|
|||
|
|
|||
|
|
|||
|
pAnoImage->lAnoStart = 0;
|
|||
|
|
|||
|
if (nStatus = BlockedAnoRead(hWnd, pAnoImage, 4, (PSTR) &lTemp)){
|
|||
|
if (nStatus == DISPLAY_EOF){ // Ignor Real EOFs.
|
|||
|
nStatus = 0;
|
|||
|
}
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
if (lTemp[0] == 1){ // 32 bit Intel.
|
|||
|
bDontRead = FALSE;
|
|||
|
while(1){
|
|||
|
if (!bDontRead){
|
|||
|
if (nStatus = BlockedAnoRead(hWnd, pAnoImage, 8, (PSTR) lTemp)){
|
|||
|
if (nStatus != DISPLAY_EOF){ // Ignor Real EOFs.
|
|||
|
Error(nStatus);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
nStatus = 0;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
bDontRead = FALSE;
|
|||
|
|
|||
|
switch (lTemp[0]){
|
|||
|
case SAVE_ANO_DEFAULT_MARK_NAMED_BLOCK:
|
|||
|
pMark = pAnoImage->Annotations.pDefMark;
|
|||
|
CheckError( BlockedAnoRead(hWnd, pAnoImage, 8, &NamedBlock.szName[0]))
|
|||
|
CheckError( BlockedAnoRead(hWnd, pAnoImage, 4, (PSTR) &NamedBlock.lSize))
|
|||
|
bThrowItAway = FALSE;
|
|||
|
if (!memcmp(NamedBlock.szName, szOiAnoDat, 8)){
|
|||
|
if (pMark->pOiAnoDat){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiGroup, 8)){
|
|||
|
if (pMark->pOiGroup){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiSelect, 8)){
|
|||
|
if (pMark->pOiSelect){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiIndex, 8)){
|
|||
|
if (pMark->pOiIndex){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else{
|
|||
|
for (nNamedBlockIndex = 0; nNamedBlockIndex < pMark->nNamedBlocks; nNamedBlockIndex++){
|
|||
|
if (!memcmp(pMark->ppNamedBlock[nNamedBlockIndex]->szName, NamedBlock.szName, 8)){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (bThrowItAway){
|
|||
|
// Duplicate name. Read it and throw it away.
|
|||
|
CheckError2( ReAllocateMemory(NamedBlock.lSize, &pTemp, ZERO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, NamedBlock.lSize, pTemp))
|
|||
|
CheckError2( FreeMemory(&pTemp))
|
|||
|
}else{
|
|||
|
pBlock = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, NamedBlock.szName, &pBlock, NamedBlock.lSize))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, NamedBlock.lSize, pBlock))
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case SAVE_ANO_MARK_ATTRIBUTES:
|
|||
|
CheckError2( ReAllocateMemory(sizeof(PMARK) * (*pnMarks + 2), (PPSTR) &(*pppMarks), ZERO_INIT))
|
|||
|
CheckError2( AllocateMemory(sizeof(MARK), (PPSTR) &((*pppMarks)[*pnMarks]), ZERO_INIT))
|
|||
|
pMark = (*pppMarks)[*pnMarks];
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], (PSTR) &pMark->Attributes))
|
|||
|
(*pnMarks)++;
|
|||
|
break;
|
|||
|
|
|||
|
case SAVE_ANO_MARK_NAMED_BLOCK:
|
|||
|
if (!pMark){
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, 8, &NamedBlock.szName[0]))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, 4, (PSTR) &NamedBlock.lSize))
|
|||
|
bThrowItAway = FALSE;
|
|||
|
if (!memcmp(NamedBlock.szName, szOiAnoDat, 8)){
|
|||
|
if (pMark->pOiAnoDat){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiGroup, 8)){
|
|||
|
if (pMark->pOiGroup){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiSelect, 8)){
|
|||
|
if (pMark->pOiSelect){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(NamedBlock.szName, szOiIndex, 8)){
|
|||
|
if (pMark->pOiIndex){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else{
|
|||
|
for (nNamedBlockIndex = 0; nNamedBlockIndex < pMark->nNamedBlocks; nNamedBlockIndex++){
|
|||
|
if (!memcmp(pMark->ppNamedBlock[nNamedBlockIndex]->szName, NamedBlock.szName, 8)){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (bThrowItAway){
|
|||
|
// Duplicate name. Read it and throw it away.
|
|||
|
CheckError2( ReAllocateMemory(NamedBlock.lSize, &pTemp, ZERO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, NamedBlock.lSize, pTemp))
|
|||
|
CheckError2( FreeMemory(&pTemp))
|
|||
|
}else{
|
|||
|
pBlock = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, NamedBlock.szName, &pBlock, NamedBlock.lSize))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, NamedBlock.lSize, pBlock))
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}else if (lTemp[0] == 0){ // 16 bit Intel.
|
|||
|
bDontRead = FALSE;
|
|||
|
while(!nStatus){
|
|||
|
if (!bDontRead){
|
|||
|
if (nStatus = BlockedAnoRead(hWnd, pAnoImage, 8, (PSTR) lTemp)){
|
|||
|
if (nStatus != DISPLAY_EOF){ // Ignor Real EOFs.
|
|||
|
Error(nStatus);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
nStatus = 0;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
bDontRead = FALSE;
|
|||
|
|
|||
|
switch (lTemp[0]){
|
|||
|
case SAVE_ANO_DEFAULT_MARK_NAMED_BLOCK:
|
|||
|
pMark = pAnoImage->Annotations.pDefMark;
|
|||
|
CheckError2( AllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
lTemp[1] = ((PNAMED_BLOCK) pTemp)->lSize;
|
|||
|
|
|||
|
bThrowItAway = FALSE;
|
|||
|
if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiAnoDat, 8)){
|
|||
|
if (pMark->pOiAnoDat){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}else{
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
pMark->pOiAnoDat = pTemp;
|
|||
|
pMark->nOiAnoDatSize = lTemp[1];
|
|||
|
pTemp = 0;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiGroup, 8)){
|
|||
|
if (pMark->pOiGroup){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}else{
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
pMark->pOiGroup = pTemp;
|
|||
|
pMark->nOiGroupSize = lTemp[1];
|
|||
|
pTemp = 0;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiSelect, 8)){
|
|||
|
if (pMark->pOiSelect){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}else{
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
pMark->pOiSelect = pTemp;
|
|||
|
pMark->nOiSelectSize = lTemp[1];
|
|||
|
pTemp = 0;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiIndex, 8)){
|
|||
|
if (pMark->pOiIndex){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}else{
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
pMark->pOiIndex = pTemp;
|
|||
|
pMark->nOiIndexSize = lTemp[1];
|
|||
|
pTemp = 0;
|
|||
|
}
|
|||
|
}else{
|
|||
|
for (nNamedBlockIndex = 0; nNamedBlockIndex < pMark->nNamedBlocks; nNamedBlockIndex++){
|
|||
|
if (!memcmp(pMark->ppNamedBlock[nNamedBlockIndex]->szName, ((PNAMED_BLOCK) pTemp)->szName, 8)){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
if (bThrowItAway){
|
|||
|
break;
|
|||
|
}
|
|||
|
CheckError2( ReAllocateMemory(sizeof(PNAMED_BLOCK) * (pMark->nNamedBlocks + 1),
|
|||
|
(PPSTR) &pMark->ppNamedBlock, ZERO_INIT))
|
|||
|
pMark->ppNamedBlock[nNamedBlockIndex] = (PNAMED_BLOCK) pTemp;
|
|||
|
pMark->nNamedBlocks++;
|
|||
|
|
|||
|
CheckError2( AllocateMemory(lTemp[1], &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
pMark->ppNamedBlock[nNamedBlockIndex]->pBlock = pTemp;
|
|||
|
pTemp = 0;
|
|||
|
}
|
|||
|
if (bThrowItAway){
|
|||
|
// Duplicate name. Read it and throw it away.
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, ZERO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
CheckError2( FreeMemory(&pTemp))
|
|||
|
}
|
|||
|
pMark = 0;
|
|||
|
break;
|
|||
|
|
|||
|
case SAVE_ANO_MARK_ATTRIBUTES:
|
|||
|
if (lTemp[1] != 138){
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
CheckError2( ReAllocateMemory(sizeof(PMARK) * (*pnMarks + 2),
|
|||
|
(PPSTR) &(*pppMarks), ZERO_INIT))
|
|||
|
CheckError2( AllocateMemory(sizeof(MARK),
|
|||
|
(PPSTR) &((*pppMarks)[*pnMarks]), ZERO_INIT))
|
|||
|
pMark = (*pppMarks)[*pnMarks];
|
|||
|
(*pnMarks)++;
|
|||
|
CheckError2( ReadMarkAttributes16(hWnd, pAnoImage, pMark))
|
|||
|
break;
|
|||
|
|
|||
|
case SAVE_ANO_MARK_NAMED_BLOCK:
|
|||
|
if (!pMark){
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
CheckError2( AllocateMemory(sizeof(NAMED_BLOCK), &pTemp, NO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
lTemp[1] = ((PNAMED_BLOCK) pTemp)->lSize;
|
|||
|
bThrowItAway = FALSE;
|
|||
|
if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiAnoDat, 8)){
|
|||
|
if (pMark->pOiAnoDat){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiGroup, 8)){
|
|||
|
if (pMark->pOiGroup){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiSelect, 8)){
|
|||
|
if (pMark->pOiSelect){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiIndex, 8)){
|
|||
|
if (pMark->pOiIndex){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
}
|
|||
|
}else{
|
|||
|
for (nNamedBlockIndex = 0; nNamedBlockIndex < pMark->nNamedBlocks; nNamedBlockIndex++){
|
|||
|
if (!memcmp(pMark->ppNamedBlock[nNamedBlockIndex]->szName, ((PNAMED_BLOCK) pTemp)->szName, 8)){
|
|||
|
bThrowItAway = TRUE;
|
|||
|
break;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (bThrowItAway){
|
|||
|
// Duplicate name. Read it and throw it away.
|
|||
|
CheckError2( ReAllocateMemory(lTemp[1], &pTemp, ZERO_INIT))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
CheckError2( FreeMemory(&pTemp))
|
|||
|
}else{
|
|||
|
bDone = FALSE;
|
|||
|
if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiAnoDat, 8)){
|
|||
|
switch ((int) pMark->Attributes.uType){
|
|||
|
case OIOP_AN_LINE:
|
|||
|
case OIOP_AN_FREEHAND:
|
|||
|
// AN_POINTS.
|
|||
|
nMaxPoints = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
nPoints = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pPoints = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiAnoDat, (PPSTR) &pPoints,
|
|||
|
sizeof(AN_POINTS) + (sizeof(POINT) * nMaxPoints)))
|
|||
|
pPoints->nMaxPoints = nMaxPoints;
|
|||
|
pPoints->nPoints = nPoints;
|
|||
|
for (nLoop = 0; nLoop < nMaxPoints + 1; nLoop++){
|
|||
|
pPoints->ptPoint[nLoop].x = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pPoints->ptPoint[nLoop].y = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
}
|
|||
|
bDone = TRUE;
|
|||
|
break;
|
|||
|
|
|||
|
case OIOP_AN_IMAGE:
|
|||
|
case OIOP_AN_IMAGE_BY_REFERENCE:
|
|||
|
case OIOP_AN_FORM:
|
|||
|
pAnRotation = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiAnoDat, (PPSTR) &pAnRotation,
|
|||
|
sizeof(AN_NEW_ROTATE_STRUCT)))
|
|||
|
|
|||
|
if (lTemp[1] == 12){
|
|||
|
// pre 3.7.2 image rotation data blocks
|
|||
|
pAnRotation->rotation = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->scale = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nHRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nVRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nOrigHRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nOrigVRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->bFormMark = FALSE;
|
|||
|
pAnRotation->bClipboardOp = FALSE;
|
|||
|
|
|||
|
}else if (lTemp[1] == 28){
|
|||
|
// 3.7.2 image rotation data blocks
|
|||
|
pAnRotation->rotation = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->scale = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nHRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nVRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nOrigHRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nOrigVRes = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->bFormMark = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->bClipboardOp = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[0] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[1] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[2] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[3] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[4] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAnRotation->nReserved[5] = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
}else{
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
bDone = TRUE;
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiAnTextData, 8)){
|
|||
|
switch ((int) pMark->Attributes.uType){
|
|||
|
case OIOP_AN_TEXT:
|
|||
|
case OIOP_AN_TEXT_FROM_A_FILE:
|
|||
|
case OIOP_AN_TEXT_STAMP:
|
|||
|
case OIOP_AN_ATTACH_A_NOTE:
|
|||
|
pTextPrivData = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiAnTextData, (PPSTR) &pTextPrivData,
|
|||
|
sizeof(OIAN_TEXTPRIVDATA)))
|
|||
|
|
|||
|
pTextPrivData->nCurrentOrientation = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pTextPrivData->uCurrentScale = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pTextPrivData->uCreationScale = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pTextPrivData->uAnoTextLength = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
|
|||
|
CheckError2( ReAllocateAMarkNamedBlock(pMark, szOiAnTextData, (PPSTR) &pTextPrivData,
|
|||
|
sizeof(OIAN_TEXTPRIVDATA) + pTextPrivData->uAnoTextLength))
|
|||
|
BlockedAnoReadStr(hWnd, pAnoImage, &nStatus,
|
|||
|
pTextPrivData->uAnoTextLength, (PSTR) &pTextPrivData->szAnoText[0]);
|
|||
|
bDone = TRUE;
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiCurPt, 8)){
|
|||
|
// LRECT
|
|||
|
plrRect = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiCurPt, (PPSTR) &plrRect, sizeof(LRECT)))
|
|||
|
|
|||
|
plrRect->left = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
plrRect->top = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
plrRect->right = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
plrRect->bottom = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
bDone = TRUE;
|
|||
|
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiACL, 8)){
|
|||
|
// OI_ACL_BLOCK
|
|||
|
nIDs = BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pAclBlock = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiACL, (PPSTR) &pAclBlock,
|
|||
|
sizeof(OI_ACL_BLOCK) + (sizeof(OI_ACL_STRUCT) * nIDs)))
|
|||
|
|
|||
|
pAclBlock->uIDs = nIDs;
|
|||
|
for (nLoop = 0; nLoop < nIDs; nLoop++){
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, 8, pAclBlock->ACL[nLoop].ID))
|
|||
|
pAclBlock->ACL[nLoop].dwPermissions
|
|||
|
= BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
}
|
|||
|
bDone = TRUE;
|
|||
|
|
|||
|
}else if (!memcmp(((PNAMED_BLOCK) pTemp)->szName, szOiDIB, 8)){
|
|||
|
// BITMAPINFOHEADER
|
|||
|
pDib = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiDIB, (PPSTR) &pDib, sizeof(BITMAPINFOHEADER)))
|
|||
|
|
|||
|
pDib->biSize = (DWORD) BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biSize = sizeof(BITMAPINFOHEADER);
|
|||
|
(int) pDib->biWidth = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
(int) pDib->biHeight = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biPlanes = (WORD) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biBitCount = (WORD) BlockedAnoReadShort(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biCompression = (DWORD) BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biSizeImage = (DWORD) BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biXPelsPerMeter = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biYPelsPerMeter = BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biClrUsed = (DWORD) BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
pDib->biClrImportant = (DWORD) BlockedAnoReadLong(hWnd, pAnoImage, &nStatus);
|
|||
|
|
|||
|
CheckError2( ReAllocateAMarkNamedBlock(pMark, szOiDIB, (PPSTR) &pDib,
|
|||
|
sizeof(BITMAPINFOHEADER) + (sizeof(RGBQUAD) * pDib->biClrUsed)
|
|||
|
+ (((((int) pDib->biWidth * pDib->biBitCount) + 31) & -32) >> 3) * (int) pDib->biHeight))
|
|||
|
|
|||
|
pRGBQuad = (RGBQUAD *) ((PSTR) pDib + sizeof(BITMAPINFOHEADER));
|
|||
|
for (nLoop = 0; nLoop < (int) pDib->biClrUsed; nLoop++){
|
|||
|
pRGBQuad->rgbBlue = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pRGBQuad->rgbGreen = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pRGBQuad->rgbRed = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pRGBQuad->rgbReserved = BlockedAnoReadChar(hWnd, pAnoImage, &nStatus);
|
|||
|
pRGBQuad++;
|
|||
|
}
|
|||
|
pTemp = ((PSTR) pDib) + sizeof(BITMAPINFOHEADER)
|
|||
|
+ (sizeof(RGBQUAD) * pDib->biClrUsed);
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage,
|
|||
|
(((((int) pDib->biWidth * pDib->biBitCount) + 31) & -32) >> 3) * (int) pDib->biHeight,
|
|||
|
(PSTR) pTemp))
|
|||
|
bDone = TRUE;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
if (!bDone){
|
|||
|
// Name not a known structure, assume it is a string.
|
|||
|
memcpy(NamedBlock.szName, ((PNAMED_BLOCK) pTemp)->szName, 8);
|
|||
|
CheckError2( FreeMemory(&pTemp))
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, NamedBlock.szName,
|
|||
|
(PPSTR) &pTemp, lTemp[1]))
|
|||
|
CheckError2( BlockedAnoRead(hWnd, pAnoImage, lTemp[1], pTemp))
|
|||
|
}
|
|||
|
// if it is an oiop_activate mark, then delete it
|
|||
|
// they were saved by mistake in 3.7.2
|
|||
|
if ((int) pMark->Attributes.uType == OIOP_ACTIVATE){
|
|||
|
CheckError2( DeleteMark(pAnoImage, (*pnMarks) - 1))
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
nStatus = Error(DISPLAY_BAD_ANO_DATA);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (nStatus){
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
|
|||
|
// Update file with index# info.
|
|||
|
pDefMark = pAnoImage->Annotations.pDefMark;
|
|||
|
if (!pDefMark->pOiIndex){
|
|||
|
nIndex = 0;
|
|||
|
for (nMarkIndex = 0; nMarkIndex < *pnMarks; nMarkIndex++){
|
|||
|
pMark = (*pppMarks)[nMarkIndex];
|
|||
|
pTemp = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pMark, szOiIndex, (PPSTR) &pTemp, 10))
|
|||
|
_itoa(nIndex, Buff1, 10);
|
|||
|
strcpy(pTemp, Buff1);
|
|||
|
nIndex++;
|
|||
|
}
|
|||
|
pTemp = 0;
|
|||
|
CheckError2( AddAMarkNamedBlock(pDefMark, szOiIndex, (PPSTR) &pTemp, 10))
|
|||
|
_itoa(nIndex, Buff1, 10);
|
|||
|
strcpy(pTemp, Buff1);
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: IMGCacheUpdate
|
|||
|
|
|||
|
PURPOSE: Prepares for filing to make changes to a file.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI IMGCacheUpdate(HWND hWnd, PSTR pFileName, int nPage, int nUpdateType){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
PANO_IMAGE pAnoImage;
|
|||
|
PIMAGE pImage;
|
|||
|
int nLoop;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2( IntSeqfileInit())
|
|||
|
|
|||
|
// Read all data for all locked pages of this file.
|
|||
|
// Look for the file in the AnoImage Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!(pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pAnoImage->nLockCount){
|
|||
|
CheckError2( ValidateCacheLines(hWnd, pAnoImage, 0xffffff))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Look for the file in the Image Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pSubSegMemory->ppCachedImage[nLoop]->szFileName){
|
|||
|
if (!_stricmp(pSubSegMemory->ppCachedImage[nLoop]->szFileName, pFileName)){
|
|||
|
if (pImage->nLockCount && !pImage->bCacheValid){
|
|||
|
CheckError2( CacheRead(hWnd, pSubSegMemory->ppCachedImage[nLoop],
|
|||
|
pSubSegMemory->ppCachedImage[nLoop]->nHeight - pSubSegMemory->ppCachedImage[nLoop]->nLinesRead))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Delete all nnlocked images, or finish reading them, or just continue - as needed.
|
|||
|
switch (nUpdateType){
|
|||
|
case CACHE_UPDATE_OVERWRITE_FILE:
|
|||
|
case CACHE_UPDATE_DELETE_FILE:
|
|||
|
case CACHE_UPDATE_ROTATE_ALL:
|
|||
|
// Delete all nnlocked pages of this file.
|
|||
|
// Look for the file in the AnoImage Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!(pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (!pAnoImage->nLockCount){
|
|||
|
CheckError2( CacheClearAno(&pAnoImage))
|
|||
|
nLoop--;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
// Look for the file in the Image Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (!pImage->nLockCount){
|
|||
|
CheckError2( CacheClear(&pImage))
|
|||
|
nLoop--;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case CACHE_UPDATE_DELETE_PAGE:
|
|||
|
case CACHE_UPDATE_APPEND:
|
|||
|
case CACHE_UPDATE_INSERT_BEFORE:
|
|||
|
case CACHE_UPDATE_CLOSE_FILE:
|
|||
|
// Read all data for all pages of this file.
|
|||
|
// Look for the file in the AnoImage Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!(pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (nUpdateType == CACHE_UPDATE_DELETE_PAGE
|
|||
|
&& pImage->nFilePageNum == nPage){
|
|||
|
CheckError2( CacheClearAno(&pAnoImage))
|
|||
|
nLoop--;
|
|||
|
}else{
|
|||
|
CheckError2( ValidateCacheLines(hWnd, pAnoImage, 0xffffff))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Look for the file in the Image Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (nUpdateType == CACHE_UPDATE_DELETE_PAGE
|
|||
|
&& pImage->nFilePageNum == nPage){
|
|||
|
CheckError2( CacheClear(&pImage))
|
|||
|
nLoop--;
|
|||
|
}else{
|
|||
|
if (!pImage->bCacheValid){
|
|||
|
CheckError2( CacheRead(hWnd, pImage,
|
|||
|
pImage->nHeight - pImage->nLinesRead))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case CACHE_UPDATE_OVERWRITE_PAGE:
|
|||
|
// Read all data for this page of this file.
|
|||
|
// Look for the file in the AnoImage Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxAnoCachedEntries; nLoop++){
|
|||
|
if (!(pAnoImage = pSubSegMemory->ppCachedAnoImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage = pAnoImage->pBaseImage){
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pImage->nFilePageNum == nPage){
|
|||
|
if (!pAnoImage->nLockCount){
|
|||
|
CheckError2( CacheClearAno(&pAnoImage))
|
|||
|
nLoop--;
|
|||
|
}else{
|
|||
|
CheckError2( ValidateCacheLines(hWnd, pAnoImage, 0xffffff))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// Look for the file in the Image Table.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pImage->nFilePageNum == nPage){
|
|||
|
if (!pImage->bCacheValid){
|
|||
|
CheckError2( CacheRead(hWnd, pImage, pImage->nHeight - pImage->nLinesRead))
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
// Do all page number modifying stuff here. (Also some error checking.)
|
|||
|
switch (nUpdateType){
|
|||
|
case CACHE_UPDATE_DELETE_PAGE:
|
|||
|
// If this page is in the cache then fail.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pImage->nFilePageNum == nPage){
|
|||
|
nStatus = Error(DISPLAY_CACHEFILEINUSE);
|
|||
|
goto Exit;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
// We have to decrement the page numbers that are greater than this one in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pImage->nFilePageNum > nPage){
|
|||
|
pImage->nFilePageNum--;
|
|||
|
}
|
|||
|
pImage->nFileTotalPages--;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case CACHE_UPDATE_INSERT_BEFORE:
|
|||
|
// We have to increment the page numbers that are equal to and greater than this one in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
if (pImage->nFilePageNum >= nPage){
|
|||
|
pImage->nFilePageNum++;
|
|||
|
}
|
|||
|
pImage->nFileTotalPages++;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
case CACHE_UPDATE_APPEND:
|
|||
|
// We have to increment the number of pages in the cache.
|
|||
|
for (nLoop = 0; nLoop < pSubSegMemory->nMaxCachedEntries; nLoop++){
|
|||
|
if (!(pImage = pSubSegMemory->ppCachedImage[nLoop])){
|
|||
|
break;
|
|||
|
}
|
|||
|
if (pImage->szFileName){
|
|||
|
if (!_stricmp(pImage->szFileName, pFileName)){
|
|||
|
pImage->nFileTotalPages++;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
break;
|
|||
|
|
|||
|
|
|||
|
case CACHE_UPDATE_OVERWRITE_PAGE:
|
|||
|
case CACHE_UPDATE_OVERWRITE_FILE:
|
|||
|
case CACHE_UPDATE_DELETE_FILE:
|
|||
|
case CACHE_UPDATE_ROTATE_ALL:
|
|||
|
case CACHE_UPDATE_CLOSE_FILE:
|
|||
|
default:
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|
|||
|
/****************************************************************************
|
|||
|
|
|||
|
FUNCTION: OiRotateAllPages
|
|||
|
|
|||
|
PURPOSE: Marks all pages in a file for rotation.
|
|||
|
|
|||
|
****************************************************************************/
|
|||
|
|
|||
|
int WINAPI OiRotateAllPages(HWND hWnd, PSTR pFileName, int nRotation, int nFlags){
|
|||
|
|
|||
|
int nStatus = 0;
|
|||
|
|
|||
|
FIO_INFO_MISC MiscInfo;
|
|||
|
|
|||
|
|
|||
|
Start();
|
|||
|
|
|||
|
CheckError2( IntSeqfileInit())
|
|||
|
|
|||
|
memset(&MiscInfo, 0, sizeof(FIO_INFO_MISC));
|
|||
|
MiscInfo.LastInfo.BandSize = 0;
|
|||
|
MiscInfo.LastInfo.Rotation = nRotation;
|
|||
|
MiscInfo.LastInfo.ScaleX = 0;
|
|||
|
MiscInfo.LastInfo.ScaleY = 0;
|
|||
|
MiscInfo.LastInfo.Flags = FIO_LASTINFO_ROTATE_ALL;
|
|||
|
MiscInfo.bLastInfoValid = TRUE;
|
|||
|
|
|||
|
CheckError( IMGFilePutInfo(hWnd, pFileName, 0, &MiscInfo))
|
|||
|
|
|||
|
|
|||
|
Exit:
|
|||
|
End();
|
|||
|
return(nStatus);
|
|||
|
}
|