1 /* 2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 3 % % 4 % % 5 % % 6 % PPPP L AAA SSSSS M M AAA % 7 % P P L A A SS MM MM A A % 8 % PPPP L AAAAA SSS M M M AAAAA % 9 % P L A A SS M M A A % 10 % P LLLLL A A SSSSS M M A A % 11 % % 12 % % 13 % Read a Plasma Image. % 14 % % 15 % Software Design % 16 % Cristy % 17 % July 1992 % 18 % % 19 % % 20 % Copyright 1999-2016 ImageMagick Studio LLC, a non-profit organization % 21 % dedicated to making software imaging solutions freely available. % 22 % % 23 % You may not use this file except in compliance with the License. You may % 24 % obtain a copy of the License at % 25 % % 26 % http://www.imagemagick.org/script/license.php % 27 % % 28 % Unless required by applicable law or agreed to in writing, software % 29 % distributed under the License is distributed on an "AS IS" BASIS, % 30 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. % 31 % See the License for the specific language governing permissions and % 32 % limitations under the License. % 33 % % 34 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 35 % 36 % 37 */ 38 39 /* 41 Include declarations. 42 */ 43 #include "MagickCore/studio.h" 44 #include "MagickCore/blob.h" 45 #include "MagickCore/blob-private.h" 46 #include "MagickCore/cache.h" 47 #include "MagickCore/channel.h" 48 #include "MagickCore/constitute.h" 49 #include "MagickCore/exception.h" 50 #include "MagickCore/exception-private.h" 51 #include "MagickCore/fx.h" 52 #include "MagickCore/image.h" 53 #include "MagickCore/image-private.h" 54 #include "MagickCore/list.h" 55 #include "MagickCore/magick.h" 56 #include "MagickCore/memory_.h" 57 #include "MagickCore/monitor.h" 58 #include "MagickCore/monitor-private.h" 59 #include "MagickCore/pixel-accessor.h" 60 #include "MagickCore/random_.h" 61 #include "MagickCore/random-private.h" 62 #include "MagickCore/signature-private.h" 63 #include "MagickCore/quantum-private.h" 64 #include "MagickCore/static.h" 65 #include "MagickCore/string_.h" 66 #include "MagickCore/module.h" 67 68 /* 70 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 71 % % 72 % % 73 % % 74 % R e a d P L A S M A I m a g e % 75 % % 76 % % 77 % % 78 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 79 % 80 % ReadPlasmaImage creates a plasma fractal image. The image is 81 % initialized to the X server color as specified by the filename. 82 % 83 % The format of the ReadPlasmaImage method is: 84 % 85 % Image *ReadPlasmaImage(const ImageInfo *image_info, 86 % ExceptionInfo *exception) 87 % 88 % A description of each parameter follows: 89 % 90 % o image_info: the image info. 91 % 92 % o exception: return any errors or warnings in this structure. 93 % 94 */ 95 96 static inline void PlasmaPixel(Image *image,RandomInfo *random_info,double x, 97 double y,ExceptionInfo *exception) 98 { 99 register Quantum 100 *q; 101 102 q=GetAuthenticPixels(image,(ssize_t) ceil(x-0.5),(ssize_t) ceil(y-0.5),1,1, 103 exception); 104 if (q == (Quantum *) NULL) 105 return; 106 SetPixelRed(image,ScaleShortToQuantum((unsigned short) (65535.0* 107 GetPseudoRandomValue(random_info)+0.5)),q); 108 SetPixelGreen(image,ScaleShortToQuantum((unsigned short) (65535.0* 109 GetPseudoRandomValue(random_info)+0.5)),q); 110 SetPixelBlue(image,ScaleShortToQuantum((unsigned short) (65535.0* 111 GetPseudoRandomValue(random_info)+0.5)),q); 112 (void) SyncAuthenticPixels(image,exception); 113 } 114 115 static Image *ReadPlasmaImage(const ImageInfo *image_info, 116 ExceptionInfo *exception) 117 { 118 Image 119 *image; 120 121 ImageInfo 122 *read_info; 123 124 MagickBooleanType 125 status; 126 127 register ssize_t 128 x; 129 130 register Quantum 131 *q; 132 133 register size_t 134 i; 135 136 SegmentInfo 137 segment_info; 138 139 size_t 140 depth, 141 max_depth; 142 143 ssize_t 144 y; 145 146 /* 147 Recursively apply plasma to the image. 148 */ 149 read_info=CloneImageInfo(image_info); 150 SetImageInfoBlob(read_info,(void *) NULL,0); 151 (void) FormatLocaleString(read_info->filename,MagickPathExtent, 152 "gradient:%s",image_info->filename); 153 image=ReadImage(read_info,exception); 154 read_info=DestroyImageInfo(read_info); 155 if (image == (Image *) NULL) 156 return((Image *) NULL); 157 (void) SetImageStorageClass(image,DirectClass,exception); 158 for (y=0; y < (ssize_t) image->rows; y++) 159 { 160 q=GetAuthenticPixels(image,0,y,image->columns,1,exception); 161 if (q == (Quantum *) NULL) 162 break; 163 for (x=0; x < (ssize_t) image->columns; x++) 164 { 165 SetPixelAlpha(image,QuantumRange/2,q); 166 q+=GetPixelChannels(image); 167 } 168 if (SyncAuthenticPixels(image,exception) == MagickFalse) 169 break; 170 } 171 segment_info.x1=0; 172 segment_info.y1=0; 173 segment_info.x2=(double) image->columns-1; 174 segment_info.y2=(double) image->rows-1; 175 if (LocaleCompare(image_info->filename,"fractal") == 0) 176 { 177 RandomInfo 178 *random_info; 179 180 /* 181 Seed pixels before recursion. 182 */ 183 (void) SetImageColorspace(image,sRGBColorspace,exception); 184 random_info=AcquireRandomInfo(); 185 PlasmaPixel(image,random_info,segment_info.x1,segment_info.y1,exception); 186 PlasmaPixel(image,random_info,segment_info.x1,(segment_info.y1+ 187 segment_info.y2)/2,exception); 188 PlasmaPixel(image,random_info,segment_info.x1,segment_info.y2,exception); 189 PlasmaPixel(image,random_info,(segment_info.x1+segment_info.x2)/2, 190 segment_info.y1,exception); 191 PlasmaPixel(image,random_info,(segment_info.x1+segment_info.x2)/2, 192 (segment_info.y1+segment_info.y2)/2,exception); 193 PlasmaPixel(image,random_info,(segment_info.x1+segment_info.x2)/2, 194 segment_info.y2,exception); 195 PlasmaPixel(image,random_info,segment_info.x2,segment_info.y1,exception); 196 PlasmaPixel(image,random_info,segment_info.x2,(segment_info.y1+ 197 segment_info.y2)/2,exception); 198 PlasmaPixel(image,random_info,segment_info.x2,segment_info.y2,exception); 199 random_info=DestroyRandomInfo(random_info); 200 } 201 i=(size_t) MagickMax(image->columns,image->rows)/2; 202 for (max_depth=0; i != 0; max_depth++) 203 i>>=1; 204 for (depth=1; ; depth++) 205 { 206 if (PlasmaImage(image,&segment_info,0,depth,exception) != MagickFalse) 207 break; 208 status=SetImageProgress(image,LoadImageTag,(MagickOffsetType) depth, 209 max_depth); 210 if (status == MagickFalse) 211 break; 212 } 213 return(GetFirstImageInList(image)); 214 } 215 216 /* 218 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 219 % % 220 % % 221 % % 222 % R e g i s t e r P L A S M A I m a g e % 223 % % 224 % % 225 % % 226 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 227 % 228 % RegisterPLASMAImage() adds attributes for the Plasma image format to 229 % the list of supported formats. The attributes include the image format 230 % tag, a method to read and/or write the format, whether the format 231 % supports the saving of more than one frame to the same file or blob, 232 % whether the format supports native in-memory I/O, and a brief 233 % description of the format. 234 % 235 % The format of the RegisterPLASMAImage method is: 236 % 237 % size_t RegisterPLASMAImage(void) 238 % 239 */ 240 ModuleExport size_t RegisterPLASMAImage(void) 241 { 242 MagickInfo 243 *entry; 244 245 entry=AcquireMagickInfo("PLASMA","PLASMA","Plasma fractal image"); 246 entry->decoder=(DecodeImageHandler *) ReadPlasmaImage; 247 entry->flags^=CoderAdjoinFlag; 248 entry->format_type=ImplicitFormatType; 249 (void) RegisterMagickInfo(entry); 250 entry=AcquireMagickInfo("PLASMA","FRACTAL","Plasma fractal image"); 251 entry->decoder=(DecodeImageHandler *) ReadPlasmaImage; 252 entry->flags^=CoderAdjoinFlag; 253 entry->format_type=ImplicitFormatType; 254 (void) RegisterMagickInfo(entry); 255 return(MagickImageCoderSignature); 256 } 257 258 /* 260 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 261 % % 262 % % 263 % % 264 % U n r e g i s t e r P L A S M A I m a g e % 265 % % 266 % % 267 % % 268 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 269 % 270 % UnregisterPLASMAImage() removes format registrations made by the 271 % PLASMA module from the list of supported formats. 272 % 273 % The format of the UnregisterPLASMAImage method is: 274 % 275 % UnregisterPLASMAImage(void) 276 % 277 */ 278 ModuleExport void UnregisterPLASMAImage(void) 279 { 280 (void) UnregisterMagickInfo("FRACTAL"); 281 (void) UnregisterMagickInfo("PLASMA"); 282 } 283