home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 13 / AACD13.ISO / AACD / Graphics / PPT / pluginsrc / contrast / contrast.c next >
C/C++ Source or Header  |  1999-12-27  |  8KB  |  340 lines

  1. /*----------------------------------------------------------------------*/
  2. /*
  3.     PROJECT: ppt filters
  4.     MODULE : contrast
  5.  
  6.     PPT is (C) Janne Jalkanen 1995-1997.
  7.  
  8.     $Id: contrast.c,v 3.0 1999/12/27 21:20:25 jj Exp jj $
  9.  
  10. */
  11. /*----------------------------------------------------------------------*/
  12.  
  13. /*----------------------------------------------------------------------*/
  14. /* Includes */
  15.  
  16. #include <pptplugin.h>
  17.  
  18. #include <stdlib.h>
  19. #include "contrast.h"
  20.  
  21. /*----------------------------------------------------------------------*/
  22. /* Defines */
  23.  
  24. #define MYNAME      "Contrast"
  25.  
  26.  
  27.  
  28. /*----------------------------------------------------------------------*/
  29. /* Internal prototypes */
  30.  
  31.  
  32. /*----------------------------------------------------------------------*/
  33. /* Global variables */
  34.  
  35. const struct TagItem MyTagArray[] = {
  36.     PPTX_Name,          (ULONG)MYNAME,
  37.     /* Other tags go here */
  38.     PPTX_Author,        (ULONG)"Janne Jalkanen, 1996-1999",
  39.     PPTX_InfoTxt,       (ULONG)"Provides contrast correction for the image",
  40.     PPTX_ColorSpaces,   CSF_RGB|CSF_GRAYLEVEL|CSF_ARGB,
  41.     PPTX_RexxTemplate,  (ULONG)"AMOUNT",
  42.     PPTX_ReqPPTVersion, 4,
  43.     PPTX_SupportsGetArgs, TRUE,
  44.     TAG_END, 0L
  45. };
  46.  
  47. struct Library *MathIeeeDoubBasBase = NULL;
  48.  
  49. /*----------------------------------------------------------------------*/
  50. /* Code */
  51.  
  52. #ifdef __SASC
  53. /* Disable SAS/C control-c handling. */
  54. void __regargs __chkabort(void) {}
  55. void __regargs _CXBRK(void) {}
  56. #include <dos.h>
  57. #endif
  58.  
  59. #if defined( __GNUC__ )
  60. const BYTE LibName[]="contrast.effect";
  61. const BYTE LibIdString[]="contrast.effect 1.6";
  62. const UWORD LibVersion=1;
  63. const UWORD LibRevision=6;
  64. ADD2LIST(LIBEffectInquire,__FuncTable__,22);
  65. ADD2LIST(LIBEffectExec,__FuncTable__,22);
  66. /* The following two definitions are only required
  67.    if you link with libinitr */
  68. ADD2LIST(LIBEffectInquire,__LibTable__,22);
  69. ADD2LIST(LIBEffectExec,__LibTable__,22);
  70.  
  71. /* Make GNU C specific declarations. __UtilityBase is
  72.    required for the libnix integer multiplication */
  73. struct ExecBase *SysBase = NULL;
  74. struct Library *__UtilityBase = NULL;
  75. #endif
  76.  
  77. /*
  78.     These build the histogram transformation tables required.
  79. */
  80. void Contrast( FRAME *frame, int correction, UBYTE *dest, struct PPTBase *PPTBase )
  81. {
  82.     int i;
  83.     float c, dx, dy, b;
  84.  
  85.     c = correction * 128 / 1000.0;
  86.  
  87.     if( correction <= 0 ) {
  88.         c  = -c;
  89.         dx = 256.0;
  90.         dy = 256.0 - 2.0 * c;
  91.         b  = c;
  92.     } else {
  93.         dx = 256.0 - 2.0 * c;
  94.         if( dx == 0.0 ) dx = 1.0;
  95.         dy = 256.0;
  96.         b  = 128.0 - (256.0*128.0)/dx;
  97.     }
  98.  
  99.     for(i = 0; i < 256; i++) {
  100.         float val;
  101.         val = (dy * i) / dx + b;
  102.         if(val > 255.0) val = 255.0; else if(val < 0.0) val = 0.0;
  103.         dest[i] = (UBYTE)val;
  104.     }
  105. }
  106.  
  107. #ifdef DEBUG_MODE
  108. void DumpTable( UBYTE *table )
  109. {
  110.     int i;
  111.  
  112.     for(i = 0; i < 256; i++) {
  113.         PDebug("%3d -> %3d     ",i,table[i]);
  114.         if(i % 4 == 3) PDebug("\n");
  115.     }
  116. }
  117. #else
  118. #define DumpTable(x)
  119. #endif
  120.  
  121. /*
  122.     Main dispatcher
  123. */
  124. int DoModify( FRAME *frame, ULONG which, int howmuch, struct PPTBase *PPTBase )
  125. {
  126.     UWORD row;
  127.     UBYTE T[256];
  128.     int res = PERR_OK;
  129.     WORD pixelsize = frame->pix->components;
  130.     BOOL alpha = 0;
  131.  
  132.     /*
  133.      *  Select the transform function.
  134.      */
  135.  
  136.     Contrast( frame, howmuch, T, PPTBase );
  137.  
  138.     DumpTable( T );
  139.  
  140.     InitProgress( frame, "Correcting contrast...", frame->selbox.MinY, frame->selbox.MaxY );
  141.  
  142.     if( frame->pix->colorspace == CS_ARGB ) alpha = 1;
  143.  
  144.     for(row = frame->selbox.MinY; row < frame->selbox.MaxY; row++ ) {
  145.         ROWPTR cp, dcp;
  146.         WORD col;
  147.  
  148.         cp = GetPixelRow( frame, row );
  149.         dcp = cp + (frame->selbox.MinX) * pixelsize;
  150.         if(Progress(frame,row)) {
  151.             res = PERR_BREAK;
  152.             goto quit;
  153.         }
  154.  
  155.         for( col = frame->selbox.MinX; col < frame->selbox.MaxX; col++) {
  156.             UBYTE comp;
  157.  
  158.             if( alpha ) dcp++;
  159.  
  160.             for(comp = 0; comp < pixelsize-alpha; comp++) {
  161.                 *dcp = T[*dcp];
  162.                 dcp++;
  163.             }
  164.         }
  165.  
  166.         PutPixelRow( frame, row, cp );
  167.     }
  168. quit:
  169.     return res;
  170. }
  171.  
  172. ASM ULONG MyHookFunc( REG(a0) struct Hook *hook,
  173.                       REG(a2) Object *obj,
  174.                       REG(a1) struct ARUpdateMsg *msg )
  175. {
  176.     /*
  177.      *  Set up A4 so that globals still work
  178.      */
  179.  
  180.     PUTDS( (long) hook->h_Data );
  181.  
  182.     DoModify( msg->aum_Frame, 0, msg->aum_Values[0], msg->aum_PPTBase );
  183.  
  184.     return ARR_REDRAW;
  185. }
  186.  
  187.  
  188. LIBINIT
  189. {
  190. #if defined(__GNUC__)
  191.     SysBase = SYSBASE();
  192.  
  193.     if( NULL == (__UtilityBase = OpenLibrary("utility.library",37L))) {
  194.         return 1L;
  195.     }
  196.     __initlibraries();
  197.  
  198. #endif
  199.     if(MathIeeeDoubBasBase = OpenLibrary( "mathieeedoubbas.library", 0L ) ) {
  200.         return 0;
  201.     }
  202.     return 1;
  203. }
  204.  
  205. LIBCLEANUP
  206. {
  207.     if(MathIeeeDoubBasBase) CloseLibrary( MathIeeeDoubBasBase );
  208. #if defined(__GNUC__)
  209.     __exitlibraries();
  210.     if( __UtilityBase ) CloseLibrary(__UtilityBase);
  211. #endif
  212. }
  213.  
  214. EFFECTINQUIRE(attr,PPTBase,EffectBase)
  215. {
  216.     return TagData( attr, MyTagArray );
  217. }
  218.  
  219. PERROR
  220. ParseRexxArgs(ULONG *args, int *contrast, struct PPTBase *PPTBase )
  221. {
  222.     if( args[0] )
  223.         *contrast = atof( (STRPTR)args[0] ) * 1000;
  224.     else
  225.         *contrast = 0;
  226.  
  227.     return PERR_OK;
  228. }
  229.  
  230. PERROR DoGUI( FRAME *frame, int *contrast, struct PPTBase *PPTBase )
  231. {
  232.     struct Hook pwhook = { {0}, MyHookFunc, 0L, NULL };
  233.     struct TagItem bright[] = { AROBJ_Value, NULL,
  234.                                 ARFLOAT_Min, -1000,
  235.                                 ARFLOAT_Default, 0,
  236.                                 ARFLOAT_Max, 1000,
  237.                                 AROBJ_PreviewHook, NULL,
  238.                                 ARFLOAT_Divisor, 1000,
  239.                                 ARFLOAT_FormatString, (ULONG) "%.4f",
  240.                                 TAG_END };
  241.  
  242.     struct TagItem win[] = { AR_FloatObject, NULL,
  243.                              AR_Text, (ULONG)"Choose contrast change",
  244.                              AR_HelpNode, (ULONG)"effects.guide/Contrast",
  245.                              TAG_END };
  246.     FRAME *pwframe;
  247.     PERROR res;
  248.  
  249.     pwhook.h_Data = (void *)GETDS(); // Save register
  250.  
  251.     bright[0].ti_Data = (ULONG) contrast;
  252.     bright[2].ti_Data = (ULONG) *contrast;
  253.     bright[4].ti_Data = (ULONG) &pwhook;
  254.     win[0].ti_Data = (ULONG) bright;
  255.  
  256.     pwframe = ObtainPreviewFrame( frame, NULL );
  257.  
  258.     if( ( res = AskReqA( frame, win )) != PERR_OK) {
  259.         SetErrorCode( frame, res );
  260.         if( pwframe ) ReleasePreviewFrame( pwframe );
  261.         return NULL;
  262.     }
  263.     if( pwframe ) ReleasePreviewFrame( pwframe );
  264.  
  265.     return res;
  266. }
  267.  
  268.  
  269. EFFECTEXEC(frame,tags,PPTBase,EffectBase)
  270. {
  271.     int res;
  272.     int contrast = 0;
  273.     ULONG *args;
  274.     int *dta;
  275.  
  276.     D(bug(MYNAME": Exec()\n"));
  277.  
  278.     if( dta = (int *)GetOptions(MYNAME) ) {
  279.         contrast = *dta;
  280.     }
  281.  
  282.     args = (ULONG *)TagData( PPTX_RexxArgs, tags );
  283.  
  284.     /*
  285.      *  Check if we got the brightness?
  286.      */
  287.  
  288.     if( args ) {
  289.         ParseRexxArgs( args, &contrast, PPTBase );
  290.     } else {
  291.         res = DoGUI( frame, &contrast, PPTBase );
  292.     }
  293.  
  294.     /*
  295.      *  Check that the argument is correct and call the modify routine.
  296.      */
  297.  
  298.     if( contrast < -1000 || contrast > 1000 ) {
  299.         SetErrorCode( frame, PERR_INVALIDARGS );
  300.         return NULL;
  301.     } else {
  302.         DoModify( frame, 0, contrast, PPTBase );
  303.     }
  304.  
  305.     PutOptions(MYNAME,&contrast,sizeof(int));
  306.  
  307.     return frame;
  308. }
  309.  
  310. EFFECTGETARGS(frame,tags,PPTBase,EffectBase)
  311. {
  312.     PERROR res;
  313.     ULONG *args;
  314.     STRPTR buffer;
  315.     int contrast = 0, *dta;
  316.  
  317.     if( dta = (int *)GetOptions(MYNAME) ) {
  318.         contrast = *dta;
  319.     }
  320.  
  321.     buffer = (STRPTR) TagData( PPTX_ArgBuffer, tags );
  322.  
  323.     if( args = (ULONG *) TagData( PPTX_RexxArgs, tags ) ) {
  324.         res = ParseRexxArgs( args, &contrast, PPTBase );
  325.     }
  326.  
  327.     res = DoGUI( frame, &contrast, PPTBase );
  328.  
  329.     if( res == PERR_OK ) {
  330.         SPrintF( buffer, "AMOUNT %f", contrast/1000.0f );
  331.     }
  332.  
  333.     return res;
  334. }
  335.  
  336. /*----------------------------------------------------------------------*/
  337. /*                            END OF CODE                               */
  338. /*----------------------------------------------------------------------*/
  339.  
  340.