TheCalendarProgrammer
TheCalendarProgrammer

Reputation: 103

Prevent empty tooltips at a wpf datagrid

I am working on a calendar program, which consists mainly of a WPF DataGrid. As there is not always enough space to display all the entries of a day (which is a DataGridCell), a tooltip with all the entries of the day shell appear at mouse over. This works so far with the code snippet shown below. And now the (little) problem: If there are no entries for a day, no tooltip shell pop up. With the code below an empty tooltip pops up.

<DataGridTemplateColumn x:Name="Entry" 
                        IsReadOnly="True">
  <DataGridTemplateColumn.CellTemplate>
    <DataTemplate>
      <Grid>
        <TextBlock Text="{Binding EntryText}"
                   Foreground="{Binding EntryForeground}"
                   FontWeight="{Binding EntryFontWeight}">
        </TextBlock>
        <TextBlock Text="{Binding RightAlignedText}"
                   Foreground="Gray"    
                   Background="Transparent">
          <TextBlock.ToolTip>
            <TextBlock Text="{Binding AllEntriesText}"/>
          </TextBlock.ToolTip>
        </TextBlock>
      </Grid>
    </DataTemplate>
  </DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>

The Databinding is made via

myCalDataGrid.Itemssource = _listOfDays; 

in code behind, where a 'Day' is the view model for a single calendar row.

Upvotes: 8

Views: 8403

Answers (4)

Viliam
Viliam

Reputation: 678

Another option is to use an own Converter. I prefer this way for example for a TextBlock tooltip that displays TextBlock's text, but for the case there is no text, the empty tooltip is not desired.

XAML code:

//step #1
xmlns:local="clr-namespace:MyNamespace"

//step #2 - into Window.Resources or other
<local:StringToVisibleTooltip x:Key="StringToVis" />


//step #3 - example of use
<TextBlock ...other attributes... TextTrimming="CharacterEllipsis">                                                        
    <TextBlock.ToolTip>
            <ToolTip Visibility="{Binding Path=Text, Converter={StaticResource StringToVis}}">
                    <TextBlock Text="{Binding Text}"/>                                
                </ToolTip>
        </TextBlock.ToolTip>
</TextBlock>

And code behind

  namespace MyNamespace
  {
    public class StringToVisibleTooltip : IValueConverter
    {

        public StringToVisibleTooltip() { }

        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value != null && ((string)value).Length > 0) //empty string does not need tooltip
                return Visibility.Visible;
            else
                return Visibility.Collapsed;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
             return null;
        }
    }
   }

Upvotes: 1

TheCalendarProgrammer
TheCalendarProgrammer

Reputation: 103

Thanks for the solutions, they may work, no question. But I need a TextBlock for the tooltip to format and align the text. So I found this solution:

   <TextBlock Text="{Binding RightAlignedText}"
            HorizontalAlignment="Stretch"
            TextAlignment="Right" Padding="2,0"
            Foreground="Gray"    
            Background="Transparent"
            ToolTipService.ShowDuration="60000"
            ToolTipService.BetweenShowDelay="0"
            ToolTipService.InitialShowDelay="0"
            >
        <TextBlock.ToolTip>
            <ToolTip Visibility="{Binding EntryToolTipVisibility}">
                <TextBlock Text="{Binding ToolTipText}" 
                            TextAlignment="Left"
                            FontFamily="Courier New"/>
            </ToolTip>
        </TextBlock.ToolTip>

    </TextBlock>

I bound the propertie "Visibility" of tooltip to a propertie "EntryToolTipVisibility" (of type Visibility) in the view model. See code snippet below.

public Visibility EntryToolTipVisibility
{ 
    get
    { 
        return _entries.Count > 0 ? Visibility.Visible : Visibility.Collapsed; 
    } 
}

Upvotes: 2

Rohit Vats
Rohit Vats

Reputation: 81253

As H.B. suggested bind directly to the ToolTip property instead of using TextBlock and in case AllEntriesText is empty string you can apply a trigger on your TextBlock to disable your tooltip by setting the property ToolTipService.IsEnabled like this -

<TextBlock Text="{Binding RightAlignedText}"
           Foreground="Gray"    
           Background="Transparent"
           ToolTip="{Binding AllEntriesText}">
   <TextBlock.Style>
      <Style TargetType="TextBlock">
         <Style.Triggers>
            <Trigger Property="ToolTip"
                     Value="{x:Static system:String.Empty}">
               <Setter Property="ToolTipService.IsEnabled" Value="False" />
            </Trigger>
         </Style.Triggers>
       </Style>
    </TextBlock.Style>
</TextBlock>

Make sure to add namespace system in your xaml -

xmlns:system="clr-namespace:System;assembly=mscorlib"

Upvotes: 12

brunnerh
brunnerh

Reputation: 185140

Bind directly to the ToolTip property (do not create a TextBlock for it) and set AllEntriesText to null if there are no entries, then the ToolTip itself is also null and should not show.

Upvotes: 4

Related Questions