00001 /*************************************************************************** 00002 *cr 00003 *cr (C) Copyright 1995-2019 The Board of Trustees of the 00004 *cr University of Illinois 00005 *cr All Rights Reserved 00006 *cr 00007 ***************************************************************************/ 00008 00009 /*************************************************************************** 00010 * RCS INFORMATION: 00011 * 00012 * $RCSfile: py_render.C,v $ 00013 * $Author: johns $ $Locker: $ $State: Exp $ 00014 * $Revision: 1.23 $ $Date: 2019年05月30日 05:24:51 $ 00015 * 00016 *************************************************************************** 00017 * DESCRIPTION: 00018 * Python interface to external renderer commands 00019 ***************************************************************************/ 00020 00021 #include "py_commands.h" 00022 #include "VMDApp.h" 00023 00024 static const char listall_doc[] = 00025 "List all supported render methods\n\n" 00026 "Returns:\n" 00027 " (list of str): Supported render methods, suitable for calls to `render()`"; 00028 static PyObject *py_listall(PyObject *self, PyObject *args) { 00029 PyObject *newlist = NULL; 00030 int i; 00031 00032 VMDApp *app; 00033 if (!(app = get_vmdapp())) 00034 return NULL; 00035 00036 if (!(newlist = PyList_New(0))) 00037 goto failure; 00038 00039 // Need a tmp object here because PyList_Append increments refcount 00040 for (i=0; i<app->filerender_num(); i++) { 00041 PyObject *tmp = as_pystring(app->filerender_name(i)); 00042 PyList_Append(newlist, tmp); 00043 Py_XDECREF(tmp); 00044 00045 if (PyErr_Occurred()) 00046 goto failure; 00047 } 00048 return newlist; 00049 00050 // Don't leak new list reference in case of a failure 00051 failure: 00052 Py_XDECREF(newlist); 00053 PyErr_SetString(PyExc_RuntimeError, "Problem listing render methods"); 00054 return NULL; 00055 } 00056 00057 00058 static const char render_doc[] = 00059 "Render the current scene with an external or internal renderer. For some\n" 00060 "rendering engines this entails writing an input file and then invoking an\n" 00061 "external program\n\n" 00062 "Args:\n" 00063 " method (str): Render method. See `render.listall()` for supported values\n" 00064 " filename (str): File name to render to. For external rendering engines,\n" 00065 " filename may be input file to external program"; 00066 static PyObject *py_render(PyObject *self, PyObject *args, PyObject *kwargs) { 00067 const char *kwlist[] = {"method", "filename", NULL}; 00068 char *method, *filename; 00069 00070 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "ss:render.render", 00071 (char**) kwlist, &method, &filename)) 00072 return NULL; 00073 00074 VMDApp *app; 00075 if (!(app = get_vmdapp())) 00076 return NULL; 00077 00078 if (!app->filerender_render(method, filename, NULL)) { 00079 PyErr_Format(PyExc_RuntimeError, "Unable to render to file '%s'", filename); 00080 return NULL; 00081 } 00082 00083 Py_INCREF(Py_None); 00084 return Py_None; 00085 } 00086 00087 00088 static PyMethodDef methods[] = { 00089 {"listall", (PyCFunction)py_listall, METH_NOARGS, listall_doc}, 00090 {"render", (PyCFunction)py_render, METH_VARARGS | METH_KEYWORDS, render_doc}, 00091 {NULL, NULL} 00092 }; 00093 00094 00095 static const char render_moddoc[] = 00096 "Methods to render the current scene using a specified rendering engine"; 00097 00098 00099 #if PY_MAJOR_VERSION >= 3 00100 static struct PyModuleDef renderdef = { 00101 PyModuleDef_HEAD_INIT, 00102 "render", 00103 render_moddoc, 00104 -1, 00105 methods, 00106 }; 00107 #endif 00108 00109 00110 PyObject* initrender(void) { 00111 #if PY_MAJOR_VERSION >= 3 00112 PyObject *m = PyModule_Create(&renderdef); 00113 #else 00114 PyObject *m = Py_InitModule3("render", methods, render_moddoc); 00115 #endif 00116 return m; 00117 } 00118