private double GetDifferenceForTarget(MosaicTileColour tileColor, int i, Target target) { if (target == Target.Whole) { return(GetLibraryTileDifference(tileColor, i)); } else { switch (target) { case Target.TL: return(tileColor.AverageWhole.GetDifference(library[i].AverageTL)); case Target.TR: return(tileColor.AverageWhole.GetDifference(library[i].AverageTR)); case Target.BL: return(tileColor.AverageWhole.GetDifference(library[i].AverageBL)); case Target.BR: return(tileColor.AverageWhole.GetDifference(library[i].AverageBR)); default: return(GetLibraryTileDifference(tileColor, i)); } } }
public MosaicTileColour[,] CreateMap(Bitmap img) { int horizontalTiles = (int)img.Width / tileSize.Width; int verticalTiles = (int)img.Height / tileSize.Height; var colorMap = new MosaicTileColour[horizontalTiles, verticalTiles]; int tileWidth = (img.Width - img.Width % horizontalTiles) / horizontalTiles; int tileHeight = (img.Height - img.Height % verticalTiles) / verticalTiles; // Explore option of making this a parallel for loop for (int x = 0; x < horizontalTiles; x++) { for (int y = 0; y < verticalTiles; y++) { var xstart = tileWidth * x; var ystart = tileHeight * y; var tileColour = new MosaicTileColour(); // These are the opertaions to perform if we want to subdivide tile tileColour.AverageTL = getAverageTileColor(CreateQuadrantRectangle(xstart, ystart, tileWidth, tileHeight, Target.TL), img, quality); tileColour.AverageTR = getAverageTileColor(CreateQuadrantRectangle(xstart, ystart, tileWidth, tileHeight, Target.TR), img, quality); tileColour.AverageBL = getAverageTileColor(CreateQuadrantRectangle(xstart, ystart, tileWidth, tileHeight, Target.BL), img, quality); tileColour.AverageBR = getAverageTileColor(CreateQuadrantRectangle(xstart, ystart, tileWidth, tileHeight, Target.BR), img, quality); tileColour.AverageWhole = getAverageTileColor(CreateQuadrantRectangle(xstart, ystart, tileWidth, tileHeight, Target.Whole), img, quality); colorMap[x, y] = tileColour; } } return(colorMap); }
private double GetLibraryTileDifference(MosaicTileColour color, int i) { var differenceTL = color.AverageTL.GetDifference(library[i].AverageTL); var differenceTR = color.AverageTR.GetDifference(library[i].AverageTR); var differenceBL = color.AverageBL.GetDifference(library[i].AverageBL); var differenceBR = color.AverageBR.GetDifference(library[i].AverageBR); return(differenceTL + differenceTR + differenceBL + differenceBR); }
// Passes the colour value for the current tile being analysed // Uses library which contains the average colour for all of the tile images private int GetBestImageIndex(MosaicTileColour tileColor, int x, int y, bool random, Target target) { double bestPercent = double.MaxValue; var bestIndexes = new Dictionary <int, double>(); bestIndexes.Add(-1, bestPercent); const byte offset = 7; double difference; for (int i = 0; i < library.Count(); i++) { difference = GetDifferenceForTarget(tileColor, i, target); // as well as best diff store the 10th best diff and replace that item when necessary if (difference < bestPercent) { Point point = new Point(); if (library[i].Data.Count > 0 && library[i].Data[0] != null) { point = (Point)library[i].Data[0]; } if (point.IsEmpty) { bestIndexes.Add(i, difference); } else if (point.X + offset <= x && point.Y + offset > y && point.Y - offset < y) { bestIndexes.Add(i, difference); } // if length of dictionary is > 10 remove the largest value entry if (bestIndexes.Count() > 10) { var maxValue = bestIndexes.Values.Max(); var maxKey = bestIndexes.FirstOrDefault(v => v.Value == maxValue).Key; bestIndexes.Remove(maxKey); } // update best percent to largest value in dictionary bestPercent = bestIndexes.Values.Max(); } } // Will remove the inital entry if still present if (bestIndexes.ContainsKey(-1)) { bestIndexes.Remove(-1); } int index; if (random) { // Randomly select one of the best fit indexes index = bestIndexes.ElementAt(new Random().Next(0, bestIndexes.Count - 1)).Key; } else { var min = bestIndexes.Values.Min(); index = bestIndexes.FirstOrDefault(v => v.Value == min).Key; } library[index].Data.Add(new Point(x, y)); library[index].Difference = bestIndexes.GetValueOrDefault(index); return(index); }