Пример #1
0
        private void ExtractFrames(Texture2D spriteSheet, int frameWidth, int frameHeight)
        {
            List <Texture2D> frames = new List <Texture2D>();

            int  pixelCountPerFrame = frameWidth * frameHeight;
            bool foundEmptyFrame    = false;

            for (int y = 0; y < spriteSheet.Height; y += frameHeight)
            {
                if (y + frameHeight <= spriteSheet.Height && !foundEmptyFrame)
                {
                    for (int x = 0; x < spriteSheet.Width; x += frameWidth)
                    {
                        if (x + frameWidth <= spriteSheet.Width && !foundEmptyFrame)
                        {
                            var frameData = new Color[pixelCountPerFrame];
                            spriteSheet.GetData(0, new Rectangle(x, y, frameWidth, frameHeight), frameData, 0, pixelCountPerFrame);

                            if (frameData.All(c => c.A == 0))
                            {
                                foundEmptyFrame = true;
                            }
                            else
                            {
                                Texture2D frame = new Texture2D(GameProvider.GameInstance.GraphicsDevice, frameWidth, frameHeight);
                                frame.SetData(frameData);
                                frames.Add(frame);
                            }
                        }
                    }
                }
            }

            _frames = frames.ToArray();
        }
        public void Edit <T>(IAssetData asset)
        {
            const int styleW = 16;
            const int styleH = 128;

            // Dictionary data
            var data    = asset.AsDictionary <int, string>().Data;
            var newData = new Dictionary <int, string>();

            // Image data
            Texture2D hairstylesTexture = Game1.content.Load
                                          <Texture2D>
                                              (ModConsts.GameContentHairstyleImagePath);
            int count = 0;

            Color[] pixelData = new Color[styleW * styleH];

            // Find index of first non-empty slot in custom hairstyles spritesheet
            for (int x = (hairstylesTexture.Width / styleW) - 1; x >= 0 && count == 0; --x)
            {
                for (int y = (hairstylesTexture.Height / styleH) - 1; y >= 0 && count == 0; --y)
                {
                    int cur = x + (hairstylesTexture.Width / styleW * y);
                    hairstylesTexture.GetData(0, new Rectangle(x * styleW, y * styleH, styleW, styleH), pixelData, 0, pixelData.Length);
                    if (!pixelData.All(colour => colour.A == 0))
                    {
                        count = cur + 1;
                    }
                }
            }
            Log.D($"Hairstyles to add: {count}",
                  ModEntry.Config.DebugMode);

            // Add in HairData entries for every hairstyle up until the last non-empty hairstyle in the spritesheet
            const bool hasLeftStyle   = true;
            const bool isBaldStyle    = false;
            const int  coveredStyleId = -1;
            int        startId        = int.Parse(ModEntry.Instance.ModManifest.UpdateKeys.First().Split(':')[1]) * 100;

            if (data.Keys.Count(key => key >= startId && key < startId + count) is int conflicts && conflicts > 0)
            {
                Log.W($"Identified ID conflicts with {conflicts} hairstyles: Please share a log file on the mod page!");
            }
            for (int i = 0; i < count; ++i)
            {
                int styleId = startId + i;
                if (data.ContainsKey(styleId))
                {
                    string[] style = data[styleId].Split('/');
                    Log.W($"Overriding hairstyle at {styleId} ({style[0]} at X:{style[1]}, Y:{style[2]})");
                }

                int x = i % 8;
                int y = (int)(i * 0.125) * 8;
                newData.Add(styleId, $"{ModConsts.HairstylesSheetId}/{x}/{y}/{hasLeftStyle}/{coveredStyleId}/{isBaldStyle}");
            }
            Log.D(newData.Aggregate("HairData:", (total, cur) => $"{total}\n{cur.Key}: {cur.Value}"),
                  ModEntry.Config.DebugMode);
            asset.ReplaceWith(data.Concat(newData).ToDictionary(pair => pair.Key, pair => pair.Value));
        }
