having a slight problem. I am reworking a project of mine using SpriteFactory, and have used a youtube following the exact same code as his but running into the following error:
using UnityEngine;
using System.Collections;
using SpriteFactory;
public class Running : MonoBehaviour {
private SpriteFactory.Sprite;
// Use this for initialization
void Start () {
sprite = GetComponent<Sprite> ();
}
// Update is called once per frame
void Update () {
if(Input.GetKey(KeyCode.RightArrow)) {
Sprite.Play("Run");
Vector3 pos = transform.position;
pos.x += Time.deltaTime * 2;
transform.position = pos;
}
else{
sprite.Stop();
}
}
}
Error It results in is Unexpected Symbol ";" in class, struct or interface member declaration which i know is referring to:
private SpriteFactory.Sprite;
but I am not even sure why? Suggestions
Here you go :)
using UnityEngine;
using System.Collections;
// below solved conflict of class names
// we won't "using" whole SpriteFactory namespace because
// both UnityEngine and SpriteFactory have got same class "Sprite"
// so we pull out only needed class
using FactorySprite = SpriteFactory.Sprite;
public class Running : MonoBehaviour {
// you forgot to set name of variable representing your sprite
private FactorySprite sprite;
// Use this for initialization
void Start () {
sprite = GetComponent<FactorySprite> (); // Edited
}
// Update is called once per frame
void Update () {
if(Input.GetKey(KeyCode.RightArrow)) {
sprite.Play("Run"); // heh, remember C# is case sensitive :)
Vector3 pos = transform.position;
pos.x += Time.deltaTime * 2;
transform.position = pos;
}
else{
sprite.Stop();
}
}
}
Related
Just picked up Unity about a week ago, I have really been struggling to fix this problem and referencing overall, I'm well aware that I need to read and watch more tutorials, I just want to get this fixed so I can continue working on my game.
An object reference is required for the non-static field, method, or property PlayerMovement.activeMoveSpeed
The first problem was referencing the other Game Object and script, I not sure if its completely fixed now but
at least that not the error that its giving me anymore, I've tried doing what this link says
https://answers.unity.com/questions/1119537/help-how-do-i-referenceaccess-another-script-in-un.html
but as you might see it hasn't worked out, every single time I get the compile errors fixed the script doesn't work because the object reference is not set to an instance of an object, any help would be extremely appreciated (the script I'm trying to reference will be at the end)
Thanks
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ShieldAttack : MonoBehaviour
{
public GameObject shield;
private Vector3 mousePos;
private Camera mainCam;
public bool isDashing;
private Rigidbody2D rb;
GameObject Player;
PlayerMovement playerMovement;
Shooting shooting;
// Start is called before the first frame update
void Start()
{
GameObject.FindGameObjectWithTag("EnemyMelee");
GameObject.FindGameObjectWithTag("Enemy2");
mainCam = GameObject.FindGameObjectWithTag("MainCamera").GetComponent<Camera>();
rb = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update()
{
mousePos = mainCam.ScreenToWorldPoint(Input.mousePosition);
Vector3 rotation = mousePos - transform.position;
float rotZ = Mathf.Atan2(rotation.y, rotation.x) * Mathf.Rad2Deg;
transform.rotation = Quaternion.Euler(0, 0, rotZ);
if (Input.GetKeyDown(KeyCode.Space) && playerMovement.dashCoolCounter <= 0 && playerMovement.dashCounter <= 0)
{
isDashing = true;
Instantiate(shield, shooting.bulletTransform.position, Quaternion.identity);
if (PlayerMovement.activeMoveSpeed == 5)
{
DestroyShield();
isDashing = false;
}
}
}
void DestroyShield()
{
Destroy(gameObject);
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class PlayerMovement : MonoBehaviour
{
public float moveSpeed;
public Rigidbody2D rb2d;
private Vector2 moveInput;
public float activeMoveSpeed;
public float dashSpeed;
public float dashLength = 0.5f, dashCooldown = 1f;
public float dashCounter;
public float dashCoolCounter;
[SerializeField] private TrailRenderer tr;
//Start is called before the first frame update
void Start()
{
activeMoveSpeed = moveSpeed;
}
//Update is called once per frame
void Update()
{
if(dashCounter > 0)
{
tr.emitting = true;
}
if(dashCounter < 0)
{
tr.emitting = false;
}
moveInput.x = Input.GetAxisRaw("Horizontal");
moveInput.y = Input.GetAxisRaw("Vertical");
moveInput.Normalize();
rb2d.velocity = moveInput * activeMoveSpeed;
if (Input.GetKeyDown(KeyCode.Space))
{
if (dashCoolCounter <=0 && dashCounter <=0)
{
activeMoveSpeed = dashSpeed;
dashCounter = dashLength;
}
}
if (dashCounter > 0)
{
dashCounter -= Time.deltaTime;
if (dashCounter <= 0)
{
activeMoveSpeed = moveSpeed;
dashCoolCounter = dashCooldown;
}
}
if (dashCoolCounter > 0)
{
dashCoolCounter -= Time.deltaTime;
}
}
}
You are using class name PlayerMovement.activeMoveSpeed instead of object name playerMovement.activeMoveSpeed in this part of code:
if (PlayerMovement.activeMoveSpeed == 5)
{
DestroyShield();
isDashing = false;
}
Also I cannot see playerMovement variable initialization in the ShieldAttack script. You need to mark it with the [SerializeField] attribute or make it public to be able to assign it in the inspector. Or initialize it in your Start() method along with the other fields.
When you create a variable, you do <type> <name>, where <type> is the kind of thing you want to create and <name> is how you want to reference the instance you created.
We as programmers are generally lazy, so if we wanted to create a pineapple we would create an instance of the Pineapple class. What do we call it? Typically just pineapple, and then you wind up with code like
Pineapple pineapple;
The first term means you're wanting to create a Pineapple, and the second term means you're going to refer to that instance as pineapple. Note the capitalization differences there.
The issue with your code is that you've created an instance of PlayerMovement:
PlayerMovement playerMovement;
but when you're trying to use the instance in your code, you are using the class name PlayerMovement and not the instance name playerMovement. Again, note the capitalization difference.
The particular line that you've got:
if (PlayerMovement.activeMoveSpeed == 5)
should instead be:
if (playerMovement.activeMoveSpeed == 5)
to refer to the instance and not the class.
It is possible to have things that are common to all instances of a class. Those are static items and you would access them by referencing the class name instead of the instance name.
The error message you got:
An object reference is required for the non-static field, method, or property PlayerMovement.activeMoveSpeed
was telling you that you were trying to access a part of the class, but it wasn't static, so you needed to reference the object (instance).
This question already has answers here:
What is a NullReferenceException, and how do I fix it?
(27 answers)
Closed 3 years ago.
Hello I am new to coding in unity and i was trying to make the health bar go down when the player hits an object. When i use a debug.log it prints what i want it to print when it collides with the object however when i try to make the health go down when it hits the object it gives me this error
NullReferenceException:
Object reference not set to an instance of an object
DamagePlayer.OnCollisionEnter2D (UnityEngine.Collision2D collision)
(at Assets/Scripts/DamagePlayer.cs:30)
here is my code.
My Damage class
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class DamagePlayer : MonoBehaviour
{
public BarScript bar;
public int playerHealth = 100;
int damage = 10;
// Start is called before the first frame update
void Start()
{
print(playerHealth);
}
// Update is called once per frame
void Update()
{
}
private void OnCollisionEnter2D(Collision2D collision)
{
if(collision.collider.tag =="enemy")
{
Debug.Log("enemy");
bar.math(damage);
}
}
}
Health Bar class
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class BarScript : MonoBehaviour
{
private float fillAmount;
[SerializeField]
private Image content;
// Start is called before the first frame update
void Start()
{
fillAmount = 1f;
}
// Update is called once per frame
void Update()
{
content.fillAmount = fillAmount;
}
public float math(float value)
{
return fillAmount =(value / 100);
}
}
My Player class
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Player : MonoBehaviour
{
private Rigidbody2D rb;
[SerializeField]
private float speed = 300f;
private float jump = 400f;
// Start is called before the first frame update
void Start()
{
rb = GetComponent<Rigidbody2D>();
}
// Update is called once per frame
void Update()
{
Movement();
}
void Movement()
{
if (Input.GetKeyDown("d")){
rb.velocity = new Vector2(speed * Time.fixedDeltaTime, rb.velocity.y);
}else if (Input.GetKeyDown("a"))
{
rb.velocity = new Vector2(-speed * Time.fixedDeltaTime, rb.velocity.y);
}else if (Input.GetKeyDown("space"))
{
rb.velocity = new Vector2(rb.velocity.x, jump * Time.fixedDeltaTime);
}
}
}
You haven't create an instance of BarScript in DamagePlayer, that's why this is creating problem.
Without instance you can't access member method of a class, you can use static to make that accessible by anyone. If it is just for Player then you can do that (Single-player), But it won't be so nice.
If you it's multi-player or you want do the same for enemy, then create prefab with both script, then instantiate or use pooling. Finally use findGameobjectsWithTag (not findGameobjectWithTag) and access those scripts, members and use their member methods.
I am a bit confused as to why this is, so basically Im trying to get it to where the camera follows the player without moving left and right with him.
using System.Collections;
using UnityEngine;
public class CameraMotor : MonoBehaviour {
private Transform lookAt;
private Vector3 startOffset;
private Vector3 moveVector;
void Start () {
GameObject.FindGameObjectWithTag ("Player").transform;
}
// Update is called once per frame
void Update () {
moveVector = lookAt.position + startOffset;
//X
moveVector.x = 0; //center of track
//Y[image][1]
moveVector.y = Mathf.Clamp(moveVector.y,3,5);// for ramps/stairs
transform.position = moveVector;
}
}
I think you want GameObject.FindWithTag
https://docs.unity3d.com/ScriptReference/GameObject.FindWithTag.html
Even so,
GameObject.FindWithTag ("Player").transform;
does nothing. (Nothing usefull atleast)
lookAt is never assigned, so im guessing what you want to do is
lookAt = GameObject.FindWithTag ("Player").transform;
If you are looking for an object in your scene, then use this simple script;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class AnswerScript : MonoBehaviour {
private Transform lookAt;
// Use this for initialization
void Start () {
lookAt.Find("The Object That You are Looking For");
}
// Update is called once per frame
void Update () {
}
}
I am trying to code my first game 'Tappy Bird' using Unity2D. When I try to run the app, I am receiving the following error message in Unity:
Assets/scripts/TapController.cs(6,6): error CS0592: The attribute
UnityEngine.RequireComponent is not valid on this declaration type.
It is valid on class declarations only
Code:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class NewBehaviourScript : MonoBehaviour
{
[RequireComponent(typeof(Rigidbody2D))]
public float tapForce = 10;
public float tiltSmooth = 5;
public Vector3 startPos;
Rigidbody2D rigidbody;
Quaternion downRotation;
Quaternion forwardRotation;
void Start()
{
rigidbody = GetComponent<Rigidbody2D();
downRotation = Quaternion.Euler(0, 0, -90);
forwardRotation = Quaternion.Euler(0, 0, 35);
}
void update()
{
if (input.GetMouseButtonDown(0))
{
transform.rotation = forwardRotation;
rigidbody.AddForce(vector2.up * tapForce, ForceMode2D.Force);
}
transform.rotation = Quaternion.Lerp(
transform.rotation, downRotation, tiltSmooth * Time.deltaTime);
}
void onTriggerEnter2D(Collider2D col){
if(col.gameObject.tag == "ScoreZone") {
//register a Score event
//play sound
}
if(col.gmeObject.tag == "DeadZone") {
//register a dead event
//play a sound
}
}
}
If I understand your code right you should add attribute before class declaration:
[RequireComponent(typeof(Rigidbody2D))]
public class NewBehaviourScript : MonoBehaviour
{
...
}
The RequireComponent attribute that adds required components as dependencies needs to be set outside of your class.
https://docs.unity3d.com/ScriptReference/RequireComponent.html
https://docs.unity3d.com/ScriptReference/RequireComponent.html
Firstly, it should be in front of the class name;
Secondly, if you have attach the script to gameobject, you need to reattach again.
[RequireComponent(typeof(Rigidbody2D))]
public class NewBehaviourScript : MonoBehaviour
{
//...
}
My Code work properly, but i need to limiting the prefab to 5 times only.
I want to using for loop.....
using UnityEngine;
using System.Collections;
public class theScript : MonoBehaviour {
public GameObject prefab1;
// Use this for initialization
void Start () {
InvokeRepeating ("Instant_", 1f, 1f);
}
// Update is called once per frame
void Update () {
}
void Instant_(){
Instantiate (prefab1, transform.position, transform.rotation );
}
}
Avoid using the functions like Invoke or InvokeRepeating. Since you refer to a function by its name, if you change it, the string in the Invoke call won't update. Moreover, The Instant_ method will be called uselessly until you change scene or quit game with the method of #bismute.
I suggest you using coroutines. And bonus, you will use a foor loop ! ;D
using UnityEngine;
using System.Collections;
public class theScript : MonoBehaviour {
public GameObject prefab1;
public int MaxInstantiation = 5;
void Start ()
{
StartCoroutine( InstantiatePrefab(1) ) ;
}
private IEnumerator InstantiatePrefab( float delay = 1f )
{
WaitForSeconds waitDelay = new WaitForSeconds( delay ) ;
for( int instantiateCount = 0 ; instantiateCount < MaxInstantiation ; ++instantiateCount )
{
yield return waitDelay ;
Instantiate (prefab1, transform.position, transform.rotation ) ;
}
yield return null ;
}
}
Is there any reason for using 'for' statement?
How about this?
using UnityEngine;
using System.Collections;
public class theScript : MonoBehaviour {
public GameObject prefab1;
public int FiveTimeCheck;
// Use this for initialization
void Start () {
FiveTimeCheck = 0;
InvokeRepeating ("Instant_", 1f, 1f);
}
// Update is called once per frame
void Update () {
}
void Instant_(){
if(FiveTimeCheck <= 5)
{
FiveTimeCheck += 1;
Instantiate (prefab1, transform.position, transform.rotation );
}
}
}