JokerMartini
JokerMartini

Reputation: 6147

wpf innershadow of path

So how can i go about generating an inner shadow on my path. You can see in the example below i was able to create it on the border but im not sure how to get it onto my path. The goal is for the shadow to appear on the inner area of the heart.

enter image description here

<Border Background="LightGray" BorderBrush="DarkGray" Width="40" Height="20"
           BorderThickness="0" ClipToBounds="True">
            <Border Background="Transparent" BorderBrush="Black" BorderThickness="1" Margin="-2">
                <Border.Effect>
                    <DropShadowEffect ShadowDepth="0" BlurRadius="5"/>
                </Border.Effect>
            </Border>
        </Border>

        <Path Stretch="Uniform" Width="50" Fill="Red" StrokeThickness="5" Data="M74,130C40,102.4,0,69.4,0,40.3C0,17.1,15.3,0,40,0 c21.3,0,32.4,14,34,18.1C75.6,14,86.7,0,108,0c24.7,0,40,17.1,40,40.3C148,69.4,108,102.4,74,130z">
        </Path>

Upvotes: 1

Views: 547

Answers (1)

King King
King King

Reputation: 63377

Your best way is try understanding about ShaderEffect - a kind of custom Effect which you can implement based on HLSL (High Level Shader Language). However doing so is not easy. Some simple effects can be done easily but to me this effect is not so easy. You can try searching round such as for glow effect in HLSL - and try modifying it to make an inner shadow effect.

I would like to introduce a work-around here in which you use pure XAML. However we use the deprecated effect OuterGlowBitmapEffect, you can easily find a free library of Effect (which has the corresponding OuterGlowEffect) and use that instead of the OuterGlowBitmapEffect in the following code. The new Effect should be set for Effect property instead of BitmapEffect property.

Here is the code:

<Grid>
    <Grid.Resources>
        <PathGeometry x:Key="data" Figures="M74,130C40,102.4,0,69.4,0,40.3C0,17.1,15.3,0,40,0 c21.3,0,32.4,14,34,18.1C75.6,14,86.7,0,108,0c24.7,0,40,17.1,40,40.3C148,69.4,108,102.4,74,130z"/>
        <VisualBrush x:Key="heartGlow" Stretch="Uniform" ViewportUnits="RelativeToBoundingBox" Viewport="-0.25,-0.25,1.5,1.5">
            <VisualBrush.Visual>
                <Path Data="{StaticResource data}" Stroke="Gray" StrokeThickness="2">
                    <Path.BitmapEffect>
                        <OuterGlowBitmapEffect GlowColor="Gray" GlowSize="25" Opacity="1"/>
                    </Path.BitmapEffect>
                </Path>
            </VisualBrush.Visual>                
        </VisualBrush>
        <VisualBrush x:Key="heart" Stretch="Uniform">
            <VisualBrush.Visual>
                <Path Data="{StaticResource data}" Stroke="Transparent" StrokeThickness="1" Fill="Red">                        
                </Path>
            </VisualBrush.Visual>
        </VisualBrush>
    </Grid.Resources>
    <Border Background="{StaticResource heart}" Width="50">
        <Border Background="{StaticResource heartGlow}"  OpacityMask="{StaticResource heart}">                
        </Border>
    </Border>
</Grid>

You need to use the whole Grid above to render just what you want, it's some kind of composite element. The idea here is we use a glowed element (by OuterGlowBitmapEffect) to render on top of a normal element (rendering the exact original heart). The glow part has both 2 sides: inner glow and outer glow. The inner glow will cover the behind background and create the effect we want. However the outer glow should be cut off. We use OpacityMask to cut off that part and finally have a perfect result.

enter image description here

Upvotes: 1

Related Questions