2010-06-15 93 views
1

我想打斷行元素的TextBlock控制內部用戶首選項中啓用/禁用它在那裏WPF:換行啓用/禁用動態

<TextBlock Style="{StaticResource TextBlockStyle}" Width="130"> 
<TextBlock.Inlines> 
    <Run Text="{Binding Path=Name}" FontWeight="Bold" Foreground="#FF2A4D9E" /> 
    <Run Text="{Binding Path=Price}" FontWeight="Bold" /> 

     <LineBreak /> 

    <Run Text="{Binding Path=Quantity}" Foreground="#99000000" /> 
</TextBlock.Inlines> 
</TextBlock> 
+0

其實我注意到的IsEnabled斷行元素的屬性,但它設置爲false,不作休息去了... – 2010-06-15 12:55:33

回答

1

我不相信有任何在FlowDocument中的方式,使LineBreak不會真正打破,除非把它拿出來。您的選擇是切換到使用WPF佈局或使用附加屬性在LineBreak和空Run之間切換。

使用WPF佈局

您可以考慮使用WPF佈局來代替。例如:

<DataTemplate x:Key="Layout1"> 
    <DockPanel> 
    <TextBlock Text="{Binding Name}" FontWeight="Bold" Foreground="#FF2A4D9E" /> 
    <TextBlock Text="{Binding Price}" FontWeight="Bold" /> 
    <TextBlock Text="{Binding Quantity}" Foreground="#99000000" /> 
    </DockPanel> 
</DataTemplate> 

<DataTemplate x:Key="Layout2"> 
    <DockPanel> 
    <DockPanel DockPanel.Dock="Top"> 
     <TextBlock Text="{Binding Name}" FontWeight="Bold" Foreground="#FF2A4D9E" /> 
     <TextBlock Text="{Binding Price}" FontWeight="Bold" /> 
    </DockPanel> 

    <TextBlock Text="{Binding Quantity}" Foreground="#99000000" /> 
    </DockPanel> 
</DataTemplate> 

現在只需切換DataTemplates即可輕鬆切換佈局。

使用綁定

如果你想「隱藏」通過換行符自動刪除換行符綁定你可以附加「BecomeLineBreak」屬性做到這一點,當應用於空運行,並設置爲true,刪除它並用LineBreak替換它。

就像魔術你現在寫的能力:將變成一個換行符任何時候SomeCondition屬性爲true

<Run my:LineBreakSwitcher.BecomeLineBreak="{Binding SomeCondition}" /> 

和你的運行。

下面是代碼:

public class LineBreakSwitcher : DependencyObject 
{ 
    public static bool GetBecomeLineBreak(DependencyObject obj) { return (bool)obj.GetValue(BecomeLineBreakProperty); } 
    public static void SetBecomeLineBreak(DependencyObject obj, bool value) { obj.SetValue(BecomeLineBreakProperty, value); } 
    public static readonly DependencyProperty BecomeLineBreakProperty = DependencyProperty.RegisterAttached("BecomeLineBreak", typeof(bool), typeof(LineBreakSwitcher), new PropertyMetadata 
    { 
    PropertyChangedCallback = (obj, e) => 
     { 
     var oldElement = (Inline)obj; 
     var newElement = (bool)e.NewValue ? (Inline)new LineBreak() : new Run(); 
     newElement.SetBinding(BecomeLineBreakProperty, oldElement.GetBindingExpression(BecomeLineBreakProperty).ParentBindingBase); 

     var parent = (Paragraph)oldElement.Parent; 
     parent.Inlines.InsertBefore(oldElement, newElement); 
     parent.Inlines.Remove(oldElement); 
     } 
    }); 

它是如何工作的:當BecomeLineBreak上運行爲真,則創建一個新的斷行,該BecomeLineBreak結合被複制過,斷行是在運行之前插入,然後運行被刪除。如果BecomeLineBreak變爲false,將創建一個新的Run,整個過程將相反。

+0

是..接受我的文本塊模板和大,所以我希望避免這種方法不在多個地方編輯。 thansk雖然 – 2010-06-16 02:44:32

+0

那麼我想你確實需要代碼解決方案。我已經更新了我的答案,以提供您需要的算法。這不是真正的代碼 - 大概50行 - 但我現在沒有時間打印它。 – 2010-06-16 03:32:03

+0

狂野。謝謝:) – 2010-06-18 20:21:21

0

這是你想要的(100%XAML):

<TextBlock Text="{Binding Text, ElementName=MyContainer}" 
      FontWeight="Bold" FontSize="14" Name="TextBlockA" /> 
<TextBlock Name="TextBlockB"> 
    <TextBlock.Style> 
     <Style> 
      <Setter Property="TextBlock.Visibility" Value="Visible"/> 
      <Style.Triggers> 
       <DataTrigger Binding="{Binding Path=Text.Length, 
         ElementName=TextBlockC}" Value="0"> 
        <Setter Property="TextBlock.Visibility" Value="Collapsed"/> 
       </DataTrigger> 
      </Style.Triggers> 
     </Style> 
    </TextBlock.Style> 
    <LineBreak /> 
</TextBlock> 
<TextBlock Text="{Binding SubText, ElementName=MyContainer}" 
      FontWeight="Normal" FontSize="12" Name="TextBlockC" />