Reply
Solved! Go to solution

Rotate camera using the mouse

Hi guys, I've searched a lot before creating this post. I'm trying to create a C# win32 program that rotates Solid Edge camera when I move the mouse inside my application. As I understood, there are at least 2 ways to rotate the camera.

 

First way: view.RotateCamera

Second way: view.GetCamera / view.SetCamera

 

In my program, if I move the mouse from the center to the top, it means I've moved the Y axis, because my program is 2D. So, in this case: X=0, Y=5.

 

My question is: How can I translate this information to use on view.RotateCamera X-Y-Z, as I don't know which axis I have to rotate? For example: Depending of the position of my elements, sometimes Solid Edge camera X axis is pointing down, sometimes it's pointing right, etc...

 

Another example, if you rotate your view using your keyboard arrows, it will always rotate to the same direction, doesn't matter what is the current view X-Y-Z position. I wanna do the same, but using my mouse direction information.

 

I hope someone can clarify that for me. Sample codes are welcomed as well.

 

Thank you guys!

Josh.

 

9 REPLIES

Re: Rotate camera using the mouse

Josh,

 

you will probably use the GetCamera method to get the axis. Use the Up vector for rotations about the y-axis and the cross product of the target and up vector for the x-axis rotation.

Then you call RotateCamera with the computed rotation axis and a rotation angle based on some mapping from the mouse translation, e.g. 180 degrees when moving the mouse from one side to the other.

Re: Rotate camera using the mouse

[ Edited ]

Hi Martin, thanks for your reply!

 

Yes, I think that's the way to solve this problem, using the GetCamera information to do some calculations. But that's the point I'm stuck, I can't figure out which calculation I've to do.

 

For example, let's say I have this cube:

 

 

And let's say it's in this position (front face):

 


 

If I wanna rotate the cube to the right, in this case it's easy. Just need to rotate the Z axis:

 

RotateCamera(15, 0, 0, 0, 0, 0, 1);

 

Now let's say I have the cube in this position and I wanna rotate to the right as well:

 

 

var eye = new double[3];
var target = new double[3];
var up = new double[3];
var isPerspective = false;
double scale = 0;

 

view.GetCamera(out eye[0], out eye[1], out eye[2], out target[0], out target[1], out target[2], out up[0], out up[1], out up[2], out isPerspective, out scale);

 

var angle = 15;

var axisX = 0;

var axisY = 0;

var axisZ = 0;

 

// What should I do here?

 

view.RotateCamera(angle, 0, 0, 0, axisX, axisY, axisZ);

 

Thanks!

 

Re: Rotate camera using the mouse

To rotate to the right, you should rotate about the Up vector:

 

view.RotateCamera(angle, 0, 0, 0, up{0], up[1], up[2]);

 

If you want to rotate up/down, your axis should be the cross product between the target vector and the up vector:

 

axisX = target[1]*up[2] - target[2]*up[1];

axisY = target[2]*up[0] - target[0]*up[2];

axisZ = target[0]*up[1] - target[1]*up[0];

view.RotateCamera(angle, 0, 0, 0, axisX, axisY, axisZ);

 

Re: Rotate camera using the mouse

[ Edited ]

That's what I'm talking about! Martin, you the guy!

 

Please let me ask 2 more questions:

- The rotate left/right is perfect, but the rotate up is also slightly rotating to the right. Is that possible to rotate only to the top?

- If I have the following information coming from my mouse reading: X = 5, Y = 0, it means rotate right, I'm testing it using switch/case, to rotate for all directions, including diagonals. Is there a better way to calculate the axisX, axisY, axisZ using my X/Y rather than using switch/case?

 

Thanks a lot man.

 

 

Re: Rotate camera using the mouse

I don't know why the up/down rotation also rotates a liitle to the right. Maybe ensure that the target and up vector are normalized BEFORE computing the cross product.

I don't understand what you are doing in your code which leads to the second question. Can you provide some code?

Re: Rotate camera using the mouse

[ Edited ]

Hi Martin,

 

About the first question, I think it's normalized, isn't it? It rotates slightly to right when rotating up, and rotates left and rotating down. Here goes my code:

 

private static void RotateCamera(int x, int y)
{
   var eye = new double[3];
   var target = new double[3];
   var up = new double[3];
   var isPerspective = false;
   double scale = 0;

   view.GetCamera(out eye[0], out eye[1], out eye[2], out target[0], out target[1], out target[2], out up[0], out up[1], out up[2], out isPerspective, out scale);

   const int angle = 15;

   var axis = getAxis(x,y, target, up);
   view.RotateCamera(angle, 0, 0, 0, axis[0], axis[1], axis[2]);
}

 

