• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 %                                                                             %
4 %                                                                             %
5 %                                                                             %
6 %                            TTTTT  TTTTT  FFFFF                              %
7 %                              T      T    F                                  %
8 %                              T      T    FFF                                %
9 %                              T      T    F                                  %
10 %                              T      T    F                                  %
11 %                                                                             %
12 %                                                                             %
13 %             Return A Preview For A TrueType or Postscript Font              %
14 %                                                                             %
15 %                              Software Design                                %
16 %                                   Cristy                                    %
17 %                                 July 1992                                   %
18 %                                                                             %
19 %                                                                             %
20 %  Copyright 1999-2021 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 %    https://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 /*
40   Include declarations.
41 */
42 #include "MagickCore/studio.h"
43 #include "MagickCore/blob.h"
44 #include "MagickCore/blob-private.h"
45 #include "MagickCore/draw.h"
46 #include "MagickCore/exception.h"
47 #include "MagickCore/exception-private.h"
48 #include "MagickCore/image.h"
49 #include "MagickCore/image-private.h"
50 #include "MagickCore/list.h"
51 #include "MagickCore/magick.h"
52 #include "MagickCore/memory_.h"
53 #include "MagickCore/quantum-private.h"
54 #include "MagickCore/resource_.h"
55 #include "MagickCore/static.h"
56 #include "MagickCore/string_.h"
57 #include "MagickCore/module.h"
58 #include "MagickCore/type.h"
59 #include "MagickCore/utility.h"
60 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
61 #include <ft2build.h>
62 #if defined(FT_FREETYPE_H)
63 #  include FT_FREETYPE_H
64 #else
65 #  include <freetype/freetype.h>
66 #endif
67 #endif
68 
69 /*
70 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
71 %                                                                             %
72 %                                                                             %
73 %                                                                             %
74 %   I s P F A                                                                 %
75 %                                                                             %
76 %                                                                             %
77 %                                                                             %
78 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
79 %
80 %  IsPFA()() returns MagickTrue if the image format type, identified by the
81 %  magick string, is PFA.
82 %
83 %  The format of the IsPFA method is:
84 %
85 %      MagickBooleanType IsPFA(const unsigned char *magick,const size_t length)
86 %
87 %  A description of each parameter follows:
88 %
89 %    o magick: compare image format pattern against these bytes.
90 %
91 %    o length: Specifies the length of the magick string.
92 %
93 %
94 */
IsPFA(const unsigned char * magick,const size_t length)95 static MagickBooleanType IsPFA(const unsigned char *magick,const size_t length)
96 {
97   if (length < 14)
98     return(MagickFalse);
99   if (LocaleNCompare((char *) magick,"%!PS-AdobeFont",14) == 0)
100     return(MagickTrue);
101   return(MagickFalse);
102 }
103 
104 /*
105 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
106 %                                                                             %
107 %                                                                             %
108 %                                                                             %
109 %   I s T T F                                                                 %
110 %                                                                             %
111 %                                                                             %
112 %                                                                             %
113 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
114 %
115 %  IsTTF()() returns MagickTrue if the image format type, identified by the
116 %  magick string, is TTF.
117 %
118 %  The format of the IsTTF method is:
119 %
120 %      MagickBooleanType IsTTF(const unsigned char *magick,const size_t length)
121 %
122 %  A description of each parameter follows:
123 %
124 %    o magick: compare image format pattern against these bytes.
125 %
126 %    o length: Specifies the length of the magick string.
127 %
128 %
129 */
IsTTF(const unsigned char * magick,const size_t length)130 static MagickBooleanType IsTTF(const unsigned char *magick,const size_t length)
131 {
132   if (length < 5)
133     return(MagickFalse);
134   if (((int) magick[0] == 0x00) && ((int) magick[1] == 0x01) &&
135       ((int) magick[2] == 0x00) && ((int) magick[3] == 0x00) &&
136       ((int) magick[4] == 0x00))
137     return(MagickTrue);
138   return(MagickFalse);
139 }
140 
141 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
142 /*
143 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
144 %                                                                             %
145 %                                                                             %
146 %                                                                             %
147 %   R e a d T T F I m a g e                                                   %
148 %                                                                             %
149 %                                                                             %
150 %                                                                             %
151 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
152 %
153 %  ReadTTFImage() reads a TrueType font file and returns it.  It
154 %  allocates the memory necessary for the new Image structure and returns a
155 %  pointer to the new image.
156 %
157 %  The format of the ReadTTFImage method is:
158 %
159 %      Image *ReadTTFImage(const ImageInfo *image_info,ExceptionInfo *exception)
160 %
161 %  A description of each parameter follows:
162 %
163 %    o image_info: the image info.
164 %
165 %    o exception: return any errors or warnings in this structure.
166 %
167 */
ReadTTFImage(const ImageInfo * image_info,ExceptionInfo * exception)168 static Image *ReadTTFImage(const ImageInfo *image_info,ExceptionInfo *exception)
169 {
170   char
171     buffer[MagickPathExtent],
172     *text;
173 
174   const char
175     Text[] =
176       "abcdefghijklmnopqrstuvwxyz\n"
177       "ABCDEFGHIJKLMNOPQRSTUVWXYZ\n"
178       "0123456789.:,;(*!?}^)#${%^&-+@\n";
179 
180   const TypeInfo
181     *type_info;
182 
183   DrawInfo
184     *draw_info;
185 
186   Image
187     *image;
188 
189   MagickBooleanType
190     status;
191 
192   PixelInfo
193     background_color;
194 
195   ssize_t
196     i,
197     x;
198 
199   Quantum
200     *q;
201 
202   ssize_t
203     y;
204 
205   /*
206     Open image file.
207   */
208   assert(image_info != (const ImageInfo *) NULL);
209   assert(image_info->signature == MagickCoreSignature);
210   if (image_info->debug != MagickFalse)
211     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
212       image_info->filename);
213   assert(exception != (ExceptionInfo *) NULL);
214   assert(exception->signature == MagickCoreSignature);
215   image=AcquireImage(image_info,exception);
216   image->columns=800;
217   image->rows=480;
218   type_info=GetTypeInfo(image_info->filename,exception);
219   if ((type_info != (const TypeInfo *) NULL) &&
220       (type_info->glyphs != (char *) NULL))
221     (void) CopyMagickString(image->filename,type_info->glyphs,MagickPathExtent);
222   status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
223   if (status == MagickFalse)
224     {
225       image=DestroyImageList(image);
226       return((Image *) NULL);
227     }
228   status=SetImageExtent(image,image->columns,image->rows,exception);
229   if (status == MagickFalse)
230     return(DestroyImageList(image));
231   /*
232     Color canvas with background color
233   */
234   background_color=image_info->background_color;
235   for (y=0; y < (ssize_t) image->rows; y++)
236   {
237     q=QueueAuthenticPixels(image,0,y,image->columns,1,exception);
238     if (q == (Quantum *) NULL)
239       break;
240     for (x=0; x < (ssize_t) image->columns; x++)
241     {
242       SetPixelViaPixelInfo(image,&background_color,q);
243       q+=GetPixelChannels(image);
244     }
245     if (SyncAuthenticPixels(image,exception) == MagickFalse)
246       break;
247   }
248   (void) CopyMagickString(image->magick,image_info->magick,MagickPathExtent);
249   (void) CopyMagickString(image->filename,image_info->filename,
250     MagickPathExtent);
251   /*
252     Prepare drawing commands
253   */
254   y=20;
255   draw_info=CloneDrawInfo(image_info,(DrawInfo *) NULL);
256   draw_info->font=AcquireString("");
257   (void) ImageToFile(image,draw_info->font,exception);
258   ConcatenateString(&draw_info->primitive,"push graphic-context\n");
259   (void) FormatLocaleString(buffer,MagickPathExtent,
260     " viewbox 0 0 %.20g %.20g\n",(double) image->columns,(double) image->rows);
261   ConcatenateString(&draw_info->primitive,buffer);
262   ConcatenateString(&draw_info->primitive," font-size 18\n");
263   (void) FormatLocaleString(buffer,MagickPathExtent," text 10,%.20g '",
264     (double) y);
265   ConcatenateString(&draw_info->primitive,buffer);
266   text=EscapeString(Text,'"');
267   ConcatenateString(&draw_info->primitive,text);
268   text=DestroyString(text);
269   (void) FormatLocaleString(buffer,MagickPathExtent,"'\n");
270   ConcatenateString(&draw_info->primitive,buffer);
271   y+=20*(ssize_t) MultilineCensus((char *) Text)+20;
272   for (i=12; i <= 72; i+=6)
273   {
274     y+=i+12;
275     ConcatenateString(&draw_info->primitive," font-size 18\n");
276     (void) FormatLocaleString(buffer,MagickPathExtent,
277       " text 10,%.20g '%.20g'\n",(double) y,(double) i);
278     ConcatenateString(&draw_info->primitive,buffer);
279     (void) FormatLocaleString(buffer,MagickPathExtent," font-size %.20g\n",
280       (double) i);
281     ConcatenateString(&draw_info->primitive,buffer);
282     (void) FormatLocaleString(buffer,MagickPathExtent," text 50,%.20g "
283       "'That which does not destroy me, only makes me stronger.'\n",(double) y);
284     ConcatenateString(&draw_info->primitive,buffer);
285     if (i >= 24)
286       i+=6;
287   }
288   ConcatenateString(&draw_info->primitive,"pop graphic-context");
289   (void) DrawImage(image,draw_info,exception);
290   /*
291     Relinquish resources.
292   */
293   (void) RelinquishUniqueFileResource(draw_info->font);
294   draw_info=DestroyDrawInfo(draw_info);
295   (void) CloseBlob(image);
296   return(GetFirstImageInList(image));
297 }
298 #endif /* MAGICKCORE_FREETYPE_DELEGATE */
299 
300 /*
301 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
302 %                                                                             %
303 %                                                                             %
304 %                                                                             %
305 %   R e g i s t e r T T F I m a g e                                           %
306 %                                                                             %
307 %                                                                             %
308 %                                                                             %
309 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
310 %
311 %  RegisterTTFImage() adds attributes for the TTF image format to
312 %  the list of supported formats.  The attributes include the image format
313 %  tag, a method to read and/or write the format, whether the format
314 %  supports the saving of more than one frame to the same file or blob,
315 %  whether the format supports native in-memory I/O, and a brief
316 %  description of the format.
317 %
318 %  The format of the RegisterTTFImage method is:
319 %
320 %      size_t RegisterTTFImage(void)
321 %
322 */
RegisterTTFImage(void)323 ModuleExport size_t RegisterTTFImage(void)
324 {
325   char
326     version[MagickPathExtent];
327 
328   MagickInfo
329     *entry;
330 
331   *version='\0';
332 #if defined(FREETYPE_MAJOR) && defined(FREETYPE_MINOR) && defined(FREETYPE_PATCH)
333   (void) FormatLocaleString(version,MagickPathExtent,"Freetype %d.%d.%d",
334     FREETYPE_MAJOR,FREETYPE_MINOR,FREETYPE_PATCH);
335 #endif
336   entry=AcquireMagickInfo("TTF","DFONT","Multi-face font package");
337 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
338   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
339 #endif
340   entry->magick=(IsImageFormatHandler *) IsTTF;
341   entry->flags^=CoderAdjoinFlag;
342   if (*version != '\0')
343     entry->version=ConstantString(version);
344   (void) RegisterMagickInfo(entry);
345   entry=AcquireMagickInfo("TTF","PFA","Postscript Type 1 font (ASCII)");
346 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
347   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
348 #endif
349   entry->magick=(IsImageFormatHandler *) IsPFA;
350   entry->flags^=CoderAdjoinFlag;
351   if (*version != '\0')
352     entry->version=ConstantString(version);
353   (void) RegisterMagickInfo(entry);
354   entry=AcquireMagickInfo("TTF","PFB","Postscript Type 1 font (binary)");
355 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
356   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
357 #endif
358   entry->magick=(IsImageFormatHandler *) IsPFA;
359   entry->flags^=CoderAdjoinFlag;
360   if (*version != '\0')
361     entry->version=ConstantString(version);
362   (void) RegisterMagickInfo(entry);
363   entry=AcquireMagickInfo("TTF","OTF","Open Type font");
364 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
365   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
366 #endif
367   entry->magick=(IsImageFormatHandler *) IsTTF;
368   entry->flags^=CoderAdjoinFlag;
369   if (*version != '\0')
370     entry->version=ConstantString(version);
371   (void) RegisterMagickInfo(entry);
372   entry=AcquireMagickInfo("TTF","TTC","TrueType font collection");
373 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
374   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
375 #endif
376   entry->magick=(IsImageFormatHandler *) IsTTF;
377   entry->flags^=CoderAdjoinFlag;
378   if (*version != '\0')
379     entry->version=ConstantString(version);
380   (void) RegisterMagickInfo(entry);
381   entry=AcquireMagickInfo("TTF","TTF","TrueType font");
382 #if defined(MAGICKCORE_FREETYPE_DELEGATE)
383   entry->decoder=(DecodeImageHandler *) ReadTTFImage;
384 #endif
385   entry->magick=(IsImageFormatHandler *) IsTTF;
386   entry->flags^=CoderAdjoinFlag;
387   if (*version != '\0')
388     entry->version=ConstantString(version);
389   (void) RegisterMagickInfo(entry);
390   return(MagickImageCoderSignature);
391 }
392 
393 /*
394 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
395 %                                                                             %
396 %                                                                             %
397 %                                                                             %
398 %   U n r e g i s t e r T T F I m a g e                                       %
399 %                                                                             %
400 %                                                                             %
401 %                                                                             %
402 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
403 %
404 %  UnregisterTTFImage() removes format registrations made by the
405 %  TTF module from the list of supported formats.
406 %
407 %  The format of the UnregisterTTFImage method is:
408 %
409 %      UnregisterTTFImage(void)
410 %
411 */
UnregisterTTFImage(void)412 ModuleExport void UnregisterTTFImage(void)
413 {
414   (void) UnregisterMagickInfo("TTF");
415   (void) UnregisterMagickInfo("TTC");
416   (void) UnregisterMagickInfo("OTF");
417   (void) UnregisterMagickInfo("PFA");
418   (void) UnregisterMagickInfo("PFB");
419   (void) UnregisterMagickInfo("PFA");
420   (void) UnregisterMagickInfo("DFONT");
421 }
422