Changing a gameobject's rotation from script - c#

I have a gameobject and position and rotation are set originally as
mainModel.transform.position = new Vector3 (-3.25f,-0.2f,0.1f);
mainModel.transform.rotation = Quaternion.Euler (0,95,0);
Then I spin the model in swiping as
f_difX = Mathf.Abs(f_lastX - Input.GetAxis ("Mouse X"));
if (f_lastX < Input.GetAxis ("Mouse X"))
{
i_direction = -1;
if (yPos > (Screen.height*3 / 4)) {
Swinginfo.SetActive (true);
Swinginfo2.SetActive (false);
} else if(yPos < (Screen.height*3 / 4) && yPos > (Screen.height / 4)){
m_CurrentObj.transform.Rotate(Vector3.up, -f_difX);
}
}
if (f_lastX > Input.GetAxis ("Mouse X"))
{
i_direction = 1;
if (yPos > (Screen.height*3 / 4)) {
Swinginfo.SetActive (false);
Swinginfo2.SetActive (true);
} else if(yPos < (Screen.height*3 / 4) && yPos > (Screen.height / 4)){
m_CurrentObj.transform.Rotate(Vector3.up, f_difX);
}
}
f_lastX = -Input.GetAxis ("Mouse X")*1.5f;
The model spin.
When I want to set its initial position and rotation, I set as
mainModel.transform.position = new Vector3 (-3.25f,-0.2f,0.1f);
mainModel.transform.rotation = Quaternion.Euler (0,95,0);
But it doesn't change back to its initial setting.
How can I have its initial position and rotation?
EDIT:
Debug.Log ("RangeViewScript.index "+RangeViewScript.index);
if (RangeViewScript.index == 0) {//pass
mainModel.transform.position = new Vector3 (-3.25f,-0.2f,0);
mainModel.transform.rotation = Quaternion.Euler (0,95,0);
Debug.Log ("Reset 0 is called");
}else if (RangeViewScript.index == 1) {//cheapshot
mainModel.transform.position = new Vector3 (-2.6f,-0.2f,0);
mainModel.transform.rotation = Quaternion.Euler (0,105,0);
Debug.Log ("Reset 1 is called");
}else if (RangeViewScript.index == 2) {//fullswing driver
mainModel.transform.position = new Vector3 (-5.0f,-0.2f,0);
mainModel.transform.rotation = Quaternion.Euler (0,90,0);
Debug.Log ("Reset 2 is called");
}else if (RangeViewScript.index == 3) {//putting
mainModel.transform.position = new Vector3 (-1.9f,-0.2f,0.1f);
mainModel.transform.rotation = Quaternion.Euler (0,95,0);
Debug.Log ("Reset 3 is called");
}else if (RangeViewScript.index == 4) {//shoot
mainModel.transform.position = new Vector3 (-2.75f,-0.2f,0.69f);
mainModel.transform.rotation = Quaternion.Euler (0,100,0);
Debug.Log ("Reset 4 is called");
}else if (RangeViewScript.index == 5) {//shoot
mainModel.transform.position = new Vector3 (-3.25f,-0.2f,0.1f);
mainModel.transform.rotation = Quaternion.Euler (0,95,0);
Debug.Log ("Reset 5 is called");
}

Related

Unity transform.localScale script change all the gameObject that had the script

