درود مهمان گرامی! ثبت نام

آموزش ساخت بازی با C# آموزش پروژه محور یونیتی Unity آموزش ساخت بازی حدس تصویر
آموزش مدل سازی در Maya آموزش یونیتی Unity- ساخت منو آموزش گنجینه برنامه نویسی اندروید
آموزش مدل سازی با 3Ds Max آموزش متحرک سازی با Unity آموزش گرافیک کامپیوتری با OpenGL
آموزش متحرک سازی در 3Ds Max مجموعه آموزش های ساخت بازی آموزش ساخت بازی در ویژوال بیسیک
● آموزش های رایگان ● تبلیغات دیجیتال هوشمند ● استخدام در فرادرس

امتیاز موضوع:
  • 7 رأی - میانگین امتیازات: 4.43
  • 1
  • 2
  • 3
  • 4
  • 5
کد های یونیتی
اسکریپتی به نام Spring ایجاد می کنیم… این اسکریپت رو قراره به گیم آبجکت فنر اختصاص بدیم… از OnTriggerEnter2D یا OnCollisionEnter2D میتونید برای تشخیص برخورد بازیکن به روی فنر استفاده کنید.

یک Collider  و ترجیحا Box Collider به گیم آبجکت فنر اضافه می کنیم… کمی اون رو به بالا انتقال میدیم که سطح فنر رو بپوشونه…
یک Collider به پای اسپرایت بازیکن اضافه می کنیم و اون رو کمی بیرون تر از Collider کلی قرار میدیم تا به فنر بخوره… در نهایت تیک Is Trigger رو فعال میکنیم.

