1

UNET で動作するはずのプレーヤー コントローラーがあります。ゲームに参加しているリモートプレイヤーは自分のキャラクターを制御できないため、何かを理解する必要はありません.

ホストしているローカル プレイヤーは、自分のキャラクターをうまくコントロールできます。

基本的に、これが機能していると私が思うUpdate方法は、ローカルプレーヤーでキーを押すことができるということです。これらのキープレスCommandは、同期されたブール値が設定されているサーバーに s を発行します。

サーバーではFixedUpdate、設定されたブール値に基づいて Rigidbody を移動します。プレーヤー オブジェクトには NetworkTransform があるため、サーバーが行うすべての動きをクライアントに送り返す必要があります。

using UnityEngine;
using UnityEngine.Networking;
using System.Collections;

[RequireComponent(typeof(NetworkIdentity))]
public class PlayerController : NetworkBehaviour {
    public GameObject NormalBullet;

    public Vector3 size = new Vector3(0.25f, 0.25f, 0.25f);
    private float speed = 8;
    private float angularSpeed = 35;
    private float jumpForce = 10;

    private Rigidbody _rigidbody;
    private Map _map;
    private NHNetworkedPool _pool;

    private bool _active = false;
    private Vector3 _lastPosition;

    [SyncVar]
    private bool _moveForward;
    [SyncVar]
    private bool _moveBackward;
    [SyncVar]
    private bool _turnLeft;
    [SyncVar]
    private bool _turnRight;
    [SyncVar]
    private bool _jump;
    [SyncVar]
    private bool _isgrounded;
    [SyncVar]
    private bool _isFireing;

    void Awake () {
        Messenger.AddListener ("MAP_LOADED", OnMapLoaded);

        _rigidbody = gameObject.GetComponent<Rigidbody> ();
        _map = GameObject.Find ("Map").GetComponent<Map> ();

        Physics.IgnoreLayerCollision(LayerMask.NameToLayer("Players"), LayerMask.NameToLayer("Players"), true);
    }

    override public void OnStartClient () {
        _rigidbody.position = new Vector3 (-100, -100, -100);

        if (NetworkServer.active) {
            _pool = FindObjectOfType<NHNetworkedPool> ();
        }
    }

    /// <summary>
    /// Once the board is built, hookup the camera if this is the local player
    /// and set the player as active.
    /// </summary>
    void OnMapLoaded () {
        if (isLocalPlayer) {
            // Hook up the camera
            PlayerCamera cam = Camera.main.GetComponent<PlayerCamera>();
            cam.target = transform;

            // Move the player to the it's spawn location
            CmdSpawn();
        }

        // Set the player as active
        _active = true;
    }

    /// <summary>
    /// Only and active local player should be able to
    /// issue commands for the player
    /// </summary>
    void Update () {
        if (!isLocalPlayer || !_active) {
            return;
        }

        if (Input.GetKeyDown ("up")) {
            CmdSetMoveForward (true);
        }
        if (Input.GetKeyUp ("up")) {
            CmdSetMoveForward (false);
        }
        if (Input.GetKeyDown ("down")) {
            CmdSetMoveBackward (true);
        }
        if (Input.GetKeyUp ("down")) {
            CmdSetMoveBackward (false);
        }
        if (Input.GetKeyDown ("left")) {
            CmdSetTurnLeft (true);
        }
        if (Input.GetKeyUp ("left")) {
            CmdSetTurnLeft (false);
        }
        if (Input.GetKeyDown ("right")) {
            CmdSetTurnRight (true);
        }
        if (Input.GetKeyUp ("right")) {
            CmdSetTurnRight (false);
        }
        if (Input.GetKeyDown (KeyCode.Space)) {
            CmdSetJump (true);
        }
        if (Input.GetKeyUp (KeyCode.Space)) {
            CmdSetJump (false);
        }
        if (Input.GetKeyDown (KeyCode.LeftShift)) {
            CmdSetShooting(true);
        }
        if (Input.GetKeyUp (KeyCode.LeftShift)) {
            CmdSetShooting(false);
        }
    }

    /// <summary>
    /// Only the server should update the player's location
    /// the transform is synced to the clients
    /// </summary>
    void FixedUpdate () {
        if (!isServer) {
            return;
        }

        if (_moveForward) {
            float moveAmount = speed * Time.deltaTime;
            _rigidbody.MovePosition(_rigidbody.position + _rigidbody.transform.forward * moveAmount);
        }

        if (_moveBackward) {
            float moveAmount = (-speed * 0.6f) * Time.deltaTime;
            _rigidbody.MovePosition(_rigidbody.position + _rigidbody.transform.forward * moveAmount);
        }

        if (_turnLeft) {
            Quaternion rotateAmount = Quaternion.Euler(new Vector3(0f, -angularSpeed, 0f) * Time.deltaTime);
            _rigidbody.MoveRotation(_rigidbody.rotation * rotateAmount);
        }

        if (_turnRight) {
            Quaternion rotateAmount = Quaternion.Euler(new Vector3(0f, angularSpeed, 0f) * Time.deltaTime);
            _rigidbody.MoveRotation(_rigidbody.rotation * rotateAmount);
        }

        if (_jump && _isgrounded) {
            _rigidbody.AddForce(Vector3.up * 250);
        }
    }

    void OnCollisionStay (Collision collision) {
        if(collision.gameObject.tag.ToUpper() == "GROUND") {
            _isgrounded = true;
        }
    }

    void OnCollisionExit (Collision collision) {
        if(collision.gameObject.tag.ToUpper() == "GROUND") {
            _isgrounded = false;
        }
    }

    /// <summary>
    /// Client -> Server
    /// Move the player to a spawn location
    /// </summary>
    void CmdSpawn() {
        _rigidbody.position = _map.GetPlayerSpawn();
        _rigidbody.velocity = Vector3.zero;
    }

    /// <summary>
    /// Client -> Server
    /// Set the forward move of the player on/off
    /// </summary>
    [Command]
    void CmdSetMoveForward (bool active) {
        _moveForward = active;
    }

    /// <summary>
    /// Client -> Server
    /// Set the backward of the player on/off
    /// </summary>
    [Command]
    void CmdSetMoveBackward (bool active) {
        _moveBackward = active;
    }

    /// <summary>
    /// Client -> Server
    /// Set the left turn of the player on/off
    /// </summary>
    [Command]
    void CmdSetTurnLeft (bool active) {
        _turnLeft = active;
    }

    /// <summary>
    /// Client -> Server
    /// Set the right turn of the player on/off
    /// </summary>
    [Command]
    void CmdSetTurnRight (bool active) {
        _turnRight = active;
    }

    /// <summary>
    /// Client -> Server
    /// Set the jumpping of the player on/off
    /// </summary>
    [Command]
    void CmdSetJump (bool active) {
        _jump = active;
    }

    /// <summary>
    /// Client -> Server
    /// Set shooting weapon on/off
    /// </summary>
    [Command]
    void CmdSetShooting (bool active) {
        _isFireing = true;
    }
}
4

1 に答える 1

0

サーバー上で移動を行うべきではありません。クライアント上で動きを計算して実行するように書き換えます。次に、NetworkTransform コンポーネントをプレーヤーに追加すると、機能するはずです。

Fire メソッドのみが である必要がありCommandます。_isFireing = trueしかし、正確に何を書くべきかを伝えることができない場合、実際に何が起こるかわかりません;)

編集:プレーヤーがない場合は、プレーヤーに NetworkIdentity コンポーネントも必要です。

于 2016-03-11T21:12:57.860 に答える