I have an assignment that to create a puzzle game. I have made an pretty good progress so far. Currently, I have made a script that change grabbed object size with E and Q and I assign it to every object that the player can grab.
The problem is that when I press Q and E, its changed every object in the screen including the grabbed one.
How can I fix it? Please help.
Here the code:
using UnityEngine;
using System.Collections;
[RequireComponent(typeof(MeshCollider))]
public class MouseDragAndResizing: MonoBehaviour
{
private Vector3 screenPoint;
private Vector3 offset;
void OnMouseDown()
{
screenPoint = Camera.main.WorldToScreenPoint(gameObject.transform.position);
offset = gameObject.transform.position - Camera.main.ScreenToWorldPoint(new Vector3(Input.mousePosition.x, Input.mousePosition.y, screenPoint.z));
}
void OnMouseDrag()
{
Vector3 curScreenPoint = new Vector3(Input.mousePosition.x, Input.mousePosition.y, screenPoint.z);
Vector3 curPosition = Camera.main.ScreenToWorldPoint(curScreenPoint) + offset;
transform.position = curPosition;
}
void Update()
{
if(Input.GetKeyDown(KeyCode.E) && transform.localScale.x < 3 && transform.localScale.y < 3 && transform.localScale.z < 3)
{
transform.localScale = transform.localScale + new Vector3(0.5f, 0.5f, 0.5f);
}
if (Input.GetKeyDown(KeyCode.Q) && transform.localScale.x > 0.5 && transform.localScale.y > 0.5 && transform.localScale.z > 0.5)
{
transform.localScale = transform.localScale + new Vector3(-0.5f, -0.5f, -0.5f);
}
else if (transform.localScale.x < 0.5 && transform.localScale.y < 0.5 && transform.localScale.z < 0.5)
{
transform.localScale = Vector3.zero;
}
}
}
The problem that you don't check if your piece is selected or not, so every piece moves in update
I consider to change your code to smth like this to know which piece are you actually trying to move and drag
using UnityEngine;
using System.Collections;
[RequireComponent(typeof(MeshCollider))]
public class MouseDragAndResizing: MonoBehaviour
{
private Vector3 screenPoint;
private Vector3 offset;
private bool selected;
void OnMouseDown()
{
screenPoint = Camera.main.WorldToScreenPoint(gameObject.transform.position);
offset = gameObject.transform.position - Camera.main.ScreenToWorldPoint(new Vector3(Input.mousePosition.x, Input.mousePosition.y, screenPoint.z));
selected = true;
}
void OnMouseUp
{
selected = false;
}
void OnMouseDrag()
{
Vector3 curScreenPoint = new Vector3(Input.mousePosition.x, Input.mousePosition.y, screenPoint.z);
Vector3 curPosition = Camera.main.ScreenToWorldPoint(curScreenPoint) + offset;
transform.position = curPosition;
}
void Update()
{
if (!selected){
return;
}
if(Input.GetKeyDown(KeyCode.E) && transform.localScale.x < 3 && transform.localScale.y < 3 && transform.localScale.z < 3)
{
transform.localScale = transform.localScale + new Vector3(0.5f, 0.5f, 0.5f);
}
if (Input.GetKeyDown(KeyCode.Q) && transform.localScale.x > 0.5 && transform.localScale.y > 0.5 && transform.localScale.z > 0.5)
{
transform.localScale = transform.localScale + new Vector3(-0.5f, -0.5f, -0.5f);
}
else if (transform.localScale.x < 0.5 && transform.localScale.y < 0.5 && transform.localScale.z < 0.5)
{
transform.localScale = Vector3.zero;
}
}
}

How to limit the camera on a isometric 2D game

