⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vfakeio.cxx

📁 sloedgy open sip stack source code
💻 CXX
📖 第 1 页 / 共 4 页
字号:


BOOL PVideoInputDevice_FakeVideo::GetFrameData(BYTE * buffer, PINDEX * bytesReturned)
{    
  frameTimeError += msBetweenFrames;

  PTime now;
  PTimeInterval delay = now - previousFrameTime;
  frameTimeError -= (int)delay.GetMilliSeconds();
  previousFrameTime = now;

  if (frameTimeError > 0) {
    PTRACE(6, "FakeVideo\t Sleep for " << frameTimeError << " milli seconds");
    PThread::Sleep(frameTimeError);
  }

  return GetFrameDataNoDelay(buffer, bytesReturned);
}

 
BOOL PVideoInputDevice_FakeVideo::GetFrameDataNoDelay(BYTE *destFrame, PINDEX * bytesReturned)
{
  grabCount++;

  // Make sure are NUM_PATTERNS cases here.
  switch(channelNumber){       
     case eMovingBlocks : 
       GrabMovingBlocksTestFrame(destFrame);
       break;
     case eMovingLine : 
       GrabMovingLineTestFrame(destFrame);
       break;
     case eBouncingBoxes :
       GrabBouncingBoxes(destFrame);
       break;
     case eBlankImage :
       GrabBlankImage(destFrame);
       break;
     case eOriginalMovingBlocks :
       GrabOriginalMovingBlocksFrame(destFrame);
       break;
     case eText :
       GrabTextVideoFrame(destFrame);
       break;
     case eNTSCTest :
       GrabNTSCTestFrame(destFrame);
       break;
     default :
       return FALSE;
  }

  if (NULL != converter) {
    if (!converter->Convert(destFrame, destFrame, bytesReturned))
      return FALSE;
  }

  if (bytesReturned != NULL)
    *bytesReturned = videoFrameSize;

  return TRUE;
}


void PVideoInputDevice_FakeVideo::FillRect(BYTE * frame,
                   int xPos, int initialYPos,
                   int rectWidth, int rectHeight,
                   int r, int g,  int b)
{
// PTRACE(0,"x,y is"<<xPos<<" "<<yPos<<" and size is "<<rectWidth<<" "<<rectHeight);

  //This routine fills a region of the video image with data. It is used as the central
  //point because one only has to add other image formats here.

  if (bytesPerPixel > 2) {
    for (int y = 0; y < rectHeight; y++) {
      BYTE * ptr = frame + (initialYPos+y)*scanLineWidth + xPos*bytesPerPixel;
      for (int x = 0; x < rectWidth; x++) {
        *ptr++ = (BYTE)r;
        *ptr++ = (BYTE)g;
        *ptr++ = (BYTE)b;
        if (bytesPerPixel > 3)
          *ptr++ = 0;
      }
    }
    return;
  }

  int yPos = initialYPos;

  int offset       = ( yPos * frameWidth ) + xPos;
  int colourOffset = ( (yPos * frameWidth) >> 2) + (xPos >> 1);

  int Y  =  ( 257 * r + 504 * g +  98 * b)/1000 + 16;
  int Cb =  (-148 * r - 291 * g + 439 * b)/1000 + 128;
  int Cr =  ( 439 * r - 368 * g -  71 * b)/1000 + 128;

  unsigned char * Yptr  = frame + offset;
  unsigned char * CbPtr = frame + (frameWidth * frameHeight) + colourOffset;
  unsigned char * CrPtr = frame + (frameWidth * frameHeight) + (frameWidth * frameHeight/4)  + colourOffset;

  int rr ;
  int halfRectWidth = rectWidth >> 1;
  int halfWidth     = frameWidth >> 1;
  
  for (rr = 0; rr < rectHeight;rr+=2) {
    memset(Yptr, Y, rectWidth);
    Yptr += frameWidth;
    memset(Yptr, Y, rectWidth);
    Yptr += frameWidth;

    memset(CbPtr, Cb, halfRectWidth);
    memset(CrPtr, Cr, halfRectWidth);

    CbPtr += halfWidth;
    CrPtr += halfWidth;
  }
}

