예제 #1
0
        /// <summary>
        /// Applies quantization to the image.
        /// </summary>
        /// <typeparam name="TPixel">The pixel format.</typeparam>
        /// <param name="source">The image this method extends.</param>
        /// <param name="quantizer">The quantizer to apply to perform the operation.</param>
        /// <param name="maxColors">The maximum number of colors to return.</param>
        /// <returns>The <see cref="Image{TPixel}"/>.</returns>
        public static IImageProcessingContext <TPixel> Quantize <TPixel>(this IImageProcessingContext <TPixel> source, IQuantizer <TPixel> quantizer, int maxColors)
            where TPixel : struct, IPixel <TPixel>
        {
            return(source.Apply(img =>
            {
                // TODO : move helper logic into the processor
                QuantizedImage <TPixel> quantized = quantizer.Quantize(img.Frames.RootFrame, maxColors);
                int palleteCount = quantized.Palette.Length - 1;

                using (Buffer2D <TPixel> pixels = source.MemoryManager.Allocate2D <TPixel>(quantized.Width, quantized.Height))
                {
                    Parallel.For(
                        0,
                        pixels.Height,
                        img.GetConfiguration().ParallelOptions,
                        y =>
                    {
                        Span <TPixel> row = pixels.GetRowSpan(y);
                        int yy = y * pixels.Width;
                        for (int x = 0; x < pixels.Width; x++)
                        {
                            int i = x + yy;
                            TPixel color = quantized.Palette[Math.Min(palleteCount, quantized.Pixels[i])];
                            row[x] = color;
                        }
                    });

                    Buffer2D <TPixel> .SwapContents(img.Frames[0].PixelBuffer, pixels);
                }
            }));
        }
예제 #2
0
        public static IImageProcessingContext <TPixel> ApplyScalingWaterMarkWordWrap <TPixel>(this IImageProcessingContext <TPixel> processingContext, Font font, string text, TPixel color, float padding)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img => {
                float targetWidth = img.Width - (padding * 2);
                float targetHeight = img.Height - (padding * 2);

                float targetMinHeight = img.Height - (padding * 3);

                var scaledFont = font;
                SizeF s = new SizeF(float.MaxValue, float.MaxValue);

                float scaleFactor = (scaledFont.Size / 2);
                int trapCount = (int)scaledFont.Size * 2;
                if (trapCount < 10)
                {
                    trapCount = 10;
                }

                bool isTooSmall = false;

                while ((s.Height > targetHeight || s.Height < targetMinHeight) && trapCount > 0)
                {
                    if (s.Height > targetHeight)
                    {
                        if (isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }

                        scaledFont = new Font(scaledFont, scaledFont.Size - scaleFactor);
                        isTooSmall = false;
                    }

                    if (s.Height < targetMinHeight)
                    {
                        if (!isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }
                        scaledFont = new Font(scaledFont, scaledFont.Size + scaleFactor);
                        isTooSmall = true;
                    }
                    trapCount--;

                    s = TextMeasurer.Measure(text, new RendererOptions(scaledFont)
                    {
                        WrappingWidth = targetWidth
                    });
                }

                var center = new PointF(padding, img.Height / 2);
                img.Mutate(i => i.DrawText(text, scaledFont, color, center, new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Center,
                    VerticalAlignment = VerticalAlignment.Center,
                    WrapTextWidth = targetWidth
                }));
            }));
        }