I'm developing a 2D isometric game just like Age of Empires 2, TTD, Into the Breach, and so on. I'm using Unity and C#
Relevant fact: i'm using a Isometric Tilemap
I want the camera limits to stay aligned with the borders of the map just like the games cited above but i'm having difficulty and i have spent so much time on this that i start to question myself if it's worth to use Isometric Tilemap or do the usual approach and just make a regular 2D game with the camera rotated.
And this is my first question: does Isometric Tilemap really worth or usual approach is better (non-isometric 2D game with rotated camera)? If so, how to do that in Unity?
Despite that,the code i've implemented follow below but it have two bugs:
Camera get stuck on firstBase and thirdBase if the user press right/left key and up/down arow keys
If the camera is moving on the border it may escape it
void Start(){
CameraMovement_Limits();
}
void CameraMovement_Limits(){
Vector3 gridOrigin = tilemapFloor.GetCellCenterWorld(tilemapFloor.origin);
float gridHypotenuse = ((tilemapFloor.size.x - 1) * tilemapFloor.cellSize.y);
homePlate = gridOrigin + new Vector3(0, 0, -10);
firstBase = gridOrigin + new Vector3(gridHypotenuse, gridHypotenuse/2, -10);
secondBase = gridOrigin + new Vector3(0, gridHypotenuse, -10);
thirdBase = gridOrigin + new Vector3(-gridHypotenuse, gridHypotenuse/2, -10);
}
void Update(){
CameraDiagonalMovement();
}
bool CheckCameraPosition(Vector2 p1, Vector2 p2, Vector2 pos){
//This is what this function do:
//find the linear equation for the line formed by 'p1' and 'p2' coordinates
//insert 'pos' coordinate on the equation and stores the result in 'ind'
//if 'ind' is positive, it means that 'pos' is above the line
//if its negative, its above
//if its zero, its on the line
//resuming, this funtion tells if 'pos' is above or below a line formet by 'p1' and 'p2'
float a = (p1.y - p2.y) / (p1.x - p2.x);
float ind = pos.y - p2.y - (a * (pos.x - p2.x));
return ind >= 0;
}
void CameraDiagonalMovement(){
Vector3 vecZero = Vector2.zero;
camPos = (Vector2)transform.position;
//Going to the left
if(Input.GetAxis("Vertical") < 0){
if(CheckCameraPosition(homePlate, thirdBase, camPos) && CheckCameraPosition(homePlate, firstBase, camPos)){
vecZero.y = Input.GetAxis("Vertical");
}else if(!CheckCameraPosition(homePlate, thirdBase, camPos) && CheckCameraPosition(homePlate, firstBase, camPos)){
vecZero.x = Input.GetAxis("Vertical") * .66f * -1;
vecZero.y = Input.GetAxis("Vertical") * .33f;
}else if(CheckCameraPosition(homePlate, thirdBase, camPos) && !CheckCameraPosition(homePlate, firstBase, camPos)){
vecZero.x = Input.GetAxis("Vertical") * .66f;
vecZero.y = Input.GetAxis("Vertical") * .33f;
}
}
//Going to the right
if(Input.GetAxis("Vertical") > 0){
if(!CheckCameraPosition(secondBase, thirdBase, camPos) && !CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.y = Input.GetAxis("Vertical");
}else if(CheckCameraPosition(secondBase, thirdBase, camPos) && !CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.x = Input.GetAxis("Vertical") * .66f;
vecZero.y = Input.GetAxis("Vertical") * .33f;
}else if(!CheckCameraPosition(secondBase, thirdBase, camPos) && CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.x = Input.GetAxis("Vertical") * .66f * -1;
vecZero.y = Input.GetAxis("Vertical") * .33f;
}
}
//Going down
if(Input.GetAxis("Horizontal") < 0){
if(CheckCameraPosition(homePlate, thirdBase, camPos) && !CheckCameraPosition(secondBase, thirdBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal");
}else if(!CheckCameraPosition(homePlate, thirdBase, camPos) && !CheckCameraPosition(secondBase, thirdBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal") * .66f;
vecZero.y = Input.GetAxis("Horizontal") * .33f * -1;
}else if(CheckCameraPosition(homePlate, thirdBase, camPos) && CheckCameraPosition(secondBase, thirdBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal") * .66f;
vecZero.y = Input.GetAxis("Horizontal") * .33f;
}
}
//Going up
if(Input.GetAxis("Horizontal") > 0){
if(CheckCameraPosition(homePlate, firstBase, camPos) && !CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal");
}else if(CheckCameraPosition(homePlate, firstBase, camPos) && CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal") * .66f;
vecZero.y = Input.GetAxis("Horizontal") * .33f * -1;
}else if(!CheckCameraPosition(homePlate, firstBase, camPos) && !CheckCameraPosition(firstBase, secondBase, camPos)){
vecZero.x = Input.GetAxis("Horizontal") * .66f;
vecZero.y = Input.GetAxis("Horizontal") * .33f;
}
}
Vector3 newPos = new Vector3(vecZero.x, vecZero.y, 0);
transform.position += newPos * velocity * Time.deltaTime;
}

Car control with Swipe(including No Physics)

I want to make a code with endless 3d car game, car control by swipe left and right. without using any physics.
info.
3-lane,specific lane center (9,0,car z position),(0,0,car z position),(-9,0,car z position).
I do swipe control and move swipe control but not good.
public class playercontrol: MonoBehaviour {
public void Update() {
playera.transform.Translate((Vector3.forward * speed * Time.deltaTime));
Debug.Log("speed" + speed);
if (check == false) {
if (Input.GetMouseButtonDown(0)) {
Debug.Log("left button");
firstPressPos = new Vector2(Input.mousePosition.x, Input.mousePosition.y);
}
if (Input.GetMouseButtonUp(0)) {
secondPressPos = new Vector2(Input.mousePosition.x, Input.mousePosition.y);
currentSwipe = new Vector2(secondPressPos.x - firstPressPos.x, secondPressPos.y - firstPressPos.y);
currentSwipe.Normalize();
//swipe left
if (currentSwipe.x < -1.0 f && currentSwipe.y > -0.5 f && currentSwipe.y < 0.5 f) {
Debug.Log("left swipe");
if (transform.position.x > -9 f) {
spos = transform.position;
Debug.Log("spos" + spos);
endpos = new Vector3(transform.position.x - 9 f, transform.position.y, transform.position.z + ((speed * 2) / 20));
Debug.Log("speed......... ......." + ((speed * 5) / 20));
transform.rotation = Quaternion.Euler(0, -10.0 f, 0);
check = true;
//endpos * (Time.deltaTime*0.5f);
// Time.timeScale = 0.5f;
// to.rotation = Quaternion.Euler (0, 0, 0);
}
}
//swipe right
if (currentSwipe.x > 1.0 f && currentSwipe.y > -0.5 f && currentSwipe.y < 0.5 f) {
Debug.Log("right swipe");
if (transform.position.x < 9 f) {
Debug.Log("spos1" + spos);
spos = transform.position;
endpos = new Vector3(transform.position.x + 9 f, transform.position.y, transform.position.z + ((speed * 2) / 20));
Debug.Log("speed1......... ......." + ((speed * 5) / 20));
transform.rotation = Quaternion.Euler(0, 10.0 f, 0);
check = true;
// Time.timeScale = 0.5f;
// to.rotation = Quaternion.Euler (0, 0, 0);
}
}
}
}
if (check == true) {
time += 10 * Time.deltaTime;
transform.position = Vector3.Lerp(spos, endpos, time);
// transform.rotation = Quaternion.Lerp (from.rotation, to.rotation, time);
if (time > 1) {
transform.rotation = Quaternion.Euler(0, 0, 0);
//Time.timeScale = 1.0f;
//playera.transform.Rotate (0, 0, 0);
//transform.Rotate (0, 0, 0);
check = false;
time = 0;
}
}
}
}

How to create Unity 2D enemy AI varying directional Animation?

So basically what i am trying to do is create an animation script that does not just take simple direction like Up(0,1),Down(0,-1),Left(-1,0),Right(1,0)(Those numbers being vectors) but to have range of directions for to fill in the gap between those directions and play the more dominant direction Up,Down,Left,Right.
So each quarter section below to be set to an animation.
I have created a few scripts to try and achieve this i came up with one that wasn't perfect but it did work when dragging the enemies around in the scene editor while the game was running. When using their movements scripts for their movement it did not work. The animation script is below and underneath that how i move the enemies.
Below would be how i calculate the direction the enemy was moving:
IEnumerator directionFinder()
{
// while (true)
//{
Vector3 previousPosition = transform.position;
yield return new WaitForSeconds(1/10);
currentPosition = transform.position;
currentPosition.x = currentPosition.x - previousPosition.x;
currentPosition.y = currentPosition.y - previousPosition.y;
currentPosition.z = 0f;
angle = (Mathf.Atan2(currentPosition.y, currentPosition.x) * Mathf.Rad2Deg);
if(angle < 0)
{
angle = Mathf.Abs(angle) + 180;
}
// }
}
Then this is what calculated which animation to use:
void animationDirection()
{
if (angle == 0)
{
anim.SetInteger("Move", currentAnim);
}
if (angle > 45 && angle <135)//W
{
anim.SetInteger("Move", 1);
currentAnim = 1;
}
else if (angle > 135 && angle < 225)//A
{
anim.SetInteger("Move", 2);
currentAnim = 2;
}
else if (angle > 225 && angle < 315)//S
{
anim.SetInteger("Move", 3);
currentAnim = 3;
}
else if((angle < 45 && angle >= 0) || (angle > 315 && angle <= 0))//D
{
anim.SetInteger("Move", 4);
currentAnim = 4;
}
}
This using the code below it would move to the waypoint that was selected via the rest of my code that would just loop through a set of waypoints changing the waypoint when it arrived at one.
transform.position = Vector2.MoveTowards(transform.position, waypoints[waypointNUmber].transform.position, speed * Time.deltaTime);
Below I tried another way but it did not work and created weird buggy animations:
IEnumerator directionalAnimation()
{
while (true)
{
Debug.Log("working");
Vector2 previousPosition = transform.position;
yield return new WaitForSeconds(1/10);
Vector2 currentPosition = transform.position;
Vector2 direction = (previousPosition - currentPosition).normalized;
float moveX = direction.x;
float moveY = direction.y;
if (moveX < 0)
{
moveXNegative = true;
moveX = Mathf.Abs(moveX);
}
if (moveY < 0)
{
moveYNegative = true;
moveY = Mathf.Abs(moveY);
}
if (direction.magnitude != 0)
{
if (moveX > moveY)
{
if (moveXNegative)
{
//left
Walking = true;
anim.SetInteger("Move", 2);
moveYNegative = false;
}
else
{
//Right
Walking = true;
anim.SetInteger("Move", 4);
moveYNegative = false;
}
}
else if (moveY > moveX)
{
if (moveYNegative)
{
//Down
Walking = true;
anim.SetInteger("Move", 3);
}
else
{
//Up
Walking = true;
anim.SetInteger("Move", 1);
}
}
}
else
{
source.Pause();
Walking = false;
}
if (Walking)
{
source.UnPause();
}
}
}

Stopping player from spamming movement keys which causes glitches

I wrote a script for the player movement in c#. Whenever the player presses A or D, it moves him/her to the left or right by 12 units and when the player presses W or S, it moves him/her up or down by 12 units. My script works fine, but if a person starts to spam all of the keys at once, it glitches out and the player object is not in line with the level anymore. I want to have the script check if there a movement is currently happening before executing the movement on the keypress. Here is my script:
void Update () {
transform.Translate(Vector3.forward * ForwardSpeed * Time.deltaTime);
if (Input.GetKeyDown (KeyCode.A) && side > maxSideLeft) {
MoveObjectTo(this.transform, new Vector3(this.transform.position.x - 12, this.transform.position.y, this.transform.position.z + 10), movementSpeed);
side -= 1;
} else if (Input.GetKeyDown (KeyCode.D) && side < maxSideRight) {
MoveObjectTo(this.transform, new Vector3(this.transform.position.x + 12, this.transform.position.y, this.transform.position.z + 10), movementSpeed);
side += 1;
}
if (Input.GetKeyDown (KeyCode.W) && level < maxLevelHeight) {
MoveObjectTo(this.transform, new Vector3(this.transform.position.x, this.transform.position.y + 12, this.transform.position.z + 10), movementSpeed);
level += 1;
} else if (Input.GetKeyDown (KeyCode.S) && level > minLevelHeight) {
MoveObjectTo(this.transform, new Vector3(this.transform.position.x, this.transform.position.y - 12, this.transform.position.z + 10), movementSpeed);
level -= 1;
}
if (Input.GetKeyDown (KeyCode.R) || Input.GetKeyDown(KeyCode.Space)) {
SceneManager.LoadScene ("Scene1");
Time.timeScale = 1;
}
}
private void MoveObjectTo(Transform objectToMove, Vector3 targetPosition, float moveSpeed)
{
StopCoroutine(MoveObject(objectToMove, targetPosition, moveSpeed));
StartCoroutine(MoveObject(objectToMove, targetPosition, moveSpeed));
}
public static IEnumerator MoveObject(Transform objectToMove, Vector3 targetPosition, float moveSpeed)
{
float currentProgress = 0;
Vector3 cashedObjectPosition = objectToMove.transform.position;
while (currentProgress <= 1)
{
currentProgress += moveSpeed * Time.deltaTime;
objectToMove.position = Vector3.Lerp(cashedObjectPosition, targetPosition, currentProgress);
yield return null;
}
}
You can use a simple isMoving variable for this. Don't move if the variable is true. Move if it is false. When the coroutine is done running set isMoving back to false. Also, I can't tell why MoveObject function is static. I removed the static keyword from it.
bool isMoving = false;
void Update()
{
transform.Translate(Vector3.forward * ForwardSpeed * Time.deltaTime);
if (Input.GetKeyDown(KeyCode.A) && side > maxSideLeft)
{
MoveObjectTo(this.transform, new Vector3(this.transform.position.x - 12, this.transform.position.y, this.transform.position.z + 10), movementSpeed);
side -= 1;
}
else if (Input.GetKeyDown(KeyCode.D) && side < maxSideRight)
{
MoveObjectTo(this.transform, new Vector3(this.transform.position.x + 12, this.transform.position.y, this.transform.position.z + 10), movementSpeed);
side += 1;
}
if (Input.GetKeyDown(KeyCode.W) && level < maxLevelHeight)
{
MoveObjectTo(this.transform, new Vector3(this.transform.position.x, this.transform.position.y + 12, this.transform.position.z + 10), movementSpeed);
level += 1;
}
else if (Input.GetKeyDown(KeyCode.S) && level > minLevelHeight)
{
MoveObjectTo(this.transform, new Vector3(this.transform.position.x, this.transform.position.y - 12, this.transform.position.z + 10), movementSpeed);
level -= 1;
}
if (Input.GetKeyDown(KeyCode.R) || Input.GetKeyDown(KeyCode.Space))
{
SceneManager.LoadScene("Scene1");
Time.timeScale = 1;
}
}
private void MoveObjectTo(Transform objectToMove, Vector3 targetPosition, float moveSpeed)
{
//Don't do anything Object is already moving
if (isMoving)
{
return;
}
//If not moving set isMoving to true
isMoving = true;
StartCoroutine(MoveObject(objectToMove, targetPosition, moveSpeed));
}
public IEnumerator MoveObject(Transform objectToMove, Vector3 targetPosition, float moveSpeed)
{
float currentProgress = 0;
Vector3 cashedObjectPosition = objectToMove.transform.position;
while (currentProgress <= 1)
{
currentProgress += moveSpeed * Time.deltaTime;
objectToMove.position = Vector3.Lerp(cashedObjectPosition, targetPosition, currentProgress);
yield return null;
}
//Done moving. Set isMoving to false
isMoving = false;
}
It sounds like you want to check to see if the user has completed their lerp before lerping to some new position. In that case, you will want to prevent your player from moving again until your currentProgress variable is equal to 1. Thus, use a simple boolean callback and prevent calling the Corouting until that callback is true. Your MoveObject function:
public static IEnumerator MoveObject(Transform objectToMove, Vector3 targetPosition, float moveSpeed, System.Action<bool> callBack)
{
float currentProgress = 0;
Vector3 cashedObjectPosition = objectToMove.transform.position;
while (currentProgress <= 1)
{
currentProgress += moveSpeed * Time.deltaTime;
objectToMove.position = Vector3.Lerp(cashedObjectPosition, targetPosition, currentProgress);
yield return null;
if (currentProgress >= 1)
callBack(true);
}
}
Then you can change your MoveObjectTo function to read this callback:
private void MoveObjectTo(Transform objectToMove, Vector3 targetPosition, float moveSpeed)
{
if (canCallCoroutine)
{
canCallCoroutine = false;
StartCoroutine(MoveObject(objectToMove, targetPosition, moveSpeed, finished =>
{
if (finished != null)
{
if (finished)
canCallCoroutine = true;
}
}));
}
}

Categories

Resources