home *** CD-ROM | disk | FTP | other *** search
/ QBasic & Borland Pascal & C / Delphi5.iso / C / BC_502 / WORDPAD.PAK / DOCTYPE.CPP < prev    next >
Encoding:
C/C++ Source or Header  |  1997-05-06  |  6.7 KB  |  270 lines

  1. // richdoc.cpp : implementation of the CRichEditDoc class
  2. //
  3. // This is a part of the Microsoft Foundation Classes C++ library.
  4. // Copyright (C) 1992-1995 Microsoft Corporation
  5. // All rights reserved.
  6. //
  7. // This source code is only intended as a supplement to the
  8. // Microsoft Foundation Classes Reference and related
  9. // electronic documentation provided with the library.
  10. // See these sources for detailed information regarding the
  11. // Microsoft Foundation Classes product.
  12.  
  13. #include "stdafx.h"
  14. #include "resource.h"
  15. #include "strings.h"
  16.  
  17. #include "multconv.h"
  18.  
  19. #ifdef _DEBUG
  20. #undef THIS_FILE
  21. static char BASED_CODE THIS_FILE[] = __FILE__;
  22. #endif
  23.  
  24. static const BYTE byteRTFPrefix[5] = {'{', '\\', 'r', 't', 'f'};
  25. static const BYTE byteWord2Prefix[4] = {0xDB, 0xA5, 0x2D, 0x00};
  26. static const BYTE byteCompFilePrefix[8] = {0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1};
  27. static const BYTE byteWrite1Prefix[2] = {0x31, 0xBE};
  28. static const BYTE byteWrite2Prefix[2] = {0x32, 0xBE};
  29. static const BYTE byteExePrefix[2] = {0x4D, 0x5A};
  30.  
  31. /////////////////////////////////////////////////////////////////////////////
  32.  
  33. static BOOL IsConverterFormat(LPCTSTR pszConverter, LPCTSTR pszPathName);
  34. static BOOL IsWord6(LPCTSTR pszConverter, LPCTSTR pszPathName);
  35.  
  36. DocType doctypes[NUM_DOC_TYPES] = 
  37. {
  38.     DECLARE_DOCTYPE(WINWORD2, FALSE, FALSE, FALSE, NULL),
  39.     DECLARE_DOCTYPE(WINWORD6, TRUE, FALSE, TRUE, szWordConverter),
  40.     DECLARE_DOCTYPE_SYN(WORDPAD, WINWORD6, TRUE, TRUE, FALSE, szWordConverter),
  41.     DECLARE_DOCTYPE(WRITE, TRUE, FALSE, FALSE, szWriteConverter),
  42.     DECLARE_DOCTYPE(RICHTEXT, TRUE, TRUE, FALSE, NULL),
  43.     DECLARE_DOCTYPE(TEXT, TRUE, TRUE, FALSE, NULL),
  44.     DECLARE_DOCTYPE(OEMTEXT, TRUE, TRUE, FALSE, NULL),
  45.     DECLARE_DOCTYPE(ALL, TRUE, FALSE, FALSE, NULL),
  46.     DECLARE_DOCTYPE(EXE, FALSE, FALSE, FALSE, NULL),
  47.     DECLARE_DOCTYPE_NULL(EMBEDDED, FALSE, FALSE, FALSE, NULL)
  48. };
  49.  
  50. CString DocType::GetString(int nID)
  51. {
  52.     ASSERT(idStr != NULL);
  53.     CString str;
  54.     VERIFY(str.LoadString(idStr));
  55.     CString strSub;
  56.     AfxExtractSubString(strSub, str, nID);
  57.     return strSub;
  58. }
  59.  
  60. static BOOL IsConverterFormat(LPCSTR pszConverter, LPCTSTR pszPathName)
  61. {
  62.     CConverter conv(pszConverter);
  63.     return conv.IsFormatCorrect(pszPathName);
  64. }
  65.  
  66. static BOOL IsLeadMatch(CFile& file, const BYTE* pb, UINT nCount)
  67. {
  68.     // check for match at beginning of file
  69.     BOOL b = FALSE;
  70.     BYTE* buf = new BYTE[nCount];
  71.     
  72.     TRY
  73.     {
  74.         file.SeekToBegin();
  75.         memset(buf, 0, nCount);
  76.         file.Read(buf, nCount);
  77.         if (memcmp(buf, pb, nCount) == 0)
  78.             b = TRUE;
  79.     }
  80.     END_TRY
  81.  
  82.     delete [] buf;
  83.     return b;
  84. }
  85.  
  86. static BOOL IsWord6(LPCTSTR pszPathName)
  87. {
  88.     USES_CONVERSION;
  89.     BOOL bRes = FALSE;
  90.     // see who created it
  91.     LPSTORAGE lpStorage;
  92.     SCODE sc = StgOpenStorage(T2COLE(pszPathName), NULL,
  93.         STGM_READ|STGM_SHARE_EXCLUSIVE,    0, 0, &lpStorage);
  94.     if (sc == NOERROR)
  95.     {
  96.         LPSTREAM lpStream;
  97.         sc = lpStorage->OpenStream(T2COLE(szSumInfo), NULL, 
  98.             STGM_READ|STGM_SHARE_EXCLUSIVE, NULL, &lpStream);
  99.         if (sc == NOERROR)
  100.         {
  101.             lpStream->Release();
  102.             bRes = TRUE;
  103.         }
  104.         lpStorage->Release();
  105.     }
  106.     return bRes;
  107. }
  108.  
  109. int GetDocTypeFromName(LPCTSTR pszPathName, CFileException& fe)
  110. {
  111.     CFile file;
  112.     ASSERT(pszPathName != NULL);
  113.     
  114.     if (!file.Open(pszPathName, CFile::modeRead | CFile::shareDenyWrite, &fe))
  115.         return -1;
  116.  
  117.     CFileStatus stat;
  118.     VERIFY(file.GetStatus(stat));
  119.  
  120.     if (stat.m_size == 0) // file is empty
  121.     {
  122.         CString ext = CString(pszPathName).Right(4);
  123.         if (ext[0] != '.')
  124.             return RD_TEXT;
  125.         if (lstrcmpi(ext, _T(".doc"))==0)
  126.             return RD_WORDPAD;
  127.         if (lstrcmpi(ext, _T(".rtf"))==0)
  128.             return RD_RICHTEXT;
  129.         return RD_TEXT;
  130.     }
  131.     // RTF
  132.     if (IsLeadMatch(file, byteRTFPrefix, sizeof(byteRTFPrefix)))
  133.         return RD_RICHTEXT;
  134.     // WORD 2
  135.     if (IsLeadMatch(file, byteWord2Prefix, sizeof(byteWord2Prefix)))
  136.         return RD_WINWORD2;
  137.     // EXE
  138.     if (IsLeadMatch(file, byteExePrefix, sizeof(byteExePrefix)))
  139.         return RD_EXE;
  140.     // write file can start with 31BE or 32BE depending on whether it has
  141.     // OLE objects in it or not
  142.     if (IsLeadMatch(file, byteWrite1Prefix, sizeof(byteWrite1Prefix)) ||
  143.         IsLeadMatch(file, byteWrite2Prefix, sizeof(byteWrite2Prefix)))
  144.     {
  145.         file.Close();
  146.         if (IsConverterFormat(szWriteConverter, pszPathName))
  147.             return RD_WRITE;
  148.         else
  149.             return RD_TEXT;
  150.     }
  151.  
  152.     // test for compound file
  153.     if (IsLeadMatch(file, byteCompFilePrefix, sizeof(byteCompFilePrefix)))
  154.     {
  155.         file.Close();
  156.         if (IsConverterFormat(szWordConverter, pszPathName))
  157.         {
  158.             if (IsWord6(pszPathName))
  159.                 return RD_WINWORD6;
  160.             else
  161.                 return RD_WORDPAD;
  162.         }
  163.         return RD_TEXT;
  164.     }
  165.     return RD_TEXT;
  166. }
  167.  
  168. void ScanForConverters()
  169. {
  170.     static BOOL bScanned = FALSE;
  171.     if (bScanned)
  172.         return;
  173.  
  174.     for (int i=0;i<NUM_DOC_TYPES;i++)
  175.     {
  176.         LPCSTR lpsz = doctypes[i].pszConverterName;
  177.         // if converter specified but can't find it
  178.         if (lpsz != NULL && *lpsz != NULL && !IsDLLInPath(lpsz))
  179.             doctypes[i].bRead = doctypes[i].bWrite = FALSE;
  180.     }
  181.     if (GetSystemMetrics(SM_DBCSENABLED))
  182.         doctypes[RD_OEMTEXT].bRead = doctypes[RD_OEMTEXT].bWrite = FALSE;
  183.     bScanned = TRUE;
  184. }
  185.  
  186. BOOL IsDLLInPath(LPCSTR lpszName)
  187. {
  188.     ASSERT(lpszName != NULL);
  189.     OFSTRUCT ofs;
  190.     return (OpenFile(lpszName, &ofs, OF_EXIST) != HFILE_ERROR);
  191. }
  192.  
  193. CString GetExtFromType(int nDocType)
  194. {
  195.     ScanForConverters();
  196.  
  197.     CString str = doctypes[nDocType].GetString(DOCTYPE_EXT);
  198.     if (!str.IsEmpty())
  199.     {
  200.         ASSERT(str.GetLength() == 5); // "*.ext"
  201.         ASSERT(str[1] == '.');
  202.         return str.Right(str.GetLength()-1);
  203.     }
  204.     return str;
  205. }
  206.  
  207. // returns an RD_* from an index into the openfile dialog types
  208. int GetTypeFromIndex(int nIndex, BOOL bOpen)
  209. {
  210.     ScanForConverters();
  211.  
  212.     int nCnt = 0;
  213.     for (int i=0;i<NUM_DOC_TYPES;i++)
  214.     {
  215.         if (!doctypes[i].bDup && 
  216.             (bOpen ? doctypes[i].bRead : doctypes[i].bWrite))
  217.         {
  218.             if (nCnt == nIndex)
  219.                 return i;
  220.             nCnt++;
  221.         }
  222.     }
  223.     ASSERT(FALSE);
  224.     return -1;
  225. }
  226.  
  227. // returns an index into the openfile dialog types for the RD_* type
  228. int GetIndexFromType(int nType, BOOL bOpen)
  229. {
  230.     ScanForConverters();
  231.  
  232.     int nCnt = 0;
  233.     for (int i=0;i<NUM_DOC_TYPES;i++)
  234.     {
  235.         if (!doctypes[i].bDup &&
  236.             (bOpen ? doctypes[i].bRead : doctypes[i].bWrite))
  237.         {
  238.             if (i == nType)
  239.                 return nCnt;
  240.             nCnt++;
  241.         }
  242.     }
  243.     return -1;
  244. }
  245.  
  246. CString GetFileTypes(BOOL bOpen)
  247. {
  248.     ScanForConverters();
  249.  
  250.     CString str;
  251.     for (int i=0;i<NUM_DOC_TYPES;i++)
  252.     {
  253.         if (bOpen && doctypes[i].bRead && !doctypes[i].bDup)
  254.         {
  255.             str += doctypes[i].GetString(DOCTYPE_DESC);
  256.             str += (TCHAR)NULL;
  257.             str += doctypes[i].GetString(DOCTYPE_EXT);
  258.             str += (TCHAR)NULL;
  259.         }
  260.         else if (!bOpen && doctypes[i].bWrite && !doctypes[i].bDup)
  261.         {
  262.             str += doctypes[i].GetString(DOCTYPE_DOCTYPE);
  263.             str += (TCHAR)NULL;
  264.             str += doctypes[i].GetString(DOCTYPE_EXT);
  265.             str += (TCHAR)NULL;
  266.         }
  267.     }
  268.     return str;
  269. }
  270.