예제 #3
0
파일: Resize.cs 프로젝트: bixiu/BlueMine
        /// <summary>
        /// Resizes an image to the given width and height with the given sampler and
        /// source rectangle.
        /// </summary>
        /// <typeparam name="TPixel">The pixel format.</typeparam>
        /// <param name="source">The image to resize.</param>
        /// <param name="width">The target image width.</param>
        /// <param name="height">The target image height.</param>
        /// <param name="sampler">The <see cref="IResampler"/> to perform the resampling.</param>
        /// <param name="targetRectangle">
        /// The <see cref="Rectangle"/> structure that specifies the portion of the target image object to draw to.
        /// </param>
        /// <param name="compand">Whether to compress and expand the image color-space to gamma correct the image during processing.</param>
        /// <returns>The <see cref="Image{TPixel}"/></returns>
        /// <remarks>Passing zero for one of height or width will automatically preserve the aspect ratio of the original image</remarks>
        public static IImageProcessingContext <TPixel> Resize <TPixel>(this IImageProcessingContext <TPixel> source, int width, int height, IResampler sampler, Rectangle targetRectangle, bool compand)
            where TPixel : struct, IPixel <TPixel>
        {
            return(source.Apply(img =>
            {
                // TODO : stop cheating here and move this stuff into the processors itself
                if (width == 0 && height > 0)
                {
                    width = (int)MathF.Round(img.Width * height / (float)img.Height);
                    targetRectangle.Width = width;
                }

                if (height == 0 && width > 0)
                {
                    height = (int)MathF.Round(img.Height * width / (float)img.Width);
                    targetRectangle.Height = height;
                }

                Guard.MustBeGreaterThan(width, 0, nameof(width));
                Guard.MustBeGreaterThan(height, 0, nameof(height));

                img.Mutate(x => x.ApplyProcessor(new ResizeProcessor <TPixel>(sampler, width, height, targetRectangle)
                {
                    Compand = compand
                }));
            }));
        }
 public static IImageProcessingContext <TPixel> EnsureMaximumSize <TPixel>(this IImageProcessingContext <TPixel> source, int maxWidth, int maxHeight,
                                                                           bool maintainAspectRatio = true) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(image =>
     {
         if ((image.Width > maxWidth) || (image.Height > maxHeight))
         {
             if (maintainAspectRatio)
             {
                 // Handle if width is larger.
                 if (image.Width > image.Height)
                 {
                     image.Mutate(x => x.Resize(maxWidth, Convert.ToInt32(image.Height * maxWidth / image.Width)));
                 }
                 // Else height is larger.
                 else
                 {
                     image.Mutate(x => x.Resize(Convert.ToInt32(image.Width * maxHeight / image.Height), maxHeight));
                 }
             }
             else
             {
                 image.Mutate(x => x.Resize(maxWidth, maxHeight));
             }
         }
     }));
 }
예제 #5
0
        /// <summary>
        /// Applies quantization to the image.
        /// </summary>
        /// <typeparam name="TPixel">The pixel format.</typeparam>
        /// <param name="source">The image this method extends.</param>
        /// <param name="quantizer">The quantizer to apply to perform the operation.</param>
        /// <param name="maxColors">The maximum number of colors to return.</param>
        /// <returns>The <see cref="Image{TPixel}"/>.</returns>
        public static IImageProcessingContext <TPixel> Quantize <TPixel>(this IImageProcessingContext <TPixel> source, IQuantizer <TPixel> quantizer, int maxColors)
            where TPixel : struct, IPixel <TPixel>
        {
            return(source.Apply(img =>
            {
                // TODO : move helper logic into the processor
                QuantizedImage <TPixel> quantized = quantizer.Quantize(img.Frames.RootFrame, maxColors);
                int palleteCount = quantized.Palette.Length - 1;

                using (var pixels = new PixelAccessor <TPixel>(quantized.Width, quantized.Height))
                {
                    Parallel.For(
                        0,
                        pixels.Height,
                        img.GetConfiguration().ParallelOptions,
                        y =>
                    {
                        for (int x = 0; x < pixels.Width; x++)
                        {
                            int i = x + (y * pixels.Width);
                            TPixel color = quantized.Palette[Math.Min(palleteCount, quantized.Pixels[i])];
                            pixels[x, y] = color;
                        }
                    });

                    img.Frames[0].SwapPixelsBuffers(pixels);
                }
            }));
        }
예제 #6
0
        public static IImageProcessingContext <TPixel> ApplyScalingLogoWaterMark <TPixel>(
            this IImageProcessingContext <TPixel> processingContext,
            byte[] watermark)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(
                       image =>
            {
                // Dispose of logo once used.
                using (var logo = Image.Load <TPixel>(watermark))
                {
                    bool worh = image.Width > image.Height;
                    double coff = worh
                            ? image.Width * 0.127 / Math.Min(logo.Width, logo.Height)
                            : image.Height * 0.127 / Math.Max(logo.Width, logo.Height);

                    var size = new Size((int)(logo.Width * coff), (int)(logo.Height * coff));
                    var location = new Point(image.Width - size.Width - 57, image.Height - size.Height - 271);

                    // Resize the logo
                    logo.Mutate(i => i.Resize(size));

                    image.Mutate(i => i.DrawImage(logo, location, PixelColorBlendingMode.Normal, PixelAlphaCompositionMode.SrcOver, 1f));
                }
            }));
        }