Пример #3
0
        /// <summary>
        /// Draws the elements border to the window. Skips sides that have color set to <see cref="Color.Transparent"/>
        /// </summary>
        /// <param name="spriteBatch">Sprite batch to draw the border to.</param>
        protected void DrawBorder(SpriteBatch spriteBatch)
        {
            var colors = new Color[] { BorderTopColor, BorderRightColor, BorderBottomColor, BorderLeftColor };

            if (colors.All(clr => clr == BorderTopColor))
            {
                spriteBatch.DrawRectangle(_borderRect, BorderTopColor, BorderWidth);
            }
            else
            {
                if (BorderTopColor != Color.Transparent)
                {
                    spriteBatch.DrawLine(_borderTop.Start, _borderTop.End, BorderTopColor, BorderWidth);
                }
                if (BorderRightColor != Color.Transparent)
                {
                    spriteBatch.DrawLine(_borderRight.Start, _borderRight.End, BorderRightColor, BorderWidth);
                }
                if (BorderBottomColor != Color.Transparent)
                {
                    spriteBatch.DrawLine(_borderBottom.Start, _borderBottom.End, BorderBottomColor, BorderWidth);
                }
                if (BorderLeftColor != Color.Transparent)
                {
                    spriteBatch.DrawLine(_borderLeft.Start, _borderLeft.End, BorderLeftColor, BorderWidth);
                }
            }
        }
Пример #4
0
        private bool IsRegionTransparent(Texture2D texture, Rectangle r)
        {
            int size = r.Width * r.Height;

            Color[] buffer = new Color[size];
            texture.GetData(0, r, buffer, 0, size);
            return(buffer.All(c => c == Color.Transparent));
        }
Пример #5
0
        private int GetTopPixel()
        {
            var data             = _enfFileProvider.ENFFile[NPC.ID];
            var frameTexture     = _npcSpriteSheet.GetNPCTexture(data.Graphic, NPCFrame.Standing, EODirection.Down);
            var frameTextureData = new Color[frameTexture.Width * frameTexture.Height];

            frameTexture.GetData(frameTextureData);

            if (frameTextureData.All(x => x.A == 0))
            {
                return(0);
            }

            var firstVisiblePixelIndex = frameTextureData.Select((color, index) => new { color, index })
                                         .Where(x => x.color.A != 0)
                                         .Select(x => x.index)
                                         .First();

            return(firstVisiblePixelIndex / frameTexture.Height);
        }
Пример #6
0
        private void InitializeTopPixel()
        {
            int tries;

            for (tries = 0; tries < 3; ++tries)
            {
                try
                {
                    //get the first non-transparent pixel to determine offsets for name labels and damage counters
                    var frameTexture     = _npcSheet.GetNPCTexture(NPC.Data.Graphic, NPCFrame.Standing, NPC.Direction);
                    var frameTextureData = new Color[frameTexture.Width * frameTexture.Height];
                    frameTexture.GetData(frameTextureData);

                    if (frameTextureData.All(x => x.A == 0))
                    {
                        TopPixel = 0;
                    }
                    else
                    {
                        var firstVisiblePixelIndex = frameTextureData.Select((color, index) => new { color, index })
                                                     .Where(x => x.color.R != 0)
                                                     .Select(x => x.index)
                                                     .First();
                        TopPixel = firstVisiblePixelIndex / frameTexture.Height;
                    }
                } //this block throws errors sometimes..no idea why. It usually doesn't fail 3 times.
                catch (InvalidOperationException) { continue; }

                break;
            }

            if (tries >= 3)
            {
                throw new InvalidOperationException("Something weird happened initializing this NPC.");
            }
        }