به اسکریپت Spring بر می گردیم و در OnTriggerEnter2D بررسی می کنیم که چه چیزی وارد شده و اگه بازیکن وارد شده بود، انیمیشن مربوط به باز و بسته شدن فنر رو اجرا کن…. ( انیمیشنی که طی اون فنر به بالا میره و سپس به جای اولش برمیگرده…
بعد propery به نام playerGameObject  و از جنس گیم آبجکت تعریف کردیم و این gameobject وارد شده رو به اون اختصاص میدیم (تا بعدا بگم کجا ازش استفاده می کنیم)


کد php:
void OnTriggerEnter2D(Collider2D target) {
 if (
target.gameObject.Equals("Player")) {
 
animator.SetInteger ("AnimState"1);
 
playerGameObject target.gameObject;
 }
 } 
حالا متدی به اسم OnFullOpened ایجاد می کنیم… این متد قراره از طریق Animation اجرا بشه… و زمانی احرا میشه که فریم مربوط به باز شدن کامل فنر اجرا بشه… پس به Animation میریم…
کار این متد اضافه کردن نیرو به RigidBody بازیکن هست… بازیکن رو هم قبلا در داخل OnTriggerEnter2D به پروپرتی playerGameObject  اختصاص داده ایم.


متد دیگه ای به اسم sound مینویسیم و داخلش کامپوننت صدارو می گیرم و صدای فنر رو پخش می کنیم. (کار با صدا در یونیتی)
در نهایت اسکریپت ما به صورت زیر در میاد:

کد php:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
 
public class 
Spring MonoBehaviour {
 
    public 
float force 5.0f;
 
    private 
Animator animator;
    private 
GameObject playerGameObject;
 
    
void Start() {
        
animator GetComponent<Animator> ();
    }
 
    
void OnTriggerEnter2D(Collider2D target) {
        if (
target.gameObject.Equals("Player")) {
            
animator.SetInteger ("AnimState"1);
            
playerGameObject target.gameObject;
        }
    }
 
    
void sound() {
        
GetComponent<AudioSource> ().Play ();
    }
 
    
void OnFullOpened() {
        
        try {
            
Rigidbody2D rb2d playerGameObject.GetComponent<Rigidbody2D> ();
            
rb2d.velocity = new Vector2(rb2d.velocity.xforce);
        } catch {
            
        }
        
animator.SetInteger ("AnimState"0);
    }
 

لبته این اسکریپت چندتا باگ کوچیک داره که شاید اتفاق بیفتند… اگر باگی براتون به وجود اومد از طریق نظرات مطرح کنید شاید باگ هایی باشند که انتظار داشتیم به وجود بیان. موفق باشید.
amirsh
amirzarei007_pv
پاسخ
سلام
این کد برای شبکه ای بازی کردن
کد php:
using System.Collections;
using UnityEngine;

public class 
startserver MonoBehaviour {

 
// Use this for initialization
 
public Transform obj;
 public 
Transform makan;
 public 
string sss;
 
// Update is called once per frame
 
void ongui() {
 
GUILayout.Box (Network.player.ipAddress);
 if (
Network.peerType == NetworkPeerType.Disconnected) {
 
sss GUILayout.TextField (sss);
 if (
GUILayout.Button ("startserver")) {
 
Network.InitializeServer (1025000);

 }

 if (
GUILayout.Button ("connect")) {
 
Network.Connect (sss250000);

 }
 } else {
 if (
GUILayout.Button ("createcube")) {
 
Network.Instantiate (objmakan.transform.positionmakan.transform.rotation0);
 }
 }
 }

میتونید به جای ("createcube")  هر اسمی بزارید
اگر به مشکلاتی خوردید  بگید
amirsh
amirzarei007_pv
پاسخ
سلام 
ساخت در کشویی و....
اول یک مدل پیدا میکنید.
دوم کد زیر را به در اضافه میکنید
کد php:
using UnityEngine;
using System.Collections.Generic;
using System;
using System.Collections;

[
RequireComponent(typeof(AudioSource))]
[
RequireComponent(typeof(Rigidbody))]

public class 
vp_MovingPlatform MonoBehaviour
{

    
// misc
    
protected Transform m_Transform null;

    
// path
    
public PathMoveType PathType PathMoveType.PingPong;
    public 
GameObject PathWaypoints null;
    public 
Direction PathDirection Direction.Forward;
    public 
int TargetedWaypointget{ return m_TargetedWayPoint; } }
    public 
int MoveAutoStartTarget 1000;
    protected List<
Transformm_Waypoints = new List<Transform>();
    protected 
int m_NextWaypoint 0;
    protected 
Vector3 m_CurrentTargetPosition Vector3.zero;
    protected 
Vector3 m_CurrentTargetAngle Vector3.zero;
    protected 
int m_TargetedWayPoint 0;
    protected 
float m_TravelDistance 0.0f;
    protected 
Vector3 m_OriginalAngle Vector3.zero;
    protected 
int m_CurrentWaypoint 0;

    
// comparer to sort waypoints in alphabetical order
    
protected class WaypointComparer IComparer
    
{
        
int IComparer.Compare(System.Object xSystem.Object y)
        { return ((new 
CaseInsensitiveComparer()).Compare(((Transform)x).name, ((Transform)y).name)); }
    }

    
// movement
    
public float MoveSpeed 0.1f;
    public 
float MoveReturnDelay 0.0f;        // time before returning to start upon stopping at target (Target mode)
    
public float MoveCooldown 0.0f;            // time to sleep (disable trigger) after returning to start
    
public MovementInterpolationMode MoveInterpolationMode MovementInterpolationMode.EaseInOut;
    protected 
bool m_Moving false;
    protected 
float m_NextAllowedMoveTime 0.0f;
    protected 
float m_MoveTime;
    protected 
vp_Timer.Handle m_ReturnDelayTimer = new vp_Timer.Handle();
    protected 
Vector3 m_PrevPos Vector3.zero;        // used to calculate velocity
    
protected AnimationCurve m_EaseInOutCurve AnimationCurve.EaseInOut(0011);
    protected 
AnimationCurve m_LinearCurve AnimationCurve.Linear(0011);
    
    
// rotation
    
public float RotationEaseAmount 0.1f;
    public 
Vector3 RotationSpeed Vector3.zero;
    public 
RotateInterpolationMode RotationInterpolationMode RotateInterpolationMode.SyncToMovement;
    protected 
Vector3 m_PrevAngle Vector3.zero;    // used to calculate velocity


    // sound
    
public AudioClip SoundStart null;
    public 
AudioClip SoundStop null;
    public 
AudioClip SoundMove null;
    public 
AudioClip SoundWaypoint null;
    protected 
AudioSource m_Audio null;

    
// physics
    
public bool PhysicsSnapPlayerToTopOnIntersect true;
    public 
float m_PhysicsPushForce 2.0f;
    protected 
Rigidbody m_RigidBody null;
    protected 
Collider m_Collider null;
    protected 
Collider m_PlayerCollider null;
    protected 
vp_PlayerEventHandler m_PlayerToPush null;
    protected 
float m_PhysicsCurrentMoveVelocity;
    protected 
float m_PhysicsCurrentRotationVelocity;

    
// dictionary to optimize lookup of colliding players
    
protected static Dictionary<Collidervp_PlayerEventHandlerm_KnownPlayers = new Dictionary<Collidervp_PlayerEventHandler>();

    
// enums

    
public enum PathMoveType
    
{
        
PingPong,    // goes to the last waypoint and back the same way without stopping
        
Loop,        // goes to the last waypoint, then directly to the first without stopping
        
Target        // stands still unless given a target
    
}

    public 
enum Direction
    
{
        
Forward,
        
Backwards,
        
Direct
    
}
    
    public 
enum MovementInterpolationMode
    
{
        
EaseInOut,
        
EaseIn,
        
EaseOut,
        
EaseOut2,
        
Slerp,
        
Lerp
    
}
    
    public 
enum RotateInterpolationMode
    
{
        
SyncToMovement,
        
EaseOut,
        
CustomEaseOut,
        
CustomRotate
    
}


    
/// <summary>
    /// 
    /// </summary>
    
void Start()
    {

        
m_Transform transform;
        
m_Collider GetComponentInChildren<Collider>();
        
m_RigidBody GetComponent<Rigidbody>();
        
m_RigidBody.useGravity false;
        
m_RigidBody.isKinematic true;

        
m_NextWaypoint 0;
        
m_Audio GetComponent<AudioSource>();
        
m_Audio.loop true;
        
m_Audio.clip SoundMove;

        
// abort if no waypoints
        
if (PathWaypoints == null)
            return;

        
// init the hierarchy
        
gameObject.layer vp_Layer.MovingPlatform;
        foreach (
Transform w in PathWaypoints.transform)
        {
            if (
vp_Utility.IsActive(w.gameObject))
            {
                
m_Waypoints.Add(w);
                
w.gameObject.layer vp_Layer.MovingPlatform;
            }
            if (
w.GetComponent<Renderer>() != null)
                
w.GetComponent<Renderer>().enabled false;
            if (
w.GetComponent<Collider>() != null)
                
w.GetComponent<Collider>().enabled false;
        }

        
// sort the waypoints alphabetically
        
IComparer comparer = new WaypointComparer();
        
m_Waypoints.Sort(comparer.Compare);
        
        
// prepare for takeoff
        
if (m_Waypoints.Count 0)
        {
            
m_CurrentTargetPosition m_Waypoints[m_NextWaypoint].position;
            
m_CurrentTargetAngle m_Waypoints[m_NextWaypoint].eulerAngles;
            
m_Transform.position m_CurrentTargetPosition;
            
m_Transform.eulerAngles m_CurrentTargetAngle;
            if (
MoveAutoStartTarget m_Waypoints.Count 1)
                
MoveAutoStartTarget m_Waypoints.Count 1;
        }

    }


    
/// <summary>
    /// 
    /// </summary>
    
void FixedUpdate()
    {
                
        
UpdatePath();
        
        
UpdateMovement();

        
UpdateRotation();
        
        
UpdateVelocity();

    }


    
/// <summary>
    /// detects touching a waypoint, schedules going to the next one
    /// and triggers effects on various states (start, stop, arrive etc.)
    /// </summary>
    
protected void UpdatePath()
    {
        
        if (
m_Waypoints.Count 2)
            return;

        if (
GetDistanceLeft() < 0.01f)
        {

            if (
Time.time >= m_NextAllowedMoveTime)
            {

                switch (
PathType)
                {

                    
// --- target mode ---
                    
case PathMoveType.Target:

                        if (
m_NextWaypoint == m_TargetedWayPoint)
                        {
                            if (
m_Moving)
                                
OnStop();
                            else if(
m_NextWaypoint != 0)
                                
OnArriveAtDestination();
                        }
                        else
                        {
                            if (
m_Moving)
                            {
                                if (
m_PhysicsCurrentMoveVelocity == 0.0f)
                                    
OnStart();
                                else
                                    
OnArriveAtWaypoint();
                            }
                            
GoToNextWaypoint();
                        }
                        break;

                    
// --- loop mode ---
                    
case PathMoveType.Loop:
                        
OnArriveAtWaypoint();
                        
GoToNextWaypoint();
                        break;

                    
// --- ping pong mode ---
                    
case PathMoveType.PingPong:
                        if (
PathDirection == Direction.Backwards)
                        {
                            if (
m_NextWaypoint == 0)
                                
PathDirection Direction.Forward;
                        }
                        else
                        {
                            if (
m_NextWaypoint == (m_Waypoints.Count 1))
                                
PathDirection Direction.Backwards;
                        }
                        
OnArriveAtWaypoint();
                        
GoToNextWaypoint();
                        break;
                }
            }

        }

    
    }


    
/// <summary>
    /// called when a platform in 'Target' mode begins moving
    /// </summary>
    
protected void OnStart()
    {

        
// play the start sound, if any
        
if (SoundStart != null)
            
m_Audio.PlayOneShot(SoundStart);

        
// SNIPPET: here is how to detect whether we are heading out
        // from the first versus going back from the last waypoint
        /*
        if (m_CurrentWaypoint == 0)
            Debug.Log("... departing: " + Time.time);
        else if (m_NextWaypoint == m_Waypoints.Count - 1)
            Debug.Log("... going back: " + Time.time);
        */

    
}
    

    
/// <summary>
    /// called when a platform in any mode touches a waypoint. in 'Target'
    /// mode, the first and last waypoints are not included
    /// </summary>
    
protected void OnArriveAtWaypoint()
    {

        
// play the waypoint sound, if any
        
if (SoundWaypoint != null)
            
m_Audio.PlayOneShot(SoundWaypoint);

    }
    

    
/// <summary>
    /// called when a platform in 'Target' mode arrives at the last waypoint
    /// </summary>
    
protected void OnArriveAtDestination()
    {

        
// if the platform should wait before going back, schedule the return
        
if ((MoveReturnDelay 0.0f) && !m_ReturnDelayTimer.Active)
        {
            
vp_Timer.In(MoveReturnDelaydelegate()
            {
                GoTo(
0);
            }, 
m_ReturnDelayTimer);
        }

    }
    

    
/// <summary>
    /// called when a platform in 'Target' mode stops
    /// </summary>
    
protected void OnStop()
    {

        
m_Audio.Stop();

        
// play the stop sound, if any
        
if (SoundStop != null)
            
m_Audio.PlayOneShot(SoundStop);

        
// snap in place
        
m_Transform.position m_CurrentTargetPosition;
        
m_Transform.eulerAngles m_CurrentTargetAngle;
        
m_Moving false;

        
// if we are returning home and have cooldown, disable platform for a while
        
if (m_NextWaypoint == 0)
            
m_NextAllowedMoveTime Time.time MoveCooldown;

    }


    
/// <summary>
    /// updates platform position according to the current movement
    /// interpolation mode
    /// </summary>
    
protected void UpdateMovement()
    {

        if (
m_Waypoints.Count 2)
            return;

        switch (
MoveInterpolationMode)
        {

            case 
MovementInterpolationMode.EaseInOut:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.Lerp(    m_Transform.position,
                                                                                
m_CurrentTargetPosition,
                                                                                
m_EaseInOutCurve.Evaluate(m_MoveTime)));
                break;
            case 
MovementInterpolationMode.EaseIn:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.MoveTowards(    m_Transform.position,
                                                                                        
m_CurrentTargetPosition,
                                                                                        
m_MoveTime));
                break;
            case 
MovementInterpolationMode.EaseOut:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.Lerp(    m_Transform.position,
                                                                                
m_CurrentTargetPosition,
                                                                                
m_LinearCurve.Evaluate(m_MoveTime)));
                break;
            case 
MovementInterpolationMode.EaseOut2:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.Lerp(    m_Transform.position,
                                                                                
m_CurrentTargetPosition,
                                                                                
MoveSpeed 0.25f));
                break;
            case 
MovementInterpolationMode.Lerp:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.MoveTowards(    m_Transform.position,
                                                                                        
m_CurrentTargetPosition,
                                                                                        
MoveSpeed));
                break;
            case 
MovementInterpolationMode.Slerp:
                
