vdr  1.7.27
dvbspu.h
Go to the documentation of this file.
00001 /*
00002  * SPU decoder for DVB devices
00003  *
00004  * Copyright (C) 2001.2002 Andreas Schultz <aschultz@warp10.net>
00005  *
00006  * This code is distributed under the terms and conditions of the
00007  * GNU GENERAL PUBLIC LICENSE. See the file COPYING for details.
00008  *
00009  * parts of this file are derived from the OMS program.
00010  *
00011  * $Id: dvbspu.h 2.5 2011/03/27 14:50:48 kls Exp $
00012  */
00013 
00014 #ifndef __DVBSPU_H
00015 #define __DVBSPU_H
00016 
00017 #include <inttypes.h>
00018 #include "osd.h"
00019 #include "spu.h"
00020 #include "thread.h"
00021 
00022 typedef struct sDvbSpuPalDescr {
00023     uint8_t index;
00024     uint8_t trans;
00025 
00026     bool operator != (const sDvbSpuPalDescr pd) const {
00027         return index != pd.index && trans != pd.trans;
00028     };
00029 } aDvbSpuPalDescr[4];
00030 
00031 typedef struct sDvbSpuRect {
00032     int x1, y1;
00033     int x2, y2;
00034 
00035     sDvbSpuRect(void) {
00036         x1 = y1 = x2 = y2 = 0;
00037     };
00038     int width() const {
00039         return x2 - x1 + 1;
00040     };
00041     int height() const {
00042         return y2 - y1 + 1;
00043     };
00044 
00045     bool operator != (const sDvbSpuRect r) const {
00046         return r.x1 != x1 || r.y1 != y1 || r.x2 != x2 || r.y2 != y2;
00047     };
00048 }
00049 
00050 sDvbSpuRect;
00051 
00052 // --- cDvbSpuPalette---------------------------------------------------------
00053 
00054 class cDvbSpuPalette {
00055   private:
00056     uint32_t palette[16];
00057 
00058   private:
00059     uint32_t yuv2rgb(uint32_t yuv_color);
00060 
00061   public:
00062     void setPalette(const uint32_t * pal);
00063     uint32_t getColor(uint8_t idx, uint8_t trans) const;
00064 };
00065 
00066 // --- cDvbSpuBitmap----------------------------------------------------------
00067 
00068 class cDvbSpuBitmap {
00069   private:
00070     sDvbSpuRect bmpsize;
00071     sDvbSpuRect minsize[4];
00072     uint8_t *bmp;
00073 
00074   private:
00075     void putPixel(int xp, int yp, int len, uint8_t colorid);
00076     void putFieldData(int field, uint8_t * data, uint8_t * endp);
00077 
00078   public:
00079      cDvbSpuBitmap(sDvbSpuRect size,
00080                    uint8_t * fodd, uint8_t * eodd,
00081                    uint8_t * feven, uint8_t * eeven);
00082     ~cDvbSpuBitmap();
00083 
00084     bool getMinSize(const aDvbSpuPalDescr paldescr,
00085                     sDvbSpuRect & size) const;
00086     int getMinBpp(const aDvbSpuPalDescr paldescr);
00087     cBitmap *getBitmap(const aDvbSpuPalDescr paldescr,
00088                        const cDvbSpuPalette & pal,
00089                        sDvbSpuRect & size) const;
00090 };
00091 
00092 // --- cDvbSpuDecoder---------------------------------------------------------
00093 
00094 class cDvbSpuDecoder:public cSpuDecoder {
00095   private:
00096     cOsd *osd;
00097     cMutex mutex;
00098 
00099     // processing state
00100     uint8_t *spu;
00101     uint32_t spupts;
00102     bool clean;
00103     bool ready;
00104     bool restricted_osd;
00105 
00106     enum spFlag { spNONE, spHIDE, spSHOW, spMENU };
00107     spFlag state;
00108 
00109      cSpuDecoder::eScaleMode scaleMode;
00110 
00111     //highligh area
00112     bool highlight;
00113     sDvbSpuRect hlpsize;
00114     aDvbSpuPalDescr hlpDescr;
00115 
00116     //palette
00117     cDvbSpuPalette palette;
00118 
00119     // spu info's
00120     sDvbSpuRect size;
00121     aDvbSpuPalDescr palDescr;
00122 
00123     uint16_t DCSQ_offset;
00124     uint16_t prev_DCSQ_offset;
00125 
00126     cDvbSpuBitmap *spubmp;
00127     bool allowedShow;
00128   private:
00129     int cmdOffs(void) {
00130         return ((spu[2] << 8) | spu[3]);
00131     };
00132     int spuSize(void) {
00133         return ((spu[0] << 8) | spu[1]);
00134     };
00135 
00136     sDvbSpuRect CalcAreaSize(sDvbSpuRect fgsize, cBitmap *fgbmp, sDvbSpuRect bgsize, cBitmap *bgbmp);
00137     int CalcAreaBpp(cBitmap *fgbmp, cBitmap *bgbmp);
00138 
00139   public:
00140     cDvbSpuDecoder();
00141     ~cDvbSpuDecoder();
00142 
00143     int setTime(uint32_t pts);
00144 
00145     cSpuDecoder::eScaleMode getScaleMode(void) { return scaleMode; }
00146     void setScaleMode(cSpuDecoder::eScaleMode ScaleMode);
00147     void setPalette(uint32_t * pal);
00148     void setHighlight(uint16_t sx, uint16_t sy, uint16_t ex, uint16_t ey,
00149                       uint32_t palette);
00150     void clearHighlight(void);
00151     void Empty(void);
00152     void Hide(void);
00153     void Draw(void);
00154     bool IsVisible(void) { return osd != NULL; }
00155     void processSPU(uint32_t pts, uint8_t * buf, bool AllowedShow);
00156 };
00157 
00158 // --- cDvbSpuPalette --------------------------------------------------------
00159 
00160 inline uint32_t cDvbSpuPalette::yuv2rgb(uint32_t yuv_color)
00161 {
00162     int Y, Cb, Cr;
00163     int Ey, Epb, Epr;
00164     int Eg, Eb, Er;
00165 
00166     Y = (yuv_color >> 16) & 0xff;
00167     Cb = (yuv_color) & 0xff;
00168     Cr = (yuv_color >> 8) & 0xff;
00169 
00170     Ey = (Y - 16);
00171     Epb = (Cb - 128);
00172     Epr = (Cr - 128);
00173     /* ITU-R 709
00174        Eg = (298*Ey - 55*Epb - 137*Epr)/256;
00175        Eb = (298*Ey + 543*Epb)/256;
00176        Er = (298*Ey + 460*Epr)/256;
00177      */
00178     /* FCC ~= mediaLib */
00179     Eg = (298 * Ey - 100 * Epb - 208 * Epr) / 256;
00180     Eb = (298 * Ey + 516 * Epb) / 256;
00181     Er = (298 * Ey + 408 * Epr) / 256;
00182 
00183     if (Eg > 255)
00184         Eg = 255;
00185     if (Eg < 0)
00186         Eg = 0;
00187 
00188     if (Eb > 255)
00189         Eb = 255;
00190     if (Eb < 0)
00191         Eb = 0;
00192 
00193     if (Er > 255)
00194         Er = 255;
00195     if (Er < 0)
00196         Er = 0;
00197 
00198     return Eb | (Eg << 8) | (Er << 16);
00199 }
00200 
00201 inline uint32_t cDvbSpuPalette::getColor(uint8_t idx, uint8_t trans) const
00202 {
00203     return palette[idx] | ((trans == 0x0f) ? 0xff000000 : (trans << 28));
00204 }
00205 
00206 #endif                          // __DVBSPU_H