Trying to move 2D object with accelerometer - unity3d

I want to be able to direct my player when he is in the air. So I maded a method called CheckTilt() which is called in FixedUpdate() which is basically checking to see if the tablet has been moved in the x direction. The condition inside of CheckTilt() is based on a bool variable called isGrounded which basically is false when the player is airborne and true otherwise that part works fine. However, I cannot get the player to move based on the accelerometer. Here is my method:
public void checkTilt()
{
if (!isGrounded)
{
float tiltSpeed = 10.0f;
float x = Input.acceleration.x;
Vector2 tilted = new Vector2(x, 0);
myRigidBody.AddForce(tilted * tiltSpeed * Time.deltaTime);
}
}
Other Info: I'm building this for android device, and have tested it with the unity remote.

Fortunately the answer is just that nothing like that works with the Unity remote - you must build to try it.
Re your other question: it's almost impossible to guess the "parity". you have to try it, and if that is not right, just multiply by -1f. (What I do is include a UI button on screen, which, swaps the parity - but really just build twice until you get it!)
"I'm still not getting any movement when moved..."
it's an incredible pain in the ass getting the axes right. YES, on fact, it is 100% a fact that you will need to read all 3 axis, even if a 2D game.
Don't forget that
Apple STUPIDLY USE Z-BACKWARDS orientation ...
because they are utter idiots who have never worked in the game industry.
DOCO
But you will almost certainly have to do this:
You are familiar with using the Canvas / UI system, right? if not tell me.
1) make a canvas and add three Text fields
2) do this
public Text showX;
public Text showY;
public Text showZ;
and then
showX.text = yourAccelerometer.x.ToString("f2");
.. same for the others ..
It seems like a pain but I assure, it's the ONLY WAY to figure out what the hell is going on.

Related

Stuck Implementing A Way To Rotate A Rigidbody Towards A Point With Rigidbody.AddTorque

So I am kinda stuck on what to do now because as I said I am trying to use Rigidbody.AddTorque to rotate a rigid body towards a certain point, which I was going to use to align a player with a gravitational pull so they can be upright. I have got the input part of the code, I just don't have a way to rotate the player to align with it, without violating the laws of physics with Quaternion.FromToRotation and messing with my character controller too, which I am trying to make entirely physics based rotation wise too to avoid any other problems.
I have experimented with a couple of methods, first I tried adapting my character controller code which used Rigidbody.AddForce to move the player and also dampening unwanted movements, as Rigidbody.AddTorque is basically Rigidbody.AddForce but for rotations, however, it was too weak and just flopping around when I tried it, here's the code for the character controller for calculating the force needed for one axes:
if(projected_speed.x*speed == relative_v.x)
{
applied_speed.x = 0f;
}
else if(Mathf.Sign(projected_speed.x)== -1)
{
applied_speed.x = relative_v.x - Mathf.Abs(projected_speed.x*speed);
}
else if (Mathf.Sign(projected_speed.x) == 1)
{
applied_speed.x = projected_speed.x*speed - relative_v.x;
}
Where projected_speed is the speed the controller wants to be at,relative_v is the relative velocity, and applied_speed is the speed that will be actually applied in Rigidbody.AddForce.
Anyways so maybe I didn't use enough force, as the player is under a gravitational pull, but that would have probably made it flip out or something, anyways so the second thing I tried was a PID controller, and I managed to find a page which explains it pretty well, sadly don't have the link anymore, but when I tried this because you have to tune it, I was stuck doing it, and it just wasn't able to do anything and was just rolling around the floor and sometimes spinning, probably as it couldn't cope with gravity, so that didn't work, so does anyone know how I could finally do this and make my character able to right themselves according to gravity?
Sorry for not indicating that my issue is solved, click here for the answer, credit to Ruzihm.

Unity returning incorrect transform.rotation