void PVideoInputDevice_FakeVideo::GrabBouncingBoxes(BYTE *resFrame)
{
  FillRect(resFrame,
     0, 0, frameWidth, frameHeight, //Fill the whole frame with the colour.
     200,200,200); //a light grey colour.

  double t= (grabCount%50) -25 ;
  double h=  t*t*frameHeight*0.85/625;
  int    yBox = (int)h;
  yBox= (yBox>>1) * 2;  //yBox is even.
  
  int boxHeight= (int)(frameHeight*0.1);
  boxHeight= (boxHeight >>1) * 2;
  int boxWidth = (int)(frameWidth*0.1);
  boxWidth = (boxWidth >>1) * 2;

  FillRect(resFrame,
     frameWidth >> 2, yBox,  boxWidth, boxHeight,
           255, 0, 0); // Red Box.

  t= (grabCount%40) -20 ;
  h= t*t*frameHeight*0.85/400 ;
  yBox = (int)h;
  yBox= (yBox>>1) * 2;  //yBox is even.

  FillRect(resFrame,
           frameWidth>>1, yBox, boxWidth, boxHeight,
           0, 255, 0); // Green

  t= (grabCount%100) -50 ;
  h= t*t*frameHeight*0.85/2500;      
  yBox = (int)h;
  yBox= (yBox>>1) * 2;  //yBox is even.

  FillRect(resFrame,
           (frameWidth>>1) + (frameWidth>>2), yBox,  boxWidth, boxHeight,
           0, 0, 255); // Blue
}

void PVideoInputDevice_FakeVideo::GrabNTSCTestFrame(BYTE *resFrame)
{
  //  Test image # 1
  //  A static image is generated, consisting of a series of coloured block.
  //  Sample NTSC test frame is found at http://www.displaymate.com/patterns.html
  //
  static int row1[7][3] = {
    { 204, 204, 204 },   // 80% grey
    { 255, 255,   0 },   // yellow
    {   0, 255, 255 },   // cyan
    {   0, 255,   0 },   // green
    { 255,   0, 255 },   // magenta
    { 255,   0,   0 },   // red
    {   0,   0, 255 },   // blue
  };

  static int row2[7][3] = {
    {   0,   0, 255 },   // blue
    {  19,  19,  19 },   // black
    { 255,   0, 255 },   // magenta
    {  19,  19,  19 },   // black
    {   0, 255, 255 },   // cyan
    {  19,  19,  19 },   // black
    { 204, 204, 204 },   // grey
  };

  static int row3a[4][3] = {
    {   8,  62,  89 },   // I
    { 255, 255, 255 },   // white
    {  58,   0, 126 },   // +Q
    {  19,  19,  19 },   // black
  };

  static int row3b[3][3] = {
    {   0,   0,   0 },   // 3.5
    {  19,  19,  19 },   // 7.5
    {  38,  38,  38 },   // 11.5
  };

  static int row3c[3] = { 19,  19,  19 };

  int row1Height = (int)(0.66 * frameHeight);
  int row2Height = (int)((0.75 * frameHeight) - row1Height);
  row1Height = (row1Height>>1)*2;     //Require that height is even.
  row2Height = (row2Height>>1)*2;     
  int row3Height = frameHeight - row1Height - row2Height;

  int columns[8];
  PINDEX i;

  for(i=0;i<7;i++) {    
    columns[i]= i*frameWidth/7;
    columns[i]= (columns[i]>>1)*2;  // require that columns[i] is even.
  }
  columns[7] = frameWidth;


  // first row
  for (i = 0; i < 6; i++) 
    FillRect(resFrame,
             columns[i], 0, columns[i+1]-columns[i], row1Height, //x,y,w,h
             row1[i][0], row1[i][1], row1[i][2]); // rgb



  // second row
  for (i = 0; i < 7; i++) 
    FillRect(resFrame,
             columns[i], row1Height,  columns[i+1]-columns[i], row2Height, 
             row2[i][0], row2[i][1], row2[i][2]);

  // third row
  int columnBot[5];

  for (i=0; i<4; i++) {    
    columnBot[i]= i*columns[5]/4;
    columnBot[i] = 2 * (columnBot[i]>>1);
  }
  columnBot[4]= columns[5];

  for (i = 0; i < 4; i++) 
    FillRect(resFrame,
             columnBot[i],row1Height + row2Height, columnBot[i+1]-columnBot[i], row3Height, 
             row3a[i][0], row3a[i][1], row3a[i][2]);

  for (i=0; i<3; i++) {
    columnBot[i] = columns[4]+(i*frameWidth)/(7*3);
    columnBot[i] = 2 * (columnBot[i]>>1);       //Force even.
  }
  columnBot[3]= columns[5];

  for (i = 0; i < 3; i++) 
    FillRect(resFrame,
             columnBot[i], row1Height + row2Height, columnBot[i+1] - columnBot[i], row3Height,
             row3b[i][0], row3b[i][1], row3b[i][2]);

  FillRect(resFrame,
           columns[6], row1Height + row2Height, columns[7] - columns[6], row3Height, 
           row3c[0], row3c[1], row3c[2]);
}


