Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
134 changes: 134 additions & 0 deletions Uno.Gallery/Helpers/Canvas/SampleSKCanvasElement.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
#if HAS_UNO_SKIA
using SkiaSharp;
using Uno.WinUI.Graphics2DSK;
using Windows.Foundation;

namespace Uno.Gallery.Helpers.Canvas;

public class SampleSKCanvasElement : SKCanvasElement
{
public static int SampleCount => 3;

public static DependencyProperty SampleProperty { get; } = DependencyProperty.Register(
nameof(Sample),
typeof(int),
typeof(SampleSKCanvasElement),
new PropertyMetadata(0, (o, args) => ((SampleSKCanvasElement)o).SampleChanged((int)args.NewValue)));

public int Sample
{
get => (int)GetValue(SampleProperty);
set => SetValue(SampleProperty, value);
}

private void SampleChanged(int newIndex)
{
Sample = Math.Min(Math.Max(0, newIndex), SampleCount - 1);
Invalidate();
}

protected override void RenderOverride(SKCanvas canvas, Size area)
{
var minDim = Math.Min(area.Width, area.Height);
// draw horizontally centered
var x = (area.Width - minDim) / 2;
var y = (area.Height - minDim) / 2;
canvas.Translate((float)x, (float)y);
// rescale to fit the given area, assuming each drawing is 260x260
canvas.Scale((float)(minDim / 260), (float)(minDim / 260));

switch (Sample)
{
case 0:
SkiaDrawing0(canvas);
break;
case 1:
SkiaDrawing1(canvas);
break;
case 2:
SkiaDrawing2(canvas);
break;
}
}

// https://fiddle.skia.org/c/@shapes
private void SkiaDrawing0(SKCanvas canvas)
{
var paint = new SKPaint();
paint.Style = SKPaintStyle.Fill;
paint.IsAntialias = true;
paint.StrokeWidth = 4;
paint.Color = new SKColor(0xff4285F4);

var rect = SKRect.Create(10, 10, 100, 160);
canvas.DrawRect(rect, paint);

var oval = new SKPath();
oval.AddRoundRect(rect, 20, 20);
oval.Offset(new SKPoint(40, 80));
paint.Color = new SKColor(0xffDB4437);
canvas.DrawPath(oval, paint);

paint.Color = new SKColor(0xff0F9D58);
canvas.DrawCircle(180, 50, 25, paint);

rect.Offset(80, 50);
paint.Color = new SKColor(0xffF4B400);
paint.Style = SKPaintStyle.Stroke;
canvas.DrawRoundRect(rect, 10, 10, paint);
}

// https://fiddle.skia.org/c/@bezier_curves
private void SkiaDrawing1(SKCanvas canvas)
{
var paint = new SKPaint();
paint.Style = SKPaintStyle.Stroke;
paint.StrokeWidth = 8;
paint.Color = new SKColor(0xff4285F4);
paint.IsAntialias = true;
paint.StrokeCap = SKStrokeCap.Round;

var path = new SKPath();
path.MoveTo(10, 10);
path.QuadTo(256, 64, 128, 128);
path.QuadTo(10, 192, 250, 250);
canvas.DrawPath(path, paint);
}

// https://fiddle.skia.org/c/@shader
private void SkiaDrawing2(SKCanvas canvas)
{
var paint = new SKPaint();
using var pathEffect = SKPathEffect.CreateDiscrete(10.0f, 4.0f);
paint.PathEffect = pathEffect;
SKPoint[] points =
{
new SKPoint(0.0f, 0.0f),
new SKPoint(256.0f, 256.0f)
};
SKColor[] colors =
{
new SKColor(66, 133, 244),
new SKColor(15, 157, 88)
};
paint.Shader = SKShader.CreateLinearGradient(points[0], points[1], colors, SKShaderTileMode.Clamp);
paint.IsAntialias = true;
var path = Star();
canvas.DrawPath(path, paint);

SKPath Star()
{
const float R = 60.0f, C = 128.0f;
var path = new SKPath();
path.MoveTo(C + R, C);
for (var i = 1; i < 15; ++i)
{
var a = 0.44879895f * i;
var r = R + R * (i % 2);
path.LineTo((float)(C + r * Math.Cos(a)), (float)(C + r * Math.Sin(a)));
}
return path;
}
}
}
#endif
49 changes: 49 additions & 0 deletions Uno.Gallery/Views/SamplePages/SKCanvasElementPage.xaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
<Page x:Class="Uno.Gallery.Views.SamplePages.SKCanvasElementPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:Uno.Gallery"
xmlns:samples="using:Uno.Gallery.Views.Samples"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:smtx="using:ShowMeTheXAML"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">

<Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<local:SamplePageLayout IsDesignAgnostic="True">
<local:SamplePageLayout.DesignAgnosticTemplate>
<DataTemplate>
<smtx:XamlDisplay UniqueKey="SKCanvasElementPage_Basic"
smtx:XamlDisplayExtensions.Header="Basic SKCanvasElement">
<Grid>
<Grid RowSpacing="20">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Button HorizontalAlignment="Center"
Click="NextSample_Click">
Next sample
</Button>
<Grid Height="140"
Grid.Row="1"
x:Name="SKContainer" />
</Grid>
</Grid>

<!--
C# code
public class SampleSKCanvasElement : SKCanvasElement
{
protected override void RenderOverride(SKCanvas canvas, Size area)
{
// Custom rendering logic goes here
}
}
-->
</smtx:XamlDisplay>
</DataTemplate>
</local:SamplePageLayout.DesignAgnosticTemplate>
</local:SamplePageLayout>
</Grid>
</Page>
53 changes: 53 additions & 0 deletions Uno.Gallery/Views/SamplePages/SKCanvasElementPage.xaml.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
using Microsoft.UI.Xaml;
using Microsoft.UI.Xaml.Controls;
using Microsoft.UI.Xaml.Controls.Primitives;
using Microsoft.UI.Xaml.Data;
using Microsoft.UI.Xaml.Input;
using Microsoft.UI.Xaml.Media;
using Microsoft.UI.Xaml.Navigation;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices.WindowsRuntime;
using Windows.Foundation;
using Windows.Foundation.Collections;
#if HAS_UNO_SKIA
using Uno.Gallery.Helpers.Canvas;
#endif

namespace Uno.Gallery.Views.SamplePages;

#if HAS_UNO_SKIA
[SamplePage(SampleCategory.UIComponents, "SKCanvasElement", Description = "Represents a 2D graphics canvas.", DocumentationLink = "https://platform.uno/docs/articles/controls/SKCanvasElement.html")]
#endif
public sealed partial class SKCanvasElementPage : Page
{
#if HAS_UNO_SKIA
public int MaxSampleIndex => SampleSKCanvasElement.SampleCount - 1;

private SampleSKCanvasElement _canvasElement;
#endif

public SKCanvasElementPage()
{
this.InitializeComponent();

this.Loaded += SKCanvasElementPage_Loaded;
}

private void SKCanvasElementPage_Loaded(object sender, RoutedEventArgs e)
{
#if HAS_UNO_SKIA
var container = (Grid)FindName("SKContainer");
container.Children.Add(_canvasElement = new SampleSKCanvasElement());
#endif
}

private void NextSample_Click(object sender, RoutedEventArgs e)
{
#if HAS_UNO_SKIA
_canvasElement.Sample = (_canvasElement.Sample + 1) % SampleSKCanvasElement.SampleCount;
#endif
}
}
Loading