Update of /cvsroot/mahogany/M/src/Python
In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv30406/src/Python
Modified Files:
PythonHelp.cpp
Log Message:
added PythonStringFunction()
Index: PythonHelp.cpp
===================================================================
RCS file: /cvsroot/mahogany/M/src/Python/PythonHelp.cpp,v
retrieving revision 1.36
retrieving revision 1.37
diff -b -u -2 -r1.36 -r1.37
--- PythonHelp.cpp 18 Sep 2004 19:02:57 -0000 1.36
+++ PythonHelp.cpp 18 Sep 2004 19:27:54 -0000 1.37
@@ -48,4 +48,5 @@
// ----------------------------------------------------------------------------
+extern const MOption MP_PYTHONMODULE_TO_LOAD;
extern const MOption MP_USEPYTHON;
@@ -70,48 +71,11 @@
};
-// ----------------------------------------------------------------------------
-// private functions prototypes
-// ----------------------------------------------------------------------------
-
-/**
- Converts a PyObject to a C++ variable in a safe way.
-
- This function takes ownership of pyResult (i.e. it calls Py_DECREF() on it if
- it is not non-NULL) unless it is returned in result.
-
- @param pyResult the object to convert
- @param format the format string
- @param result where to store it
- @return true if ok, false on error
-*/
-static bool
-PythonConvertResultToC(PyObject *pyResult, const char *format, void *result);
-
// ============================================================================
// implementation
// ============================================================================
-bool
-PythonConvertResultToC(PyObject *pyResult, const char *format, void *result)
-{
- CHECK( result && format && format[0], false,
- _T("PythonConvertResultToC: invalid parameters") );
-
- if ( !pyResult )
- return false;
-
- // try to convert
- if ( !PyArg_Parse(pyResult, (char *)format, result) )
- {
- Py_DECREF(pyResult);
- return false;
- }
-
- // free the object unless we return it as our result
- if ( format[0] != 'O' )
- Py_DECREF(pyResult);
-
- return true;
-}
+// ----------------------------------------------------------------------------
+// calling Python functions
+// ----------------------------------------------------------------------------
int
@@ -155,10 +119,8 @@
}
+// common part of PythonFunction() and PythonStringFunction()
+static
bool
-PythonFunction(const char *func,
- void *obj,
- const char *classname,
- const char *resultfmt,
- void *result)
+FindPythonFunction(const char *func, PyObject **module, PyObject **function)
{
// first check if Python is not disabled
@@ -167,7 +129,7 @@
ERRORMESSAGE(( _("Python support is disabled, please enable it in "
"the \"Preferences\" dialog.") ));
+ return false;
}
- else
- {
+
// next determine which module should we load the function from
String functionName = func;
@@ -187,8 +149,9 @@
else // no explicit module, use the default one
{
- modname = MP_PYTHONMODULE_TO_LOAD_DEFVAL;
+ modname = GetStringDefault(MP_PYTHONMODULE_TO_LOAD);
}
- M_PyObject module(PyImport_ImportModule((char *)modname.c_str()));
+ // load the module containing the function
+ *module = PyImport_ImportModule((char *)modname.c_str());
if ( !module )
@@ -196,29 +159,48 @@
ERRORMESSAGE(( _("Module \"%s\" couldn't be loaded."),
modname.c_str() ));
+ return false;
}
- else
- {
+
// we want to allow modifying the Python code on the fly, so try to
// reload the module here -- this is nice for playing with Python even
// if possibly very slow...
- PyObject *moduleRe = PyImport_ReloadModule(module);
+ PyObject *moduleRe = PyImport_ReloadModule(*module);
if ( moduleRe )
{
- // if reloading failed, fall back to the original module
- module = moduleRe;
+ Py_XDECREF(*module);
+ *module = moduleRe;
}
+ //else: if reloading failed, fall back to the original module
- PyObject *function = PyObject_GetAttrString
- (
- module,
- const_cast<char *>(functionName.c_str())
- );
- if ( !function )
+ *function = PyObject_GetAttrString(*module,
+ const_cast<char *>(functionName.c_str()));
+ if ( !*function )
{
+ Py_XDECREF(*module);
+
ERRORMESSAGE(( _("Function \"%s\" not found in module \"%s\"."),
functionName.c_str(), modname.c_str() ));
+ return false;
}
- else // ok
+
+ return true;
+}
+
+bool
+PythonFunction(const char *func,
+ void *obj,
+ const char *classname,
+ const char *resultfmt,
+ void *result)
+{
+ PyObject *module,
+ *function;
+
+ if ( FindPythonFunction(func, &module, &function) )
{
+ // this ensures we always release them
+ M_PyObject pyModule(module),
+ pyFunc(function);
+
// now build object reference argument:
String ptrCls(classname);
@@ -227,15 +209,83 @@
// and do call the function
- PyObject *rc = PyObject_CallFunction(function, "O", object);
+ M_PyObject rc(PyObject_CallFunction(function, "O", object));
// translate result back to C
- if ( PythonConvertResultToC(rc, resultfmt, result) )
+ if ( PyArg_Parse(rc, const_cast<char *>(resultfmt), result) )
{
// everything ok, skip error messages below
return true;
}
+
+ String err = PythonGetErrorMessage();
+ if ( !err.empty() )
+ {
+ ERRORMESSAGE((_T("%s"), err.c_str()));
}
}
+ ERRORMESSAGE((_("Calling Python function \"%s\" failed."), func));
+
+ return false;
+}
+
+bool
+PythonStringFunction(const String& func,
+ const wxArrayString& arguments,
+ String *value)
+{
+ PyObject *module,
+ *function;
+
+ if ( FindPythonFunction(func, &module, &function) )
+ {
+ // this ensures we always release them
+ M_PyObject pyModule(module),
+ pyFunc(function);
+
+ // do call the function
+ PyObject *rc;
+ switch ( arguments.size() )
+ {
+ case 0:
+ rc = PyObject_CallFunction(function, NULL);
+ break;
+
+ case 1:
+ rc = PyObject_CallFunction(function, "s", arguments[0].c_str());
+ break;
+
+ case 2:
+ rc = PyObject_CallFunction(function, "ss",
+ arguments[0].c_str(),
+ arguments[1].c_str());
+ break;
+
+ case 3:
+ rc = PyObject_CallFunction(function, "sss",
+ arguments[0].c_str(),
+ arguments[1].c_str(),
+ arguments[2].c_str());
+ break;
+
+ default:
+ ERRORMESSAGE((_("Too many arguments to Python function \"%s\"."),
+ func.c_str()));
+ rc = NULL;
+ }
+
+ M_PyObject pyRc(rc);
+
+ // translate result back to C, if we expect to get any result back
+ char *p = NULL;
+ if ( !value || PyArg_Parse(rc, "s", &p) )
+ {
+ if ( value )
+ *value = p;
+
+ // everything ok, skip error messages below
+ return true;
+ }
+
String err = PythonGetErrorMessage();
if ( !err.empty() )
@@ -250,4 +300,8 @@
}
+// ----------------------------------------------------------------------------
+// running Python scripts
+// ----------------------------------------------------------------------------
+
bool
PythonRunScript(const char *filename)
@@ -320,4 +374,8 @@
+// ----------------------------------------------------------------------------
+// helpers
+// ----------------------------------------------------------------------------
+
String PythonGetErrorMessage()
{
-------------------------------------------------------
This SF.Net email is sponsored by: YOU BE THE JUDGE. Be one of 170
Project Admins to receive an Apple iPod Mini FREE for your judgement on
who ports your project to Linux PPC the best. Sponsored by IBM.
Deadline: Sept. 24. Go here: http://sf.net/ppc_contest.php
_______________________________________________
Mahogany-cvsupdates mailing list
[EMAIL PROTECTED]
https://lists.sourceforge.net/lists/listinfo/mahogany-cvsupdates