예제 #7
0
        /// <summary>
        /// 画圆圈(泡泡)
        /// </summary>
        /// <typeparam name="TPixel"></typeparam>
        /// <param name="processingContext"></param>
        /// <param name="containerWidth"></param>
        /// <param name="containerHeight"></param>
        /// <param name="count"></param>
        /// <param name="miniR"></param>
        /// <param name="maxR"></param>
        /// <param name="color"></param>
        /// <param name="canOverlap"></param>
        /// <returns></returns>
        public static IImageProcessingContext <TPixel> DrawingCircles <TPixel>(this IImageProcessingContext <TPixel> processingContext, int containerWidth, int containerHeight, int count, int miniR, int maxR, TPixel color, bool canOverlap = false)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img =>
            {
                EllipsePolygon ep = null;
                Random random = new Random();
                PointF tempPoint = new PointF();
                List <PointF> points = new List <PointF>();

                if (count > 0)
                {
                    for (int i = 0; i < count; i++)
                    {
                        if (canOverlap)
                        {
                            tempPoint = new PointF(random.Next(0, containerWidth), random.Next(0, containerHeight));
                        }
                        else
                        {
                            tempPoint = getCirclePoginF(containerWidth, containerHeight, (miniR + maxR), ref points);
                        }
                        ep = new EllipsePolygon(tempPoint, random.Next(miniR, maxR));

                        img.Mutate(ctx => ctx
                                   .Draw(color, (float)(random.Next(94, 145) / 100.0), ep.Clip())
                                   );
                    }
                }
            }));
        }
예제 #8
0
        public static IImageProcessingContext <TPixel> SetAlphaMask <TPixel>(this IImageProcessingContext <TPixel> source, Image <Alpha8> mask, PixelAlphaCompositionMode mode) where TPixel : struct, IPixel <TPixel>
        {
            if (mask == null)
            {
                return(source);
            }

            return(source.Apply
                   (
                       img =>
            {
                if (mask.Width == img.Width && mask.Height == img.Height)
                {
                    using (var rmask = mask.CloneAs <TPixel>())
                    {
                        img.Mutate(dc => dc.DrawImage(rmask, PixelColorBlendingMode.Normal, mode, 1));
                    }
                }
                else
                {
                    using (var rmask = mask.CloneAs <TPixel>())
                    {
                        rmask.Mutate(dc => dc.Resize(img.Width, img.Height));
                        img.Mutate(dc => dc.DrawImage(rmask, PixelColorBlendingMode.Normal, mode, 1));
                    }
                }
            }
                   ));
        }
예제 #9
0
        /// <summary>
        /// 绘制中文字符(可以绘制字母数字,但样式可能需要改)
        /// </summary>
        /// <typeparam name="TPixel"></typeparam>
        /// <param name="processingContext"></param>
        /// <param name="containerWidth"></param>
        /// <param name="containerHeight"></param>
        /// <param name="text"></param>
        /// <param name="color"></param>
        /// <param name="font"></param>
        /// <returns></returns>
        public static IImageProcessingContext <TPixel> DrawingCnText <TPixel>(this IImageProcessingContext <TPixel> processingContext, int containerWidth, int containerHeight, string text, Rgba32 color, Font font)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img =>
            {
                if (string.IsNullOrEmpty(text) == false)
                {
                    Random random = new Random();
                    var textWidth = (img.Width / text.Length);
                    var img2Size = Math.Min(textWidth, img.Height);
                    var fontMiniSize = (int)(img2Size * 0.6);
                    var fontMaxSize = (int)(img2Size * 0.95);

                    for (int i = 0; i < text.Length; i++)
                    {
                        using (Image <Rgba32> img2 = new Image <Rgba32>(img2Size, img2Size))
                        {
                            Font scaledFont = new Font(font, random.Next(fontMiniSize, fontMaxSize));
                            var point = new Point(i * textWidth, (containerHeight - img2.Height) / 2);
                            var textGraphicsOptions = new TextGraphicsOptions(true)
                            {
                                HorizontalAlignment = HorizontalAlignment.Left,
                                VerticalAlignment = VerticalAlignment.Top
                            };

                            img2.Mutate(ctx => ctx
                                        .DrawText(textGraphicsOptions, text[i].ToString(), scaledFont, color, new Point(0, 0))
                                        .Rotate(random.Next(-45, 45))
                                        );
                            img.Mutate(ctx => ctx.DrawImage(img2, point, 1));
                        }
                    }
                }
            }));
        }
