mifillarc.c revision 05b261ec
1/************************************************************ 2 3Copyright 1989, 1998 The Open Group 4 5Permission to use, copy, modify, distribute, and sell this software and its 6documentation for any purpose is hereby granted without fee, provided that 7the above copyright notice appear in all copies and that both that 8copyright notice and this permission notice appear in supporting 9documentation. 10 11The above copyright notice and this permission notice shall be included in 12all copies or substantial portions of the Software. 13 14THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 17OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 18AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 19CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 20 21Except as contained in this notice, the name of The Open Group shall not be 22used in advertising or otherwise to promote the sale, use or other dealings 23in this Software without prior written authorization from The Open Group. 24 25Author: Bob Scheifler, MIT X Consortium 26 27********************************************************/ 28 29 30#ifdef HAVE_DIX_CONFIG_H 31#include <dix-config.h> 32#endif 33 34#include <math.h> 35#include <X11/X.h> 36#include <X11/Xprotostr.h> 37#include "regionstr.h" 38#include "gcstruct.h" 39#include "pixmapstr.h" 40#include "mifpoly.h" 41#include "mi.h" 42#include "mifillarc.h" 43 44#define QUADRANT (90 * 64) 45#define HALFCIRCLE (180 * 64) 46#define QUADRANT3 (270 * 64) 47 48#ifndef M_PI 49#define M_PI 3.14159265358979323846 50#endif 51 52#define Dsin(d) sin((double)d*(M_PI/11520.0)) 53#define Dcos(d) cos((double)d*(M_PI/11520.0)) 54 55_X_EXPORT void 56miFillArcSetup(arc, info) 57 xArc *arc; 58 miFillArcRec *info; 59{ 60 info->y = arc->height >> 1; 61 info->dy = arc->height & 1; 62 info->yorg = arc->y + info->y; 63 info->dx = arc->width & 1; 64 info->xorg = arc->x + (arc->width >> 1) + info->dx; 65 info->dx = 1 - info->dx; 66 if (arc->width == arc->height) 67 { 68 /* (2x - 2xorg)^2 = d^2 - (2y - 2yorg)^2 */ 69 /* even: xorg = yorg = 0 odd: xorg = .5, yorg = -.5 */ 70 info->ym = 8; 71 info->xm = 8; 72 info->yk = info->y << 3; 73 if (!info->dx) 74 { 75 info->xk = 0; 76 info->e = -1; 77 } 78 else 79 { 80 info->y++; 81 info->yk += 4; 82 info->xk = -4; 83 info->e = - (info->y << 3); 84 } 85 } 86 else 87 { 88 /* h^2 * (2x - 2xorg)^2 = w^2 * h^2 - w^2 * (2y - 2yorg)^2 */ 89 /* even: xorg = yorg = 0 odd: xorg = .5, yorg = -.5 */ 90 info->ym = (arc->width * arc->width) << 3; 91 info->xm = (arc->height * arc->height) << 3; 92 info->yk = info->y * info->ym; 93 if (!info->dy) 94 info->yk -= info->ym >> 1; 95 if (!info->dx) 96 { 97 info->xk = 0; 98 info->e = - (info->xm >> 3); 99 } 100 else 101 { 102 info->y++; 103 info->yk += info->ym; 104 info->xk = -(info->xm >> 1); 105 info->e = info->xk - info->yk; 106 } 107 } 108} 109 110static void 111miFillArcDSetup(xArc *arc, miFillArcDRec *info) 112{ 113 /* h^2 * (2x - 2xorg)^2 = w^2 * h^2 - w^2 * (2y - 2yorg)^2 */ 114 /* even: xorg = yorg = 0 odd: xorg = .5, yorg = -.5 */ 115 info->y = arc->height >> 1; 116 info->dy = arc->height & 1; 117 info->yorg = arc->y + info->y; 118 info->dx = arc->width & 1; 119 info->xorg = arc->x + (arc->width >> 1) + info->dx; 120 info->dx = 1 - info->dx; 121 info->ym = ((double)arc->width) * (arc->width * 8); 122 info->xm = ((double)arc->height) * (arc->height * 8); 123 info->yk = info->y * info->ym; 124 if (!info->dy) 125 info->yk -= info->ym / 2.0; 126 if (!info->dx) 127 { 128 info->xk = 0; 129 info->e = - (info->xm / 8.0); 130 } 131 else 132 { 133 info->y++; 134 info->yk += info->ym; 135 info->xk = -info->xm / 2.0; 136 info->e = info->xk - info->yk; 137 } 138} 139 140static void 141miGetArcEdge( 142 xArc *arc, 143 miSliceEdgePtr edge, 144 int k, 145 Bool top, 146 Bool left ) 147{ 148 int xady, y; 149 150 y = arc->height >> 1; 151 if (!(arc->width & 1)) 152 y++; 153 if (!top) 154 { 155 y = -y; 156 if (arc->height & 1) 157 y--; 158 } 159 xady = k + y * edge->dx; 160 if (xady <= 0) 161 edge->x = - ((-xady) / edge->dy + 1); 162 else 163 edge->x = (xady - 1) / edge->dy; 164 edge->e = xady - edge->x * edge->dy; 165 if ((top && (edge->dx < 0)) || (!top && (edge->dx > 0))) 166 edge->e = edge->dy - edge->e + 1; 167 if (left) 168 edge->x++; 169 edge->x += arc->x + (arc->width >> 1); 170 if (edge->dx > 0) 171 { 172 edge->deltax = 1; 173 edge->stepx = edge->dx / edge->dy; 174 edge->dx = edge->dx % edge->dy; 175 } 176 else 177 { 178 edge->deltax = -1; 179 edge->stepx = - ((-edge->dx) / edge->dy); 180 edge->dx = (-edge->dx) % edge->dy; 181 } 182 if (!top) 183 { 184 edge->deltax = -edge->deltax; 185 edge->stepx = -edge->stepx; 186 } 187} 188 189static void 190miEllipseAngleToSlope (int angle, int width, int height, int *dxp, int *dyp, 191 double *d_dxp, double *d_dyp) 192{ 193 int dx, dy; 194 double d_dx, d_dy, scale; 195 Bool negative_dx, negative_dy; 196 197 switch (angle) { 198 case 0: 199 *dxp = -1; 200 *dyp = 0; 201 if (d_dxp) { 202 *d_dxp = width / 2.0; 203 *d_dyp = 0; 204 } 205 break; 206 case QUADRANT: 207 *dxp = 0; 208 *dyp = 1; 209 if (d_dxp) { 210 *d_dxp = 0; 211 *d_dyp = - height / 2.0; 212 } 213 break; 214 case HALFCIRCLE: 215 *dxp = 1; 216 *dyp = 0; 217 if (d_dxp) { 218 *d_dxp = - width / 2.0; 219 *d_dyp = 0; 220 } 221 break; 222 case QUADRANT3: 223 *dxp = 0; 224 *dyp = -1; 225 if (d_dxp) { 226 *d_dxp = 0; 227 *d_dyp = height / 2.0; 228 } 229 break; 230 default: 231 d_dx = Dcos(angle) * width; 232 d_dy = Dsin(angle) * height; 233 if (d_dxp) { 234 *d_dxp = d_dx / 2.0; 235 *d_dyp = - d_dy / 2.0; 236 } 237 negative_dx = FALSE; 238 if (d_dx < 0.0) 239 { 240 d_dx = -d_dx; 241 negative_dx = TRUE; 242 } 243 negative_dy = FALSE; 244 if (d_dy < 0.0) 245 { 246 d_dy = -d_dy; 247 negative_dy = TRUE; 248 } 249 scale = d_dx; 250 if (d_dy > d_dx) 251 scale = d_dy; 252 dx = floor ((d_dx * 32768) / scale + 0.5); 253 if (negative_dx) 254 dx = -dx; 255 *dxp = dx; 256 dy = floor ((d_dy * 32768) / scale + 0.5); 257 if (negative_dy) 258 dy = -dy; 259 *dyp = dy; 260 break; 261 } 262} 263 264static void 265miGetPieEdge( 266 xArc *arc, 267 int angle, 268 miSliceEdgePtr edge, 269 Bool top, 270 Bool left ) 271{ 272 int k; 273 int dx, dy; 274 275 miEllipseAngleToSlope (angle, arc->width, arc->height, &dx, &dy, 0, 0); 276 277 if (dy == 0) 278 { 279 edge->x = left ? -65536 : 65536; 280 edge->stepx = 0; 281 edge->e = 0; 282 edge->dx = -1; 283 return; 284 } 285 if (dx == 0) 286 { 287 edge->x = arc->x + (arc->width >> 1); 288 if (left && (arc->width & 1)) 289 edge->x++; 290 else if (!left && !(arc->width & 1)) 291 edge->x--; 292 edge->stepx = 0; 293 edge->e = 0; 294 edge->dx = -1; 295 return; 296 } 297 if (dy < 0) { 298 dx = -dx; 299 dy = -dy; 300 } 301 k = (arc->height & 1) ? dx : 0; 302 if (arc->width & 1) 303 k += dy; 304 edge->dx = dx << 1; 305 edge->dy = dy << 1; 306 miGetArcEdge(arc, edge, k, top, left); 307} 308 309_X_EXPORT void 310miFillArcSliceSetup(arc, slice, pGC) 311 xArc *arc; 312 miArcSliceRec *slice; 313 GCPtr pGC; 314{ 315 int angle1, angle2; 316 317 angle1 = arc->angle1; 318 if (arc->angle2 < 0) 319 { 320 angle2 = angle1; 321 angle1 += arc->angle2; 322 } 323 else 324 angle2 = angle1 + arc->angle2; 325 while (angle1 < 0) 326 angle1 += FULLCIRCLE; 327 while (angle1 >= FULLCIRCLE) 328 angle1 -= FULLCIRCLE; 329 while (angle2 < 0) 330 angle2 += FULLCIRCLE; 331 while (angle2 >= FULLCIRCLE) 332 angle2 -= FULLCIRCLE; 333 slice->min_top_y = 0; 334 slice->max_top_y = arc->height >> 1; 335 slice->min_bot_y = 1 - (arc->height & 1); 336 slice->max_bot_y = slice->max_top_y - 1; 337 slice->flip_top = FALSE; 338 slice->flip_bot = FALSE; 339 if (pGC->arcMode == ArcPieSlice) 340 { 341 slice->edge1_top = (angle1 < HALFCIRCLE); 342 slice->edge2_top = (angle2 <= HALFCIRCLE); 343 if ((angle2 == 0) || (angle1 == HALFCIRCLE)) 344 { 345 if (angle2 ? slice->edge2_top : slice->edge1_top) 346 slice->min_top_y = slice->min_bot_y; 347 else 348 slice->min_top_y = arc->height; 349 slice->min_bot_y = 0; 350 } 351 else if ((angle1 == 0) || (angle2 == HALFCIRCLE)) 352 { 353 slice->min_top_y = slice->min_bot_y; 354 if (angle1 ? slice->edge1_top : slice->edge2_top) 355 slice->min_bot_y = arc->height; 356 else 357 slice->min_bot_y = 0; 358 } 359 else if (slice->edge1_top == slice->edge2_top) 360 { 361 if (angle2 < angle1) 362 { 363 slice->flip_top = slice->edge1_top; 364 slice->flip_bot = !slice->edge1_top; 365 } 366 else if (slice->edge1_top) 367 { 368 slice->min_top_y = 1; 369 slice->min_bot_y = arc->height; 370 } 371 else 372 { 373 slice->min_bot_y = 0; 374 slice->min_top_y = arc->height; 375 } 376 } 377 miGetPieEdge(arc, angle1, &slice->edge1, 378 slice->edge1_top, !slice->edge1_top); 379 miGetPieEdge(arc, angle2, &slice->edge2, 380 slice->edge2_top, slice->edge2_top); 381 } 382 else 383 { 384 double w2, h2, x1, y1, x2, y2, dx, dy, scale; 385 int signdx, signdy, y, k; 386 Bool isInt1 = TRUE, isInt2 = TRUE; 387 388 w2 = (double)arc->width / 2.0; 389 h2 = (double)arc->height / 2.0; 390 if ((angle1 == 0) || (angle1 == HALFCIRCLE)) 391 { 392 x1 = angle1 ? -w2 : w2; 393 y1 = 0.0; 394 } 395 else if ((angle1 == QUADRANT) || (angle1 == QUADRANT3)) 396 { 397 x1 = 0.0; 398 y1 = (angle1 == QUADRANT) ? h2 : -h2; 399 } 400 else 401 { 402 isInt1 = FALSE; 403 x1 = Dcos(angle1) * w2; 404 y1 = Dsin(angle1) * h2; 405 } 406 if ((angle2 == 0) || (angle2 == HALFCIRCLE)) 407 { 408 x2 = angle2 ? -w2 : w2; 409 y2 = 0.0; 410 } 411 else if ((angle2 == QUADRANT) || (angle2 == QUADRANT3)) 412 { 413 x2 = 0.0; 414 y2 = (angle2 == QUADRANT) ? h2 : -h2; 415 } 416 else 417 { 418 isInt2 = FALSE; 419 x2 = Dcos(angle2) * w2; 420 y2 = Dsin(angle2) * h2; 421 } 422 dx = x2 - x1; 423 dy = y2 - y1; 424 if (arc->height & 1) 425 { 426 y1 -= 0.5; 427 y2 -= 0.5; 428 } 429 if (arc->width & 1) 430 { 431 x1 += 0.5; 432 x2 += 0.5; 433 } 434 if (dy < 0.0) 435 { 436 dy = -dy; 437 signdy = -1; 438 } 439 else 440 signdy = 1; 441 if (dx < 0.0) 442 { 443 dx = -dx; 444 signdx = -1; 445 } 446 else 447 signdx = 1; 448 if (isInt1 && isInt2) 449 { 450 slice->edge1.dx = dx * 2; 451 slice->edge1.dy = dy * 2; 452 } 453 else 454 { 455 scale = (dx > dy) ? dx : dy; 456 slice->edge1.dx = floor((dx * 32768) / scale + .5); 457 slice->edge1.dy = floor((dy * 32768) / scale + .5); 458 } 459 if (!slice->edge1.dy) 460 { 461 if (signdx < 0) 462 { 463 y = floor(y1 + 1.0); 464 if (y >= 0) 465 { 466 slice->min_top_y = y; 467 slice->min_bot_y = arc->height; 468 } 469 else 470 { 471 slice->max_bot_y = -y - (arc->height & 1); 472 } 473 } 474 else 475 { 476 y = floor(y1); 477 if (y >= 0) 478 slice->max_top_y = y; 479 else 480 { 481 slice->min_top_y = arc->height; 482 slice->min_bot_y = -y - (arc->height & 1); 483 } 484 } 485 slice->edge1_top = TRUE; 486 slice->edge1.x = 65536; 487 slice->edge1.stepx = 0; 488 slice->edge1.e = 0; 489 slice->edge1.dx = -1; 490 slice->edge2 = slice->edge1; 491 slice->edge2_top = FALSE; 492 } 493 else if (!slice->edge1.dx) 494 { 495 if (signdy < 0) 496 x1 -= 1.0; 497 slice->edge1.x = ceil(x1); 498 slice->edge1_top = signdy < 0; 499 slice->edge1.x += arc->x + (arc->width >> 1); 500 slice->edge1.stepx = 0; 501 slice->edge1.e = 0; 502 slice->edge1.dx = -1; 503 slice->edge2_top = !slice->edge1_top; 504 slice->edge2 = slice->edge1; 505 } 506 else 507 { 508 if (signdx < 0) 509 slice->edge1.dx = -slice->edge1.dx; 510 if (signdy < 0) 511 slice->edge1.dx = -slice->edge1.dx; 512 k = ceil(((x1 + x2) * slice->edge1.dy - (y1 + y2) * slice->edge1.dx) / 2.0); 513 slice->edge2.dx = slice->edge1.dx; 514 slice->edge2.dy = slice->edge1.dy; 515 slice->edge1_top = signdy < 0; 516 slice->edge2_top = !slice->edge1_top; 517 miGetArcEdge(arc, &slice->edge1, k, 518 slice->edge1_top, !slice->edge1_top); 519 miGetArcEdge(arc, &slice->edge2, k, 520 slice->edge2_top, slice->edge2_top); 521 } 522 } 523} 524 525#define ADDSPANS() \ 526 pts->x = xorg - x; \ 527 pts->y = yorg - y; \ 528 *wids = slw; \ 529 pts++; \ 530 wids++; \ 531 if (miFillArcLower(slw)) \ 532 { \ 533 pts->x = xorg - x; \ 534 pts->y = yorg + y + dy; \ 535 pts++; \ 536 *wids++ = slw; \ 537 } 538 539static void 540miFillEllipseI( 541 DrawablePtr pDraw, 542 GCPtr pGC, 543 xArc *arc ) 544{ 545 int x, y, e; 546 int yk, xk, ym, xm, dx, dy, xorg, yorg; 547 int slw; 548 miFillArcRec info; 549 DDXPointPtr points; 550 DDXPointPtr pts; 551 int *widths; 552 int *wids; 553 554 points = (DDXPointPtr)ALLOCATE_LOCAL(sizeof(DDXPointRec) * arc->height); 555 if (!points) 556 return; 557 widths = (int *)ALLOCATE_LOCAL(sizeof(int) * arc->height); 558 if (!widths) 559 { 560 DEALLOCATE_LOCAL(points); 561 return; 562 } 563 miFillArcSetup(arc, &info); 564 MIFILLARCSETUP(); 565 if (pGC->miTranslate) 566 { 567 xorg += pDraw->x; 568 yorg += pDraw->y; 569 } 570 pts = points; 571 wids = widths; 572 while (y > 0) 573 { 574 MIFILLARCSTEP(slw); 575 ADDSPANS(); 576 } 577 (*pGC->ops->FillSpans)(pDraw, pGC, pts - points, points, widths, FALSE); 578 DEALLOCATE_LOCAL(widths); 579 DEALLOCATE_LOCAL(points); 580} 581 582static void 583miFillEllipseD( 584 DrawablePtr pDraw, 585 GCPtr pGC, 586 xArc *arc ) 587{ 588 int x, y; 589 int xorg, yorg, dx, dy, slw; 590 double e, yk, xk, ym, xm; 591 miFillArcDRec info; 592 DDXPointPtr points; 593 DDXPointPtr pts; 594 int *widths; 595 int *wids; 596 597 points = (DDXPointPtr)ALLOCATE_LOCAL(sizeof(DDXPointRec) * arc->height); 598 if (!points) 599 return; 600 widths = (int *)ALLOCATE_LOCAL(sizeof(int) * arc->height); 601 if (!widths) 602 { 603 DEALLOCATE_LOCAL(points); 604 return; 605 } 606 miFillArcDSetup(arc, &info); 607 MIFILLARCSETUP(); 608 if (pGC->miTranslate) 609 { 610 xorg += pDraw->x; 611 yorg += pDraw->y; 612 } 613 pts = points; 614 wids = widths; 615 while (y > 0) 616 { 617 MIFILLARCSTEP(slw); 618 ADDSPANS(); 619 } 620 (*pGC->ops->FillSpans)(pDraw, pGC, pts - points, points, widths, FALSE); 621 DEALLOCATE_LOCAL(widths); 622 DEALLOCATE_LOCAL(points); 623} 624 625#define ADDSPAN(l,r) \ 626 if (r >= l) \ 627 { \ 628 pts->x = l; \ 629 pts->y = ya; \ 630 pts++; \ 631 *wids++ = r - l + 1; \ 632 } 633 634#define ADDSLICESPANS(flip) \ 635 if (!flip) \ 636 { \ 637 ADDSPAN(xl, xr); \ 638 } \ 639 else \ 640 { \ 641 xc = xorg - x; \ 642 ADDSPAN(xc, xr); \ 643 xc += slw - 1; \ 644 ADDSPAN(xl, xc); \ 645 } 646 647static void 648miFillArcSliceI( 649 DrawablePtr pDraw, 650 GCPtr pGC, 651 xArc *arc ) 652{ 653 int yk, xk, ym, xm, dx, dy, xorg, yorg, slw; 654 int x, y, e; 655 miFillArcRec info; 656 miArcSliceRec slice; 657 int ya, xl, xr, xc; 658 DDXPointPtr points; 659 DDXPointPtr pts; 660 int *widths; 661 int *wids; 662 663 miFillArcSetup(arc, &info); 664 miFillArcSliceSetup(arc, &slice, pGC); 665 MIFILLARCSETUP(); 666 slw = arc->height; 667 if (slice.flip_top || slice.flip_bot) 668 slw += (arc->height >> 1) + 1; 669 points = (DDXPointPtr)ALLOCATE_LOCAL(sizeof(DDXPointRec) * slw); 670 if (!points) 671 return; 672 widths = (int *)ALLOCATE_LOCAL(sizeof(int) * slw); 673 if (!widths) 674 { 675 DEALLOCATE_LOCAL(points); 676 return; 677 } 678 if (pGC->miTranslate) 679 { 680 xorg += pDraw->x; 681 yorg += pDraw->y; 682 slice.edge1.x += pDraw->x; 683 slice.edge2.x += pDraw->x; 684 } 685 pts = points; 686 wids = widths; 687 while (y > 0) 688 { 689 MIFILLARCSTEP(slw); 690 MIARCSLICESTEP(slice.edge1); 691 MIARCSLICESTEP(slice.edge2); 692 if (miFillSliceUpper(slice)) 693 { 694 ya = yorg - y; 695 MIARCSLICEUPPER(xl, xr, slice, slw); 696 ADDSLICESPANS(slice.flip_top); 697 } 698 if (miFillSliceLower(slice)) 699 { 700 ya = yorg + y + dy; 701 MIARCSLICELOWER(xl, xr, slice, slw); 702 ADDSLICESPANS(slice.flip_bot); 703 } 704 } 705 (*pGC->ops->FillSpans)(pDraw, pGC, pts - points, points, widths, FALSE); 706 DEALLOCATE_LOCAL(widths); 707 DEALLOCATE_LOCAL(points); 708} 709 710static void 711miFillArcSliceD( 712 DrawablePtr pDraw, 713 GCPtr pGC, 714 xArc *arc ) 715{ 716 int x, y; 717 int dx, dy, xorg, yorg, slw; 718 double e, yk, xk, ym, xm; 719 miFillArcDRec info; 720 miArcSliceRec slice; 721 int ya, xl, xr, xc; 722 DDXPointPtr points; 723 DDXPointPtr pts; 724 int *widths; 725 int *wids; 726 727 miFillArcDSetup(arc, &info); 728 miFillArcSliceSetup(arc, &slice, pGC); 729 MIFILLARCSETUP(); 730 slw = arc->height; 731 if (slice.flip_top || slice.flip_bot) 732 slw += (arc->height >> 1) + 1; 733 points = (DDXPointPtr)ALLOCATE_LOCAL(sizeof(DDXPointRec) * slw); 734 if (!points) 735 return; 736 widths = (int *)ALLOCATE_LOCAL(sizeof(int) * slw); 737 if (!widths) 738 { 739 DEALLOCATE_LOCAL(points); 740 return; 741 } 742 if (pGC->miTranslate) 743 { 744 xorg += pDraw->x; 745 yorg += pDraw->y; 746 slice.edge1.x += pDraw->x; 747 slice.edge2.x += pDraw->x; 748 } 749 pts = points; 750 wids = widths; 751 while (y > 0) 752 { 753 MIFILLARCSTEP(slw); 754 MIARCSLICESTEP(slice.edge1); 755 MIARCSLICESTEP(slice.edge2); 756 if (miFillSliceUpper(slice)) 757 { 758 ya = yorg - y; 759 MIARCSLICEUPPER(xl, xr, slice, slw); 760 ADDSLICESPANS(slice.flip_top); 761 } 762 if (miFillSliceLower(slice)) 763 { 764 ya = yorg + y + dy; 765 MIARCSLICELOWER(xl, xr, slice, slw); 766 ADDSLICESPANS(slice.flip_bot); 767 } 768 } 769 (*pGC->ops->FillSpans)(pDraw, pGC, pts - points, points, widths, FALSE); 770 DEALLOCATE_LOCAL(widths); 771 DEALLOCATE_LOCAL(points); 772} 773 774/* MIPOLYFILLARC -- The public entry for the PolyFillArc request. 775 * Since we don't have to worry about overlapping segments, we can just 776 * fill each arc as it comes. 777 */ 778_X_EXPORT void 779miPolyFillArc(pDraw, pGC, narcs, parcs) 780 DrawablePtr pDraw; 781 GCPtr pGC; 782 int narcs; 783 xArc *parcs; 784{ 785 int i; 786 xArc *arc; 787 788 for(i = narcs, arc = parcs; --i >= 0; arc++) 789 { 790 if (miFillArcEmpty(arc)) 791 continue;; 792 if ((arc->angle2 >= FULLCIRCLE) || (arc->angle2 <= -FULLCIRCLE)) 793 { 794 if (miCanFillArc(arc)) 795 miFillEllipseI(pDraw, pGC, arc); 796 else 797 miFillEllipseD(pDraw, pGC, arc); 798 } 799 else 800 { 801 if (miCanFillArc(arc)) 802 miFillArcSliceI(pDraw, pGC, arc); 803 else 804 miFillArcSliceD(pDraw, pGC, arc); 805 } 806 } 807} 808