m_Transform.position vp_MathUtility.NaNSafeVector3(Vector3.Slerp(    m_Transform.position,
                                                                                
m_CurrentTargetPosition,
                                                                                
m_LinearCurve.Evaluate(m_MoveTime)));
                break;
        }
    
    }


    
/// <summary>
    /// updates platform angle according to the current rotation
    /// interpolation mode
    /// </summary>
    
protected void UpdateRotation()
    {

        switch (
RotationInterpolationMode)
        {

            case 
RotateInterpolationMode.SyncToMovement:
                if (!
m_Moving)
                    break;
                
m_Transform.eulerAngles vp_MathUtility.NaNSafeVector3(new Vector3(
                
Mathf.LerpAngle(m_OriginalAngle.xm_CurrentTargetAngle.x1.0f - (GetDistanceLeft() / m_TravelDistance)),
                
Mathf.LerpAngle(m_OriginalAngle.ym_CurrentTargetAngle.y1.0f - (GetDistanceLeft() / m_TravelDistance)),
                
Mathf.LerpAngle(m_OriginalAngle.zm_CurrentTargetAngle.z1.0f - (GetDistanceLeft() / m_TravelDistance))));
                break;

            case 
RotateInterpolationMode.EaseOut:
                
m_Transform.eulerAngles vp_MathUtility.NaNSafeVector3(new Vector3(
                
Mathf.LerpAngle(m_Transform.eulerAngles.xm_CurrentTargetAngle.xm_LinearCurve.Evaluate(m_MoveTime)),
                
Mathf.LerpAngle(m_Transform.eulerAngles.ym_CurrentTargetAngle.ym_LinearCurve.Evaluate(m_MoveTime)),
                
Mathf.LerpAngle(m_Transform.eulerAngles.zm_CurrentTargetAngle.zm_LinearCurve.Evaluate(m_MoveTime))));
                break;


            case 
RotateInterpolationMode.CustomEaseOut:
                
m_Transform.eulerAngles vp_MathUtility.NaNSafeVector3(new Vector3(
                
Mathf.LerpAngle(m_Transform.eulerAngles.xm_CurrentTargetAngle.xRotationEaseAmount),
                
Mathf.LerpAngle(m_Transform.eulerAngles.ym_CurrentTargetAngle.yRotationEaseAmount),
                
Mathf.LerpAngle(m_Transform.eulerAngles.zm_CurrentTargetAngle.zRotationEaseAmount)));
                break;

            case 
RotateInterpolationMode.CustomRotate:
                
m_Transform.Rotate(RotationSpeed);
                break;

        }

    }


    
/// <summary>
    /// updates velocity variables for motion interpolation and physics
    /// </summary>
    
protected void UpdateVelocity()
    {

        
// step the movement time
        
m_MoveTime += MoveSpeed 0.01f vp_TimeUtility.AdjustedTimeScale;

        
// calculate velocities, mainly for physics
        
m_PhysicsCurrentMoveVelocity = (m_Transform.position m_PrevPos).magnitude;
        
m_PhysicsCurrentRotationVelocity = (m_Transform.eulerAngles m_PrevAngle).magnitude;

        
// store the final states from this frame, for next velocity calculation
        
m_PrevPos m_Transform.position;
        
m_PrevAngle m_Transform.eulerAngles;

    }



    
/// <summary>
    /// this method can be used by an external script such as trigger
    /// (button / lever) to start a platform and make it go to a specific
    /// waypoint. NOTE: the platform must be in 'Target' Path mode.
    /// </summary>
    
public void GoTo(int targetWayPoint)
    {

        if (!
vp_Gameplay.isMaster)
            return;

        if (
Time.time m_NextAllowedMoveTime)
            return;

        if (
PathType != PathMoveType.Target)
            return;

        
m_TargetedWayPoint GetValidWaypoint(targetWayPoint);

        if (
targetWayPoint m_NextWaypoint)
        {
            if (
PathDirection != Direction.Direct)
                
PathDirection Direction.Forward;
        }
        else
        {
            if (
PathDirection != Direction.Direct)
                
PathDirection Direction.Backwards;
        }

        
m_Moving true;

    }


    
/// <summary>
    /// calculates the distance left to the next waypoint
    /// </summary>
    
protected float GetDistanceLeft()
    {

        if (
m_Waypoints.Count 2)
            return 
0.0f;

        return 
Vector3.Distance(m_Transform.positionm_Waypoints[m_NextWaypoint].position);

    }


    
/// <summary>
    /// selects the next waypoint according to platform path direction
    /// and sets it moving
    /// </summary>
    
protected void GoToNextWaypoint()
    {

        if (
m_Waypoints.Count 2)
            return;
        
m_MoveTime 0;

        if (!
m_Audio.isPlaying)
            
m_Audio.Play();

        
m_CurrentWaypoint m_NextWaypoint;
        
        switch (
PathDirection)
        {
            case 
Direction.Forward:
                
m_NextWaypoint GetValidWaypoint(m_NextWaypoint 1);
                break;
            case 
Direction.Backwards:
                
m_NextWaypoint GetValidWaypoint(m_NextWaypoint 1);
                break;
            case 
Direction.Direct:
                
m_NextWaypoint m_TargetedWayPoint;
                break;
        }
        
        
m_OriginalAngle m_CurrentTargetAngle;
        
m_CurrentTargetPosition m_Waypoints[m_NextWaypoint].position;
        
m_CurrentTargetAngle m_Waypoints[m_NextWaypoint].eulerAngles;
        
        
m_TravelDistance GetDistanceLeft();

        
m_Moving true;

    }


    
/// <summary>
    /// converts the passed waypoint number into the nearest valid
    /// waypoint number (unless it is already valid)
    /// </summary>
    
protected int GetValidWaypoint(int wayPoint)
    {

        if(
wayPoint 0)
            return (
m_Waypoints.Count 1);
            
        if(
wayPoint > (m_Waypoints.Count 1))
            return 
0;

        return 
wayPoint;

    }


    
/// <summary>
    /// NOTE: this method will get called in multiplayer even if we're not
    /// the master (i.e. despite the script being disabled). this is because
    /// 'OnTriggerEnter' will fire regardless of components being disabled
    /// or enabled. this is a good thing since we want the script to send a
    /// 'TryAutoStart' message to the corresponding multiplayer script which
    /// will ask for 
    /// </summary>
    
protected void OnTriggerEnter(Collider col)
    {

        if(!
GetPlayer(col))
            return;

        
TryPushPlayer();

        
TryAutoStart();
        
    }


    
/// <summary>
    /// 
    /// </summary>
    
protected void OnTriggerStay(Collider col)
    {

        if (!
PhysicsSnapPlayerToTopOnIntersect)
            return;

        if (!
GetPlayer(col))
            return;

        
TrySnapPlayerToTop();
            
    }


    
/// <summary>
    /// this method 1) determines if the colliding object is a player
    /// that we will do something about, and 2) stores the collider and
    /// player event handler that will be manipulated. a dictionary is
    /// used to remember past players so we don't have to scan their
    /// hierarchy for an event handler every time
    /// </summary>
    
public bool GetPlayer(Collider col)
    {

        if ((
col.gameObject.layer != vp_Layer.LocalPlayer)
            && (
col.gameObject.layer != vp_Layer.RemotePlayer))
            return 
false;
        
        
// see if this is a valid player object, or auto-approve
        // if it has been recently validated
        
if (!m_KnownPlayers.ContainsKey(col))
        {

            
vp_PlayerEventHandler player col.transform.root.GetComponent<vp_PlayerEventHandler>();

            if (
player == null)
                return 
false;

            
m_KnownPlayers.Add(colplayer);

        }

        if (!
m_KnownPlayers.TryGetValue(colout m_PlayerToPush))
            return 
false;

        
m_PlayerCollider col;

        return 
true;

    }


    
/// <summary>
    /// if the platform runs into a player from the side or the top,
    /// this method will attempt to push the player out of the way
    /// using the player's own horizontal force mechanism
    /// </summary>
    