예제 #10
0
        public static IImageProcessingContext <TPixel> ApplyScalingWaterMarkSimple <TPixel>(this IImageProcessingContext <TPixel> processingContext, Font font, string text, TPixel color, float padding)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img =>
            {
                float targetWidth = img.Width - (padding * 2);
                float targetHeight = img.Height - (padding * 2);

                // measure the text size
                SizeF size = TextMeasurer.Measure(text, new RendererOptions(font));

                //find out how much we need to scale the text to fill the space (up or down)
                float scalingFactor = Math.Min(img.Width / size.Width, img.Height / size.Height);

                //create a new font
                Font scaledFont = new Font(font, scalingFactor * font.Size);

                var center = new PointF(img.Width / 2, img.Height / 2);
                var textGraphicOptions = new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Center,
                    VerticalAlignment = VerticalAlignment.Center
                };
                img.Mutate(i => i.DrawText(textGraphicOptions, text, scaledFont, color, center));
            }));
        }
예제 #11
0
 public static IImageProcessingContext <Rgba32> CreateLayerFromBoundingBox(this IImageProcessingContext <Rgba32> context, BaseBoundingBox boundingBox, string param)
 {
     return(context.Apply(img =>
     {
         using (var layer = new Image <Rgba32>(img.Width, img.Height))
         {
             boundingBox.SetInput(param);
             layer.Mutate(i => boundingBox.Apply(i));
             img.Mutate(i => i.DrawImage(layer, 1.0f, new Point(0, 0)));
         }
     }));
 }
예제 #12
0
 // From https://github.com/SixLabors/Samples/blob/master/ImageSharp/DrawWaterMarkOnImage/Program.cs
 public static IImageProcessingContext <TPixel> ApplyScalingWaterMarkSimple <TPixel>(this IImageProcessingContext <TPixel> processingContext, Font font, TPixel color, float padding, int scalingFactor, string text)
     where TPixel : struct, IPixel <TPixel>
 {
     return(processingContext.Apply(img =>
     {
         SizeF size = TextMeasurer.Measure(text, new RendererOptions(font));
         Font scaledFont = new Font(font, Math.Min(img.Width, img.Height) / scalingFactor * font.Size);
         var pos = new PointF(img.Width - padding, img.Height - padding);
         img.Mutate(i => i.DrawText(text, scaledFont, color, pos, new TextGraphicsOptions(true)
         {
             HorizontalAlignment = HorizontalAlignment.Right,
             VerticalAlignment = VerticalAlignment.Bottom
         }));
     }));
 }
예제 #13
0
 /// <summary>
 /// 画杂线
 /// </summary>
 /// <typeparam name="TPixel"></typeparam>
 /// <param name="processingContext"></param>
 /// <param name="containerWidth"></param>
 /// <param name="containerHeight"></param>
 /// <param name="color"></param>
 /// <param name="count"></param>
 /// <param name="thickness"></param>
 /// <returns></returns>
 public static IImageProcessingContext <TPixel> DrawingGrid <TPixel>(this IImageProcessingContext <TPixel> processingContext, int containerWidth, int containerHeight, TPixel color, int count, float thickness)
     where TPixel : struct, IPixel <TPixel>
 {
     return(processingContext.Apply(img =>
     {
         var points = new List <PointF> {
             new PointF(0, 0)
         };
         for (int i = 0; i < count; i++)
         {
             getCirclePoginF(containerWidth, containerHeight, 9, ref points);
         }
         points.Add(new PointF(containerWidth, containerHeight));
         img.Mutate(ctx => ctx
                    .DrawLines(color, thickness, points.ToArray())
                    );
     }));
 }
예제 #14
0
        public static IImageProcessingContext <TPixel> DrawingEnText <TPixel>(this IImageProcessingContext <TPixel> processingContext, int containerWidth, int containerHeight, string text, string[] colorHexArr, Font[] fonts, int gridCoefficient = 6)
            where TPixel : struct, IPixel <TPixel>
        {
            if (gridCoefficient < 0)
            {
                gridCoefficient = 0;
            }
            return(processingContext.Apply(img =>
            {
                if (string.IsNullOrEmpty(text) == false)
                {
                    Random random = new Random();
                    var textWidth = (img.Width / text.Length);
                    var img2Size = Math.Min(textWidth, img.Height);
                    var fontMiniSize = (int)(img2Size * 0.9);
                    var fontMaxSize = (int)(img2Size * 1.37);
                    Array fontStyleArr = Enum.GetValues(typeof(FontStyle));

                    for (int i = 0; i < text.Length; i++)
                    {
                        using (Image <Rgba32> img2 = new Image <Rgba32>(img2Size, img2Size))
                        {
                            Font scaledFont = new Font(fonts[random.Next(0, fonts.Length)], random.Next(fontMiniSize, fontMaxSize), (FontStyle)fontStyleArr.GetValue(random.Next(fontStyleArr.Length)));
                            var point = new Point(i * textWidth, (containerHeight - img2.Height) / 2);
                            var colorHex = colorHexArr[random.Next(0, colorHexArr.Length)];
                            var textGraphicsOptions = new TextGraphicsOptions(true)
                            {
                                HorizontalAlignment = HorizontalAlignment.Left,
                                VerticalAlignment = VerticalAlignment.Top
                            };

                            img2.Mutate(ctx => ctx
                                        .DrawText(textGraphicsOptions, text[i].ToString(), scaledFont, Rgba32.FromHex(colorHex), new Point(0, 0))
                                        .DrawingGrid(containerWidth, containerHeight, Rgba32.FromHex(colorHex), gridCoefficient, 1)
                                        .Rotate(random.Next(-45, 45))
                                        );
                            img.Mutate(ctx => ctx.DrawImage(img2, point, 1));
                        }
                    }
                }
            }));
        }
