coriolis/documentation/content/pages/python-cpp/NonDBo.rst

170 lines
5.4 KiB
ReStructuredText

.. -*- Mode: rst -*-
5. Case 3 - Non-DBo Standalone Classe
=======================================
Let's have a look at the encapsulation of ``Hurricane::Point``.
Non-BDo derived classes do not support the bi-directionnal communication.
So each Python object is associated with one C++ object. The C++ object
is created and deleted along with the Python one. This behavior implies
that the C++ object is *copy constructible* (which should be the case).
5.1 Class Header
~~~~~~~~~~~~~~~~~~
Changes from `3.1 Class Associated Header File`:
* There is no ``PyPoint_Link()`` function, as it's related to the
bi-directional communication mechanism.
.. note::
**About the _object attribute** of the PyPoint. As the C++ object life span
(``Point``) is linked to the Python (``PyPoint``) one, we may have used a
value instead of a pointer. It is best to keep a pointer as the macros
written for ``DBo`` derived classes will remain usables.
.. code-block:: c++
#ifndef ISOBAR_PY_POINT_H
#define ISOBAR_PY_POINT_H
#include "hurricane/isobar/PyHurricane.h"
#include "hurricane/Point.h"
namespace Isobar {
extern "C" {
typedef struct {
PyObject_HEAD
Hurricane::Point* _object;
} PyPoint;
extern PyTypeObject PyTypePoint;
extern PyMethodDef PyPoint_Methods[];
extern void PyPoint_LinkPyType();
#define IsPyPoint(v) ( (v)->ob_type == &PyTypePoint )
#define PYPOINT(v) ( (PyPoint*)(v) )
#define PYPOINT_O(v) ( PYPOINT(v)->_object )
} // extern "C".
} // Isobar namespace.
#endif // ISOBAR_PY_POINT_H
|newpage|
5.2 Class File
~~~~~~~~~~~~~~~~
Changes from `3.2 Class Associated File`:
* As there is no ``PyPoint_Link()`` function, there is no call to any
flavor of the ``DBoLinkcreatemethod()`` macro (obvious as it's *not*
a ``DBo``).
* To use the standard Python constructor, we have to define ``PyPoint_NEW()``
and ``PyPoint_Init()`` functions, I'm not absolutely certain that the later
needs to be defined (that part is still not clear to me from the Python doc).
* As it's not a ``DBo`` there is no ``destroy()`` method, so no call to
``DirectDestroyMethod()``
* Lastly, as this object has a ``PyPoint_NEW()`` (field ``tp_new``) and
a ``PyPoint_Init()`` (field ``tp_init``) we have to use the macro
``PyTypeObjectLinkPyTypeNewInit()`` to define ``PyPoint_LinkPyType()``.
.. code-block:: c++
#include "hurricane/isobar/PyPoint.h"
namespace Isobar {
using namespace Hurricane;
extern "C" {
#define METHOD_HEAD(function) GENERIC_METHOD_HEAD(Point,point,function)
#if defined(__PYTHON_MODULE__)
static PyObject* PyPoint_NEW ( PyObject* module, PyObject *args )
{
Point* point = NULL;
HTRY
PyObject* arg0 = NULL;
PyObject* arg1 = NULL;
__cs.init( "Point.Point" );
if (not PyArg_ParseTuple( args,"|O&O&:Point.Point"
, Converter,&arg0
, Converter,&arg1 )) {
PyErr_SetString ( ConstructorError
, "invalid number of parameters for Point constructor." );
return NULL;
}
if (__cs.getObjectIds() == "")
{ point = new Point()); }
else if (__cs.getObjectIds() == ":point")
{ point = new Point( *PYPOINT_O(arg0) ); }
else if (__cs.getObjectIds() == ":int:int")
{ point = new Point( PyAny_AsLong(arg0), PyAny_AsLong(arg1) ); }
else {
PyErr_SetString ( ConstructorError
, "invalid number of parameters for Point constructor." );
return NULL;
}
PyPoint* pyPoint = PyObject_NEW( PyPoint, &PyTypePoint );
if (pyPoint == NULL) { delete point; return NULL; }
pyPoint->_object = point;
HCATCH
return (PyObject*)pyPoint;
}
static int PyPoint_Init ( PyPoint* self, PyObject* args, PyObject* kwargs )
{ return 0; }
DirectGetLongAttribute(PyPoint_getX,getX,PyPoint,Point)
DirectGetLongAttribute(PyPoint_getY,getY,PyPoint,Point)
DirectSetLongAttribute(PyPoint_SetX,setX,PyPoint,Point)
DirectSetLongAttribute(PyPoint_SetY,setY,PyPoint,Point)
PyMethodDef PyPoint_Methods[] =
{ { "getX" , (PyCFunction)PyPoint_getX , METH_NOARGS
, "Return the Point X value." }
, { "getY" , (PyCFunction)PyPoint_getY , METH_NOARGS
, "Return the Point Y value." }
, { "setX" , (PyCFunction)PyPoint_SetX , METH_VARARGS
, "Modify the Point X value." }
, { "setY" , (PyCFunction)PyPoint_SetY , METH_VARARGS
, "Modify the Point Y value." }
, {NULL, NULL, 0, NULL} /* sentinel */
};
DirectDeleteMethod(PyPoint_DeAlloc,PyPoint)
PyTypeObjectLinkPyTypeNewInit(Point)
#else // Python Module Code Part.
PyTypeObjectDefinitions(Point)
#endif // Shared Library Code Part.
} // extern "C".
} // Isobar namespace.
5.2 Class File
~~~~~~~~~~~~~~~~
To put it bluntly, there is no difference in the Python module for
a standalone ``DBo`` class and a non-``DBo`` class.