Как реализовать масштабирование относительно произвольной точки? Реализую специализированный 2D-редактор в .NET. Хочу реализовать масштабирование относительно курсора В GDI+ у класса Graphics есть замечательное свойство Transform, которое позволяет с помощью аппарата аффинных преобразований в матричной форме реализовать то, что мне нужно. Во всех книжках пишут, что для масштабирования относительно произвольной точки необходимо:выполнить преобразование смещения так, чтобы точка относительно которой масштабируем сместилась в начало координатвыполнить непосредственно масштабирование относительно начала координатвыполнить преобразование смещение так, чтобы начало координат сместилось в исходную точку То есть в рамках моего приложения достаточно правильным образом менять матрицу Transform при вращении колесика мыши Делаю так:public class DrawingAreaControl : UserContro
но это не работает так как надо. После нескольких масштабирований, рисунок под мышкой начинает убегать и уже нет нужного масштабирования относительно курсора По любому это из-за неправильного расчета преобразований в начало координат и обратно. Как вычислить их, чтобы работало правильно?
Проблема заключается в том, что вы неправильно компенсируете смещение при выполнении преобразований относительно курсора. Вместо этого, вам нужно сначала выполнить преобразование относительно курсора, а затем отменить это преобразование для коррекции расположения курсора на холсте.
Приведу пример ваших методов с исправлениями:
protected override void OnMouseWheel(MouseEventArgs e
Таким образом, вы сначала выполняете преобразование относительно курсора, затем масштабирование и, наконец, отменяете преобразование относительно курсора. Это должно исправить проблему с уходом изображения от курсора при масштабировании.
Проблема заключается в том, что вы неправильно компенсируете смещение при выполнении преобразований относительно курсора. Вместо этого, вам нужно сначала выполнить преобразование относительно курсора, а затем отменить это преобразование для коррекции расположения курсора на холсте.
Приведу пример ваших методов с исправлениями:
protected override void OnMouseWheel(MouseEventArgs ebase.OnMouseWheel(e)
Matrix translationMatrix = new Matrix()
translationMatrix.Translate(e.Location.X, e.Location.Y)
Matrix scaleMatrix = new Matrix()
scaleMatrix.Scale(e.Delta > 0 ? SCALE_MUL : 1 / SCALE_MUL, e.Delta > 0 ? SCALE_MUL : 1 / SCALE_MUL)
Matrix revertTranslationMatrix = new Matrix()
revertTranslationMatrix.Translate(-e.Location.X, -e.Location.Y)
Matrix tempMatrix = new Matrix()
tempMatrix.Multiply(revertTranslationMatrix)
tempMatrix.Multiply(scaleMatrix)
tempMatrix.Multiply(translationMatrix)
transform.Multiply(tempMatrix)
Invalidate()
}
Таким образом, вы сначала выполняете преобразование относительно курсора, затем масштабирование и, наконец, отменяете преобразование относительно курсора. Это должно исправить проблему с уходом изображения от курсора при масштабировании.