Mercurial > sdl-ios-xcode
comparison src/video/SDL_renderer_sw.c @ 3536:0267b8b1595c
Added interfaces for batch drawing of points, lines and rects:
SDL_DrawPoints()
SDL_BlendPoints()
SDL_BlendLines()
SDL_DrawLines()
SDL_FillRects()
SDL_BlendRects()
SDL_RenderPoints()
SDL_RenderLines()
SDL_RenderRects()
Renamed SDL_RenderFill() to SDL_RenderRect()
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Wed, 09 Dec 2009 15:56:56 +0000 |
parents | 9f62f47d989b |
children | f638ded38b8a |
comparison
equal
deleted
inserted
replaced
3535:b403f790df65 | 3536:0267b8b1595c |
---|---|
57 int pitch); | 57 int pitch); |
58 static int SW_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture, | 58 static int SW_LockTexture(SDL_Renderer * renderer, SDL_Texture * texture, |
59 const SDL_Rect * rect, int markDirty, void **pixels, | 59 const SDL_Rect * rect, int markDirty, void **pixels, |
60 int *pitch); | 60 int *pitch); |
61 static void SW_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture); | 61 static void SW_UnlockTexture(SDL_Renderer * renderer, SDL_Texture * texture); |
62 static int SW_RenderPoint(SDL_Renderer * renderer, int x, int y); | 62 static int SW_RenderPoints(SDL_Renderer * renderer, const SDL_Point * points, |
63 static int SW_RenderLine(SDL_Renderer * renderer, int x1, int y1, int x2, | 63 int count); |
64 int y2); | 64 static int SW_RenderLines(SDL_Renderer * renderer, const SDL_Point * points, |
65 static int SW_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect); | 65 int count); |
66 static int SW_RenderRects(SDL_Renderer * renderer, const SDL_Rect ** rects, | |
67 int count); | |
66 static int SW_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture, | 68 static int SW_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture, |
67 const SDL_Rect * srcrect, const SDL_Rect * dstrect); | 69 const SDL_Rect * srcrect, const SDL_Rect * dstrect); |
68 static int SW_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect, | 70 static int SW_RenderReadPixels(SDL_Renderer * renderer, const SDL_Rect * rect, |
69 Uint32 format, void * pixels, int pitch); | 71 Uint32 format, void * pixels, int pitch); |
70 static int SW_RenderWritePixels(SDL_Renderer * renderer, const SDL_Rect * rect, | 72 static int SW_RenderWritePixels(SDL_Renderer * renderer, const SDL_Rect * rect, |
226 return NULL; | 228 return NULL; |
227 } | 229 } |
228 renderer->ActivateRenderer = SW_ActivateRenderer; | 230 renderer->ActivateRenderer = SW_ActivateRenderer; |
229 renderer->DisplayModeChanged = SW_DisplayModeChanged; | 231 renderer->DisplayModeChanged = SW_DisplayModeChanged; |
230 | 232 |
231 renderer->RenderPoint = SW_RenderPoint; | 233 renderer->RenderPoints = SW_RenderPoints; |
232 renderer->RenderLine = SW_RenderLine; | 234 renderer->RenderLines = SW_RenderLines; |
233 renderer->RenderFill = SW_RenderFill; | 235 renderer->RenderRects = SW_RenderRects; |
234 renderer->RenderCopy = SW_RenderCopy; | 236 renderer->RenderCopy = SW_RenderCopy; |
235 renderer->RenderReadPixels = SW_RenderReadPixels; | 237 renderer->RenderReadPixels = SW_RenderReadPixels; |
236 renderer->RenderWritePixels = SW_RenderWritePixels; | 238 renderer->RenderWritePixels = SW_RenderWritePixels; |
237 renderer->RenderPresent = SW_RenderPresent; | 239 renderer->RenderPresent = SW_RenderPresent; |
238 renderer->DestroyRenderer = SW_DestroyRenderer; | 240 renderer->DestroyRenderer = SW_DestroyRenderer; |
535 SDL_SW_UnlockYUVTexture((SDL_SW_YUVTexture *) texture->driverdata); | 537 SDL_SW_UnlockYUVTexture((SDL_SW_YUVTexture *) texture->driverdata); |
536 } | 538 } |
537 } | 539 } |
538 | 540 |
539 static int | 541 static int |
540 SW_RenderPoint(SDL_Renderer * renderer, int x, int y) | 542 SW_RenderPoints(SDL_Renderer * renderer, const SDL_Point * points, int count) |
541 { | 543 { |
542 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; | 544 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; |
545 SDL_Texture *texture = data->texture[data->current_texture]; | |
543 SDL_Rect rect; | 546 SDL_Rect rect; |
544 int status; | 547 int i; |
545 | 548 int x, y; |
546 rect.x = x; | 549 int status = 0; |
547 rect.y = y; | 550 |
548 rect.w = 1; | 551 /* Get the smallest rectangle that contains everything */ |
549 rect.h = 1; | 552 rect.x = 0; |
553 rect.y = 0; | |
554 rect.w = texture->w; | |
555 rect.h = texture->h; | |
556 if (!SDL_EnclosePoints(points, count, &rect, &rect)) { | |
557 /* Nothing to draw */ | |
558 return 0; | |
559 } | |
550 | 560 |
551 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { | 561 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { |
552 SDL_AddDirtyRect(&data->dirty, &rect); | 562 SDL_AddDirtyRect(&data->dirty, &rect); |
553 } | 563 } |
554 | 564 |
555 if (data->renderer->LockTexture(data->renderer, | 565 if (data->renderer->LockTexture(data->renderer, texture, &rect, 1, |
556 data->texture[data->current_texture], | |
557 &rect, 1, | |
558 &data->surface.pixels, | 566 &data->surface.pixels, |
559 &data->surface.pitch) < 0) { | 567 &data->surface.pitch) < 0) { |
560 return -1; | 568 return -1; |
561 } | 569 } |
562 | 570 |
563 data->surface.w = 1; | 571 data->surface.clip_rect.w = data->surface.w = rect.w; |
564 data->surface.h = 1; | 572 data->surface.clip_rect.h = data->surface.h = rect.h; |
565 data->surface.clip_rect.w = 1; | 573 |
566 data->surface.clip_rect.h = 1; | 574 /* Draw the points! */ |
567 | |
568 if (renderer->blendMode == SDL_BLENDMODE_NONE || | 575 if (renderer->blendMode == SDL_BLENDMODE_NONE || |
569 renderer->blendMode == SDL_BLENDMODE_MASK) { | 576 renderer->blendMode == SDL_BLENDMODE_MASK) { |
570 Uint32 color = | 577 Uint32 color = SDL_MapRGBA(data->surface.format, |
571 SDL_MapRGBA(data->surface.format, renderer->r, renderer->g, | 578 renderer->r, renderer->g, renderer->b, |
572 renderer->b, renderer->a); | 579 renderer->a); |
573 | 580 |
574 status = SDL_DrawPoint(&data->surface, 0, 0, color); | 581 for (i = 0; i < count; ++i) { |
575 } else { | 582 x = points[i].x - rect.x; |
576 status = | 583 y = points[i].y - rect.y; |
577 SDL_BlendPoint(&data->surface, 0, 0, renderer->blendMode, | 584 |
578 renderer->r, renderer->g, renderer->b, | 585 status = SDL_DrawPoint(&data->surface, x, y, color); |
579 renderer->a); | 586 } |
580 } | 587 } else { |
581 | 588 for (i = 0; i < count; ++i) { |
582 data->renderer->UnlockTexture(data->renderer, | 589 x = points[i].x - rect.x; |
583 data->texture[data->current_texture]); | 590 y = points[i].y - rect.y; |
591 | |
592 status = SDL_BlendPoint(&data->surface, x, y, | |
593 renderer->blendMode, | |
594 renderer->r, renderer->g, renderer->b, | |
595 renderer->a); | |
596 } | |
597 } | |
598 | |
599 data->renderer->UnlockTexture(data->renderer, texture); | |
600 | |
584 return status; | 601 return status; |
585 } | 602 } |
586 | 603 |
587 static int | 604 static int |
588 SW_RenderLine(SDL_Renderer * renderer, int x1, int y1, int x2, int y2) | 605 SW_RenderLines(SDL_Renderer * renderer, const SDL_Point * points, int count) |
589 { | 606 { |
590 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; | 607 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; |
591 SDL_Rect rect; | 608 SDL_Texture *texture = data->texture[data->current_texture]; |
592 int status; | 609 SDL_Rect clip, rect; |
593 | 610 int i; |
594 if (x1 < x2) { | 611 int x1, y1, x2, y2; |
595 rect.x = x1; | 612 int status = 0; |
596 rect.w = (x2 - x1) + 1; | 613 |
597 x2 -= x1; | 614 /* Get the smallest rectangle that contains everything */ |
598 x1 = 0; | 615 clip.x = 0; |
599 } else { | 616 clip.y = 0; |
600 rect.x = x2; | 617 clip.w = texture->w; |
601 rect.w = (x1 - x2) + 1; | 618 clip.h = texture->h; |
602 x1 -= x2; | 619 SDL_EnclosePoints(points, count, NULL, &rect); |
603 x2 = 0; | 620 if (!SDL_IntersectRect(&rect, &clip, &rect)) { |
604 } | 621 /* Nothing to draw */ |
605 if (y1 < y2) { | 622 return 0; |
606 rect.y = y1; | |
607 rect.h = (y2 - y1) + 1; | |
608 y2 -= y1; | |
609 y1 = 0; | |
610 } else { | |
611 rect.y = y2; | |
612 rect.h = (y1 - y2) + 1; | |
613 y1 -= y2; | |
614 y2 = 0; | |
615 } | 623 } |
616 | 624 |
617 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { | 625 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { |
618 SDL_AddDirtyRect(&data->dirty, &rect); | 626 SDL_AddDirtyRect(&data->dirty, &rect); |
619 } | 627 } |
620 | 628 |
621 if (data->renderer->LockTexture(data->renderer, | 629 if (data->renderer->LockTexture(data->renderer, texture, &rect, 1, |
622 data->texture[data->current_texture], | |
623 &rect, 1, | |
624 &data->surface.pixels, | 630 &data->surface.pixels, |
625 &data->surface.pitch) < 0) { | 631 &data->surface.pitch) < 0) { |
626 return -1; | 632 return -1; |
627 } | 633 } |
628 | 634 |
629 data->surface.w = rect.w; | 635 data->surface.clip_rect.w = data->surface.w = rect.w; |
630 data->surface.h = rect.h; | 636 data->surface.clip_rect.h = data->surface.h = rect.h; |
631 data->surface.clip_rect.w = rect.w; | 637 |
632 data->surface.clip_rect.h = rect.h; | 638 /* Draw the points! */ |
633 | |
634 if (renderer->blendMode == SDL_BLENDMODE_NONE || | 639 if (renderer->blendMode == SDL_BLENDMODE_NONE || |
635 renderer->blendMode == SDL_BLENDMODE_MASK) { | 640 renderer->blendMode == SDL_BLENDMODE_MASK) { |
636 Uint32 color = | 641 Uint32 color = SDL_MapRGBA(data->surface.format, |
637 SDL_MapRGBA(data->surface.format, renderer->r, renderer->g, | 642 renderer->r, renderer->g, renderer->b, |
638 renderer->b, renderer->a); | 643 renderer->a); |
639 | 644 |
640 status = SDL_DrawLine(&data->surface, x1, y1, x2, y2, color); | 645 for (i = 1; i < count; ++i) { |
641 } else { | 646 x1 = points[i-1].x - rect.x; |
642 status = | 647 y1 = points[i-1].y - rect.y; |
643 SDL_BlendLine(&data->surface, x1, y1, x2, y2, renderer->blendMode, | 648 x2 = points[i].x - rect.x; |
644 renderer->r, renderer->g, renderer->b, renderer->a); | 649 y2 = points[i].y - rect.y; |
645 } | 650 |
646 | 651 status = SDL_DrawLine(&data->surface, x1, y1, x2, y2, color); |
647 data->renderer->UnlockTexture(data->renderer, | 652 } |
648 data->texture[data->current_texture]); | 653 } else { |
654 for (i = 1; i < count; ++i) { | |
655 x1 = points[i-1].x - rect.x; | |
656 y1 = points[i-1].y - rect.y; | |
657 x2 = points[i].x - rect.x; | |
658 y2 = points[i].y - rect.y; | |
659 | |
660 status = SDL_BlendLine(&data->surface, x1, y1, x2, y2, | |
661 renderer->blendMode, | |
662 renderer->r, renderer->g, renderer->b, | |
663 renderer->a); | |
664 } | |
665 } | |
666 | |
667 data->renderer->UnlockTexture(data->renderer, texture); | |
668 | |
649 return status; | 669 return status; |
650 } | 670 } |
651 | 671 |
652 static int | 672 static int |
653 SW_RenderFill(SDL_Renderer * renderer, const SDL_Rect * rect) | 673 SW_RenderRects(SDL_Renderer * renderer, const SDL_Rect ** rects, int count) |
654 { | 674 { |
655 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; | 675 SW_RenderData *data = (SW_RenderData *) renderer->driverdata; |
656 SDL_Rect real_rect; | 676 SDL_Texture *texture = data->texture[data->current_texture]; |
657 int status; | 677 SDL_Rect clip, rect; |
658 | 678 Uint32 color = 0; |
659 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { | 679 int i; |
660 SDL_AddDirtyRect(&data->dirty, rect); | 680 int status = 0; |
661 } | 681 |
662 | 682 clip.x = 0; |
663 if (data->renderer->LockTexture(data->renderer, | 683 clip.y = 0; |
664 data->texture[data->current_texture], | 684 clip.w = texture->w; |
665 rect, 1, &data->surface.pixels, | 685 clip.h = texture->h; |
666 &data->surface.pitch) < 0) { | 686 |
667 return -1; | 687 if (renderer->blendMode == SDL_BLENDMODE_NONE || |
668 } | 688 renderer->blendMode == SDL_BLENDMODE_MASK) { |
669 | 689 color = SDL_MapRGBA(data->surface.format, |
670 data->surface.w = rect->w; | 690 renderer->r, renderer->g, renderer->b, |
671 data->surface.h = rect->h; | 691 renderer->a); |
672 data->surface.clip_rect.w = rect->w; | 692 } |
673 data->surface.clip_rect.h = rect->h; | 693 |
674 real_rect = data->surface.clip_rect; | 694 for (i = 0; i < count; ++i) { |
675 | 695 if (!SDL_IntersectRect(rects[i], &clip, &rect)) { |
676 if (renderer->blendMode == SDL_BLENDMODE_NONE) { | 696 /* Nothing to draw */ |
677 Uint32 color = | 697 continue; |
678 SDL_MapRGBA(data->surface.format, renderer->r, renderer->g, | 698 } |
679 renderer->b, renderer->a); | 699 |
680 | 700 if (data->renderer->info.flags & SDL_RENDERER_PRESENTCOPY) { |
681 status = SDL_FillRect(&data->surface, &real_rect, color); | 701 SDL_AddDirtyRect(&data->dirty, &rect); |
682 } else { | 702 } |
683 status = | 703 |
684 SDL_BlendRect(&data->surface, &real_rect, renderer->blendMode, | 704 if (data->renderer->LockTexture(data->renderer, texture, &rect, 1, |
685 renderer->r, renderer->g, renderer->b, renderer->a); | 705 &data->surface.pixels, |
686 } | 706 &data->surface.pitch) < 0) { |
687 | 707 return -1; |
688 data->renderer->UnlockTexture(data->renderer, | 708 } |
689 data->texture[data->current_texture]); | 709 |
710 data->surface.clip_rect.w = data->surface.w = rect.w; | |
711 data->surface.clip_rect.h = data->surface.h = rect.h; | |
712 | |
713 if (renderer->blendMode == SDL_BLENDMODE_NONE || | |
714 renderer->blendMode == SDL_BLENDMODE_MASK) { | |
715 status = SDL_FillRect(&data->surface, NULL, color); | |
716 } else { | |
717 status = SDL_BlendRect(&data->surface, NULL, | |
718 renderer->blendMode, | |
719 renderer->r, renderer->g, renderer->b, | |
720 renderer->a); | |
721 } | |
722 | |
723 data->renderer->UnlockTexture(data->renderer, texture); | |
724 } | |
690 return status; | 725 return status; |
691 } | 726 } |
692 | 727 |
693 static int | 728 static int |
694 SW_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture, | 729 SW_RenderCopy(SDL_Renderer * renderer, SDL_Texture * texture, |