- added support for ControlActionProcs, exposing the following calls:

- ctl.SetControlAction()
    - CreateScrollBarControl()
    - CreateSliderControl()
- print traceback when callbacks fail
This commit is contained in:
Just van Rossum 2001-12-30 21:25:26 +00:00
parent 85f98143b7
commit cae6da632a
3 changed files with 187 additions and 7 deletions

View File

@ -128,8 +128,10 @@ DataBrowserListViewColumnDesc_Convert(PyObject *v, DataBrowserListViewColumnDesc
} }
/* TrackControl and HandleControlClick callback support */ /* TrackControl and HandleControlClick callback support */
#define kMyControlActionProcTag 'ACTN' /* not an official tag, only for internal use */
static PyObject *tracker; static PyObject *tracker;
static ControlActionUPP mytracker_upp; static ControlActionUPP mytracker_upp;
static ControlActionUPP myactionproc_upp;
static ControlUserPaneDrawUPP mydrawproc_upp; static ControlUserPaneDrawUPP mydrawproc_upp;
static ControlUserPaneIdleUPP myidleproc_upp; static ControlUserPaneIdleUPP myidleproc_upp;
static ControlUserPaneHitTestUPP myhittestproc_upp; static ControlUserPaneHitTestUPP myhittestproc_upp;
@ -1183,6 +1185,25 @@ static PyObject *CtlObj_GetControlVariant(ControlObject *_self, PyObject *_args)
return _res; return _res;
} }
static PyObject *CtlObj_SetControlAction(ControlObject *_self, PyObject *_args)
{
PyObject *_res = NULL;
PyObject* actionProc;
UniversalProcPtr c_callback;
#ifndef SetControlAction
PyMac_PRECHECK(SetControlAction);
#endif
if (!PyArg_ParseTuple(_args, "O",
&actionProc))
return NULL;
SetControlAction(_self->ob_itself,
myactionproc_upp);
Py_INCREF(Py_None);
_res = Py_None;
setcallback((PyObject*)_self, kMyControlActionProcTag, actionProc, &c_callback);
return _res;
}
static PyObject *CtlObj_SetControlReference(ControlObject *_self, PyObject *_args) static PyObject *CtlObj_SetControlReference(ControlObject *_self, PyObject *_args)
{ {
PyObject *_res = NULL; PyObject *_res = NULL;
@ -4004,6 +4025,8 @@ static PyMethodDef CtlObj_methods[] = {
"(ControlPartCode inPart, RgnHandle outRegion) -> None"}, "(ControlPartCode inPart, RgnHandle outRegion) -> None"},
{"GetControlVariant", (PyCFunction)CtlObj_GetControlVariant, 1, {"GetControlVariant", (PyCFunction)CtlObj_GetControlVariant, 1,
"() -> (ControlVariant _rv)"}, "() -> (ControlVariant _rv)"},
{"SetControlAction", (PyCFunction)CtlObj_SetControlAction, 1,
"(PyObject* actionProc) -> None"},
{"SetControlReference", (PyCFunction)CtlObj_SetControlReference, 1, {"SetControlReference", (PyCFunction)CtlObj_SetControlReference, 1,
"(SInt32 data) -> None"}, "(SInt32 data) -> None"},
{"GetControlReference", (PyCFunction)CtlObj_GetControlReference, 1, {"GetControlReference", (PyCFunction)CtlObj_GetControlReference, 1,
@ -4989,6 +5012,52 @@ static PyObject *Ctl_CreateBevelButtonControl(PyObject *_self, PyObject *_args)
} }
#endif #endif
static PyObject *Ctl_CreateSliderControl(PyObject *_self, PyObject *_args)
{
PyObject *_res = NULL;
OSStatus _err;
WindowPtr window;
Rect boundsRect;
SInt32 value;
SInt32 minimum;
SInt32 maximum;
UInt16 orientation;
UInt16 numTickMarks;
Boolean liveTracking;
PyObject* liveTrackingProc;
UniversalProcPtr c_callback;
ControlHandle outControl;
#ifndef CreateSliderControl
PyMac_PRECHECK(CreateSliderControl);
#endif
if (!PyArg_ParseTuple(_args, "O&O&lllHHbO",
WinObj_Convert, &window,
PyMac_GetRect, &boundsRect,
&value,
&minimum,
&maximum,
&orientation,
&numTickMarks,
&liveTracking,
&liveTrackingProc))
return NULL;
_err = CreateSliderControl(window,
&boundsRect,
value,
minimum,
maximum,
orientation,
numTickMarks,
liveTracking,
myactionproc_upp,
&outControl);
if (_err != noErr) return PyMac_Error(_err);
_res = Py_BuildValue("O&",
CtlObj_New, outControl);
setcallback(_res, kMyControlActionProcTag, liveTrackingProc, &c_callback);
return _res;
}
#if TARGET_API_MAC_CARBON #if TARGET_API_MAC_CARBON
static PyObject *Ctl_CreateDisclosureTriangleControl(PyObject *_self, PyObject *_args) static PyObject *Ctl_CreateDisclosureTriangleControl(PyObject *_self, PyObject *_args)
@ -5755,6 +5824,49 @@ static PyObject *Ctl_CreateCheckBoxControl(PyObject *_self, PyObject *_args)
} }
#endif #endif
static PyObject *Ctl_CreateScrollBarControl(PyObject *_self, PyObject *_args)
{
PyObject *_res = NULL;
OSStatus _err;
WindowPtr window;
Rect boundsRect;
SInt32 value;
SInt32 minimum;
SInt32 maximum;
SInt32 viewSize;
Boolean liveTracking;
PyObject* liveTrackingProc;
UniversalProcPtr c_callback;
ControlHandle outControl;
#ifndef CreateScrollBarControl
PyMac_PRECHECK(CreateScrollBarControl);
#endif
if (!PyArg_ParseTuple(_args, "O&O&llllbO",
WinObj_Convert, &window,
PyMac_GetRect, &boundsRect,
&value,
&minimum,
&maximum,
&viewSize,
&liveTracking,
&liveTrackingProc))
return NULL;
_err = CreateScrollBarControl(window,
&boundsRect,
value,
minimum,
maximum,
viewSize,
liveTracking,
myactionproc_upp,
&outControl);
if (_err != noErr) return PyMac_Error(_err);
_res = Py_BuildValue("O&",
CtlObj_New, outControl);
setcallback(_res, kMyControlActionProcTag, liveTrackingProc, &c_callback);
return _res;
}
#if TARGET_API_MAC_CARBON #if TARGET_API_MAC_CARBON
static PyObject *Ctl_CreatePopupButtonControl(PyObject *_self, PyObject *_args) static PyObject *Ctl_CreatePopupButtonControl(PyObject *_self, PyObject *_args)
@ -6144,6 +6256,8 @@ static PyMethodDef Ctl_methods[] = {
{"CreateBevelButtonControl", (PyCFunction)Ctl_CreateBevelButtonControl, 1, {"CreateBevelButtonControl", (PyCFunction)Ctl_CreateBevelButtonControl, 1,
"(WindowPtr window, Rect boundsRect, CFStringRef title, UInt16 thickness, UInt16 behavior, ControlButtonContentInfo info, SInt16 menuID, UInt16 menuBehavior, UInt16 menuPlacement) -> (ControlHandle outControl)"}, "(WindowPtr window, Rect boundsRect, CFStringRef title, UInt16 thickness, UInt16 behavior, ControlButtonContentInfo info, SInt16 menuID, UInt16 menuBehavior, UInt16 menuPlacement) -> (ControlHandle outControl)"},
#endif #endif
{"CreateSliderControl", (PyCFunction)Ctl_CreateSliderControl, 1,
"(WindowPtr window, Rect boundsRect, SInt32 value, SInt32 minimum, SInt32 maximum, UInt16 orientation, UInt16 numTickMarks, Boolean liveTracking, PyObject* liveTrackingProc) -> (ControlHandle outControl)"},
#if TARGET_API_MAC_CARBON #if TARGET_API_MAC_CARBON
{"CreateDisclosureTriangleControl", (PyCFunction)Ctl_CreateDisclosureTriangleControl, 1, {"CreateDisclosureTriangleControl", (PyCFunction)Ctl_CreateDisclosureTriangleControl, 1,
@ -6259,6 +6373,8 @@ static PyMethodDef Ctl_methods[] = {
{"CreateCheckBoxControl", (PyCFunction)Ctl_CreateCheckBoxControl, 1, {"CreateCheckBoxControl", (PyCFunction)Ctl_CreateCheckBoxControl, 1,
"(WindowPtr window, Rect boundsRect, CFStringRef title, SInt32 initialValue, Boolean autoToggle) -> (ControlHandle outControl)"}, "(WindowPtr window, Rect boundsRect, CFStringRef title, SInt32 initialValue, Boolean autoToggle) -> (ControlHandle outControl)"},
#endif #endif
{"CreateScrollBarControl", (PyCFunction)Ctl_CreateScrollBarControl, 1,
"(WindowPtr window, Rect boundsRect, SInt32 value, SInt32 minimum, SInt32 maximum, SInt32 viewSize, Boolean liveTracking, PyObject* liveTrackingProc) -> (ControlHandle outControl)"},
#if TARGET_API_MAC_CARBON #if TARGET_API_MAC_CARBON
{"CreatePopupButtonControl", (PyCFunction)Ctl_CreatePopupButtonControl, 1, {"CreatePopupButtonControl", (PyCFunction)Ctl_CreatePopupButtonControl, 1,
@ -6371,8 +6487,10 @@ mytracker(ControlHandle ctl, short part)
} }
if (rv) if (rv)
Py_DECREF(rv); Py_DECREF(rv);
else else {
PySys_WriteStderr("TrackControl or HandleControlClick: exception in tracker function\n"); PySys_WriteStderr("TrackControl or HandleControlClick: exception in tracker function\n");
PyErr_Print();
}
} }
static int static int
@ -6381,7 +6499,9 @@ setcallback(PyObject *myself, OSType which, PyObject *callback, UniversalProcPtr
ControlObject *self = (ControlObject *)myself; ControlObject *self = (ControlObject *)myself;
char keybuf[9]; char keybuf[9];
if ( which == kControlUserPaneDrawProcTag ) if ( which == kMyControlActionProcTag )
*uppp = (UniversalProcPtr)myactionproc_upp;
else if ( which == kControlUserPaneDrawProcTag )
*uppp = (UniversalProcPtr)mydrawproc_upp; *uppp = (UniversalProcPtr)mydrawproc_upp;
else if ( which == kControlUserPaneIdleProcTag ) else if ( which == kControlUserPaneIdleProcTag )
*uppp = (UniversalProcPtr)myidleproc_upp; *uppp = (UniversalProcPtr)myidleproc_upp;
@ -6418,11 +6538,26 @@ callcallback(ControlObject *self, OSType which, PyObject *arglist)
return NULL; return NULL;
} }
rv = PyEval_CallObject(func, arglist); rv = PyEval_CallObject(func, arglist);
if ( rv == NULL ) if ( rv == NULL ) {
PySys_WriteStderr("Exception in control callback %x handler\n", (unsigned)which); PySys_WriteStderr("Exception in control callback %x handler\n", (unsigned)which);
PyErr_Print();
}
return rv; return rv;
} }
static pascal void
myactionproc(ControlHandle control, SInt16 part)
{
ControlObject *ctl_obj;
PyObject *arglist, *rv;
ctl_obj = (ControlObject *)CtlObj_WhichControl(control);
arglist = Py_BuildValue("Oh", ctl_obj, part);
rv = callcallback(ctl_obj, kMyControlActionProcTag, arglist);
Py_XDECREF(arglist);
Py_XDECREF(rv);
}
static pascal void static pascal void
mydrawproc(ControlHandle control, SInt16 part) mydrawproc(ControlHandle control, SInt16 part)
{ {
@ -6494,6 +6629,7 @@ void init_Ctl(void)
mytracker_upp = NewControlActionUPP(mytracker); mytracker_upp = NewControlActionUPP(mytracker);
myactionproc_upp = NewControlActionUPP(myactionproc);
mydrawproc_upp = NewControlUserPaneDrawUPP(mydrawproc); mydrawproc_upp = NewControlUserPaneDrawUPP(mydrawproc);
myidleproc_upp = NewControlUserPaneIdleUPP(myidleproc); myidleproc_upp = NewControlUserPaneIdleUPP(myidleproc);
myhittestproc_upp = NewControlUserPaneHitTestUPP(myhittestproc); myhittestproc_upp = NewControlUserPaneHitTestUPP(myhittestproc);

View File

@ -88,6 +88,7 @@ class MyScanner(Scanner):
'GetControlPropertySize', 'GetControlPropertySize',
'SendControlMessage', # Parameter changed from long to void* from UH3.3 to UH3.4 'SendControlMessage', # Parameter changed from long to void* from UH3.3 to UH3.4
'CreateTabsControl', # wrote manually 'CreateTabsControl', # wrote manually
'GetControlAction', # too much effort for too little usefulness
# too lazy for now # too lazy for now
'GetImageWellContentInfo', 'GetImageWellContentInfo',
@ -259,7 +260,7 @@ class MyScanner(Scanner):
def makeblacklisttypes(self): def makeblacklisttypes(self):
return [ return [
'ProcPtr', 'ProcPtr',
'ControlActionUPP', # 'ControlActionUPP',
'Ptr', 'Ptr',
'ControlDefSpec', # Don't know how to do this yet 'ControlDefSpec', # Don't know how to do this yet
'ControlDefSpec_ptr', # ditto 'ControlDefSpec_ptr', # ditto
@ -319,6 +320,9 @@ class MyScanner(Scanner):
([("ControlButtonContentInfo", '*', "OutMode")], ([("ControlButtonContentInfo", '*', "OutMode")],
[("ControlButtonContentInfo", '*', "InMode")]), [("ControlButtonContentInfo", '*', "InMode")]),
([("ControlActionUPP", 'liveTrackingProc', "InMode")],
[("ControlActionUPPNewControl", 'liveTrackingProc', "InMode")]),
] ]
if __name__ == "__main__": if __name__ == "__main__":

View File

@ -94,6 +94,24 @@ ControlBevelButtonMenuBehavior = UInt16
ControlBevelButtonMenuPlacement = UInt16 ControlBevelButtonMenuPlacement = UInt16
ControlPushButtonIconAlignment = UInt16 ControlPushButtonIconAlignment = UInt16
class ControlActionDefinition(Type):
def declare(self, name):
Output("%s %s;", self.typeName, name)
Output("UniversalProcPtr c_callback;")
def passInput(self, name):
return "myactionproc_upp"
def cleanup(self, name):
Output("setcallback((PyObject*)_self, kMyControlActionProcTag, actionProc, &c_callback);")
class ControlActionDefinitionNewControl(ControlActionDefinition):
def cleanup(self, name):
Output("setcallback(_res, kMyControlActionProcTag, liveTrackingProc, &c_callback);")
ControlActionUPP = ControlActionDefinition("PyObject*", "O")
ControlActionUPPNewControl = ControlActionDefinitionNewControl("PyObject*", "O")
ControlSliderOrientation = UInt16
includestuff = includestuff + """ includestuff = includestuff + """
#ifdef WITHOUT_FRAMEWORKS #ifdef WITHOUT_FRAMEWORKS
#include <Controls.h> #include <Controls.h>
@ -203,8 +221,10 @@ DataBrowserListViewColumnDesc_Convert(PyObject *v, DataBrowserListViewColumnDesc
} }
/* TrackControl and HandleControlClick callback support */ /* TrackControl and HandleControlClick callback support */
#define kMyControlActionProcTag 'ACTN' /* not an official tag, only for internal use */
static PyObject *tracker; static PyObject *tracker;
static ControlActionUPP mytracker_upp; static ControlActionUPP mytracker_upp;
static ControlActionUPP myactionproc_upp;
static ControlUserPaneDrawUPP mydrawproc_upp; static ControlUserPaneDrawUPP mydrawproc_upp;
static ControlUserPaneIdleUPP myidleproc_upp; static ControlUserPaneIdleUPP myidleproc_upp;
static ControlUserPaneHitTestUPP myhittestproc_upp; static ControlUserPaneHitTestUPP myhittestproc_upp;
@ -279,8 +299,10 @@ mytracker(ControlHandle ctl, short part)
} }
if (rv) if (rv)
Py_DECREF(rv); Py_DECREF(rv);
else else {
PySys_WriteStderr("TrackControl or HandleControlClick: exception in tracker function\\n"); PySys_WriteStderr("TrackControl or HandleControlClick: exception in tracker function\\n");
PyErr_Print();
}
} }
static int static int
@ -289,7 +311,9 @@ setcallback(PyObject *myself, OSType which, PyObject *callback, UniversalProcPtr
ControlObject *self = (ControlObject *)myself; ControlObject *self = (ControlObject *)myself;
char keybuf[9]; char keybuf[9];
if ( which == kControlUserPaneDrawProcTag ) if ( which == kMyControlActionProcTag )
*uppp = (UniversalProcPtr)myactionproc_upp;
else if ( which == kControlUserPaneDrawProcTag )
*uppp = (UniversalProcPtr)mydrawproc_upp; *uppp = (UniversalProcPtr)mydrawproc_upp;
else if ( which == kControlUserPaneIdleProcTag ) else if ( which == kControlUserPaneIdleProcTag )
*uppp = (UniversalProcPtr)myidleproc_upp; *uppp = (UniversalProcPtr)myidleproc_upp;
@ -326,11 +350,26 @@ callcallback(ControlObject *self, OSType which, PyObject *arglist)
return NULL; return NULL;
} }
rv = PyEval_CallObject(func, arglist); rv = PyEval_CallObject(func, arglist);
if ( rv == NULL ) if ( rv == NULL ) {
PySys_WriteStderr("Exception in control callback %x handler\\n", (unsigned)which); PySys_WriteStderr("Exception in control callback %x handler\\n", (unsigned)which);
PyErr_Print();
}
return rv; return rv;
} }
static pascal void
myactionproc(ControlHandle control, SInt16 part)
{
ControlObject *ctl_obj;
PyObject *arglist, *rv;
ctl_obj = (ControlObject *)CtlObj_WhichControl(control);
arglist = Py_BuildValue("Oh", ctl_obj, part);
rv = callcallback(ctl_obj, kMyControlActionProcTag, arglist);
Py_XDECREF(arglist);
Py_XDECREF(rv);
}
static pascal void static pascal void
mydrawproc(ControlHandle control, SInt16 part) mydrawproc(ControlHandle control, SInt16 part)
{ {
@ -396,6 +435,7 @@ mytrackingproc(ControlHandle control, Point startPt, ControlActionUPP actionProc
initstuff = initstuff + """ initstuff = initstuff + """
mytracker_upp = NewControlActionUPP(mytracker); mytracker_upp = NewControlActionUPP(mytracker);
myactionproc_upp = NewControlActionUPP(myactionproc);
mydrawproc_upp = NewControlUserPaneDrawUPP(mydrawproc); mydrawproc_upp = NewControlUserPaneDrawUPP(mydrawproc);
myidleproc_upp = NewControlUserPaneIdleUPP(myidleproc); myidleproc_upp = NewControlUserPaneIdleUPP(myidleproc);
myhittestproc_upp = NewControlUserPaneHitTestUPP(myhittestproc); myhittestproc_upp = NewControlUserPaneHitTestUPP(myhittestproc);