2016-06-27 4 views
1

게임을하는 클라이언트가 항목을 구입하고 네트워크를 통해 해당 항목을 생성하도록 허용하려고합니다. 이렇게하려면 두 개의 스크립트, 플레이어의 스크립트 및 항목 구입 버튼의 스크립트를 사용하고 있습니다. NetworkServer.Spawn()은 서버에서만 호출 할 수 있으므로 구매 항목 스크립트에서 수행하는 대신 내 항목을 생성하는 플레이어 함수에 명령 함수를 만들었습니다. 그러나이 문제를 해결할 때 NullReferenceException 오류가 발생했습니다.은 전달한 인수가 null임을 나타냅니다. 인수가 null 인 이유는 무엇입니까?클라이언트에서 서버로 보낼 때 인수가 null이되었습니다.

구입 항목 스크립트 코드 :

void BuyItemAndSubtractGold(){ 
    GameObject item = SearchForItem(); 
    int cost = item.GetComponent<ItemManager_ItemStats>().item.buyValue; 
    if (item.GetComponent<ItemManager_ItemStats>() != null && storeMaster.gold >= cost) { 
     GameObject newItem = (GameObject)Instantiate (item); 
     playerMaster.CmdSpawnOnServer (newItem); 
     newItem.transform.parent = playerInventory.transform; 
     newItem.SetActive (false); 
     Vector3 gunPosition = newItem.GetComponent<ItemManager_ItemPickup>().gunPositions [0]; 
     newItem.transform.localPosition = gunPosition; 
     newItem.transform.rotation = Quaternion.Euler(itemThrow.originalRotation); 
     storeMaster.gold -= cost; 
     audioSource.clip = boughtItem; 
     audioSource.Play(); 
     storeMaster.CallEventUpdateUI(); 
     sellInventory.LoadInventory(); 
     playerMaster.CmdCallEventInventoryChanged(); 
    } else { 
     noGold.SetActive (true); 
     StartCoroutine (wait5sec()); 
    } 
} 

플레이어 스크립트 코드 : 명령을 통해 게임 오브젝트를 보내려고 같은 오류 enter image description here

+1

당신은 시스템이'NetworkIdentity' 구성 요소에 대해보고가는 경우가'NullReferenceException'가 발생 알 수 있습니다. 여러분이 클라이언트 - 서버 아키텍처를 해결하려고 노력하고있는 것처럼 보입니다.하지만 좋은 접근 방식이 아닐 수도 있습니다. 자습서를 확인하는 것이 좋습니다. – rutter

+0

@rutter 좋은 자습서를 추천 해 주시겠습니까? –

답변

1

[Command] 
public void CmdSpawnOnServer(GameObject item){ 
    print (item != null); 
    NetworkServer.Spawn (item); 
} 

사진이 보인다. command, clientrpc 및 syncvar를 통해 전송할 수있는 인수는 특정 유형으로 제한되며 gameObject는 그 중 하나가 아닌 것으로 보입니다. 이 작업을 수행하는 대신 지원되는 유형 (항목 ID를 지정하는 int와 같음)을 사용하거나 사용자 정의 값 유형 (구조체)을 만드는 방법이 있습니다. 전달 될 때 인수가 null이되는 것은 명령이 인수로 gameobjects를 지원하지 않는다는 사실 때문인 것 같습니다. 따라서 오류를 해결하려면 지원되는 유형을 통해 값을 보내야합니다. 예를 들어, gameobjects 항목의 배열을 포함하는 클래스를 만든 다음 원하는 게임 객체의 인덱스를 지정하는 정수를 사용하여 명령을 보낼 수 있습니다. 그런 다음 전송 된 정수 값을 사용하여 원하는 항목 gameObject를 검색하십시오. 유효한 유형에 대한

자세한 내용은 여기에서 볼 수 있습니다 : http://answers.unity3d.com/questions/1001474/unet-parameter-restrictions-for-command-and-client.html

+0

syncvars를 사용하여 검색 할 정수를 사용하는 게임 객체가 클라이언트와 서버에 모두 존재하는지 확인해야합니까? –

+0

나와 함께 제공된 링크에서 메서드를 사용할 때 networkID가 성공적으로 전송되었지만 ClientScene.FindLocalObject (itemID) 또는 NetworkServer.FindLocalObject (itemID)를 사용하여 gameobject에 액세스하려고 할 때마다 null 참조 예외가 발생합니다. –

+0

첫 번째 의견에 대한 답변 - 아니요, 그렇지 않습니다. gameobject 항목이 포함 된 배열을 가진 스크립트를 유지할 수 있습니다 (클라이언트 및 서버 빌드 모두에서). 이것은 서버 및 클라이언트 빌드 (목록 스크립트가 연결된 빈 게임 객체 일 수 있음)에 있기 때문에 클라이언트 및 서버에 항목이 있는지 확인할 필요가 없습니다. 필요한 경우에만이 작업을 수행 할 수 있습니다. 게임 플레이를 통해 무기가 동적으로 생성되는 경우 (무기가 아닌 경우), 더 많은 데이터를 보내거나 사용자 정의 구조체를 사용할 수 있습니다. – user3210251

관련 문제