예제 #15
0
        public static IImageProcessingContext <TPixel> ApplyFaceInfo <TPixel>(this IImageProcessingContext <TPixel> processingContext, IList <FaceDetails> faces, TPixel color, TPixel textColor)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img =>
            {
                var gfxOptions = new GraphicsOptions(true)
                {
                };
                var gfxTextOptions = new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Center, VerticalAlignment = VerticalAlignment.Center
                };

                var font = SystemFonts.CreateFont("Arial", 39, FontStyle.Bold);
                foreach (var face in faces)
                {
                    PointF left_top = new PointF((float)face.BoundingBox.X, (float)face.BoundingBox.Y);
                    PointF left_bottom = new PointF((float)face.BoundingBox.X, (float)face.BoundingBox.Y + (float)face.BoundingBox.Height);
                    PointF right_top = new PointF((float)face.BoundingBox.X + (float)face.BoundingBox.Width, (float)face.BoundingBox.Y);
                    PointF right_bottom = new PointF((float)face.BoundingBox.X + (float)face.BoundingBox.Width, (float)face.BoundingBox.Y + (float)face.BoundingBox.Height);
                    PointF[] boundingBox = new PointF[] { left_top, right_top, right_bottom, left_bottom };

                    img.Mutate(i => i.DrawPolygon(color, 5f, boundingBox, gfxOptions));

                    PointF text_Age_pos = new PointF((float)face.BoundingBox.X + (float)face.BoundingBox.Width / 2, (float)face.BoundingBox.Y - 45f);
                    SizeF size = TextMeasurer.Measure($"{face.Age}", new RendererOptions(font)
                    {
                        HorizontalAlignment = HorizontalAlignment.Center, VerticalAlignment = VerticalAlignment.Center, Origin = text_Age_pos
                    });
                    PointF[] text_Background_Age = new PointF[] { new PointF(text_Age_pos.X - size.Width / 2 - 20f, text_Age_pos.Y - 20f), new PointF(text_Age_pos.X + size.Width / 2 + 20f, text_Age_pos.Y - 20f), new PointF(text_Age_pos.X + size.Width / 2 + 20f, text_Age_pos.Y + size.Height - 10f), new PointF(text_Age_pos.X - size.Width / 2 - 20f, text_Age_pos.Y + size.Height - 10f) };
                    img.Mutate(i => i.FillPolygon(color, text_Background_Age, gfxOptions));
                    img.Mutate(i => i.DrawText($"{face.Age}", font, textColor, text_Age_pos, gfxTextOptions));

                    PointF text_Emotion_pos = new PointF((float)face.BoundingBox.X + (float)face.BoundingBox.Width / 2, (float)face.BoundingBox.Y + (float)face.BoundingBox.Height + 45f);
                    size = TextMeasurer.Measure($"{face.Emotion}", new RendererOptions(font));
                    PointF[] text_Background_Emotion = new PointF[] { new PointF(text_Emotion_pos.X - size.Width / 2 - 20f, text_Emotion_pos.Y - 20f), new PointF(text_Emotion_pos.X + size.Width / 2 + 20f, text_Emotion_pos.Y - 20f), new PointF(text_Emotion_pos.X + size.Width / 2 + 20f, text_Emotion_pos.Y + size.Height - 10f), new PointF(text_Emotion_pos.X - size.Width / 2 - 20f, text_Emotion_pos.Y + size.Height - 10f) };
                    img.Mutate(i => i.FillPolygon(color, text_Background_Emotion, gfxOptions));
                    img.Mutate(i => i.DrawText($"{face.Emotion}", font, textColor, text_Emotion_pos, gfxTextOptions));
                }
            }));
        }