protected void TryPushPlayer()
    {

        if (
m_PlayerToPush == null || m_PlayerToPush.Platform == null)
            return;

        
// don't push a player that is standing on top of the platform. this
        // assumes a small distance between the player's feet and the top of
        // the platform bounding box (due to charactercontroller 'Skin Width').
        
if (m_PlayerToPush.Position.Get().m_Collider.bounds.max.y)
            return;

        
// don't push around a player if it considers itself attached to the
        // platform. this player has some crazy holding-on-to-skillz!
        
if (m_PlayerToPush.Platform.Get() == m_Transform)
            return;

        
// alright, try to push player away from the center of the platform
        
float speed m_PhysicsCurrentMoveVelocity;
        if (
speed == 0.0f)
            
speed m_PhysicsCurrentRotationVelocity 0.1f;    // if we have no positional speed, use angular speed
        
if(speed 0.0f)
            
m_PlayerToPush.ForceImpact.Send(vp_3DUtility.HorizontalVector(
                -(
m_Transform.position m_PlayerCollider.bounds.center).normalized *
                
speed *
                
m_PhysicsPushForce));

        
// TIP: player could get hurt here

    
}


    
/// <summary>
    /// this method is used to instantly snap the player out of the way
    /// if all else fails. that is, the controller has been forced or
    /// squeezed into the platform and is in a buggy state. if this
    /// happens, we snap player to the top of the platform. NOTE: will
    /// abort for platforms that rotate excessively
    /// </summary>
    
protected void TrySnapPlayerToTop()
    {

        if (
m_PlayerToPush == null || m_PlayerToPush.Platform == null)
            return;

        
// don't snap a player that is already on top of the platform
        
if (m_PlayerToPush.Position.Get().m_Collider.bounds.max.y)
            return;

        
// don't push around a player that's attached to the platform
        
if (m_PlayerToPush.Platform.Get() == m_Transform)
            return;

        
// only snap to top if platform moves in such a way that the top
        // will remain level
        
if (RotationSpeed.!= 0.0f || RotationSpeed.!= 0.0f ||
            
m_CurrentTargetAngle.!= 0.0f || m_CurrentTargetAngle.!= 0.0f)
            return;

        
// only snap if the player bounding box is horizontally and fully
        // encapsulated by the platform bounding box
        
if ((m_Collider.bounds.max.m_PlayerCollider.bounds.max.x) ||
            (
m_Collider.bounds.max.m_PlayerCollider.bounds.max.z) ||
            (
m_Collider.bounds.min.m_PlayerCollider.bounds.min.x) ||
            (
m_Collider.bounds.min.m_PlayerCollider.bounds.min.z))
            return;

        
// approved! snap to top
        
Vector3 newPos m_PlayerToPush.Position.Get();
        
newPos.m_Collider.bounds.max.0.1f;
        
m_PlayerToPush.Position.Set(newPos);

        
// TIP: instead of snapping players to top here, this would also
        // be a great place to gib 'em!

    
}


    
/// <summary>
    /// auto starts the platform if player is on top of it and auto
    /// start is enabled
    /// </summary>
    
public void TryAutoStart()
    {

        if (!
vp_Gameplay.isMaster)
            return;

        if (
MoveAutoStartTarget == 0)
            return;

        if (
m_PhysicsCurrentMoveVelocity 0.0f || m_Moving)
            return;

        GoTo(
MoveAutoStartTarget);

    }
    

    
/// <summary>
    /// 
    /// </summary>
    
protected void OnLevelWasLoaded()
    {

        
m_KnownPlayers.Clear();

    }




زمانی که کد رو اضافه کردید در قسمت path باید یه waypoints اضافه کنید 
اول یک gameobj میسازید اسمشو میزارید open door بعد دوتا دیگه gameobj میسازی اسم یکی1 اسم اون یکی2 بعد باید obj های 1و2 رو در جایی که در قرار باز و بسته شه قرار دهید 
دوم open door رو توی waypoints اضافه میکنیم
برای تعیین نوع باز و بسته شدن در  قسمت type گزینه target رو انتخاب میکنیم تا در کشویی باز شود
برای باز کردن در نیاز به یه کد سوییچ داریم مانند کد زیر
کد php:
using UnityEngine;
using System.Collections;
using System.Collections.Generic;

public class 
vp_PlatformSwitch vp_Interactable
{
    
    public 
float SwitchTimeout 0;                                        // time in seconds before next switch can occur
    
public vp_MovingPlatform Platform null;                            // platform to control
    
public AudioSource AudioSource null;
    public 
Vector2 SwitchPitchRange = new Vector2(1.0f1.5f);
    public List<
AudioClipSwitchSounds = new List<AudioClip>();        // list of sounds to randomly play when switched
    
    
protected bool m_IsSwitched false// is this object in switched mode
    
protected float m_Timeout 0;
    
    
    protected 
override void Start()
    {
        
        
base.Start();
        
        if(
AudioSource == null)
            
AudioSource GetComponent<AudioSource>() == null gameObject.AddComponent<AudioSource>() : GetComponent<AudioSource>();
        
    }
    
    
    
/// <summary>
    /// try to press this platform switch. this will have effect
    /// in singleplayer, but only in multiplayer if we're the
    /// master / server. sounds will always play and timers will
    /// be maintained in case of a master client handover
    /// </summary>
    
public override bool TryInteract(vp_PlayerEventHandler player)
    {

        if(
Platform == null)
            return 
false;
        
        if(
m_Player == null)
            
m_Player player;
        
        if(
Time.time m_Timeout)
            return 
false;

        
PlaySound();

        
// only try to actually operate the platform if we're the master.
        // if we're just a client the master should detect the trigger enter
        // too, and should activate the platform remotely
        
if (vp_Gameplay.isMaster)
            
Platform.SendMessage("GoTo"Platform.TargetedWaypoint == 0SendMessageOptions.DontRequireReceiver);
        else if (
InteractType == vp_InteractType.Normal)
            
this.SendMessage("ClientTryInteract");
        
        
m_Timeout Time.time SwitchTimeout;
        
        
m_IsSwitched = !m_IsSwitched;
        
        return 
true;
        
    }


    
/// <summary>
    /// 
    /// </summary>
    
public virtual void PlaySound()
    {
        
        if(
AudioSource == null)
        {
            
Debug.LogWarning("Audio Source is not set");
            return;
        }
        
        if( 
SwitchSounds.Count == )
            return;
        
        
AudioClip soundToPlay SwitchSoundsRandom.Range0SwitchSounds.Count ) ];
        
        if(
soundToPlay == null)
            return;
        
        
AudioSource.pitch Random.Range(SwitchPitchRange.xSwitchPitchRange.y);
        
AudioSource.PlayOneShotsoundToPlay );
        
    }
    
    
    
/// <summary>
    /// this is triggered when an object enters the collider and
    /// InteractType is set to trigger
    /// </summary>
    
protected override void OnTriggerEnter(Collider col)
    {
        
        
// only do something if the trigger is of type Trigger
        
if (InteractType != vp_InteractType.Trigger)
            return;

        
// see if the colliding object was a valid recipient
        
foreach(string s in RecipientTags)
        {
            if(
col.gameObject.tag == s)
                goto 
isRecipient;
        }
        return;
    
isRecipient:

        
m_Player col.transform.root.GetComponent<vp_PlayerEventHandler>();

        if (
m_Player == null)
            return;

        if((
m_Player.Interactable.Get() != null) && (m_Player.Interactable.Get().GetComponent<Collider>() == col))
            return;
        
        
// calls the TryInteract method which is hopefully on the inherited class
        
TryInteract(m_Player);
        
    }



حالا باید کد رو به در اضافه کنیم 
زمانی که کد اضافه شد در قسمت پلتفرم باید کد قبلی رو تگ کنم 
تمام شود اگر به مشکلی خوردید بگید تا برطرف کنمش
amirsh
amirzarei007_pv
پاسخ
(23/8/1391، 10:10 صبح)ahahah نوشته است:

اقا من یک ماه تمام دنبال اینم که یه کد پیدا کنم که این کارکتر(یه کارکتر کروی شکل ) یه حرکتی بکنه ولی متاسفانه یه ماه من هدر رفت و تا الان دارم سعی میکنم این کد رو پیدا کنم 
یه کد واضح میخوام که مثلا وقتی دکمه w رو فشار بدم رو به جلو حرکت کنه یا همچنین A S D W کد های زیادی پیدا کردم ولی همه شون  بعد از وارد شدن یا ارور میدن یا پلیرم کار نمیکنه 
من فقط کد رو وارد میکنم داخل جاوا یا سی.. و بعد اونرو وارد پلیر میکنم  
درخواست من اینه که اگه کد واضح وتست شده دارید به من بدید و اون بخش کلید ها رو هم همون W A S D بنویسید بعدا من خودم تغییر میدم خواهشا یه کد واضح بدید 
یعنی کار کنه بدون یه هیچ ارور که بازی رو متوقف کنه 
من یه تازه کارم واسه همین از چیزهای ساده وبدون دردسر استفاده میکنم یا حتی اگه از داخل خود یونیتی میشه این کار رو کرد بدون کد نویسی اونو بدین راحتره
پاسخ
Information 
(16/12/1396، 09:40 صبح)خالد عبیدی نوشته است:
(23/8/1391، 10:10 صبح)ahahah نوشته است:

