Click here to Skip to main content
15,888,610 members
Please Sign up or sign in to vote.
3.00/5 (1 vote)
Goal: To draw shapes by VisualCollection.
Problem: It draws nothing.
Question: How to solve?
Code:
C#
public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();

        this.Loaded += MainWindow_Loaded;
    }

    void MainWindow_Loaded(object sender, RoutedEventArgs e)
    {
        VisualCollection vc = new VisualCollection(this);
        DrawingVisual dv = new DrawingVisual();
        DrawingContext dc = dv.RenderOpen();

        dc.DrawRectangle(Brushes.Red, new Pen(Brushes.Red, 5), new Rect(10, 10, 100, 100));
        dc.Close();

        vc.Add(dv);
    }
}
Posted
Updated 2-Jun-15 10:12am
v2
Comments
Sergey Alexandrovich Kryukov 2-Jun-15 16:39pm    
I'm glad to see serious improvements in how you ask questions, congratulations!
—SA

1 solution

The problem is that you never use your VisualCollection, only create it. How do you think the rest of your application can "know" that this collection even exist?

You don't even need this fictional "Loaded" event; you can call the code adding visuals from the constructor directly. For example, the rendering you tried to create in your code sample can be done this way:
C#
public partial class MainWindow : Window {

    public MainWindow() {
        InitializeComponent();
        visuals = new VisualCollection(this);
        DrawIt();
    } // MainWindow constructor

    VisualCollection visuals;

    void DrawIt() {
            DrawingVisual visual = new DrawingVisual();
            using (DrawingContext dc = visual.RenderOpen()) {
                dc.DrawRectangle(
                    Brushes.Red, new Pen(Brushes.Red, 5),
                    new Rect(10, 10, 100, 100));
            }
            visuals.Add(visual);
    } //DrawIt

    protected override Visual GetVisualChild(int index) {
        return visuals[index];
    } //GetVisualChild
    protected override int VisualChildrenCount {
        get { return visuals.Count; }
    } //VisualChildrenCount

} // MainWindow class

Can you spot the difference? :-)

But I would not advise drawing on the Window directly. Instead, create some custom UIElement (derived class) using the visuals in exact same way, and add it the the window's logical tree, as any other UIElement (to a grid or other container, or a window itself), directly or using XAML. Please see the complete sample in this tutorial:
https://tarundotnet.wordpress.com/2011/05/19/wpf-tutorial-drawing-visual[^].

I tried it out, it works.

—SA
 
Share this answer
 
v7
Comments
Sascha Lefèvre 2-Jun-15 17:08pm    
5ed
Sergey Alexandrovich Kryukov 2-Jun-15 17:13pm    
Thank you, Sascha.
—SA
Ziya1995 3-Jun-15 3:52am    
> Can you spot the difference?
The only difference i spot is 2 protected override voids.

I checked the code via the link before i came here and it didn't work like yours until i tweaked it:
WPF app has Grid on Window by default and that is why i didn't see the drawing, i removed it and it worked.
Solved!
Sergey Alexandrovich Kryukov 3-Jun-15 10:54am    
Very good. Don't you see that these 2 overrides is exactly what expose the visual of the declaring class?
And yes, it does work, I tested it. It would work on an empty logical tree of the window. That's why I advised to implement the visual in the separate UI element, which you really want to do in practical cases.
Good luck, call again.
—SA
Ziya1995 7-Jun-15 12:03pm    
> Don't you see that these 2 overrides is exactly what expose the visual of the declaring class?

I sent "this" as "Visual Parent" in constructor of "VisualCollection" and thought it is enough, but it was not, because it is done by 2 override voids.
I change it to another UI element and it still draws on Window.

What does "Visual Parent" mean?

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900