/*
 *      public static IImageProcessingContext<TPixel> ApplyScalingWaterMarkSimple<TPixel>(this IImageProcessingContext<TPixel> processingContext, Font font, string text, TPixel color, float padding)
 *          where TPixel : struct, IPixel<TPixel>
 *      {
 *          return processingContext.Apply(img =>
 *          {
 *              float targetWidth = img.Width - (padding * 2);
 *              float targetHeight = img.Height - (padding * 2);
 *
 *              // measure the text size
 *              SizeF size = TextMeasurer.Measure(text, new RendererOptions(font));
 *
 *              //find out how much we need to scale the text to fill the space (up or down)
 *              float scalingFactor = Math.Min(img.Width / size.Width, img.Height / size.Height);
 *
 *              //create a new font
 *              Font scaledFont = new Font(font, scalingFactor * font.Size);
 *
 *              var center = new PointF(img.Width / 2, img.Height / 2);
 *              var textGraphicOptions = new TextGraphicsOptions(true)
 *              {
 *                  HorizontalAlignment = HorizontalAlignment.Center,
 *                  VerticalAlignment = VerticalAlignment.Center
 *              };
 *              img.Mutate(i => i.DrawText(textGraphicOptions, text, scaledFont, color, center));
 *          });
 *      }
 */

        private static void ApplyScalingWaterMarkSimpleTopLeft <TPixel>(
            this IImageProcessingContext <TPixel> p_processingContext, Font p_font, string p_text, TPixel p_fontColor,
            TPixel p_backgroundColor, float p_targetSize)
            where TPixel : struct, IPixel <TPixel>
        {
            p_processingContext.Apply(p_img =>
            {
                var targetSizePercent = 100 / p_targetSize;

                // measure the text size
                var size = TextMeasurer.Measure(p_text, new RendererOptions(p_font));

                //find out how much we need to scale the text to fill the space (up or down)
                var scalingFactor = Math.Min(p_img.Width / targetSizePercent / size.Width,
                                             p_img.Height / targetSizePercent / size.Height);

                //create a new font
                var scaledFont = new Font(p_font, scalingFactor * p_font.Size);

                size = TextMeasurer.Measure(p_text, new RendererOptions(scaledFont));

                var center = new PointF(p_img.Width / 75.0f + size.Width / 2,
                                        p_img.Height / 75.0f + size.Height / 2);
                var textGraphicOptions = new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Center,
                    VerticalAlignment   = VerticalAlignment.Center
                };
                p_img.Mutate(p_i =>
                             p_i.FillPolygon(new GraphicsOptions(true, PixelColorBlendingMode.Multiply, 0.5f),
                                             p_backgroundColor, new PointF(0, 0), new PointF(0, size.Height * 2), new
                                             PointF(size.Width + p_img.Width / 75 * 2,
                                                    size.Height * 2), new
                                             PointF(size.Width + p_img.Width / 75 * 2,
                                                    0)));
                p_img.Mutate(p_i => p_i.DrawText(textGraphicOptions, p_text, scaledFont, p_fontColor,
                                                 center));
            });
        }
예제 #17
0
파일: Resize.cs 프로젝트: bixiu/BlueMine
        /// <summary>
        /// Resizes an image in accordance with the given <see cref="ResizeOptions"/>.
        /// </summary>
        /// <typeparam name="TPixel">The pixel format.</typeparam>
        /// <param name="source">The image to resize.</param>
        /// <param name="options">The resize options.</param>
        /// <returns>The <see cref="Image{TPixel}"/></returns>
        /// <remarks>Passing zero for one of height or width within the resize options will automatically preserve the aspect ratio of the original image</remarks>
        public static IImageProcessingContext <TPixel> Resize <TPixel>(this IImageProcessingContext <TPixel> source, ResizeOptions options)
            where TPixel : struct, IPixel <TPixel>
        {
            return(source.Apply(img =>
            {
                // Cheat and bound through a run, inside here we should just be mutating, this really needs moving over to a processor
                // Ensure size is populated across both dimensions.
                if (options.Size.Width == 0 && options.Size.Height > 0)
                {
                    options.Size = new Size((int)MathF.Round(img.Width * options.Size.Height / (float)img.Height), options.Size.Height);
                }

                if (options.Size.Height == 0 && options.Size.Width > 0)
                {
                    options.Size = new Size(options.Size.Width, (int)MathF.Round(img.Height * options.Size.Width / (float)img.Width));
                }

                Rectangle targetRectangle = ResizeHelper.CalculateTargetLocationAndBounds(img.Frames.RootFrame, options);

                img.Mutate(x => Resize(x, options.Size.Width, options.Size.Height, options.Sampler, targetRectangle, options.Compand));
            }));
        }
