コード例 #1
0
ファイル: ImageConverter.cs プロジェクト: cybort/ALDExplorer
        public static void RemapPalette(FreeImageBitmap bitmap, Palette newPalette)
        {
            if (bitmap.ColorDepth > 8)
            {
                bitmap.Quantize(FREE_IMAGE_QUANTIZE.FIQ_WUQUANT, 256, newPalette);
            }

            var sourcePal = bitmap.Palette.AsArray.Select(c => c.uintValue).ToArray();
            var destPal   = newPalette.AsArray.Select(c => c.uintValue).ToArray();

            int[] srcToDest = new int[256];
            for (int i = 0; i < 256; i++)
            {
                srcToDest[i] = -1;
            }

            //first map identical colors
            {
                Dictionary <int, int> rgbToPaletteIndex = new Dictionary <int, int>();
                for (int i = 0; i < 256; i++)
                {
                    int c = (int)(destPal[i] & 0xFFFFFF);
                    if (!rgbToPaletteIndex.ContainsKey(c))
                    {
                        rgbToPaletteIndex.Add(c, i);
                    }
                }
                for (int i = 0; i < 256; i++)
                {
                    int c = (int)(sourcePal[i] & 0xFFFFFF);
                    if (rgbToPaletteIndex.ContainsKey(c))
                    {
                        srcToDest[i] = rgbToPaletteIndex[c];
                    }
                }
            }

            //map remaining colors
            {
                for (int i = 0; i < 256; i++)
                {
                    if (srcToDest[i] == -1)
                    {
                        int c           = (int)(sourcePal[i] & 0xFFFFFF);
                        int minDistance = int.MaxValue;
                        int minIndex    = -1;
                        for (int j = 0; j < 256; j++)
                        {
                            int c2       = (int)(destPal[j] & 0xFFFFFF);
                            int distance = GetDistance(c, c2);
                            if (distance < minDistance)
                            {
                                minDistance = distance;
                                minIndex    = j;
                            }
                        }
                        srcToDest[i] = minIndex;
                    }
                }
            }
            byte[] sequence      = new byte[256];
            byte[] srcToDestByte = new byte[256];
            {
                for (int i = 0; i < 256; i++)
                {
                    sequence[i]      = (byte)i;
                    srcToDestByte[i] = (byte)srcToDest[i];
                }
            }

            bitmap.ApplyPaletteIndexMapping(sequence, srcToDestByte, 256, false);
            bitmap.Palette.AsArray = newPalette.AsArray;
        }