22171f69321fd459ce7088c9ac599cc53b49f67f
[blender.git] / source / gameengine / VideoTexture / blendVideoTex.cpp
1 /* $Id$
2 -----------------------------------------------------------------------------
3 This source file is part of VideoTexture library
4
5 Copyright (c) 2006 The Zdeno Ash Miklas
6
7 This program is free software; you can redistribute it and/or modify it under
8 the terms of the GNU Lesser General Public License as published by the Free Software
9 Foundation; either version 2 of the License, or (at your option) any later
10 version.
11
12 This program is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14 FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
15
16 You should have received a copy of the GNU Lesser General Public License along with
17 this program; if not, write to the Free Software Foundation, Inc., 59 Temple
18 Place - Suite 330, Boston, MA 02111-1307, USA, or go to
19 http://www.gnu.org/copyleft/lesser.txt.
20 -----------------------------------------------------------------------------
21 */
22
23 #include <PyObjectPlus.h>
24
25 #include <RAS_GLExtensionManager.h>
26
27 #include <RAS_IPolygonMaterial.h>
28
29 //Old API
30 //#include "TexPlayer.h"
31 //#include "TexImage.h"
32 //#include "TexFrameBuff.h"
33
34 //#include "TexPlayerGL.h"
35
36 #include "ImageBase.h"
37 #include "FilterBase.h"
38 #include "Texture.h"
39
40 #include "Exception.h"
41
42
43 // get material id
44 static PyObject * getMaterialID (PyObject *self, PyObject *args)
45 {
46         // parameters - game object with video texture
47         PyObject * obj = NULL;
48         // material name
49         char * matName;
50
51         // get parameters
52         if (!PyArg_ParseTuple(args, "Os:materialID", &obj, &matName))
53                 return NULL;
54         // get material id
55         short matID = getMaterialID(obj, matName);
56         // if material was not found, report errot
57         if (matID < 0)
58         {
59                 PyErr_SetString(PyExc_RuntimeError, "VideoTexture.materialID(ob, string): Object doesn't have material with given name");
60                 return NULL;
61         }
62         // return material ID
63         return Py_BuildValue("h", matID);
64 }
65
66
67 // get last error description
68 static PyObject * getLastError (PyObject *self, PyObject *args)
69 {
70         return PyUnicode_FromString(Exception::m_lastError.c_str());
71 }
72
73 // set log file
74 static PyObject * setLogFile (PyObject *self, PyObject *args)
75 {
76         // get parameters
77         if (!PyArg_ParseTuple(args, "s:setLogFile", &Exception::m_logFile))
78                 return Py_BuildValue("i", -1);
79         // log file was loaded
80         return Py_BuildValue("i", 0);
81 }
82
83
84 // image to numpy array
85 static PyObject * imageToArray (PyObject * self, PyObject *args)
86 {
87         // parameter is Image object
88         PyObject * pyImg;
89         if (!PyArg_ParseTuple(args, "O:imageToArray", &pyImg) || !pyImageTypes.in(pyImg->ob_type))
90         {
91                 // if object is incorect, report error
92                 PyErr_SetString(PyExc_TypeError, "VideoTexture.imageToArray(image): The value must be a image source object");
93                 return NULL;
94         }
95         // get image structure
96         PyImage * img = reinterpret_cast<PyImage*>(pyImg);
97         // create array object
98         unsigned int * imgBuff = img->m_image->getImage();
99         // if image is available, convert it to array
100         if (imgBuff != NULL)
101         // Nasty problem here: the image buffer is an array of integers 
102         // in the processor endian format. The user must take care of that in the script. 
103         // Need to find an elegant solution to this problem 
104         return Py_BuildValue("s#", imgBuff, img->m_image->getBuffSize());
105         // otherwise return None
106         Py_RETURN_NONE;
107 }
108
109
110 // metody modulu
111 static PyMethodDef moduleMethods[] =
112 {
113         {"materialID", getMaterialID, METH_VARARGS, "Gets object's Blender Material ID"},
114         {"getLastError", getLastError, METH_NOARGS, "Gets last error description"},
115         {"setLogFile", setLogFile, METH_VARARGS, "Sets log file name"},
116         {"imageToArray", imageToArray, METH_VARARGS, "get array from image source"},
117         {NULL}  /* Sentinel */
118 };
119
120 #if WITH_FFMPEG
121 extern PyTypeObject VideoFFmpegType;
122 extern PyTypeObject ImageFFmpegType;
123 #endif
124 extern PyTypeObject FilterBlueScreenType;
125 extern PyTypeObject FilterGrayType;
126 extern PyTypeObject FilterColorType;
127 extern PyTypeObject FilterLevelType;
128 extern PyTypeObject FilterNormalType;
129 extern PyTypeObject FilterRGB24Type;
130 extern PyTypeObject FilterRGBA32Type;
131 extern PyTypeObject FilterBGR24Type;
132 extern PyTypeObject ImageBuffType;
133 extern PyTypeObject ImageMixType;
134 extern PyTypeObject ImageRenderType;
135 extern PyTypeObject ImageMirrorType;
136 extern PyTypeObject ImageViewportType;
137 extern PyTypeObject ImageViewportType;
138
139
140 static void registerAllTypes(void)
141 {
142 #if WITH_FFMPEG
143         pyImageTypes.add(&VideoFFmpegType, "VideoFFmpeg");
144         pyImageTypes.add(&ImageFFmpegType, "ImageFFmpeg");
145 #endif
146         pyImageTypes.add(&ImageBuffType, "ImageBuff");
147         pyImageTypes.add(&ImageMixType, "ImageMix");
148         pyImageTypes.add(&ImageRenderType, "ImageRender");
149         pyImageTypes.add(&ImageMirrorType, "ImageMirror");
150         pyImageTypes.add(&ImageViewportType, "ImageViewport");
151
152         pyFilterTypes.add(&FilterBlueScreenType, "FilterBlueScreen");
153         pyFilterTypes.add(&FilterGrayType, "FilterGray");
154         pyFilterTypes.add(&FilterColorType, "FilterColor");
155         pyFilterTypes.add(&FilterLevelType, "FilterLevel");
156         pyFilterTypes.add(&FilterNormalType, "FilterNormal");
157         pyFilterTypes.add(&FilterRGB24Type, "FilterRGB24");
158         pyFilterTypes.add(&FilterRGBA32Type, "FilterRGBA32");
159         pyFilterTypes.add(&FilterBGR24Type, "FilterBGR24");
160 }
161
162
163 #if (PY_VERSION_HEX >= 0x03000000)
164 static struct PyModuleDef VideoTexture_module_def = {
165         {}, /* m_base */
166         "VideoTexture",  /* m_name */
167         "Module that allows to play video files on textures in GameBlender.",  /* m_doc */
168         0,  /* m_size */
169         moduleMethods,  /* m_methods */
170         0,  /* m_reload */
171         0,  /* m_traverse */
172         0,  /* m_clear */
173         0,  /* m_free */
174 };
175 #endif
176
177 PyObject* initVideoTexture(void) 
178 {
179         PyObject * m;
180         
181         // initialize GL extensions
182         //bgl::InitExtensions(0);
183
184         // prepare classes
185         registerAllTypes();
186     registerAllExceptions();
187
188         if (!pyImageTypes.ready()) 
189                 return NULL;
190         if (!pyFilterTypes.ready()) 
191                 return NULL;
192         if (PyType_Ready(&TextureType) < 0) 
193                 return NULL;
194
195         /* Use existing module where possible
196          * be careful not to init any runtime vars after this */
197         m = PyImport_ImportModule( "VideoTexture" );
198         if(m) {
199                 Py_DECREF(m);
200                 return m;
201         }
202         else {
203                 PyErr_Clear();
204         
205 #if (PY_VERSION_HEX >= 0x03000000)
206                 m = PyModule_Create(&VideoTexture_module_def);
207                 PyDict_SetItemString(PySys_GetObject("modules"), VideoTexture_module_def.m_name, m);
208 #else
209                 m = Py_InitModule4("VideoTexture", moduleMethods,
210                         "Module that allows to play video files on textures in GameBlender.",
211                         (PyObject*)NULL,PYTHON_API_VERSION);
212 #endif
213         }
214         
215         if (m == NULL) 
216                 return NULL;
217
218         // initialize classes
219         pyImageTypes.reg(m);
220         pyFilterTypes.reg(m);
221
222         Py_INCREF(&TextureType);
223         PyModule_AddObject(m, (char*)"Texture", (PyObject*)&TextureType);
224         
225         // init last error description
226         Exception::m_lastError[0] = '\0';
227         
228         return m;
229 }
230
231 // registration to Image types, put here because of silly linker bug