|
MagickCore
6.7.5
|
00001 /* 00002 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00003 % % 00004 % % 00005 % % 00006 % GGGG EEEEE OOO M M EEEEE TTTTT RRRR Y Y % 00007 % G E O O MM MM E T R R Y Y % 00008 % G GG EEE O O M M M EEE T RRRR Y % 00009 % G G E O O M M E T R R Y % 00010 % GGGG EEEEE OOO M M EEEEE T R R Y % 00011 % % 00012 % % 00013 % MagickCore Geometry Methods % 00014 % % 00015 % Software Design % 00016 % John Cristy % 00017 % January 2003 % 00018 % % 00019 % % 00020 % Copyright 1999-2012 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 Include declarations. 00041 */ 00042 #include "MagickCore/studio.h" 00043 #include "MagickCore/constitute.h" 00044 #include "MagickCore/draw.h" 00045 #include "MagickCore/exception.h" 00046 #include "MagickCore/exception-private.h" 00047 #include "MagickCore/geometry.h" 00048 #include "MagickCore/memory_.h" 00049 #include "MagickCore/string_.h" 00050 #include "MagickCore/string-private.h" 00051 #include "MagickCore/token.h" 00052 00053 /* 00054 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00055 % % 00056 % % 00057 % % 00058 % G e t G e o m e t r y % 00059 % % 00060 % % 00061 % % 00062 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00063 % 00064 % GetGeometry() parses a geometry specification and returns the width, 00065 % height, x, and y values. It also returns flags that indicates which 00066 % of the four values (width, height, x, y) were located in the string, and 00067 % whether the x or y values are negative. In addition, there are flags to 00068 % report any meta characters (%, !, <, or >). 00069 % 00070 % The format of the GetGeometry method is: 00071 % 00072 % MagickStatusType GetGeometry(const char *geometry,ssize_t *x,ssize_t *y, 00073 % size_t *width,size_t *height) 00074 % 00075 % A description of each parameter follows: 00076 % 00077 % o geometry: The geometry. 00078 % 00079 % o x,y: The x and y offset as determined by the geometry specification. 00080 % 00081 % o width,height: The width and height as determined by the geometry 00082 % specification. 00083 % 00084 */ 00085 MagickExport MagickStatusType GetGeometry(const char *geometry,ssize_t *x, 00086 ssize_t *y,size_t *width,size_t *height) 00087 { 00088 char 00089 *p, 00090 pedantic_geometry[MaxTextExtent], 00091 *q; 00092 00093 double 00094 value; 00095 00096 int 00097 c; 00098 00099 MagickStatusType 00100 flags; 00101 00102 /* 00103 Remove whitespace and meta characters from geometry specification. 00104 */ 00105 flags=NoValue; 00106 if ((geometry == (char *) NULL) || (*geometry == '\0')) 00107 return(flags); 00108 if (strlen(geometry) >= (MaxTextExtent-1)) 00109 return(flags); 00110 (void) CopyMagickString(pedantic_geometry,geometry,MaxTextExtent); 00111 for (p=pedantic_geometry; *p != '\0'; ) 00112 { 00113 if (isspace((int) ((unsigned char) *p)) != 0) 00114 { 00115 (void) CopyMagickString(p,p+1,MaxTextExtent); 00116 continue; 00117 } 00118 c=(int) ((unsigned int) *p); 00119 switch (c) 00120 { 00121 case '%': 00122 { 00123 flags|=PercentValue; 00124 (void) CopyMagickString(p,p+1,MaxTextExtent); 00125 break; 00126 } 00127 case '!': 00128 { 00129 flags|=AspectValue; 00130 (void) CopyMagickString(p,p+1,MaxTextExtent); 00131 break; 00132 } 00133 case '<': 00134 { 00135 flags|=LessValue; 00136 (void) CopyMagickString(p,p+1,MaxTextExtent); 00137 break; 00138 } 00139 case '>': 00140 { 00141 flags|=GreaterValue; 00142 (void) CopyMagickString(p,p+1,MaxTextExtent); 00143 break; 00144 } 00145 case '^': 00146 { 00147 flags|=MinimumValue; 00148 (void) CopyMagickString(p,p+1,MaxTextExtent); 00149 break; 00150 } 00151 case '@': 00152 { 00153 flags|=AreaValue; 00154 (void) CopyMagickString(p,p+1,MaxTextExtent); 00155 break; 00156 } 00157 case '(': 00158 case ')': 00159 { 00160 (void) CopyMagickString(p,p+1,MaxTextExtent); 00161 break; 00162 } 00163 case '-': 00164 case '.': 00165 case ',': 00166 case '+': 00167 case '0': 00168 case '1': 00169 case '2': 00170 case '3': 00171 case '4': 00172 case '5': 00173 case '6': 00174 case '7': 00175 case '8': 00176 case '9': 00177 case 'x': 00178 case 'X': 00179 case 215: 00180 { 00181 p++; 00182 break; 00183 } 00184 default: 00185 return(flags); 00186 } 00187 } 00188 /* 00189 Parse width, height, x, and y. 00190 */ 00191 p=pedantic_geometry; 00192 if (*p == '\0') 00193 return(flags); 00194 q=p; 00195 value=StringToDouble(p,&q); 00196 (void) value; 00197 if (LocaleNCompare(p,"0x",2) == 0) 00198 value=(double) strtol(p,&q,10); 00199 c=(int) ((unsigned char) *q); 00200 if ((c == 215) || (*q == 'x') || (*q == 'X') || (*q == '\0')) 00201 { 00202 /* 00203 Parse width. 00204 */ 00205 q=p; 00206 if (LocaleNCompare(p,"0x",2) == 0) 00207 *width=(size_t) strtol(p,&p,10); 00208 else 00209 *width=(size_t) floor(StringToDouble(p,&p)+0.5); 00210 if (p != q) 00211 flags|=WidthValue; 00212 } 00213 c=(*p); 00214 c=(int) ((unsigned char) *p); 00215 if ((c == 215) || (*p == 'x') || (*p == 'X')) 00216 { 00217 p++; 00218 if ((*p != '+') && (*p != '-')) 00219 { 00220 /* 00221 Parse height. 00222 */ 00223 q=p; 00224 *height=(size_t) floor(StringToDouble(p,&p)+0.5); 00225 if (p != q) 00226 flags|=HeightValue; 00227 } 00228 } 00229 if ((*p == '+') || (*p == '-')) 00230 { 00231 /* 00232 Parse x value. 00233 */ 00234 if (*p == '-') 00235 flags|=XNegative; 00236 q=p; 00237 *x=(ssize_t) ceil(StringToDouble(p,&p)-0.5); 00238 if (p != q) 00239 flags|=XValue; 00240 if ((*p == '+') || (*p == '-')) 00241 { 00242 /* 00243 Parse y value. 00244 */ 00245 if (*p == '-') 00246 flags|=YNegative; 00247 q=p; 00248 *y=(ssize_t) ceil(StringToDouble(p,&p)-0.5); 00249 if (p != q) 00250 flags|=YValue; 00251 } 00252 } 00253 return(flags); 00254 } 00255 00256 /* 00257 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00258 % % 00259 % % 00260 % % 00261 % G e t P a g e G e o m e t r y % 00262 % % 00263 % % 00264 % % 00265 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00266 % 00267 % GetPageGeometry() replaces any page mneumonic with the equivalent size in 00268 % picas. 00269 % 00270 % The format of the GetPageGeometry method is: 00271 % 00272 % char *GetPageGeometry(const char *page_geometry) 00273 % 00274 % A description of each parameter follows. 00275 % 00276 % o page_geometry: Specifies a pointer to an array of characters. The 00277 % string is either a Postscript page name (e.g. A4) or a postscript page 00278 % geometry (e.g. 612x792+36+36). 00279 % 00280 */ 00281 MagickExport char *GetPageGeometry(const char *page_geometry) 00282 { 00283 static const char 00284 *PageSizes[][2]= 00285 { 00286 { "4x6", "288x432" }, 00287 { "5x7", "360x504" }, 00288 { "7x9", "504x648" }, 00289 { "8x10", "576x720" }, 00290 { "9x11", "648x792" }, 00291 { "9x12", "648x864" }, 00292 { "10x13", "720x936" }, 00293 { "10x14", "720x1008" }, 00294 { "11x17", "792x1224" }, 00295 { "a0", "2384x3370" }, 00296 { "a1", "1684x2384" }, 00297 { "a10", "73x105" }, 00298 { "a2", "1191x1684" }, 00299 { "a3", "842x1191" }, 00300 { "a4", "595x842" }, 00301 { "a4smaLL", "595x842" }, 00302 { "a5", "420x595" }, 00303 { "a6", "297x420" }, 00304 { "a7", "210x297" }, 00305 { "a8", "148x210" }, 00306 { "a9", "105x148" }, 00307 { "archa", "648x864" }, 00308 { "archb", "864x1296" }, 00309 { "archC", "1296x1728" }, 00310 { "archd", "1728x2592" }, 00311 { "arche", "2592x3456" }, 00312 { "b0", "2920x4127" }, 00313 { "b1", "2064x2920" }, 00314 { "b10", "91x127" }, 00315 { "b2", "1460x2064" }, 00316 { "b3", "1032x1460" }, 00317 { "b4", "729x1032" }, 00318 { "b5", "516x729" }, 00319 { "b6", "363x516" }, 00320 { "b7", "258x363" }, 00321 { "b8", "181x258" }, 00322 { "b9", "127x181" }, 00323 { "c0", "2599x3676" }, 00324 { "c1", "1837x2599" }, 00325 { "c2", "1298x1837" }, 00326 { "c3", "918x1296" }, 00327 { "c4", "649x918" }, 00328 { "c5", "459x649" }, 00329 { "c6", "323x459" }, 00330 { "c7", "230x323" }, 00331 { "executive", "540x720" }, 00332 { "flsa", "612x936" }, 00333 { "flse", "612x936" }, 00334 { "folio", "612x936" }, 00335 { "halfletter", "396x612" }, 00336 { "isob0", "2835x4008" }, 00337 { "isob1", "2004x2835" }, 00338 { "isob10", "88x125" }, 00339 { "isob2", "1417x2004" }, 00340 { "isob3", "1001x1417" }, 00341 { "isob4", "709x1001" }, 00342 { "isob5", "499x709" }, 00343 { "isob6", "354x499" }, 00344 { "isob7", "249x354" }, 00345 { "isob8", "176x249" }, 00346 { "isob9", "125x176" }, 00347 { "jisb0", "1030x1456" }, 00348 { "jisb1", "728x1030" }, 00349 { "jisb2", "515x728" }, 00350 { "jisb3", "364x515" }, 00351 { "jisb4", "257x364" }, 00352 { "jisb5", "182x257" }, 00353 { "jisb6", "128x182" }, 00354 { "ledger", "1224x792" }, 00355 { "legal", "612x1008" }, 00356 { "letter", "612x792" }, 00357 { "lettersmaLL", "612x792" }, 00358 { "quarto", "610x780" }, 00359 { "statement", "396x612" }, 00360 { "tabloid", "792x1224" }, 00361 { (char *) NULL, (char *) NULL } 00362 }; 00363 00364 char 00365 *page; 00366 00367 register ssize_t 00368 i; 00369 00370 assert(page_geometry != (char *) NULL); 00371 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",page_geometry); 00372 page=AcquireString(page_geometry); 00373 for (i=0; *PageSizes[i] != (char *) NULL; i++) 00374 if (LocaleNCompare(PageSizes[i][0],page,strlen(PageSizes[i][0])) == 0) 00375 { 00376 RectangleInfo 00377 geometry; 00378 00379 MagickStatusType 00380 flags; 00381 00382 /* 00383 Replace mneumonic with the equivalent size in dots-per-inch. 00384 */ 00385 (void) CopyMagickString(page,PageSizes[i][1],MaxTextExtent); 00386 (void) ConcatenateMagickString(page,page_geometry+ 00387 strlen(PageSizes[i][0]),MaxTextExtent); 00388 flags=GetGeometry(page,&geometry.x,&geometry.y,&geometry.width, 00389 &geometry.height); 00390 if ((flags & GreaterValue) == 0) 00391 (void) ConcatenateMagickString(page,">",MaxTextExtent); 00392 break; 00393 } 00394 return(page); 00395 } 00396 00397 /* 00398 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00399 % % 00400 % % 00401 % % 00402 % G r a v i t y A d j u s t G e o m e t r y % 00403 % % 00404 % % % % 00405 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00406 % 00407 % GravityAdjustGeometry() adjusts the offset of a region with regard to the 00408 % given: width, height and gravity; against which it is positioned. 00409 % 00410 % The region should also have an appropriate width and height to correctly 00411 % set the right offset of the top left corner of the region. 00412 % 00413 % The format of the GravityAdjustGeometry method is: 00414 % 00415 % void GravityAdjustGeometry(const size_t width, const size_t height, 00416 % const GravityType gravity,RectangleInfo *region); 00417 % 00418 % A description of each parameter follows: 00419 % 00420 % o width, height: the larger area the region is relative to 00421 % 00422 % o gravity: the edge/corner the current offset is relative to 00423 % 00424 % o region: The region requiring a offset adjustment relative to gravity 00425 % 00426 */ 00427 MagickExport void GravityAdjustGeometry(const size_t width, 00428 const size_t height,const GravityType gravity,RectangleInfo *region) 00429 { 00430 if (region->height == 0) 00431 region->height=height; 00432 if (region->width == 0) 00433 region->width=width; 00434 switch (gravity) 00435 { 00436 case NorthEastGravity: 00437 case EastGravity: 00438 case SouthEastGravity: 00439 { 00440 region->x=(ssize_t) (width-region->width-region->x); 00441 break; 00442 } 00443 case NorthGravity: 00444 case SouthGravity: 00445 case CenterGravity: 00446 case StaticGravity: 00447 { 00448 region->x+=(ssize_t) (width/2-region->width/2); 00449 break; 00450 } 00451 case ForgetGravity: 00452 case NorthWestGravity: 00453 case WestGravity: 00454 case SouthWestGravity: 00455 default: 00456 break; 00457 } 00458 switch (gravity) 00459 { 00460 case SouthWestGravity: 00461 case SouthGravity: 00462 case SouthEastGravity: 00463 { 00464 region->y=(ssize_t) (height-region->height-region->y); 00465 break; 00466 } 00467 case EastGravity: 00468 case WestGravity: 00469 case CenterGravity: 00470 case StaticGravity: 00471 { 00472 region->y+=(ssize_t) (height/2-region->height/2); 00473 break; 00474 } 00475 case ForgetGravity: 00476 case NorthWestGravity: 00477 case NorthGravity: 00478 case NorthEastGravity: 00479 default: 00480 break; 00481 } 00482 return; 00483 } 00484 00485 /* 00486 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00487 % % 00488 % % 00489 % % 00490 + I s G e o m e t r y % 00491 % % 00492 % % 00493 % % 00494 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00495 % 00496 % IsGeometry() returns MagickTrue if the geometry specification is valid. 00497 % Examples are 100, 100x200, x200, 100x200+10+20, +10+20, 200%, 200x200!, etc. 00498 % 00499 % The format of the IsGeometry method is: 00500 % 00501 % MagickBooleanType IsGeometry(const char *geometry) 00502 % 00503 % A description of each parameter follows: 00504 % 00505 % o geometry: This string is the geometry specification. 00506 % 00507 */ 00508 MagickExport MagickBooleanType IsGeometry(const char *geometry) 00509 { 00510 GeometryInfo 00511 geometry_info; 00512 00513 MagickStatusType 00514 flags; 00515 00516 if (geometry == (const char *) NULL) 00517 return(MagickFalse); 00518 flags=ParseGeometry(geometry,&geometry_info); 00519 if (flags == NoValue) 00520 flags=ParseGeometry(geometry+1,&geometry_info); /* i.e. +-4+-4 */ 00521 return(flags != NoValue ? MagickTrue : MagickFalse); 00522 } 00523 00524 /* 00525 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00526 % % 00527 % % 00528 % % 00529 + I s S c e n e G e o m e t r y % 00530 % % 00531 % % 00532 % % 00533 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00534 % 00535 % IsSceneGeometry() returns MagickTrue if the geometry is a valid scene 00536 % specification (e.g. [1], [1-9], [1,7,4]). 00537 % 00538 % The format of the IsSceneGeometry method is: 00539 % 00540 % MagickBooleanType IsSceneGeometry(const char *geometry, 00541 % const MagickBooleanType pedantic) 00542 % 00543 % A description of each parameter follows: 00544 % 00545 % o geometry: This string is the geometry specification. 00546 % 00547 % o pedantic: A value other than 0 invokes a more restrictive set of 00548 % conditions for a valid specification (e.g. [1], [1-4], [4-1]). 00549 % 00550 */ 00551 MagickExport MagickBooleanType IsSceneGeometry(const char *geometry, 00552 const MagickBooleanType pedantic) 00553 { 00554 char 00555 *p; 00556 00557 double 00558 value; 00559 00560 if (geometry == (const char *) NULL) 00561 return(MagickFalse); 00562 p=(char *) geometry; 00563 value=StringToDouble(geometry,&p); 00564 (void) value; 00565 if (p == geometry) 00566 return(MagickFalse); 00567 if (strspn(geometry,"0123456789-, ") != strlen(geometry)) 00568 return(MagickFalse); 00569 if ((pedantic != MagickFalse) && (strchr(geometry,',') != (char *) NULL)) 00570 return(MagickFalse); 00571 return(MagickTrue); 00572 } 00573 00574 /* 00575 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00576 % % 00577 % % 00578 % % 00579 % P a r s e A b s o l u t e G e o m e t r y % 00580 % % 00581 % % 00582 % % 00583 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00584 % 00585 % ParseAbsoluteGeometry() returns a region as defined by the geometry string, 00586 % without any modification by percentages or gravity. 00587 % 00588 % It currently just a wrapper around GetGeometry(), but may be expanded in 00589 % the future to handle other positioning information. 00590 % 00591 % The format of the ParseAbsoluteGeometry method is: 00592 % 00593 % MagickStatusType ParseAbsoluteGeometry(const char *geometry, 00594 % RectangleInfo *region_info) 00595 % 00596 % A description of each parameter follows: 00597 % 00598 % o geometry: The geometry string (e.g. "100x100+10+10"). 00599 % 00600 % o region_info: the region as defined by the geometry string. 00601 % 00602 */ 00603 MagickExport MagickStatusType ParseAbsoluteGeometry(const char *geometry, 00604 RectangleInfo *region_info) 00605 { 00606 MagickStatusType 00607 flags; 00608 00609 flags=GetGeometry(geometry,®ion_info->x,®ion_info->y, 00610 ®ion_info->width,®ion_info->height); 00611 return(flags); 00612 } 00613 00614 /* 00615 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00616 % % 00617 % % 00618 % % 00619 % P a r s e A f f i n e G e o m e t r y % 00620 % % 00621 % % 00622 % % 00623 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00624 % 00625 % ParseAffineGeometry() returns an affine matrix as defined by a string of 4 00626 % to 6 comma/space separated floating point values. 00627 % 00628 % The affine matrix determinant is checked for validity of the values. 00629 % 00630 % The format of the ParseAffineGeometry method is: 00631 % 00632 % MagickStatusType ParseAffineGeometry(const char *geometry, 00633 % AffineMatrix *affine_matrix,ExceptionInfo *exception) 00634 % 00635 % A description of each parameter follows: 00636 % 00637 % o geometry: The geometry string (e.g. "1.0,0.0,0.0,1.0,3.2,1.2"). 00638 % 00639 % o affine_matrix: the affine matrix as defined by the geometry string. 00640 % 00641 % o exception: return any errors or warnings in this structure. 00642 % 00643 */ 00644 MagickExport MagickStatusType ParseAffineGeometry(const char *geometry, 00645 AffineMatrix *affine_matrix,ExceptionInfo *exception) 00646 { 00647 char 00648 token[MaxTextExtent]; 00649 00650 const char 00651 *p; 00652 00653 double 00654 determinant; 00655 00656 MagickStatusType 00657 flags; 00658 00659 register ssize_t 00660 i; 00661 00662 GetAffineMatrix(affine_matrix); 00663 flags=NoValue; 00664 p=(char *) geometry; 00665 for (i=0; (*p != '\0') && (i < 6); i++) 00666 { 00667 GetMagickToken(p,&p,token); 00668 if (*token == ',') 00669 GetMagickToken(p,&p,token); 00670 switch (i) 00671 { 00672 case 0: 00673 { 00674 affine_matrix->sx=StringToDouble(token,(char **) NULL); 00675 break; 00676 } 00677 case 1: 00678 { 00679 affine_matrix->rx=StringToDouble(token,(char **) NULL); 00680 break; 00681 } 00682 case 2: 00683 { 00684 affine_matrix->ry=StringToDouble(token,(char **) NULL); 00685 break; 00686 } 00687 case 3: 00688 { 00689 affine_matrix->sy=StringToDouble(token,(char **) NULL); 00690 break; 00691 } 00692 case 4: 00693 { 00694 affine_matrix->tx=StringToDouble(token,(char **) NULL); 00695 flags|=XValue; 00696 break; 00697 } 00698 case 5: 00699 { 00700 affine_matrix->ty=StringToDouble(token,(char **) NULL); 00701 flags|=YValue; 00702 break; 00703 } 00704 } 00705 } 00706 determinant=(affine_matrix->sx*affine_matrix->sy-affine_matrix->rx* 00707 affine_matrix->ry); 00708 if (fabs(determinant) < MagickEpsilon) 00709 (void) ThrowMagickException(exception,GetMagickModule(),OptionError, 00710 "InvalidGeometry","`%s'",geometry); 00711 return(flags); 00712 } 00713 00714 /* 00715 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00716 % % 00717 % % 00718 % % 00719 % P a r s e G e o m e t r y % 00720 % % 00721 % % 00722 % % 00723 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00724 % 00725 % ParseGeometry() parses a geometry specification and returns the sigma, 00726 % rho, xi, and psi values. It also returns flags that indicates which 00727 % of the four values (sigma, rho, xi, psi) were located in the string, and 00728 % whether the xi or pi values are negative. 00729 % 00730 % In addition, it reports if there are any of meta characters (%, !, <, >, @, 00731 % and ^) flags present. It does not report the location of the percentage 00732 % relative to the values. 00733 % 00734 % The format of the ParseGeometry method is: 00735 % 00736 % MagickStatusType ParseGeometry(const char *geometry, 00737 % GeometryInfo *geometry_info) 00738 % 00739 % A description of each parameter follows: 00740 % 00741 % o geometry: The geometry string (e.g. "100x100+10+10"). 00742 % 00743 % o geometry_info: returns the parsed width/height/x/y in this structure. 00744 % 00745 */ 00746 MagickExport MagickStatusType ParseGeometry(const char *geometry, 00747 GeometryInfo *geometry_info) 00748 { 00749 char 00750 *p, 00751 pedantic_geometry[MaxTextExtent], 00752 *q; 00753 00754 double 00755 value; 00756 00757 int 00758 c; 00759 00760 MagickStatusType 00761 flags; 00762 00763 /* 00764 Remove whitespaces meta characters from geometry specification. 00765 */ 00766 assert(geometry_info != (GeometryInfo *) NULL); 00767 flags=NoValue; 00768 if ((geometry == (char *) NULL) || (*geometry == '\0')) 00769 return(flags); 00770 if (strlen(geometry) >= (MaxTextExtent-1)) 00771 return(flags); 00772 (void) CopyMagickString(pedantic_geometry,geometry,MaxTextExtent); 00773 for (p=pedantic_geometry; *p != '\0'; ) 00774 { 00775 if (isspace((int) ((unsigned char) *p)) != 0) 00776 { 00777 (void) CopyMagickString(p,p+1,MaxTextExtent); 00778 continue; 00779 } 00780 c=(int) ((unsigned char) *p); 00781 switch (c) 00782 { 00783 case '%': 00784 { 00785 flags|=PercentValue; 00786 (void) CopyMagickString(p,p+1,MaxTextExtent); 00787 break; 00788 } 00789 case '!': 00790 { 00791 flags|=AspectValue; 00792 (void) CopyMagickString(p,p+1,MaxTextExtent); 00793 break; 00794 } 00795 case '<': 00796 { 00797 flags|=LessValue; 00798 (void) CopyMagickString(p,p+1,MaxTextExtent); 00799 break; 00800 } 00801 case '>': 00802 { 00803 flags|=GreaterValue; 00804 (void) CopyMagickString(p,p+1,MaxTextExtent); 00805 break; 00806 } 00807 case '^': 00808 { 00809 flags|=MinimumValue; 00810 (void) CopyMagickString(p,p+1,MaxTextExtent); 00811 break; 00812 } 00813 case '@': 00814 { 00815 flags|=AreaValue; 00816 (void) CopyMagickString(p,p+1,MaxTextExtent); 00817 break; 00818 } 00819 case '(': 00820 case ')': 00821 { 00822 (void) CopyMagickString(p,p+1,MaxTextExtent); 00823 break; 00824 } 00825 case '-': 00826 case '+': 00827 case ',': 00828 case '0': 00829 case '1': 00830 case '2': 00831 case '3': 00832 case '4': 00833 case '5': 00834 case '6': 00835 case '7': 00836 case '8': 00837 case '9': 00838 case 'x': 00839 case 'X': 00840 case '/': 00841 case ':': 00842 case 215: 00843 { 00844 p++; 00845 break; 00846 } 00847 case '.': 00848 { 00849 p++; 00850 flags|=DecimalValue; 00851 break; 00852 } 00853 default: 00854 return(flags); 00855 } 00856 } 00857 /* 00858 Parse rho, sigma, xi, psi, and optionally chi. 00859 */ 00860 p=pedantic_geometry; 00861 if (*p == '\0') 00862 return(flags); 00863 q=p; 00864 value=StringToDouble(p,&q); 00865 if (LocaleNCompare(p,"0x",2) == 0) 00866 value=(double) strtol(p,&q,10); 00867 c=(int) ((unsigned char) *q); 00868 if ((c == 215) || (*q == 'x') || (*q == 'X') || (*q == ',') || 00869 (*q == '/') || (*q == ':') || (*q =='\0')) 00870 { 00871 /* 00872 Parse rho. 00873 */ 00874 q=p; 00875 if (LocaleNCompare(p,"0x",2) == 0) 00876 value=(double) strtol(p,&p,10); 00877 else 00878 value=StringToDouble(p,&p); 00879 if (p != q) 00880 { 00881 flags|=RhoValue; 00882 geometry_info->rho=value; 00883 } 00884 } 00885 q=p; 00886 c=(int) ((unsigned char) *p); 00887 if ((c == 215) || (*p == 'x') || (*p == 'X') || (*p == ',') || (*p == '/') || 00888 (*p == ':')) 00889 { 00890 /* 00891 Parse sigma. 00892 */ 00893 p++; 00894 while (isspace((int) ((unsigned char) *p)) != 0) 00895 p++; 00896 c=(int) ((unsigned char) *q); 00897 if (((c != 215) && (*q != 'x') && (*q != 'X')) || ((*p != '+') && 00898 (*p != '-'))) 00899 { 00900 q=p; 00901 value=StringToDouble(p,&p); 00902 if (p != q) 00903 { 00904 flags|=SigmaValue; 00905 geometry_info->sigma=value; 00906 } 00907 } 00908 } 00909 while (isspace((int) ((unsigned char) *p)) != 0) 00910 p++; 00911 if ((*p == '+') || (*p == '-') || (*p == ',') || (*p == '/') || (*p == ':')) 00912 { 00913 /* 00914 Parse xi value. 00915 */ 00916 if ((*p == ',') || (*p == '/') || (*p == ':')) 00917 p++; 00918 q=p; 00919 value=StringToDouble(p,&p); 00920 if (p != q) 00921 { 00922 flags|=XiValue; 00923 if (*q == '-') 00924 flags|=XiNegative; 00925 geometry_info->xi=value; 00926 } 00927 while (isspace((int) ((unsigned char) *p)) != 0) 00928 p++; 00929 if ((*p == '+') || (*p == '-') || (*p == ',') || (*p == '/') || 00930 (*p == ':')) 00931 { 00932 /* 00933 Parse psi value. 00934 */ 00935 if ((*p == ',') || (*p == '/') || (*p == ':')) 00936 p++; 00937 q=p; 00938 value=StringToDouble(p,&p); 00939 if (p != q) 00940 { 00941 flags|=PsiValue; 00942 if (*q == '-') 00943 flags|=PsiNegative; 00944 geometry_info->psi=value; 00945 } 00946 } 00947 while (isspace((int) ((unsigned char) *p)) != 0) 00948 p++; 00949 if ((*p == '+') || (*p == '-') || (*p == ',') || (*p == '/') || 00950 (*p == ':')) 00951 { 00952 /* 00953 Parse chi value. 00954 */ 00955 if ((*p == ',') || (*p == '/') || (*p == ':')) 00956 p++; 00957 q=p; 00958 value=StringToDouble(p,&p); 00959 if (p != q) 00960 { 00961 flags|=ChiValue; 00962 if (*q == '-') 00963 flags|=ChiNegative; 00964 geometry_info->chi=value; 00965 } 00966 } 00967 } 00968 if (strchr(pedantic_geometry,':') != (char *) NULL) 00969 { 00970 /* 00971 Normalize sampling factor (e.g. 4:2:2 => 2x1). 00972 */ 00973 geometry_info->rho/=geometry_info->sigma; 00974 geometry_info->sigma=1.0; 00975 if (geometry_info->xi == 0.0) 00976 geometry_info->sigma=2.0; 00977 } 00978 if (((flags & SigmaValue) == 0) && ((flags & XiValue) != 0) && 00979 ((flags & PsiValue) == 0)) 00980 { 00981 /* 00982 Support negative height values (e.g. 30x-20). 00983 */ 00984 geometry_info->sigma=geometry_info->xi; 00985 geometry_info->xi=0.0; 00986 flags|=SigmaValue; 00987 flags&=(~XiValue); 00988 } 00989 return(flags); 00990 } 00991 00992 /* 00993 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 00994 % % 00995 % % 00996 % % 00997 % P a r s e G r a v i t y G e o m e t r y % 00998 % % 00999 % % 01000 % % 01001 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01002 % 01003 % ParseGravityGeometry() returns a region as defined by the geometry string 01004 % with respect to the given image page (canvas) dimensions and the images 01005 % gravity setting. 01006 % 01007 % This is typically used for specifing a area within a given image for 01008 % cropping images to a smaller size, chopping out rows and or columns, or 01009 % resizing and positioning overlay images. 01010 % 01011 % Percentages are relative to image size and not page size, and are set to 01012 % nearest integer (pixel) size. 01013 % 01014 % The format of the ParseGravityGeometry method is: 01015 % 01016 % MagickStatusType ParseGravityGeometry(Image *image,const char *geometry, 01017 % RectangeInfo *region_info,ExceptionInfo *exception) 01018 % 01019 % A description of each parameter follows: 01020 % 01021 % o geometry: The geometry string (e.g. "100x100+10+10"). 01022 % 01023 % o region_info: the region as defined by the geometry string with respect 01024 % to the image dimensions and its gravity. 01025 % 01026 % o exception: return any errors or warnings in this structure. 01027 % 01028 */ 01029 MagickExport MagickStatusType ParseGravityGeometry(const Image *image, 01030 const char *geometry,RectangleInfo *region_info,ExceptionInfo *exception) 01031 { 01032 MagickStatusType 01033 flags; 01034 01035 size_t 01036 height, 01037 width; 01038 01039 SetGeometry(image,region_info); 01040 if (image->page.width != 0) 01041 region_info->width=image->page.width; 01042 if (image->page.height != 0) 01043 region_info->height=image->page.height; 01044 flags=ParseAbsoluteGeometry(geometry,region_info); 01045 if (flags == NoValue) 01046 { 01047 (void) ThrowMagickException(exception,GetMagickModule(),OptionError, 01048 "InvalidGeometry","`%s'",geometry); 01049 return(flags); 01050 } 01051 if ((flags & PercentValue) != 0) 01052 { 01053 GeometryInfo 01054 geometry_info; 01055 01056 MagickStatusType 01057 status; 01058 01059 PointInfo 01060 scale; 01061 01062 /* 01063 Geometry is a percentage of the image size, not canvas size 01064 */ 01065 if (image->gravity != UndefinedGravity) 01066 flags|=XValue | YValue; 01067 status=ParseGeometry(geometry,&geometry_info); 01068 scale.x=geometry_info.rho; 01069 if ((status & RhoValue) == 0) 01070 scale.x=100.0; 01071 scale.y=geometry_info.sigma; 01072 if ((status & SigmaValue) == 0) 01073 scale.y=scale.x; 01074 region_info->width=(size_t) floor((scale.x*image->columns/100.0)+0.5); 01075 region_info->height=(size_t) floor((scale.y*image->rows/100.0)+0.5); 01076 } 01077 /* 01078 Adjust offset according to gravity setting. 01079 */ 01080 width=region_info->width; 01081 height=region_info->height; 01082 if (width == 0) 01083 region_info->width=image->page.width | image->columns; 01084 if (height == 0) 01085 region_info->height=image->page.height | image->rows; 01086 GravityAdjustGeometry(image->columns,image->rows,image->gravity,region_info); 01087 region_info->width=width; 01088 region_info->height=height; 01089 return(flags); 01090 } 01091 01092 /* 01093 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01094 % % 01095 % % 01096 % % 01097 + P a r s e M e t a G e o m e t r y % 01098 % % 01099 % % 01100 % % 01101 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01102 % 01103 % ParseMetaGeometry() is similar to GetGeometry() except the returned 01104 % geometry is modified as determined by the meta characters: %, !, <, >, @, 01105 % and ^ in relation to image resizing. 01106 % 01107 % Final image dimensions are adjusted so as to preserve the aspect ratio as 01108 % much as possible, while generating a integer (pixel) size, and fitting the 01109 % image within the specified geometry width and height. 01110 % 01111 % Flags are interpreted... 01112 % % geometry size is given percentage of original image size 01113 % ! do not try to preserve aspect ratio 01114 % < only enlarge images smaller that geometry 01115 % > only shrink images larger than geometry 01116 % @ Fit image to contain at most this many pixels 01117 % ^ Contain the given geometry given, (minimal dimensions given) 01118 % 01119 % The format of the ParseMetaGeometry method is: 01120 % 01121 % MagickStatusType ParseMetaGeometry(const char *geometry,ssize_t *x, 01122 % ssize_t *y, size_t *width,size_t *height) 01123 % 01124 % A description of each parameter follows: 01125 % 01126 % o geometry: The geometry string (e.g. "100x100+10+10"). 01127 % 01128 % o x,y: The x and y offset, set according to the geometry specification. 01129 % 01130 % o width,height: The width and height of original image, modified by 01131 % the given geometry specification. 01132 % 01133 */ 01134 01135 static inline size_t MagickMax(const size_t x, 01136 const size_t y) 01137 { 01138 if (x > y) 01139 return(x); 01140 return(y); 01141 } 01142 01143 MagickExport MagickStatusType ParseMetaGeometry(const char *geometry,ssize_t *x, 01144 ssize_t *y,size_t *width,size_t *height) 01145 { 01146 GeometryInfo 01147 geometry_info; 01148 01149 MagickStatusType 01150 flags; 01151 01152 size_t 01153 former_height, 01154 former_width; 01155 01156 /* 01157 Ensure the image geometry is valid. 01158 */ 01159 assert(x != (ssize_t *) NULL); 01160 assert(y != (ssize_t *) NULL); 01161 assert(width != (size_t *) NULL); 01162 assert(height != (size_t *) NULL); 01163 if ((geometry == (char *) NULL) || (*geometry == '\0')) 01164 return(NoValue); 01165 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",geometry); 01166 /* 01167 Parse geometry using GetGeometry. 01168 */ 01169 SetGeometryInfo(&geometry_info); 01170 former_width=(*width); 01171 former_height=(*height); 01172 flags=GetGeometry(geometry,x,y,width,height); 01173 if ((flags & PercentValue) != 0) 01174 { 01175 MagickStatusType 01176 flags; 01177 01178 PointInfo 01179 scale; 01180 01181 /* 01182 Geometry is a percentage of the image size. 01183 */ 01184 flags=ParseGeometry(geometry,&geometry_info); 01185 scale.x=geometry_info.rho; 01186 if ((flags & RhoValue) == 0) 01187 scale.x=100.0; 01188 scale.y=geometry_info.sigma; 01189 if ((flags & SigmaValue) == 0) 01190 scale.y=scale.x; 01191 *width=(size_t) floor(scale.x*former_width/100.0+0.5); 01192 if (*width == 0) 01193 *width=1; 01194 *height=(size_t) floor(scale.y*former_height/100.0+0.5); 01195 if (*height == 0) 01196 *height=1; 01197 former_width=(*width); 01198 former_height=(*height); 01199 } 01200 if (((flags & AspectValue) != 0) || ((*width == former_width) && 01201 (*height == former_height))) 01202 { 01203 if ((flags & RhoValue) == 0) 01204 *width=former_width; 01205 if ((flags & SigmaValue) == 0) 01206 *height=former_height; 01207 } 01208 else 01209 { 01210 double 01211 scale_factor; 01212 01213 /* 01214 Respect aspect ratio of the image. 01215 */ 01216 if ((former_width == 0) || (former_height == 0)) 01217 scale_factor=1.0; 01218 else 01219 if (((flags & RhoValue) != 0) && (flags & SigmaValue) != 0) 01220 { 01221 scale_factor=(double) *width/(double) former_width; 01222 if ((flags & MinimumValue) == 0) 01223 { 01224 if (scale_factor > ((double) *height/(double) former_height)) 01225 scale_factor=(double) *height/(double) former_height; 01226 } 01227 else 01228 if (scale_factor < ((double) *height/(double) former_height)) 01229 scale_factor=(double) *height/(double) former_height; 01230 } 01231 else 01232 if ((flags & RhoValue) != 0) 01233 { 01234 scale_factor=(double) *width/(double) former_width; 01235 if (((flags & MinimumValue) != 0) && 01236 (scale_factor < ((double) *width/(double) former_height))) 01237 scale_factor=(double) *width/(double) former_height; 01238 } 01239 else 01240 { 01241 scale_factor=(double) *height/(double) former_height; 01242 if (((flags & MinimumValue) != 0) && 01243 (scale_factor < ((double) *height/(double) former_width))) 01244 scale_factor=(double) *height/(double) former_width; 01245 } 01246 *width=MagickMax((size_t) floor(scale_factor*former_width+0.5),1UL); 01247 *height=MagickMax((size_t) floor(scale_factor*former_height+0.5),1UL); 01248 } 01249 if ((flags & GreaterValue) != 0) 01250 { 01251 if (former_width < *width) 01252 *width=former_width; 01253 if (former_height < *height) 01254 *height=former_height; 01255 } 01256 if ((flags & LessValue) != 0) 01257 { 01258 if (former_width > *width) 01259 *width=former_width; 01260 if (former_height > *height) 01261 *height=former_height; 01262 } 01263 if ((flags & AreaValue) != 0) 01264 { 01265 double 01266 area, 01267 distance; 01268 01269 PointInfo 01270 scale; 01271 01272 /* 01273 Geometry is a maximum area in pixels. 01274 */ 01275 (void) ParseGeometry(geometry,&geometry_info); 01276 area=geometry_info.rho; 01277 distance=sqrt((double) former_width*former_height); 01278 scale.x=former_width/(distance/sqrt((double) area)); 01279 scale.y=former_height/(distance/sqrt((double) area)); 01280 if ((scale.x < (double) *width) || (scale.y < (double) *height)) 01281 { 01282 *width=(size_t) (former_width/(distance/sqrt(area))+0.5); 01283 *height=(size_t) (former_height/(distance/sqrt(area))+0.5); 01284 } 01285 former_width=(*width); 01286 former_height=(*height); 01287 } 01288 return(flags); 01289 } 01290 01291 /* 01292 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01293 % % 01294 % % 01295 % % 01296 % P a r s e P a g e G e o m e t r y % 01297 % % 01298 % % 01299 % % 01300 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01301 % 01302 % ParsePageGeometry() returns a region as defined by the geometry string with 01303 % respect to the image page (canvas) dimensions. 01304 % 01305 % WARNING: Percentage dimensions remain relative to the actual image 01306 % dimensions, and not canvas dimensions. 01307 % 01308 % The format of the ParsePageGeometry method is: 01309 % 01310 % MagickStatusType ParsePageGeometry(const Image *image, 01311 % const char *geometry,RectangeInfo *region_info, 01312 % ExceptionInfo *exception) 01313 % 01314 % A description of each parameter follows: 01315 % 01316 % o geometry: The geometry string (e.g. "100x100+10+10"). 01317 % 01318 % o region_info: the region as defined by the geometry string with 01319 % respect to the image and its gravity. 01320 % 01321 % o exception: return any errors or warnings in this structure. 01322 % 01323 */ 01324 MagickExport MagickStatusType ParsePageGeometry(const Image *image, 01325 const char *geometry,RectangleInfo *region_info,ExceptionInfo *exception) 01326 { 01327 MagickStatusType 01328 flags; 01329 01330 SetGeometry(image,region_info); 01331 if (image->page.width != 0) 01332 region_info->width=image->page.width; 01333 if (image->page.height != 0) 01334 region_info->height=image->page.height; 01335 flags=ParseAbsoluteGeometry(geometry,region_info); 01336 if (flags == NoValue) 01337 { 01338 (void) ThrowMagickException(exception,GetMagickModule(),OptionError, 01339 "InvalidGeometry","`%s'",geometry); 01340 return(flags); 01341 } 01342 if ((flags & PercentValue) != 0) 01343 { 01344 region_info->width=image->columns; 01345 region_info->height=image->rows; 01346 } 01347 flags=ParseMetaGeometry(geometry,®ion_info->x,®ion_info->y, 01348 ®ion_info->width,®ion_info->height); 01349 return(flags); 01350 } 01351 01352 /* 01353 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01354 % % 01355 % % 01356 % % 01357 % P a r s e R e g i o n G e o m e t r y % 01358 % % 01359 % % 01360 % % 01361 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01362 % 01363 % ParseRegionGeometry() returns a region as defined by the geometry string 01364 % with respect to the image dimensions and aspect ratio. 01365 % 01366 % This is basically a wrapper around ParseMetaGeometry. This is typically 01367 % used to parse a geometry string to work out the final integer dimensions 01368 % for image resizing. 01369 % 01370 % The format of the ParseRegionGeometry method is: 01371 % 01372 % MagickStatusType ParseRegionGeometry(const Image *image, 01373 % const char *geometry,RectangeInfo *region_info, 01374 % ExceptionInfo *exception) 01375 % 01376 % A description of each parameter follows: 01377 % 01378 % o geometry: The geometry string (e.g. "100x100+10+10"). 01379 % 01380 % o region_info: the region as defined by the geometry string. 01381 % 01382 % o exception: return any errors or warnings in this structure. 01383 % 01384 */ 01385 MagickExport MagickStatusType ParseRegionGeometry(const Image *image, 01386 const char *geometry,RectangleInfo *region_info,ExceptionInfo *exception) 01387 { 01388 MagickStatusType 01389 flags; 01390 01391 SetGeometry(image,region_info); 01392 flags=ParseMetaGeometry(geometry,®ion_info->x,®ion_info->y, 01393 ®ion_info->width,®ion_info->height); 01394 if (flags == NoValue) 01395 (void) ThrowMagickException(exception,GetMagickModule(),OptionError, 01396 "InvalidGeometry","`%s'",geometry); 01397 return(flags); 01398 } 01399 01400 /* 01401 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01402 % % 01403 % % 01404 % % 01405 % S e t G e o m e t r y % 01406 % % 01407 % % 01408 % % 01409 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01410 % 01411 % SetGeometry() sets the geometry to its default values. 01412 % 01413 % The format of the SetGeometry method is: 01414 % 01415 % SetGeometry(const Image *image,RectangleInfo *geometry) 01416 % 01417 % A description of each parameter follows: 01418 % 01419 % o image: the image. 01420 % 01421 % o geometry: the geometry. 01422 % 01423 */ 01424 MagickExport void SetGeometry(const Image *image,RectangleInfo *geometry) 01425 { 01426 assert(image != (Image *) NULL); 01427 assert(image->signature == MagickSignature); 01428 if (image->debug != MagickFalse) 01429 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename); 01430 assert(geometry != (RectangleInfo *) NULL); 01431 (void) ResetMagickMemory(geometry,0,sizeof(*geometry)); 01432 geometry->width=image->columns; 01433 geometry->height=image->rows; 01434 } 01435 01436 /* 01437 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01438 % % 01439 % % 01440 % % 01441 % S e t G e o m e t r y I n f o % 01442 % % 01443 % % 01444 % % 01445 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% 01446 % 01447 % SetGeometryInfo sets the GeometryInfo structure to its default values. 01448 % 01449 % The format of the SetGeometryInfo method is: 01450 % 01451 % SetGeometryInfo(GeometryInfo *geometry_info) 01452 % 01453 % A description of each parameter follows: 01454 % 01455 % o geometry_info: the geometry info structure. 01456 % 01457 */ 01458 MagickExport void SetGeometryInfo(GeometryInfo *geometry_info) 01459 { 01460 assert(geometry_info != (GeometryInfo *) NULL); 01461 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"..."); 01462 (void) ResetMagickMemory(geometry_info,0,sizeof(*geometry_info)); 01463 }