private static double[] getAxis(int x, int y, double[] target, double[] up)
{
   var axis = new double[3];

   if (x == 0)
   {
      if (y == 0) // No rotation
      {

      } else if (y > 0) // Rotate up
      {
         axis[0] = target[1] * up[2] - target[2] * up[1];
         axis[1] = target[2] * up[0] - target[0] * up[2];
         axis[2] = target[0] * up[1] - target[1] * up[0];
      }
      else // y < 0 // Rotate down
      {
         axis[0] = (target[1] * up[2] - target[2] * up[1]) * -1;
         axis[1] = (target[2] * up[0] - target[0] * up[2]) * -1;
         axis[2] = (target[0] * up[1] - target[1] * up[0]) * -1;
      }
   }
   else if (x > 0)
   {
      if (y == 0) // Rotate right
      {
         axis[0] = up[0] * -1;
         axis[1] = up[1] * -1;
         axis[2] = up[2] * -1;
      }
      else if (y > 0) // Rotate right/up
      {
         // Rotate right
         axis[0] = up[0] * -1;
         axis[1] = up[1] * -1;
         axis[2] = up[2] * -1;

         // Rotate up
         axis[0] += target[1] * up[2] - target[2] * up[1];
         axis[1] += target[2] * up[0] - target[0] * up[2];
         axis[2] += target[0] * up[1] - target[1] * up[0];
      }
      else // y < 0 // Rotate right/down
      {
         // Rotate right
         axis[0] = up[0] * -1;
         axis[1] = up[1] * -1;
         axis[2] = up[2] * -1;

         // Rotate down
         axis[0] += (target[1] * up[2] - target[2] * up[1]) * -1;
         axis[1] += (target[2] * up[0] - target[0] * up[2]) * -1;
         axis[2] += (target[0] * up[1] - target[1] * up[0]) * -1;
      }
   }
   else // x < 0
   {
      if (y == 0) // Rotate left
      {
         axis[0] = up[0];
         axis[1] = up[1];
         axis[2] = up[2];
      }
      else if (y > 0) // Rotate left/up
      {
         // Rotate left
         axis[0] = up[0];
         axis[1] = up[1];
         axis[2] = up[2];

         // Rotate up
         axis[0] += target[1] * up[2] - target[2] * up[1];
         axis[1] += target[2] * up[0] - target[0] * up[2];
         axis[2] += target[0] * up[1] - target[1] * up[0];
      }
      else // y < 0 // Rotate left/down
      {
         // Rotate left
         axis[0] = up[0];
         axis[1] = up[1];
         axis[2] = up[2];

         // Rotate down
         axis[0] += (target[1] * up[2] - target[2] * up[1]) * -1;
         axis[1] += (target[2] * up[0] - target[0] * up[2]) * -1;
         axis[2] += (target[0] * up[1] - target[1] * up[0]) * -1;
      }
   }

   return axis;
}

 

// Usage example:

RotateCamera(0, 10); // Rotate up

RotateCamera(10,10); // Rotate diagonal up/right

RotateCamera(-5,0); // Rotate left

Re: Rotate camera using the mouse

I agree my getAxis method is really stupid, I'm sure there is a much better way to do it.
Solution
Solution
Accepted by topic author JoshBaumann
‎08-26-2015 04:32 AM

Re: Rotate camera using the mouse

Josh, I was misinterpreting the target and eye arguments, so the correct view direction is the difference between both. Here is some corrected code:

private void RotateCamera(SolidEdgeFramework.View pView, int x, int y)
{
  var eye = new double[3];
  var target = new double[3];
  var up = new double[3];
  var isPerspective = false;
  double scale = 0;

  pView.GetCamera(out eye[0], out eye[1], out eye[2], out target[0], out target[1], out target[2], out up[0], out up[1], out up[2], out isPerspective, out scale);

  const int angle = 15;

  // Compute the normalized view direction
  var viewDir = new double[3];
  viewDir[0] = target[0] - eye[0];
  viewDir[1] = target[1] - eye[1];
  viewDir[2] = target[2] - eye[2];
  double len = Math.Sqrt(viewDir[0] * viewDir[0] + viewDir[1] * viewDir[1] + viewDir[2] * viewDir[2]);
  if (len > 1.0E-5)
  {
    viewDir[0] /= len;
    viewDir[1] /= len;
    viewDir[2] /= len;
  }

  var axis = getAxis(x, y, viewDir, up);
  pView.RotateCamera(angle, 0, 0, 0, axis[0], axis[1], axis[2]);
}

private double[] getAxis(int x, int y, double[] viewDir, double[] up)
{
  var axis = new double[3];

  int sx = Math.Sign(x);
  int sy = Math.Sign(y);

  axis[0] = (viewDir[1] * up[2] - viewDir[2] * up[1]) * sy - up[0] * sx;
  axis[1] = (viewDir[2] * up[0] - viewDir[0] * up[2]) * sy - up[1] * sx;
  axis[2] = (viewDir[0] * up[1] - viewDir[1] * up[0]) * sy - up[2] * sx;

  return axis;
}

 

Re: Rotate camera using the mouse

Martin, you the guy! Problem solved. You're the best.
Many thanks!