예제 #18
0
 public static IImageProcessingContext <HalfSingle> FillMandelbrot(this IImageProcessingContext <HalfSingle> source, double ox, double oy, double scale, int iterations)
 {
     return(source.Apply(image => image._FillMandelbrot(ox, oy, scale, iterations)));
 }
예제 #19
0
 public static IImageProcessingContext <TPixel> FillCheckers <TPixel>(this IImageProcessingContext <TPixel> source, int cellWidth, int cellHeight, TPixel oddColor, TPixel evenColor) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => img._FillCheckers(cellWidth, cellHeight, oddColor, evenColor)));
 }
예제 #20
0
 public static IImageProcessingContext <TPixel> SetSubjectInfo <TPixel>(this IImageProcessingContext <TPixel> source, SubjectInfo sinfo) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => img.SetSubjectInfo(sinfo)));
 }
예제 #21
0
 public static IImageProcessingContext <TPixel> OuterGlow <TPixel>(this IImageProcessingContext <TPixel> source, float radius) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => _ApplyOuterGlow(img, radius)));
 }
예제 #22
0
 public static IImageProcessingContext <TPixel> PremultiplyAlpha <TPixel>(this IImageProcessingContext <TPixel> source) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => _ApplyAlphaPremultiply(img.ToPixelSampler())));
 }
예제 #23
0
 public static IImageProcessingContext <TPixel> ApplyCommonEffect <TPixel>(this IImageProcessingContext <TPixel> source, CommonEffect <TPixel> effect) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => _ApplyCommonEffect <TPixel>(img, effect)));
 }
예제 #24
0
 public static IImageProcessingContext <TPixel> FillRGB <TPixel>(this IImageProcessingContext <TPixel> source, TPixel rgb) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => _FillRGB(img.ToPixelSampler(), rgb.ToVector4())));
 }
예제 #25
0
 public static IImageProcessingContext <TPixel> EdgePaddingAlpha <TPixel>(this IImageProcessingContext <TPixel> source, float minAlpha) where TPixel : struct, IPixel <TPixel>
 {
     return(source.Apply(img => _ApplyEdgePadding(img, minAlpha, int.MaxValue)));
 }
예제 #26
0
 public static IImageProcessingContext <HalfSingle> FillRandomNoise(this IImageProcessingContext <HalfSingle> source, int blurRadius = 0, int randomSeed = 177)
 {
     return(source.Apply(image => image._FillRandomNoise(blurRadius, randomSeed)));
 }
예제 #27
0
 public static IImageProcessingContext <TPixel> ApplyPolarDistort <TPixel>(this IImageProcessingContext <TPixel> dc, bool inverse) where TPixel : struct, IPixel <TPixel>
 {
     return(dc.Apply(image => image._DistortImage(inverse)));
 }
예제 #28
0
 public static IImageProcessingContext <HalfSingle> FillPerlinNoise(this IImageProcessingContext <HalfSingle> source, float scale = 16, int repeat = 0, int octaves = 8, double persistence = 0.1f, int randomSeed = 177)
 {
     return(source.Apply(image => image._FillPerlinNoise(scale, repeat, octaves, persistence, randomSeed)));
 }