In the endless running game I am creating, there is a mechanic called the jump pad. It basically takes in the change in the player's position since the last frame and converts that to an angle. Then it uses that along with the transform.rotation of the jump pad to figure out which direction to move the player in, as if it was actually bouncing off of it.
This algorithm would've been working perfectly except for one problem: Unity was reading an incorrect transform.rotation. When the jump pad was rotated 45 degrees, it read 21.92615 (after being multiplied with Mathf.Rad2Deg.) When the jump pad was rotated 20 degrees, it read 9.949307.
At first I thought it was being multiplied by an unknown constant for some reason, but after checking it through the Calculator app I found this to be not exactly the case. After a bit more experimenting I found that the possible "unknown constants", while close enough together, did seem to have a range from around 2 to around 2.1. And while I don't have the faintest clue how this is happening, it does seem to be remarkably consistent.
So my question is: what is this problem I am facing and is there any way I can fix it? Brief side note: I know this is not some other problem with the code because I stripped it down to the bare minimum:
public void OnTriggerEnter2D(Collider2D collision){
Debug.Log(collision.gameObject.transform.rotation.z * Mathf.Rad2Deg);
}
OK. After looking up the scripting API for transform.rotation and messing around a bit, I discovered that it was returning the z value of a quaternion and fixed it using the .ToEulerAngles() call.

Unity3D forcing object to a given orientation with minimum artificial effect

In my board game, the points are given by throwing 7 sea-shells cowry shell. These shells are dropped onto a sphere in Unity so they get rolled over randomly to different places. Once the rigidbody.isSleeping() returns true, I do a Raycast(from the belly side downwards) to figure out the orientation of the shell. If it is NOT a hit we know the shells belly is turned upside which means a point.
All is good and very realistic when in single player mode. Reason is I just activate the gravity of the shells and they dropped on to sphere, gets rolled randomly and when stopped i get the marks as stated above.
Now the problem is I am making the game multiplayer. In this case, I sent the randomly generated marks from the server and client will have to animate the shells to represent the marks. For example, if server send 3, out of 7 shells, 3 should have it's belly turned upside.
Trying to do this has been a major problem for me. I tried to transform.Rotate() when the velocity is reduced but it was not very reliable and sometimes acts crazy. Rotating afterrigidbody.isSleeping() works but very unrealistic.
I know I am trying to defy physics here, but there may be some ways to achieve what I want with minimum artificial effect.
I actually need some ideas.
Update - 1
After infor I receive below, I did found some information here, some advanced stuff here. Since the latter link had some advanced stuff, I wanted to start small. So I followed the first link and did below test.
I recorded the position, rotation & velocity of the sea shell with autosimulation enabled and logged them to a file. Then i used the Physics.Simulate() for the same scenario and logged the same.
Comparing the two tells me that data in both cases are kind of similar. So seems like for my requirements I need to simulate the sea-shell drop and then apply that sequence to the actual object.
Now my problem is how can I apply the results of physics.simulate() results (position, rotation, velocity etc..) to the actual sea-shell so the animation can be seen. If I set the positions to my gameobject within the simulation loop nothing happens.
public void Simulate()
{
rbdy = GetComponent<Rigidbody>();
rbdy.AddForce(new Vector3(0f, 0f, 10f));
rbdy.useGravity = true;
rbdy.mass = 1f;
//Simulate where it will be in 5 seconds
int i = 0;
while (simulateTime >= Time.fixedDeltaTime)
{
simulateTime -= Time.fixedDeltaTime;
Debug.Log($"position: {rbdy.position.ToString()} rotation: {rbdy.rotation.ToString()} Velocity {rbdy.velocity.magnitude}");
gameObject.transform.position = rbdy.position;
Physics.Simulate(Time.fixedDeltaTime);
}
}
So, how can I get this simulated data applied to actual gameobject in the scene?
Assume Physics are deterministic, just set the velocity and position and let it simulate on each client. Output should be the same. If the output differs slighly, you could adjust it and it may be only barely noticable.
Physics.simulate may be interesting to read, even if it's kind of the opposite of what you want.
You can throw in the client, record the steps in realtime or using physics.simulate (see point 2) and transmit the animation data as binary - then use it in the other clients to play the animation.

Wheel Collider Unity: after adding torque the vehicle starts moving sideways