void PVideoInputDevice_FakeVideo::GrabMovingBlocksTestFrame(BYTE * resFrame)
{
  // Test image # 2
  /*Brightness is set to alter, left to right.
  Colour component alters top to bottom.

  Image contains lots of high and low resolution areas.
  */
  unsigned wi,hi, colourIndex,colNo, boxSize;   

#define COL(b,x,y) ((b+x+y)%7)

  static int background[7][3] = {
    { 254, 254, 254 },   // white
    { 255, 255,   0 },   // yellow
    {   0, 255, 255 },   // cyan
    {   0, 255,   0 },   // green
    { 255,   0, 255 },   // magenta
    { 255,   0,   0 },   // red
    {   0,   0, 255 },   // blue
  };

  int columns[9];
  int heights[9];
  int offset;
  offset = (frameWidth >> 3) & 0xffe;

  for(wi = 0; wi < 8; wi++) 
    columns[wi] = wi * offset;
  columns[8] = frameWidth;

  offset = (frameHeight >> 3) & 0xffe;
  for(hi = 0; hi < 9; hi++) 
    heights[hi] = hi * offset;
  heights[8] = frameHeight;

  grabCount++;
  colourIndex = time(NULL);//time in seconds since last epoch.
  // Provides a difference if run on two ohphone sessions.
  colNo = (colourIndex / 10) % 7;   //Every 10 seconds, coloured background blocks move.

  for(hi = 0; hi < 8; hi++) //Fill the background in.
    for(wi = 0 ; wi < 8; wi++) {
      FillRect(resFrame,
               columns[wi], heights[hi], columns[wi + 1] - columns[wi], heights[hi + 1] - heights[hi],
               background[COL(colNo, wi, hi)][0], background[COL(colNo, wi, hi)][1], background[COL(colNo, wi, hi)][2]);
    }

    //Draw a black box rapidly moving down the left of the window.
    boxSize= frameHeight / 10;
    hi = ((3 * colourIndex) % (frameHeight-boxSize)) & 0xffe; //Make certain hi is even.
    FillRect(resFrame, 10, hi, boxSize, boxSize, 0, 0, 0); //Black Box.

    //Draw four parallel black lines, which move up the middle of the window.
    colourIndex = colourIndex / 3;     //Every three seconds, lines move.

    for(wi = 0; wi < 2; wi++) 
      columns[wi]= (((wi + 1)  * frameWidth) / 3) & 0xffe;// Force columns to be even.

    hi = colourIndex % ((frameHeight - 16) / 2);
    hi = (frameHeight - 16) - (hi * 2);     //hi is even, Lines move in opp. direction to box.

    unsigned yi;    
    for(yi = 0; yi < 4; yi++) 
      FillRect(resFrame,
               columns[0], hi+(yi * 4), columns[1] - columns[0], 2,
               0, 0, 0);
}


