Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members   File Members   Related Pages  

py_selection.C

Go to the documentation of this file.
00001 /***************************************************************************
00002  *cr
00003  *cr            (C) Copyright 1995-2016 The Board of Trustees of the
00004  *cr                        University of Illinois
00005  *cr                         All Rights Reserved
00006  *cr
00007  ***************************************************************************/
00008 /***************************************************************************
00009  * RCS INFORMATION:
00010  *
00011  *      $RCSfile: py_selection.C,v $
00012  *      $Author: johns $        $Locker:  $             $State: Exp $
00013  *      $Revision: 1.2 $      $Date: 2019/06/05 06:17:24 $
00014  *
00015  ***************************************************************************
00016  * DESCRIPTION:
00017  *   New Python atom selection interface
00018  ***************************************************************************/
00019 
00020 #include "py_commands.h"
00021 #include "AtomSel.h"
00022 #include "VMDApp.h"
00023 #include "MoleculeList.h"
00024 #include "SymbolTable.h"
00025 #include "Measure.h"
00026 #include "SpatialSearch.h"
00027 
00028 static const char getmacro_doc[] =
00029 "Gets the atom selection string corresponding to a macro\n\n"
00030 "Args:\n"
00031 "    name (str): Macro name\n"
00032 "Returns:\n"
00033 "    (str): Atom selection string that macro expands to";
00034 static PyObject *py_getmacro(PyObject *self, PyObject *args, PyObject *kwargs) {
00035   const char *kwlist[] = {"name", NULL};
00036   const char *s;
00037   char *name;
00038 
00039   if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s:selection.get_macro",
00040                                    (char**) kwlist, &name))
00041     return NULL;
00042 
00043   VMDApp *app;
00044   if (!(app = get_vmdapp()))
00045     return NULL;
00046 
00047   if (!(s = app->atomSelParser->get_custom_singleword(name))) {
00048     PyErr_Format(PyExc_ValueError, "No such macro '%s'", name);
00049     return NULL;
00050   }
00051 
00052   return as_pystring(s);
00053 }
00054 
00055 
00056 static const char allmacro_doc[] =
00057 "Get all defined macros\n\n"
00058 "Returns:\n"
00059 "    (list of str): All defined macro names";
00060 static PyObject *py_allmacros(PyObject *self, PyObject *args) {
00061   PyObject *result = NULL;
00062   SymbolTable *table;
00063   const char *s;
00064   int i;
00065 
00066   VMDApp *app;
00067   if (!(app = get_vmdapp()))
00068     return NULL;
00069 
00070   table = app->atomSelParser;
00071 
00072   if (!(result = PyList_New(0)))
00073     goto failure;
00074 
00075   for (i = 0; i < table->num_custom_singleword(); i++) {
00076     s = table->custom_singleword_name(i);
00077 
00078     // Handle PyList_Append not stealing a reference
00079     if (s && strlen(s)) {
00080       PyObject *tmp = as_pystring(s);
00081       PyList_Append(result, tmp);
00082       Py_XDECREF(tmp);
00083     }
00084 
00085     if (PyErr_Occurred())
00086       goto failure;
00087   }
00088 
00089   return result;
00090 
00091 failure:
00092   Py_XDECREF(result);
00093   PyErr_SetString(PyExc_RuntimeError, "Problem listing macro names");
00094   return NULL;
00095 }
00096 
00097 
00098 static const char addmacro_doc[] =
00099 "Create a new atom selection macro. A macro is a word or words that expand\n"
00100 "to be a much larger selection string, for example 'noh' is a built-in macro\n"
00101 "that expands to 'not hydrogen'\n\n"
00102 "Args:\n"
00103 "    name (str): Macro name\n"
00104 "    selection (str): Atom selection that macro will expand to";
00105 static PyObject *py_addmacro(PyObject *self, PyObject *args, PyObject *kwargs) {
00106   const char *kwlist[] = {"name", "selection", NULL};
00107   char *name, *selection;
00108 
00109   if (!PyArg_ParseTupleAndKeywords(args, kwargs, "ss:selection.add_macro",
00110                                    (char**) kwlist, &name, &selection))
00111     return NULL;
00112 
00113   VMDApp *app;
00114   if (!(app = get_vmdapp()))
00115     return NULL;
00116 
00117   if (!app->atomSelParser->add_custom_singleword(name, selection)) {
00118     PyErr_Format(PyExc_ValueError, "Unable to create macro '%s'", name);
00119     return NULL;
00120   }
00121 
00122   Py_INCREF(Py_None);
00123   return Py_None;
00124 }
00125 
00126 
00127 static const char delmacro_doc[] =
00128 "Delete an atom selection macro, by name\n\n"
00129 "Args:\n"
00130 "    name (str): Macro name to delete";
00131 static PyObject *py_delmacro(PyObject *self, PyObject *args, PyObject *kwargs) {
00132   const char *kwlist[] = {"name", NULL};
00133   char *name;
00134 
00135   if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s:selection.del_macro",
00136                                    (char**) kwlist, &name))
00137     return NULL;
00138 
00139   VMDApp *app;
00140   if (!(app = get_vmdapp()))
00141     return NULL;
00142 
00143   if (!app->atomSelParser->remove_custom_singleword(name)) {
00144     PyErr_Format(PyExc_ValueError, "Unable to remove macro '%s'", name);
00145     return NULL;
00146   }
00147 
00148   Py_INCREF(Py_None);
00149   return Py_None;
00150 }
00151 
00152 
00153 #define SYMBOL_TABLE_FUNC(funcname, elemtype) \
00154 static PyObject *funcname(PyObject *self) { \
00155   VMDApp *app = get_vmdapp(); \
00156   if (!app) return NULL; \
00157   PyObject *result = PyList_New(0); \
00158   if (!result) return NULL; \
00159   SymbolTable *table = app->atomSelParser; \
00160   int i, n = table->fctns.num(); \
00161   for (i=0; i<n; i++) \
00162     if (table->fctns.data(i)->is_a == elemtype && \
00163         strlen(table->fctns.name(i))) { \
00164       PyObject *tmp = as_pystring(table->fctns.name(i)); \
00165       PyList_Append(result, tmp); \
00166       Py_XDECREF(tmp); \
00167   } \
00168   return result; \
00169 }
00170 
00171 SYMBOL_TABLE_FUNC(keywords, SymbolTableElement::KEYWORD)
00172 SYMBOL_TABLE_FUNC(booleans, SymbolTableElement::SINGLEWORD)
00173 SYMBOL_TABLE_FUNC(functions, SymbolTableElement::FUNCTION)
00174 SYMBOL_TABLE_FUNC(stringfunctions, SymbolTableElement::STRINGFCTN)
00175 
00176 #undef SYMBOL_TABLE_FUNC
00177 
00178 
00179 /* List of functions exported by this module */
00180 static PyMethodDef selection_methods[] = {
00181   {"add_macro", (PyCFunction)py_addmacro, METH_VARARGS | METH_KEYWORDS, addmacro_doc},
00182   {"get_macro", (PyCFunction)py_getmacro, METH_VARARGS | METH_KEYWORDS, getmacro_doc},
00183   {"all_macros", (PyCFunction)py_allmacros, METH_NOARGS, allmacro_doc},
00184   {"del_macro", (PyCFunction)py_delmacro, METH_VARARGS | METH_KEYWORDS, delmacro_doc},
00185   {"keywords", (PyCFunction)keywords, METH_NOARGS,
00186     "keywords() -> List of available atom selection keywords."},
00187   {"booleans", (PyCFunction)booleans, METH_NOARGS,
00188     "booleans() -> List of available atom selection boolean tokens."},
00189   {"functions", (PyCFunction)functions, METH_NOARGS,
00190     "functions() -> List of available atom selection functions."},
00191   {"stringfunctions", (PyCFunction)stringfunctions, METH_NOARGS,
00192     "stringfunctions() -> List of available atom selection string functions."},
00193   { NULL, NULL }
00194 };
00195 
00196 
00197 static const char module_doc[] =
00198 "Methods for creating, modifying, or deleting macros for atom selections.";
00199 
00200 
00201 #if PY_MAJOR_VERSION >= 3
00202 static struct PyModuleDef selectiondef = {
00203     PyModuleDef_HEAD_INIT,
00204     "selection",
00205     module_doc,
00206     -1,
00207     selection_methods,
00208 };
00209 
00210 #endif
00211 
00212 
00213 PyObject* initselection() {
00214 
00215 #if PY_MAJOR_VERSION >= 3
00216   PyObject *m = PyModule_Create(&selectiondef);
00217 #else
00218   PyObject *m = Py_InitModule3("selection", selection_methods, module_doc);
00219 #endif
00220 
00221   Py_INCREF((PyObject *)&Atomsel_Type);
00222   if (PyModule_AddObject(m, "selection", (PyObject *)&Atomsel_Type))
00223     return NULL;
00224   return m;
00225 }
00226 

Generated on Thu Mar 28 02:44:04 2024 for VMD (current) by doxygen1.2.14 written by Dimitri van Heesch, © 1997-2002