CENUMPT.CPP
资源名称:MSDN_VC98.zip [点击查看]
上传用户:bangxh
上传日期:2007-01-31
资源大小:42235k
文件大小:6k
源码类别:
Windows编程
开发平台:
Visual C++
- /***
- *cenumpt.cpp
- *
- * This is a part of the Microsoft Source Code Samples.
- *
- * Copyright (C) 1992-1997 Microsoft Corporation. All rights reserved.
- *
- * This source code is only intended as a supplement to Microsoft Development
- * Tools and/or WinHelp documentation. See these sources for detailed
- * information regarding the Microsoft samples programs.
- *
- *Purpose:
- * This module implements the CEnumPoint class.
- *
- *
- *Implementation Notes:
- *
- *****************************************************************************/
- #include "hostenv.h"
- #include "cenumpt.h"
- CEnumPoint::CEnumPoint()
- {
- m_refs = 0;
- m_psa = NULL;
- m_celts = 0;
- m_iCurrent = 0;
- }
- /***
- *HRESULT CEnumPoint::Create(SAFEARRAY*, CEnumPoint**)
- *Purpose:
- * This routine creates a CPoint enumerator from the given
- * (1 X N) SafeArray of CPoint IDispatch pointers.
- *
- *Entry:
- * psa = pointer to a SafeArray of VARIANTs
- *
- *Exit:
- * return value = HRESULT
- *
- * *ppenum = pointer to a CPoint enumerator
- *
- ***********************************************************************/
- HRESULT
- CEnumPoint::Create(SAFEARRAY FAR* psa, CEnumPoint FAR* FAR* ppenum)
- {
- long lBound;
- HRESULT hresult;
- CEnumPoint FAR* penum;
- // Verify that the SafeArray is the proper shape.
- //
- if(SafeArrayGetDim(psa) != 1)
- return E_INVALIDARG;
- hresult = SafeArrayGetLBound(psa, 1, &lBound);
- if(FAILED(hresult))
- return hresult;
- if(lBound != 0)
- return E_INVALIDARG;
- penum = new FAR CEnumPoint();
- if(penum == NULL)
- return E_OUTOFMEMORY;
- penum->AddRef();
- hresult = SafeArrayGetUBound(psa, 1, &lBound);
- if(FAILED(hresult))
- goto LError0;
- penum->m_psa = psa;
- penum->m_celts = lBound + 1;
- *ppenum = penum;
- return NOERROR;
- LError0:;
- penum->Release();
- return hresult;
- }
- //---------------------------------------------------------------------
- // IUnknown methods
- //---------------------------------------------------------------------
- STDMETHODIMP
- CEnumPoint::QueryInterface(REFIID riid, void FAR* FAR* ppv)
- {
- if(IsEqualIID(riid, IID_IEnumVARIANT) || IsEqualIID(riid, IID_IUnknown)){
- *ppv = this;
- AddRef();
- return NOERROR;
- }
- *ppv = NULL;
- return E_NOINTERFACE;
- }
- STDMETHODIMP_(unsigned long)
- CEnumPoint::AddRef()
- {
- return ++m_refs;
- }
- STDMETHODIMP_(unsigned long)
- CEnumPoint::Release()
- {
- if(--m_refs == 0){
- if(m_psa != NULL)
- SafeArrayDestroy(m_psa);
- delete this;
- return 0;
- }
- return m_refs;
- }
- //---------------------------------------------------------------------
- // IEnumVARIANT methods
- //---------------------------------------------------------------------
- /***
- *HRESULT CEnumPoint::Next(unsigned long, VARIANT*, unsigned long*)
- *Purpose:
- * Attempt to get the next 'celt' items in the enumeration sequence.
- *
- *Entry:
- * celt = the number of elements to get
- *
- *Exit:
- * return value = HRESULT
- * S_OK
- * S_FALSE - the end of the sequence was reached
- *
- * rgvar = array of the next 'celt' items
- * *pceltFetched = count of the elements actually fetched.
- *
- ***********************************************************************/
- STDMETHODIMP
- CEnumPoint::Next(
- unsigned long celt,
- VARIANT FAR* rgvar,
- unsigned long FAR* pceltFetched)
- {
- long ix;
- unsigned int i;
- HRESULT hresult;
- for(i = 0; i < celt; ++i)
- VariantInit(&rgvar[i]);
- for(i = 0; i < celt; ++i){
- if(m_iCurrent == m_celts){
- hresult = S_FALSE;
- goto LDone;
- }
- ix = m_iCurrent++;
- hresult = SafeArrayGetElement(m_psa, &ix, &rgvar[i]);
- if(FAILED(hresult))
- goto LError0;
- }
- hresult = NOERROR;
- LDone:;
- if (pceltFetched != NULL)
- *pceltFetched = i;
- return hresult;
- LError0:;
- for(i = 0; i < celt; ++i)
- VariantClear(&rgvar[i]);
- return hresult;
- }
- /***
- *HRESULT CEnumPoint::Skip(unsigned long)
- *Purpose:
- * Attempt to skip over the next 'celt' elements in the enumeration
- * sequence.
- *
- *Entry:
- * celt = the count of elements to skip
- *
- *Exit:
- * return value = HRESULT
- * S_OK
- * S_FALSE - the end of the sequence was reached
- *
- ***********************************************************************/
- STDMETHODIMP
- CEnumPoint::Skip(unsigned long celt)
- {
- m_iCurrent += celt;
- if(m_iCurrent > m_celts)
- m_iCurrent = m_celts;
- return (m_iCurrent == m_celts)
- ? S_FALSE : NOERROR;
- }
- /***
- *HRESULT CEnumPoint::Reset(void)
- *Purpose:
- * Reset the enumeration sequence back to the beginning.
- *
- *Entry:
- * None
- *
- *Exit:
- * return value = SHRESULT CODE
- * S_OK
- *
- ***********************************************************************/
- STDMETHODIMP
- CEnumPoint::Reset()
- {
- m_iCurrent = 0;
- return NOERROR;
- }
- /***
- *HRESULT CEnumPoint::Clone(IEnumVARIANT**)
- *Purpose:
- * Retrun a CPoint enumerator with exactly the same state as the
- * current one.
- *
- *Entry:
- * None
- *
- *Exit:
- * return value = HRESULT
- * S_OK
- * E_OUTOFMEMORY
- *
- ***********************************************************************/
- STDMETHODIMP
- CEnumPoint::Clone(IEnumVARIANT FAR* FAR* ppenum)
- {
- HRESULT hresult;
- SAFEARRAY FAR* psa;
- CEnumPoint FAR* penum;
- hresult = SafeArrayCopy(m_psa, &psa);
- if(FAILED(hresult))
- return hresult;
- hresult = CEnumPoint::Create(psa, &penum);
- if(FAILED(hresult))
- goto LError0;
- // Assert(penum->m_celts == m_celts);
- penum->m_iCurrent = m_iCurrent;
- *ppenum = penum;
- return NOERROR;
- LError0:
- SafeArrayDestroy(psa);
- return hresult;
- }