اقا من یک ماه تمام دنبال اینم که یه کد پیدا کنم که این کارکتر(یه کارکتر کروی شکل ) یه حرکتی بکنه ولی متاسفانه یه ماه من هدر رفت و تا الان دارم سعی میکنم این کد رو پیدا کنم 
یه کد واضح میخوام که مثلا وقتی دکمه w رو فشار بدم رو به جلو حرکت کنه یا همچنین A S D W کد های زیادی پیدا کردم ولی همه شون  بعد از وارد شدن یا ارور میدن یا پلیرم کار نمیکنه 
من فقط کد رو وارد میکنم داخل جاوا یا سی.. و بعد اونرو وارد پلیر میکنم  
درخواست من اینه که اگه کد واضح وتست شده دارید به من بدید و اون بخش کلید ها رو هم همون W A S D بنویسید بعدا من خودم تغییر میدم خواهشا یه کد واضح بدید 
یعنی کار کنه بدون یه هیچ ارور که بازی رو متوقف کنه 
من یه تازه کارم واسه همین از چیزهای ساده وبدون دردسر استفاده میکنم یا حتی اگه از داخل خود یونیتی میشه این کار رو کرد بدون کد نویسی اونو بدین راحتره
سلام این کد خودم نیست ولی چند خطش مال خودم 
اینو اد کن روی کارکتر بعد من بعضی عدد هاشو بنا بر نیاز خودم نوشتم خودت تغییرش بده 
بعد هم یه خط هست که سرعت کارکتر رو بنا بر سرعت باد کم و زیاد میکنه میتونی پاکش کنی

کد:
using UnityEngine;
using System.Collections;
using System.Collections.Generic;


public class vp_FPController : vp_CharacterController
{
    
    // general
    protected Vector3 m_FixedPosition = Vector3.zero;        
    protected Vector3 m_SmoothPosition = Vector3.zero;        
    public Vector3 SmoothPosition { get { return m_SmoothPosition; } }    
    public Vector3 Velocity { get { return CharacterController.velocity; } }
    protected bool m_IsFirstPerson = true;

    // collision
    public bool HeadContact { get { return m_HeadContact; } }
    public Vector3 GroundNormal { get { return m_GroundHit.normal; } }
    public float GroundAngle { get { return Vector3.Angle(m_GroundHit.normal, Vector3.up); } }
    protected bool m_HeadContact = false;
    protected RaycastHit m_CeilingHit;                    
    protected RaycastHit m_WallHit;                        

    // physics trigger
    protected CapsuleCollider m_TriggerCollider = null;        
    public bool PhysicsHasCollisionTrigger = true;            
    protected GameObject m_Trigger = null;                    

    // surface identifier
    protected vp_SurfaceIdentifier m_SurfaceIdentifier = null;
    protected vp_SurfaceIdentifier SurfaceIdentifier
    {
        get
        {
            if ((m_SurfaceIdentifier == null))
                m_SurfaceIdentifier = GetComponent<vp_SurfaceIdentifier>();
            return m_SurfaceIdentifier;
        }
    }

    // motor
    public float MotorAcceleration = 0.18f;
    public float MotorDamping = 0.17f;
    public float MotorBackwardsSpeed = 0.65f;
    public float MotorAirSpeed = 0.35f;
    public float MotorSlopeSpeedUp = 1.0f;
    public float MotorSlopeSpeedDown = 1.0f;
    protected Vector3 m_MoveDirection = Vector3.zero;
    protected float m_SlopeFactor = 1.0f;
    protected Vector3 m_MotorThrottle = Vector3.zero;
    protected float m_MotorAirSpeedModifier = 1.0f;
    protected float m_CurrentAntiBumpOffset = 0.0f;

    // jump
    public float MotorJumpForce = 0.18f;
    public float MotorJumpForceDamping = 0.08f;
    public float MotorJumpForceHold = 0.003f;
    public float MotorJumpForceHoldDamping = 0.5f;
    protected int m_MotorJumpForceHoldSkipFrames = 0;
    protected float m_MotorJumpForceAcc = 0.0f;
    protected bool m_MotorJumpDone = true;

    // physics
    public float PhysicsForceDamping = 0.05f;            
    public float PhysicsSlopeSlideLimit = 30.0f;        
    public float PhysicsSlopeSlidiness = 0.15f;            
    public float PhysicsWallBounce = 0.0f;                
    public float PhysicsWallFriction = 0.0f;
    protected Vector3 m_ExternalForce = Vector3.zero;    
    protected Vector3[] m_SmoothForceFrame = new Vector3[120];
    protected bool m_Slide = false;                        
    protected bool m_SlideFast = false;                    
    protected float m_SlideFallSpeed = 0.0f;            
    protected float m_OnSteepGroundSince = 0.0f;        
    protected float m_SlopeSlideSpeed = 0.0f;            
    protected Vector3 m_PredictedPos = Vector3.zero;
    protected Vector3 m_PrevDir = Vector3.zero;
    protected Vector3 m_NewDir = Vector3.zero;
    protected float m_ForceImpact = 0.0f;
    protected float m_ForceMultiplier = 0.0f;
    protected Vector3 CapsuleBottom = Vector3.zero;
    protected Vector3 CapsuleTop = Vector3.zero;


    /// <summary>
    ///
    /// </summary>
    protected override void OnEnable()
    {

        base.OnEnable();

        vp_TargetEvent<Vector3>.Register(m_Transform, "ForceImpact", AddForce);

    }


    /// <summary>
    ///
    /// </summary>
    protected override void OnDisable()
    {

        base.OnDisable();

        vp_TargetEvent<Vector3>.Unregister(m_Root, "ForceImpact", AddForce);

    }


    /// <summary>
    ///
    /// </summary>
    protected override void Start()
    {

        base.Start();

        SetPosition(Transform.position);    

        
        
        if (PhysicsHasCollisionTrigger)
        {

            m_Trigger = new GameObject("Trigger");
            m_Trigger.transform.parent = m_Transform;
            m_Trigger.layer = vp_Layer.LocalPlayer;
            m_Trigger.transform.localPosition = Vector3.zero;

            m_TriggerCollider = m_Trigger.AddComponent<CapsuleCollider>();
            m_TriggerCollider.isTrigger = true;
            m_TriggerCollider.radius = CharacterController.radius + SkinWidth;
            m_TriggerCollider.height = CharacterController.height + (SkinWidth * 2.0f);
            m_TriggerCollider.center = CharacterController.center;

            m_Trigger.gameObject.AddComponent<vp_DamageTransfer>();

            
            if (SurfaceIdentifier != null)
            {
                vp_Timer.In(0.05f, ()=>    
                {
                    vp_SurfaceIdentifier triggerSurfaceIdentifier = m_Trigger.gameObject.AddComponent<vp_SurfaceIdentifier>();
                    triggerSurfaceIdentifier.SurfaceType = SurfaceIdentifier.SurfaceType;
                    triggerSurfaceIdentifier.AllowDecals = SurfaceIdentifier.AllowDecals;
                });
            }

        }

    }


    
    protected override void RefreshCollider()
    {

        base.RefreshCollider();

        // update physics trigger size
        if (m_TriggerCollider != null)
        {
            m_TriggerCollider.radius = CharacterController.radius + SkinWidth;
            m_TriggerCollider.height = CharacterController.height + (SkinWidth * 2.0f);
            m_TriggerCollider.center = CharacterController.center;
        }

    }


    /// <summary>
    /// enables or disables the collider
    /// </summary>
    public override void EnableCollider(bool isEnabled = true)
    {

        if (CharacterController != null)
            CharacterController.enabled = isEnabled;

    }


    /// <summary>
    ///
    /// </summary>
    protected override void Update()
    {

        base.Update();

        
        SmoothMove();

        

    }


    /// <summary>
    ///
    /// </summary>
    protected override void FixedUpdate()
    {

        if (Time.timeScale == 0.0f)
            return;

        
        UpdateMotor();

        
        UpdateJump();

        
        UpdateForces();

        // apply sliding in slopes
        UpdateSliding();

        
        UpdateOutOfControl();
        
        
        FixedMove();

        
        UpdateCollisions();

        
        UpdatePlatformMove();

        // store final position and velocity for next frame's physics calculations
        UpdateVelocity();

    }


