📄 00000005.htm
字号:
PyObject *args;
<BR>{
<BR>
<BR> if (!PyArg_ParseTuple(args, ""))
<BR> return NULL;
<BR> Py_INCREF(Py_None);
<BR> return Py_None;
<BR>}
<BR>
<BR>static char tortoise_turn__doc__[] =
<BR>""
<BR>;
<BR>
<BR>static PyObject *
<BR>tortoise_turn(self, args)
<BR> PyObject *self; /* Not used */
<BR> PyObject *args;
<BR>{
<BR>
<BR> if (!PyArg_ParseTuple(args, ""))
<BR> return NULL;
<BR> Py_INCREF(Py_None);
<BR> return Py_None;
<BR>}
<BR>
<BR>static char tortoise_move__doc__[] =
<BR>""
<BR>;
<BR>
<BR>static PyObject *
<BR>tortoise_move(self, args)
<BR> PyObject *self; /* Not used */
<BR> PyObject *args;
<BR>{
<BR>
<BR> if (!PyArg_ParseTuple(args, ""))
<BR> return NULL;
<BR> Py_INCREF(Py_None);
<BR> return Py_None;
<BR>}
<BR>
<BR>/* List of methods defined in the module */
<BR>/* 模块中所有方法的列表,这是一个扩展模块的关键数据结构
<BR> 例如当你在python里调用tortoise.pendown()方法时,
<BR> python解释器会来查这个表,找到对应的函数tortoise_pendown()
<BR>*/
<BR>
<BR>static struct PyMethodDef tortoise_methods[] = {
<BR> {"reset", (PyCFunction)tortoise_reset, METH_VARARGS, tortoise_reset__doc__},
<BR> <BR> {"pendown", (PyCFunction)tortoise_pendown, METH_VARARGS, tortoise_pendown__do <BR>c__},
<BR> {"penup", (PyCFunction)tortoise_penup, METH_VARARGS, tortoise_penup__doc__},
<BR> <BR> {"turn", (PyCFunction)tortoise_turn, METH_VARARGS, tortoise_turn__doc__},
<BR> {"move", (PyCFunction)tortoise_move, METH_VARARGS, tortoise_move__doc__},
<BR>
<BR> {NULL, (PyCFunction)NULL, 0, NULL} /* sentinel */
<BR>};
<BR>
<BR>
<BR>/* Initialization function for the module (*must* be called inittortoise) */
<BR>
<BR>static char tortoise_module_documentation[] =
<BR>""
<BR>;
<BR>
<BR>/* 每个模块都要有这样一个初始化函数,
<BR> 在import这个模块的时候python会自动执行这个函数.
<BR> 函数命名必须是 init<modulename>
<BR>*/
<BR>void
<BR>inittortoise()
<BR>{
<BR> PyObject *m, *d;
<BR>
<BR> /* Create the module and add the functions */
<BR> /* 增加tortoise这个模块 */
<BR> m = Py_InitModule4("tortoise", tortoise_methods,
<BR> tortoise_module_documentation,
<BR> (PyObject*)NULL,PYTHON_API_VERSION);
<BR>
<BR> /* Add some symbolic constants to the module */
<BR> /* 得到此模块的名字空间 */
<BR> d = PyModule_GetDict(m);
<BR> /* 添加一个错误对象的名字 */
<BR> ErrorObject = PyString_FromString("tortoise.error");
<BR> PyDict_SetItemString(d, "error", ErrorObject);
<BR>
<BR> /* XXXX Add constants here */
<BR> /* 在这里可以加入模块的常量 */
<BR>
<BR> /* Check for errors */
<BR> if (PyErr_Occurred())
<BR> Py_FatalError("can't initialize module tortoise");
<BR>}
<BR>
<BR>/*------------------------------------------------------------------------*/
<BR>
<BR> 这个文件其实就可以编译了,只不过没有任何功能罢了,呵呵.我们去Python源程序的 <BR>Demo/extend目录,把make_shared拷贝一份叫my_make_shared,然后把my_make_shared里面 <BR>的xxmodule都改成我们的tortoisemodule.如果上面那个tortoisemodule.c不在 <BR>Tools/modulator目录下,还需要修改第10行的路径指向tortoisemodule.c的目录.最后,再 <BR>加上编译X程序需要的包含库.呵呵,说起来挺罗嗦的,看看我的my_make_shared文件吧:
<BR>
<BR>
<BR>#! /bin/sh
<BR>
<BR># This script tests and demonstrates the mechanism for building a
<BR># shared library for an additional extension module using the
<BR># generic Makefile.pre.in from the Misc directory.
<BR>
<BR>./make_clean
<BR>
<BR>cp ../../Misc/Makefile.pre.in .
<BR>cp /home/kafa/guile/tortoisemodule.c .
<BR>echo '*shared*' >Setup.in
<BR>echo tortoise tortoisemodule.c -I/usr/X11R6/include -lX11 -L/usr/X11R6/lib <BR>-lm >>Setup.in
<BR>
<BR>make -f Makefile.pre.in boot
<BR>make Makefile
<BR>make
<BR>
<BR>######################################################################
<BR>
<BR> 然后我们运行my_make_shared就可以在此目录下生成一个叫tortoisemodule.so的动态联 <BR>接库文件,这就是我们需要的python扩展模块.现在我们就可以在此目录下试试这个扩展模 <BR>块了,运行命令'python'起动python的交互式解释器,然后执行'import tortoise'导入 <BR>tortoise模块.如果没有错误发生的话,现在你可以用'dir(tortoise)'看看tortoise模块 <BR>里是不是包含了我们要的那些函数,也可以用'tortoise.pendown()'命令调用一下这些方 <BR>法看看有什么结果.
<BR>
<BR> OK,现在tortoise的基本程序和扩展模块的骨架都已经有了,让我们把它们合在一起,就在 <BR>那个tortoisemodule.c上面改吧,先把tortoise1.c里的头文件和定义的宏copy进来,然后 <BR>把main()函数里面初始化X和工作窗口的代码放到一个函数里,就叫init_workspace()吧, <BR>然后就是真正有意义的工作--把模块函数加入真正的代码实现我们需要的功能,就以 <BR>tortoise_turn()为例:
<BR>
<BR>static PyObject *
<BR>tortoise_turn(self, args)
<BR> PyObject *self; /* Not used */
<BR> PyObject *args;
<BR>{
<BR> /* 定义一个整型变量用来放真正传进来的degrees参数 */
<BR> int degrees;
<BR>
<BR> /* 从python对象里提取出一个整型参数付给degrees
<BR> PyArg_ParseTuple()函数里的"i"表示int类型 */
<BR> if (!PyArg_ParseTuple(args, "i", &degrees))
<BR> return NULL;
<BR>
<BR> /* 真正的功能代码 */
<BR> currentDirection += (double)degrees;
<BR>
<BR> /* 没有错误发生,正常返回 */
<BR> Py_INCREF(Py_None);
<BR> return Py_None;
<BR>}
<BR>
<BR> 很简单吧?呵呵,依样画葫芦修改其它几个函数,这个扩展模块就完成了.我的改过的 <BR>tortoisemodule.c文件内容如下:
<BR>
<BR>/* ------------------------------------------------------- */
<BR>/* tortoisemodule.c */
<BR>
<BR>#include <unistd.h>
<BR>#include <math.h>
<BR>#include <X11/Xlib.h>
<BR>
<BR>#define WINDOW_SIZE 500
<BR>#define DEGREES_TO_RADIANS (3.1415926535897932384626433832795029L/180.0)
<BR>
<BR>Display *theDisplay;
<BR>Window theWindow;
<BR>Screen *theScreen;
<BR>GC theGC;
<BR>double currentX;
<BR>double currentY;
<BR>double currentDirection;
<BR>int penDown;
<BR>
<BR>#include "Python.h"
<BR>static PyObject *ErrorObject;
<BR>
<BR>/* ----------------------------------------------------- */
<BR>static void
<BR>init_workspace(void)
<BR>{
<BR> theDisplay = XOpenDisplay(NULL);
<BR> XSynchronize(theDisplay, True);
<BR> theScreen = DefaultScreenOfDisplay(theDisplay);
<BR> theWindow = XCreateSimpleWindow(theDisplay, RootWindowOfScreen(theScreen), <BR>
<BR> 0, 0,
<BR> WINDOW_SIZE, WINDOW_SIZE, 0,
<BR> BlackPixelOfScreen(theScreen),
<BR> WhitePixelOfScreen(theScreen));
<BR> theGC = XCreateGC(theDisplay, theWindow, 0L, NULL);
<BR> XSetForeground(theDisplay, theGC, BlackPixelOfScreen(theScreen));
<BR> XMapWindow(theDisplay,theWindow);
<BR>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -