Поворот изображения с использованием положения мыши в C #

В основном то, что я пытаюсь сделать, - это повернуть изображение с помощью событий мыши. Например, когда вы удерживаете левую кнопку мыши, изображение вращается, когда вы перемещаете мышь вверх и вниз. Я нашел здесь еще один вопрос, почти такой же, как у меня (Как повернуть изображение в C #), но при сопоставлении параметра угла в методе поворота (исходный код метода в ссылке) с вычисленным углом между мышью и центром изображения возникает исключение переполнения. Изображение, которое я пытаюсь повернуть, находится в рамке с картинками. Любые идеи? Должен ли я сделать это по-другому?

Заранее спасибо!

--------- РЕДАКТИРОВАТЬ 1 -----------

Хорошо, я думаю, что мой триггер был отключен, я изменил его на ...

Угол = Атан ((mousePosY - imageCenterY) / (mousePosX - imageCenterX)

Но теперь изображение не вращается, оно просто движется (я также запрограммировал его способность двигаться, но это работает нормально). Вот фрагмент кода, с которым я имею дело.

    private void pictureBox_MouseDown(object sender, MouseEventArgs e)
    {
        isDragging = true;

        pbCurrentX = e.X;
        pbCurrentY = e.Y;

    }

    private void pictureBox_MouseMove(object sender, MouseEventArgs e)
    {
        // For moving the image
        if (isDragging)
        {
            this.pictureBox1.Top = this.pictureBox1.Top + (e.Y - pbCurrentY);
            this.pictureBox1.Left = this.pictureBox1.Left + (e.X - pbCurrentX);
        }

        // For rotating the image
        if (rotateMode  && isDragging)
        {
            y2 = e.Y;
            y1 = (this.pictureBox1.Location.Y + (this.pictureBox1.Height / 2));
            x2 = e.X;
            x1 = (this.pictureBox1.Location.X + (this.pictureBox1.Width / 2));

            angle = (float)Math.Atan((y2-y1)/(x2-x1));

            // RotateImage method from the other question linked above
            this.pictureBox1.Image = RotateImage(this.pictureBox1.Image, angle);
        }


    }

Флаг rotateMode устанавливается в значение true при двойном щелчке по изображению. Спасибо всем!

---------ОТВЕЧАТЬ-----------

Благодаря Гейбу я обнаружил все небольшие изъяны в своем коде, и теперь он отлично работает. Единственное, что я должен был сделать размер рамки изображения больше, чтобы соответствовать повернутому изображению. Вот правильный код для всех, кто хочет знать ответ.

private void pictureBox_MouseDown(object sender, MouseEventArgs e)
    {
        isDragging = true;

        pbCurrentX = e.X;
        pbCurrentY = e.Y;

    }

    private void pictureBox_MouseMove(object sender, MouseEventArgs e)
    {

        if (isDragging && !rotateMode)
        {
            this.pictureBox1.Top = this.pictureBox1.Top + (e.Y - pbCurrentY);
            this.pictureBox1.Left = this.pictureBox1.Left + (e.X - pbCurrentX);
        }

        if (rotateMode  && isDragging)
        {
            y2 = e.Y;
            y1 = (this.pictureBox1.Location.Y + (this.pictureBox1.Height / 2));
            x2 = e.X;
            x1 = (this.pictureBox1.Location.X + (this.pictureBox1.Width / 2));

            angle = (float)Math.Atan2((y1 - y2), (x1 - x2));

            pictureBox1.Image =  RotateImage(currentImage, (100*angle));
        } 

    }

    private void pictureBox_MouseUp(object sender, MouseEventArgs e)
    {
        isDragging = false;
    }

Спасибо Гейбу и всем остальным!


person Gaax    schedule 28.02.2010    source источник
comment
Не могли бы вы показать код, который не работает?   -  person Vlad    schedule 28.02.2010
comment
Возможно, вы пытались использовать угол в градусах, в то время как параметр поворота должен быть в радианах.   -  person Gabe    schedule 28.02.2010
comment
Слава богу, есть еще люди, которые любезно публикуют свои решения, чтобы другие могли у них поучиться!   -  person    schedule 22.08.2010


Ответы (4)


Вы пробовали что-то вроде this.pictureBox1.Image = RotateImage(this.pictureBox1.Image, angle);? Функция RotateImage, с которой вы связались, вернула новое повернутое изображение, а не поворачивала его на месте, как ожидает ваш код.

К сожалению, это поворачивает уже повернутое изображение. Что вам нужно сделать, так это сохранить где-нибудь исходное изображение, скажем originalImage. Тогда есть this.pictureBox1.Image = RotateImage(originalImage, angle);. Таким образом всегда будет вращаться свежая версия оригинала.

person Gabe    schedule 28.02.2010
comment
Ага! Не уловил, и теперь это работает, спасибо! Но теперь у меня возникла совершенно новая проблема ... lol, изображение искажается каждый раз, когда оно поворачивается до неузнаваемости. Любые идеи? - person Gaax; 28.02.2010
comment
Я установил глобальную переменную с именем currentImage для хранения исходного изображения: Image currentImage = picturebox1.Image Теперь я получаю исключение NullReferenceException внутри метода RotateImage, когда он создает новое растровое изображение, используя размеры изображения: Ссылка на объект не установлена ​​на экземпляр объекта. - person Gaax; 28.02.2010
comment
Если вы получаете исключение NullReferenceException, это просто означает, что вы не инициализируете currentImage в нужное время или не вызываете RotateImage(currentImage, angle). - person Gabe; 28.02.2010
comment
Ха, да, ты прав. Я чувствую себя глупо из-за того, что даже опубликовал это ›‹ Спасибо, чувак, теперь все работает отлично! - person Gaax; 28.02.2010

Не видя вашего кода, мы можем только догадываться. Я предполагаю, что вы выполняете какой-то расчет триггера, например:

theta = Math.Atan((y2 - y1) / (x2 - x1));

Если ваш x2-x1 стремится к 0, ваш аргумент Math.Atan стремится к бесконечности и выходит за пределы.

person mbeckish    schedule 28.02.2010

Угол = Атан ((mousePosY - imageCenterY) / (mousePosX - imageCenterY)

Вы дважды используете imageCenterY (хотя это нормально в опубликованном вами коде).

В любом случае я бы предложил использовать Atan2, а не Atan.

person Community    schedule 28.02.2010
comment
Изменил, но проблема осталась прежней :( - person Gaax; 28.02.2010
comment
Да, для этого нужно использовать Atan2, иначе ваше изображение не сможет вращаться по полному кругу. - person Gabe; 28.02.2010

     int  y2 = _cursory; // Cursor.Postion.Y

     int   y1 = (this.pictureBox1.Location.Y + (this.pictureBox1.Height / 2));
     int x2 = _cursorx; // Cursor.Postion.X
     int   x1 = (this.pictureBox1.Location.X + (this.pictureBox1.Width / 2));

      float  angle = (float)Math.Atan2((y1 - y2), (x1 - x2));
      float xDistance = x1 - this.pictureBox1.Location.X;
      float yDistance = y1 - this.pictureBox1.Location.Y;

      double deg = angle / Math.PI * 180 + 180;
      pictureBox1.Image = RotateImage(img, (int)deg);

// img == исходное изображение

этот код работал у меня

person Ehsan KHAN    schedule 27.11.2019