changed: moved url and isFolder arguments back to XBMC_setDirectoryEntry
[xbmc:xbmc-antiquated.git] / xbmc / lib / libPython / xbmcmodule / listitem.cpp
1 #include "stdafx.h"
2 #include "../python/python.h"
3 #include "listitem.h"
4 #include "pyutil.h"
5
6 #pragma code_seg("PY_TEXT")
7 #pragma data_seg("PY_DATA")
8 #pragma bss_seg("PY_BSS")
9 #pragma const_seg("PY_RDATA")
10
11 #ifdef __cplusplus
12 extern "C" {
13 #endif
14
15 namespace PYXBMC
16 {
17   PyObject* ListItem_New(PyTypeObject *type, PyObject *args, PyObject *kwds)
18   {
19     ListItem *self;
20     static char *keywords[] = { "label", "label2",
21       "iconImage", "thumbnailImage", NULL };
22
23     PyObject* label = NULL;
24     PyObject* label2 = NULL;
25     char* cIconImage = NULL;
26     char* cThumbnailImage = NULL;
27
28     // allocate new object
29     self = (ListItem*)type->tp_alloc(type, 0);
30     if (!self) return NULL;
31       self->item = NULL;
32
33     // parse user input
34     if (!PyArg_ParseTupleAndKeywords(
35       args, kwds,
36       "|OOss", keywords,
37       &label, &label2,
38       &cIconImage, &cThumbnailImage))
39     {
40       Py_DECREF( self );
41       return NULL;
42     }
43
44     // create CFileItem
45     self->item = new CFileItem();
46     if (!self->item)
47     {
48       Py_DECREF( self );
49       return NULL;
50     }
51     CStdString utf8String;
52     if (label && PyGetUnicodeString(utf8String, label, 1))
53     {
54       self->item->SetLabel( utf8String );
55     }
56     if (label2 && PyGetUnicodeString(utf8String, label2, 1))
57     {
58       self->item->SetLabel2( utf8String );
59     }
60     if (cIconImage)
61     {
62       self->item->SetIconImage( cIconImage );
63     }
64     if (cThumbnailImage)
65     {
66       self->item->SetThumbnailImage( cThumbnailImage );
67     }
68     return (PyObject*)self;
69   }
70
71   /*
72    * allocate a new listitem. Used for c++ and not the python user
73    * returns a new reference
74    */
75   ListItem* ListItem_FromString(string strLabel)
76   {
77     ListItem* self = (ListItem*)ListItem_Type.tp_alloc(&ListItem_Type, 0);
78     if (!self) return NULL;
79
80     self->item = new CFileItem(strLabel);
81     if (!self->item)
82     {
83       Py_DECREF( self );
84       return NULL;
85     }
86
87     return self;
88   }
89
90   void ListItem_Dealloc(ListItem* self)
91   {
92     if (self->item) delete self->item;
93     self->ob_type->tp_free((PyObject*)self);
94   }
95
96   PyDoc_STRVAR(getLabel__doc__,
97     "getLabel() -- Returns the listitem label.\n"
98     "\n"
99     "example:\n"
100     "  - label = self.list.getSelectedItem().getLabel()\n");
101
102   PyObject* ListItem_GetLabel(ListItem *self, PyObject *args)
103   {
104     if (!self->item) return NULL;
105
106     PyGUILock();
107     const char *cLabel =  self->item->GetLabel().c_str();
108     PyGUIUnlock();
109
110     return Py_BuildValue("s", cLabel);
111   }
112
113   PyDoc_STRVAR(getLabel2__doc__,
114     "getLabel2() -- Returns the listitem's second label.\n"
115     "\n"
116     "example:\n"
117     "  - label2 = self.list.getSelectedItem().getLabel2()\n");
118
119   PyObject* ListItem_GetLabel2(ListItem *self, PyObject *args)
120   {
121     if (!self->item) return NULL;
122
123     PyGUILock();
124     const char *cLabel = self->item->GetLabel2().c_str();
125     PyGUIUnlock();
126
127     return Py_BuildValue("s", cLabel);
128   }
129
130   PyDoc_STRVAR(setLabel__doc__,
131     "setLabel(label) -- Sets the listitem's label.\n"
132     "\n"
133     "label          : string or unicode - text string.\n"
134     "\n"
135     "example:\n"
136     "  - self.list.getSelectedItem().setLabel('Casino Royale')\n");
137
138   PyObject* ListItem_SetLabel(ListItem *self, PyObject *args)
139   {
140     PyObject* unicodeLine = NULL;
141     if (!self->item) return NULL;
142
143     if (!PyArg_ParseTuple(args, "O", &unicodeLine)) return NULL;
144
145     string utf8Line;
146     if (unicodeLine && !PyGetUnicodeString(utf8Line, unicodeLine, 1))
147       return NULL;
148     // set label
149     PyGUILock();
150     self->item->SetLabel(utf8Line);
151     PyGUIUnlock();
152
153     Py_INCREF(Py_None);
154     return Py_None;
155   }
156
157   PyDoc_STRVAR(setLabel2__doc__,
158     "setLabel2(label2) -- Sets the listitem's second label.\n"
159     "\n"
160     "label2         : string or unicode - text string.\n"
161     "\n"
162     "example:\n"
163     "  - self.list.getSelectedItem().setLabel2('[pg-13]')\n");
164   
165   PyObject* ListItem_SetLabel2(ListItem *self, PyObject *args)
166   {
167     PyObject* unicodeLine = NULL;
168     if (!self->item) return NULL;
169
170     if (!PyArg_ParseTuple(args, "O", &unicodeLine)) return NULL;
171
172     string utf8Line;
173     if (unicodeLine && !PyGetUnicodeString(utf8Line, unicodeLine, 1))
174       return NULL;
175     // set label
176     PyGUILock();
177     self->item->SetLabel2(utf8Line);
178     PyGUIUnlock();
179
180     Py_INCREF(Py_None);
181     return Py_None;
182   }
183
184   PyDoc_STRVAR(setIconImage__doc__,
185     "setIconImage(icon) -- Sets the listitem's icon image.\n"
186     "\n"
187     "icon            : string - image filename.\n"
188     "\n"
189     "example:\n"
190     "  - self.list.getSelectedItem().setIconImage('emailread.png')\n");
191
192   PyObject* ListItem_SetIconImage(ListItem *self, PyObject *args)
193   {
194     char *cLine = NULL;
195     if (!self->item) return NULL;
196
197     if (!PyArg_ParseTuple(args, "s", &cLine)) return NULL;
198
199     // set label
200     PyGUILock();
201     self->item->SetIconImage(cLine ? cLine : "");
202     PyGUIUnlock();
203
204     Py_INCREF(Py_None);
205     return Py_None;
206   }
207
208   PyDoc_STRVAR(setThumbnailImage__doc__,
209     "setThumbnailImage(thumb) -- Sets the listitem's thumbnail image.\n"
210     "\n"
211     "thumb           : string - image filename.\n"
212     "\n"
213     "example:\n"
214     "  - self.list.getSelectedItem().setThumbnailImage('emailread.png')\n");
215
216   PyObject* ListItem_SetThumbnailImage(ListItem *self, PyObject *args)
217   {
218     char *cLine = NULL;
219     if (!self->item) return NULL;
220
221     if (!PyArg_ParseTuple(args, "s", &cLine)) return NULL;
222
223     // set label
224     PyGUILock();
225     self->item->SetThumbnailImage(cLine ? cLine : "");
226     PyGUIUnlock();
227
228     Py_INCREF(Py_None);
229     return Py_None;
230   }
231
232   PyDoc_STRVAR(select__doc__,
233     "select(selected) -- Sets the listitem's selected status.\n"
234     "\n"
235     "selected        : bool - True=selected/False=not selected\n"
236     "\n"
237     "example:\n"
238     "  - self.list.getSelectedItem().select(True)\n");
239
240   PyObject* ListItem_Select(ListItem *self, PyObject *args)
241   {
242     if (!self->item) return NULL;
243
244     bool bOnOff = false;
245     if (!PyArg_ParseTuple(args, "b", &bOnOff)) return NULL;
246
247     PyGUILock();
248     self->item->Select(bOnOff);
249     PyGUIUnlock();
250
251     Py_INCREF(Py_None);
252     return Py_None;
253   }
254   
255   PyDoc_STRVAR(isSelected__doc__,
256     "isSelected() -- Returns the listitem's selected status.\n"
257     "\n"
258     "example:\n"
259     "  - is = self.list.getSelectedItem().isSelected()\n");
260
261   PyObject* ListItem_IsSelected(ListItem *self, PyObject *args)
262   {
263     if (!self->item) return NULL;
264
265     PyGUILock();
266     bool bOnOff = self->item->IsSelected();
267     PyGUIUnlock();
268
269     return Py_BuildValue("b", bOnOff);
270   }
271
272   PyDoc_STRVAR(setInfo__doc__,
273     "setInfo(type, infoLabels) -- Sets the listitem's infoLabels.\n"
274     "\n"
275     "type           : string - type of media(video/music/pictures).\n"
276     "infoLabels     : dictionary - pairs of { label: value }.\n"
277     "\n"
278     "*Note, You can use the above as keywords for arguments and skip certain optional arguments.\n"
279     "       Once you use a keyword, all following arguments require the keyword.\n"
280     "\n"
281     "example:\n"
282     "  - self.list.getSelectedItem().setInfo('video', { 'Genre': 'Comedy' })\n");
283
284   PyObject* ListItem_SetInfo(ListItem *self, PyObject *args, PyObject *kwds)
285   {
286     static char *keywords[] = { "type", "infoLabels", NULL };
287     char *cType = NULL;
288     PyObject *pInfoLabels = NULL;
289     if (!PyArg_ParseTupleAndKeywords(
290       args,
291       kwds,
292       "sO",
293       keywords,
294       &cType,
295       &pInfoLabels))
296     {
297       return NULL;
298     }
299     if (!PyObject_TypeCheck(pInfoLabels, &PyDict_Type))
300     {
301       PyErr_SetString(PyExc_TypeError, "infoLabels object should be of type Dict");
302       return NULL;
303     }
304     CLog::Log(LOGDEBUG, __FUNCTION__" - InfoLabel Dictionary has %i items", PyDict_Size(pInfoLabels));
305     if (PyDict_Size(pInfoLabels) == 0)
306     {
307       PyErr_SetString(PyExc_ValueError, "Empty InfoLabel dictionary");
308       return NULL;
309     }
310
311     PyObject *key, *value;
312     int pos = 0;
313
314     PyGUILock();
315     while (PyDict_Next(pInfoLabels, &pos, &key, &value)) {
316       //CLog::Log(LOGDEBUG, __FUNCTION__" - Tag Dictionary: pos: %i  key: %s  value: %s", pos, PyString_AsString(key), PyString_AsString(value));
317       if (strcmpi(cType, "video") == 0)
318       {
319         // TODO: add the rest of the infolabels
320         //CLog::Log(LOGDEBUG, __FUNCTION__" - Type: %s - Tag: %s - Value: %s ", cType, PyString_AsString(key), PyString_AsString(value));
321         if (strcmpi(PyString_AsString(key), "genre") == 0)
322           self->item->GetVideoInfoTag()->m_strGenre = PyString_AsString(value);
323         else if (strcmpi(PyString_AsString(key), "year") == 0)
324           self->item->GetVideoInfoTag()->m_iYear = PyInt_AsLong(value);
325         else if (strcmpi(PyString_AsString(key), "director") == 0)
326           self->item->GetVideoInfoTag()->m_strDirector = PyString_AsString(value);
327         else if (strcmpi(PyString_AsString(key), "MPAARating") == 0)
328           self->item->GetVideoInfoTag()->m_strMPAARating = PyString_AsString(value);
329         else if (strcmpi(PyString_AsString(key), "plot") == 0)
330           self->item->GetVideoInfoTag()->m_strPlot = PyString_AsString(value);
331         else if (strcmpi(PyString_AsString(key), "plotoutline") == 0)
332           self->item->GetVideoInfoTag()->m_strPlotOutline = PyString_AsString(value);
333         else if (strcmpi(PyString_AsString(key), "runtime") == 0)
334           self->item->GetVideoInfoTag()->m_strRuntime = PyString_AsString(value);
335         else if (strcmpi(PyString_AsString(key), "title") == 0)
336           self->item->GetVideoInfoTag()->m_strTitle = PyString_AsString(value);
337         else if (strcmpi(PyString_AsString(key), "rating") == 0)
338           self->item->GetVideoInfoTag()->m_fRating = (float)PyFloat_AsDouble(value);
339         // TODO: Add a python list of cast members to m_cast
340         //else if (strcmpi(PyString_AsString(key), "cast") == 0)
341         //  self->item->GetVideoInfoTag()->m_cast = PyString_AsString(value);//
342       }
343       else if (strcmpi(cType, "music") == 0)
344       {
345         // TODO: add the rest of the infolabels
346         //CLog::Log(LOGDEBUG, __FUNCTION__" - Type: %s - Tag: %s - Value: %s ", cType, PyString_AsString(key), PyString_AsString(value));
347         if (strcmpi(PyString_AsString(key), "genre") == 0)
348           self->item->GetMusicInfoTag()->SetGenre(PyString_AsString(value));
349         else if (strcmpi(PyString_AsString(key), "album") == 0)
350           self->item->GetMusicInfoTag()->SetAlbum(PyString_AsString(value));
351         else if (strcmpi(PyString_AsString(key), "artist") == 0)
352           self->item->GetMusicInfoTag()->SetArtist(PyString_AsString(value));
353         else if (strcmpi(PyString_AsString(key), "tracknumber") == 0)
354           self->item->GetMusicInfoTag()->SetTrackNumber(PyInt_AsLong(value));
355       }
356       else if (strcmpi(cType, "pictures") == 0)
357       {
358         // TODO: Figure out how to set picture tags
359         //CLog::Log(LOGDEBUG, __FUNCTION__" - Type: %s - Tag: %s - Value: %s ", cType, PyString_AsString(key), PyString_AsString(value));
360         //if (strcmpi(PyString_AsString(key), "picturedatetime") == 0)
361         //  self->item->GetPictureInfoTag()->m_exifInfo.DateTime = PyString_AsString(value);
362         //else if (strcmpi(PyString_AsString(key), "pictureresolution") == 0)
363         //{
364           // TODO: Grab a tuple and set width/height
365           //value.Format("%d x %d", m_exifInfo.Width, m_exifInfo.Height);
366           //self->item->GetPictureInfoTag()->m_exifInfo.Width = PyInt_AsLong(value);
367           //self->item->GetPictureInfoTag()->m_exifInfo.Height = PyInt_AsLong(value);
368         //}
369         if (strcmpi(PyString_AsString(key), "picturepath") == 0)
370           self->item->m_strPath = PyString_AsString(value);
371       }
372     }
373     PyGUIUnlock();
374
375     Py_INCREF(Py_None);
376     return Py_None;
377   }
378   PyMethodDef ListItem_methods[] = {
379     {"getLabel" , (PyCFunction)ListItem_GetLabel, METH_VARARGS, getLabel__doc__},
380     {"setLabel" , (PyCFunction)ListItem_SetLabel, METH_VARARGS, setLabel__doc__},
381     {"getLabel2", (PyCFunction)ListItem_GetLabel2, METH_VARARGS, getLabel2__doc__},
382     {"setLabel2", (PyCFunction)ListItem_SetLabel2, METH_VARARGS, setLabel2__doc__},
383     {"setIconImage", (PyCFunction)ListItem_SetIconImage, METH_VARARGS, setIconImage__doc__},
384     {"setThumbnailImage", (PyCFunction)ListItem_SetThumbnailImage, METH_VARARGS, setThumbnailImage__doc__},
385     {"select", (PyCFunction)ListItem_Select, METH_VARARGS, select__doc__},
386     {"isSelected", (PyCFunction)ListItem_IsSelected, METH_VARARGS, isSelected__doc__},
387     {"setInfo", (PyCFunction)ListItem_SetInfo, METH_KEYWORDS, setInfo__doc__},
388     {NULL, NULL, 0, NULL}
389   };
390
391   PyDoc_STRVAR(listItem__doc__,
392     "ListItem class.\n"
393     "\n"
394     "ListItem([label, label2, iconImage, thumbnailImage]) -- Creates a new ListItem.\n"
395     "\n"
396     "label          : [opt] string or unicode - label1 text.\n"
397     "label2         : [opt] string or unicode - label2 text.\n"
398     "iconImage      : [opt] string - icon filename.\n"
399     "thumbnailImage : [opt] string - thumbnail filename.\n"
400     "\n"
401     "example:\n"
402     "  - listitem = xbmcgui.ListItem('Casino Royale', '[PG-13]', 'blank-poster.tbn', 'poster.tbn')\n");
403
404 // Restore code and data sections to normal.
405 #pragma code_seg()
406 #pragma data_seg()
407 #pragma bss_seg()
408 #pragma const_seg()
409
410   PyTypeObject ListItem_Type;
411
412   void initListItem_Type()
413   {
414     PyInitializeTypeObject(&ListItem_Type);
415
416     ListItem_Type.tp_name = "xbmcgui.ListItem";
417     ListItem_Type.tp_basicsize = sizeof(ListItem);
418     ListItem_Type.tp_dealloc = (destructor)ListItem_Dealloc;
419     ListItem_Type.tp_flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE;
420     ListItem_Type.tp_doc = listItem__doc__;
421     ListItem_Type.tp_methods = ListItem_methods;
422     ListItem_Type.tp_base = 0;
423     ListItem_Type.tp_new = ListItem_New;
424   }
425 }
426
427 #ifdef __cplusplus
428 }
429 #endif