Я новичок в WPF, и я пытаюсь написать интерактивный элемент управления панорамированием с масштабированием. У меня уже есть зум-сковорода изображение, которое, кажется, работает:Выбор пикселя для PanZoomImage
<Border Name="border" ClipToBounds="True">
<Canvas>
<Image Name ="image">
Source="{Binding Path=Source}"
MouseLeftButtonDown="image_MouseLeftButtonDown"
MouseLeftButtonUp="image_MouseLeftButtonUp"
MouseMove="image_MouseMove"
MouseWheel="image_MouseWheel">
</Image>
</Canvas>
</Border>
Для мыши и колеса событий я использовал этот пост: http://www.codeproject.com/Articles/168176/Zooming-and-panning-in-WPF-with-fixed-focus
Я пишу интерактивное управление наследованием от ZoomPanImage и добавления события для LeftMouseUp.
public class ClickableImage : PanZoomImage
{
public event Action<Point> Click;
//...
protected override void OnMouseLeftButtonUp(MouseButtonEventArgs e)
{
base.OnMouseLeftButtonUp(e);
// ... all sorts of checks to distinguish click from mouse move
if (Click != null)
{
Click(ControlToImage(mouseUpCoordinates));
}
}
protected Point ControlToImage(Point controlPixel)
{
//this is where i am stuck...
}
}
Моя проблема заключается в том, что я не могу вычислить правильные координаты изображения, заданные координатами управления. Мне нужно учесть, что изображение можно масштабировать и панорамировать, а само окно можно изменить.
Я попытался использовать преобразование рендеринга. Когда я увеличиваю и панорамирую изображение, я обновляю преобразование. И когда я пытаюсь преобразовать координаты управления в координаты изображения, я использую обратное преобразование:
Point imagePixel = image.RenderTransform.Inverse.Transform(controlPixel);
Но это не сработало. Одна из проблем заключается в том, что Transform начинается как Identity, в то время как на самом деле изображение равномерно растягивается до размера элемента управления.
Спасибо, Дина
Убедитесь, что вы установили [Image.Stretch] (http://msdn.microsoft.com/en-us/library/system.windows.controls. image.stretch.aspx) до 'None' перед применением RenderTransform. – Clemens
@ Clemens, Да, я сделал это. Проблема с этим решением заключается в том, что изначально изображение больше окна. Я хочу, чтобы он изменялся в зависимости от размера окна. Поэтому я попытался добавить обратный вызов, который будет вызываться сразу после изменения источника изображения и изменит преобразование. Но это не сработало, потому что, когда обратный вызов назывался image.actualHeight и image.actualWidth, все равно 0 ... – Dina
Когда вы устанавливаете свойство Source (я предполагаю, что в коде позади), вы устанавливаете его в некоторый [ImageSource] (http: //msdn.microsoft.com/en-us/library/system.windows.media.imagesource.aspx)-derived, например BitmapSource. Получите размер изображения из свойств Width и Height ImageSource и соответствующим образом настройте RenderTransform. Во всяком случае, вам нужно избегать автоматического масштабирования, если вы хотите сделать это вручную. – Clemens