MythTV  master
mhi.h
Go to the documentation of this file.
1 #ifndef _MHI_H_
2 #define _MHI_H_
3 
4 // Misc header
5 #include <ft2build.h>
6 #include FT_FREETYPE_H
7 
8 // STL headers
9 #include <list>
10 #include <vector>
11 using namespace std;
12 
13 // Qt headers
14 #include <QWaitCondition>
15 #include <QRunnable>
16 #include <QString>
17 #include <QMutex>
18 #include <QImage>
19 #include <QList>
20 #include <QRect>
21 #include <QPair>
22 #include <QMap> // for QMap
23 #include <QRegion> // for QRegion
24 #include <QSize> // for QSize
25 
26 // MythTV headers
27 #include "mythconfig.h"
28 #include "../libmythfreemheg/freemheg.h"
29 #include "mhegic.h"
30 #include "mythdeque.h"
31 
32 class MythPainter;
33 class InteractiveScreen;
34 class DSMCCPacket;
35 class MHIImageData;
36 class MHIContext;
37 class MythAVCopy;
38 class Dsmcc;
39 class InteractiveTV;
40 class MHStream;
41 class MThread;
42 class QByteArray;
43 
44 // Special value for the NetworkBootInfo version. Real values are a byte.
45 #define NBI_VERSION_UNSET 257
46 
50 class MHIContext : public MHContext, public QRunnable
51 {
52  public:
53  explicit MHIContext(InteractiveTV *parent);
54  ~MHIContext() override;
55 
56  void QueueDSMCCPacket(unsigned char *data, int length, int componentTag,
57  unsigned carouselId, int dataBroadcastId);
58  // A NetworkBootInfo sub-descriptor is present in the PMT.
59  void SetNetBootInfo(const unsigned char *data, uint length);
61  void Restart(int chanid, int sourceid, bool isLive);
62  // Offer a key press. Returns true if it accepts it.
63  // This will depend on the current profile.
64  bool OfferKey(const QString& key);
66  void UpdateOSD(InteractiveScreen *osdWindow, MythPainter *osdPainter);
68  void Reinit(const QRect &videoRect, const QRect &dispRect, float aspect);
69 
71  void StopEngine(void);
72 
73  // Test for an object in the carousel.
74  // Returns true if the object is present and
75  // so a call to GetCarouselData will not block and will return the data.
76  // Returns false if the object is not currently present because it has not
77  // yet appeared and also if it is not present in the containing directory.
78  bool CheckCarouselObject(QString objectPath) override; // MHContext
79 
80  // Get an object from the carousel. Returns true and sets the data if
81  // it was able to retrieve the named object. Blocks if the object seems
82  // to be present but has not yet appeared. Returns false if the object
83  // cannot be retrieved.
84  bool GetCarouselData(QString objectPath, QByteArray &result) override; // MHContext
85 
86  // Set the input register. This sets the keys that are to be handled
87  // by MHEG. Flushes the key queue.
88  void SetInputRegister(int num) override; // MHContext
89 
91  void RequireRedraw(const QRegion &region) override; // MHContext
92 
94  bool CheckStop(void) override // MHContext
95  { return m_stop; }
96 
98  void GetInitialStreams(int &audioTag, int &videoTag);
99 
101  MHDLADisplay *CreateDynamicLineArt(
102  bool isBoxed, MHRgba lineColour, MHRgba fillColour) override; // MHContext
103  MHTextDisplay *CreateText(void) override; // MHContext
104  MHBitmapDisplay *CreateBitmap(bool tiled) override; // MHContext
106  void DrawRect(int xPos, int yPos, int width, int height,
107  MHRgba colour) override; // MHContext
108  void DrawBackground(const QRegion &reg) override; // MHContext
109  void DrawVideo(const QRect &videoRect, const QRect &dispRect) override; // MHContext
110 
111  void DrawImage(int x, int y, const QRect &rect, const QImage &image,
112  bool bScaled = false, bool bUnder = false);
113 
114  int GetChannelIndex(const QString &str) override; // MHContext
116  bool GetServiceInfo(int channelId, int &netId, int &origNetId,
117  int &transportId, int &serviceId) override; // MHContext
118  bool TuneTo(int channel, int tuneinfo) override; // MHContext
119 
121  bool BeginStream(const QString &str, MHStream* notify) override; // MHContext
122  void EndStream() override; // MHContext
123  // Called when the stream starts or stops
124  bool StreamStarted(bool bStarted = true);
126  bool BeginAudio(int tag) override; // MHContext
128  void StopAudio() override; // MHContext
130  bool BeginVideo(int tag) override; // MHContext
132  void StopVideo() override; // MHContext
133  // Get current stream position, -1 if unknown
134  long GetStreamPos() override; // MHContext
135  // Get current stream size, -1 if unknown
136  long GetStreamMaxPos() override; // MHContext
137  // Set current stream position
138  long SetStreamPos(long pos) override; // MHContext
139  // Play or pause a stream
140  void StreamPlay(bool play) override; // MHContext
141 
142  // Get the context id strings. The format of these strings is specified
143  // by the UK MHEG profile.
144  const char *GetReceiverId(void) override // MHContext
145  { return "MYT001001"; } // Version number?
146  const char *GetDSMCCId(void) override // MHContext
147  { return "DSMMYT001"; } // DSMCC version.
148 
149  // InteractionChannel
150  // 0= Active, 1= Inactive, 2= Disabled
151  int GetICStatus() override; // MHContext
152 
153  // Operations used by the display classes
154  // Add an item to the display vector
155  void AddToDisplay(const QImage &image, const QRect &rect, bool bUnder = false);
156  int ScaleX(int n, bool roundup = false) const;
157  int ScaleY(int n, bool roundup = false) const;
158  QRect Scale(const QRect &r) const;
159  int ScaleVideoX(int n, bool roundup = false) const;
160  int ScaleVideoY(int n, bool roundup = false) const;
161  QRect ScaleVideo(const QRect &r) const;
162 
163  FT_Face GetFontFace(void) { return m_face; }
164  bool IsFaceLoaded(void) { return m_faceLoaded; }
165  bool LoadFont(const QString& name);
166  bool ImageUpdated(void) { return m_updated; }
167 
168  static const int kStdDisplayWidth = 720;
169  static const int kStdDisplayHeight = 576;
170 
171  protected:
172  void run(void) override; // QRunnable
173  void ProcessDSMCCQueue(void);
174  void NetworkBootRequested(void);
175  void ClearDisplay(void);
176  void ClearQueue(void);
177  bool LoadChannelCache();
178  bool GetDSMCCObject(const QString &objectPath, QByteArray &result);
179  bool CheckAccess(const QString &objectPath, QByteArray &cert);
180 
181  InteractiveTV *m_parent {nullptr};
182 
183  // Pointer to the DSMCC object carousel.
184  Dsmcc *m_dsmcc {nullptr};
185  QMutex m_dsmccLock;
187 
188  MHInteractionChannel m_ic; // Interaction channel
189  MHStream *m_notify {nullptr};
190 
191  QMutex m_keyLock;
193  int m_keyProfile {0};
194 
195  MHEG *m_engine; // Pointer to the MHEG engine
196 
197  mutable QMutex m_runLock;
198  QWaitCondition m_engine_wait; // protected by m_runLock
199  bool m_stop {false}; // protected by m_runLock
201  bool m_updated {false};
202 
203  list<MHIImageData*> m_display; // List of items to display
204 
205  FT_Face m_face {nullptr};
206  bool m_faceLoaded {false};
207 
208  MThread *m_engineThread {nullptr};
209 
210  int m_currentChannel {-1};
211  int m_currentStream {-1};
212  bool m_isLive {false};
213  int m_currentSource {-1};
214 
215  int m_audioTag {-1};
216  int m_videoTag {-1};
217  QList<int> m_tuneInfo;
218 
219  uint m_lastNbiVersion {NBI_VERSION_UNSET};
220  vector<unsigned char> m_nbiData;
221 
222  QRect m_videoRect, m_videoDisplayRect;
224 
225  // Channel index database cache
226  using Val_t = QPair< int, int >; // transportid, chanid
227  using Key_t = QPair< int, int >; // networkid, serviceid
228  using ChannelCache_t = QMap< Key_t, Val_t >;
231  static inline int Tid(ChannelCache_t::const_iterator it) { return it->first; }
232  static inline int Cid(ChannelCache_t::const_iterator it) { return it->second; }
233  static inline int Nid(ChannelCache_t::const_iterator it) { return it.key().first; }
234  static inline int Sid(ChannelCache_t::const_iterator it) { return it.key().second; }
235 };
236 
237 // Object for drawing text.
238 class MHIText : public MHTextDisplay
239 {
240  public:
241  explicit MHIText(MHIContext *parent)
242  : m_parent(parent) {}
243  ~MHIText() override = default;
244 
245  void Draw(int x, int y) override; // MHTextDisplay
246  void Clear(void) override; // MHTextDisplay
247  void AddText(int x, int y, const QString &str, MHRgba colour) override; // MHTextDisplay
248 
249  void SetSize(int width, int height) override; // MHTextDisplay
250  void SetFont(int size, bool isBold, bool isItalic) override; // MHTextDisplay
251 
252  QRect GetBounds(const QString &str, int &strLen, int maxSize = -1) override; // MHTextDisplay
253 
254  public:
255  MHIContext *m_parent {nullptr};
256  QImage m_image;
257  int m_fontSize {12};
258  bool m_fontItalic {false};
259  bool m_fontBold {false};
260  int m_width {0};
261  int m_height {0};
262 };
263 
268 {
269  public:
270  MHIBitmap(MHIContext *parent, bool tiled);
271  ~MHIBitmap() override;
272 
273  // Deleted functions should be public.
274  MHIBitmap(const MHIBitmap &) = delete; // not copyable
275  MHIBitmap &operator=(const MHIBitmap &) = delete; // not copyable
276 
278  void CreateFromPNG(const unsigned char *data, int length) override; // MHBitmapDisplay
279 
281  void CreateFromMPEG(const unsigned char *data, int length) override; // MHBitmapDisplay
282 
284  void CreateFromJPEG(const unsigned char *data, int length) override; // MHBitmapDisplay
285 
295  void Draw(int x, int y, QRect rect, bool tiled, bool bUnder) override; // MHBitmapDisplay
296 
298  void ScaleImage(int newWidth, int newHeight) override; // MHBitmapDisplay
299 
300  // Gets
301  QSize GetSize(void) override { return m_image.size(); } // MHBitmapDisplay
302  bool IsOpaque(void) override { return !m_image.isNull() && m_opaque; } // MHBitmapDisplay
303 
304  public:
305  MHIContext *m_parent {nullptr};
306  bool m_tiled;
307  QImage m_image;
308  bool m_opaque {false};
309  MythAVCopy *m_copyCtx {nullptr};
310 };
311 
315 class MHIDLA : public MHDLADisplay
316 {
317  public:
318  MHIDLA(MHIContext *parent, bool isBoxed,
319  MHRgba lineColour, MHRgba fillColour)
320  : m_parent(parent), m_boxed(isBoxed),
321  m_boxLineColour(lineColour), m_boxFillColour(fillColour) {}
323  void Draw(int x, int y) override; // MHDLADisplay
325  void SetSize(int width, int height) override // MHDLADisplay
326  {
327  m_width = width;
328  m_height = height;
329  Clear();
330  }
331  void SetLineSize(int width) override // MHDLADisplay
332  { m_lineWidth = width; }
333  void SetLineColour(MHRgba colour) override // MHDLADisplay
334  { m_lineColour = colour; }
335  void SetFillColour(MHRgba colour) override // MHDLADisplay
336  { m_fillColour = colour; }
337 
339  void Clear(void) override; // MHDLADisplay
340 
341  // add items to the drawing.
342  void DrawLine(int x1, int y1, int x2, int y2) override; // MHDLADisplay
343  void DrawBorderedRectangle(int x, int y, int width, int height) override; // MHDLADisplay
344  void DrawOval(int x, int y, int width, int height) override; // MHDLADisplay
345  void DrawArcSector(int x, int y, int width, int height,
346  int start, int arc, bool isSector) override; // MHDLADisplay
347  void DrawPoly(bool isFilled, int nPoints, const int *xArray, const int *yArray) override; // MHDLADisplay
348 
349  protected:
350  void DrawRect(int x, int y, int width, int height, MHRgba colour);
351  void DrawLineSub(int x1, int y1, int x2, int y2, bool swapped);
352 
353  protected:
354  MHIContext *m_parent {nullptr};
355  QImage m_image;
356  int m_width {0};
357  int m_height {0};
358  bool m_boxed;
363  int m_lineWidth {0};
364 };
365 
370 {
371  public:
372  DSMCCPacket(unsigned char *data, int length, int tag,
373  unsigned car, int dbid)
374  : m_data(data), m_length(length),
375  m_componentTag(tag), m_carouselId(car),
376  m_dataBroadcastId(dbid)
377  {
378  }
379 
381  {
382  free(m_data);
383  }
384 
385  public:
386  unsigned char *m_data {nullptr};
387  int m_length;
389  unsigned m_carouselId;
391 };
392 
393 #endif // _MHI_H_
QMutex m_displayLock
Definition: mhi.h:200
unsigned m_carouselId
Definition: mhi.h:389
This is a wrapper around QThread that does several additional things.
Definition: mthread.h:46
QMutex m_dsmccLock
Definition: mhi.h:185
ChannelCache_t m_channelCache
Definition: mhi.h:229
bool m_boxed
Does it have a border?
Definition: mhi.h:358
Data for items in the interactive television display stack.
Definition: mhi.cpp:66
static int Tid(ChannelCache_t::const_iterator it)
Definition: mhi.h:231
static int Nid(ChannelCache_t::const_iterator it)
Definition: mhi.h:233
Object for displaying Dynamic Line Art.
Definition: mhi.h:315
MythAVCopy Copy AVFrame<->frame, performing the required conversion if any.
Definition: mythavutil.h:106
FT_Face GetFontFace(void)
Definition: mhi.h:163
Data for the queued DSMCC tables.
Definition: mhi.h:369
Definition: dsmcc.h:75
bool m_tiled
Definition: mhi.h:306
QMap< Key_t, Val_t > ChannelCache_t
Definition: mhi.h:228
const char * GetReceiverId(void) override
Definition: mhi.h:144
QWaitCondition m_engine_wait
Definition: mhi.h:198
bool ImageUpdated(void)
Definition: mhi.h:166
QRect m_displayRect
Definition: mhi.h:223
MHRgba m_lineColour
Current line colour.
Definition: mhi.h:361
static int Sid(ChannelCache_t::const_iterator it)
Definition: mhi.h:234
int m_length
Definition: mhi.h:387
bool IsFaceLoaded(void)
Definition: mhi.h:164
void SetLineColour(MHRgba colour) override
Definition: mhi.h:333
Contains various utility functions for interactive television.
Definition: mhi.h:50
Definition: freemheg.h:48
MHRgba m_boxFillColour
Fill colour for the background.
Definition: mhi.h:360
int m_dataBroadcastId
Definition: mhi.h:390
bool CheckStop(void) override
Check whether we have requested a stop.
Definition: mhi.h:94
static int x2
Definition: mythsocket.cpp:61
QList< int > m_tuneInfo
Definition: mhi.h:217
#define NBI_VERSION_UNSET
Definition: mhi.h:45
MythDeque< int > m_keyQueue
Definition: mhi.h:192
QPair< int, int > Key_t
Definition: mhi.h:227
MHIDLA(MHIContext *parent, bool isBoxed, MHRgba lineColour, MHRgba fillColour)
Definition: mhi.h:318
QMutex m_channelMutex
Definition: mhi.h:230
DSMCCPacket(unsigned char *data, int length, int tag, unsigned car, int dbid)
Definition: mhi.h:372
unsigned int uint
Definition: compat.h:140
~DSMCCPacket()
Definition: mhi.h:380
static int Cid(ChannelCache_t::const_iterator it)
Definition: mhi.h:232
MHIText(MHIContext *parent)
Definition: mhi.h:241
const char * GetDSMCCId(void) override
Definition: mhi.h:146
QPair< int, int > Val_t
Definition: mhi.h:226
QRect m_videoRect
Definition: mhi.h:222
MHRgba m_fillColour
Current fill colour.
Definition: mhi.h:362
vector< unsigned char > m_nbiData
Definition: mhi.h:220
QSize GetSize(void) override
Definition: mhi.h:301
bool IsOpaque(void) override
Definition: mhi.h:302
Definition: mhi.h:238
MHEG * m_engine
Definition: mhi.h:195
QImage m_image
Definition: mhi.h:307
MythDeque< DSMCCPacket * > m_dsmccQueue
Definition: mhi.h:186
MHInteractionChannel m_ic
Definition: mhi.h:188
MHRgba m_boxLineColour
Line colour for the background.
Definition: mhi.h:359
Object for drawing bitmaps.
Definition: mhi.h:267
list< MHIImageData * > m_display
Definition: mhi.h:203
QMutex m_keyLock
Definition: mhi.h:191
void SetSize(int width, int height) override
Set the box size. Also clears the drawing.
Definition: mhi.h:325
void SetFillColour(MHRgba colour) override
Definition: mhi.h:335
int m_componentTag
Definition: mhi.h:388
QImage m_image
Definition: mhi.h:256
#define Clear(a)
QMutex m_runLock
Definition: mhi.h:197
This is the interface between an MHEG engine and a MythTV TV object.
Definition: interactivetv.h:12
static int x1
Definition: mythsocket.cpp:60
void SetLineSize(int width) override
Definition: mhi.h:331
QImage m_image
Definition: mhi.h:355