Пример #7
0
        public static void Main(string[] args)
        {
            Console.WriteLine("Enter input path: ");
            string image = Console.ReadLine();

            Console.WriteLine("Enter settings of conversion to black (semicolon-separated rules): ");

            Console.WriteLine("For R: ");
            string rRule = Console.ReadLine();

            ColorCondition[] rPredicates = ParseRule(rRule, color => color.R);

            Console.WriteLine("For G: ");
            string gRule = Console.ReadLine();

            ColorCondition[] gPredicates = ParseRule(gRule, color => color.G);

            Console.WriteLine("For B: ");
            string bRule = Console.ReadLine();

            ColorCondition[] bPredicates = ParseRule(bRule, color => color.B);

            if (rPredicates.Length != gPredicates.Length || rPredicates.Length != bPredicates.Length)
            {
                throw new Exception();
            }

            Predicate <Color>[] strictShouldBeBlack = Enumerable.Range(0, rPredicates.Length)
                                                      .Where(i => rPredicates[i].IsStrict)
                                                      .Select(i => new Predicate <Color>(color => rPredicates[i].Predicate(color) && gPredicates[i].Predicate(color) && bPredicates[i].Predicate(color)))
                                                      .ToArray();

            Predicate <Color>[] shouldBeBlack = Enumerable.Range(0, rPredicates.Length)
                                                .Where(i => !rPredicates[i].IsStrict)
                                                .Select(i => new Predicate <Color>(color => rPredicates[i].Predicate(color) && gPredicates[i].Predicate(color) && bPredicates[i].Predicate(color)))
                                                .ToArray();

            using (Bitmap bmp = new Bitmap(image))
            {
                for (int i = 0; i < bmp.Height; ++i)
                {
                    for (int j = 0; j < bmp.Width; ++j)
                    {
                        Color pixel = bmp.GetPixel(j, i);

                        if (pixel.R == 53 && pixel.G == 61 && pixel.B == 213)
                        {
                            for (int k = 0; k <= 14 && i + k < bmp.Height; ++k)
                            {
                                for (int q = 0; q <= 14 && j + q < bmp.Width; ++q)
                                {
                                    bmp.SetPixel(j + q, i + k, Color.White);
                                }
                            }
                        }

                        if (pixel.R == 244 && pixel.G == 223 && pixel.B == 116)
                        {
                            for (int k = 0; k <= 10 && i + k < bmp.Height; ++k)
                            {
                                for (int q = -2; q <= 3 && j + q < bmp.Width; ++q)
                                {
                                    Color currentPixel = bmp.GetPixel(j + q, i + k);
                                    bmp.SetPixel(j + q, i + k, currentPixel.R > 200 && currentPixel.G > 200 && currentPixel.B > 200 ? Color.White : Color.Black);
                                }
                            }
                        }

                        if (pixel.R == 102 && pixel.G == 102 && pixel.B == 102)
                        {
                            Color[] testPixels = new Color[]
                            {
                                bmp.GetPixel(j + 1, i + 1),
                                bmp.GetPixel(j + 2, i + 2)
                            };

                            if (testPixels.All(testPixel => testPixel.R == 102 && testPixel.G == 102 && testPixel.B == 102))
                            {
                                for (int k = -2; k < 8 && i + k < bmp.Height; ++k)
                                {
                                    for (int q = -2; q < 8 && j + q < bmp.Width; ++q)
                                    {
                                        bmp.SetPixel(j + q, i + k, Color.White);
                                    }
                                }
                            }
                        }

                        bmp.SetPixel(j, i, strictShouldBeBlack.All(pred => pred(pixel)) && shouldBeBlack.Any(pred => pred(pixel)) ? Color.Black : Color.White);
                    }
                }

                int    indexOfExtension = image.LastIndexOf('.');
                string name             = image.Substring(0, indexOfExtension);
                string extension        = image.Substring(indexOfExtension);

                if (File.Exists(name + "-modified" + extension))
                {
                    int i = 0;
                    for (; File.Exists(name + "-modified-" + i + extension); ++i)
                    {
                        ;
                    }

                    bmp.Save(name + "-modified-" + i + extension);
                }
                else
                {
                    bmp.Save(name + "-modified" + extension);
                }
            }
        }
Пример #8
0
		private void InitializeTopPixel()
		{
			int tries;
			for (tries = 0; tries < 3; ++tries)
			{
				try
				{
					//get the first non-transparent pixel to determine offsets for name labels and damage counters
					Frame = NPCFrame.Standing;

					var frameTexture = _npcSheet.GetNPCTexture();
					var frameTextureData = new Color[frameTexture.Width * frameTexture.Height];
					frameTexture.GetData(frameTextureData);

					if (frameTextureData.All(x => x.A == 0))
						TopPixel = 0;
					else
					{
						var firstVisiblePixelIndex = frameTextureData.Select((color, index) => new { color, index })
																	 .Where(x => x.color.R != 0)
																	 .Select(x => x.index)
																	 .First();
						TopPixel = firstVisiblePixelIndex/frameTexture.Height;
					}
				} //this block throws errors sometimes..no idea why. It usually doesn't fail 3 times.
				catch (InvalidOperationException) { continue; }

				break;
			}

			if (tries >= 3)
				throw new InvalidOperationException("Something weird happened initializing this NPC.");
		}