В WPF у меня есть своего рода редактор кривых, который состоит из средства просмотра прокрутки (для панорамирования) поверх холста, где я отображаю ключи и сегменты кривой (линейные, постоянные и сплайны). Я использую MVVM. Кроме того, у меня могут быть сотни ключей с сегментами между собой. Кроме того, панорамирование / масштабирование должно быть действительно плавным и отзывчивым.
В модели (и ViewModel) ключ имеет позиции XY; сегменты имеют PointCollection
.
В представлении ключи Rectangle
, сегменты кривых Polyline
.
Все эти элементы пользовательского интерфейса привязаны к свойствам зависимости Top и Left холста.
Проблема, с которой я столкнулся при реализации масштабирования.
Сначала я работал с окном просмотра, которое вставляется между прокруткой и холстом
<ScrollViewer>
<Viewbox>
<Canvas/>
</Viewbox>
</ScrollViewer>
Панорамирование работало нормально, но зум был не тем зумом, который мне нужен. Он сделал «графический» зум, который делает все больше, прямоугольники и полилинии.
Я хочу, чтобы при увеличении клавиши (прямоугольники) перемещались дальше друг от друга, не увеличиваясь, а сегмент (полилиния) растягивался между двумя клавишами, при этом StrokeThickness
не выглядел больше.
Решение, которое я искал, - это перевод всех координат в ВМ при изменении масштаба.
Ex:
Ключ в модели имеет позицию (2,3). Когда значение масштабирования равно 2,0, ViewModel клавиши будет показывать позиции (4,6). Для сегментов я переведу все точки в PointCollection модели и поместу их в PointCollection модели представления.
Проблема с этим решением заключается в том, что при быстром увеличении / уменьшении он может снижать производительность, когда у меня будут сотни клавиш. Поскольку изменение коэффициента масштабирования изменит все-все координаты ViewModels, и, таким образом, будут перемещены все элементы UIE.
Я думал о RenderTransform в UIElements, чтобы применить трансляцию масштабирования, но он не будет работать с полилиниями. Я мог бы использовать ScaleTransform для полилиний, но это растянет их визуально.
Это довольно сложно описать, поэтому не стесняйтесь спрашивать более подробную информацию.
Есть идеи, как мне этого добиться?