I really killed few hours to try to fix this, Googling for a solution, but I could not.
I've got a vehicle, it's a go-cart, so there are no suspensions (technically there are, but the values are close to 0, to simulate the tires). The vehicle has a rigid body attached and the child object contains the 4 wheel colliders (and the model itself), as can be seen here:
https://dl.dropboxusercontent.com/u/76599014/sxc/Clipboard01.jpg
For testing, I added a short script to make the vehicle move. It's in the GameObject called "gokart":
public class carControler : MonoBehaviour {
public WheelCollider fr, fl, rr, rl;
public float performance = 50f;
void FixedUpdate () {
throttle();
}
public void throttle() {
this.rl.motorTorque = this.performance;
this.rr.motorTorque = this.performance;
} }
What happens is: the rear wheels start to rotate, as intended, but the vehicle starts moving sideways slowly. The movement speed depends on the torque amount (the wheel rotation in this case). There is no movement forward, so this is not the bug, where when you are standing on a flat surface you are drifting on the sides.
Any ideas? If you need a video or a GIF (I have to figure out how to make one) of the movement, I'll be glad to provide one.
I think you should try and apply 0 brake torque to the front wheels while applying motor torque to the rear wheels.
public void throttle() {
this.rl.motorTorque = this.performance;
this.rr.motorTorque = this.performance;
this.fr.brakeTorque = 0f;
this.fl.brakeTorque = 0f;
}
That being said, anything could go wrong if the Rigidbody/wheelcolliders aren't set up correctly. Unity's wheel colliders can be difficult to set up and work with. Unity changed the physics in Unity 5 so most documentations are outdated.
I found this very good short document that was made by unity: http://unity3d.com/profiles/unity3d/themes/unity/resources/downloads/beta/unity-5.0-user-guide.pdf
It highlights the changes that was made to unity 5 and at the end of page 5 you can find a section that explains how to set up a car. I have tried it about a month ago in a new unity project and it worked. the instructions are clear so try this tutorial out and I hope it will help.
Regards
Not having the image available I'm not a totally sure about the situation but my assumption based on your description is you should try increasing the sideways friction and tweak the forward friction a little bit according to your taste. You have to increase the sideways friction anyways as you are making a go-cart. As far as I know, most arcadey go-carts don't drift and behave a lot different from regular racing cars.
Hope that will solve the problem.

Modifying Rotation w/ GamePad

I'd like to modify the rotation of the camera object via a gamepad. I have code that works in the editor, but doesn't work on iOS. (However, it looks like it's working but being pushed back on the 2nd frame by the VROne code).
I was able to get this working w/ the Rift, but haven't been able to figure it out with VROne yet. For the Rift I added an "offset" to the rotation that was changed by the GamePad joystick. The offset was calculated into the final rotation that also includes the players look direction.
Any idea what part of the code I'd modify to get this properly working with the VROne sdk?
If you want to use your own GameRotation angles (from the gamepad), the values might be getting overwritten by the integrated HeadTracking. Have you tried disabling the VR Head Tracking Script, in the VROneSDKHead object?
The HeadTracking angles are dealt with in the HeadTrackingIOS class, which calls the native static library. You can try adding your gamepad offset to the Quaternion returned on line 43.
Hope this helps, let us know if it worked!
EDIT: Nevermind, the below code works in the editor, but on the iOS device the camera is still forced ahead. I'll try the other answer.
Cool -- that may work, the above answer. It sounds like what I was looking for.
However, per a suggestion on the Unity forum, I implemented this solution: First I made the VROne Object a child of another empty game object, with the localPosition 0,0,0.
On rotation, I rotate the parent, but first make sure the parent is the same position of the child and then the child localPosition is 0,0,0 - -right now the child is doing the physical movement, and the parent does the rotation. I'm not sure if moving the character controller to the parent would work or make something else funky in the SDK, but this seems to work for now.
if (RightStickX.Value != 0)
{
transform.position = childObject.transform.position;
childObject.transform.localPosition = Vector3(0,0,0);
transform.eulerAngles.y += RightStickX.Value * rotationSpeed * Time.deltaTime;
}
Just in case this would help someone, I was able to solve it in a much simpler way.
The VrOneSDK object is a child of the object that I am rotating with my gamepad.
and then in 'vrHeadTracking.cs' I simply changed
transform.rotation = Quaternion.Inverse(initialRotation) * rot;
to
transform.localRotation = Quaternion.Inverse(initialRotation) * rot;
that way the head tracking is relative to my parent object's rotation.