home *** CD-ROM | disk | FTP | other *** search
/ PC Welt 2001 September / PC-WELT 9-2001.ISO / software / hw / brennen / flask_src.exe / PostProcessing.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  2000-06-02  |  8.9 KB  |  342 lines

  1. /* 
  2.  *  PostProcessing.cpp 
  3.  *
  4.  *    Copyright (C) Alberto Vigata - January 2000 - ultraflask@yahoo.com
  5.  *
  6.  *  This file is part of FlasKMPEG, a free MPEG to MPEG/AVI converter
  7.  *    
  8.  *  FlasKMPEG is free software; you can redistribute it and/or modify
  9.  *  it under the terms of the GNU General Public License as published by
  10.  *  the Free Software Foundation; either version 2, or (at your option)
  11.  *  any later version.
  12.  *   
  13.  *  FlasKMPEG is distributed in the hope that it will be useful,
  14.  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  15.  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  16.  *  GNU General Public License for more details.
  17.  *   
  18.  *  You should have received a copy of the GNU General Public License
  19.  *  along with GNU Make; see the file COPYING.  If not, write to
  20.  *  the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 
  21.  *
  22.  */
  23.  
  24. #include <windows.h>
  25. #include "flaskmpeg.h"
  26. #include ".\resizer\vbitmap.h"
  27. #include ".\resizer\resizer.h"
  28. #include ".\Video\Deinterlacer\Deinterlacer.h"
  29. #include ".\postprocessing.h"
  30.  
  31. struct TPostRun{
  32.     int             cropWidthFlag;
  33.     int             cropHeightFlag;
  34.     Pixel32      *buffer;
  35.     VBitmap      temp;
  36.     VBitmap      deinterlacer_output;
  37.     Pixel32      *deinterlacer_output_data;
  38.  
  39. } PostRun;
  40.  
  41. #include ".\Video\VideoWrapper.h"
  42. #include "subpic\subpic.h"
  43. extern VideoWrapper *myVideo;
  44.  
  45. //Post processing functions
  46. int PostProcessingStart(VBitmap *source, VBitmap *dest, TPPost *pp){
  47.     
  48.  
  49.     if( !source || !dest  ||  !pp )
  50.         return 0;
  51.     
  52.     PostRun.cropWidthFlag  = 0;
  53.     PostRun.cropHeightFlag = 0;
  54.     PostRun.buffer         = NULL;
  55.     dest->offset = 0;
  56.     // init resizer
  57.     PrepareResizer(pp->resWidth, pp->resHeight, pp->doAR, pp->iDAR, pp->filterMode, source);
  58.  
  59.     if(pp->deinterlace)
  60.     {
  61.         TDeinterlacerConfig config;
  62.         config.blend    = pp->blend_fields;
  63.         config.threshold= pp->threshold;
  64.  
  65.         // Start deinterlacer
  66.         StartDeinterlacer(source->w, source->h, &config);
  67.         PostRun.deinterlacer_output_data = new Pixel32[source->w*source->h];
  68.         PostRun.deinterlacer_output.init( PostRun.deinterlacer_output_data
  69.                                         , source->w
  70.                                         , source->h
  71.                                         , 32);
  72.         PostRun.deinterlacer_output.AlignTo4();
  73.     }
  74.  
  75.     if( pp->crop )
  76.         if(pp->cropHeight < pp->resHeight )
  77.             PostRun.cropHeightFlag = 1;
  78.  
  79.     // prepare buffer if crop width
  80.     if( pp->crop )
  81.         if(pp->cropWidth < pp->resWidth){
  82.             if( !(PostRun.buffer = (Pixel32 *)malloc(pp->resWidth*pp->resHeight*4)) )
  83.                 return 0;
  84.             PostRun.cropWidthFlag=1;
  85.         }
  86.  
  87.     return 1;
  88. }
  89.  
  90. int PostProcess(VBitmap *source_bmp, VBitmap *dest, TPPost *pp){
  91.     int w,h,diff,firstline, width, height;
  92.     VBitmap *source;
  93.     Pixel32 *src, *dst;
  94.  
  95.     if( !source_bmp || !dest  ||  !pp )
  96.         return 0;
  97.  
  98.     if(pp->deinterlace){
  99.         DeInterlace(source_bmp, &PostRun.deinterlacer_output);
  100.         source = &PostRun.deinterlacer_output;
  101.     }
  102.     else
  103.         source = source_bmp;
  104.  
  105.     subpic_apply(source, (double)pp->myClock/27000.0);
  106.  
  107.     // Resize
  108.     if(PostRun.cropWidthFlag){
  109.         PostRun.temp.init(PostRun.buffer, pp->resWidth, pp->resHeight, 32);
  110.         ResizerRun( source, &PostRun.temp);
  111.     }
  112.     else if(PostRun.cropHeightFlag){
  113.         // Run resizer over dest->data
  114.         PostRun.temp.init(dest->data, pp->resWidth, pp->resHeight, 32);
  115.         ResizerRun( source, &PostRun.temp);
  116.     }
  117.     else
  118.         ResizerRun( source, dest);
  119.     
  120.     // Crop
  121.     if( pp->crop ){
  122.         if( PostRun.cropHeightFlag )            //Height cropping
  123.             dest->offset = (pp->resHeight - pp->cropTopOffset - pp->cropHeight ) * pp->resWidth;
  124.         if( PostRun.cropWidthFlag  ){
  125.             // Width or Width & Height cropping. Resized image is at PostRun.temp
  126.             dest->offset=0;
  127.             h = pp->cropHeight;
  128.  
  129.             firstline = pp->resHeight - pp->cropTopOffset;
  130.             diff      = pp->cropLeftOffset + (pp->resWidth -pp->cropWidth - pp->cropLeftOffset);
  131.             dst       = (Pixel32 *)dest->data + pp->cropWidth * pp->cropHeight -1;
  132.             src       = PostRun.temp.data + pp->cropLeftOffset + (firstline - 1)*pp->resWidth + pp->cropWidth - 1;
  133.  
  134.  
  135.             do{
  136.  
  137.                 w   = pp->cropWidth;
  138.                 do{
  139.                     *dst-- = *src--;
  140.                 }while(--w);
  141.                 src = src - diff;
  142.             }while(--h);
  143.  
  144.  
  145.         }
  146.     }
  147.     else
  148.         dest->offset = 0;       // No cropping
  149.  
  150.  
  151.     // Letterbox
  152.     width  = pp->crop ? pp->cropWidth  : pp->resWidth;
  153.     height = pp->crop ? pp->cropHeight : pp->resHeight;
  154.  
  155.     if(pp->letterbox){
  156.         //Bottom bar
  157.         if (pp->letterboxBottom>0){
  158.             h = pp->letterboxBottom;
  159.             dst = dest->Address();
  160.             do {
  161.                 w = width;
  162.                 do {
  163.                     *dst++ = 0;
  164.                 } while(--w);
  165.             } while(--h);
  166.         }
  167.  
  168.         //Top bar
  169.  
  170.         if (pp->letterboxTop>0){
  171.             h = pp->letterboxTop;
  172.             // Point to last pixel
  173.             dst = dest->Address() + width * height - 1;
  174.             do {
  175.                 w = width;
  176.                 do {
  177.                     *dst-- = 0;
  178.                 } while(--w);
  179.             } while(--h);
  180.         }
  181.  
  182.         // Left Bar
  183.         if (pp->letterboxLeft >0 ){
  184.             h = height;
  185.             do {
  186.                 // Point to first pixel of last row
  187.                 w = pp->letterboxLeft;
  188.                 dst = dest->Address() + (h-1) * width;
  189.                 do {
  190.                     *dst++ = 0;
  191.                 } while(--w);
  192.             } while(--h);
  193.         }
  194.  
  195.         // Right Bar
  196.         if (pp->letterboxRight >0 ){
  197.             h = height;
  198.             do {
  199.                 w = pp->letterboxRight;
  200.                 // Point to last pixel
  201.                 dst = dest->Address() + h * width - 1;
  202.                 do {
  203.                     *dst-- = 0;
  204.                 } while(--w);
  205.             } while(--h);
  206.         }
  207.     }
  208.     // That was it
  209.  
  210.     return 1;
  211. }
  212.  
  213. int PostProcessingStop(TPPost *pp){
  214.  
  215.     UnPrepareResizer();
  216.     // Free horizontal crop buffer if necessary
  217.     if(PostRun.cropWidthFlag)
  218.         if(PostRun.buffer){
  219.             free(PostRun.buffer);
  220.             PostRun.buffer =NULL;
  221.         }
  222.     if(pp->deinterlace)
  223.     {
  224.         StopDeinterlacer();
  225.         delete [] PostRun.deinterlacer_output_data;
  226.     }
  227.  
  228.  
  229.     return 0;
  230. }
  231.  
  232.  
  233. // Auxiliary Post processing functions
  234.  
  235. // Fix absurd post processing settings
  236. void FixPPostSettings(TPPost *pp){
  237.  
  238.         if(pp->cropWidth>pp->resWidth)
  239.             pp->cropWidth  = pp->resWidth;
  240.         if(pp->cropHeight > pp->resHeight)
  241.             pp->cropHeight = pp->resHeight;
  242.  
  243. }
  244.  
  245. int CheckVideoParameters(TPPost *pp){
  246.     int w,h;
  247.     
  248.     FixPPostSettings(pp);
  249.     // Image dimension settings
  250.     if( (pp->cropHeight%16 != 0) || (pp->cropWidth%16 != 0) )
  251.         return 0;
  252.     if( (pp->resWidth%16 != 0) || (pp->resHeight%16 != 0) )
  253.         return 0;
  254.  
  255.     //Crop Checkings
  256.     // Crop widht&height must be less than input image resolution
  257.     if( pp->crop && (pp->cropHeight > pp->resHeight) )
  258.         return 0;
  259.     if( pp->crop && (pp->cropWidth  > pp->resWidth) )
  260.         return 0;
  261.     if( pp->crop && ((pp->cropTopOffset + pp->cropHeight) > pp->resHeight)  )
  262.         return 0;
  263.     if( pp->crop && ((pp->cropLeftOffset + pp->cropWidth) > pp->resWidth)  )
  264.         return 0;
  265.  
  266.     if( (pp->cropHeight < 0) || (pp->cropWidth < 0) )
  267.         return 0;
  268.     if( pp->crop && ((pp->cropTopOffset<0) ||  (pp->cropTopOffset > pp->cropHeight-16)) )
  269.         return 0;
  270.     if( pp->crop && ((pp->cropLeftOffset<0) ||  (pp->cropLeftOffset > pp->cropWidth-16)) )
  271.         return 0;
  272.     
  273.     // image size
  274.     if( pp->resWidth > 1024 || pp->resHeight > 1024)
  275.         return 0;
  276.  
  277.     // Letterboxing
  278.     w = pp->crop ? pp->cropWidth  : pp->resWidth;
  279.     h = pp->crop ? pp->cropHeight : pp->resHeight;
  280.  
  281.     if( pp->letterbox && (pp->letterboxLeft>w || pp->letterboxRight >w
  282.                        || pp->letterboxTop >h || pp->letterboxBottom>h))
  283.         return 0;
  284.     if( pp->letterbox && (pp->letterboxLeft<0 || pp->letterboxRight <0
  285.                        || pp->letterboxTop <0 || pp->letterboxBottom<0))
  286.         return 0;
  287.  
  288.  
  289.     return 1;
  290. }
  291.  
  292. void SetPPostConfig( TConfig *c, TPPost *pp){
  293.  
  294.     c->options.crop           =   pp->crop;
  295.     c->options.cropWidth      =   pp->cropWidth;
  296.     c->options.cropHeight     =   pp->cropHeight;
  297.     c->options.cropTopOffset  =   pp->cropTopOffset;
  298.     c->options.cropLeftOffset =   pp->cropLeftOffset;
  299.  
  300.     c->options.letterbox      =   pp->letterbox;
  301.     c->options.letterboxBottom=   pp->letterboxBottom;
  302.     c->options.letterboxTop   =   pp->letterboxTop;
  303.     c->options.letterboxLeft  =   pp->letterboxLeft;
  304.     c->options.letterboxRight =   pp->letterboxRight;
  305.  
  306.     c->options.InterpolatedWidth   = pp->resWidth;
  307.     c->options.InterpolatedHeight  = pp->resHeight;
  308.     c->options.filter              = pp->filterMode;
  309.     c->options.keepAspect          = pp->doAR;
  310.  
  311.     c->options.deinterlace = pp->deinterlace;
  312.     c->options.blend = pp->blend_fields;
  313.     c->options.threshold = pp->threshold;
  314. }
  315.  
  316. void GetPPostConfig( TConfig *c, TPPost *pp){
  317.     
  318.     pp->crop          =  c->options.crop;
  319.     pp->cropWidth     =  c->options.cropWidth;
  320.     pp->cropHeight    =  c->options.cropHeight;
  321.     pp->cropTopOffset =  c->options.cropTopOffset;
  322.     pp->cropLeftOffset=  c->options.cropLeftOffset;
  323.  
  324.  
  325.     pp->letterbox       =  c->options.letterbox;
  326.     pp->letterboxBottom =  c->options.letterboxBottom;
  327.     pp->letterboxTop    =  c->options.letterboxTop;
  328.     pp->letterboxLeft   =  c->options.letterboxLeft;
  329.     pp->letterboxRight  =  c->options.letterboxRight;
  330.     
  331.     pp->resWidth   = c->options.InterpolatedWidth ;
  332.     pp->resHeight  = c->options.InterpolatedHeight;
  333.     pp->filterMode = c->options.filter;
  334.     pp->doAR       = c->options.keepAspect;
  335.  
  336.     pp->deinterlace  = c->options.deinterlace;
  337.     pp->blend_fields = c->options.blend;
  338.     pp->threshold    = c->options.threshold;
  339.  
  340. }
  341.  
  342.