Click here to Skip to main content
15,887,821 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
I create a ATL project with Visual Studio 2010, and add a ATL simple object class in this project. There is no any error during the building process. But when I declare a class object, such as CCartoPoint pt, I get the error message "error C2259: 'CCartoPoint' : cannot instantiate abstract class"

In the following codes, the error message is from the method 'STDMETHODIMP CCartoPoint::get_Centroid( ICartoPoint** pCentroidVal)'.

I have checked the the numbers of methods in IDL file, in .h file and the .cpp file is same.

The *.IDL file:
C++
[
	object,
	uuid(14428BC6-A897-4268-8FFD-B4947DEDDFC6),
	dual,
	nonextensible,
	pointer_default(unique)
]
interface ICartoPoint : IDispatch{
	[propget, id(2)] HRESULT X([out, retval] DOUBLE* pVal);
	[propput, id(2)] HRESULT X([in] DOUBLE newVal);
	[propget, id(3)] HRESULT Y([out, retval] DOUBLE* pVal);
	[propput, id(3)] HRESULT Y([in] DOUBLE newVal);
};
[
	object,
	uuid(238155D0-220A-4BFA-90D2-46E27461E314),
	dual,
	nonextensible,
	pointer_default(unique)
]
interface ICartoGeometry : IDispatch{
	[propget, id(1)] HRESULT Area([out, retval] DOUBLE* pAreaVal);
	[propget, id(2)] HRESULT Centroid([out, retval] ICartoPoint** pCentroidVal);
	[propget, id(3)] HRESULT GeometryType([out, retval] cartoGeometryType* pTypeVal);
	//[propget, id(4)] HRESULT Coordinates([out, retval] ICartoCoordinate** pCdsVal,[out] DOUBLE* pCountVal);
	[propget, id(5)] HRESULT NumGeometries([out, retval] LONG* pNumberVal);
	[propget, id(6)] HRESULT NumPoints([out, retval] LONG* pNumberVal);
	[propget, id(7)] HRESULT Coordinates([out, retval] ICartoCoordinate** pVal);
};


The *.h file
C++
class ATL_NO_VTABLE CCartoPoint :
	public CComObjectRootEx<CComSingleThreadModel>,
	public CComCoClass<CCartoPoint, &CLSID_CartoPoint>,
	public IDispatchImpl<ICartoPoint, &IID_ICartoPoint, &LIBID_GeometryObjectLib, /*wMajor =*/ 1, /*wMinor =*/ 0>,
    public IDispatchImpl<ICartoGeometry, &IID_ICartoGeometry, &LIBID_GeometryObjectLib, /*wMajor =*/ 1, /*wMinor =*/ 0>
{
public:
	CCartoPoint()
	{
		m_pCoordinate = new Coordinate(0,0);

		GeometryFactory factory;
		m_pPoint = factory.createPoint(*m_pCoordinate);

	}

	CCartoPoint(DOUBLE x, DOUBLE y)
	{
		m_pCoordinate = new Coordinate(x,y);

		GeometryFactory factory;
		m_pPoint = factory.createPoint(*m_pCoordinate);

	}

DECLARE_REGISTRY_RESOURCEID(IDR_CARTOPOINT)


BEGIN_COM_MAP(CCartoPoint)
	COM_INTERFACE_ENTRY(ICartoPoint)
	COM_INTERFACE_ENTRY2(IDispatch,ICartoPoint)
	COM_INTERFACE_ENTRY(ICartoGeometry)
END_COM_MAP()



	DECLARE_PROTECT_FINAL_CONSTRUCT()

	HRESULT FinalConstruct()
	{
		return S_OK;
	}

	void FinalRelease()
	{
	}

public:
	STDMETHOD(get_X)(DOUBLE* pVal);
	STDMETHOD(put_X)(DOUBLE newVal);
	STDMETHOD(get_Y)(DOUBLE* pVal);
	STDMETHOD(put_Y)(DOUBLE newVal);

public:
	STDMETHOD(get_Area)(DOUBLE* pAreaVal);
	STDMETHOD(get_Centroid)( ICartoPoint** pCentroidVal);
	STDMETHOD(get_GeometryType)( cartoGeometryType* pTypeVal);
	STDMETHOD(get_NumGeometries)(LONG* pNumberVal);
	STDMETHOD(get_NumPoints)( LONG* pNumberVal);
	STDMETHOD(get_Coordinates)(ICartoCoordinate** pVal);

private:
	Point* m_pPoint;
	Coordinate* m_pCoordinate;
};

OBJECT_ENTRY_AUTO(__uuidof(CartoPoint), CCartoPoint)


The *.cpp file
C++
STDMETHODIMP CCartoPoint::get_X(DOUBLE* pVal)
{
	return S_OK;
}


STDMETHODIMP CCartoPoint::put_X(DOUBLE newVal)
{
	return S_OK;
}


STDMETHODIMP CCartoPoint::get_Y(DOUBLE* pVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::put_Y(DOUBLE newVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::get_Area(DOUBLE* pAreaVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::get_Centroid( ICartoPoint** pCentroidVal)
{
	CCartoPoint pt;

	return S_OK;
}

STDMETHODIMP CCartoPoint::get_GeometryType( cartoGeometryType* pTypeVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::get_NumGeometries(LONG* pNumberVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::get_NumPoints( LONG* pNumberVal)
{
	return S_OK;
}

STDMETHODIMP CCartoPoint::get_Coordinates(ICartoCoordinate** pVal)
{
	return S_OK;
}
Posted
Updated 18-Jul-13 16:04pm
v2

I didn't check if you are missing any APIs but the ATL_NO_VTABLE spec on the class definition tells the compiler that the class will not be instantiated.

[If you fix that, there still might be one or more APIs that need to be implemented...]
 
Share this answer
 
The idea of abstract class is to limit its instantiation. Such class is not designed for having instances of it, it is designed to be used as a base class in some derived classes, some of which also may remain abstract. And abstract class may have pure abstract functions (which have their placeholder in a virtual table, but not implementation, even though they are actually used in other functions, so using instances of such classes would be dangerous. Formally, however, it's not required; a class can be abstract by design, and some functions of it can be virtual but implemented (pseudo-abstract or non-abstract).

—SA
 
Share this answer
 
Comments
Member fish 18-Jul-13 22:54pm    
The Class 'CCartoPoint' in my code is not a abstract class. I can call the dll created from the project in c#. And the instantiation of the class 'CCartoPoint' is allowed in c#.

So in the ATL or c++, is there a special method to create a class object of ATL Simple Object Class, such the class 'CCartoPoint' in my code ?

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900