Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 12 Next capture
2021 2022 2023
1 capture
12 Jun 22 - 12 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
0
Question by ClownChad · Jul 11, 2019 at 10:36 PM · movementrigidbody2dkinematicpixel artblurry

2D Pixel Art Player Blurry/Vibrates When Moving Via Kinematic Platformer Controller

Two example gifs here: https://imgur.com/a/st2ONuD

There are two sprites in the gifs. The above sprite is enlarged and is only moving back and forth. The smaller sprite is the player sprite and is controlled via a slightly modified 2D Kinematic Platformer Controller which I made following the Unity tutorial for making a kinematic platformer controller: https://www.youtube.com/watch?v=wGI2e3Dzk_w&list=PLX2vGYjWbI0SUWwVPCERK88Qw8hpjEGd8

Here are the scripts used for the player:

Physics Object Script:

 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 
 public class PhysicsObject : MonoBehaviour
 {
 
     [Header("Custom Physics Variables")]
     //0.65 is about a 50 degree angle on rotated object
     public float minGroundAngleY = 0.65f;
     public float gravityModifier = 1f;
     public Vector2 gravity = new Vector2(0, -9.8f);
 
     [Tooltip("Jump decay when going up")]
     public float jumpDecay = 0.2f;
     [Tooltip("Jump decay when player reaches apex and starts to fall")]
     public float jumpApexDecay = 0.3f;
 
     protected Vector2 targetVelocity;
     protected bool grounded;
     protected Vector2 groundNormal;
     protected Rigidbody2D rb;
     protected Vector2 velocity;
     protected ContactFilter2D contactFilter;
     protected RaycastHit2D[] hitBuffer = new RaycastHit2D[16];
     protected List<RaycastHit2D> hitBufferList = new List<RaycastHit2D>(16);
 
     protected const float minCheckColDist = 0.001f;
     protected const float shellRadius = 0.01f;
 
     private void OnEnable()
     {
 
         rb = GetComponent<Rigidbody2D>();
 
     }
 
     private void Start()
     {
 
         contactFilter.useTriggers = false;
         contactFilter.SetLayerMask(Physics2D.GetLayerCollisionMask(gameObject.layer));
         contactFilter.useLayerMask = true;
 
     }
 
     private void Update()
     {
         targetVelocity = Vector2.zero;
         ComputeVelocity();
     }
 
     protected virtual void ComputeVelocity()
     {
 
     }
 
     private void FixedUpdate()
     {
         MovementPrep();
     }
 
     private void MovementPrep()
     {
         velocity += gravityModifier * gravity * Time.deltaTime;
         velocity.x = targetVelocity.x;
 
         if (velocity.y > 0)
         {
             velocity.y -= jumpDecay * Time.deltaTime;
         }
         else if (velocity.y < 0)
         {
             velocity.y -= jumpApexDecay * Time.deltaTime;
         }
 
         grounded = false;
 
         Vector2 moveAlongGround = new Vector2(groundNormal.y, -groundNormal.x);
 
         Vector2 move = moveAlongGround * velocity.x * Time.deltaTime;
 
         Movement(move, false);
 
         move = Vector2.up * velocity.y * Time.deltaTime;
 
         Movement(move, true);
     }
 
     private void Movement(Vector2 move, bool yMovement)
     {
 
         float colMoveDist = move.magnitude;
 
         if (colMoveDist > minCheckColDist)
         {
 
             int count = rb.Cast(move, contactFilter, hitBuffer, colMoveDist + shellRadius);
 
             hitBufferList.Clear();
 
             for (int i = 0; i < count; i++)
             {
                 hitBufferList.Add(hitBuffer[i]);
             }
 
             for (int i = 0; i < hitBufferList.Count; i++)
             {
                 Vector2 currentNormal = hitBufferList[i].normal;
 
                 if (currentNormal.y > minGroundAngleY)
                 {
                     grounded = true;
 
                     if (yMovement)
                     {
                         groundNormal = currentNormal;
                         currentNormal.x = 0;
                     }
                 }
 
                 float projection = Vector2.Dot(velocity, currentNormal);
 
                 if (projection < 0)
                 {
                     velocity = velocity - projection * currentNormal;
                 }
 
                 float modifiedDistance = hitBufferList[i].distance - shellRadius;
                 colMoveDist = modifiedDistance < colMoveDist ? modifiedDistance : colMoveDist;
             }
 
         }
 
         rb.position = rb.position + move.normalized * colMoveDist;
     }
 }