예제 #29
0
        public static IImageProcessingContext <TPixel> ApplyScalingWaterMarkWordWrap <TPixel>(this IImageProcessingContext <TPixel> processingContext, Font font, string text, TPixel color, float padding)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(img =>
            {
                float targetWidth = img.Width - (padding * 2);
                float targetHeight = img.Height - (padding * 2);

                float targetMinHeight = img.Height - (padding * 3); // must be with in a margin width of the target height

                // now we are working i 2 dimensions at once and can't just scale because it will cause the text to
                // reflow we need to just try multiple times

                var scaledFont = font;
                SizeF s = new SizeF(float.MaxValue, float.MaxValue);

                float scaleFactor = (scaledFont.Size / 2);// everytime we change direction we half this size
                int trapCount = (int)scaledFont.Size * 2;
                if (trapCount < 10)
                {
                    trapCount = 10;
                }

                bool isTooSmall = false;

                while ((s.Height > targetHeight || s.Height < targetMinHeight) && trapCount > 0)
                {
                    if (s.Height > targetHeight)
                    {
                        if (isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }

                        scaledFont = new Font(scaledFont, scaledFont.Size - scaleFactor);
                        isTooSmall = false;
                    }

                    if (s.Height < targetMinHeight)
                    {
                        if (!isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }
                        scaledFont = new Font(scaledFont, scaledFont.Size + scaleFactor);
                        isTooSmall = true;
                    }
                    trapCount--;

                    s = TextMeasurer.Measure(text, new RendererOptions(scaledFont)
                    {
                        WrappingWidth = targetWidth
                    });
                }

                var center = new PointF(padding, img.Height / 2);
                var textGraphicOptions = new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Left,
                    VerticalAlignment = VerticalAlignment.Center,
                    WrapTextWidth = targetWidth
                };
                img.Mutate(i => i.DrawText(textGraphicOptions, text, scaledFont, color, center));
            }));
        }
        public static IImageProcessingContext <TPixel> ApplyScalingedText <TPixel>(this IImageProcessingContext <TPixel> processingContext, Font font, string text, string highlight,
                                                                                   TPixel color, TPixel colorHighlight, float padding, int maxFontSize)
            where TPixel : struct, IPixel <TPixel>
        {
            return(processingContext.Apply(image =>
            {
                float targetWidth = image.Width - (padding * 2);
                float targetHeight = image.Height - (padding * 2);
                float targetMinHeight = image.Height - (padding * 3) - 100; // must be with in a margin width of the target height

                // now we are working in 2 dimensions at once and can't just scale because it will cause the text to
                // reflow we need to just try multiple times
                var scaledFont = font;
                SizeF s = new SizeF(float.MaxValue, float.MaxValue);

                float scaleFactor = (scaledFont.Size / 2);// everytime we change direction we half this size
                int trapCount = (int)scaledFont.Size * 2;
                if (trapCount < 10)
                {
                    trapCount = 10;
                }

                bool isTooSmall = false;

                while ((s.Height > targetHeight || s.Height < targetMinHeight) && trapCount > 0)
                {
                    if (s.Height > targetHeight)
                    {
                        if (isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }

                        scaledFont = new Font(scaledFont, scaledFont.Size - scaleFactor);
                        isTooSmall = false;
                    }

                    if (s.Height < targetMinHeight)
                    {
                        if (!isTooSmall)
                        {
                            scaleFactor = scaleFactor / 2;
                        }
                        scaledFont = new Font(scaledFont, scaledFont.Size + scaleFactor);
                        isTooSmall = true;
                    }
                    trapCount--;

                    s = TextMeasurer.Measure(text, new RendererOptions(scaledFont)
                    {
                        HorizontalAlignment = HorizontalAlignment.Left,
                        VerticalAlignment = VerticalAlignment.Top,
                        WrappingWidth = targetWidth
                    });
                }

                var location = new PointF(padding, padding);
                var textGraphicOptions = new TextGraphicsOptions(true)
                {
                    HorizontalAlignment = HorizontalAlignment.Left,
                    VerticalAlignment = VerticalAlignment.Top,
                    WrapTextWidth = targetWidth
                };

                if (scaledFont.Size > maxFontSize)
                {
                    scaledFont = new Font(scaledFont, maxFontSize);
                }

                image.Mutate(ctx =>
                {
                    foreach (string word in text.Split(new[] { ' ' }, options: System.StringSplitOptions.None))
                    {
                        var wordSize = TextMeasurer.Measure(word, new RendererOptions(scaledFont)
                        {
                            HorizontalAlignment = HorizontalAlignment.Left,
                            VerticalAlignment = VerticalAlignment.Top
                                                //WrappingWidth = targetWidth
                        });

                        // Wort zu langen. Umbrechen.
                        if (location.X + wordSize.Width > targetWidth)
                        {
                            //location = new PointF(padding, location.Y + wordSize.Height);
                            location = new PointF(padding, location.Y + scaledFont.Size);
                        }

                        foreach (char c in word + " ")
                        {
                            ctx.DrawText(textGraphicOptions, c.ToString(), scaledFont, color, location);

                            var charSize = TextMeasurer.Measure(c.ToString(), new RendererOptions(scaledFont)
                            {
                                HorizontalAlignment = HorizontalAlignment.Left,
                                VerticalAlignment = VerticalAlignment.Top
                            });

                            location = new PointF(location.X + charSize.Width, location.Y);
                        }
                    }
                    //ctx.DrawText(textGraphicOptions, text, scaledFont, color, location);
                    //ctx.DrawText(textGraphicOptions, highlight, scaledFont, colorHighlight, location);
                });
            }));
        }