fishycrakers
fishycrakers

Reputation: 71

WPF - canvas declaration xaml

Is it possible to declare a canvas in xaml without it being local to the MainWindow.xaml.cs page?

I have created a class called ImageBoard, but I need this class to have the xaml canvas held locally within it - and not within Mainwindow.xaml.cs. What I want is the ImageBoard to act as the manager of this canvas.

The only other way I can imagine doing this is to have the ImageBoard derive from Canvas itself, so that it is the canvas. Then I could place this into the MainWindow.

At the moment I have this.

Xaml:

<Canvas HorizontalAlignment="Center" Height="370" VerticalAlignment="Center" Width="688"
  x:Name="canvas1" Background="#f6f6f6"/>

But it can only be called from the MainWindow, as it is part of the MainWindow. Because of this I have to pass it to the ImageBoard to perform various Methods.

What I think would be best is this

Public class ImageBoard : Canvas

which would eliminate the need for passing the canvas.

I did try to declare a reference to the canvas, via the ImageBoard's constructor, but I think this would be bad practice; as I am, essentially, using the ImageBoard for all drawing purposes anyway. Why keep a canvas when I can turn the ImageBoard into a canvas, right?

Upvotes: 1

Views: 961

Answers (1)

Pragmateek
Pragmateek

Reputation: 13406

You could build a ImageBoard UserControl:

XAML:

<UserControl x:Class="WpfMagic.ImageBoard"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             d:DesignHeight="300" d:DesignWidth="300">
    <Grid>
        <Canvas x:Name="canvas" Background="Transparent" MouseLeftButtonUp="Canvas_MouseLeftButtonUp"></Canvas>    
    </Grid>
</UserControl>

Code behind:

using System.Windows.Controls;
using System.Windows.Input;

namespace WpfMagic
{
    public partial class ImageBoard : UserControl
    {
        public ImageBoard()
        {
            InitializeComponent();
        }

        private void Canvas_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
        {
            TextBlock tb = new TextBlock { Text = "*", FontSize = 20 };

            tb.SetValue(Canvas.TopProperty, e.GetPosition(canvas).Y);
            tb.SetValue(Canvas.LeftProperty, e.GetPosition(canvas).X);

            canvas.Children.Add(tb);
        }
    }
}

And from you main page you can do:

<Window x:Class="WpfMagic.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:WpfMagic"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <local:ImageBoard></local:ImageBoard>
    </Grid>
</Window>

This way you never directly manipulate the Canvas, it is abstracted away from the code using the ImageBoard, this is encapsulation.

Upvotes: 1

Related Questions