Themes/MaterialDesignTheme.RatingBar.xaml

<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
                    xmlns:converters="clr-namespace:MaterialDesignThemes.Wpf.Converters"
                    xmlns:system="clr-namespace:System;assembly=mscorlib"
                    xmlns:wpf="clr-namespace:MaterialDesignThemes.Wpf">
 
  <Style TargetType="{x:Type wpf:RatingBar}">
    <Setter Property="ClipToBounds" Value="False" />
    <Setter Property="Foreground" Value="{DynamicResource MaterialDesign.Brush.Primary}" />
    <Setter Property="Template">
      <Setter.Value>
        <ControlTemplate TargetType="{x:Type wpf:RatingBar}">
          <ItemsControl Margin="{TemplateBinding Padding}"
                        HorizontalAlignment="Left"
                        VerticalAlignment="Top"
                        ItemsSource="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=RatingButtons}">
            <ItemsControl.ItemsPanel>
              <ItemsPanelTemplate>
                <StackPanel Orientation="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=Orientation}" />
              </ItemsPanelTemplate>
            </ItemsControl.ItemsPanel>
          </ItemsControl>
        </ControlTemplate>
      </Setter.Value>
    </Setter>
    <Setter Property="ValueItemContainerButtonStyle">
      <Setter.Value>
        <Style TargetType="wpf:RatingBarButton">
          <Style.Setters>
            <Setter Property="Command" Value="{x:Static wpf:RatingBar.SelectRatingCommand}" />
            <Setter Property="CommandParameter" Value="{Binding RelativeSource={RelativeSource Self}, Path=Value}" />
            <Setter Property="wpf:RippleAssist.ClipToBounds" Value="False" />
            <Setter Property="wpf:RippleAssist.IsCentered" Value="True" />
            <Setter Property="wpf:RippleAssist.RippleSizeMultiplier" Value="0.5" />
            <Setter Property="Template">
              <Setter.Value>
                <ControlTemplate TargetType="wpf:RatingBarButton">
                  <Grid>
                    <wpf:Ripple Padding="{TemplateBinding Padding}"
                                HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
                                VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
                                Content="{TemplateBinding Content}"
                                ContentTemplate="{TemplateBinding ContentTemplate}"
                                Focusable="False"
                                RenderTransformOrigin=".5, .5"
                                SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
                                Tag="{DynamicResource MaterialDesign.Brush.Primary}">
                      <TextBlock.Foreground>
                        <MultiBinding Converter="{x:Static wpf:RatingBar+TextBlockForegroundConverter.Instance}">
                          <Binding Path="Tag" RelativeSource="{RelativeSource Self}" />
                          <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="RatingBar.Value" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                        </MultiBinding>
                      </TextBlock.Foreground>
                      <wpf:Ripple.RenderTransform>
                        <RotateTransform x:Name="RotateTransform" />
                      </wpf:Ripple.RenderTransform>
                    </wpf:Ripple>
                    <Canvas>
                      <Grid x:Name="previewValueHorizontal"
                            Height="36"
                            IsHitTestVisible="False"
                            Visibility="Collapsed">
                        <Grid.RenderTransform>
                          <TransformGroup>
                            <TranslateTransform>
                              <TranslateTransform.X>
                                <MultiBinding Converter="{x:Static wpf:RatingBar+PreviewIndicatorTransformXConverter.Instance}">
                                  <Binding Path="ActualWidth" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding ElementName="previewValueHorizontal" Path="ActualWidth" />
                                  <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.IsFractionalValueEnabled" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.PreviewValue" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="IsMouseOver" RelativeSource="{RelativeSource TemplatedParent}" />
                                </MultiBinding>
                              </TranslateTransform.X>
                              <TranslateTransform.Y>
                                <MultiBinding Converter="{x:Static wpf:RatingBar+PreviewIndicatorTransformYConverter.Instance}">
                                  <Binding Path="ActualHeight" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding ElementName="previewValueHorizontal" Path="ActualHeight" />
                                  <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.IsFractionalValueEnabled" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.PreviewValue" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="IsMouseOver" RelativeSource="{RelativeSource TemplatedParent}" />
                                </MultiBinding>
                              </TranslateTransform.Y>
                            </TranslateTransform>
                          </TransformGroup>
                        </Grid.RenderTransform>
                        <AdornerDecorator CacheMode="{Binding RelativeSource={RelativeSource Self}, Path=(wpf:ShadowAssist.CacheMode)}">
                          <Grid Effect="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=(wpf:ElevationAssist.Elevation), Converter={x:Static converters:ShadowConverter.Instance}}">
                            <Rectangle Margin="0,0,0,5"
                                       Fill="{DynamicResource MaterialDesign.Brush.ToolTip.Background}"
                                       RadiusX="2"
                                       RadiusY="2" />
                            <Polygon HorizontalAlignment="Center"
                                     VerticalAlignment="Bottom"
                                     Fill="{DynamicResource MaterialDesign.Brush.ToolTip.Background}"
                                     Points="0,0 4.5,5 9,0" />
                          </Grid>
                        </AdornerDecorator>
                        <TextBlock x:Name="previewValueTextHorizontal"
                                   Margin="12,0,12,5"
                                   VerticalAlignment="Center"
                                   Foreground="{DynamicResource MaterialDesign.Brush.Background}"
                                   Text="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=PreviewValue}"
                                   TextAlignment="Center" />
                      </Grid>
                      <Grid x:Name="previewValueVertical"
                            Height="31"
                            IsHitTestVisible="False"
                            Visibility="Collapsed">
                        <Grid.RenderTransform>
                          <TransformGroup>
                            <TranslateTransform>
                              <TranslateTransform.X>
                                <MultiBinding Converter="{x:Static wpf:RatingBar+PreviewIndicatorTransformXConverter.Instance}">
                                  <Binding Path="ActualWidth" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding ElementName="previewValueVertical" Path="ActualWidth" />
                                  <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.IsFractionalValueEnabled" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.PreviewValue" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="IsMouseOver" RelativeSource="{RelativeSource TemplatedParent}" />
                                </MultiBinding>
                              </TranslateTransform.X>
                              <TranslateTransform.Y>
                                <MultiBinding Converter="{x:Static wpf:RatingBar+PreviewIndicatorTransformYConverter.Instance}">
                                  <Binding Path="ActualHeight" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding ElementName="previewValueVertical" Path="ActualHeight" />
                                  <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.IsFractionalValueEnabled" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="RatingBar.PreviewValue" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                                  <Binding Path="IsMouseOver" RelativeSource="{RelativeSource TemplatedParent}" />
                                </MultiBinding>
                              </TranslateTransform.Y>
                            </TranslateTransform>
                          </TransformGroup>
                        </Grid.RenderTransform>
                        <AdornerDecorator CacheMode="{Binding RelativeSource={RelativeSource Self}, Path=(wpf:ShadowAssist.CacheMode)}">
                          <Grid Effect="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=(wpf:ElevationAssist.Elevation), Converter={x:Static converters:ShadowConverter.Instance}}">
                            <Rectangle Margin="0,0,5,0"
                                       Fill="{DynamicResource MaterialDesign.Brush.ToolTip.Background}"
                                       RadiusX="2"
                                       RadiusY="2" />
                            <Polygon HorizontalAlignment="Right"
                                     VerticalAlignment="Center"
                                     Fill="{DynamicResource MaterialDesign.Brush.ToolTip.Background}"
                                     Points="0,0 6,5 0,10" />
                          </Grid>
                        </AdornerDecorator>
                        <TextBlock x:Name="previewValueTextVertical"
                                   Margin="12,0,17,0"
                                   VerticalAlignment="Center"
                                   Foreground="{DynamicResource MaterialDesign.Brush.Background}"
                                   Text="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=PreviewValue}"
                                   TextAlignment="Center" />
                      </Grid>
                    </Canvas>
                  </Grid>
                  <ControlTemplate.Triggers>
                    <MultiDataTrigger>
                      <MultiDataTrigger.Conditions>
                        <Condition Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseOver}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=Orientation}" Value="Horizontal" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsPreviewValueEnabled}" Value="True" />
                      </MultiDataTrigger.Conditions>
                      <Setter TargetName="previewValueHorizontal" Property="Visibility" Value="Visible" />
                    </MultiDataTrigger>
                    <MultiDataTrigger>
                      <MultiDataTrigger.Conditions>
                        <Condition Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseOver}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=Orientation}" Value="Horizontal" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsPreviewValueEnabled}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsFractionalValueEnabled}" Value="True" />
                      </MultiDataTrigger.Conditions>
                      <!-- When fractional values are enabled, always show the preview with 2 decimal places -->
                      <Setter TargetName="previewValueTextHorizontal" Property="Text" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=PreviewValue, StringFormat=' {0:N2}'}" />
                    </MultiDataTrigger>
                    <MultiDataTrigger>
                      <MultiDataTrigger.Conditions>
                        <Condition Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseOver}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=Orientation}" Value="Vertical" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsPreviewValueEnabled}" Value="True" />
                      </MultiDataTrigger.Conditions>
                      <Setter TargetName="previewValueVertical" Property="Visibility" Value="Visible" />
                    </MultiDataTrigger>
                    <MultiDataTrigger>
                      <MultiDataTrigger.Conditions>
                        <Condition Binding="{Binding RelativeSource={RelativeSource Self}, Path=IsMouseOver}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=Orientation}" Value="Vertical" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsPreviewValueEnabled}" Value="True" />
                        <Condition Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=IsFractionalValueEnabled}" Value="True" />
                      </MultiDataTrigger.Conditions>
                      <!-- When fractional values are enabled, always show the preview with 2 decimal places -->
                      <Setter TargetName="previewValueTextVertical" Property="Text" Value="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}, Path=PreviewValue, StringFormat=' {0:N2}'}" />
                    </MultiDataTrigger>
                    <EventTrigger RoutedEvent="Click">
                      <EventTrigger.Actions>
                        <BeginStoryboard>
                          <Storyboard TargetProperty="Angle" TargetName="RotateTransform">
                            <DoubleAnimationUsingKeyFrames>
                              <SplineDoubleKeyFrame KeyTime="0" Value="0" />
                              <EasingDoubleKeyFrame KeyTime="0:0:0.8" Value="360">
                                <EasingDoubleKeyFrame.EasingFunction>
                                  <SineEase EasingMode="EaseInOut" />
                                </EasingDoubleKeyFrame.EasingFunction>
                              </EasingDoubleKeyFrame>
                            </DoubleAnimationUsingKeyFrames>
                          </Storyboard>
                        </BeginStoryboard>
                      </EventTrigger.Actions>
                    </EventTrigger>
                  </ControlTemplate.Triggers>
                </ControlTemplate>
              </Setter.Value>
            </Setter>
          </Style.Setters>
          <Style.Triggers>
            <DataTrigger Binding="{Binding IsReadOnly, RelativeSource={RelativeSource FindAncestor, AncestorType=wpf:RatingBar}}" Value="True">
              <Setter Property="Template">
                <Setter.Value>
                  <ControlTemplate TargetType="wpf:RatingBarButton">
                    <wpf:Ripple Padding="{TemplateBinding Padding}"
                                HorizontalContentAlignment="{TemplateBinding HorizontalContentAlignment}"
                                VerticalContentAlignment="{TemplateBinding VerticalContentAlignment}"
                                Content="{TemplateBinding Content}"
                                ContentTemplate="{TemplateBinding ContentTemplate}"
                                Focusable="False"
                                IsEnabled="False"
                                RenderTransformOrigin=".5, .5"
                                SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}"
                                Tag="{DynamicResource MaterialDesign.Brush.Primary}">
                      <TextBlock.Foreground>
                        <MultiBinding Converter="{x:Static wpf:RatingBar+TextBlockForegroundConverter.Instance}">
                          <Binding Path="Tag" RelativeSource="{RelativeSource Self}" />
                          <Binding Path="RatingBar.Orientation" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="RatingBar.InvertDirection" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="RatingBar.Value" RelativeSource="{RelativeSource TemplatedParent}" />
                          <Binding Path="Value" RelativeSource="{RelativeSource TemplatedParent}" />
                        </MultiBinding>
                      </TextBlock.Foreground>
                    </wpf:Ripple>
                  </ControlTemplate>
                </Setter.Value>
              </Setter>
            </DataTrigger>
          </Style.Triggers>
        </Style>
      </Setter.Value>
    </Setter>
    <Setter Property="ValueItemTemplate">
      <Setter.Value>
        <DataTemplate DataType="system:Int32">
          <Viewbox Width="24" Height="24">
            <Canvas Width="24" Height="24">
              <Path Data="M12,17.27L18.18,21L16.54,13.97L22,9.24L14.81,8.62L12,2L9.19,8.62L2,9.24L7.45,13.97L5.82,21L12,17.27Z" Fill="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=Control}, Path=Foreground}" />
            </Canvas>
          </Viewbox>
        </DataTemplate>
      </Setter.Value>
    </Setter>
    <Setter Property="wpf:ElevationAssist.Elevation" Value="Dp2" />
    <Setter Property="wpf:RippleAssist.Feedback" Value="{DynamicResource MaterialDesign.Brush.Button.Ripple}" />
    <Style.Triggers>
      <Trigger Property="IsEnabled" Value="False">
        <Setter Property="Opacity" Value=".26" />
      </Trigger>
    </Style.Triggers>
  </Style>
 
</ResourceDictionary>