    /// <summary>
    /// simulates velocity acceleration and damping in the cardinal
    /// directions
    /// </summary>
    protected virtual void UpdateMotor()
    {

        if (!MotorFreeFly)
            UpdateThrottleWalk();
        else
            UpdateThrottleFree();

        
        m_MotorThrottle = vp_MathUtility.SnapToZero(m_MotorThrottle);

    }

   
    protected virtual void UpdateThrottleWalk()
    {

        
        UpdateSlopeFactor();

        m_MotorAirSpeedModifier = (m_Grounded ? 1.0f : MotorAirSpeed);

        m_MotorThrottle +=
            ((Player.InputMoveVector.Get().y > 0) ? Player.InputMoveVector.Get().y :
            (Player.InputMoveVector.Get().y * MotorBackwardsSpeed))        
            * (Transform.TransformDirection(
            Vector3.forward *
            (MotorAcceleration * 0.1f) *
            m_MotorAirSpeedModifier) *
            m_SlopeFactor);
        m_MotorThrottle += Player.InputMoveVector.Get().x * (Transform.TransformDirection(
            Vector3.right *
            (MotorAcceleration * 0.1f) *
            m_MotorAirSpeedModifier) *
            m_SlopeFactor);

        // dampen motor force
        m_MotorThrottle.x /= (1.0f + (MotorDamping * m_MotorAirSpeedModifier * Time.timeScale));
        m_MotorThrottle.z /= (1.0f + (MotorDamping * m_MotorAirSpeedModifier * Time.timeScale));

    }


    
    protected virtual void UpdateThrottleFree()
    {

        
        m_MotorThrottle += Player.InputMoveVector.Get().y * (Transform.TransformDirection(
            Transform.InverseTransformDirection(((vp_FPPlayerEventHandler)Player).CameraLookDirection.Get()) *
            (MotorAcceleration * 0.1f)));
        m_MotorThrottle += Player.InputMoveVector.Get().x * (Transform.TransformDirection(
            Vector3.right *
            (MotorAcceleration * 0.1f)));

        
        m_MotorThrottle.x /= (1.0f + (MotorDamping * Time.timeScale));
        m_MotorThrottle.z /= (1.0f + (MotorDamping * Time.timeScale));

    }



    protected virtual void UpdateJump()
    {

        
        if (m_HeadContact)
            Player.Jump.Stop(1.0f);

        if (!MotorFreeFly)
            UpdateJumpForceWalk();
        else
            UpdateJumpForceFree();

        // apply accumulated 'hold jump' force
        m_MotorThrottle.y += m_MotorJumpForceAcc * Time.timeScale;

        // dampen forces
        m_MotorJumpForceAcc /= (1.0f + (MotorJumpForceHoldDamping * Time.timeScale));
        m_MotorThrottle.y /= (1.0f + (MotorJumpForceDamping * Time.timeScale));

    }


    
    protected virtual void UpdateJumpForceWalk()
    {

        if (Player.Jump.Active)
        {
            if (!m_Grounded)
            {
                
                if (m_MotorJumpForceHoldSkipFrames > 2)
                {
                    
                    if (!(Player.Velocity.Get().y < 0.0f))
                        m_MotorJumpForceAcc += MotorJumpForceHold;
                }
                else
                    m_MotorJumpForceHoldSkipFrames++;
            }
        }

    }


    
    protected virtual void UpdateJumpForceFree()
    {

        if (Player.Jump.Active && Player.Crouch.Active)
            return;

        if (Player.Jump.Active)
            m_MotorJumpForceAcc += MotorJumpForceHold;
        else if (Player.Crouch.Active)
        {

            m_MotorJumpForceAcc -= MotorJumpForceHold;

            
            if (Grounded && CharacterController.height == m_NormalHeight)
            {
                CharacterController.height = m_CrouchHeight;
                CharacterController.center = m_CrouchCenter;
            }

        }

    }


    protected override void UpdateForces()
    {

        base.UpdateForces();

        
        if (m_SmoothForceFrame[0] != Vector3.zero)
        {
            AddForceInternal(m_SmoothForceFrame[0]);
            for (int v = 0; v < 120; v++)
            {
                m_SmoothForceFrame[v] = (v < 119) ? m_SmoothForceFrame[v + 1] : Vector3.zero;
                if (m_SmoothForceFrame[v] == Vector3.zero)
                    break;
            }
        }

        // dampen external forces
        m_ExternalForce /= (1.0f + (PhysicsForceDamping * vp_TimeUtility.AdjustedTimeScale));

    }


    
    protected virtual void UpdateSliding()
    {

        bool wasSlidingFast = m_SlideFast;
        bool wasSliding = m_Slide;
       
        m_Slide = false;
        if (!m_Grounded)
        {
            m_OnSteepGroundSince = 0.0f;
            m_SlideFast = false;
        }
        
        else if (GroundAngle > PhysicsSlopeSlideLimit)
        {

            m_Slide = true;

            
            if (GroundAngle <= Player.SlopeLimit.Get())
            {
                m_SlopeSlideSpeed = Mathf.Max(m_SlopeSlideSpeed, (PhysicsSlopeSlidiness * 0.01f));
                m_OnSteepGroundSince = 0.0f;
                m_SlideFast = false;
                
                m_SlopeSlideSpeed = (Mathf.Abs(m_SlopeSlideSpeed) < 0.0001f) ? 0.0f :
                    (m_SlopeSlideSpeed / (1.0f + (0.05f * vp_TimeUtility.AdjustedTimeScale)));
            }
            else    
            {
                if ((m_SlopeSlideSpeed) > 0.01f)
                    m_SlideFast = true;
                if (m_OnSteepGroundSince == 0.0f)
                    m_OnSteepGroundSince = Time.time;
                m_SlopeSlideSpeed += (((PhysicsSlopeSlidiness * 0.01f) * ((Time.time - m_OnSteepGroundSince) * 0.125f)) * vp_TimeUtility.AdjustedTimeScale);
                m_SlopeSlideSpeed = Mathf.Max((PhysicsSlopeSlidiness * 0.01f), m_SlopeSlideSpeed);    // keep minimum slidiness
            }

            
            AddForce(Vector3.Cross(Vector3.Cross(GroundNormal, Vector3.down), GroundNormal) *
                m_SlopeSlideSpeed * vp_TimeUtility.AdjustedTimeScale);

        }
        else
        {
            m_OnSteepGroundSince = 0.0f;
            m_SlideFast = false;
            m_SlopeSlideSpeed = 0.0f;
        }

        
        if (m_MotorThrottle != Vector3.zero)
            m_Slide = false;

        
        if (m_SlideFast)
            m_SlideFallSpeed = Transform.position.y;    
        else if (wasSlidingFast && !Grounded)
            m_FallSpeed = Transform.position.y - m_SlideFallSpeed;    

        

        if (wasSliding != m_Slide)
            Player.SetState("Slide", m_Slide);

    }


    
    void UpdateOutOfControl()
    {

        if ((m_ExternalForce.magnitude > 0.2f) ||        // TODO: make 0.2 a constant
            (m_FallSpeed < -0.2f) ||    // TODO: make 0.2 a constant
                (m_SlideFast == true))
            Player.OutOfControl.Start();
        else if (Player.OutOfControl.Active)
                Player.OutOfControl.Stop();

    }