void PVideoInputDevice_FakeVideo::GrabMovingLineTestFrame(BYTE *resFrame)
{
  //  Test image # 3
  //  Faster image generation. Same every times system runs.
  //  Colours cycle through. Have a vertical lines style of pattern.
  //  There is a horizontal bar which moves down the screen .
  static int v=0;
  int r,g,b;

  v++;
  r = (200+v) & 255;
  g = (100+v) & 255;
  b = (000+v) & 255;

  FillRect(resFrame, 0, 0,frameWidth, frameHeight, r, g, b);

  int hi = (v % (frameHeight-2) >> 1) *2;
  FillRect(resFrame, 0, hi, frameWidth, 2, 0, 0, 0);
}

void PVideoInputDevice_FakeVideo::GrabBlankImage(BYTE *resFrame)
{
  // Change colour every second, cycle is:
  // black, red, green, yellow, blue, magenta, cyan, white
  int mask = grabCount/frameRate;
  FillRect(resFrame,
           0, 0, frameWidth, frameHeight, //Fill the whole frame with the colour.
           (mask&1) ? 255 : 0, // red
           (mask&2) ? 255 : 0, // green
           (mask&4) ? 255 : 0);//blue
}

void PVideoInputDevice_FakeVideo::GrabOriginalMovingBlocksFrame(BYTE *frame)
{
  unsigned wi,hi,colourIndex,colourNumber;
  int framesize = frameWidth*frameHeight;

  static int gCount=0;
  gCount++;

  colourIndex = gCount/10;
  colourNumber= (colourIndex/10)%7;   //Every 10 seconds, coloured background blocks move.

  for(hi=0; hi<frameHeight; hi++)               //slow moving group of lines going upwards.
    for(wi=0; wi<frameWidth; wi++) 
      if ( (wi>frameWidth/3)&&(wi<frameWidth*2/3)&&
        ( ((gCount+hi)%frameHeight)<16)&&
        ( (hi%4)<2)                     )
        frame[(hi*frameWidth)+wi] = 16;
      else
        frame[(hi*frameWidth)+wi] = (BYTE)(((colourNumber+((wi*7)/frameWidth))%7)*35+26);

  for(hi=1; hi<=frameHeight; hi++)                 //fast moving block going downwards.
    for(wi=frameWidth/9; wi<(2*frameWidth/9); wi++) 
      if(  (( (gCount*4)+hi)%frameHeight)<20)
        frame[((frameHeight-hi)*frameWidth)+wi] = 16;

  unsigned halfWidth  = frameWidth/2;
  unsigned halfHeight = frameHeight/2;
  for(hi=1; hi<halfHeight; hi++)  
    for(wi=0; wi<halfWidth; wi++)
      frame[framesize+(hi*halfWidth)+wi] = (BYTE)(((((hi*7)/halfHeight)+colourNumber)%7)*35+26);
}


