home *** CD-ROM | disk | FTP | other *** search
/ Tricks of the Windows Gam…ming Gurus (2nd Edition) / Disc2.iso / vc98 / include / _dbdao.h next >
C/C++ Source or Header  |  1998-04-25  |  22KB  |  734 lines

  1. /************************************************************************
  2. **    _ D B D A O . H                                                    *
  3. **                                                                        *
  4. *************************************************************************
  5. ** Copyright (C) 1996 by Microsoft Corporation                     *
  6. **           All Rights Reserved                                             *
  7. ************************************************************************/
  8. /*
  9.     _DBDAO.H
  10.  
  11.     Internal definitions and prototypes for dbdao C++ classes
  12. */
  13. #ifndef __DBDAO_H_
  14. #define __DBDAO_H_
  15.  
  16.  
  17. /*****************************************************************************
  18. * Forwards
  19. */
  20. class COleVariant;
  21. class CdbBookmark;
  22. class CdbException;
  23. class CdbOleObject;
  24. class CdbObject;
  25. class CdbError;
  26. class CdbProperty;
  27. class CdbDBEngine;
  28. class CdbWorkspace;
  29. class CdbDatabase;
  30. class CdbConnection;
  31. class CdbRecordset;
  32. class CdbGetRowsEx;
  33. class CdbQueryDef;
  34. class CdbTableDef;
  35. class CdbField;
  36. class CdbRelation;
  37. class CdbIndex;
  38. class CdbUser;
  39. class CdbGroup;
  40. class CdbDocument;
  41. class CdbContainer;
  42. class CdbParameter;
  43. class CdbCollection;
  44. class CdbErrors;
  45. class CdbProperties;
  46. class CdbWorkspaces;
  47. class CdbDatabases;
  48. class CdbConnections;
  49. class CdbRecordsets;
  50. class CdbQueryDefs;
  51. class CdbTableDefs;
  52. class CdbFields;
  53. class CdbRelations;
  54. class CdbIndexes;
  55. class CdbUsers;
  56. class CdbGroups;
  57. class CdbDocuments;
  58. class CdbContainers;
  59. class CdbParameters;
  60. class CdbBStr;
  61.  
  62. /*****************************************************************************
  63. * DAO runtime key
  64. */
  65. const char szKEY[] = "mbmabptebkjcdlgtjmskjwtsdhjbmkmwtrak";
  66.  
  67. /*****************************************************************************
  68. * Miscellaneous defines
  69. */
  70. #define DAO_MAXSEEKFIELDS 13
  71.  
  72.  
  73. /*****************************************************************************
  74. * CdbBSTR (OLE BSTR helper)
  75. */
  76. class DLLEXPORT CdbBSTR
  77.     {
  78.     public:
  79.     CONSTRUCTOR            CdbBSTR                (BSTR=NULL);
  80.     DESTRUCTOR            ~CdbBSTR            (VOID);
  81.  
  82.     operator            BSTR *                (VOID);
  83.     operator            LPCTSTR                (VOID);
  84.  
  85.     private:
  86.     BSTR                m_bstr;
  87.     };
  88.  
  89. /*****************************************************************************
  90. * CdbVariant (OLE Variant helper)
  91. */
  92. class CdbVariant : public COleVariant
  93.     {
  94.     public:
  95.     CONSTRUCTOR                        CdbVariant                        (LONG l);
  96.     CONSTRUCTOR                     CdbVariant                      (VOID);
  97.     CONSTRUCTOR                     CdbVariant                      (LPCTSTR pstr);
  98.     CONSTRUCTOR                     CdbVariant                      (SHORT s, BOOL bIsBool = FALSE);
  99.     CONSTRUCTOR                     CdbVariant                      (LPVARIANT pv);
  100.     CONSTRUCTOR                     CdbVariant                      (LPSAFEARRAY psa);
  101.  
  102.     VOID                            operator =                      (LPVARIANT pv);
  103.     VOID                            operator =                      (LPCTSTR pstr);
  104.     VOID                            operator =                      (SHORT s);
  105.     VOID                            operator =                      (const int i);
  106.     VOID                            operator =                      (LONG l);
  107.     };
  108.  
  109. inline CONSTRUCTOR    CdbVariant::CdbVariant(
  110.     VOID) : COleVariant()
  111.     {
  112.     vt        = VT_ERROR;
  113.     scode    = DISP_E_PARAMNOTFOUND;
  114.     }
  115.  
  116. inline CdbVariant::CdbVariant (LONG l)
  117. {
  118.         if (l == -1)        
  119.             {    
  120.             vt        = VT_ERROR;
  121.             scode    = DISP_E_PARAMNOTFOUND;
  122.             }
  123.         else
  124.             {
  125.             vt        = VT_I4;
  126.             lVal    = l;
  127.             }
  128. }
  129.  
  130.  
  131. inline CONSTRUCTOR    CdbVariant::CdbVariant(
  132.     LPCTSTR pstr): COleVariant(pstr,VT_BSTRT)
  133.     {
  134.     if (!pstr)
  135.         {
  136.         VariantClear(this);
  137.         vt        = VT_ERROR;
  138.         scode    = DISP_E_PARAMNOTFOUND;
  139.         }
  140.     }
  141.  
  142.  
  143. inline CONSTRUCTOR    CdbVariant::CdbVariant(
  144.     SHORT s, BOOL bIsBool) : COleVariant(s)
  145.     {
  146.     if (bIsBool)
  147.         {
  148.         vt        = VT_BOOL;
  149.         boolVal    = s;
  150.         }
  151.     else if (s==-1)
  152.         {
  153.         vt        = VT_ERROR;
  154.         scode    = DISP_E_PARAMNOTFOUND;
  155.         }
  156.     }
  157.  
  158. inline CONSTRUCTOR    CdbVariant::CdbVariant(
  159.     LPVARIANT    pv)
  160.     {
  161.     if (!pv)
  162.         {
  163.         vt        = VT_ERROR;
  164.         scode    = DISP_E_PARAMNOTFOUND;
  165.         }
  166.     else
  167.         VariantCopy(this, pv);
  168.     }
  169.  
  170. inline CONSTRUCTOR    CdbVariant::CdbVariant(
  171.     LPSAFEARRAY psa)
  172.     {
  173.     if (!psa)
  174.         {
  175.         vt        = VT_ERROR;
  176.         scode    = DISP_E_PARAMNOTFOUND;
  177.         }
  178.     else
  179.         {
  180.         vt        = VT_ARRAY|VT_UI1;
  181.         parray    = psa;
  182.         }
  183.     }
  184.  
  185. inline VOID    CdbVariant::operator =(
  186.     LPVARIANT pv)
  187.     {
  188.     if (!pv)
  189.         {
  190.         vt        = VT_ERROR;
  191.         scode    = DISP_E_PARAMNOTFOUND;
  192.         }
  193.     else
  194.         VariantCopy(this, pv);
  195.     }
  196.  
  197. inline VOID    CdbVariant::operator =(
  198.     LPCTSTR pstr) 
  199.     {
  200.     if (!pstr)
  201.         {
  202.         VariantClear(this);
  203.         vt        = VT_ERROR;
  204.         scode    = DISP_E_PARAMNOTFOUND;
  205.         }
  206.     else
  207.         {
  208. #ifdef UNICODE
  209.         bstrVal = SysAllocString(pstr);
  210. #else
  211.         bstrVal = SysAllocStringByteLen(pstr, strlen(pstr));
  212. #endif
  213.         vt = VT_BSTR;
  214.         }
  215.     }
  216.  
  217.  
  218. inline VOID    CdbVariant::operator =(
  219.     SHORT s)
  220.     {
  221.     if (s==-1)
  222.         {
  223.         vt        = VT_ERROR;
  224.         scode    = DISP_E_PARAMNOTFOUND;
  225.         }
  226.     else
  227.         {
  228.         vt        = VT_I2;
  229.         iVal    = s;
  230.         }
  231.     }
  232.  
  233. inline VOID    CdbVariant::operator =(
  234.     const int i)
  235.     {
  236.     if (i==-1)
  237.         {
  238.         vt        = VT_ERROR;
  239.         scode    = DISP_E_PARAMNOTFOUND;
  240.         }
  241.     else
  242.         {
  243.         vt        = VT_I2;
  244.         iVal    = (SHORT)i;
  245.         }
  246.     }
  247.  
  248.  
  249. inline VOID    CdbVariant::operator =(
  250.     LONG     l)
  251.     {
  252.     if (l==-1)
  253.         {
  254.         vt         = VT_ERROR;
  255.         scode    = DISP_E_PARAMNOTFOUND;
  256.         }
  257.     else
  258.         {
  259.         vt        = VT_I4;
  260.         lVal    = l;
  261.         }
  262.     }
  263.  
  264.  
  265. /*****************************************************************************
  266. * CdbWide
  267. */
  268. HRESULT    CdbWideFromAnsi(LPSTR, unsigned int, BSTR *);
  269.  
  270. class CdbWide
  271.     {
  272.     public:
  273.     CONSTRUCTOR            CdbWide                (LPSTR pstr, unsigned int cb=0)
  274.         {
  275.         CdbWideFromAnsi(pstr, (pstr ? (cb==0 ? strlen(pstr) : cb) : 0), &m_bstr);
  276.         }
  277.     DESTRUCTOR            ~CdbWide            ()
  278.         {
  279.         SysFreeString(m_bstr);
  280.         }
  281.  
  282.     operator            LPWSTR                    ()
  283.         {
  284.         return (LPWSTR)m_bstr;
  285.         }
  286.     operator            LPSTR                    ()
  287.         {
  288.         return (LPSTR)m_bstr;
  289.         }
  290.  
  291.     ULONG                cBytes                    ()
  292.         {
  293.         return SysStringByteLen(m_bstr);
  294.         }
  295.  
  296.     private:
  297.     BSTR                m_bstr;
  298.     };
  299.  
  300.  
  301. /*****************************************************************************
  302. * CdbOleObject
  303. */
  304. class DLLEXPORT CdbOleObject : public CObject
  305.     {
  306.     public:
  307.     CONSTRUCTOR                             CdbOleObject            (VOID);
  308.     virtual DESTRUCTOR                        ~CdbOleObject           (VOID);
  309.     BOOL                                    Exists                  (VOID);
  310.     CdbOleObject &                            operator =              (CdbOleObject &o);
  311.                                             operator LPUNKNOWN        (){ return GetInterface();}
  312.     VOID                                    SetInterface            (LPUNKNOWN punk, BOOL bAddRef=FALSE);
  313.     VOID                                    SetInterface            (REFIID riidClass, REFIID riidInterface);
  314.     VOID                                    SetInterfaceLic         (REFIID riidClass, REFIID riidInterface);
  315.     LPUNKNOWN                                GetInterface            (BOOL bAddRef=FALSE, BOOL bThrowException=TRUE) const;
  316.  
  317.     virtual VOID                            OnInterfaceChange       (VOID);
  318.     VOID                                    SetRichErrorInfo        (LPOLESTR pstrSource, LPOLESTR pstrDescription, LPOLESTR pstrHelpFile, ULONG ulHelpID) const;
  319.  
  320.     protected:
  321.     BOOL                                    StartOLE                        (VOID);
  322.     LPUNKNOWN                               m_punkInterface;
  323.     };
  324.  
  325.  
  326.  
  327. /*****************************************************************************
  328. * CdbCollection
  329. */
  330. class DLLEXPORT CdbCollection : public CdbOleObject
  331.     {
  332.     public:
  333.  
  334.     // Methods
  335.     virtual CdbObject               ObItem                  (LONG i) = 0;
  336.     virtual CdbObject               ObItem                  (LPCTSTR pstr) = 0;
  337.     virtual LONG                    GetCount                (VOID) = 0;
  338.     virtual VOID                    ObAppend                (CdbObject &obj) = 0;
  339.     virtual VOID                    Delete                  (LPCTSTR pstr) = 0;
  340.     virtual VOID                    Refresh                 (VOID) = 0;
  341.     };
  342.  
  343. class DLLEXPORT CdbStaticCollection : public CdbCollection
  344.     {
  345.     public:
  346.     CdbObject                               ObItem                  (LONG i);
  347.     CdbObject                               ObItem                  (LPCTSTR pstr);
  348.     LONG                                    GetCount                (VOID);
  349.     VOID                                    ObAppend                (CdbObject &obj);
  350.     VOID                                    Delete                  (LPCTSTR pstr);
  351.     VOID                                    Refresh                 (VOID) ;
  352.     };
  353.  
  354. class DLLEXPORT CdbDynamicCollection : public CdbCollection
  355.     {
  356.     public:
  357.     CdbObject                               ObItem                  (LONG i);
  358.     CdbObject                               ObItem                  (LPCTSTR pstr);
  359.     LONG                                    GetCount                (VOID);
  360.     VOID                                    ObAppend                (CdbObject &obj);
  361.     VOID                                    Delete                  (LPCTSTR pstr);
  362.     VOID                                    Refresh                 (VOID);
  363.     };
  364.  
  365. #define DAOMFC_STATIC_COLLECTION_DECL(objColl, objSingle, intSingle)    \
  366.     class DLLEXPORT objColl : public CdbStaticCollection                                                    \
  367.         {                                                                                                                               \
  368.         public:                                                                                                                 \
  369.                                                                         \
  370.         objSingle                       Item                            (LONG i);                               \
  371.         objSingle                       Item                            (LPCTSTR pstr);                 \
  372.         objSingle                       operator[]                      (LONG i);                               \
  373.         objSingle                       operator[]                      (LPCTSTR pstr);                 \
  374.         }
  375.  
  376. #define DAOMFC_DYNAMIC_COLLECTION_DECL(objColl, objSingle, intSingle)   \
  377.     class DLLEXPORT objColl : public CdbDynamicCollection                                                   \
  378.         {                                                                                                                               \
  379.         public:                                                                                                                 \
  380.                                                                         \
  381.         objSingle                       Item                            (LONG i);                               \
  382.         objSingle                       Item                            (LPCTSTR pstr);                 \
  383.         VOID                            Append                          (objSingle &o);                 \
  384.         objSingle                       operator[]                      (LONG i);                               \
  385.         objSingle                       operator[]                      (LPCTSTR pstr);                 \
  386.         }
  387.  
  388. DAOMFC_STATIC_COLLECTION_DECL(CdbErrors, CdbError, DAOError);
  389. DAOMFC_STATIC_COLLECTION_DECL(CdbDatabases, CdbDatabase, DAODatabase);
  390. //Connections are special cased so we can trap the copy constructor
  391. DAOMFC_STATIC_COLLECTION_DECL(CdbRecordsets, CdbRecordset, DAORecordset);
  392. DAOMFC_STATIC_COLLECTION_DECL(CdbParameters, CdbParameter, DAOParameter);
  393. DAOMFC_STATIC_COLLECTION_DECL(CdbDocuments, CdbDocument, DAODocument);
  394. DAOMFC_STATIC_COLLECTION_DECL(CdbContainers, CdbContainer, DAOContainer);
  395.  
  396. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbProperties, CdbProperty, DAOProperty);
  397. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbFields, CdbField, DAOField);
  398. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbQueryDefs, CdbQueryDef, DAOQueryDef);
  399. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbTableDefs, CdbTableDef, DAOTableDef);
  400. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbIndexes, CdbIndex, DAOIndex);
  401. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbRelations, CdbRelation, DAORelation);
  402. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbUsers, CdbUser, DAOUser);
  403. DAOMFC_DYNAMIC_COLLECTION_DECL(CdbGroups, CdbGroup, DAOGroup);
  404.  
  405. //Need some extra functions in CdbWorkspaces to support the delay in creating the 
  406. //default workspace needed to support the JET/ODBC option.
  407. class DLLEXPORT CdbWorkspaces : public CdbDynamicCollection
  408.     {        
  409.     friend CdbDBEngine;
  410.     private:
  411.     DAODBEngine    *                    pDBEng;
  412.     BOOL                            m_bDontStart;
  413.  
  414.     public:                                                                                                                 
  415.     CONSTRUCTOR                     CdbWorkspaces            (VOID){pDBEng = NULL;}
  416.     CdbWorkspace                    Item                    (LONG i);                               
  417.     CdbWorkspace                    Item                    (LPCTSTR pstr);                 
  418.     VOID                            Append                  (CdbWorkspace &o);                 
  419.     CdbWorkspace                    operator[]              (LONG i);                         
  420.     CdbWorkspace                    operator[]              (LPCTSTR pstr);                
  421.     VOID                            SetDBEngine                (DAODBEngine    *peng){pDBEng = peng;}
  422.     VOID                            GetDelayedInterface     ();
  423.     };
  424.  
  425. //Need to trap Connections in the copy constructor so the user can't
  426. //get a "sorta-kinda" working Connections collection on a Jet workspace
  427. class DLLEXPORT CdbConnections : public CdbStaticCollection
  428.     {        
  429.     public:
  430.     CONSTRUCTOR                        CdbConnections            (CdbConnections &Connections);
  431.     CONSTRUCTOR                        CdbConnections            (){pwrk = NULL;}
  432.     CdbConnection                   Item                    (LONG i);                               
  433.     CdbConnection                   Item                    (LPCTSTR pstr);                 
  434.     CdbConnection                   operator[]              (LONG i);                               
  435.     CdbConnection                   operator[]              (LPCTSTR pstr);               
  436.     CdbConnections    &                operator =                (CdbConnections &o);
  437.     LONG                            GetCount                (VOID);
  438.     VOID                            Refresh                 (VOID) ;
  439.     VOID                            SetWorkspace            (DAOWorkspace * pParent){pwrk = pParent;}            
  440.  
  441.     private:
  442.     VOID                            CheckInterface();
  443.     DAOWorkspace *                    pwrk;
  444.     };
  445.  
  446. /*****************************************************************************
  447. * CdbObject
  448. */
  449. class DLLEXPORT CdbObject : public CdbOleObject
  450.     {
  451.     public:
  452.     CONSTRUCTOR                             CdbObject                       (VOID);
  453.     CONSTRUCTOR                             CdbObject                       (LPUNKNOWN punk, BOOL bAddRef=FALSE);
  454.  
  455.     virtual CString                 GetName                         (VOID); 
  456.     virtual VOID                    SetName                         (LPCTSTR pstr);
  457.  
  458.     CdbProperties                   Properties;
  459.     };
  460.  
  461.  
  462.  
  463. /*****************************************************************************
  464. * CdbGetRowsEx  (holds GetRowsEx for Recordset)
  465. */
  466.  
  467. class DLLEXPORT CdbGetRowsEx : public CdbObject
  468.     {
  469.     public:
  470.  
  471.     // Administration
  472.     CONSTRUCTOR                     CdbGetRowsEx            (VOID);
  473.     CONSTRUCTOR                     CdbGetRowsEx            (ICDAORecordset *pGetRows, BOOL bAddRef=FALSE);
  474.     CONSTRUCTOR                     CdbGetRowsEx            (const CdbGetRowsEx &);
  475.     CdbGetRowsEx &          operator =                      (const CdbGetRowsEx &);
  476.     VOID                            OnInterfaceChange       (VOID);
  477.  
  478.     };
  479.  
  480. /*****************************************************************************
  481. * Helper macros
  482. */
  483.  
  484. //Initialize a variant
  485. #define DAOVINIT(var)                        \
  486.     do                                        \
  487.         {                                    \
  488.         (var).vt    = VT_ERROR;                \
  489.         (var).scode    = DISP_E_PARAMNOTFOUND;    \
  490.         }                                    \
  491.     while (0)
  492.  
  493.  
  494. // LPTSTR to VARIANT
  495. #define STV(pstr)    CdbVariant(pstr)
  496.  
  497. // LPTSTR to BSTR
  498. #define STB(pstr)    V_BSTR(((LPVARIANT)STV(pstr)))
  499.  
  500. // LONG to VARIANT
  501. #define LTV(l)        CdbVariant(l)
  502.  
  503. // Optional LONG to VARIANT
  504. #define OLTV(l)        CdbVariant((l))
  505.  
  506. // C/C++ bool to DAO bool
  507. #define BTB(b)        ((VARIANT_BOOL)(b?-1:0))
  508.  
  509. // C/C++ bool to VARIANT
  510. #define BTV(b)        CdbVariant(BTB(b), TRUE)
  511.  
  512. // C/C++ short to VARIANT
  513. #define SHTV(s)        CdbVariant((SHORT)s)
  514.  
  515. // OLE variant to VARIANT
  516. #define VTV(pv)        CdbVariant(pv)
  517.  
  518. // SAFEARRAY to VARIANT
  519. #define ATV(psa, var)                                \
  520.     do                                                \
  521.         {                                            \
  522.         if (!psa)                                    \
  523.             {                                        \
  524.             var.vt        = VT_ERROR;                    \
  525.             var.scode    = DISP_E_PARAMNOTFOUND;        \
  526.             }                                        \
  527.         else                                        \
  528.             {                                        \
  529.             var.vt        = VT_ARRAY|VT_UI1;            \
  530.             SafeArrayCopy(psa, &var.parray);    \
  531.             }                                        \
  532.         }                                            \
  533.     while (0)
  534.  
  535. #define DAOMFC_CALL(hr)                        \
  536.     do \
  537.     { \
  538.     HRESULT  hresult = (hr);           \
  539.         if(FAILED(hresult)) \
  540.         { \
  541.             TRACE0("\nDBDAO Call Failed.\n\t"); \
  542.             TRACE2("\nIn file %s on line %d\n", _T("DBDAO.CPP"), __LINE__); \
  543.             TRACE1("hResult = %X\n", hresult); \
  544.             if (GetScode(hresult) == E_OUTOFMEMORY) \
  545.                 AfxThrowMemoryException(); \
  546.             else \
  547.                 throw CdbException(hresult); \
  548.         } \
  549.     } while (0)
  550.  
  551.  
  552. /*****************************************************************************
  553. * Property Set/Get helper macros
  554. */
  555.  
  556. // Get a LONG property
  557. #define LPROPGET(intDAO, meth)                        \
  558.     do                                                \
  559.         {                                            \
  560.         intDAO *    p    = (intDAO *)GetInterface();    \
  561.         LONG        l    = 0;                        \
  562.                                                     \
  563.         DAOMFC_CALL(p->meth(&l));                    \
  564.                                                     \
  565.         return l;                                    \
  566.         }                                            \
  567.     while (0)
  568.  
  569. // Set a LONG property
  570. #define LPROPSET(intDAO, meth, l)                    \
  571.     do                                                \
  572.         {                                            \
  573.         intDAO *    p = (intDAO *)GetInterface();    \
  574.                                                     \
  575.         DAOMFC_CALL(p->meth(l));                    \
  576.         }                                            \
  577.     while(0)
  578.  
  579. // Get a SHORT property
  580. #define WPROPGET(intDAO, meth)                        \
  581.     do                                                \
  582.         {                                            \
  583.         intDAO *    p    = (intDAO *)GetInterface();    \
  584.         SHORT        s    = 0;                        \
  585.                                                     \
  586.         DAOMFC_CALL(p->meth(&s));                    \
  587.                                                     \
  588.         return s;                                    \
  589.         }                                            \
  590.     while (0)
  591.  
  592. // Set a SHORT property
  593. #define WPROPSET(intDAO, meth, s)                    \
  594.     do                                                \
  595.         {                                            \
  596.         intDAO *    p = (intDAO *)GetInterface();    \
  597.                                                     \
  598.         DAOMFC_CALL(p->meth(s));                    \
  599.         }                                            \
  600.     while(0)
  601.  
  602. // Get a STRING property
  603. #define SPROPGET(intDAO, meth)                        \
  604.     do                                                \
  605.         {                                            \
  606.         intDAO *    p    = (intDAO *)GetInterface();    \
  607.         CdbBSTR        bstr;                            \
  608.                                                     \
  609.         DAOMFC_CALL(p->meth(bstr));                    \
  610.                                                     \
  611.         return bstr;                                \
  612.         }                                            \
  613.     while (0)
  614.  
  615. // Set a STRING property
  616. #define SPROPSET(intDAO, meth, s)                    \
  617.     do                                                \
  618.         {                                            \
  619.         intDAO *    p = (intDAO *)GetInterface();    \
  620.                                                     \
  621.         DAOMFC_CALL(p->meth(STB(s)));                \
  622.         }                                            \
  623.     while(0)
  624.  
  625. // Get a DATETIME property
  626. #define DPROPGET(intDAO, meth)                        \
  627.     do                                                \
  628.         {                                            \
  629.         intDAO *    p    = (intDAO *)GetInterface();    \
  630.         VARIANT     Var;                                \
  631.                                                     \
  632.         VariantInit(&Var);                            \
  633.         DAOMFC_CALL(p->meth(&Var));                    \
  634.         return Var;                                    \
  635.         }                                            \
  636.     while (0)
  637.  
  638. // Set a DATETIME property
  639. #define DPROPSET(intDAO, meth, pv)                    \
  640.     do                                                \
  641.         {                                            \
  642.         intDAO *    p = (intDAO *)GetInterface();    \
  643.                                                     \
  644.         DAOMFC_CALL(p->meth(*pv));                    \
  645.         }                                            \
  646.     while(0)
  647.  
  648. // Get a BOOLEAN property
  649. #define BPROPGET(intDAO, meth)                            \
  650.     do                                                    \
  651.         {                                                \
  652.         intDAO *        p    = (intDAO *)GetInterface();    \
  653.         VARIANT_BOOL    vb    = 0;                        \
  654.                                                         \
  655.         DAOMFC_CALL(p->meth(&vb));                        \
  656.                                                         \
  657.         return (BOOL)vb;                                \
  658.         }                                                \
  659.     while (0)
  660.  
  661. // Set a BOOLEAN property
  662. #define BPROPSET(intDAO, meth, b)                        \
  663.     do                                                    \
  664.         {                                                \
  665.         intDAO *    p = (intDAO *)GetInterface();        \
  666.                                                         \
  667.         DAOMFC_CALL(p->meth(BTB(b)));                    \
  668.         }                                                \
  669.     while(0)
  670.  
  671. // Get a VARIANT property
  672. #define VPROPGET(intDAO, meth)                        \
  673.     do                                                \
  674.         {                                            \
  675.         intDAO *    p    = (intDAO *)GetInterface();    \
  676.         COleVariant     v;                                \
  677.                                                     \
  678.         VariantInit(&v);                            \
  679.         DAOMFC_CALL(p->meth(&v));                    \
  680.                                                     \
  681.         return &v;                                    \
  682.         }                                            \
  683.     while (0)
  684.  
  685. // Set a VARIANT property
  686. #define VPROPSET(intDAO, meth, pv)                    \
  687.     do                                                \
  688.         {                                            \
  689.         intDAO *    p = (intDAO *)GetInterface();    \
  690.                                                     \
  691.         DAOMFC_CALL(p->meth(*pv));                    \
  692.         }                                            \
  693.     while(0)
  694.  
  695. // Get a DWORD property
  696. #define DWPROPGET(intDAO, meth)                        \
  697.     do                                                \
  698.         {                                            \
  699.         intDAO *    p    = (intDAO *)GetInterface();    \
  700.         DWORD        dw    = 0;                        \
  701.                                                     \
  702.         DAOMFC_CALL(p->meth(&dw));                    \
  703.                                                     \
  704.         return dw;                                    \
  705.         }                                            \
  706.     while (0)
  707.  
  708.  
  709. #define DAOMFC_STATIC_COLLECTION_IMPL(objColl, objSingle, intColl, intSingle)                                                     \
  710.         objSingle            objColl::Item                (LONG i)         { return (intSingle *)(ObItem(i).GetInterface(TRUE)); }     \
  711.         objSingle            objColl::Item                (LPCTSTR pstr)    { return (intSingle *)(ObItem(pstr).GetInterface(TRUE)); } \
  712.         objSingle            objColl::operator[]            (LONG i)        { return (intSingle *)(Item(i).GetInterface(TRUE)); } \
  713.         objSingle            objColl::operator[]            (LPCTSTR pstr)    { return (intSingle *)(Item(pstr).GetInterface(TRUE)); }
  714.  
  715. #define DAOMFC_DYNAMIC_COLLECTION_IMPL(objColl, objSingle, intColl, intSingle)                                                     \
  716.         objSingle            objColl::Item                (LONG i)         { return (intSingle *)(ObItem(i).GetInterface(TRUE)); }     \
  717.         objSingle            objColl::Item                (LPCTSTR pstr)    { return (intSingle *)(ObItem(pstr).GetInterface(TRUE)); } \
  718.         VOID                objColl::Append                (objSingle &o)    { ObAppend(o); } \
  719.         objSingle            objColl::operator[]            (LONG i)        { return (intSingle *)(Item(i).GetInterface(TRUE)); } \
  720.         objSingle            objColl::operator[]            (LPCTSTR pstr)    { return (intSingle *)(Item(pstr).GetInterface(TRUE)); }
  721.  
  722. DECLARE_INTERFACE_(DAOMFCSCollection, _DAOCollection)
  723. {
  724. STDMETHOD(get_Item)        (VARIANT index, LPUNKNOWN *ppunk);
  725. };
  726.  
  727. DECLARE_INTERFACE_(DAOMFCDCollection, _DAODynaCollection)
  728. {
  729. STDMETHOD(get_Item)        (VARIANT index, LPUNKNOWN *ppunk);
  730. };
  731.  
  732.  
  733. #endif // __DBDAO_H_ 
  734.