import os
import sys

os.environ['GI_TYPELIB_PATH'] = '.:' + os.environ['GI_TYPELIB_PATH']

from gi.repository import PygSigTest
from gi.repository import GObject

import ctypes
import ctypes.util
import cairo

pycairo_dll = ctypes.pydll.LoadLibrary(cairo._cairo.__file__)
pycairo_dll.PycairoContext_FromContext.restype = ctypes.py_object
pycairo_dll.PycairoContext_FromContext.argtypes = (ctypes.c_void_p, ctypes.py_object, ctypes.py_object)

cairo_dll = ctypes.pydll.LoadLibrary(ctypes.util.find_library('cairo'))
cairo_dll.cairo_reference.restype = ctypes.c_void_p
cairo_dll.cairo_reference.argtypes = (ctypes.c_void_p,)


def cairo_context_from_gi(gicr):
    assert isinstance(gicr, GObject.GBoxed)
    offset = sys.getsizeof(object())  # size of PyObject_HEAD
    # Pull the "boxed" pointer off out and use it as a cairo_t*
    cr_ptr = ctypes.c_void_p.from_address(id(gicr) + offset)
    cr = pycairo_dll.PycairoContext_FromContext(cr_ptr, cairo.Context, None)
    # Add a new ref because the pycairo context will attempt to manage this
    cairo_dll.cairo_reference(cr_ptr)
    return cr


o = PygSigTest.create()

def on_draw(obj, gicr):
    print(gicr, gicr.__class__.mro())
    print(dir(gicr))

    cr = cairo_context_from_gi(gicr)
    print(cr, cr.__class__.mro())
    print(dir(cr))
    del cr
    del gicr

o.connect('draw', on_draw)
PygSigTest.draw(o)


# vi:ts=4:et
