decorate.c

Go to the documentation of this file.
00001 /*
00002 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00003 %                                                                             %
00004 %                                                                             %
00005 %                                                                             %
00006 %            DDDD   EEEEE   CCCC   OOO   RRRR    AAA   TTTTT  EEEEE           %
00007 %            D   D  E      C      O   O  R   R  A   A    T    E               %
00008 %            D   D  EEE    C      O   O  RRRR   AAAAA    T    EEE             %
00009 %            D   D  E      C      O   O  R R    A   A    T    E               %
00010 %            DDDD   EEEEE   CCCC   OOO   R  R   A   A    T    EEEEE           %
00011 %                                                                             %
00012 %                                                                             %
00013 %                     MagickCore Image Decoration Methods                     %
00014 %                                                                             %
00015 %                                Software Design                              %
00016 %                                  John Cristy                                %
00017 %                                   July 1992                                 %
00018 %                                                                             %
00019 %                                                                             %
00020 %  Copyright 1999-2009 ImageMagick Studio LLC, a non-profit organization      %
00021 %  dedicated to making software imaging solutions freely available.           %
00022 %                                                                             %
00023 %  You may not use this file except in compliance with the License.  You may  %
00024 %  obtain a copy of the License at                                            %
00025 %                                                                             %
00026 %    http://www.imagemagick.org/script/license.php                            %
00027 %                                                                             %
00028 %  Unless required by applicable law or agreed to in writing, software        %
00029 %  distributed under the License is distributed on an "AS IS" BASIS,          %
00030 %  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   %
00031 %  See the License for the specific language governing permissions and        %
00032 %  limitations under the License.                                             %
00033 %                                                                             %
00034 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00035 %
00036 %
00037 %
00038 */
00039 
00040 /*
00041   Include declarations.
00042 */
00043 #include "magick/studio.h"
00044 #include "magick/cache-view.h"
00045 #include "magick/color-private.h"
00046 #include "magick/colorspace-private.h"
00047 #include "magick/composite.h"
00048 #include "magick/decorate.h"
00049 #include "magick/exception.h"
00050 #include "magick/exception-private.h"
00051 #include "magick/image.h"
00052 #include "magick/memory_.h"
00053 #include "magick/monitor.h"
00054 #include "magick/monitor-private.h"
00055 #include "magick/pixel-private.h"
00056 #include "magick/quantum.h"
00057 #include "magick/transform.h"
00058 
00059 /*
00060   Define declarations.
00061 */
00062 #define AccentuateModulate  ScaleCharToQuantum(80)
00063 #define HighlightModulate  ScaleCharToQuantum(125)
00064 #define ShadowModulate  ScaleCharToQuantum(135)
00065 #define DepthModulate  ScaleCharToQuantum(185)
00066 #define TroughModulate  ScaleCharToQuantum(110)
00067 
00068 /*
00069 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00070 %                                                                             %
00071 %                                                                             %
00072 %                                                                             %
00073 %   B o r d e r I m a g e                                                     %
00074 %                                                                             %
00075 %                                                                             %
00076 %                                                                             %
00077 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00078 %
00079 %  BorderImage() surrounds the image with a border of the color defined by
00080 %  the bordercolor member of the image structure.  The width and height
00081 %  of the border are defined by the corresponding members of the border_info
00082 %  structure.
00083 %
00084 %  The format of the BorderImage method is:
00085 %
00086 %      Image *BorderImage(const Image *image,const RectangleInfo *border_info,
00087 %        ExceptionInfo *exception)
00088 %
00089 %  A description of each parameter follows:
00090 %
00091 %    o image: the image.
00092 %
00093 %    o border_info:  Define the width and height of the border.
00094 %
00095 %    o exception: return any errors or warnings in this structure.
00096 %
00097 */
00098 MagickExport Image *BorderImage(const Image *image,
00099   const RectangleInfo *border_info,ExceptionInfo *exception)
00100 {
00101   Image
00102     *border_image,
00103     *clone_image;
00104 
00105   FrameInfo
00106     frame_info;
00107 
00108   assert(image != (const Image *) NULL);
00109   assert(image->signature == MagickSignature);
00110   if (image->debug != MagickFalse)
00111     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
00112   assert(border_info != (RectangleInfo *) NULL);
00113   frame_info.width=image->columns+(border_info->width << 1);
00114   frame_info.height=image->rows+(border_info->height << 1);
00115   frame_info.x=(long) border_info->width;
00116   frame_info.y=(long) border_info->height;
00117   frame_info.inner_bevel=0;
00118   frame_info.outer_bevel=0;
00119   clone_image=CloneImage(image,0,0,MagickTrue,exception);
00120   if (clone_image == (Image *) NULL)
00121     return((Image *) NULL);
00122   clone_image->matte_color=image->border_color;
00123   border_image=FrameImage(clone_image,&frame_info,exception);
00124   clone_image=DestroyImage(clone_image);
00125   if (border_image != (Image *) NULL)
00126     border_image->matte_color=image->matte_color;
00127   return(border_image);
00128 }
00129 
00130 /*
00131 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00132 %                                                                             %
00133 %                                                                             %
00134 %                                                                             %
00135 %   F r a m e I m a g e                                                       %
00136 %                                                                             %
00137 %                                                                             %
00138 %                                                                             %
00139 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00140 %
00141 %  FrameImage() adds a simulated three-dimensional border around the image.
00142 %  The color of the border is defined by the matte_color member of image.
00143 %  Members width and height of frame_info specify the border width of the
00144 %  vertical and horizontal sides of the frame.  Members inner and outer
00145 %  indicate the width of the inner and outer shadows of the frame.
00146 %
00147 %  The format of the FrameImage method is:
00148 %
00149 %      Image *FrameImage(const Image *image,const FrameInfo *frame_info,
00150 %        ExceptionInfo *exception)
00151 %
00152 %  A description of each parameter follows:
00153 %
00154 %    o image: the image.
00155 %
00156 %    o frame_info: Define the width and height of the frame and its bevels.
00157 %
00158 %    o exception: return any errors or warnings in this structure.
00159 %
00160 */
00161 MagickExport Image *FrameImage(const Image *image,const FrameInfo *frame_info,
00162   ExceptionInfo *exception)
00163 {
00164 #define FrameImageTag  "Frame/Image"
00165 
00166   Image
00167     *frame_image;
00168 
00169   long
00170     progress,
00171     y;
00172 
00173   MagickBooleanType
00174     status;
00175 
00176   MagickPixelPacket
00177     accentuate,
00178     border,
00179     highlight,
00180     interior,
00181     matte,
00182     shadow,
00183     trough;
00184 
00185   register long
00186     x;
00187 
00188   unsigned long
00189     bevel_width,
00190     height,
00191     width;
00192 
00193   CacheView
00194     *image_view,
00195     *frame_view;
00196 
00197   /*
00198     Check frame geometry.
00199   */
00200   assert(image != (Image *) NULL);
00201   assert(image->signature == MagickSignature);
00202   if (image->debug != MagickFalse)
00203     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
00204   assert(frame_info != (FrameInfo *) NULL);
00205   if ((frame_info->outer_bevel < 0) || (frame_info->inner_bevel < 0))
00206     ThrowImageException(OptionError,"FrameIsLessThanImageSize");
00207   bevel_width=(unsigned long) (frame_info->outer_bevel+frame_info->inner_bevel);
00208   width=frame_info->width-frame_info->x-bevel_width;
00209   height=frame_info->height-frame_info->y-bevel_width;
00210   if ((width < image->columns) || (height < image->rows))
00211     ThrowImageException(OptionError,"FrameIsLessThanImageSize");
00212   /*
00213     Initialize framed image attributes.
00214   */
00215   frame_image=CloneImage(image,frame_info->width,frame_info->height,MagickTrue,
00216     exception);
00217   if (frame_image == (Image *) NULL)
00218     return((Image *) NULL);
00219   if (SetImageStorageClass(frame_image,DirectClass) == MagickFalse)
00220     {
00221       InheritException(exception,&frame_image->exception);
00222       frame_image=DestroyImage(frame_image);
00223       return((Image *) NULL);
00224     }
00225   if (frame_image->matte_color.opacity != OpaqueOpacity)
00226     frame_image->matte=MagickTrue;
00227   frame_image->page=image->page;
00228   if ((image->page.width != 0) && (image->page.height != 0))
00229     {
00230       frame_image->page.width+=frame_image->columns-image->columns;
00231       frame_image->page.height+=frame_image->rows-image->rows;
00232     }
00233   /*
00234     Initialize 3D effects color.
00235   */
00236   GetMagickPixelPacket(frame_image,&interior);
00237   SetMagickPixelPacket(frame_image,&image->border_color,(IndexPacket *) NULL,
00238     &interior);
00239   GetMagickPixelPacket(frame_image,&matte);
00240   matte.colorspace=RGBColorspace;
00241   SetMagickPixelPacket(frame_image,&image->matte_color,(IndexPacket *) NULL,
00242     &matte);
00243   GetMagickPixelPacket(frame_image,&border);
00244   border.colorspace=RGBColorspace;
00245   SetMagickPixelPacket(frame_image,&image->border_color,(IndexPacket *) NULL,
00246     &border);
00247   GetMagickPixelPacket(frame_image,&accentuate);
00248   accentuate.red=(MagickRealType) (QuantumScale*((QuantumRange-
00249     AccentuateModulate)*matte.red+(QuantumRange*AccentuateModulate)));
00250   accentuate.green=(MagickRealType) (QuantumScale*((QuantumRange-
00251     AccentuateModulate)*matte.green+(QuantumRange*AccentuateModulate)));
00252   accentuate.blue=(MagickRealType) (QuantumScale*((QuantumRange-
00253     AccentuateModulate)*matte.blue+(QuantumRange*AccentuateModulate)));
00254   accentuate.opacity=matte.opacity;
00255   GetMagickPixelPacket(frame_image,&highlight);
00256   highlight.red=(MagickRealType) (QuantumScale*((QuantumRange-
00257     HighlightModulate)*matte.red+(QuantumRange*HighlightModulate)));
00258   highlight.green=(MagickRealType) (QuantumScale*((QuantumRange-
00259     HighlightModulate)*matte.green+(QuantumRange*HighlightModulate)));
00260   highlight.blue=(MagickRealType) (QuantumScale*((QuantumRange-
00261     HighlightModulate)*matte.blue+(QuantumRange*HighlightModulate)));
00262   highlight.opacity=matte.opacity;
00263   GetMagickPixelPacket(frame_image,&shadow);
00264   shadow.red=QuantumScale*matte.red*ShadowModulate;
00265   shadow.green=QuantumScale*matte.green*ShadowModulate;
00266   shadow.blue=QuantumScale*matte.blue*ShadowModulate;
00267   shadow.opacity=matte.opacity;
00268   GetMagickPixelPacket(frame_image,&trough);
00269   trough.red=QuantumScale*matte.red*TroughModulate;
00270   trough.green=QuantumScale*matte.green*TroughModulate;
00271   trough.blue=QuantumScale*matte.blue*TroughModulate;
00272   trough.opacity=matte.opacity;
00273   if (image->colorspace == CMYKColorspace)
00274     {
00275       ConvertRGBToCMYK(&interior);
00276       ConvertRGBToCMYK(&matte);
00277       ConvertRGBToCMYK(&border);
00278       ConvertRGBToCMYK(&accentuate);
00279       ConvertRGBToCMYK(&highlight);
00280       ConvertRGBToCMYK(&shadow);
00281       ConvertRGBToCMYK(&trough);
00282     }
00283   status=MagickTrue;
00284   progress=0;
00285   image_view=AcquireCacheView(image);
00286   frame_view=AcquireCacheView(frame_image);
00287   height=(unsigned long) (frame_info->outer_bevel+(frame_info->y-bevel_width)+
00288     frame_info->inner_bevel);
00289   if (height != 0)
00290     {
00291       register IndexPacket
00292         *__restrict frame_indexes;
00293 
00294       register long
00295         x;
00296 
00297       register PixelPacket
00298         *__restrict q;
00299 
00300       /*
00301         Draw top of ornamental border.
00302       */
00303       q=QueueCacheViewAuthenticPixels(frame_view,0,0,frame_image->columns,
00304         height,exception);
00305       frame_indexes=GetCacheViewAuthenticIndexQueue(frame_view);
00306       if (q != (PixelPacket *) NULL)
00307         {
00308           /*
00309             Draw top of ornamental border.
00310           */
00311           for (y=0; y < (long) frame_info->outer_bevel; y++)
00312           {
00313             for (x=0; x < (long) (frame_image->columns-y); x++)
00314             {
00315               if (x < y)
00316                 SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00317               else
00318                 SetPixelPacket(frame_image,&accentuate,q,frame_indexes);
00319               q++;
00320               frame_indexes++;
00321             }
00322             for ( ; x < (long) frame_image->columns; x++)
00323             {
00324               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00325               q++;
00326               frame_indexes++;
00327             }
00328           }
00329           for (y=0; y < (long) (frame_info->y-bevel_width); y++)
00330           {
00331             for (x=0; x < (long) frame_info->outer_bevel; x++)
00332             {
00333               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00334               q++;
00335               frame_indexes++;
00336             }
00337             width=frame_image->columns-2*frame_info->outer_bevel;
00338             for (x=0; x < (long) width; x++)
00339             {
00340               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00341               q++;
00342               frame_indexes++;
00343             }
00344             for (x=0; x < (long) frame_info->outer_bevel; x++)
00345             {
00346               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00347               q++;
00348               frame_indexes++;
00349             }
00350           }
00351           for (y=0; y < (long) frame_info->inner_bevel; y++)
00352           {
00353             for (x=0; x < (long) frame_info->outer_bevel; x++)
00354             {
00355               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00356               q++;
00357               frame_indexes++;
00358             }
00359             for (x=0; x < (long) (frame_info->x-bevel_width); x++)
00360             {
00361               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00362               q++;
00363               frame_indexes++;
00364             }
00365             width=image->columns+((unsigned long) frame_info->inner_bevel << 1)-
00366               y;
00367             for (x=0; x < (long) width; x++)
00368             {
00369               if (x < y)
00370                 SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00371               else
00372                 SetPixelPacket(frame_image,&trough,q,frame_indexes);
00373               q++;
00374               frame_indexes++;
00375             }
00376             for ( ; x < (long) (image->columns+2*frame_info->inner_bevel); x++)
00377             {
00378               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00379               q++;
00380               frame_indexes++;
00381             }
00382             width=frame_info->width-frame_info->x-image->columns-bevel_width;
00383             for (x=0; x < (long) width; x++)
00384             {
00385               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00386               q++;
00387               frame_indexes++;
00388             }
00389             for (x=0; x < (long) frame_info->outer_bevel; x++)
00390             {
00391               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00392               q++;
00393               frame_indexes++;
00394             }
00395           }
00396           (void) SyncCacheViewAuthenticPixels(frame_view,exception);
00397         }
00398     }
00399   /*
00400     Draw sides of ornamental border.
00401   */
00402 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00403   #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
00404 #endif
00405   for (y=0; y < (long) image->rows; y++)
00406   {
00407     register IndexPacket
00408       *__restrict frame_indexes;
00409 
00410     register long
00411       x;
00412 
00413     register PixelPacket
00414       *__restrict q;
00415 
00416     /*
00417       Initialize scanline with matte color.
00418     */
00419     if (status == MagickFalse)
00420       continue;
00421     q=QueueCacheViewAuthenticPixels(frame_view,0,frame_info->y+y,
00422       frame_image->columns,1,exception);
00423     if (q == (PixelPacket *) NULL)
00424       {
00425         status=MagickFalse;
00426         continue;
00427       }
00428     frame_indexes=GetCacheViewAuthenticIndexQueue(frame_view);
00429     for (x=0; x < (long) frame_info->outer_bevel; x++)
00430     {
00431       SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00432       q++;
00433       frame_indexes++;
00434     }
00435     for (x=0; x < (long) (frame_info->x-bevel_width); x++)
00436     {
00437       SetPixelPacket(frame_image,&matte,q,frame_indexes);
00438       q++;
00439       frame_indexes++;
00440     }
00441     for (x=0; x < (long) frame_info->inner_bevel; x++)
00442     {
00443       SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00444       q++;
00445       frame_indexes++;
00446     }
00447     /*
00448       Set frame interior to interior color.
00449     */
00450     if ((image->compose != CopyCompositeOp) &&
00451         ((image->compose != OverCompositeOp) || (image->matte != MagickFalse)))
00452       for (x=0; x < (long) image->columns; x++)
00453       {
00454         SetPixelPacket(frame_image,&interior,q,frame_indexes);
00455         q++;
00456         frame_indexes++;
00457       }
00458     else
00459       {
00460         register const IndexPacket
00461           *indexes;
00462 
00463         register const PixelPacket
00464           *p;
00465 
00466         p=GetCacheViewVirtualPixels(image_view,0,y,image->columns,1,exception);
00467         if (p == (const PixelPacket *) NULL)
00468           {
00469             status=MagickFalse;
00470             continue;
00471           }
00472         indexes=GetCacheViewVirtualIndexQueue(image_view);
00473         (void) CopyMagickMemory(q,p,image->columns*sizeof(*p));
00474         if ((image->colorspace == CMYKColorspace) &&
00475             (frame_image->colorspace == CMYKColorspace))
00476           {
00477             (void) CopyMagickMemory(frame_indexes,indexes,image->columns*
00478               sizeof(*indexes));
00479             frame_indexes+=image->columns;
00480           }
00481         q+=image->columns;
00482       }
00483     for (x=0; x < (long) frame_info->inner_bevel; x++)
00484     {
00485       SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00486       q++;
00487       frame_indexes++;
00488     }
00489     width=frame_info->width-frame_info->x-image->columns-bevel_width;
00490     for (x=0; x < (long) width; x++)
00491     {
00492       SetPixelPacket(frame_image,&matte,q,frame_indexes);
00493       q++;
00494       frame_indexes++;
00495     }
00496     for (x=0; x < (long) frame_info->outer_bevel; x++)
00497     {
00498       SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00499       q++;
00500       frame_indexes++;
00501     }
00502     if (SyncCacheViewAuthenticPixels(frame_view,exception) == MagickFalse)
00503       status=MagickFalse;
00504     if (image->progress_monitor != (MagickProgressMonitor) NULL)
00505       {
00506         MagickBooleanType
00507           proceed;
00508 
00509 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00510   #pragma omp critical (MagickCore_FrameImage)
00511 #endif
00512         proceed=SetImageProgress(image,FrameImageTag,progress++,image->rows);
00513         if (proceed == MagickFalse)
00514           status=MagickFalse;
00515       }
00516   }
00517   height=(unsigned long) (frame_info->inner_bevel+frame_info->height-
00518     frame_info->y-image->rows-bevel_width+frame_info->outer_bevel);
00519   if (height != 0)
00520     {
00521       register IndexPacket
00522         *__restrict frame_indexes;
00523 
00524       register long
00525         x;
00526 
00527       register PixelPacket
00528         *__restrict q;
00529 
00530       /*
00531         Draw bottom of ornamental border.
00532       */
00533       q=QueueCacheViewAuthenticPixels(frame_view,0,(long) (frame_image->rows-
00534         height),frame_image->columns,height,exception);
00535       if (q != (PixelPacket *) NULL)
00536         {
00537           /*
00538             Draw bottom of ornamental border.
00539           */
00540           frame_indexes=GetCacheViewAuthenticIndexQueue(frame_view);
00541           for (y=frame_info->inner_bevel-1; y >= 0; y--)
00542           {
00543             for (x=0; x < (long) frame_info->outer_bevel; x++)
00544             {
00545               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00546               q++;
00547               frame_indexes++;
00548             }
00549             for (x=0; x < (long) (frame_info->x-bevel_width); x++)
00550             {
00551               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00552               q++;
00553               frame_indexes++;
00554             }
00555             for (x=0; x < y; x++)
00556             {
00557               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00558               q++;
00559               frame_indexes++;
00560             }
00561             for ( ; x < (long) (image->columns+2*frame_info->inner_bevel); x++)
00562             {
00563               if (x >= (long) (image->columns+2*frame_info->inner_bevel-y))
00564                 SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00565               else
00566                 SetPixelPacket(frame_image,&accentuate,q,frame_indexes);
00567               q++;
00568               frame_indexes++;
00569             }
00570             width=frame_info->width-frame_info->x-image->columns-bevel_width;
00571             for (x=0; x < (long) width; x++)
00572             {
00573               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00574               q++;
00575               frame_indexes++;
00576             }
00577             for (x=0; x < (long) frame_info->outer_bevel; x++)
00578             {
00579               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00580               q++;
00581               frame_indexes++;
00582             }
00583           }
00584           height=frame_info->height-frame_info->y-image->rows-bevel_width;
00585           for (y=0; y < (long) height; y++)
00586           {
00587             for (x=0; x < (long) frame_info->outer_bevel; x++)
00588             {
00589               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00590               q++;
00591               frame_indexes++;
00592             }
00593             width=frame_image->columns-2*frame_info->outer_bevel;
00594             for (x=0; x < (long) width; x++)
00595             {
00596               SetPixelPacket(frame_image,&matte,q,frame_indexes);
00597               q++;
00598               frame_indexes++;
00599             }
00600             for (x=0; x < (long) frame_info->outer_bevel; x++)
00601             {
00602               SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00603               q++;
00604               frame_indexes++;
00605             }
00606           }
00607           for (y=frame_info->outer_bevel-1; y >= 0; y--)
00608           {
00609             for (x=0; x < y; x++)
00610             {
00611               SetPixelPacket(frame_image,&highlight,q,frame_indexes);
00612               q++;
00613               frame_indexes++;
00614             }
00615             for ( ; x < (long) frame_image->columns; x++)
00616             {
00617               if (x >= (long) (frame_image->columns-y))
00618                 SetPixelPacket(frame_image,&shadow,q,frame_indexes);
00619               else
00620                 SetPixelPacket(frame_image,&trough,q,frame_indexes);
00621               q++;
00622               frame_indexes++;
00623             }
00624           }
00625           (void) SyncCacheViewAuthenticPixels(frame_view,exception);
00626         }
00627     }
00628   frame_view=DestroyCacheView(frame_view);
00629   image_view=DestroyCacheView(image_view);
00630   if ((image->compose != CopyCompositeOp) &&
00631       ((image->compose != OverCompositeOp) || (image->matte != MagickFalse)))
00632     {
00633       x=(long) (frame_info->outer_bevel+(frame_info->x-bevel_width)+
00634         frame_info->inner_bevel);
00635       y=(long) (frame_info->outer_bevel+(frame_info->y-bevel_width)+
00636         frame_info->inner_bevel);
00637       (void) CompositeImage(frame_image,image->compose,image,x,y);
00638     }
00639   return(frame_image);
00640 }
00641 
00642 /*
00643 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00644 %                                                                             %
00645 %                                                                             %
00646 %                                                                             %
00647 %   R a i s e I m a g e                                                       %
00648 %                                                                             %
00649 %                                                                             %
00650 %                                                                             %
00651 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
00652 %
00653 %  RaiseImage() creates a simulated three-dimensional button-like effect
00654 %  by lightening and darkening the edges of the image.  Members width and
00655 %  height of raise_info define the width of the vertical and horizontal
00656 %  edge of the effect.
00657 %
00658 %  The format of the RaiseImage method is:
00659 %
00660 %      MagickBooleanType RaiseImage(const Image *image,
00661 %        const RectangleInfo *raise_info,const MagickBooleanType raise)
00662 %
00663 %  A description of each parameter follows:
00664 %
00665 %    o image: the image.
00666 %
00667 %    o raise_info: Define the width and height of the raise area.
00668 %
00669 %    o raise: A value other than zero creates a 3-D raise effect,
00670 %      otherwise it has a lowered effect.
00671 %
00672 */
00673 MagickExport MagickBooleanType RaiseImage(Image *image,
00674   const RectangleInfo *raise_info,const MagickBooleanType raise)
00675 {
00676 #define AccentuateFactor  ScaleCharToQuantum(135)
00677 #define HighlightFactor  ScaleCharToQuantum(190)
00678 #define ShadowFactor  ScaleCharToQuantum(190)
00679 #define RaiseImageTag  "Raise/Image"
00680 #define TroughFactor  ScaleCharToQuantum(135)
00681 
00682   ExceptionInfo
00683     *exception;
00684 
00685   long
00686     progress,
00687     y;
00688 
00689   MagickBooleanType
00690     status;
00691 
00692   Quantum
00693     foreground,
00694     background;
00695 
00696   CacheView
00697     *image_view;
00698 
00699   assert(image != (Image *) NULL);
00700   assert(image->signature == MagickSignature);
00701   if (image->debug != MagickFalse)
00702     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
00703   assert(raise_info != (RectangleInfo *) NULL);
00704   if ((image->columns <= (raise_info->width << 1)) ||
00705       (image->rows <= (raise_info->height << 1)))
00706     ThrowBinaryException(OptionError,"ImageSizeMustExceedBevelWidth",
00707       image->filename);
00708   foreground=(Quantum) QuantumRange;
00709   background=(Quantum) 0;
00710   if (raise == MagickFalse)
00711     {
00712       foreground=(Quantum) 0;
00713       background=(Quantum) QuantumRange;
00714     }
00715   if (SetImageStorageClass(image,DirectClass) == MagickFalse)
00716     return(MagickFalse);
00717   /*
00718     Raise image.
00719   */
00720   status=MagickTrue;
00721   progress=0;
00722   exception=(&image->exception);
00723   image_view=AcquireCacheView(image);
00724 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00725   #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
00726 #endif
00727   for (y=0; y < (long) raise_info->height; y++)
00728   {
00729     register long
00730       x;
00731 
00732     register PixelPacket
00733       *__restrict q;
00734 
00735     if (status == MagickFalse)
00736       continue;
00737     q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
00738     if (q == (PixelPacket *) NULL)
00739       {
00740         status=MagickFalse;
00741         continue;
00742       }
00743     for (x=0; x < y; x++)
00744     {
00745       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*
00746         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00747         HighlightFactor)));
00748       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00749         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00750         HighlightFactor)));
00751       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00752         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00753         HighlightFactor)));
00754       q++;
00755     }
00756     for ( ; x < (long) (image->columns-y); x++)
00757     {
00758       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*
00759         AccentuateFactor+(MagickRealType) foreground*(QuantumRange-
00760         AccentuateFactor)));
00761       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00762         AccentuateFactor+(MagickRealType) foreground*(QuantumRange-
00763         AccentuateFactor)));
00764       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00765         AccentuateFactor+(MagickRealType) foreground*(QuantumRange-
00766         AccentuateFactor)));
00767       q++;
00768     }
00769     for ( ; x < (long) image->columns; x++)
00770     {
00771       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*ShadowFactor+
00772         (MagickRealType) background*(QuantumRange-ShadowFactor)));
00773       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00774         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00775       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00776         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00777       q++;
00778     }
00779     if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
00780       status=MagickFalse;
00781     if (image->progress_monitor != (MagickProgressMonitor) NULL)
00782       {
00783         MagickBooleanType
00784           proceed;
00785 
00786         proceed=SetImageProgress(image,RaiseImageTag,progress++,image->rows);
00787         if (proceed == MagickFalse)
00788           status=MagickFalse;
00789       }
00790   }
00791 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00792   #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
00793 #endif
00794   for (y=(long) raise_info->height; y < (long) (image->rows-raise_info->height); y++)
00795   {
00796     register long
00797       x;
00798 
00799     register PixelPacket
00800       *__restrict q;
00801 
00802     if (status == MagickFalse)
00803       continue;
00804     q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
00805     if (q == (PixelPacket *) NULL)
00806       {
00807         status=MagickFalse;
00808         continue;
00809       }
00810     for (x=0; x < (long) raise_info->width; x++)
00811     {
00812       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*
00813         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00814         HighlightFactor)));
00815       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00816         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00817         HighlightFactor)));
00818       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00819         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00820         HighlightFactor)));
00821       q++;
00822     }
00823     for ( ; x < (long) (image->columns-raise_info->width); x++)
00824       q++;
00825     for ( ; x < (long) image->columns; x++)
00826     {
00827       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*ShadowFactor+
00828         (MagickRealType) background*(QuantumRange-ShadowFactor)));
00829       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00830         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00831       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00832         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00833       q++;
00834     }
00835     if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
00836       status=MagickFalse;
00837     if (image->progress_monitor != (MagickProgressMonitor) NULL)
00838       {
00839         MagickBooleanType
00840           proceed;
00841 
00842         proceed=SetImageProgress(image,RaiseImageTag,progress++,image->rows);
00843         if (proceed == MagickFalse)
00844           status=MagickFalse;
00845       }
00846   }
00847 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00848   #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
00849 #endif
00850   for (y=(long) (image->rows-raise_info->height); y < (long) image->rows; y++)
00851   {
00852     register long
00853       x;
00854 
00855     register PixelPacket
00856       *__restrict q;
00857 
00858     if (status == MagickFalse)
00859       continue;
00860     q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
00861     if (q == (PixelPacket *) NULL)
00862       {
00863         status=MagickFalse;
00864         continue;
00865       }
00866     for (x=0; x < (long) (image->rows-y); x++)
00867     {
00868       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*
00869         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00870         HighlightFactor)));
00871       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00872         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00873         HighlightFactor)));
00874       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00875         HighlightFactor+(MagickRealType) foreground*(QuantumRange-
00876         HighlightFactor)));
00877       q++;
00878     }
00879     for ( ; x < (long) (image->columns-(image->rows-y)); x++)
00880     {
00881       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*TroughFactor+
00882         (MagickRealType) background*(QuantumRange-TroughFactor)));
00883       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00884         TroughFactor+(MagickRealType) background*(QuantumRange-TroughFactor)));
00885       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00886         TroughFactor+(MagickRealType) background*(QuantumRange-TroughFactor)));
00887       q++;
00888     }
00889     for ( ; x < (long) image->columns; x++)
00890     {
00891       q->red=RoundToQuantum(QuantumScale*((MagickRealType) q->red*ShadowFactor+
00892         (MagickRealType) background*(QuantumRange-ShadowFactor)));
00893       q->green=RoundToQuantum(QuantumScale*((MagickRealType) q->green*
00894         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00895       q->blue=RoundToQuantum(QuantumScale*((MagickRealType) q->blue*
00896         ShadowFactor+(MagickRealType) background*(QuantumRange-ShadowFactor)));
00897       q++;
00898     }
00899     if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
00900       status=MagickFalse;
00901     if (image->progress_monitor != (MagickProgressMonitor) NULL)
00902       {
00903         MagickBooleanType
00904           proceed;
00905 
00906 #if defined(MAGICKCORE_OPENMP_SUPPORT)
00907   #pragma omp critical (MagickCore_RaiseImage)
00908 #endif
00909         proceed=SetImageProgress(image,RaiseImageTag,progress++,image->rows);
00910         if (proceed == MagickFalse)
00911           status=MagickFalse;
00912       }
00913   }
00914   image_view=DestroyCacheView(image_view);
00915   return(status);
00916 }

Generated on 19 Nov 2009 for MagickCore by  doxygen 1.6.1