我的WPF应用程序覆盖了它,它显示了一些寄宿生"上下文敏感的帮助"。寄宿生现在应该否决父母背景并显示背后的内容(某种视图端口通过背景)。
如果没有覆盖,控件看起来像这样:
Overlay Activated看起来像这样:
Overlay是一个Usercontrol,包含一个ListBox,它应该提供一个寄存器。 ListBoxPanel是一个Canvas,ListBoxItems是你可以看到的Boarders(Buttons),它们使用ItemContainerStyle移动到它们应该包围的UIElements上。
Overlay看起来像这样:
<ItemsControl ItemsSource="{Binding HelpItems}" KeyboardNavigation.TabNavigation="Cycle" IsTabStop="True"
helpers:FocusHelper.FocusOnLoad="True" FocusVisualStyle="{StaticResource EmptyFocusVisual}">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<Canvas IsItemsHost="True"/>
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
<DataTemplate>
<Grid>
<Button Command="{Binding ShowPopupCommand}" Background="Transparent" BorderThickness="2">
<Button.Style>
<Style>
<Setter Property="Button.Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Button}">
<Border Background="{TemplateBinding Background}"
BorderThickness="{TemplateBinding BorderThickness}" BorderBrush="{TemplateBinding BorderBrush}"/>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Button.Style>
</Button>
</Grid>
</DataTemplate>
</ItemsControl.ItemTemplate>
<ItemsControl.ItemContainerStyle>
<Style>
<Setter Property="Canvas.Left" Value="{Binding Left}" />
<Setter Property="Canvas.Top" Value="{Binding Top}" />
<Setter Property="FrameworkElement.Width" Value="{Binding Width}" />
<Setter Property="FrameworkElement.Height" Value="{Binding Height}" />
</Style>
</ItemsControl.ItemContainerStyle>
</ItemsControl>
我希望叠加层在边框内是透明的,同时保持列表框上的半透明调暗背景,换句话说,我的ListBox的空白区域应该是灰色。 有没有简单的方法我可以让Light Blue边框显示面板背后的内容而没有我Overlay的半透明背景?
这是目标结果:
我也尝试创建一个不透明度过滤器,但这是错误的方法。并且似乎没有一种简单的方法来反转不透明度滤镜。
答案 0 :(得分:1)
控制台,
好的,我们“要在冰上打个洞”。
所以这是一个自定义控件:OverlayWithGaps
自我绘制,给定的背景可以是半透明的。
OverlayWithGaps
有一个代表差距的Rect Collection:
public ObservableCollection<Rect> Gaps
{
get { return (ObservableCollection<Rect>)GetValue(GapsProperty); }
set { SetValue(GapsProperty, value); }
}
private static FrameworkPropertyMetadata fpm = new FrameworkPropertyMetadata(
null,
FrameworkPropertyMetadataOptions.AffectsRender |
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault,
null,
null
);
public static readonly DependencyProperty GapsProperty =
DependencyProperty.Register("Gaps", typeof(ObservableCollection<Rect>), typeof(OverlayWithGaps), fpm);
使用AffectsRender
,如果该依赖项属性发生更改,则会发生重绘。
这是绘图功能:
protected override void OnRender(System.Windows.Media.DrawingContext dc)
{
if (Gaps != null && Gaps.Count > 0)
{
Geometry newGeometry = new RectangleGeometry(new Rect(0, 0, ActualWidth, ActualHeight));
foreach (var gap in Gaps)
// remove each rectangle of the global clipping rectangle :
// we make "a hole in the ice"
newGeometry = Geometry.Combine(newGeometry,
new RectangleGeometry(gap),
GeometryCombineMode.Exclude,
transform: null);
// When the geometry is finished, we make the hole
dc.PushClip(newGeometry);
}
dc.DrawRectangle(Background, null, new Rect(0, 0, ActualWidth, ActualHeight));
}
修改强>
3. ItemsControl ListViewItems
void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
// overlay is the OverlayWithGaps instance
// in the window
overlay.Gaps = new ObservableCollection<Rect>(
itemsControl1.FindAllVisualDescendants()
.OfType<Grid>()
.Select(grid => {
Point relativePoint = grid.TransformToAncestor(this)
.Transform(new Point(0, 0));
return new Rect(relativePoint.X,
relativePoint.Y,
grid.ActualWidth,
grid.ActualHeight
);
})
);
}
请注意,我在LINQ查询中选择了Grids,因为它们位于DataTemplate中 但是Linq查询几乎可以选择任何东西(按名称,......)
FindAllVisualDescendants()
扩展功能可在此处找到:
Datagrid templatecolumn update source trigger explicit only updates first row
最佳编码