/// <summary> /// 生成图片验证码 /// </summary> /// <param name="code">随机码</param> public static byte[] CreateImg(string code) { var random = new Random(); //为验证码插入空格 for (int i = 0; i < 2; i++) { code = code.Insert(random.Next(code.Length - 1), " "); } //验证码颜色集合 SKColor[] colors = { SKColors.LightBlue, SKColors.LightCoral, SKColors.LightGreen, SKColors.LightPink, SKColors.LightSkyBlue, SKColors.LightSteelBlue, SKColors.LightSalmon }; //旋转角度 int randAngle = 40; using SKBitmap bitmap = new SKBitmap(code.Length * 22, 38); using SKCanvas canvas = new SKCanvas(bitmap); //背景设为白色 canvas.Clear(SKColors.White); //在随机位置画背景点 for (int i = 0; i < 200; i++) { int x = random.Next(0, bitmap.Width); int y = random.Next(0, bitmap.Height); var paint = new SKPaint() { Color = colors[random.Next(colors.Length)] }; canvas.DrawRect(new SKRect(x, y, x + 2, y + 2), paint); } //验证码绘制 for (int i = 0; i < code.Length; i++) { //角度 float angle = random.Next(-randAngle, randAngle); //不同高度 int ii = random.Next(20) * (random.Next(1) % 2 == 0 ? -1 : 1) + 20; SKPoint point = new SKPoint(18, 20); canvas.Translate(point); canvas.RotateDegrees(angle); var textPaint = new SKPaint() { TextAlign = SKTextAlign.Center, Color = colors[random.Next(colors.Length)], TextSize = 28, IsAntialias = true, FakeBoldText = true }; canvas.DrawText(code.Substring(i, 1), new SKPoint(0, ii), textPaint); canvas.RotateDegrees(-angle); canvas.Translate(0, -point.Y); } canvas.Translate(-4, 0); using var image = SKImage.FromBitmap(bitmap); using var ms = new System.IO.MemoryStream(); image.Encode(SKEncodedImageFormat.Jpeg, 90).SaveTo(ms); return(ms.ToArray()); }
/// <inheritdoc/> public string EncodeImage(string inputPath, DateTime dateModified, string outputPath, bool autoOrient, ImageOrientation?orientation, int quality, ImageProcessingOptions options, ImageFormat selectedOutputFormat) { if (inputPath.Length == 0) { throw new ArgumentException("String can't be empty.", nameof(inputPath)); } if (outputPath.Length == 0) { throw new ArgumentException("String can't be empty.", nameof(outputPath)); } var skiaOutputFormat = GetImageFormat(selectedOutputFormat); var hasBackgroundColor = !string.IsNullOrWhiteSpace(options.BackgroundColor); var hasForegroundColor = !string.IsNullOrWhiteSpace(options.ForegroundLayer); var blur = options.Blur ?? 0; var hasIndicator = options.AddPlayedIndicator || options.UnplayedCount.HasValue || !options.PercentPlayed.Equals(0); using (var bitmap = GetBitmap(inputPath, options.CropWhiteSpace, autoOrient, orientation)) { if (bitmap == null) { throw new InvalidDataException($"Skia unable to read image {inputPath}"); } var originalImageSize = new ImageDimensions(bitmap.Width, bitmap.Height); if (!options.CropWhiteSpace && options.HasDefaultOptions(inputPath, originalImageSize) && !autoOrient) { // Just spit out the original file if all the options are default return(inputPath); } var newImageSize = ImageHelper.GetNewImageSize(options, originalImageSize); var width = newImageSize.Width; var height = newImageSize.Height; using (var resizedBitmap = new SKBitmap(width, height, bitmap.ColorType, bitmap.AlphaType)) { // scale image bitmap.ScalePixels(resizedBitmap, SKFilterQuality.High); // If all we're doing is resizing then we can stop now if (!hasBackgroundColor && !hasForegroundColor && blur == 0 && !hasIndicator) { Directory.CreateDirectory(Path.GetDirectoryName(outputPath)); using (var outputStream = new SKFileWStream(outputPath)) using (var pixmap = new SKPixmap(new SKImageInfo(width, height), resizedBitmap.GetPixels())) { pixmap.Encode(outputStream, skiaOutputFormat, quality); return(outputPath); } } // create bitmap to use for canvas drawing used to draw into bitmap using (var saveBitmap = new SKBitmap(width, height)) // , bitmap.ColorType, bitmap.AlphaType)) using (var canvas = new SKCanvas(saveBitmap)) { // set background color if present if (hasBackgroundColor) { canvas.Clear(SKColor.Parse(options.BackgroundColor)); } // Add blur if option is present if (blur > 0) { // create image from resized bitmap to apply blur using (var paint = new SKPaint()) using (var filter = SKImageFilter.CreateBlur(blur, blur)) { paint.ImageFilter = filter; canvas.DrawBitmap(resizedBitmap, SKRect.Create(width, height), paint); } } else { // draw resized bitmap onto canvas canvas.DrawBitmap(resizedBitmap, SKRect.Create(width, height)); } // If foreground layer present then draw if (hasForegroundColor) { if (!double.TryParse(options.ForegroundLayer, out double opacity)) { opacity = .4; } canvas.DrawColor(new SKColor(0, 0, 0, (byte)((1 - opacity) * 0xFF)), SKBlendMode.SrcOver); } if (hasIndicator) { DrawIndicator(canvas, width, height, options); } Directory.CreateDirectory(Path.GetDirectoryName(outputPath)); using (var outputStream = new SKFileWStream(outputPath)) { using (var pixmap = new SKPixmap(new SKImageInfo(width, height), saveBitmap.GetPixels())) { pixmap.Encode(outputStream, skiaOutputFormat, quality); } } } } } return(outputPath); }
/// <inheritdoc /> public void Clear(Color color) { Canvas.Clear(color.ToSKColor()); }
/// <summary> /// Clears the canvas. /// </summary> public void Clear(SKColor?color = null) { _canvas.Clear(color ?? (!GameConfig.Instance.Debug ? Colors.Transparent : Colors.DebugBlack1)); }
// Clear the bitmap of all user drawings. void OnClearButtonClicked(object sender, EventArgs args) { // Color the bitmap background, erasing all user drawing bitmapCanvas.Clear(backgroundColor); }
public void Skia_Clear() { skCanvas.Clear(new SKColor(145, 145, 156)); }
private void DrawTileset() { //currentTilesetInfo = TilesetInfo.ReadTilesetInfo(currentRoom.StateInfo[currentRoomState].StateData.TilesetIndex); currentTilesetInfo = TilesetInfo.ReadTilesetInfo(3); currentTileset = Tileset.ReadTilesetFromInfo(currentTilesetInfo); // Load global palette list for (int i = 0; i < 9; ++i) { TilesetInfo info = TilesetInfo.ReadTilesetInfo(i); palettes.Add(Tileset.ReadPalette(info.PaletteAddress.ToPointer())); } // Combine common and unique tile graphics data //byte[] allTileData = new byte[currentTileset.TileGraphics.CommonTileGraphics.Length + currentTileset.TileGraphics.UniqueTileGraphics.Length]; byte[] allTileData = new byte[0x5000 + currentTileset.TileGraphics.CommonTileGraphics.Length]; // should be 0x8000 instead of 0x5000 for tileset 26 or 17? Array.Copy(currentTileset.TileGraphics.UniqueTileGraphics, 0, allTileData, 0, currentTileset.TileGraphics.UniqueTileGraphics.Length); Array.Copy(currentTileset.TileGraphics.CommonTileGraphics, 0, allTileData, 0x5000, currentTileset.TileGraphics.CommonTileGraphics.Length); // Convert indexed tile graphics to a paletted pixelmap byte[] allTilePixelData = Tileset.IndexedGraphicsToPixelData(allTileData); // Apparently used to add 0x5000 in earlier versions of SMILE, but was later changed to 0x6000. // I've opted to simply add the length of unique tile graphics just to be more precise. int tileCount = allTileData.Length / 32; // DISABLED UNTIL I CAN FIGURE OUT WHAT'S WRONG int tileDrawSize = 8; int lineSize = 32; // Number of blocks to draw per line in the block preview SKImageInfo imageInfo = new SKImageInfo((tileCount * tileDrawSize * 2) / lineSize, (lineSize * tileDrawSize * 2)); using SKSurface surface = SKSurface.Create(imageInfo); SKCanvas canvas = surface.Canvas; canvas.Clear(SKColors.Transparent); byte[] combinedTileTable = new byte[currentTileset.TileTables.CommonTileTable.Length + currentTileset.TileTables.UniqueTileTable.Length]; Array.Copy(currentTileset.TileTables.CommonTileTable, 0, combinedTileTable, 0, currentTileset.TileTables.CommonTileTable.Length); Array.Copy(currentTileset.TileTables.UniqueTileTable, 0, combinedTileTable, currentTileset.TileTables.CommonTileTable.Length, currentTileset.TileTables.UniqueTileTable.Length); for (int blockNum = 0; blockNum < combinedTileTable.Length; ++blockNum) { ushort[] blockEntry = Tileset.GetTileTableEntry(blockNum, combinedTileTable); int lineNum = blockNum / lineSize; for (int e = 0; e < 4; ++e) { SKBitmap tileBitmap = new SKBitmap(8, 8); ushort tileData = blockEntry[e]; ushort tileNum = (ushort)(tileData & 0x3FF); bool xFlip = ((tileData & 0b0100000000000000) >> 14) == 1; bool yFlip = ((tileData & 0b1000000000000000) >> 15) == 1; byte paletteNum = (byte)((tileData & 0b0001110000000000) >> 10); for (byte y = 0; y < 8; ++y) { for (byte x = 0; x < 8; ++x) { // Get palette color for pixel int trueOffset = (tileNum * 64) + (y * 8) + x; uint colorIndex = allTilePixelData[trueOffset]; // Get tile palette uint[] palette = PaletteConverter.SnesPaletteToPcPalette(currentTileset.Palette, false); uint[] paletteMask = PaletteConverter.SnesPaletteToPcPalette(currentTileset.Palette, true); SKColor pixelColor = SKColor.Parse(palette[colorIndex].ToString("X6")); if (xFlip && yFlip) { tileBitmap.SetPixel(7 - x, 7 - y, pixelColor); } else if (xFlip) { tileBitmap.SetPixel(7 - x, y, pixelColor); } else if (yFlip) { tileBitmap.SetPixel(x, 7 - y, pixelColor); } else { tileBitmap.SetPixel(x, y, pixelColor); } } } int drawStartX, drawStartY, drawEndX, drawEndY; drawStartX = (((blockNum % lineSize) * 2) + (e % 2)) * tileDrawSize; drawEndX = (((blockNum % lineSize) * 2) + (e % 2) + 1) * tileDrawSize; drawStartY = ((lineNum * 2) + (e / 2)) * tileDrawSize; drawEndY = ((lineNum * 2) + (e / 2) + 1) * tileDrawSize; canvas.DrawBitmap(tileBitmap, new SKRect(drawStartX, drawStartY, drawEndX, drawEndY)); } } /* * // Draw the raw tileset image instead of block data * int lineSize = 16; * int tileDrawSize = 32; * SKImageInfo imageInfo = new SKImageInfo(lineSize * tileDrawSize, (tileCount / lineSize) * tileDrawSize); * using SKSurface surface = SKSurface.Create(imageInfo); * SKCanvas canvas = surface.Canvas; * canvas.Clear(SKColors.Transparent); * * for (int tileNum = 0; tileNum < tileCount; ++tileNum) * { * int lineNum = tileNum / lineSize; * SKBitmap tileBitmap = new SKBitmap(8, 8); * for (byte y = 0; y < 8; ++y) * { * for (byte x = 0; x < 8; ++x) * { * // Get palette color for pixel * uint colorIndex = allTilePixelData[(tileNum * 64) + (y * 8) + x]; * uint pixelColor = pcPalette[colorIndex]; * tileBitmap.SetPixel(x, y, SKColor.Parse(pixelColor.ToString("X6"))); * } * } * int drawStartX, drawEndX, drawStartY, drawEndY; * drawStartX = (tileNum % lineSize) * tileDrawSize; * drawEndX = ((tileNum % lineSize) + 1) * tileDrawSize; * drawStartY = lineNum * tileDrawSize; * drawEndY = (lineNum + 1) * tileDrawSize; * canvas.DrawBitmap(tileBitmap, new SKRect(drawStartX, drawStartY, drawEndX, drawEndY)); * * //Mark each tile with its index for debugging assistance * SKTextBlobBuilder textBuilder = new SKTextBlobBuilder(); * SKPaint fontPaint = new SKPaint(); * fontPaint.Color = SKColors.Red; * fontPaint.StrokeWidth = 5; * fontPaint.Typeface = SKTypeface.FromFamilyName("Courier New", SKFontStyle.Bold); * fontPaint.TextSize = 14; * canvas.DrawText(tileNum.ToString(), drawStartX, drawEndY, fontPaint); * } */ // Copy data to output Image using SKImage image = surface.Snapshot(); using SKData data = image.Encode(SKEncodedImageFormat.Png, 100); using MemoryStream mStream = new MemoryStream(data.ToArray()); BitmapImage bmp = new BitmapImage(); bmp.BeginInit(); bmp.StreamSource = mStream; bmp.CacheOption = BitmapCacheOption.OnLoad; bmp.EndInit(); tileset_OutputImage.Source = bmp; }
private void CanvasView_PaintSurface(object sender, SKPaintSurfaceEventArgs e) { SKCanvas canvas = e.Surface.Canvas; canvas.Clear(SKColors.CornflowerBlue); int width = e.Info.Width; int height = e.Info.Height; canvas.Translate(width / 2, height / 2); canvas.Scale(width / 210f); canvas.DrawCircle(0, 0, 100, blackFillPaint); var painter = new TextPainter { FontSize = 8, TextColor = SKColors.White }; for (int i = 0; i < 60; i++) { // Dots canvas.Save(); canvas.RotateDegrees(6 * i); canvas.DrawCircle(0, -90, i % 5 == 0 ? 4 : 2, whiteFillPaint); canvas.Restore(); // Maths if (i % 5 == 0) { painter.Text = labels[i / 5]; var measure = painter.Measure(width).Value; var θ = (90 - 6 * i) / 180f * PI; var sinθ = (float)Sin(θ); var cosθ = (float)Cos(θ); painter.Draw(canvas, new System.Drawing.PointF((75) * cosθ - measure.Width / 2, (-75) * sinθ - measure.Height / 2), float.PositiveInfinity); } } DateTime dateTime = DateTime.Now; // H canvas.Save(); canvas.RotateDegrees(30 * dateTime.Hour + dateTime.Minute / 2f); whiteStrokePaint.StrokeWidth = 12; canvas.DrawLine(0, 0, 0, -50, whiteStrokePaint); canvas.Restore(); // M canvas.Save(); canvas.RotateDegrees(6 * dateTime.Minute + dateTime.Second / 10f); whiteStrokePaint.StrokeWidth = 6; canvas.DrawLine(0, 0, 0, -65, whiteStrokePaint); canvas.Restore(); // S canvas.Save(); float seconds = dateTime.Second + dateTime.Millisecond / 1000f; canvas.RotateDegrees(6f * seconds); redStrokePaint.StrokeWidth = 2; canvas.DrawLine(0, 0, 0, -75, redStrokePaint); canvas.Restore(); }
public void Draw(SpriteBatch batch, Point position, Color color) { batch.Begin(); if (Texture == null) { using (SKCanvas canvas = new SKCanvas(bitmap)) using (SKPaint paint = new SKPaint()) { paint.Typeface = DefaultTypeface; paint.TextSize = _textSize; paint.Color = new SKColor(TextColor.R, TextColor.G, TextColor.B, TextColor.A); // Enable Text Shadow paint.ImageFilter = SKImageFilter.CreateDropShadow( ShadowOffsetX, ShadowOffsetY, ShadowSigmaX, ShadowSigmaY, SKColors.Black, SKDropShadowImageFilterShadowMode.DrawShadowAndForeground); // Enable Text Stroke //paint.StrokeCap = SKStrokeCap.Square; //paint.StrokeWidth = 1; //paint.IsStroke = true; canvas.Clear(SKColor.Empty); var textOffsetY = -paint.FontMetrics.Ascent; var underline = paint.FontMetrics.UnderlinePosition ?? paint.FontMetrics.Descent; var underlineOffsetY = textOffsetY + underline; var lines = SplitLines(paint); int counter = 0; foreach (var line in lines) { var textPosition = new SKPoint(0, textOffsetY + counter * paint.FontSpacing); canvas.DrawText(line.Line, textPosition, paint); // Enable Underline Effect { var underlinePosition1 = new SKPoint(0, underlineOffsetY + counter * paint.FontSpacing); var underlinePosition2 = new SKPoint(0 + line.Width, underlineOffsetY + counter * paint.FontSpacing); paint.StrokeWidth = (int)(paint.FontMetrics.UnderlineThickness ?? 1); paint.IsStroke = true; canvas.DrawLine(underlinePosition1, underlinePosition2, paint); paint.IsStroke = false; } counter++; } // Top of Text box. canvas.DrawLine(new SKPoint(0, 1), new SKPoint(RealWidth, 1), paint); // Bottom of Text box. canvas.DrawLine(new SKPoint(0, 1 + RealHeight), new SKPoint(RealWidth, 1 + RealHeight), paint); // Bottom of canvas. canvas.DrawLine(new SKPoint(0, _size.Y - 1), new SKPoint(RealWidth, _size.Y - 1), paint); Texture = new Texture2D(batch.GraphicsDevice, _size.X, _size.Y, false, SurfaceFormat.Color); Texture.SetData(bitmap.Bytes); } } batch.Draw(Texture, position.ToVector2(), color); batch.End(); }
public void Fill(SKColor color) { using var canvas = new SKCanvas(_bitmap); canvas.Clear(color); }
public void Clear(Color color) { _image.Clear(color.SKColor()); }
public DrawingContextImpl(SKCanvas canvas) { Canvas = canvas; Canvas.Clear(); }
private SKBitmap BuildThumbCollageBitmap(string[] paths, int width, int height) { var bitmap = new SKBitmap(width, height); using (var canvas = new SKCanvas(bitmap)) { canvas.Clear(SKColors.Black); // determine sizes for each image that will composited into the final image var iSlice = Convert.ToInt32(width * 0.23475); int iTrans = Convert.ToInt32(height * .25); int iHeight = Convert.ToInt32(height * .70); var horizontalImagePadding = Convert.ToInt32(width * 0.0125); var verticalSpacing = Convert.ToInt32(height * 0.01111111111111111111111111111111); int imageIndex = 0; for (int i = 0; i < 4; i++) { using (var currentBitmap = GetNextValidImage(paths, imageIndex, out int newIndex)) { imageIndex = newIndex; if (currentBitmap == null) { continue; } // resize to the same aspect as the original int iWidth = (int)Math.Abs(iHeight * currentBitmap.Width / currentBitmap.Height); using (var resizeBitmap = new SKBitmap(iWidth, iHeight, currentBitmap.ColorType, currentBitmap.AlphaType)) { currentBitmap.ScalePixels(resizeBitmap, SKFilterQuality.High); // crop image int ix = (int)Math.Abs((iWidth - iSlice) / 2); using (var image = SKImage.FromBitmap(resizeBitmap)) using (var subset = image.Subset(SKRectI.Create(ix, 0, iSlice, iHeight))) { // draw image onto canvas canvas.DrawImage(subset ?? image, (horizontalImagePadding * (i + 1)) + (iSlice * i), verticalSpacing); if (subset == null) { continue; } // create reflection of image below the drawn image using (var croppedBitmap = SKBitmap.FromImage(subset)) using (var reflectionBitmap = new SKBitmap(croppedBitmap.Width, croppedBitmap.Height / 2, croppedBitmap.ColorType, croppedBitmap.AlphaType)) { // resize to half height currentBitmap.ScalePixels(reflectionBitmap, SKFilterQuality.High); using (var flippedBitmap = new SKBitmap(reflectionBitmap.Width, reflectionBitmap.Height, reflectionBitmap.ColorType, reflectionBitmap.AlphaType)) using (var flippedCanvas = new SKCanvas(flippedBitmap)) { // flip image vertically var matrix = SKMatrix.MakeScale(1, -1); matrix.SetScaleTranslate(1, -1, 0, flippedBitmap.Height); flippedCanvas.SetMatrix(matrix); flippedCanvas.DrawBitmap(reflectionBitmap, 0, 0); flippedCanvas.ResetMatrix(); // create gradient to make image appear as a reflection var remainingHeight = height - (iHeight + (2 * verticalSpacing)); flippedCanvas.ClipRect(SKRect.Create(reflectionBitmap.Width, remainingHeight)); using (var gradient = new SKPaint()) { gradient.IsAntialias = true; gradient.BlendMode = SKBlendMode.SrcOver; gradient.Shader = SKShader.CreateLinearGradient(new SKPoint(0, 0), new SKPoint(0, remainingHeight), new[] { new SKColor(0, 0, 0, 128), new SKColor(0, 0, 0, 208), new SKColor(0, 0, 0, 240), new SKColor(0, 0, 0, 255) }, null, SKShaderTileMode.Clamp); flippedCanvas.DrawPaint(gradient); } // finally draw reflection onto canvas canvas.DrawBitmap(flippedBitmap, (horizontalImagePadding * (i + 1)) + (iSlice * i), iHeight + (2 * verticalSpacing)); } } } } } } } return(bitmap); }
//loop private void canvasView_PaintSurface(object sender, SKPaintSurfaceEventArgs e) //AREA DI DISEGNO { if (startup) { translateBottonBarDown(); //abbasso al barra height = (int)(canvasView.Height * dpi); startup = false; } SKCanvas canvas = e.Surface.Canvas; canvas.Clear(); if (!openPopUp) { foreach (parallaxObj st in stars) //stelle sotto { if (st.paral < 1) { canvas.DrawCircle(getPoint(st.cp.X, st.cp.Y, st.paral), (float)(3.5 * scale), StarColor.colors[st.colorIndex]); } } } if (!openPopUp) { dottedOrbit(canvas); //orbite } createPlanet(canvas); //pianeti if (!openPopUp) { foreach (parallaxObj st in stars) //stelle sopra { if (st.paral > 1) { canvas.DrawCircle(getPoint(st.cp.X, st.cp.Y, st.paral), (float)(3.5 * scale), StarColor.colors[st.colorIndex]); } } } //stampa puntatore sole updateSunPointer(); //animazioni di cliccare ed uscire dal popup if (clickedPlanet) //pre apertura popup { planetTranslationFunction(); } if (restoreCamera) //riportare lo zoom alla posizione prima dello zoom { restoreCameraFunction(); } //creazione del popup con i suoi dati if (openPopUp) { createPopUp(canvas); } if (resetCamera) { resetCameraFunction(); } if (!openPopUp && !restoreCamera) { if (isPinCamActive) { center.X = -pl[iPlanet].coord.X + (width / 2); center.Y = -pl[iPlanet].coord.Y + (height / 2); } } }
public async Task <Tuple <Stream, LoadingResult, ImageInformation> > Resolve(string identifier, TaskParameter parameters, CancellationToken token) { ImageSource source = parameters.Source; if (!string.IsNullOrWhiteSpace(parameters.LoadingPlaceholderPath) && parameters.LoadingPlaceholderPath == identifier) { source = parameters.LoadingPlaceholderSource; } else if (!string.IsNullOrWhiteSpace(parameters.ErrorPlaceholderPath) && parameters.ErrorPlaceholderPath == identifier) { source = parameters.ErrorPlaceholderSource; } var resolvedData = await(Configuration.DataResolverFactory ?? new DataResolverFactory()) .GetResolver(identifier, source, parameters, Configuration) .Resolve(identifier, parameters, token).ConfigureAwait(false); if (resolvedData?.Item1 == null) { throw new FileNotFoundException(identifier); } var svg = new SKSvg() { ThrowOnUnsupportedElement = false, }; SKPicture picture; if (ReplaceStringMap == null || ReplaceStringMap.Count == 0) { using (var svgStream = resolvedData.Item1) { picture = svg.Load(svgStream); } } else { using (var svgStream = resolvedData.Item1) using (var reader = new StreamReader(svgStream)) { var inputString = await reader.ReadToEndAsync(); foreach (var map in ReplaceStringMap .Where(v => v.Key.StartsWith("regex:"))) { inputString = Regex.Replace(inputString, map.Key.Substring(0, 6), map.Value); } var builder = new StringBuilder(inputString); foreach (var map in ReplaceStringMap .Where(v => !v.Key.StartsWith("regex:", StringComparison.OrdinalIgnoreCase))) { builder.Replace(map.Key, map.Value); } using (var svgFinalStream = new MemoryStream(Encoding.UTF8.GetBytes(builder.ToString()))) { picture = svg.Load(svgFinalStream); } } } double sizeX = 0; double sizeY = 0; if (VectorWidth == 0 && VectorHeight == 0) { if (picture.CullRect.Width > 0) { sizeX = picture.CullRect.Width; } else { sizeX = 300; } if (picture.CullRect.Height > 0) { sizeY = picture.CullRect.Height; } else { sizeY = 300; } } else if (VectorWidth > 0 && VectorHeight > 0) { sizeX = VectorWidth; sizeY = VectorHeight; } else if (VectorWidth > 0) { sizeX = VectorWidth; sizeY = (VectorWidth / picture.CullRect.Width) * picture.CullRect.Height; } else { sizeX = (VectorHeight / picture.CullRect.Height) * picture.CullRect.Width; sizeY = VectorHeight; } if (UseDipUnits) { sizeX = sizeX.DpToPixels(); sizeY = sizeY.DpToPixels(); } lock (_encodingLock) { using (var bitmap = new SKBitmap(new SKImageInfo((int)sizeX, (int)sizeY))) //using (var bitmap = new SKBitmap((int)sizeX, (int)sizeY)) using (var canvas = new SKCanvas(bitmap)) using (var paint = new SKPaint()) { canvas.Clear(SKColors.Transparent); float scaleX = (float)sizeX / picture.CullRect.Width; float scaleY = (float)sizeY / picture.CullRect.Height; var matrix = SKMatrix.MakeScale(scaleX, scaleY); canvas.DrawPicture(picture, ref matrix, paint); canvas.Flush(); using (var image = SKImage.FromBitmap(bitmap)) //using (var data = image.Encode(SKImageEncodeFormat.Png, 100)) //TODO disabled because of https://github.com/mono/SkiaSharp/issues/285 using (var data = image.Encode()) { var stream = new MemoryStream(); data.SaveTo(stream); stream.Position = 0; resolvedData.Item3.SetType(ImageInformation.ImageType.SVG); return(new Tuple <Stream, LoadingResult, ImageInformation>(stream, resolvedData.Item2, resolvedData.Item3)); } } } }
public static async Task <byte[]> AnnotateImage(SoftwareBitmap sb, string headerText = "", string footerText = "", int headerSize = 40, int footerSize = 40, int maxWidth = 1280) { try { using (var t = await ConvertToIRandomAccessStream(sb)) { SKPaint pntBlack = new SKPaint() { Color = new SKColor(0, 0, 0) }; SKPaint pntWhite = new SKPaint() { Color = new SKColor(255, 255, 255), TextSize = 24, TextAlign = SKTextAlign.Left }; SKPaint pntWhiteFooter = new SKPaint() { Color = new SKColor(255, 255, 255), TextSize = 22, TextAlign = SKTextAlign.Left }; byte[] data = await ConvertInputStreamToBytes(t); float w = (float)sb.PixelWidth; float h = (float)sb.PixelHeight; float origW = (float)sb.PixelWidth; float origH = (float)sb.PixelHeight; int newWidth = sb.PixelWidth; int newHeight = sb.PixelHeight; if (w > maxWidth) { float aspect = w / h; w = (float)maxWidth; h = w / aspect; newWidth = (int)Math.Ceiling(w); newHeight = (int)Math.Ceiling(h); } SKImageInfo info = new SKImageInfo(newWidth, newHeight + headerSize + footerSize); using (SKSurface sf = SKSurface.Create(info)) using (SKCanvas cnv = sf.Canvas) { using (SKBitmap skb = SKBitmap.Decode(new SKMemoryStream(data))) { cnv.Clear(pntBlack.Color); cnv.DrawBitmap(skb, new SKRect(0, 0, origW, origH), new SKRect(0, (float)headerSize, w, h + (float)headerSize)); if (headerText != "") { cnv.DrawText(headerText, 5, 3 + pntWhite.TextSize, pntWhite); } if (footerText != "") { cnv.DrawText(footerText, 5, 3 + h + headerSize + pntWhiteFooter.TextSize, pntWhiteFooter); } using (SKData enc = sf.Snapshot().Encode(SKEncodedImageFormat.Jpeg, 90)) { return(enc.ToArray()); } } } } } catch (Exception) { } return(new byte[] {}); }
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args) { SKImageInfo info = args.Info; SKSurface surface = args.Surface; SKCanvas canvas = surface.Canvas; canvas.Clear(); SKPoint center = new SKPoint(info.Width / 2, info.Height / 2); float radius = 0.45f * Math.Min(info.Width, info.Height); SKPath path = new SKPath { FillType = (SKPathFillType)Enum.Parse(typeof(SKPathFillType), fillTypePicker.Items[fillTypePicker.SelectedIndex]) }; path.MoveTo(info.Width / 2, info.Height / 2 - radius); for (int i = 1; i < 5; i++) { // angle from vertical double angle = i * 4 * Math.PI / 5; path.LineTo(center + new SKPoint(radius * (float)Math.Sin(angle), -radius * (float)Math.Cos(angle))); } path.Close(); SKPaint strokePaint = new SKPaint { Style = SKPaintStyle.Stroke, Color = SKColors.Red, StrokeWidth = 50, StrokeJoin = SKStrokeJoin.Round }; SKPaint fillPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = SKColors.Blue }; switch (drawingModePicker.SelectedIndex) { case 0: canvas.DrawPath(path, fillPaint); break; case 1: canvas.DrawPath(path, strokePaint); break; case 2: canvas.DrawPath(path, strokePaint); canvas.DrawPath(path, fillPaint); break; case 3: canvas.DrawPath(path, fillPaint); canvas.DrawPath(path, strokePaint); break; } }
//METHODS /********************************************************************** *********************************************************************/ // do the drawing //notice: this method get's called several times. For example when you scroll the listview in buddysystem or when the listview is updated void PaintSurface(object sender, SKPaintSurfaceEventArgs e) { SKImageInfo info = e.Info; var surfaceWidth = info.Width; var surfaceHeight = info.Height; SKSurface surface = e.Surface; SKCanvas canvas = surface.Canvas; if (canvas != null) { canvas.Clear(); //Important! Otherwise the drawing will look messed up in iOS } /*important: the coordinate system starts in the upper left corner*/ float lborder = canvas.LocalClipBounds.Left; float tborder = canvas.LocalClipBounds.Top; float rborder = canvas.LocalClipBounds.Right; float bborder = canvas.LocalClipBounds.Bottom; this.xe = rborder / 100; //using the variable surfacewidth instead would mess everything up this.ye = bborder / 100; MakeSKPaint(); //depends on xe and ye and therfore has to be called after they were initialized // draw on the canvas //rect for memory 80units long SKRect sk_r = new SKRect(xe * 2, ye * 10, xe * 82, ye * 90); //left, top, right, bottom canvas.DrawRect(sk_r, sk_Paint1); //draw an rect with dimensions of sk_r and paint sk_1 //calculate units for memory float memoryUnit = (float)(80f / BuddySystem.absoluteMemorySize); //Draw blocks in memory float startValue = xe * 2; for (int i = 0; i < buddySystem.Count; i++) { //block int blockSize = buddySystem[i].GetBlockSize(); float value = memoryUnit * blockSize; SKPoint sk_p1 = new SKPoint(startValue + xe * value, ye * 10); SKPoint sk_p2 = new SKPoint(startValue + xe * value, ye * 90); canvas.DrawLine(sk_p1, sk_p2, sk_Paint1); startValue = startValue + xe * value; } //draw processes in memory float startValue2 = xe * 2; for (int i = 0; i < buddySystem.Count; i++) { int blockSize2 = buddySystem[i].GetBlockSize(); float value2 = memoryUnit * blockSize2; //process int processSize = buddySystem[i].GetProcessSize(); float processValue = memoryUnit * processSize; bool isFree = buddySystem[i].GetFree(); if (!isFree) { //sry for that. Is there a better(shorter) solution? SKPaint processColor; switch (buddySystem[i].GetProcessName()) { case "A": processColor = sk_A; break; case "B": processColor = sk_B; break; case "C": processColor = sk_C; break; case "D": processColor = sk_D; break; case "E": processColor = sk_E; break; case "F": processColor = sK_F; break; case "G": processColor = sk_G; break; case "H": processColor = sk_H; break; case "I": processColor = sk_I; break; case "J": processColor = sk_J; break; case "K": processColor = sk_K; break; case "L": processColor = sk_L; break; case "M": processColor = sk_M; break; case "N": processColor = sk_N; break; case "O": processColor = sk_O; break; case "P": processColor = sk_P; break; case "Q": processColor = sk_Q; break; case "R": processColor = sk_R; break; case "S": processColor = sk_S; break; case "T": processColor = sk_T; break; case "U": processColor = sk_U; break; case "V": processColor = sK_V; break; case "W": processColor = sk_W; break; case "X": processColor = sk_X; break; case "Y": processColor = sk_Y; break; case "Z": processColor = sk_Z; break; default: processColor = sk_processColor; break; } SKRect sk_r2 = new SKRect(startValue2, ye * 10, startValue2 + xe * processValue, ye * 90); canvas.DrawRect(sk_r2, processColor); //left, top, right, bottom, color SKPoint textPosition = new SKPoint(startValue2 - xe + ((xe * processValue) / 2), ye * 60); canvas.DrawText(buddySystem[i].GetProcessName(), textPosition, sk_blackTextSmall); } startValue2 = startValue2 + xe * value2; } //text SKPaint infoColor = sk_blackTextSmall; //Debug.WriteLine("Processname " + this.processName); if (this.processName == "merge") { canvas.DrawText("merge", new SKPoint(xe * 84, ye * 55), infoColor); } else if (this.processName == "first") { canvas.DrawText("size: " + BuddySystem.absoluteMemorySize.ToString(), new SKPoint(xe * 84, ye * 55), infoColor); } else { if (this.endProcess) { //TODO canvas.DrawText("end: " + processName, new SKPoint(xe * 84, ye * 55), infoColor); } else { //TODO canvas.DrawText("start: " + processName, new SKPoint(xe * 84, ye * 55), infoColor); } } //execute all drawing actions canvas.Flush(); }
private void DrawRoom() { if (currentRoom.Header.Height == 0 || currentRoom.Header.Width == 0 || currentLevelData.Header == 0) { return; } int tileCountX = currentRoom.Header.Width * 16; int tileCountY = currentRoom.Header.Height * 16; // Set up the output area levelEditorWidth = tileCountX * 16; levelEditorHeight = tileCountY * 16; SKImageInfo imageInfo = new SKImageInfo((int)levelEditorWidth, (int)levelEditorHeight); using SKSurface surface = SKSurface.Create(imageInfo); SKCanvas canvas = surface.Canvas; canvas.Clear(SKColors.Transparent); using SKPaint tilePaint = new SKPaint(); tilePaint.IsAntialias = false; tilePaint.StrokeWidth = 1; tilePaint.Style = SKPaintStyle.Fill; // Render the tiles // Layer 1 if (layersToDraw.HasFlag(RoomLayers.TileLayer1)) { for (int tileY = 0; tileY < tileCountY; ++tileY) { for (int tileX = 0; tileX < tileCountX; ++tileX) { SKRect tileRect = new SKRect(tileX * 16, tileY * 16, tileX * 16 + 16, tileY * 16 + 16); byte blockId = currentLevelData.TileLayer1[tileX, tileY].BlockID; tilePaint.Color = SKColor.Parse((blockId * 100).ToString("X6")); canvas.DrawRect(tileRect, tilePaint); } } } // Layer 2 if (layersToDraw.HasFlag(RoomLayers.TileLayer2)) { if (currentLevelData.TileLayer2.Length > 0) { for (int tileY = 0; tileY < tileCountY; ++tileY) { for (int tileX = 0; tileX < tileCountX; ++tileX) { SKRect tileRect = new SKRect(tileX * 16, tileY * 16, tileX * 16 + 16, tileY * 16 + 16); byte blockId = currentLevelData.TileLayer2[tileX, tileY].BlockID; tilePaint.Color = SKColor.Parse($"7F{(blockId << 16).ToString("X6")}"); canvas.DrawRect(tileRect, tilePaint); } } } } using SKImage image = surface.Snapshot(); using SKData data = image.Encode(SKEncodedImageFormat.Png, 100); using MemoryStream mStream = new MemoryStream(data.ToArray()); BitmapImage bmp = new BitmapImage(); bmp.BeginInit(); bmp.StreamSource = mStream; bmp.CacheOption = BitmapCacheOption.OnLoad; bmp.EndInit(); roomRenderOutput = bmp; slider_Zoom_ValueChanged(this, new RoutedPropertyChangedEventArgs <double>(100, 100)); }
private void canvasView_PaintSurface(object sender, SKPaintSurfaceEventArgs e) { SKSurface surface = e.Surface; SKCanvas canvas = surface.Canvas; canvas.Clear(SKColors.CornflowerBlue); int width = e.Info.Width; int height = e.Info.Height; // Set Transforms canvas.Translate(width / 2, height / 2); canvas.Scale(Math.Min(width / 210f, height / 520f)); // Date Time DateTime dateTime = DateTime.Now; /// Head canvas.DrawCircle(0, -160, 75, blackFillPaint); // Draw ears and eyes for (int i = 0; i < 2; i++) { canvas.Save(); canvas.Scale(2 * i - 1, 1); canvas.Save(); canvas.Translate(-65, -225); canvas.DrawPath(catEarPath, blackFillPaint); canvas.Restore(); canvas.Save(); canvas.Translate(-60, -170); canvas.RotateDegrees(7, 0, 0); canvas.DrawPath(catEyePath, greenFillPaint); canvas.DrawPath(catPupilPath, blackFillPaint); canvas.Restore(); // draw whiskers canvas.DrawLine(10, -120, 100, -100, whiteStrokePaint); canvas.DrawLine(10, -125, 100, -120, whiteStrokePaint); canvas.DrawLine(10, -130, 100, -140, whiteStrokePaint); canvas.DrawLine(10, -135, 100, -160, whiteStrokePaint); canvas.Restore(); } // Draw tail canvas.DrawPath(catTailPath, blackStrokePaint); // Clock Background canvas.DrawCircle(0, 0, 100, blackFillPaint); // Hour and Minute Marks for (int angle = 0; angle < 360; angle += 6) { canvas.DrawCircle(0, -90, angle % 30 == 0 ? 4 : 2, whiteFillPaint); canvas.RotateDegrees(6); } // Hour Hand canvas.Save(); canvas.RotateDegrees(30 * dateTime.Hour + dateTime.Minute / 2f); canvas.DrawPath(hourHandPath, greyFillPaint); canvas.DrawPath(hourHandPath, whiteStrokePaint); canvas.Restore(); if (dateTime.Minute == 0) { // await CrossMediaManager.Current.Play("Cat-Street-Meow_Wav.wav"); // var player = Plugin.SimpleAudioPlayer.CrossSimpleAudioPlayer.Current; // player.Load("Cat-Street-Meow-Wav.wav"); } // Minute Hand canvas.Save(); canvas.RotateDegrees(6 * dateTime.Minute + dateTime.Second / 10f); canvas.DrawPath(hourHandPath, greyFillPaint); canvas.DrawPath(minuteHandPath, whiteStrokePaint); canvas.Restore(); // Second Hand canvas.Save(); float seconds = dateTime.Second + dateTime.Millisecond / 1000f; canvas.RotateDegrees(6 * seconds); canvas.DrawLine(0, 10, 0, -80, whiteStrokePaint); canvas.Restore(); }
public void Render(SKCanvas canvas, float canvasWidth, float canvasHeight) { canvas.Clear(new SKColor(0xFFFFFFFF)); const float margin = 80; float?height = (float)(canvasHeight - margin * 2); float?width = (float)(canvasWidth - margin * 2); //width = 25; if (!UseMaxHeight) { height = null; } if (!UseMaxWidth) { width = null; } using (var gridlinePaint = new SKPaint() { Color = new SKColor(0xFFFF0000), StrokeWidth = 1 }) { canvas.DrawLine(new SKPoint(margin, 0), new SKPoint(margin, (float)canvasHeight), gridlinePaint); if (width.HasValue) { canvas.DrawLine(new SKPoint(margin + width.Value, 0), new SKPoint(margin + width.Value, (float)canvasHeight), gridlinePaint); } canvas.DrawLine(new SKPoint(0, margin), new SKPoint((float)canvasWidth, margin), gridlinePaint); if (height.HasValue) { canvas.DrawLine(new SKPoint(0, margin + height.Value), new SKPoint((float)canvasWidth, margin + height.Value), gridlinePaint); } } //string typefaceName = "Times New Roman"; string typefaceName = "Segoe UI"; //string typefaceName = "Segoe Script"; var styleSmall = new Style() { FontFamily = typefaceName, FontSize = 12 * Scale }; var styleScript = new Style() { FontFamily = "Segoe Script", FontSize = 18 * Scale }; var styleHeading = new Style() { FontFamily = typefaceName, FontSize = 24 * Scale, FontWeight = 700 }; var styleNormal = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, LineHeight = 1.0f }; var styleFixedPitch = new Style() { FontFamily = "Courier New", FontSize = 18 * Scale, LineHeight = 1.0f }; var styleLTR = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, TextDirection = TextDirection.LTR }; var styleBold = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, FontWeight = 700 }; var styleUnderline = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, Underline = UnderlineStyle.Gapped, TextColor = new SKColor(0xFFFF0000) }; var styleStrike = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, StrikeThrough = StrikeThroughStyle.Solid }; var styleSubScript = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, FontVariant = FontVariant.SubScript }; var styleSuperScript = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, FontVariant = FontVariant.SuperScript }; var styleItalic = new Style() { FontFamily = typefaceName, FontItalic = true, FontSize = 18 * Scale }; var styleBoldLarge = new Style() { FontFamily = typefaceName, FontSize = 28 * Scale, FontWeight = 700 }; var styleRed = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, TextColor = new SKColor(0xFFFF0000) }; var styleBlue = new Style() { FontFamily = typefaceName, FontSize = 18 * Scale, TextColor = new SKColor(0xFF0000FF) }; var styleFontAwesome = new Style() { FontFamily = "FontAwesome", FontSize = 24 }; _textBlock.Clear(); _textBlock.MaxWidth = width; _textBlock.MaxHeight = height; _textBlock.BaseDirection = BaseDirection; _textBlock.Alignment = TextAlignment; switch (ContentMode) { case 0: _textBlock.AddText("Welcome to RichTextKit!\n", styleHeading); _textBlock.AddText("\nRichTextKit is a rich text layout, rendering and measurement library for SkiaSharp.\n\nIt supports normal, ", styleNormal); _textBlock.AddText("bold", styleBold); _textBlock.AddText(", ", styleNormal); _textBlock.AddText("italic", styleItalic); _textBlock.AddText(", ", styleNormal); _textBlock.AddText("underline", styleUnderline); _textBlock.AddText(" (including ", styleNormal); _textBlock.AddText("gaps over descenders", styleUnderline); _textBlock.AddText("), ", styleNormal); _textBlock.AddText("strikethrough", styleStrike); _textBlock.AddText(", superscript (E=mc", styleNormal); _textBlock.AddText("2", styleSuperScript); _textBlock.AddText("), subscript (H", styleNormal); _textBlock.AddText("2", styleSubScript); _textBlock.AddText("O), ", styleNormal); _textBlock.AddText("colored ", styleRed); _textBlock.AddText("text", styleBlue); _textBlock.AddText(" and ", styleNormal); _textBlock.AddText("mixed ", styleNormal); _textBlock.AddText("sizes", styleSmall); _textBlock.AddText(" and ", styleNormal); _textBlock.AddText("fonts", styleScript); _textBlock.AddText(".\n\n", styleNormal); _textBlock.AddText("Font fallback means emojis work: 🌐 🍪 🍕 🚀 and ", styleNormal); _textBlock.AddText("text shaping and bi-directional text support means complex scripts and languages like Arabic: مرحبا بالعالم, Japanese: ハローワールド, Chinese: 世界您好 and Hindi: हैलो वर्ल्ड are rendered correctly!\n\n", styleNormal); _textBlock.AddText("RichTextKit also supports left/center/right text alignment, word wrapping, truncation with ellipsis place-holder, text measurement, hit testing, painting a selection range, caret position & shape helpers.", styleNormal); break; case 1: _textBlock.AddText("Hello Wor", styleNormal); _textBlock.AddText("ld", styleRed); _textBlock.AddText(". This is normal 18px. These are emojis: 🌐 🍪 🍕 🚀 🏴☠️", styleNormal); _textBlock.AddText("This is ", styleNormal); _textBlock.AddText("bold 28px", styleBoldLarge); _textBlock.AddText(". ", styleNormal); _textBlock.AddText("This is italic", styleItalic); _textBlock.AddText(". This is ", styleNormal); _textBlock.AddText("red", styleRed); _textBlock.AddText(". This is Arabic: (", styleNormal); _textBlock.AddText("تسجّل ", styleNormal); _textBlock.AddText("يتكلّم", styleNormal); _textBlock.AddText("), Hindi: ", styleNormal); _textBlock.AddText("हालाँकि प्रचलित रूप पूज", styleNormal); _textBlock.AddText(", Han: ", styleNormal); _textBlock.AddText("緳 踥踕", styleNormal); break; case 2: _textBlock.AddText("Hello Wor", styleNormal); _textBlock.AddText("ld", styleRed); _textBlock.AddText(".\nThis is normal 18px.\nThese are emojis: 🌐 🍪 🍕 🚀\n", styleNormal); _textBlock.AddText("This is ", styleNormal); _textBlock.AddText("bold 28px", styleBoldLarge); _textBlock.AddText(".\n", styleNormal); _textBlock.AddText("This is italic", styleItalic); _textBlock.AddText(".\nThis is ", styleNormal); _textBlock.AddText("red", styleRed); /* * tle.AddText(".\nThis is Arabic: (", styleNormal); * tle.AddText("تسجّل ", styleNormal); * tle.AddText("يتكلّم", styleNormal); * tle.AddText("), Hindi: ", styleNormal); */ _textBlock.AddText(".\nThis is Arabic: (تسجّل يتكلّم), Hindi: ", styleNormal); _textBlock.AddText("हालाँकि प्रचलित रूप पूज", styleNormal); _textBlock.AddText(", Han: ", styleNormal); _textBlock.AddText("緳 踥踕", styleNormal); break; case 3: _textBlock.AddText("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Phasellus semper, sapien vitae placerat sollicitudin, lorem diam aliquet quam, id finibus nisi quam eget lorem.\nDonec facilisis sem nec rhoncus elementum. Cras laoreet porttitor malesuada.\n\nVestibulum sed lacinia diam. Mauris a mollis enim. Cras in rhoncus mauris, at vulputate nisl. Sed nec lobortis dolor, hendrerit posuere quam. Vivamus malesuada sit amet nunc ac cursus. Praesent volutpat euismod efficitur. Nam eu ante.", styleNormal); break; case 4: //_textBlock.AddText("مرحبا بالعالم. هذا هو اختبار التفاف \nالخط للتأكد من أنه يعمل للغات من اليمين إلى اليسار.\n", styleNormal); _textBlock.AddText("مرحبا بالعالم. هذا هو اختبار التفاف \n", styleNormal); _textBlock.AddText("مرحبا بالعالم. هذا هو اختبار الت", styleNormal); _textBlock.AddText("فاف \n", styleUnderline); break; case 5: //_textBlock.AddText("مرحبا بالعالم. هذا هو اختبار التفاف الخط للتأكد من \u2066ACME Inc.\u2069 أنه يعمل للغات من اليمين إلى اليسار.", styleNormal); _textBlock.AddText("مرحبا بالعالم. هذا هو اختبار التفاف الخط للتأكد من ", styleNormal); _textBlock.AddText("ACME Inc.", styleLTR); _textBlock.AddText(" أنه يعمل للغات من اليمين إلى اليسار.", styleNormal); break; case 6: _textBlock.AddText("Subscript: H", styleNormal); _textBlock.AddText("2", styleSubScript); _textBlock.AddText("O Superscript: E=mc", styleNormal); _textBlock.AddText("2", styleSuperScript); _textBlock.AddText(" Key: C", styleNormal); _textBlock.AddText("♯", styleSuperScript); _textBlock.AddText(" B", styleNormal); _textBlock.AddText("♭", styleSubScript); break; case 7: _textBlock.AddText("The quick brown fox jumps over the lazy dog.", styleUnderline); _textBlock.AddText(" ", styleNormal); _textBlock.AddText("Strike Through", styleStrike); _textBlock.AddText(" something ends in wooooooooq", styleNormal); break; case 8: _textBlock.AddText("Apples and Bananas\r\n", styleNormal); _textBlock.AddText("Pears\r\n", styleNormal); _textBlock.AddText("Bananas\r\n", styleNormal); break; case 9: _textBlock.AddText("Toggle Theme\r\n", styleNormal); _textBlock.AddText("T", styleUnderline); _textBlock.AddText("oggle Theme\r\n", styleNormal); break; case 10: _textBlock.AddText("", styleNormal); break; case 11: _textBlock.AddText("\uF06B", styleFontAwesome); break; case 12: _textBlock.AddText(".|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|.|\n", styleFixedPitch); _textBlock.AddText("♩♩♩♩♩♩♩♩♩♩♩\n", styleFixedPitch); _textBlock.AddText("\n", styleFixedPitch); _textBlock.AddText(" ♩__♩__♩. ♩. ♩. x4\n", styleFixedPitch); _textBlock.AddText(" ♩__♩__♩. ♩. ♩. x4\n", styleFixedPitch); _textBlock.AddText(" ♩ ♩ ♩. ♩ ♪ ♩ ♪ x4\n", styleFixedPitch); _textBlock.AddText(" ♩ ♩ ♩ ♪ ♩ ♪ ♩ ♪ x8\n", styleFixedPitch); _textBlock.AddText("\n", styleFixedPitch); _textBlock.AddText(" 🌐 🍪 🍕 🚀 🏴☠️ xxx\n", styleFixedPitch); _textBlock.AddText(" 🌐 🍪 🍕 🚀 xxx\n", styleFixedPitch); _textBlock.AddText(" 🌐🍪🍕🚀 xxx\n", styleFixedPitch); break; } var sw = new Stopwatch(); sw.Start(); _textBlock.Layout(); var elapsed = sw.ElapsedMilliseconds; var options = new TextPaintOptions() { SelectionColor = new SKColor(0x60FF0000), }; HitTestResult?htr = null; CaretInfo? ci = null; if (_showHitTest) { htr = _textBlock.HitTest(_hitTestX - margin, _hitTestY - margin); if (htr.Value.OverCodePointIndex >= 0) { options.SelectionStart = htr.Value.OverCodePointIndex; options.SelectionEnd = _textBlock.CaretIndicies[_textBlock.LookupCaretIndex(htr.Value.OverCodePointIndex) + 1]; } ci = _textBlock.GetCaretInfo(htr.Value.ClosestCodePointIndex); } if (ShowMeasuredSize) { using (var paint = new SKPaint() { Color = new SKColor(0x1000FF00), IsStroke = false, }) { var rect = new SKRect(margin + _textBlock.MeasuredPadding.Left, margin, margin + _textBlock.MeasuredWidth + _textBlock.MeasuredPadding.Left, margin + _textBlock.MeasuredHeight); canvas.DrawRect(rect, paint); } } if (_textBlock.MeasuredOverhang.Left > 0) { using (var paint = new SKPaint() { Color = new SKColor(0xFF00fff0), StrokeWidth = 1 }) { canvas.DrawLine(new SKPoint(margin - _textBlock.MeasuredOverhang.Left, 0), new SKPoint(margin - _textBlock.MeasuredOverhang.Left, (float)canvasHeight), paint); } } if (_textBlock.MeasuredOverhang.Right > 0) { using (var paint = new SKPaint() { Color = new SKColor(0xFF00ff00), StrokeWidth = 1 }) { float x; if (_textBlock.MaxWidth.HasValue) { x = margin + _textBlock.MaxWidth.Value; } else { x = margin + _textBlock.MeasuredWidth; } x += _textBlock.MeasuredOverhang.Right; canvas.DrawLine(new SKPoint(x, 0), new SKPoint(x, (float)canvasHeight), paint); } } _textBlock.Paint(canvas, new SKPoint(margin, margin), options); if (ci != null) { using (var paint = new SKPaint() { Color = new SKColor(0xFF000000), IsStroke = true, IsAntialias = true, StrokeWidth = Scale, }) { var rect = ci.Value.CaretRectangle; rect.Offset(margin, margin); canvas.DrawLine(rect.Right, rect.Top, rect.Left, rect.Bottom, paint); } } var state = $"Size: {width} x {height} Base Direction: {BaseDirection} Alignment: {TextAlignment} Content: {ContentMode} scale: {Scale} time: {elapsed}"; canvas.DrawText(state, margin, 20, new SKPaint() { Typeface = SKTypeface.FromFamilyName("Arial"), TextSize = 12, IsAntialias = true, }); state = $"Selection: {options.SelectionStart}-{options.SelectionEnd} Closest: {(htr.HasValue ? htr.Value.ClosestCodePointIndex.ToString() : "-")}"; canvas.DrawText(state, margin, 40, new SKPaint() { Typeface = SKTypeface.FromFamilyName("Arial"), TextSize = 12, IsAntialias = true, }); }
private void canvas_PaintSurface( object sender, SKPaintSurfaceEventArgs args) { SKImageInfo info = args.Info; SKSurface surface = args.Surface; SKCanvas canvas = surface.Canvas; SKPaint strokePaint = GetPaintColor(SKPaintStyle.Stroke, null, 10, SKStrokeCap.Square); SKPaint dotPaint = GetPaintColor(SKPaintStyle.Fill, "#DE0469"); SKPaint hrPaint = GetPaintColor(SKPaintStyle.Stroke, "#262626", 4, SKStrokeCap.Square); SKPaint blackPaint = GetPaintColor(SKPaintStyle.Fill, "#262626"); SKPaint minPaint = GetPaintColor(SKPaintStyle.Stroke, "#DE0469", 2, SKStrokeCap.Square); SKPaint bgPaint = GetPaintColor(SKPaintStyle.Stroke, "#FFFFFF"); canvas.Clear(); SKRect arcRect = new SKRect(10, 10, info.Width - 10, info.Height - 10); SKRect bgRect = new SKRect(25, 25, info.Width - 25, info.Height - 25); canvas.DrawOval(bgRect, bgPaint); strokePaint.Shader = SKShader.CreateLinearGradient( new SKPoint(arcRect.Left, arcRect.Right), new SKPoint(arcRect.Right, arcRect.Left), new SKColor[] { SKColor.Parse("#DE0469"), SKColors.Transparent }, new float[] { 0, 1 }, SKShaderTileMode.Repeat); _path.ArcTo(arcRect, 45, arcLength, true); canvas.DrawPath(_path, strokePaint); canvas.Translate(info.Width / 2, info.Height / 2); canvas.Scale(info.Width / 200f); canvas.Save(); canvas.RotateDegrees(240); canvas.DrawCircle(0, -75, 2, dotPaint); canvas.Restore(); DateTime dateTime = DateTime.Now; //HourHand canvas.Save(); canvas.RotateDegrees(30 * dateTime.Hour + (0.5f * dateTime.Minute) + (0.033f * dateTime.Second)); canvas.DrawLine(0, 5, 0, -60, hrPaint); canvas.Restore(); //MinuteHand canvas.Save(); canvas.RotateDegrees(6 * dateTime.Minute + (0.1f * dateTime.Second)); canvas.DrawLine(0, 20, 0, -90, hrPaint); canvas.Restore(); //SecondHand canvas.Save(); canvas.RotateDegrees(6 * dateTime.Second); canvas.DrawLine(0, 10, 0, -90, minPaint); canvas.Restore(); canvas.DrawCircle(0, 0, 5, dotPaint); for (int angle = 0; angle < 360; angle += 6) { canvas.DrawCircle(0, -90, angle % 30 == 0 ? 1 : 0.5f, blackPaint); canvas.RotateDegrees(6); } secondsText.Text = dateTime.Second.ToString("00"); timeText.Text = dateTime.ToString("hh:mm"); periodText.Text = dateTime.Hour >= 12 ? "PM" : "AM"; var alarmDiff = _alarmDate - dateTime; alarmText.Text = $"{alarmDiff.Hours}h {alarmDiff.Minutes}m until next alarm"; }
void OnPaintSurface(SKSurface surface, int width, int height) { // Get the canvas SKCanvas canvas = surface.Canvas; // These two dimensions should be the same. int canvasSize = Math.Min(width, height); // If bitmap does not exist, create it if (bitmap == null) { // Set three fields bitmapSize = canvasSize; bitmap = new SKBitmap(bitmapSize, bitmapSize); bitmapCanvas = new SKCanvas(bitmap); // Establishes circular clipping and colors background PrepBitmap(bitmapCanvas, bitmapSize); } // If the canvas has become larger, make a new bitmap of that size. else if (bitmapSize < canvasSize) { // New versions of the three fields int newBitmapSize = canvasSize; SKBitmap newBitmap = new SKBitmap(newBitmapSize, newBitmapSize); SKCanvas newBitmapCanvas = new SKCanvas(newBitmap); // New circular clipping and background PrepBitmap(newBitmapCanvas, newBitmapSize); // Copy old bitmap to new bitmap float diff = (newBitmapSize - bitmapSize) / 2f; newBitmapCanvas.DrawBitmap(bitmap, diff, diff); // Dispose old bitmap and its canvas bitmapCanvas.Dispose(); bitmap.Dispose(); // Set fields to new values bitmap = newBitmap; bitmapCanvas = newBitmapCanvas; bitmapSize = newBitmapSize; } // Clear the canvas canvas.Clear(SKColors.White); // Set the rotate transform float radius = canvasSize / 2; canvas.RotateDegrees(angle, radius, radius); // Set a circular clipping area clipPath.Reset(); clipPath.AddCircle(radius, radius, radius); canvas.ClipPath(clipPath); // Draw the bitmap float offset = (canvasSize - bitmapSize) / 2f; canvas.DrawBitmap(bitmap, offset, offset); // Draw the cross hairs canvas.DrawLine(radius, 0, radius, canvasSize, thinLinePaint); canvas.DrawLine(0, radius, canvasSize, radius, thinLinePaint); }
public void DrawBackground(Brush style) { canvas.Clear(new SKColor(style.Paint.BackgroundColor.R, style.Paint.BackgroundColor.G, style.Paint.BackgroundColor.B, style.Paint.BackgroundColor.A)); }
public async Task <Tuple <Stream, LoadingResult, ImageInformation> > Resolve(string identifier, TaskParameter parameters, CancellationToken token) { ImageSource source = parameters.Source; if (!string.IsNullOrWhiteSpace(parameters.LoadingPlaceholderPath) && parameters.LoadingPlaceholderPath == identifier) { source = parameters.LoadingPlaceholderSource; } else if (!string.IsNullOrWhiteSpace(parameters.ErrorPlaceholderPath) && parameters.ErrorPlaceholderPath == identifier) { source = parameters.ErrorPlaceholderSource; } var resolvedData = await(Configuration.DataResolverFactory ?? new DataResolverFactory()) .GetResolver(identifier, source, parameters, Configuration) .Resolve(identifier, parameters, token).ConfigureAwait(false); if (resolvedData?.Item1 == null) { throw new FileNotFoundException(identifier); } var svg = new SKSvg() { ThrowOnUnsupportedElement = false, }; SKPicture picture; if (ReplaceStringMap == null && ReplaceStringMap.Count == 0) { using (var svgStream = resolvedData.Item1) { picture = svg.Load(resolvedData?.Item1); } } else { using (var svgStream = resolvedData.Item1) using (var reader = new StreamReader(svgStream)) { var builder = new StringBuilder(await reader.ReadToEndAsync()); foreach (var map in ReplaceStringMap) { builder.Replace(map.Key, map.Value); } using (var svgFinalStream = new MemoryStream(Encoding.UTF8.GetBytes(builder.ToString()))) { picture = svg.Load(svgFinalStream); } } } double sizeX = 0; double sizeY = 0; if (VectorWidth == 0 && VectorHeight == 0) { if (picture.CullRect.Width > 0) { sizeX = picture.CullRect.Width; } else { sizeX = 300; } if (picture.CullRect.Height > 0) { sizeY = picture.CullRect.Height; } else { sizeY = 300; } } else if (VectorWidth > 0 && VectorHeight > 0) { sizeX = VectorWidth; sizeY = VectorHeight; } else if (VectorWidth > 0) { sizeX = VectorWidth; sizeY = (VectorWidth / picture.CullRect.Width) * picture.CullRect.Height; } else { sizeX = (VectorHeight / picture.CullRect.Height) * picture.CullRect.Width; sizeY = VectorHeight; } if (UseDipUnits) { #if __ANDROID__ sizeX = sizeX.DpToPixels(); sizeY = sizeY.DpToPixels(); #else sizeX = sizeX.PointsToPixels(); sizeY = sizeY.PointsToPixels(); #endif } using (var bitmap = new SKBitmap((int)sizeX, (int)sizeY)) using (var canvas = new SKCanvas(bitmap)) using (var paint = new SKPaint()) { canvas.Clear(SKColors.Transparent); float scaleX = (float)sizeX / picture.CullRect.Width; float scaleY = (float)sizeY / picture.CullRect.Height; var matrix = SKMatrix.MakeScale(scaleX, scaleY); canvas.DrawPicture(picture, ref matrix, paint); canvas.Flush(); using (var image = SKImage.FromBitmap(bitmap)) using (var data = image.Encode(SKImageEncodeFormat.Png, 80)) { var stream = new MemoryStream(); data.SaveTo(stream); stream.Position = 0; //var stream = data?.AsStream(); return(new Tuple <Stream, LoadingResult, ImageInformation>(stream, resolvedData.Item2, resolvedData.Item3)); } } }
private byte[] CreateImage() { this.GetType().Assembly.GetManifestResourceNames(); var assembly = typeof(MainPage).GetTypeInfo().Assembly; var webClient = new WebClient(); byte[] imageData = webClient.DownloadData("https://kasikornbank.com/SiteCollectionDocuments/about/img/logo/logo.png"); var resizeFactor = 1f; SKBitmap bitmap = SKBitmap.Decode(imageData); var canvasHeight = (int)Math.Round(bitmap.Height * resizeFactor) + 100; var canvasWidth = (int)Math.Round(bitmap.Width * resizeFactor) + 20; toBitmap = new SKBitmap(canvasWidth, canvasHeight, bitmap.ColorType, bitmap.AlphaType); canvas = new SKCanvas(toBitmap); canvas.Clear(SKColors.White); canvas.SetMatrix(SKMatrix.MakeScale(resizeFactor, resizeFactor)); SKPaint grayscalePaint = new SKPaint() { ColorFilter = SKColorFilter.CreateColorMatrix(new float[] { 0.95f, 0.10f, 0.10f, 0, 0, 0.10f, 0.95f, 0.10f, 0, 0, 0.10f, 0.10f, 0.95f, 0, 0, 0, 0, 0, 1, 0 }) }; canvas.DrawBitmap(bitmap, 10, 50, grayscalePaint); canvas.ResetMatrix(); var fontStream = assembly.GetManifestResourceStream("ReceiptMaker.Media.THSarabunNew.ttf"); var font = SKTypeface.FromStream(fontStream); var boldFontStream = assembly.GetManifestResourceStream("ReceiptMaker.Media.THSarabunNewBold.ttf"); var boldFont = SKTypeface.FromStream(boldFontStream); var headerBrush = new SKPaint { Typeface = boldFont, TextSize = 50.0f, IsAntialias = true, StrokeWidth = 10.0f, Color = new SKColor(0, 0, 0, 255), TextAlign = SKTextAlign.Center, TextEncoding = SKTextEncoding.Utf32 }; var subheaderBrush = new SKPaint { Typeface = font, TextSize = 40.0f, IsAntialias = true, Color = new SKColor(115, 111, 110, 255), TextAlign = SKTextAlign.Center }; var bankNameBrush = new SKPaint { Typeface = font, TextSize = 45.0f, IsAntialias = true, Color = new SKColor(115, 111, 110, 255), TextAlign = SKTextAlign.Center }; var accountNumber = new SKPaint { Typeface = boldFont, TextSize = 45.0f, IsAntialias = true, StrokeWidth = 10.0f, Color = new SKColor(0, 0, 0, 255), TextAlign = SKTextAlign.Center }; var dateNumberDetailHeaderBrush = new SKPaint { Typeface = font, TextSize = 40.0f, IsAntialias = true, StrokeWidth = 10.0f, Color = new SKColor(115, 111, 110, 255), TextAlign = SKTextAlign.Center }; var dateNumberDetailBrush = new SKPaint { Typeface = boldFont, TextSize = 40.0f, IsAntialias = true, StrokeWidth = 10.0f, Color = new SKColor(0, 0, 0, 255), TextAlign = SKTextAlign.Center }; var costDetailBrush = new SKPaint { Typeface = boldFont, TextSize = 40.0f, IsAntialias = true, StrokeWidth = 10.0f, Color = new SKColor(0, 0, 0, 255), TextAlign = SKTextAlign.Center }; int scale = 14; canvas.DrawText("โอนเงินผ่าน K-Mobile Banking PLUS", bitmap.Width / 2, canvasHeight / scale * 1, headerBrush); canvas.DrawText("ทำรายการสำเร็จ", bitmap.Width / 2, canvasHeight / scale * 2, subheaderBrush); canvas.DrawText("จาก", bitmap.Width / 4, canvasHeight / scale * 3, bankNameBrush); canvas.DrawText("โอนเข้า", bitmap.Width / 4 * 3, canvasHeight / scale * 3, bankNameBrush); canvas.DrawText("ธ.กสิกรไทย", bitmap.Width / 4, canvasHeight / scale * 6, bankNameBrush); canvas.DrawText("ธ.กสิกรไทย", bitmap.Width / 4 * 3, canvasHeight / scale * 6, bankNameBrush); canvas.DrawText("XXX-2-XXXXX-X", bitmap.Width / 4, canvasHeight / scale * 7, accountNumber); canvas.DrawText("XXX-2-XXXXX-X", bitmap.Width / 4 * 3, canvasHeight / scale * 7, accountNumber); canvas.DrawText("นาย ชื่อ สกุล", bitmap.Width / 4 * 3, canvasHeight / scale * 8, bankNameBrush); canvas.DrawText("วันที่ทำรายการ", bitmap.Width / 4, canvasHeight / scale * 10, dateNumberDetailHeaderBrush); canvas.DrawText(DateTime.Now.ToString("dd/MM/yy hh:mm"), bitmap.Width / 4, canvasHeight / scale * 11, dateNumberDetailBrush); canvas.DrawText("เลขที่รายการ", bitmap.Width / 4 * 3, canvasHeight / scale * 10, dateNumberDetailHeaderBrush); canvas.DrawText("150805172258630", bitmap.Width / 4 * 3, canvasHeight / scale * 11, dateNumberDetailBrush); canvas.DrawText("จำนวนเงิน", bitmap.Width / 4, canvasHeight / scale * 13, dateNumberDetailHeaderBrush); canvas.DrawText("350.00 บาท", bitmap.Width / 4, canvasHeight / scale * 14, costDetailBrush); canvas.DrawText("ค่าธรรมเนียม", bitmap.Width / 4 * 3, canvasHeight / scale * 13, dateNumberDetailHeaderBrush); canvas.DrawText("0.00 บาท", bitmap.Width / 4 * 3, canvasHeight / scale * 14, costDetailBrush); canvas.Flush(); var image = SKImage.FromBitmap(toBitmap); var data = image.Encode(SKEncodedImageFormat.Png, 90); return(data.ToArray()); data.Dispose(); image.Dispose(); canvas.Dispose(); //brush.Dispose(); font.Dispose(); toBitmap.Dispose(); bitmap.Dispose(); }
void OnCanvasViewPaintSurface(object sender, SKPaintSurfaceEventArgs args) { SKImageInfo info = args.Info; SKSurface surface = args.Surface; SKCanvas canvas = surface.Canvas; canvas.Clear(); App.Current.Resources.TryGetValue("BackgroundColor", out var background); SKPaint stateStrokePaint = new SKPaint { Style = SKPaintStyle.Stroke, Color = ((Color)background).ToSKColor(), StrokeWidth = 1, }; SKPaint countyStrokePaint = new SKPaint { Style = SKPaintStyle.Stroke, Color = ((Color)background).ToSKColor(), StrokeWidth = 0.25f, }; _canvasTranslateMatrix = canvas.TotalMatrix; canvas.Scale(_scale); SKRect localBounds; canvas.GetLocalClipBounds(out localBounds); float transformedX = _x / canvas.TotalMatrix.ScaleX + localBounds.MidX; float transformedY = _y / canvas.TotalMatrix.ScaleY + localBounds.MidY; canvas.Translate(transformedX, transformedY); SKPaint fillPaint; SKPaint selectedPaint = new SKPaint { Style = SKPaintStyle.Stroke, Color = SKColors.Black, StrokeWidth = 1, StrokeCap = SKStrokeCap.Round }; // Paint the counties if zoomed, else states if (_isZoomed) { foreach (CountyObject county in _selectedState.Counties.Values) { fillPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = GetColorFromValue(county.CasesItem?.Cases ?? 0, _selectedState.MaxCountyCases), }; canvas.DrawPath(county.Path, fillPaint); canvas.DrawPath(county.Path, countyStrokePaint); } if (_selectedCounty != null) { canvas.DrawPath(_selectedCounty.Path, selectedPaint); } } else { foreach (StateObject state in MapService.Service.States.Values) { fillPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = GetColorFromValue(state.CasesItem?.Cases ?? 0), }; canvas.DrawPath(state.Path, fillPaint); canvas.DrawPath(state.Path, stateStrokePaint); } if (_highlightedState != null) { canvas.DrawPath(_highlightedState.Path, selectedPaint); } } // Undo transformations to paint absolute items canvas.Translate(-transformedX, -transformedY); canvas.Scale(1 / _scale * _uiScale); // Code to draw the cases legend int maxCases = _isZoomed ? _selectedState.MaxCountyCases : _maxStateCases; int height = 400; int width = 10; float x = (info.Width / (_uiScale) - 30); float y = (info.Height / (2 * _uiScale) - height / 2); short segments = 10; short gap = 2; int segmentHeight = (height - gap * (segments - 1)) / segments; for (short i = 0; i < segments; i++) { SKPaint segPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = GetColorFromValue((int)(maxCases * (1 - (float)i / (segments - 1))), maxCases) }; SKRect seg = new SKRect(x, y + i * (segmentHeight + gap), x + width, y + i * (segmentHeight + gap) + segmentHeight); canvas.DrawRect(seg, segPaint); } SKPaint casesAmountPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = SKColors.Black, TextSize = 16, TextAlign = SKTextAlign.Right, IsAntialias = true }; canvas.DrawText(maxCases.ToString(), new SKPoint(x + width, y - casesAmountPaint.TextSize / 2), casesAmountPaint); canvas.DrawText(0.ToString(), new SKPoint(x + width, y + height + casesAmountPaint.TextSize), casesAmountPaint); #if DEBUG // Draws all of the variables on the canvas SKPaint debugPaint = new SKPaint { Style = SKPaintStyle.Fill, Color = SKColors.Black, }; SKFont debugFont = new SKFont { Size = 14, }; string[] lines = { $"{nameof(_x)}: {_x}", $"{nameof(_y)}: {_y}", $"{nameof(_scale)}: {_scale}", $"{nameof(_debugTouchX)}: {_debugTouchX}", $"{nameof(_debugTouchY)}: {_debugTouchY}", $"{nameof(_selectedState)}: {_selectedState?.State ?? "null"}", $"{nameof(_selectedCounty)}: {_selectedCounty?.County ?? "null"}", }; for (int i = 1; i <= lines.Length; i++) { canvas.DrawText(lines[i - 1], 10, (debugFont.Size + 2) * i, debugFont, debugPaint); } #endif }
public string EncodeImage(string inputPath, DateTime dateModified, string outputPath, bool autoOrient, ImageOrientation?orientation, int quality, ImageProcessingOptions options, ImageFormat selectedOutputFormat) { if (string.IsNullOrWhiteSpace(inputPath)) { throw new ArgumentNullException("inputPath"); } if (string.IsNullOrWhiteSpace(inputPath)) { throw new ArgumentNullException("outputPath"); } var skiaOutputFormat = GetImageFormat(selectedOutputFormat); var hasBackgroundColor = !string.IsNullOrWhiteSpace(options.BackgroundColor); var hasForegroundColor = !string.IsNullOrWhiteSpace(options.ForegroundLayer); var blur = options.Blur ?? 0; var hasIndicator = options.AddPlayedIndicator || options.UnplayedCount.HasValue || !options.PercentPlayed.Equals(0); using (var bitmap = GetBitmap(inputPath, options.CropWhiteSpace, autoOrient, orientation)) { if (bitmap == null) { throw new ArgumentOutOfRangeException(string.Format("Skia unable to read image {0}", inputPath)); } //_logger.Info("Color type {0}", bitmap.Info.ColorType); var originalImageSize = new ImageSize(bitmap.Width, bitmap.Height); if (!options.CropWhiteSpace && options.HasDefaultOptions(inputPath, originalImageSize) && !autoOrient) { // Just spit out the original file if all the options are default return(inputPath); } var newImageSize = ImageHelper.GetNewImageSize(options, originalImageSize); var width = Convert.ToInt32(Math.Round(newImageSize.Width)); var height = Convert.ToInt32(Math.Round(newImageSize.Height)); using (var resizedBitmap = new SKBitmap(width, height))//, bitmap.ColorType, bitmap.AlphaType)) { // scale image var resizeMethod = SKBitmapResizeMethod.Lanczos3; bitmap.Resize(resizedBitmap, resizeMethod); // If all we're doing is resizing then we can stop now if (!hasBackgroundColor && !hasForegroundColor && blur == 0 && !hasIndicator) { _fileSystem.CreateDirectory(_fileSystem.GetDirectoryName(outputPath)); using (var outputStream = new SKFileWStream(outputPath)) { resizedBitmap.Encode(outputStream, skiaOutputFormat, quality); return(outputPath); } } // create bitmap to use for canvas drawing used to draw into bitmap using (var saveBitmap = new SKBitmap(width, height)) //, bitmap.ColorType, bitmap.AlphaType)) using (var canvas = new SKCanvas(saveBitmap)) { // set background color if present if (hasBackgroundColor) { canvas.Clear(SKColor.Parse(options.BackgroundColor)); } // Add blur if option is present if (blur > 0) { // create image from resized bitmap to apply blur using (var paint = new SKPaint()) using (var filter = SKImageFilter.CreateBlur(blur, blur)) { paint.ImageFilter = filter; canvas.DrawBitmap(resizedBitmap, SKRect.Create(width, height), paint); } } else { // draw resized bitmap onto canvas canvas.DrawBitmap(resizedBitmap, SKRect.Create(width, height)); } // If foreground layer present then draw if (hasForegroundColor) { Double opacity; if (!Double.TryParse(options.ForegroundLayer, out opacity)) { opacity = .4; } canvas.DrawColor(new SKColor(0, 0, 0, (Byte)((1 - opacity) * 0xFF)), SKBlendMode.SrcOver); } if (hasIndicator) { DrawIndicator(canvas, width, height, options); } _fileSystem.CreateDirectory(_fileSystem.GetDirectoryName(outputPath)); using (var outputStream = new SKFileWStream(outputPath)) { saveBitmap.Encode(outputStream, skiaOutputFormat, quality); } } } } return(outputPath); }
internal static SKBitmap FromText(string text, SKColor color, bool isDrawRect) { try { if (!string.IsNullOrWhiteSpace(text)) { using (SKPaint paint = new SKPaint()) { paint.Color = color; paint.SubpixelText = true; paint.IsEmbeddedBitmapText = true; paint.IsAntialias = true; paint.TextEncoding = SKTextEncoding.Utf32; paint.TextSize = 255; float height; string[] lines = text.Split(splitters, StringSplitOptions.RemoveEmptyEntries); string[][] chars = new string[lines.Length][]; float[][] charsWidth = new float[chars.Length][]; SKTypeface[][] charsTypeface = new SKTypeface[chars.Length][]; float[] linesWidth = new float[chars.Length]; float maxLineHeight = 0; float maxLineWidth = 0; List <string> currentLineChars = new List <string>(); for (int i = 0; i < chars.Length; i++) { TextElementEnumerator strEnumerator = StringInfo.GetTextElementEnumerator(lines[i]); while (strEnumerator.MoveNext()) { currentLineChars.Add(strEnumerator.GetTextElement()); } chars[i] = currentLineChars.ToArray(); currentLineChars.Clear(); charsTypeface[i] = new SKTypeface[chars[i].Length]; charsWidth[i] = new float[chars[i].Length]; linesWidth[i] = 0; for (int j = 0; j < chars[i].Length; j++) { using (SKPaint charPaint = paint.Clone()) { int numberChar = 120; char[] currentChar = chars[i][j].ToCharArray(); if (currentChar?.Length > 1 && !(currentChar[1] >= 55296 && currentChar[1] <= 57000)) //checking highSurrogate { currentChar = new char[] { currentChar[0] } } ; switch (currentChar?.Length) { case 1: numberChar = Char.ConvertToUtf32(chars[i][j], 0); break; case 2: numberChar = Char.ConvertToUtf32(currentChar[0], currentChar[1]); break; case 0: chars[i][j] = $""; break; default: numberChar = Char.ConvertToUtf32(currentChar[0], currentChar[1]); chars[i][j] = $"{currentChar[0]}{currentChar[1]}"; break; } charPaint.Typeface = charsTypeface[i][j] = SKFontManager.Default.MatchCharacter(numberChar); SKRect currenttextBounds = new SKRect(); charsWidth[i][j] = charPaint.MeasureText(chars[i][j], ref currenttextBounds); linesWidth[i] += charsWidth[i][j]; if (maxLineHeight < currenttextBounds.Height) { maxLineHeight = currenttextBounds.Height; } } if (maxLineWidth < linesWidth[i]) { maxLineWidth = linesWidth[i]; } } } currentLineChars = null; maxLineHeight = (float)Math.Ceiling(maxLineHeight * 1.15); maxLineWidth = (float)Math.Ceiling(maxLineWidth * 1.05); height = (float)Math.Ceiling((chars.Length + 0.32f) * maxLineHeight); SKBitmap textBitmap = new SKBitmap((int)maxLineWidth, (int)height); SKRect textDest = new SKRect(0, 0, maxLineWidth, height); using (SKCanvas canvasText = new SKCanvas(textBitmap)) { canvasText?.Clear(); canvasText.DrawBitmap(textBitmap, textDest); if (isDrawRect) { using (var paintRect = paint.Clone()) using (var roundRect = new SKRoundRect(new SKRect(0, 0, maxLineWidth, height), 50, 50)) { paintRect.Style = SKPaintStyle.Fill; paintRect.Color = color; canvasText.DrawRoundRect(roundRect, paintRect); } } float yText = maxLineHeight; for (int i = 0; i < chars.Length; i++) { float xText = maxLineWidth / 2 - (linesWidth[i] / 2); for (int j = 0; j < chars[i].Length; j++) { using (SKPaint charPaint = paint.Clone()) { if (isDrawRect) { charPaint.Color = color == SKColors.White ? SKColors.Black : SKColors.White; } charPaint.Typeface = charsTypeface[i][j]; canvasText.DrawText(chars[i][j], xText, yText, charPaint); xText += charsWidth[i][j]; } } yText += maxLineHeight; } } foreach (var a in charsTypeface) { foreach (var b in a) { b.Dispose(); } } GC.Collect(0); return(textBitmap); } } else { return(null); } } catch (Exception) { return(null); } }
public ResizedImageInfo Resize(DpiPath dpi, string destination) { var sw = new Stopwatch(); sw.Start(); var(bgScaledSize, bgScale) = backgroundTools.GetScaledSize(backgroundOriginalSize, dpi); // Allocate using (var tempBitmap = new SKBitmap(bgScaledSize.Width, bgScaledSize.Height)) { // Draw (copy) using (var canvas = new SKCanvas(tempBitmap)) { canvas.Clear(SKColors.Transparent); canvas.Save(); canvas.Scale(bgScale, bgScale); backgroundTools.DrawUnscaled(canvas); canvas.Restore(); if (hasForeground) { var userFgScale = (float)Info.ForegroundScale; // get the ratio to make the foreground fill the background var fitRatio = bgScaledSize.Width / foregroundOriginalSize.Width; // calculate the scale for the foreground to fit the background exactly var(fgScaledSize, fgScale) = foregroundTools.GetScaledSize(foregroundOriginalSize, (decimal)fitRatio); Logger.Log("dpi.Size: " + dpi.Size); Logger.Log("dpi.Scale: " + dpi.Scale); Logger.Log("bgScaledSize: " + bgScaledSize); Logger.Log("bgScale: " + bgScale); Logger.Log("foregroundOriginalSize: " + foregroundOriginalSize); Logger.Log("fgScaledSize: " + fgScaledSize); Logger.Log("fgScale: " + fgScale); Logger.Log("userFgScale: " + userFgScale); // now work out the center as if the canvas was exactly the same size as the foreground var fgScaledSizeCenterX = foregroundOriginalSize.Width / 2; var fgScaledSizeCenterY = foregroundOriginalSize.Height / 2; Logger.Log("fgScaledSizeCenterX: " + fgScaledSizeCenterX); Logger.Log("fgScaledSizeCenterY: " + fgScaledSizeCenterY); // scale so the forground is the same size as the background canvas.Scale(fgScale, fgScale); // scale to the user scale, centering canvas.Scale(userFgScale, userFgScale, fgScaledSizeCenterX, fgScaledSizeCenterY); foregroundTools.DrawUnscaled(canvas); } } // Save (encode) using (var pixmap = tempBitmap.PeekPixels()) using (var wrapper = new SKFileWStream(destination)) { pixmap.Encode(wrapper, SKPngEncoderOptions.Default); } } sw.Stop(); Logger?.Log($"Save Image took {sw.ElapsedMilliseconds}ms"); return(new ResizedImageInfo { Dpi = dpi, Filename = destination }); }