I have got a player set up and I am trying to make an arm for my character. The shapes are all created using either PolygonShapes or CircleShapes and I have made it so it points towards the mouse but I want to change the the point of rotation from this:
to this:
(Please forgive my crude drawings)
Ok, so i used a revolute joint which allowed to me set an anchor elsewhere, however, how do i rotate it towards the mouse position as the applyTorque method uses torque instead of radians?
Related
I am writing a program that is supposed to display 3D point clouds. For this purpose, I am using the jMonkeyEngine. Unfortunately, I do not like the default camera behavior of jMonkey. Especially the mouse dragging and mouse wheel do not really do what I want. What I want is them to behave like in the pcd viewer of the PointCloudLibrary.
Mouse wheel: Should be faster, and the the effect of the turning directions should be switched.
Mouse dragging: In jMonkey it seems like mouse dragging changes the camera viewing direction in the world. I am not sure what exactly happens in the pcd viewer, but I believe the camera is moved through the world while fixating the centroid of the displayed point cloud.
How can I change the behavior of the camera to fullfil my wishes? :)
1.
In the simpleInit() method (where 100 is an abritrary number):
getFlyByCamera().setZoomSpeed(100);
getFlyByCamera().setDragToRotate(true);
Note, that zooming doesn't actually change the position of the camera, just the FOV.
2.
The normal behavior of the camera is to rotate around its own axis. By offseting the location of the camera as well, the effect you want can be achieved. In simpleUpdate():
cam.setLocation(cam.getDirection().negate().multLocal(cam.getLocation().length()));
I consider the answer to the second question a bit of a quick hack. But it does the trick.
I am new to Box2D (JBox2d in this case) and I am creating a wheel menu on an Android app.
I want to allow the user to select one menu item and the wheel should rotate automatically to the wanted section.
The wheel body is dynamic, attached by a revolute joint at its center to an anchor (static)
I am using a distance joint between the user tap location within my wheel and a static body located on top of my wheel.
My problem is with the settings of the joint. I can't figure out the combination of length/damping/frequency so I can have a fast pull with minimum oscillation at the end.
Also, if I pick one of the elements on the upper side of the weel, they stop at the right place. But if I tap one at the end, the joint doesn't respect the length of 0 I gave it and I end up with this :
If I use a length of 0, and dampingRatio of 1 and a frequencyHz of 0, the result is perfect but I have no animation : It goes instantaneously to the right position.
On iOS I did the same menu using UIKit Dynamics and I had a great result : https://www.dropbox.com/s/mb2i44geinw9yp6/iOS_wheel_rotation.mov?dl=0
Thanks in advance for any guidance.
I think the basic problem is with the type of the joint you're trying to use.
Distance Joint assumes that the distance between two connected points is constant (the basic assumptions of box2d joints in general, can bend this rule a bit, but still...).
Try using MouseJoint and just remember:
When you're creating the MouseJoint and attaching it to the body (so exactly when you're creating MouseJointDef), you specify a target which in this specific moment (AND ONLY THEN) means the part of the body in which you want to anchor the MouseJoint (pointing out once again - it's within this body!). So in your case this target should be indicating the touched part of your wheel.
When you're done with creating of the joint (so after you had called <World_Object>.createJoint(<your_joint>)) the target indicates the place you would like the previously set target(within this body) to be moved to (so this anchor at the top of the wheel).
So basically you should create your mouse joint on touch with code similar to this:
MouseJoint wheelJoint;
MouseJointDef mouseJointDef = new MouseJointDef();
mouseJointDef.bodyA = <something>;
mouseJointDef.bodyB = wheelBody;
mouseJointDef.target.set(0 + chosenWheelPositionOffsetX, 0 + chosenWheelPositionOffsetY);
mouseJointDef.target.addLocal(wheelCenterX, wheelCenterY);
mouseJointDef.dampingRatio = <chosen_value>;
mouseJointDef.frequencyHz = <chosen_value>;
mouseJointDef.maxForce = <chosen_value>;
wheelJoint = (MouseJoint) mWorld.createJoint(mouseJointDef);
and after that you should call
wheelJoint.setTarget(topAnchorX, topAnchorY);
Tweak <chosen_value>s so they make your view work exactly as intended.
I hope it's all clear, let me know if something isn't. Also just pls let me know if changing the joint type helps with your issues.
I'm trying to get the coordinates of the arcs (denoted in blue) (so that I can visually draw them [in Android path.drawArc()]) of any 2 (and eventually $n$) circles for the 'central' portion (denoted in red).
I have found this, but unfortunately I'm not at all mathematically minded!
I have coded something to find the intersection points... If that helps?
I see no path.drawArc(), only Canvas.drawArc, Path.addArc and Path.arcTo. All of these need a RectF oval argument which I would guess describes the size and position of the circle. So if you want to draw the right boundary of the lens-shaped area, this belongs to the boundary of the left circle, so you'd set oval to the bounding box of the left circle. Then you need two angles, startAngle and sweepAngle. You can get them from Math.atan2(y, x), where (x, y) is the vector which points from the center of the circle to one of the points of intersection. So knowing the points of intersection will be very useful. You'd use one to compute the start angle and the other the end angle of the first arc. The sweep angle is simply the difference between end and start. For the second arc, reverse the roles of start and end and you'll obtain an essentially closed path, although you might have to issue an explicit close call to make that closing explicit.
An alternative approach would be using Path.op(circle1, circle2, Path.Op.INTERSECT). circle1 and circle2 could be formed by Path.addCircle. This approach would delegate the whole intersection math to the Framework, but it does require a recent API (namely API level 19), so it will not work on older devices.
All of the above is untested, from reading the reference and knowing how similar frameworks behave.
In my first libgdx 3D game i now switched from createBox to createRect, to create only the visible faces (if a wall is on the left side of another wall, its right face is not visible...). I am creating 4 models:
frontFace
backFace
rightFace
leftFace
They are almost drawn how they actually should.
But there is one big issue: The side faces are only visible if i look in the positive z-Direction.
If i look the other side (negative z-Direction), they don't draw. The front and back faces only draw, if i look to them in negative x-Direction.
Has this something to do with the normals? I have set them to:
normal.x = 0;
normal.y = 1;
normal.z = 0;
Is that the error? How should i set the normals? What do they stand for? I have some basic idea about normal mapping for lighting, is that the same?
Important note: I have disabled backface culling, but it did not make any difference. View frustum culling is turned on. If any more informations are needed please post a comment and i will add them as soon as possible. Thanks
Perhaps not directly related, but still important to note: don't use createRect or createBox for anything other than debugging/testing. Instead combine multiple shapes into a single model/node/part. Or even better, use a modeling application where possible.
You didn't specify how you disabled backface culling. But keep in mind that you should not change the opengl state outside the shader/rendercontext (doing so will result in unpredicted behavior). To disable backface culling you can either specify it using the material attribute IntAttribute.CullFace (see: https://github.com/libgdx/libgdx/wiki/Material-and-environment#wiki-intattribute), the DefaultShader (or default ModelBatch) Config defaultCullFace member (see http://libgdx.badlogicgames.com/nightlies/docs/api/com/badlogic/gdx/graphics/g3d/shaders/DefaultShader.Config.html#defaultCullFace) or the (deprecated) static DefaultShader#defaultCullFace member (see http://libgdx.badlogicgames.com/nightlies/docs/api/com/badlogic/gdx/graphics/g3d/shaders/DefaultShader.html#defaultCullFace).
Whether a face is front or back is based on the vertex winding. Or in other words: the order in which you provide the corners of the rectangle is used to decide which side is front and which side is back. If you use one of the rect methods, you'll notice the arguments have either the 00, 01, 10 or 11 suffix. Here, when looking at the face, 00 is lower-left, 01 upper-left, 11 is upper-right and 10 is lower-right.
For a rectangle, it's normal is the perpendicular facing outwards the rectangle. For example if you have a rectangle on XZ plane with it front face on the top, then its normal is X=0,Y=1,Z=0. If its front face it facing the bottom, then its normal is X=0,Y=-1,Z=0. Likewise if you have a rectangle on XY plane, its normal is either X=0,Y=0,Z=1 or X=0,Y=0,Z=-1. Note that the normal is not used for face culling, it's most commonly used for lighting etc. Specifying an incorrect/opposite normal will not cause the face to be culled (it might cause incorrect/black lighting though).
For your purpose I'd recommend you to use Decal class. Decals are bitmap sprites that exist in a 3D scene. This article is about using of decals in LibGDX. I hope it is what you wanted.
I am trying to locate a point in 3D space relative to the origin (0,0,0). I have 3 values to calculate this point with: a rotation in degrees about both the x and y axis as well as a "view distance". Using these values, how can I locate a point in 3D space relative to the origin? I have tried using basic trigonometric functions, but the results seem to be random. The image below gives a visual as to what needs to be done.
'vd' being the "view distance"
'c' being a value holder
'(x,y,z)' being the coordinate I am trying to find
What I am trying to do is find the point a player is looking at a certain distance away (find a point in the direct line of sight of the player out a certain distance). Keep in mind, the rotations about the x and y axis are constantly changing, but the view distance remains the same. If anyone has any suggestions, methods of how to do this, or needs clarification, please comment/answer below.
I am doing this in LWJGL, and the code I am using is as follows:
float c = (float)(Math.cos(Math.toRadians(A00.rot.y)) * view_distance);
locate.y = (float)(Math.sin(Math.toRadians(rot.y)) * view_distance);
locate.x = (float)(Math.cos(Math.toRadians(rot.x)) * c);
locate.z = (float)(Math.sin(Math.toRadians(rot.x)) * c);
EDIT:
My issue is that this current setup does NOT work for some reason. The math seems legitimate to me, but I must have something wrong somewhere in the actual setup of the graph..
I suggest looking up quaternions. No need to fully understand how they work. You can find ready made classes for java available on the internet as well. Quaternions allow you to represent a rotation in 3D space.
What I would then do, is to start with a vector representing the direction pointing forwards from the origin, and apply the same rotation that the player currently has to it. Now it is pointing in the same direction as the player. Now if you take the player's current point, and the direction vector we now have a ray describing where the player is looking at.
I suggest this link for further information on quaternions. They may look complex but, as I said, you don't need to fully understand how and why they work to be able to use them. Just copy the formulae and learn how they are used. Once you figure out how to use them, they make 3d rotations really easy.
http://content.gpwiki.org/index.php/OpenGL:Tutorials:Using_Quaternions_to_represent_rotation