我使用了 Stack Overflow 上找到的代码,通过附加行为使 WPF 弹出窗口可拖动。此代码和行为按预期工作。弹出窗口将保持在其拖动位置,直到用户再次移动它。
我现在想做的是让弹出窗口在关闭并重新打开后显示在其原始放置目标位置。我该如何完成这个任务?
原帖:A draggable popup control in wpf
Rick Sladkey 编写的应答代码:https://stackoverflow.com/a/4784977/1286413
这是弹出窗口的 XAML:
<Grid>
<StackPanel>
<TextBox x:Name="textBox1" Width="200" Height="20"/>
</StackPanel>
<Popup PlacementTarget="{Binding ElementName=textBox1}" IsOpen="{Binding IsKeyboardFocused, ElementName=textBox1, Mode=OneWay}">
<i:Interaction.Behaviors>
<local:MouseDragPopupBehavior/>
</i:Interaction.Behaviors>
<TextBlock Background="White">
<TextBlock.Text>Sample Popup content.</TextBlock.Text>
</TextBlock>
</Popup>
</Grid>
这是他写的 AttachedBehavior:
public class MouseDragPopupBehavior : Behavior<Popup>
{
private bool mouseDown;
private Point oldMousePosition;
protected override void OnAttached()
{
AssociatedObject.MouseLeftButtonDown += (s, e) =>
{
mouseDown = true;
oldMousePosition = AssociatedObject.PointToScreen(e.GetPosition(AssociatedObject));
AssociatedObject.Child.CaptureMouse();
};
AssociatedObject.MouseMove += (s, e) =>
{
if (!mouseDown) return;
var newMousePosition = AssociatedObject.PointToScreen(e.GetPosition(AssociatedObject));
var offset = newMousePosition - oldMousePosition;
oldMousePosition = newMousePosition;
AssociatedObject.HorizontalOffset += offset.X;
AssociatedObject.VerticalOffset += offset.Y;
};
AssociatedObject.MouseLeftButtonUp += (s, e) =>
{
mouseDown = false;
AssociatedObject.Child.ReleaseMouseCapture();
};
}
}
预先感谢您的帮助!
最佳答案
在 OnAttached 中,向 Closed 添加一个处理程序,用于保存弹出窗口的位置,向 Opened 添加另一个处理程序,用于将弹出窗口移回到该位置。
public class MouseDragPopupBehavior : Behavior<Popup>
{
private bool mouseDown;
private Point oldMousePosition;
private bool useSavedPosition;
private Point savedPosition;
protected override void OnAttached()
{
AssociatedObject.MouseLeftButtonDown += (s, e) =>
{
mouseDown = true;
oldMousePosition = AssociatedObject.PointToScreen(e.GetPosition(AssociatedObject));
AssociatedObject.Child.CaptureMouse();
};
AssociatedObject.MouseMove += (s, e) =>
{
if (!mouseDown) return;
var newMousePosition = AssociatedObject.PointToScreen(e.GetPosition(AssociatedObject));
var offset = newMousePosition - oldMousePosition;
oldMousePosition = newMousePosition;
AssociatedObject.HorizontalOffset += offset.X;
AssociatedObject.VerticalOffset += offset.Y;
};
AssociatedObject.MouseLeftButtonUp += (s, e) =>
{
mouseDown = false;
AssociatedObject.Child.ReleaseMouseCapture();
};
AssociatedObject.Opened += (s, e) =>
{
if (!useSavedPosition) return;
AssociatedObject.HorizontalOffset = savedPosition.X;
AssociatedObject.VerticalOffset = savedPosition.Y;
};
AssociatedObject.Loaded += (s, e) =>
{
savedPosition = new Point(AssociatedObject.HorizontalOffset, AssociatedObject.VerticalOffset);
useSavedPosition = true;
};
}
}
关于wpf - 如何将可拖动的 wpf 弹出窗口设置为关闭后的原始位置?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14390142/