void PVideoInputDevice_FakeVideo::GrabTextVideoFrame(BYTE *resFrame)
{
  PINDEX i, j;
  static PTime startTime;

  grabCount++;
  FillRect(resFrame,
           0, 0, frameWidth, frameHeight, //Fill the whole frame with the colour.
           200, 200, 200); //a light grey colour.


  if (textLine[0].GetLength() < 2) {
    PStringStream message;
    message << PProcess::Current().GetUserName() <<  " on " <<
               PProcess::Current().GetOSName() << ":" <<
               PProcess::Current().GetOSHardware();
    PINDEX nChars = message.GetLength();
    PVideoFont::LetterData *ld;

    for (j = 0; j < PVideoFont::MAX_L_HEIGHT; j++)
      textLine[j] = "";

    for (i = 0; i < (nChars + 2); i++){
      if (i >= nChars)
        ld = PVideoFont::GetLetterData(' ');
      else
        ld = PVideoFont::GetLetterData(message[i]);
      if (ld == NULL)
        continue;
      for (j = 0; j < PVideoFont::MAX_L_HEIGHT; j++)
        textLine[j] += ld->line[j] + PString(" ");
    }
  }

  PINDEX boxSize = (frameHeight / (PVideoFont::MAX_L_HEIGHT * 2) ) & 0xffe;
  int index = (int)((PTime() - startTime).GetMilliSeconds() / 300);

  PINDEX maxI = (frameWidth / boxSize) - 2;
  for (i = 0; i < maxI; i++)
    for (j = 0; j < PVideoFont::MAX_L_HEIGHT; j++) {
      PINDEX ii = (index + i) % textLine[0].GetLength();
      if (textLine[j][ii] != ' ')
        FillRect(resFrame,
                 (i + 1) * boxSize, (frameHeight / 3) + ((j + 1) * boxSize), //x,y start pos
                 boxSize, boxSize,                    //x,y dimension
                 250, 00, 00); //red box.
    }
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////


/**This class defines a NULL video output device.
   This will do precisely nothing with the output.
 */
class PVideoOutputDevice_NULLOutput : public PVideoOutputDevice
{
  PCLASSINFO(PVideoOutputDevice_NULLOutput, PVideoOutputDevice);

  public:
    /** Create a new video output device.
     */
    PVideoOutputDevice_NULLOutput();

    /**Get a list of all of the drivers available.
      */
    static PStringList GetOutputDeviceNames();

    virtual PStringList GetDeviceNames() const
      { return GetOutputDeviceNames(); }

    /**Open the device given the device name.
      */
    virtual BOOL Open(
      const PString & deviceName,   /// Device name to open
      BOOL startImmediate = TRUE    /// Immediately start device
    );

    /**Start the video device I/O.
      */
    BOOL Start();

    /**Stop the video device I/O capture.
      */
    BOOL Stop();

    /**Close the device.
      */
    virtual BOOL Close();

    /**Determine if the device is currently open.
      */
    virtual BOOL IsOpen();

    /**Get the maximum frame size in bytes.

       Note a particular device may be able to provide variable length
       frames (eg motion JPEG) so will be the maximum size of all frames.
      */
    virtual PINDEX GetMaxFrameBytes();

    /**Set a section of the output frame buffer.
      */
    virtual BOOL SetFrameData(
      unsigned x,
      unsigned y,
      unsigned width,
      unsigned height,
      const BYTE * data,
      BOOL endFrame = TRUE
    );

    /**Indicate frame may be displayed.
      */
    virtual BOOL EndFrame();
};

PCREATE_VIDOUTPUT_PLUGIN(NULLOutput);

///////////////////////////////////////////////////////////////////////////////
// PVideoOutputDevice_NULLOutput

PVideoOutputDevice_NULLOutput::PVideoOutputDevice_NULLOutput()
{
  deviceName = "NULL";
}


BOOL PVideoOutputDevice_NULLOutput::Open(const PString & /*deviceName*/,
                                  BOOL /*startImmediate*/)
{
  return TRUE;
}

BOOL PVideoOutputDevice_NULLOutput::Close()
{
  return TRUE;
}

BOOL PVideoOutputDevice_NULLOutput::Start()
{
  return TRUE;
}

BOOL PVideoOutputDevice_NULLOutput::Stop()
{
  return TRUE;
}

BOOL PVideoOutputDevice_NULLOutput::IsOpen()
{
  return TRUE;
}


PStringList PVideoOutputDevice_NULLOutput::GetOutputDeviceNames()
{
  PStringList list;
  list += "NULL";
  return list;
}


PINDEX PVideoOutputDevice_NULLOutput::GetMaxFrameBytes()
{
  return GetMaxFrameBytesConverted(CalculateFrameBytes(frameWidth, frameHeight, colourFormat));
}


BOOL PVideoOutputDevice_NULLOutput::SetFrameData(unsigned /*x*/, unsigned /*y*/,
                                          unsigned /*width*/, unsigned /*height*/,
                                          const BYTE * /*data*/,
                                          BOOL /*endFrame*/)
{
  return TRUE;
}


BOOL PVideoOutputDevice_NULLOutput::EndFrame()
{
  return TRUE;
}


// End Of File ///////////////////////////////////////////////////////////////

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -