Mercurial > hg > dmlib
comparison gfxconv.c @ 482:6fdee3ec2894
Improve remapping.
author | Matti Hamalainen <ccr@tnsp.org> |
---|---|
date | Wed, 07 Nov 2012 05:22:25 +0200 |
parents | c3f0fca5b596 |
children | f119ebe3ad25 |
comparison
equal
deleted
inserted
replaced
481:c3f0fca5b596 | 482:6fdee3ec2894 |
---|---|
764 } | 764 } |
765 | 765 |
766 | 766 |
767 int dmRemapImageColors(DMImage *image) | 767 int dmRemapImageColors(DMImage *image) |
768 { | 768 { |
769 dmMsg(1, "Remapping %d output image colors.\n", optNRemapTable); | |
770 DMColor *npal = dmCalloc(image->ncolors, sizeof(DMColor)); | 769 DMColor *npal = dmCalloc(image->ncolors, sizeof(DMColor)); |
771 int *mapping = dmMalloc(image->ncolors * sizeof(int)); | 770 int *mapping = dmMalloc(image->ncolors * sizeof(int)); |
772 BOOL *mapped = dmMalloc(image->ncolors * sizeof(BOOL)); | 771 BOOL *mapped = dmMalloc(image->ncolors * sizeof(BOOL)); |
773 BOOL *used = dmMalloc(image->ncolors * sizeof(BOOL)); | 772 BOOL *used = dmMalloc(image->ncolors * sizeof(BOOL)); |
774 int n, index, xc, yc, ncolors = image->ncolors; | 773 int n, index, xc, yc, ncolors; |
774 | |
775 dmMsg(1, "Remapping %d output image colors of %d colors.\n", optNRemapTable, image->ncolors); | |
775 | 776 |
776 if (npal == NULL || mapping == NULL || mapped == NULL || used == NULL) | 777 if (npal == NULL || mapping == NULL || mapped == NULL || used == NULL) |
777 { | 778 { |
778 dmError("Could not allocate memory for reused palette.\n"); | 779 dmError("Could not allocate memory for reused palette.\n"); |
779 return DMERR_MALLOC; | 780 return DMERR_MALLOC; |
780 } | 781 } |
781 | 782 |
782 for (index = 0; index < image->ncolors; index++) | 783 for (index = 0; index < image->ncolors; index++) |
783 { | 784 { |
784 mapping[index] = -1; | 785 mapping[index] = -1; |
785 used[index] = mapped[index] = FALSE; | 786 mapped[index] = used[index] = FALSE; |
786 } | 787 } |
787 | 788 |
788 // Find used colors | 789 // Find used colors |
789 dmMsg(2, "Scanning image for used colors...\n"); | 790 dmMsg(2, "Scanning image for used colors...\n"); |
790 for (yc = 0; yc < image->height; yc++) | 791 for (ncolors = yc = 0; yc < image->height; yc++) |
791 { | 792 { |
792 Uint8 *dp = image->data + image->pitch * yc; | 793 Uint8 *dp = image->data + image->pitch * yc; |
793 for (xc = 0; xc < image->width; xc++) | 794 for (xc = 0; xc < image->width; xc++) |
794 { | 795 { |
795 Uint8 col = dp[xc]; | 796 Uint8 col = dp[xc]; |
796 if (col < image->ncolors) | 797 if (col < image->ncolors && !used[col]) |
798 { | |
797 used[col] = TRUE; | 799 used[col] = TRUE; |
798 } | 800 ncolors++; |
799 } | 801 } |
802 } | |
803 } | |
804 dmMsg(2, "Found %d used colors, creating remap-table.\n", ncolors); | |
800 | 805 |
801 // Match and mark mapped colors | 806 // Match and mark mapped colors |
802 for (index = 0; index < optNRemapTable; index++) | 807 for (index = 0; index < optNRemapTable; index++) |
803 { | 808 { |
804 DMMapValue *map = &optRemapTable[index]; | 809 DMMapValue *map = &optRemapTable[index]; |
811 { | 816 { |
812 dmMsg(3, "RGBA match #%02x%02x%02x%02x: %d -> %d\n", | 817 dmMsg(3, "RGBA match #%02x%02x%02x%02x: %d -> %d\n", |
813 map->color.r, map->color.g, map->color.b, map->color.a, | 818 map->color.r, map->color.g, map->color.b, map->color.a, |
814 n, | 819 n, |
815 map->to); | 820 map->to); |
816 | 821 |
817 if (used[n]) | 822 mapping[n] = map->to; |
818 { | 823 mapped[map->to] = TRUE; |
819 mapping[n] = map->to; | 824 found = TRUE; |
820 mapped[map->to] = TRUE; | |
821 found = TRUE; | |
822 } | |
823 } | 825 } |
824 } | 826 } |
825 | 827 |
826 if (!found) | 828 if (!found) |
827 { | 829 { |
830 map->color.r, map->color.g, map->color.b, map->color.a); | 832 map->color.r, map->color.g, map->color.b, map->color.a); |
831 } | 833 } |
832 } | 834 } |
833 else | 835 else |
834 { | 836 { |
835 if (used[map->from]) | 837 dmMsg(3, "Map index: %d -> %d\n", |
836 { | 838 map->from, map->to); |
837 dmMsg(3, "Map index: %d -> %d\n", | 839 |
838 map->from, map->to); | 840 mapping[map->from] = map->to; |
839 | 841 mapped[map->to] = TRUE; |
840 mapping[map->from] = map->to; | 842 } |
841 mapped[map->to] = TRUE; | 843 } |
842 } | 844 |
843 } | |
844 } | |
845 | 845 |
846 // Fill in the rest | 846 // Fill in the rest |
847 if (optRemapRemove) | 847 if (optRemapRemove) |
848 { | 848 { |
849 dmMsg(2, "Removing unused colors.\n"); | 849 dmMsg(2, "Removing unused colors.\n"); |
870 mapping[index] = n; | 870 mapping[index] = n; |
871 mapped[n] = TRUE; | 871 mapped[n] = TRUE; |
872 break; | 872 break; |
873 } | 873 } |
874 } | 874 } |
875 } | |
876 | |
877 for (index = 0; index < image->ncolors; index++) | |
878 { | |
879 fprintf(stderr, "mapping[%d] = %d\n", index, mapping[index]); | |
875 } | 880 } |
876 | 881 |
877 // Calculate final number of palette colors | 882 // Calculate final number of palette colors |
878 ncolors = 0; | 883 ncolors = 0; |
879 for (index = 0; index < image->ncolors; index++) | 884 for (index = 0; index < image->ncolors; index++) |
880 { | 885 { |
881 if (mapping[index] > ncolors) | 886 if (mapping[index] + 1 > ncolors) |
882 ncolors = mapping[index] + 1; | 887 ncolors = mapping[index] + 1; |
883 } | 888 } |
884 | 889 |
885 // Copy palette entries | 890 // Copy palette entries |
886 for (index = 0; index < ncolors; index++) | 891 for (index = 0; index < image->ncolors; index++) |
887 { | 892 { |
888 if (mapping[index] >= 0) | 893 if (mapping[index] >= 0) |
889 { | 894 { |
890 memcpy(&npal[index], &(image->pal[mapping[index]]), sizeof(DMColor)); | 895 memcpy(&npal[mapping[index]], &(image->pal[index]), sizeof(DMColor)); |
891 } | 896 } |
892 } | 897 } |
893 | 898 |
894 // Remap image | 899 // Remap image |
895 dmMsg(1, "Remapping image to %d colors...\n", ncolors); | 900 dmMsg(1, "Remapping image to %d colors...\n", ncolors); |