    protected override void FixedMove()
    {

        // --- apply forces ---
        m_MoveDirection = Vector3.zero;
        m_MoveDirection += m_ExternalForce;
        m_MoveDirection += m_MotorThrottle;
        m_MoveDirection.y += m_FallSpeed;

        m_CurrentAntiBumpOffset = 0.0f;
        if (m_Grounded && m_MotorThrottle.y <= 0.001f)
        {
            m_CurrentAntiBumpOffset = Mathf.Max(Player.StepOffset.Get(), Vector3.Scale(m_MoveDirection, (Vector3.one - Vector3.up)).magnitude);
            m_MoveDirection += m_CurrentAntiBumpOffset * Vector3.down;
        }

        m_PredictedPos = Transform.position + vp_MathUtility.NaNSafeVector3(m_MoveDirection * Delta * Time.timeScale);

        if (m_Platform != null && PositionOnPlatform != Vector3.zero)
                Player.Move.Send(vp_MathUtility.NaNSafeVector3(m_Platform.TransformPoint(PositionOnPlatform) -
                                                                        m_Transform.position));

        // move on our own
        Player.Move.Send(vp_MathUtility.NaNSafeVector3(m_MoveDirection * Delta * Time.timeScale));

        // while there is an active death event, block movement input
        if (Player.Dead.Active)
        {
            Player.InputMoveVector.Set(Vector2.zero);
            return;
        }

        // --- store ground info ---
        StoreGroundInfo();

        
        if (!m_Grounded && (Player.Velocity.Get().y > 0.0f))
        {
            Physics.SphereCast(new Ray(Transform.position, Vector3.up),
                                        Player.Radius.Get(), out m_CeilingHit,
                                        Player.Height.Get() - (Player.Radius.Get() - SkinWidth) + 0.01f,
                                        vp_Layer.Mask.ExternalBlockers);
            m_HeadContact = (m_CeilingHit.collider != null);
        }
        else
            m_HeadContact = false;

        // --- handle loss of grounding ---
        if ((m_GroundHitTransform == null) && (m_LastGroundHitTransform != null))
        {
            
            
            if (m_Platform != null && PositionOnPlatform != Vector3.zero)
            {
                AddForce(m_Platform.position - m_LastPlatformPos);
                m_Platform = null;
            }

            
            if (m_CurrentAntiBumpOffset != 0.0f)
            {
                Player.Move.Send(vp_MathUtility.NaNSafeVector3(m_CurrentAntiBumpOffset * Vector3.up) * Delta * Time.timeScale);
                m_PredictedPos += vp_MathUtility.NaNSafeVector3(m_CurrentAntiBumpOffset * Vector3.up) * Delta * Time.timeScale;
                m_MoveDirection += m_CurrentAntiBumpOffset * Vector3.up;
            }

        }


    }
    

    
    protected virtual void SmoothMove()
    {

        if (Time.timeScale == 0.0f)
            return;

        // restore last smoothpos
        m_FixedPosition = Transform.position;    // backup fixedpos
        Transform.position = m_SmoothPosition;

        // move controller to get the smooth position
        Player.Move.Send(vp_MathUtility.NaNSafeVector3((m_MoveDirection * Delta * Time.timeScale)));
        m_SmoothPosition = Transform.position;
        Transform.position = m_FixedPosition;    // restore fixedpos

        // reset smoothpos in these cases
        if ((Vector3.Distance(Transform.position, m_SmoothPosition) > Player.Radius.Get())    // smoothpos deviates too much
            || (m_Platform != null) && ((m_LastPlatformPos != m_Platform.position)))        // we're on a platform thas is moving (causes jitter)
            m_SmoothPosition = Transform.position;

        // lerp smoothpos back to fixedpos slowly over time
        m_SmoothPosition = Vector3.Lerp(m_SmoothPosition, Transform.position, Time.deltaTime);

    }


    
    protected override void UpdateCollisions()
    {

        base.UpdateCollisions();

        if (m_OnNewGround)
        {

            // deflect the controller sideways under some circumstances
            if (m_WasFalling)
            {

                DeflectDownForce();

                
                m_SmoothPosition.y = Transform.position.y;

                // reset all the jump variables
                m_MotorThrottle.y = 0.0f;
                m_MotorJumpForceAcc = 0.0f;
                m_MotorJumpForceHoldSkipFrames = 0;
            }
            // detect and store moving platforms    // TODO: should be in base class for AI
            if (m_GroundHit.collider.gameObject.layer == vp_Layer.MovingPlatform)
            {
                m_Platform = m_GroundHitTransform;
                m_LastPlatformAngle = m_Platform.eulerAngles.y;
            }
            else
                m_Platform = null;

        }


        if ((m_PredictedPos.y > Transform.position.y) && (m_ExternalForce.y > 0 || m_MotorThrottle.y > 0))
            DeflectUpForce();

        if ((m_PredictedPos.x != Transform.position.x) ||
            (m_PredictedPos.z != Transform.position.z) &&
            (m_ExternalForce != Vector3.zero))
            DeflectHorizontalForce();

    }
    

    protected virtual void UpdateSlopeFactor()
    {

        if (!m_Grounded)
        {
            m_SlopeFactor = 1.0f;
            return;
        }

        
        m_SlopeFactor = 1 + (1.0f - (Vector3.Angle(m_GroundHit.normal, m_MotorThrottle) / 90.0f));

        if (Mathf.Abs(1 - m_SlopeFactor) < 0.01f)
            m_SlopeFactor = 1.0f;        
        else if (m_SlopeFactor > 1.0f)
        {
            
            if (MotorSlopeSpeedDown == 1.0f)
            {
                
                m_SlopeFactor = 1.0f / m_SlopeFactor;
                m_SlopeFactor *= 1.2f;
            }
            else
                m_SlopeFactor *= MotorSlopeSpeedDown;    // apply user defined multiplier
        }
        else
        {
            // moving uphill
            if (MotorSlopeSpeedUp == 1.0f)
            {
                
                m_SlopeFactor *= 1.2f;
            }
            else
                m_SlopeFactor *= MotorSlopeSpeedUp;    // apply user defined multiplier

            m_SlopeFactor = (GroundAngle > Player.SlopeLimit.Get()) ? 0.0f : m_SlopeFactor;

        }

    }
    


    protected override void UpdatePlatformMove()
    {

        base.UpdatePlatformMove();

    
        if (m_Platform != null)
            m_SmoothPosition = Transform.position;

    }

    
    /// <summary>
    ///
    /// </summary>
    protected override void UpdatePlatformRotation()    
    {

        if (m_Platform == null)
            return;

        base.UpdatePlatformRotation();

    }
    

    public override void SetPosition(Vector3 position)
    {

        base.SetPosition(position);
        m_SmoothPosition = position;

    }
    

    protected virtual void AddForceInternal(Vector3 force)
    {
        m_ExternalForce += force;
    }


    
    public virtual void AddForce(float x, float y, float z)
    {
        AddForce(new Vector3(x, y, z));
    }


    
    public virtual void AddForce(Vector3 force)
    {

        if (Time.timeScale >= 1.0f)
            AddForceInternal(force);
        else
            AddSoftForce(force, 1);

    }


    
    public virtual void AddSoftForce(Vector3 force, float frames)
    {

        force /= Time.timeScale;

        frames = Mathf.Clamp(frames, 1, 120);

        AddForceInternal(force / frames);

        for (int v = 0; v < (Mathf.RoundToInt(frames) - 1); v++)
        {
            m_SmoothForceFrame[v] += (force / frames);
        }

    }


    
    public virtual void StopSoftForce()
    {

        for (int v = 0; v < 120; v++)
        {
            if (m_SmoothForceFrame[v] == Vector3.zero)
                break;
            m_SmoothForceFrame[v] = Vector3.zero;
        }

    }


    
    public override void Stop()
    {

        base.Stop();

        m_MotorThrottle = Vector3.zero;
        m_MotorJumpDone = true;
        m_MotorJumpForceAcc = 0.0f;
        m_ExternalForce = Vector3.zero;
        StopSoftForce();
        m_SmoothPosition = Transform.position;
        
    }


    
    public virtual void DeflectDownForce()
    {
        
        
        if (GroundAngle > PhysicsSlopeSlideLimit)
        {
            m_SlopeSlideSpeed = m_FallImpact * (0.25f * Time.timeScale);
        }

        
        if (GroundAngle > 85)
        {
            m_MotorThrottle += (vp_3DUtility.HorizontalVector((GroundNormal * m_FallImpact)));
            m_Grounded = false;
        }

    }


    
    protected virtual void DeflectUpForce()
    {

        if (!m_HeadContact)
            return;

        
        m_NewDir = Vector3.Cross(Vector3.Cross(m_CeilingHit.normal, Vector3.up), m_CeilingHit.normal);
        m_ForceImpact = (m_MotorThrottle.y + m_ExternalForce.y);
        Vector3 newForce = m_NewDir * (m_MotorThrottle.y + m_ExternalForce.y) * (1.0f - PhysicsWallFriction);
        m_ForceImpact = m_ForceImpact - newForce.magnitude;
        AddForce(newForce * Time.timeScale);
        m_MotorThrottle.y = 0.0f;
        m_ExternalForce.y = 0.0f;
        m_FallSpeed = 0.0f;

        
        m_NewDir.x = (Transform.InverseTransformDirection(m_NewDir).x);

        Player.HeadImpact.Send(((m_NewDir.x < 0.0f) || (m_NewDir.x == 0.0f && (Random.value < 0.5f))) ? -m_ForceImpact : m_ForceImpact);

    }


