Results 1 to 6 of 6

Thread: The Cost of a Brush

  1. #1

    Thread Starter
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    39,387

    The Cost of a Brush

    Painting in WPF is done with brushes. There appears to be two ways to do this, and I'm wondering what the cost is.

    The way that is generally described is the naïve approach:
    Code:
    SomeControl.Background = New SolidColorBrush(Colors.Green)
    This certainly looks like it is creating a new instance of a class. How long does that class live? What is the impact on memory?

    Alternatively, since I might well be using a brush with a color of green in many different places if I am using it at all, then I could create one brush at form scope and use it in various places.

    For the most part, this will be no big deal. The benefit of creating it in one place is pretty minimal if I will only be using that green brush in a few places. However, there is a time when I am creating a new brush every 100 ms, and the brushes might not be repeated...well, maybe not EVER, as it might cycle through every possible color at a rate of 10 colors per second.

    In Windows.Forms, this wasn't a big deal, because all I was creating was a color structure, which had no memory implications. Creating a class just might.

    So, the naïve approach for this would be to create a new brush for each new color. The better approach would be to use one brush at form scope and change the color property. This is the approach I took, I just don't know whether I was being reasonably cautious, or overly cautious.

    Also, it seems like I could use one brush for all painting and change the color as needed. Is there a best practice here?
    My usual boring signature: Nothing

  2. #2
    PowerPoster PlausiblyDamp's Avatar
    Join Date
    Dec 2016
    Location
    Pontypool, Wales
    Posts
    2,710

    Re: The Cost of a Brush

    On my phone at the moment and can't look this up but I seem to remember reading somewhere that SolidColorBrush has an optimised implementation for known colours. So I suspect something like your code wouldn't create a new brush each time, but using a custom RGB colour probably would.

  3. #3

    Thread Starter
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    39,387

    Re: The Cost of a Brush

    I forgot that I started this thread. Still not certain, I suppose. The approach I took was perhaps overly cautious, but I might revisit this later on.
    My usual boring signature: Nothing

  4. #4
    PowerPoster PlausiblyDamp's Avatar
    Join Date
    Dec 2016
    Location
    Pontypool, Wales
    Posts
    2,710

    Re: The Cost of a Brush

    Quote Originally Posted by Shaggy Hiker View Post
    I forgot that I started this thread. Still not certain, I suppose. The approach I took was perhaps overly cautious, but I might revisit this later on.
    Completely forgot about this thread as well...

    https://source.dot.net/#Presentation...db4a721050df52 is the source, around line 264 you can see the cache used for known colours.

  5. #5
    MS SQL Powerposter szlamany's Avatar
    Join Date
    Mar 2004
    Location
    Connecticut
    Posts
    18,263

    Re: The Cost of a Brush

    It has been so long since I've been in WPF - but is this not the whole reason for XAML files? So these resources get pre-built?

    Code:
    <Window x:Class="xxx.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:lvsort="clr-namespace:WpfListViewSorting"
        Title="xxxxxxxxx Management Software v1.113                    ** CONFIDENTIAL: NOT FOR DISTRIBUTION **" Height="575" Width="875" Icon="xxxxxx.ico" Loaded="Window_Loaded">
        <Window.Resources>
            <LinearGradientBrush x:Key="ButtonBrush" EndPoint="0,1" StartPoint="0,0">
                <GradientStop Color="#FFFFFF" Offset="0"/>
                <GradientStop Color="#FFFFFF" Offset="0.5"/>
                <GradientStop Color="#FFFFFF" Offset="0.5"/>
                <GradientStop Color="#FFFFFF" Offset="1"/>
            </LinearGradientBrush>
    
            <LinearGradientBrush x:Key="ButtonBrushx" EndPoint="0,1" StartPoint="0,0">
                <GradientStop Color="#FFF3F3F3" Offset="0"/>
                <GradientStop Color="#FFEBEBEB" Offset="0.5"/>
                <GradientStop Color="#FFDDDDDD" Offset="0.5"/>
                <GradientStop Color="#FFFCF9FC" Offset="1"/>
            </LinearGradientBrush>
            <Style x:Key="ButtonStylex">
                <Setter Property="Control.Margin" Value="2"></Setter>
                <Setter Property="Control.BorderBrush" Value="{x:Null}"></Setter>
                <EventSetter Event="Button.Click" Handler="Button_Click" />
            </Style>
            <Style x:Key="ButtonStyle">
                <Setter Property="Control.Template">
                    <Setter.Value>
                        <ControlTemplate TargetType="Button">
                            <Border Name="shortcutbutton"  
                        BorderThickness="0 0 0 0"
                        BorderBrush="#D0D1D7"
                        Background="#FFFFFF">
                                <ContentPresenter Margin="2" 
                                      HorizontalAlignment="Center"
                                      VerticalAlignment="Center" 
                                      RecognizesAccessKey="True"/>
                            </Border>
                            <ControlTemplate.Triggers>
                                <Trigger Property="IsMouseOver" Value="true">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#FFFFFF" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="Opacity" Value="1" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="1 1 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Hand" />
                                    <!--<Setter TargetName="Border" Property="Foreground" Value="#45619D\#2F477A" />-->
                                </Trigger>
                                <Trigger Property="IsPressed" Value="true">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#FFFFFF" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="1 1 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Hand" />
                                    <!--<Setter TargetName="Border" Property="Foreground" Value="Red" />-->
                                </Trigger>
                                <Trigger Property="IsEnabled" Value="false">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#F4F4F4" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="0 0 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Wait" />
                                </Trigger>
                            </ControlTemplate.Triggers>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
                <Setter Property="Control.Margin" Value="2"></Setter>
                <Setter Property="Control.Foreground" Value="#2F477A"></Setter>
                <Setter Property="Control.BorderBrush" Value="{x:Null}"></Setter>
                <EventSetter Event="Button.Click" Handler="Button_Click" />
            </Style>
            <Style x:Key="ButtonStyleOn">
                <Setter Property="Control.Template">
                    <Setter.Value>
                        <ControlTemplate TargetType="Button">
                            <Border Name="shortcutbutton"  
                        BorderThickness="0 0 0 0"
                        BorderBrush="#D0D1D7"
                        Background="#DCEAF9">
                                <ContentPresenter Margin="2" 
                                      HorizontalAlignment="Center"
                                      VerticalAlignment="Center" 
                                      RecognizesAccessKey="True"/>
                            </Border>
                            <ControlTemplate.Triggers>
                                <Trigger Property="IsMouseOver" Value="true">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#DCEAF9" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="Opacity" Value="1" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="1 1 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Hand" />
                                    <!--<Setter TargetName="Border" Property="Foreground" Value="#45619D\#2F477A" />-->
                                </Trigger>
                                <Trigger Property="IsPressed" Value="true">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#DCEAF9" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="1 1 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Hand" />
                                    <!--<Setter TargetName="Border" Property="Foreground" Value="Red" />-->
                                </Trigger>
                                <Trigger Property="IsEnabled" Value="false">
                                    <Setter TargetName="shortcutbutton" Property="Background" Value="#F4F4F4" />
                                    <Setter TargetName="shortcutbutton" Property="BorderBrush" Value="#D0D1D7" />
                                    <Setter TargetName="shortcutbutton" Property="BorderThickness" Value="1 1 0 0" />
                                    <Setter TargetName="shortcutbutton" Property="Cursor" Value="Wait" />
                                </Trigger>
                            </ControlTemplate.Triggers>
                        </ControlTemplate>
                    </Setter.Value>
                </Setter>
    then later in the code...

    Code:
                buttonOff = (System.Windows.Media.Brush)FindResource("ButtonBrush");
    
                OptionList.Visibility = System.Windows.Visibility.Collapsed;
                
                List<Button> list = new List<Button>();
                list.Clear();
                Button ib = new Button();
                ib.Style = (Style)FindResource("OptionButtonStyle");
                ib.Tag = "1";
                ib.Background = buttonOff;

    *** Read the sticky in the DB forum about how to get your question answered quickly!! ***

    Please remember to rate posts! Rate any post you find helpful - even in old threads! Use the link to the left - "Rate this Post".

    Some Informative Links:
    [ SQL Rules to Live By ] [ Reserved SQL keywords ] [ When to use INDEX HINTS! ] [ Passing Multi-item Parameters to STORED PROCEDURES ]
    [ Solution to non-domain Windows Authentication ] [ Crazy things we do to shrink log files ] [ SQL 2005 Features ] [ Loading Pictures from DB ]

    MS MVP 2006, 2007, 2008

  6. #6

    Thread Starter
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    39,387

    Re: The Cost of a Brush

    I've been getting into WPF more and more with this project. Putting things in XAML is a different way of thinking about things. When I asked the question, I didn't even know about Windows.Resources in XAML. I've done more with that, by now, but I hadn't yet encountered the idea of putting brushes in there.
    My usual boring signature: Nothing

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width