add support for Linkage services ( Premiere Subservices )
[vuplus_dvbapp] / lib / service / iservice.h
1 #ifndef __lib_dvb_iservice_h
2 #define __lib_dvb_iservice_h
3
4 #include <lib/python/swig.h>
5 #include <lib/base/object.h>
6 #include <string>
7 #include <connection.h>
8 #include <list>
9
10 class eServiceEvent;
11
12 class eServiceReference
13 {
14 public:
15         enum
16         {
17                 idInvalid=-1,
18                 idStructure,    // service_id == 0 is root
19                 idDVB,
20                 idFile,
21                 idUser=0x1000
22         };
23         int type;
24
25         int flags; // flags will NOT be compared.
26         enum
27         {
28                 isDirectory=1,          // SHOULD enter  (implies mustDescent)
29                 mustDescent=2,          // cannot be played directly - often used with "isDirectory" (implies canDescent)
30                 /*
31                         for example:
32                                 normal services have none of them - they can be fed directly into the "play"-handler.
33                                 normal directories have both of them set - you cannot play a directory directly and the UI should descent into it.
34                                 playlists have "mustDescent", but not "isDirectory" - you don't want the user to browse inside the playlist (unless he really wants)
35                                 services with sub-services have none of them, instead the have the "canDecsent" flag (as all of the above)
36                 */
37                 canDescent=4,                   // supports enterDirectory/leaveDirectory
38                 flagDirectory=isDirectory|mustDescent|canDescent,
39                 shouldSort=8,                   // should be ASCII-sorted according to service_name. great for directories.
40                 hasSortKey=16,          // has a sort key in data[3]. not having a sort key implies 0.
41                 sort1=32                                        // sort key is 1 instead of 0
42         };
43
44         inline int getSortKey() const { return (flags & hasSortKey) ? data[3] : ((flags & sort1) ? 1 : 0); }
45
46         int data[8];
47         std::string path;
48         std::string getPath() { return path; }
49
50 // only for override service names in bouquets or to give servicerefs a name which not have a
51 // real existing service ( for dvb eServiceDVB )
52         std::string name;
53         std::string getName() { return name; }
54
55         eServiceReference()
56                 : type(idInvalid), flags(0)
57         {
58                 memset(data, 0, sizeof(data));
59         }
60         eServiceReference(int type, int flags)
61                 : type(type), flags(flags)
62         {
63                 memset(data, 0, sizeof(data));
64         }
65         eServiceReference(int type, int flags, int data0)
66                 : type(type), flags(flags)
67         {
68                 memset(data, 0, sizeof(data));
69                 data[0]=data0;
70         }
71         eServiceReference(int type, int flags, int data0, int data1)
72                 : type(type), flags(flags)
73         {
74                 memset(data, 0, sizeof(data));
75                 data[0]=data0;
76                 data[1]=data1;
77         }
78         eServiceReference(int type, int flags, int data0, int data1, int data2)
79                 : type(type), flags(flags)
80         {
81                 memset(data, 0, sizeof(data));
82                 data[0]=data0;
83                 data[1]=data1;
84                 data[2]=data2;
85         }
86         eServiceReference(int type, int flags, int data0, int data1, int data2, int data3)
87                 : type(type), flags(flags)
88         {
89                 memset(data, 0, sizeof(data));
90                 data[0]=data0;
91                 data[1]=data1;
92                 data[2]=data2;
93                 data[3]=data3;
94         }
95         eServiceReference(int type, int flags, int data0, int data1, int data2, int data3, int data4)
96                 : type(type), flags(flags)
97         {
98                 memset(data, 0, sizeof(data));
99                 data[0]=data0;
100                 data[1]=data1;
101                 data[2]=data2;
102                 data[3]=data3;
103                 data[4]=data4;
104         }
105         eServiceReference(int type, int flags, const std::string &path)
106                 : type(type), flags(flags), path(path)
107         {
108                 memset(data, 0, sizeof(data));
109         }
110         eServiceReference(const std::string &string);
111         std::string toString() const;
112         bool operator==(const eServiceReference &c) const
113         {
114                 if (type != c.type)
115                         return 0;
116                 return (memcmp(data, c.data, sizeof(int)*8)==0) && (path == c.path);
117         }
118         bool operator!=(const eServiceReference &c) const
119         {
120                 return !(*this == c);
121         }
122         bool operator<(const eServiceReference &c) const
123         {
124                 if (type < c.type)
125                         return 1;
126
127                 if (type > c.type)
128                         return 0;
129
130                 int r=memcmp(data, c.data, sizeof(int)*8);
131                 if (r)
132                         return r < 0;
133                 return path < c.path;
134         }
135         operator bool() const
136         {
137                 return valid();
138         }
139         
140         int valid() const
141         {
142                 return type != idInvalid;
143         }
144 };
145
146 SWIG_ALLOW_OUTPUT_SIMPLE(eServiceReference);
147
148 typedef long long pts_t;
149
150         /* the reason we have the servicereference as additional argument is
151            that we don't have to create one object for every entry in a possibly
152            large list, provided that no state information is nessesary to deliver
153            the required information. Anyway - ref *must* be the same as the argument
154            to the info() or getIServiceInformation call! */
155
156         /* About the usage of SWIG_VOID:
157            SWIG_VOID(real_returntype_t) hides a return value from swig. This is used for
158            the "superflouus" RESULT return values.
159            
160            Python code has to check the returned pointer against 0. This works,
161            as all functions returning instances in smartpointers AND having a 
162            RESULT have to BOTH return non-zero AND set the pointer to zero.
163            
164            Python code thus can't check for the reason, but the reason isn't
165            user-servicable anyway. If you want to return a real reason which
166            goes beyong "it just doesn't work", use extra variables for this,
167            not the RESULT.
168            
169            Hide the result only if there is another way to check for failure! */
170            
171 class iStaticServiceInformation: public iObject
172 {
173 public:
174         virtual SWIG_VOID(RESULT) getName(const eServiceReference &ref, std::string &SWIG_OUTPUT)=0;
175         
176                 // doesn't need to be implemented, should return -1 then.
177         virtual int getLength(const eServiceReference &ref);
178         virtual SWIG_VOID(RESULT) getEvent(const eServiceReference &ref, ePtr<eServiceEvent> &SWIG_OUTPUT);
179                 // returns true when not implemented
180         virtual bool isPlayable(const eServiceReference &ref, const eServiceReference &ignore);
181 };
182
183 TEMPLATE_TYPEDEF(ePtr<iStaticServiceInformation>, iStaticServiceInformationPtr);
184
185 TEMPLATE_TYPEDEF(ePtr<eServiceEvent>, eServiceEventPtr);
186
187 class iServiceInformation: public iObject
188 {
189 public:
190         virtual SWIG_VOID(RESULT) getName(std::string &SWIG_OUTPUT)=0;
191         virtual SWIG_VOID(RESULT) getEvent(ePtr<eServiceEvent> &SWIG_OUTPUT, int nownext);
192
193         enum { 
194                 sIsCrypted,  /* is encrypted (no indication if decrypt was possible) */
195                 sAspect,     /* aspect ratio: 0=4:3, 1=16:9, 2=whatever we need */
196                 sIsMultichannel, /* multichannel *available* (probably not selected) */
197                 
198                         /* "user serviceable info" - they are not reliable. Don't use them for anything except the service menu!
199                            that's also the reason why they are so globally defined. 
200                            
201                            
202                            again - if somebody EVER tries to use this information for anything else than simply displaying it,
203                            i will change this to return a user-readable text like "zero x zero three three" (and change the
204                            exact spelling in every version) to stop that!
205                         */
206                 sVideoPID,
207                 sAudioPID,
208                 sPCRPID,
209                 sPMTPID,
210                 sTXTPID,
211                 
212                 sSID,
213                 sONID,
214                 sTSID,
215                 sNamespace,
216                 sProvider,
217         };
218         enum { resNA = -1, resIsString = -2 };
219
220         virtual int getInfo(int w);
221         virtual std::string getInfoString(int w);
222 };
223
224 TEMPLATE_TYPEDEF(ePtr<iServiceInformation>, iServiceInformationPtr);
225
226 class iFrontendStatusInformation: public iObject
227 {
228 public:
229         enum {
230                 bitErrorRate,
231                 signalPower,
232                 signalQuality
233         };
234         virtual int getFrontendInfo(int w)=0;
235 };
236
237 TEMPLATE_TYPEDEF(ePtr<iFrontendStatusInformation>, iFrontendStatusInformationPtr);
238
239 class iPauseableService: public iObject
240 {
241 public:
242         virtual RESULT pause()=0;
243         virtual RESULT unpause()=0;
244 };
245
246 TEMPLATE_TYPEDEF(ePtr<iPauseableService>, iPauseableServicePtr);
247
248 class iSeekableService: public iObject
249 {
250 public:
251         virtual RESULT getLength(pts_t &SWIG_OUTPUT)=0;
252         virtual RESULT seekTo(pts_t to)=0;
253         enum { dirForward = +1, dirBackward = -1 };
254         virtual RESULT seekRelative(int direction, pts_t to)=0;
255         virtual RESULT getPlayPosition(pts_t &SWIG_OUTPUT)=0;
256 };
257
258 TEMPLATE_TYPEDEF(ePtr<iSeekableService>, iSeekableServicePtr);
259
260 struct iAudioTrackInfo
261 {
262         std::string m_description;
263         std::string m_language; /* iso639 */
264         
265         std::string getDescription() { return m_description; }
266         std::string getLanguage() { return m_language; }
267 };
268
269 SWIG_ALLOW_OUTPUT_SIMPLE(iAudioTrackInfo);
270
271 class iAudioTrackSelection: public iObject
272 {
273 public:
274         virtual int getNumberOfTracks()=0;
275         virtual RESULT selectTrack(unsigned int i)=0;
276         virtual SWIG_VOID(RESULT) getTrackInfo(struct iAudioTrackInfo &SWIG_OUTPUT, unsigned int n)=0;
277 };
278
279 TEMPLATE_TYPEDEF(ePtr<iAudioTrackSelection>, iAudioTrackSelectionPtr);
280
281 class iSubserviceList: public iObject
282 {
283 public:
284         virtual int getNumberOfSubservices()=0;
285         virtual SWIG_VOID(RESULT) getSubservice(eServiceReference &SWIG_OUTPUT, unsigned int n)=0;
286 };
287
288 TEMPLATE_TYPEDEF(ePtr<iSubserviceList>, iSubserviceListPtr);
289
290 class iPlayableService: public iObject
291 {
292         friend class iServiceHandler;
293 public:
294         enum
295         {
296                 evStart,
297                 evEnd,
298                 
299                 evTuneFailed,
300                         // when iServiceInformation is implemented:
301                 evUpdatedEventInfo,
302                 evUpdatedInfo,
303         };
304         virtual RESULT connectEvent(const Slot2<void,iPlayableService*,int> &event, ePtr<eConnection> &connection)=0;
305         virtual RESULT start()=0;
306         virtual RESULT stop()=0;
307         virtual SWIG_VOID(RESULT) seek(ePtr<iSeekableService> &SWIG_OUTPUT)=0;
308         virtual SWIG_VOID(RESULT) pause(ePtr<iPauseableService> &SWIG_OUTPUT)=0;
309         virtual SWIG_VOID(RESULT) info(ePtr<iServiceInformation> &SWIG_OUTPUT)=0;
310         virtual SWIG_VOID(RESULT) audioTracks(ePtr<iAudioTrackSelection> &SWIG_OUTPUT)=0;
311         virtual SWIG_VOID(RESULT) subServices(ePtr<iSubserviceList> &SWIG_OUTPUT)=0;
312         virtual SWIG_VOID(RESULT) frontendStatusInfo(ePtr<iFrontendStatusInformation> &SWIG_OUTPUT)=0;
313 };
314
315 TEMPLATE_TYPEDEF(ePtr<iPlayableService>, iPlayableServicePtr);
316
317 class iRecordableService: public iObject
318 {
319 public:
320         virtual RESULT prepare(const char *filename)=0;
321         virtual RESULT start()=0;
322         virtual RESULT stop()=0;
323 };
324
325 TEMPLATE_TYPEDEF(ePtr<iRecordableService>, iRecordableServicePtr);
326
327 // TEMPLATE_TYPEDEF(std::list<eServiceReference>, eServiceReferenceList);
328
329 class iMutableServiceList: public iObject
330 {
331 public:
332                 /* flush changes */
333         virtual RESULT flushChanges()=0;
334                 /* adds a service to a list */
335         virtual RESULT addService(eServiceReference &ref)=0;
336                 /* removes a service from a list */
337         virtual RESULT removeService(eServiceReference &ref)=0;
338                 /* moves a service in a list, only if list suppports a specific sort method. */
339                 /* pos is the new, absolute position from 0..size-1 */
340         virtual RESULT moveService(eServiceReference &ref, int pos)=0;
341 };
342
343 TEMPLATE_TYPEDEF(ePtr<iMutableServiceList>, iMutableServiceListPtr);
344
345 class iListableService: public iObject
346 {
347 public:
348                 /* legacy interface: get a list */
349         virtual RESULT getContent(std::list<eServiceReference> &list)=0;
350         
351                 /* new, shiny interface: streaming. */
352         virtual SWIG_VOID(RESULT) getNext(eServiceReference &SWIG_OUTPUT)=0;
353         
354                 /* use this for sorting. output is not sorted because of either
355                  - performance reasons: the whole list must be buffered or
356                  - the interface would be restricted to a list. streaming
357                    (as well as a future "active" extension) won't be possible.
358                 */
359         virtual int compareLessEqual(const eServiceReference &, const eServiceReference &)=0;
360         
361         virtual SWIG_VOID(RESULT) startEdit(ePtr<iMutableServiceList> &SWIG_OUTPUT)=0;
362 };
363
364 TEMPLATE_TYPEDEF(ePtr<iListableService>, iListableServicePtr);
365
366         /* a helper class which can be used as argument to stl's sort(). */
367 class iListableServiceCompare
368 {
369         ePtr<iListableService> m_list;
370 public:
371         iListableServiceCompare(iListableService *list): m_list(list) { }
372         bool operator()(const eServiceReference &a, const eServiceReference &b)
373         {
374                 return m_list->compareLessEqual(a, b);
375         }
376 };
377
378 class iServiceOfflineOperations: public iObject
379 {
380 public:
381                 /* to delete a service, forever. */
382         virtual RESULT deleteFromDisk(int simulate=1)=0;
383         
384                 /* for transferring a service... */
385         virtual SWIG_VOID(RESULT) getListOfFilenames(std::list<std::string> &SWIG_OUTPUT)=0;
386         
387                 // TODO: additional stuff, like a conversion interface?
388 };
389
390 TEMPLATE_TYPEDEF(ePtr<iServiceOfflineOperations>, iServiceOfflineOperationsPtr);
391
392 class iServiceHandler: public iObject
393 {
394 public:
395         virtual SWIG_VOID(RESULT) play(const eServiceReference &, ePtr<iPlayableService> &SWIG_OUTPUT)=0;
396         virtual SWIG_VOID(RESULT) record(const eServiceReference &, ePtr<iRecordableService> &SWIG_OUTPUT)=0;
397         virtual SWIG_VOID(RESULT) list(const eServiceReference &, ePtr<iListableService> &SWIG_OUTPUT)=0;
398         virtual SWIG_VOID(RESULT) info(const eServiceReference &, ePtr<iStaticServiceInformation> &SWIG_OUTPUT)=0;
399         virtual SWIG_VOID(RESULT) offlineOperations(const eServiceReference &, ePtr<iServiceOfflineOperations> &SWIG_OUTPUT)=0;
400 };
401
402 TEMPLATE_TYPEDEF(ePtr<iServiceHandler>, iServiceHandlerPtr);
403
404 #endif