    protected virtual void DeflectHorizontalForce()
    {

        
        m_PredictedPos.y = Transform.position.y;
        m_PrevPosition.y = Transform.position.y;
        m_PrevDir = (m_PredictedPos - m_PrevPosition).normalized;

        
        CapsuleBottom = m_PrevPosition + Vector3.up * (Player.Radius.Get());
        CapsuleTop = CapsuleBottom + Vector3.up * (Player.Height.Get() - (Player.Radius.Get() * 2));

        
        if (!(Physics.CapsuleCast(CapsuleBottom, CapsuleTop, Player.Radius.Get(), m_PrevDir,
            out m_WallHit, Vector3.Distance(m_PrevPosition, m_PredictedPos), vp_Layer.Mask.ExternalBlockers)))
            return;

        
        m_NewDir = Vector3.Cross(m_WallHit.normal, Vector3.up).normalized;
        if ((Vector3.Dot(Vector3.Cross((m_WallHit.point - Transform.position),
            (m_PrevPosition - Transform.position)), Vector3.up)) > 0.0f)
            m_NewDir = -m_NewDir;

        
        m_ForceMultiplier = Mathf.Abs(Vector3.Dot(m_PrevDir, m_NewDir)) * (1.0f - (PhysicsWallFriction));

        // if the controller has wall bounciness, apply it
        if (PhysicsWallBounce > 0.0f)
        {
            m_NewDir = Vector3.Lerp(m_NewDir, Vector3.Reflect(m_PrevDir, m_WallHit.normal), PhysicsWallBounce);
            m_ForceMultiplier = Mathf.Lerp(m_ForceMultiplier, 1.0f, (PhysicsWallBounce * (1.0f - (PhysicsWallFriction))));
        }

        // deflect current force and report the impact
        m_ForceImpact = 0.0f;
        float yBak = m_ExternalForce.y;
        m_ExternalForce.y = 0.0f;
        m_ForceImpact = m_ExternalForce.magnitude;
        m_ExternalForce = m_NewDir * m_ExternalForce.magnitude * m_ForceMultiplier;
        m_ForceImpact = m_ForceImpact - m_ExternalForce.magnitude;
        for (int v = 0; v < 120; v++)
        {
            if (m_SmoothForceFrame[v] == Vector3.zero)
                break;
            m_SmoothForceFrame[v] = m_SmoothForceFrame[v].magnitude * m_NewDir * m_ForceMultiplier;
        }
        m_ExternalForce.y = yBak;

        

    }

    
    
    public float CalculateMaxSpeed(string stateName = "Default", float accelDuration = 5.0f)
    {

        if (stateName != "Default")
        {
            bool foundState = false;
            foreach (vp_State s in States)
            {
                if (s.Name == stateName)
                    foundState = true;
            }

            if (!foundState)
            {
                Debug.LogError("Error (" + this + ") Controller has no such state: '" + stateName + "'.");
                return 0.0f;
            }
        }

        Dictionary<vp_State, bool> statesBackup = new Dictionary<vp_State, bool>();
        foreach (vp_State s in States)
        {
            statesBackup.Add(s, s.Enabled);
            s.Enabled = false;
        }

        // reset state manager so only the default state is active
        StateManager.Reset();

        // enable the user passed state (if any)
        if (stateName != "Default")
            SetState(stateName, true);

        float speed = 0.0f;
        float seconds = 5.0f;
        for (int v = 0; v < 60 * seconds; v++)
        {
            speed += (MotorAcceleration * 0.1f) * 60.0f;
            speed /= (1.0f + MotorDamping);
        }

        
        foreach (vp_State s in States)
        {
            bool enabled;
            statesBackup.TryGetValue(s, out enabled);
            s.Enabled = enabled;
        }

        return speed;

    }


    
    protected virtual void OnControllerColliderHit(ControllerColliderHit hit)
    {
    

        if (hit.gameObject.isStatic)
            return;

        if (hit.gameObject.layer == vp_Layer.Debris)
            return;

        
        Rigidbody body = hit.collider.attachedRigidbody;

        // abort if there was no rigidbody
        if (body == null)
            return;

        
        if (vp_Gameplay.IsMaster && body.isKinematic)
            return;

        // abort if we can't push yet
        if (Time.time < m_NextAllowedPushTime)
            return;
        m_NextAllowedPushTime = Time.time + PhysicsPushInterval;

    
        if (vp_Gameplay.IsMultiplayer)
            vp_TargetEvent<Vector3, Vector3>.Send(body, "Push", hit.moveDirection, hit.point);
        else
            PushRigidbody(body, hit.moveDirection, hit.point);    // in singleplayer, go ahead and push the rigidbody

    }


    protected virtual bool CanStart_Jump()
    {

        // always allowed to move vertically in free fly mode
        if (MotorFreeFly)
            return true;

        // can't jump without ground contact
        if (!m_Grounded)
            return false;

        // can't jump until the previous jump has stopped
        if (!m_MotorJumpDone)
            return false;

        // can't bunny-hop up steep surfaces
        if (GroundAngle > Player.SlopeLimit.Get())
            return false;

        // passed the test!
        return true;

    }


    
    protected virtual bool CanStart_Run()
    {

        // can't start running while crouching
        if (Player.Crouch.Active)
            return false;

        return true;

    }



    protected virtual void OnStart_Jump()
    {

        m_MotorJumpDone = false;

        // disable impulse jump if we have no grounding in free fly mode
        if (MotorFreeFly && !Grounded)
            return;

        // perform impulse jump
        m_MotorThrottle.y = (MotorJumpForce / Time.timeScale);

        // sync camera y pos
        m_SmoothPosition.y = Transform.position.y;

    }


    /// <summary>
    /// this callback is triggered when the 'Jump' activity deactivates
    /// </summary>
    protected virtual void OnStop_Jump()
    {

        m_MotorJumpDone = true;

    }


    
    protected virtual bool CanStop_Crouch()
    {

        // can't stop crouching if there is a blocking object above us
        if (Physics.SphereCast(new Ray(Transform.position, Vector3.up),
                Player.Radius.Get(),
                (m_NormalHeight - Player.Radius.Get() + 0.01f),
                vp_Layer.Mask.ExternalBlockers))
        {

            // regulate stop test interval to reduce amount of sphere casts
            Player.Crouch.NextAllowedStopTime = Time.time + 1.0f;

            // found a low ceiling above us - abort getting up
            return false;

        }

        // nothing above us - okay to get up!
        return true;

    }


    
    protected virtual void OnMessage_ForceImpact(Vector3 force)
    {
        AddForce(force);
    }


    
    protected virtual Vector3 OnValue_MotorThrottle
    {
        get { return m_MotorThrottle; }
        set { m_MotorThrottle = value; }
    }


    
    protected virtual bool OnValue_MotorJumpDone
    {
        get { return m_MotorJumpDone; }
    }

    
    
    protected virtual bool OnValue_IsFirstPerson
    {

        get
        {
            return m_IsFirstPerson;
        }
        set
        {
            m_IsFirstPerson = value;
        }

    }


    /// <summary>
    ///
    /// </summary>
    protected virtual void OnStart_Dead()
    {
        m_Platform = null;
    }


    /// <summary>
    /// TEMP: (test)
    /// </summary>
    protected virtual void OnStop_Dead()
    {
        Player.OutOfControl.Stop();
    }


}
amirsh
amirzarei007_pv
پاسخ


موضوعات مرتبط با این موضوع...
موضوع نویسنده پاسخ بازدید آخرین ارسال
Star آموزش یونیتی از سایت یونیتی ali.z 0 400 25/4/1396، 03:49 عصر
آخرین ارسال: ali.z



کاربرانِ درحال بازدید از این موضوع: 1 مهمان
آموزش ساخت بازی با C# آموزش پروژه محور یونیتی Unity آموزش ساخت بازی حدس تصویر
آموزش مدل سازی در Maya آموزش یونیتی Unity- ساخت منو آموزش گنجینه برنامه نویسی اندروید
آموزش مدل سازی با 3Ds Max آموزش متحرک سازی با Unity آموزش گرافیک کامپیوتری با OpenGL
آموزش متحرک سازی در 3Ds Max مجموعه آموزش های ساخت بازی آموزش ساخت بازی در ویژوال بیسیک
● آموزش های رایگان ● تبلیغات دیجیتال هوشمند ● استخدام در فرادرس