summaryrefslogtreecommitdiff
path: root/video.cpp
diff options
context:
space:
mode:
authorJochen Dolze <vdr@dolze.de>2010-03-05 09:39:47 +0100
committerJochen Dolze <vdr@dolze.de>2010-03-05 09:39:47 +0100
commita73c755a421cd3b20dd9923c863a74ec860ad9ed (patch)
tree908121f0038cce0125ac0473aaa6fe6a9aee4b63 /video.cpp
parent4810e07340050c6651262da3deda8cb565c01c71 (diff)
downloadvdr-plugin-markad-a73c755a421cd3b20dd9923c863a74ec860ad9ed.tar.gz
vdr-plugin-markad-a73c755a421cd3b20dd9923c863a74ec860ad9ed.tar.bz2
Changed H264 handlingv0.0.5
Diffstat (limited to 'video.cpp')
-rw-r--r--video.cpp345
1 files changed, 252 insertions, 93 deletions
diff --git a/video.cpp b/video.cpp
index 858b49f..0d389e4 100644
--- a/video.cpp
+++ b/video.cpp
@@ -16,86 +16,124 @@ cMarkAdLogo::cMarkAdLogo(int RecvNumber, MarkAdContext *maContext)
GX[0][0] = -1;
GX[0][1] = 0;
GX[0][2] = 1;
- GX[1][0] = -2; // 2
+ GX[1][0] = -2;
GX[1][1] = 0;
- GX[1][2] = 2; // 2
+ GX[1][2] = 2;
GX[2][0] = -1;
GX[2][1] = 0;
GX[2][2] = 1;
// 3x3 GY Sobel mask
GY[0][0] = 1;
- GY[0][1] = 2; // 2
+ GY[0][1] = 2;
GY[0][2] = 1;
GY[1][0] = 0;
GY[1][1] = 0;
GY[1][2] = 0;
GY[2][0] = -1;
- GY[2][1] = -2; //2
+ GY[2][1] = -2;
GY[2][2] = -1;
- plane=NULL;
- first=true;
+ memset(&area,0,sizeof(area));
+
+ area[TOP_LEFT].init=true;
+ area[TOP_RIGHT].init=true;
+ area[BOTTOM_LEFT].init=true;
+ area[BOTTOM_RIGHT].init=true;
+
+ LOGOHEIGHT=100;
+ LOGOWIDTH=192;
+
+ framecnt=0;
+ savedlastiframe=-1;
+ logostart=-1;
+ logostate=-1;
+ counter=0;
}
cMarkAdLogo::~cMarkAdLogo()
{
- if (plane) free(plane);
}
-void cMarkAdLogo::SaveFrame(int LastIFrame)
+void cMarkAdLogo::SaveLogo(int corner, int lastiframe)
{
if (!macontext) return;
if (!macontext->Video.Info.Width) return;
- if (!plane) return;
FILE *pFile;
char szFilename[32];
// Open file
- sprintf(szFilename, "frame%06d.pgm", LastIFrame);
+ sprintf(szFilename, "%iframe%06d.pgm", corner,lastiframe);
pFile=fopen(szFilename, "wb");
if (pFile==NULL)
return;
// Write header
- fprintf(pFile, "P5\n%d %d\n255\n", macontext->Video.Info.Width,LOGOHEIGHT);
+ fprintf(pFile, "P5\n%d %d\n255\n", LOGOWIDTH,LOGOHEIGHT);
// Write pixel data
- fwrite(plane,1,macontext->Video.Info.Width*LOGOHEIGHT,pFile);
+ fwrite(area[corner].plane,1,LOGOWIDTH*LOGOHEIGHT,pFile);
// Close file
fclose(pFile);
-
- dsyslog("markad saved frame %i",LastIFrame);
- if (LastIFrame>750) abort();
}
-int cMarkAdLogo::Process(int LastIFrame)
+void cMarkAdLogo::CheckCorner(int corner)
{
- if (!macontext) return 0;
- if (!macontext->Video.Info.Width) return 0;
- if (!macontext->Video.Data.Valid) return 0;
+ if (!macontext) return;
+ if (!macontext->Video.Info.Width) return;
+ if (!macontext->Video.Info.Height) return;
+ if (!macontext->Video.Data.Valid) return;
+
+ if (corner>BOTTOM_RIGHT) return;
+ if (corner<TOP_LEFT) return;
- if (!plane)
+ int xstart,xend,ystart,yend;
+
+ switch (corner)
{
- plane=(uchar *) malloc(LOGOHEIGHT*macontext->Video.Info.Width);
- if (!plane) return 0;
+ case TOP_LEFT:
+ xstart=0;
+ xend=LOGOWIDTH;
+ ystart=0;
+ yend=LOGOHEIGHT;
+ break;
+ case TOP_RIGHT:
+ xstart=macontext->Video.Info.Width-LOGOWIDTH;
+ xend=macontext->Video.Info.Width;
+ ystart=0;
+ yend=LOGOHEIGHT;
+ break;
+ case BOTTOM_LEFT:
+ xstart=0;
+ xend=LOGOWIDTH;
+ ystart=macontext->Video.Info.Height-LOGOHEIGHT;
+ yend=macontext->Video.Info.Height;
+ break;
+ case BOTTOM_RIGHT:
+ xstart=macontext->Video.Info.Width-LOGOWIDTH;
+ xend=macontext->Video.Info.Width;
+ ystart=macontext->Video.Info.Height-LOGOHEIGHT;
+ yend=macontext->Video.Info.Height;
+ break;
+ default:
+ return;
}
int SUM;
int sumX,sumY;
-
- for (int Y=0; Y<=LOGOHEIGHT-1; Y++)
+ area[corner].blackpixel=0;
+ for (int Y=ystart; Y<=yend-1; Y++)
{
- for (int X=0; X<=macontext->Video.Info.Width-1; X++)
+ for (int X=xstart; X<=xend-1; X++)
{
sumX=0;
sumY=0;
// image boundaries
- if (Y==0 || Y==LOGOHEIGHT-1)
+ if (Y<(ystart+15) || Y>(yend-15))
SUM=0;
- else if (X==0 || X==macontext->Video.Info.Width-1)
+ else if (X<(xstart+15) || X>(xend-15))
SUM=0;
// convolution starts here
else
@@ -127,12 +165,151 @@ int cMarkAdLogo::Process(int LastIFrame)
if (SUM>=127) SUM=255;
if (SUM<127) SUM=0;
- plane[X+Y*macontext->Video.Info.Width]=255-(uchar) (SUM);
+ int val = 255-(uchar) SUM;
+
+ if (area[corner].init)
+ {
+ area[corner].plane[(X-xstart)+(Y-ystart)*LOGOWIDTH]=val;
+ }
+ else
+ {
+ if (area[corner].plane[(X-xstart)+(Y-ystart)*LOGOWIDTH]!=val)
+ {
+ area[corner].plane[(X-xstart)+(Y-ystart)*LOGOWIDTH]=255;
+ }
+ }
+
+ if (area[corner].plane[(X-xstart)+(Y-ystart)*LOGOWIDTH]!=255)
+ area[corner].blackpixel++;
}
+
}
- //SaveFrame(LastIFrame);
+ area[corner].init=false;
+ if (area[corner].blackpixel<100) area[corner].blackpixel=0;
+}
- return 0;
+void cMarkAdLogo::CheckCorners(int lastiframe)
+{
+ for (int i=TOP_LEFT; i<=BOTTOM_RIGHT; i++)
+ {
+ CheckCorner(i);
+// printf("%i ",area[i].blackpixel);
+// SaveLogo(i,lastiframe);
+ }
+// printf("\n");
+}
+
+void cMarkAdLogo::RestartLogoDetection()
+{
+ for (int i=TOP_LEFT; i<=BOTTOM_RIGHT; i++)
+ {
+ area[i].init=true;
+// area[i].cntfound=1;
+ }
+ framecnt=0;
+ counter++;
+}
+
+bool cMarkAdLogo::LogoVisible()
+{
+ int sum=0;
+ for (int i=TOP_LEFT; i<=BOTTOM_RIGHT; i++)
+ {
+ sum+=area[i].blackpixel;
+ }
+ return (sum!=0);
+}
+
+/*
+void cMarkAdLogo::ResetLogoDetection()
+{
+ for (int i=TOP_LEFT; i<=BOTTOM_RIGHT; i++)
+ {
+ area[i].init=true;
+ area[i].cntfound=0;
+ }
+ framecnt=0;
+ counter=0;
+}
+
+bool cMarkAdLogo::LogoFound()
+{
+ for (int i=TOP_LEFT; i<=BOTTOM_RIGHT; i++)
+ {
+ printf("%i ",area[i].cntfound);
+ }
+ printf("\n");
+ return false;
+}
+*/
+
+int cMarkAdLogo::Process(int LastIFrame)
+{
+ if (!macontext) return 0;
+ if (!macontext->Video.Info.Width) return 0;
+ if (!macontext->Video.Data.Valid) return 0;
+
+ if ((macontext->Video.Info.Width>720) && (LOGOWIDTH==192))
+ {
+ LOGOWIDTH=288;
+ }
+
+ int ret=0;
+ CheckCorners(LastIFrame);
+// if (framecnt>=250) abort();
+ /*
+ if (framecnt>=MAXFRAMES)
+ {
+ if (logostate==-1)
+ {
+ if (LogoVisible())
+ {
+ logostate=1;
+ }
+ else
+ {
+ logostate=0;
+ }
+ printf("Initial logo state %i\n",logostate);
+ abort();
+ }
+ else
+ {
+ if (!LogoVisible() && logostate==1)
+ {
+ if (logostart==-1) logostart=LastIFrame;
+ RestartLogoDetection();
+ printf("%i\n",counter);
+ if (counter>=2)
+ {
+ printf("%i Logo gone\n",logostart);
+ logostart=-1;
+ counter=0;
+ logostate=0;
+ ret=-1;
+ }
+ }
+ if (LogoVisible() && logostate==0)
+ {
+ if (logostart==-1) logostart=LastIFrame;
+ RestartLogoDetection();
+ printf("%i\n",counter);
+ if (counter>=2)
+ {
+ printf("%i Logo start\n",logostart);
+ logostart=-1;
+ counter=0;
+ logostate=1;
+ ret=1;
+ }
+ }
+ }
+ }
+ */
+ if (savedlastiframe!=-1) framecnt+=(LastIFrame-savedlastiframe);
+ savedlastiframe=LastIFrame;
+
+ return ret;
}
cMarkAdBlackBordersHoriz::cMarkAdBlackBordersHoriz(int RecvNumber, MarkAdContext *maContext)
@@ -177,62 +354,25 @@ int cMarkAdBlackBordersHoriz::Process(int LastIFrame, int *BorderIFrame)
#define BRIGHTNESS 20
if (!macontext) return 0;
if (!macontext->Video.Data.Valid) return 0;
- return 0;
+ if (macontext->Video.Data.PlaneLinesize[0]!=macontext->Video.Info.Width) return 0;
*BorderIFrame=borderiframe;
- int x,y;
+ int x;
bool ftop=true,fbottom=true;
- if (macontext->Video.Data.PlaneLinesize[0]!=macontext->Video.Info.Width)
+ // "fast" method
+ for (x=(macontext->Video.Info.Height-CHECKHEIGHT)*macontext->Video.Info.Width;
+ x<macontext->Video.Info.Height*macontext->Video.Info.Width; x++)
{
- // slow (?) method
- for (y=(macontext->Video.Info.Height-CHECKHEIGHT); y<macontext->Video.Info.Height; y++)
- {
- for (x=0; x<macontext->Video.Info.Width; x++)
- {
- if (macontext->Video.Data.Plane[0][y*macontext->Video.Data.PlaneLinesize[0]+x]>
- BRIGHTNESS)
- {
- fbottom=false;
- y=macontext->Video.Info.Height;
- break;
- }
- }
- }
-
- if (fbottom)
- {
- for (y=0; y<CHECKHEIGHT; y++)
- {
- for (x=0; x<macontext->Video.Info.Width; x++)
- {
- if (macontext->Video.Data.Plane[0][y*macontext->Video.Data.PlaneLinesize[0]+x]
- >BRIGHTNESS)
- {
- ftop=false;
- y=CHECKHEIGHT;
- break;
- }
- }
- }
- }
+ if (macontext->Video.Data.Plane[0][x]>BRIGHTNESS) fbottom=false;
}
- else
- {
- // "fast" method
- for (x=(macontext->Video.Info.Height-CHECKHEIGHT)*macontext->Video.Info.Width;
- x<macontext->Video.Info.Height*macontext->Video.Info.Width; x++)
- {
- if (macontext->Video.Data.Plane[0][x]>BRIGHTNESS) fbottom=false;
- }
- if (fbottom)
+ if (fbottom)
+ {
+ for (x=0; x<(macontext->Video.Info.Width*CHECKHEIGHT); x++)
{
- for (x=0; x<(macontext->Video.Info.Width*CHECKHEIGHT); x++)
- {
- if (macontext->Video.Data.Plane[0][x]>BRIGHTNESS) ftop=false;
- }
+ if (macontext->Video.Data.Plane[0][x]>BRIGHTNESS) ftop=false;
}
}
@@ -338,42 +478,61 @@ bool cMarkAdVideo::AspectRatioChange(MarkAdAspectRatio *a, MarkAdAspectRatio *b)
}
-
MarkAdMark *cMarkAdVideo::Process(int LastIFrame)
{
ResetMark();
if (!LastIFrame) return NULL;
- logo->Process(LastIFrame);
-
- if (macontext->State.ContentStarted)
+ int lret=logo->Process(LastIFrame);
+ if (lret!=0)
{
- int borderiframe;
- int hret=hborder->Process(LastIFrame,&borderiframe);
-
- if ((hret>0) && (borderiframe))
+ char *buf=NULL;
+ if (lret>0)
{
- char *buf=NULL;
- if (asprintf(&buf,"detected start of horiz. borders (%i)",borderiframe)!=-1)
+ if (asprintf(&buf,"detected logo start (%i)",LastIFrame)!=-1)
{
isyslog("markad [%i]: %s",recvnumber,buf);
- AddMark(borderiframe,buf);
+ AddMark(LastIFrame,buf);
free(buf);
}
}
-
- if ((hret<0) && (borderiframe))
+ else
{
- char *buf=NULL;
- if (asprintf(&buf,"detected stop of horiz. borders (%i)",borderiframe)!=-1)
+ if (asprintf(&buf,"detected logo stop (%i)",LastIFrame)!=-1)
{
isyslog("markad [%i]: %s",recvnumber,buf);
- AddMark(borderiframe,buf);
+ AddMark(LastIFrame,buf);
free(buf);
}
}
}
+
+ int borderiframe;
+ int hret=hborder->Process(LastIFrame,&borderiframe);
+
+ if ((hret>0) && (borderiframe))
+ {
+ char *buf=NULL;
+ if (asprintf(&buf,"detected start of horiz. borders (%i)",borderiframe)!=-1)
+ {
+ isyslog("markad [%i]: %s",recvnumber,buf);
+ AddMark(borderiframe,buf);
+ free(buf);
+ }
+ }
+
+ if ((hret<0) && (borderiframe))
+ {
+ char *buf=NULL;
+ if (asprintf(&buf,"detected stop of horiz. borders (%i)",borderiframe)!=-1)
+ {
+ isyslog("markad [%i]: %s",recvnumber,buf);
+ AddMark(borderiframe,buf);
+ free(buf);
+ }
+ }
+
if (AspectRatioChange(&macontext->Video.Info.AspectRatio,&aspectratio))
{
char *buf=NULL;