PlayerController Script

 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 
 public class PlayerController : PhysicsObject
 {
     [Header("Player Variables")]
     public float speed = 7f;
     public float jumpPower = 10f;
 
     private SpriteRenderer spriteRender;
     private Animator animator;
 
     private void Awake()
     {
         spriteRender = transform.GetChild(0).GetComponent<SpriteRenderer>();
         animator = transform.GetChild(0).GetComponent<Animator>();
     }
 
     protected override void ComputeVelocity()
     {
         Vector2 move = Vector2.zero;
 
         if (!GameManager.instance.InShop)
         {
             move.x = Input.GetAxis("Horizontal");
 
             if (Input.GetButtonDown("Jump") && grounded)
             {
                 velocity.y = jumpPower;
             }
             else if (Input.GetButtonUp("Jump"))
             {
                 if (velocity.y > 0)
                     velocity.y *= 0.5f;
             }
         }
 
         targetVelocity = move * speed;
 
         if (Mathf.Abs(targetVelocity.x) > 0)
             animator.SetBool("moving", true);
         else
             animator.SetBool("moving", false);
 
         //If moving right
         if (move.x > 0)
         {
             if (!spriteRender.flipX)
                 spriteRender.flipX = true;
         }
         //If moving left
         else if (move.x < 0)
         {
             if (spriteRender.flipX)
                 spriteRender.flipX = false;
         }
     }
 }
 

And here is the test script I made for the larger sprite:

Test Script

 using System.Collections;
 using System.Collections.Generic;
 using UnityEngine;
 
 public class Test : MonoBehaviour
 {
     public float speed;
 
     private Rigidbody2D rb;
     private bool moveRight;
 
     private void Awake()
     {
         rb = GetComponent<Rigidbody2D>();
         moveRight = true;
     }
 
     private void FixedUpdate()
     {
         MoveRBObject();
     }
 
     private void MoveRBObject()
     {
         if (moveRight)
             rb.position = rb.position + (Vector2.right * speed * Time.deltaTime);
         else
             rb.position = rb.position + (Vector2.left * speed * Time.deltaTime);
 
         if (rb.position.x > 6)
             moveRight = false;
         else if (rb.position.x < -6)
             moveRight = true;
     }
 }
 

I've searched for a solution to fix the vibrating and have tried about a half a dozen different solutions but nothing seemed to have changed the vibrating in any significant way. A few things I have tried:

  • Changed rb.position to rb.MovePosition() and set the Rigidbody interpolation to "Interpolate" and "Extrapolate"

  • Made a very simple "pixel perfect" movement script which just changed the player sprite position on LateUpdate() to be to the nearest pixel position

  • Attempted having the movement code be in Update() as opposed to FixedUpdate()

  • Tried implementing the scripts from this post I found on movement in Unity: http://www.kinematicsoup.com/news/2016/8/9/rrypp5tkubynjwxhxjzd42s3o034o8 (Not sure if I implemented them correctly or not though. They didn't seem to change anything)

  • Updated my graphics card drivers

I would be very grateful for any tips or suggestions on how to fix this. Please let me know if you need more information to help solve the problem.

Thanks!

Comment
Add comment
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

1 Reply

· Add your reply
  • Sort: 
avatar image
0

Answer by MrRightclick · Jul 12, 2019 at 08:24 AM

With pixel art characters this small you might need to use a pixel perfect camera. Check out this Unity blog post about the new Pixel Perfect 2D asset: https://blogs.unity3d.com/2019/03/13/2d-pixel-perfect-how-to-set-up-your-unity-project-for-retro-8-bits-games/

Comment
Add comment · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

167 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

Move/Rotate Kinematic (2D) Child with MovePosition/MoveRotation Doesn't Work 0 Answers

Rigidbody2D AddForce only working with large numbers 2 Answers

Hinge Joint 2D separating from object 0 Answers

Using Rigidbody.MovePosition With Local Position and Lerp 2 Answers

Moving Object in constant speed in one axis while be able to control the object in all axis 1 Answer


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges