diff options
author | Campbell Barton <ideasman42@gmail.com> | 2021-10-11 11:59:06 +0300 |
---|---|---|
committer | Campbell Barton <ideasman42@gmail.com> | 2021-10-11 12:14:15 +0300 |
commit | a6d34f4c3f2a86af1cabf75c89e85a35d38073c3 (patch) | |
tree | 3cae85c8adc109831c47dc59cccf964fd20903aa /source/blender/python/intern | |
parent | 6e92a2d5914d3f198ec16236638dfc04496da209 (diff) |
Cleanup: add utility functions to parse gizmos and target properties
Diffstat (limited to 'source/blender/python/intern')
-rw-r--r-- | source/blender/python/intern/bpy_rna_gizmo.c | 209 |
1 files changed, 141 insertions, 68 deletions
diff --git a/source/blender/python/intern/bpy_rna_gizmo.c b/source/blender/python/intern/bpy_rna_gizmo.c index f121bfd6e36..5294f56d5c6 100644 --- a/source/blender/python/intern/bpy_rna_gizmo.c +++ b/source/blender/python/intern/bpy_rna_gizmo.c @@ -17,7 +17,7 @@ /** \file * \ingroup pythonintern * - * . + * This file defines utility methods for `bpy.types.Gizmo`. */ #include <Python.h> @@ -44,6 +44,84 @@ #include "bpy_rna.h" /* -------------------------------------------------------------------- */ +/** \name Parsing Utility Functions + * + * Functions used as callbacks for #PyArg_ParseTuple `O&` format string. + * \{ */ + +struct BPyGizmoWithTarget { + wmGizmo *gz; /* Must be first. */ + wmGizmoProperty *gz_prop; +}; + +struct BPyGizmoWithTargetType { + wmGizmo *gz; /* Must be first. */ + const wmGizmoPropertyType *gz_prop_type; +}; + +static int py_rna_gizmo_parse(PyObject *o, void *p) +{ + /* No type checking (this is `self` not a user defined argument). */ + BLI_assert(BPy_StructRNA_Check(o)); + BLI_assert(((const BPy_StructRNA *)o)->ptr.type == &RNA_Gizmo); + + wmGizmo **gz_p = p; + *gz_p = ((const BPy_StructRNA *)o)->ptr.data; + return 1; +} + +static int py_rna_gizmo_target_id_parse(PyObject *o, void *p) +{ + struct BPyGizmoWithTarget *gizmo_with_target = p; + /* Must be set by `py_rna_gizmo_parse`. */ + wmGizmo *gz = gizmo_with_target->gz; + BLI_assert(gz != NULL); + + if (!PyUnicode_Check(o)) { + PyErr_Format(PyExc_TypeError, "expected a string (got %.200s)", Py_TYPE(o)->tp_name); + return 0; + } + const char *gz_prop_id = PyUnicode_AsUTF8(o); + wmGizmoProperty *gz_prop = WM_gizmo_target_property_find(gz, gz_prop_id); + if (gz_prop == NULL) { + PyErr_Format(PyExc_ValueError, + "Gizmo target property '%s.%s' not found!", + gz->type->idname, + gz_prop_id); + return 0; + } + gizmo_with_target->gz_prop = gz_prop; + return 1; +} + +static int py_rna_gizmo_target_type_id_parse(PyObject *o, void *p) +{ + struct BPyGizmoWithTargetType *gizmo_with_target = p; + /* Must be set first. */ + wmGizmo *gz = gizmo_with_target->gz; + BLI_assert(gz != NULL); + + if (!PyUnicode_Check(o)) { + PyErr_Format(PyExc_TypeError, "expected a string (got %.200s)", Py_TYPE(o)->tp_name); + return 0; + } + const char *gz_prop_id = PyUnicode_AsUTF8(o); + const wmGizmoPropertyType *gz_prop_type = WM_gizmotype_target_property_find(gz->type, + gz_prop_id); + if (gz_prop_type == NULL) { + PyErr_Format(PyExc_ValueError, + "Gizmo target property '%s.%s' not found!", + gz->type->idname, + gz_prop_id); + return 0; + } + gizmo_with_target->gz_prop_type = gz_prop_type; + return 1; +} + +/** \} */ + +/* -------------------------------------------------------------------- */ /** \name Gizmo Target Property Define API * \{ */ @@ -240,12 +318,10 @@ static PyObject *bpy_gizmo_target_set_handler(PyObject *UNUSED(self), PyObject * const PyGILState_STATE gilstate = PyGILState_Ensure(); struct { - PyObject *self; - char *target; + struct BPyGizmoWithTargetType gz_with_target_type; PyObject *py_fn_slots[BPY_GIZMO_FN_SLOT_LEN]; } params = { - .self = NULL, - .target = NULL, + .gz_with_target_type = {NULL, NULL}, .py_fn_slots = {NULL}, }; @@ -253,29 +329,25 @@ static PyObject *bpy_gizmo_target_set_handler(PyObject *UNUSED(self), PyObject * * 'Gizmo.target_set_prop & target_set_operator' * (see: rna_wm_gizmo_api.c). conventions should match. */ static const char *const _keywords[] = {"self", "target", "get", "set", "range", NULL}; - static _PyArg_Parser _parser = {"Os|$OOO:target_set_handler", _keywords, 0}; + static _PyArg_Parser _parser = {"O&O&|$OOO:target_set_handler", _keywords, 0}; if (!_PyArg_ParseTupleAndKeywordsFast(args, kw, &_parser, - ¶ms.self, - ¶ms.target, + /* `self` */ + py_rna_gizmo_parse, + ¶ms.gz_with_target_type.gz, + /* `target` */ + py_rna_gizmo_target_type_id_parse, + ¶ms.gz_with_target_type, + /* `get/set/range` */ ¶ms.py_fn_slots[BPY_GIZMO_FN_SLOT_GET], ¶ms.py_fn_slots[BPY_GIZMO_FN_SLOT_SET], ¶ms.py_fn_slots[BPY_GIZMO_FN_SLOT_RANGE_GET])) { goto fail; } - wmGizmo *gz = ((BPy_StructRNA *)params.self)->ptr.data; - - const wmGizmoPropertyType *gz_prop_type = WM_gizmotype_target_property_find(gz->type, - params.target); - if (gz_prop_type == NULL) { - PyErr_Format(PyExc_ValueError, - "Gizmo target property '%s.%s' not found", - gz->type->idname, - params.target); - goto fail; - } + wmGizmo *gz = params.gz_with_target_type.gz; + const wmGizmoPropertyType *gz_prop_type = params.gz_with_target_type.gz_prop_type; { const int slots_required = 2; @@ -338,29 +410,27 @@ PyDoc_STRVAR(bpy_gizmo_target_get_value_doc, static PyObject *bpy_gizmo_target_get_value(PyObject *UNUSED(self), PyObject *args, PyObject *kw) { struct { - PyObject *self; - char *target; + struct BPyGizmoWithTarget gz_with_target; } params = { - .self = NULL, - .target = NULL, + .gz_with_target = {NULL, NULL}, }; static const char *const _keywords[] = {"self", "target", NULL}; - static _PyArg_Parser _parser = {"Os:target_get_value", _keywords, 0}; - if (!_PyArg_ParseTupleAndKeywordsFast(args, kw, &_parser, ¶ms.self, ¶ms.target)) { + static _PyArg_Parser _parser = {"O&O&:target_get_value", _keywords, 0}; + if (!_PyArg_ParseTupleAndKeywordsFast(args, + kw, + &_parser, + /* `self` */ + py_rna_gizmo_parse, + ¶ms.gz_with_target.gz, + /* `target` */ + py_rna_gizmo_target_id_parse, + ¶ms.gz_with_target)) { goto fail; } - wmGizmo *gz = ((BPy_StructRNA *)params.self)->ptr.data; - - wmGizmoProperty *gz_prop = WM_gizmo_target_property_find(gz, params.target); - if (gz_prop == NULL) { - PyErr_Format(PyExc_ValueError, - "Gizmo target property '%s.%s' not found", - gz->type->idname, - params.target); - goto fail; - } + wmGizmo *gz = params.gz_with_target.gz; + wmGizmoProperty *gz_prop = params.gz_with_target.gz_prop; const int array_len = WM_gizmo_target_property_array_length(gz, gz_prop); switch (gz_prop->type->data_type) { @@ -396,32 +466,31 @@ PyDoc_STRVAR(bpy_gizmo_target_set_value_doc, static PyObject *bpy_gizmo_target_set_value(PyObject *UNUSED(self), PyObject *args, PyObject *kw) { struct { - PyObject *self; - char *target; + struct BPyGizmoWithTarget gz_with_target; PyObject *value; } params = { - .self = NULL, - .target = NULL, + .gz_with_target = {NULL, NULL}, .value = NULL, }; static const char *const _keywords[] = {"self", "target", "value", NULL}; - static _PyArg_Parser _parser = {"OsO:target_set_value", _keywords, 0}; - if (!_PyArg_ParseTupleAndKeywordsFast( - args, kw, &_parser, ¶ms.self, ¶ms.target, ¶ms.value)) { + static _PyArg_Parser _parser = {"O&O&O:target_set_value", _keywords, 0}; + if (!_PyArg_ParseTupleAndKeywordsFast(args, + kw, + &_parser, + /* `self` */ + py_rna_gizmo_parse, + ¶ms.gz_with_target.gz, + /* `target` */ + py_rna_gizmo_target_id_parse, + ¶ms.gz_with_target, + /* `value` */ + ¶ms.value)) { goto fail; } - wmGizmo *gz = ((BPy_StructRNA *)params.self)->ptr.data; - - wmGizmoProperty *gz_prop = WM_gizmo_target_property_find(gz, params.target); - if (gz_prop == NULL) { - PyErr_Format(PyExc_ValueError, - "Gizmo target property '%s.%s' not found", - gz->type->idname, - params.target); - goto fail; - } + wmGizmo *gz = params.gz_with_target.gz; + wmGizmoProperty *gz_prop = params.gz_with_target.gz_prop; const int array_len = WM_gizmo_target_property_array_length(gz, gz_prop); switch (gz_prop->type->data_type) { @@ -468,29 +537,27 @@ PyDoc_STRVAR(bpy_gizmo_target_get_range_doc, static PyObject *bpy_gizmo_target_get_range(PyObject *UNUSED(self), PyObject *args, PyObject *kw) { struct { - PyObject *self; - char *target; + struct BPyGizmoWithTarget gz_with_target; } params = { - .self = NULL, - .target = NULL, + .gz_with_target = {NULL, NULL}, }; static const char *const _keywords[] = {"self", "target", NULL}; - static _PyArg_Parser _parser = {"Os:target_get_range", _keywords, 0}; - if (!_PyArg_ParseTupleAndKeywordsFast(args, kw, &_parser, ¶ms.self, ¶ms.target)) { + static _PyArg_Parser _parser = {"O&O&:target_get_range", _keywords, 0}; + if (!_PyArg_ParseTupleAndKeywordsFast(args, + kw, + &_parser, + /* `self` */ + py_rna_gizmo_parse, + ¶ms.gz_with_target.gz, + /* `target` */ + py_rna_gizmo_target_id_parse, + ¶ms.gz_with_target)) { goto fail; } - wmGizmo *gz = ((BPy_StructRNA *)params.self)->ptr.data; - - wmGizmoProperty *gz_prop = WM_gizmo_target_property_find(gz, params.target); - if (gz_prop == NULL) { - PyErr_Format(PyExc_ValueError, - "Gizmo target property '%s.%s' not found", - gz->type->idname, - params.target); - goto fail; - } + wmGizmo *gz = params.gz_with_target.gz; + wmGizmoProperty *gz_prop = params.gz_with_target.gz_prop; switch (gz_prop->type->data_type) { case PROP_FLOAT: { @@ -510,6 +577,10 @@ fail: /** \} */ +/* -------------------------------------------------------------------- */ +/** \name Gizmo Module + * \{ */ + bool BPY_rna_gizmo_module(PyObject *mod_par) { static PyMethodDef method_def_array[] = { @@ -546,3 +617,5 @@ bool BPY_rna_gizmo_module(PyObject *mod_par) return false; } + +/** \} */ |