我一直在抨击这个RPC调用几个小时,尽管谷歌搜索广泛,但我无法弄清楚出了什么问题。
目前,我正在团结编辑器中进行所有测试,(如果重要的话,播放器设置为在后台运行)。
出于某种原因,我的RPC调用没有通过。
代码中有很多东西,所以唯一重要的一点(我认为)是:
public void GenerateDungeon()
{
Debug.Log ("GENERATING DUNGEON");
tiles = dungeon.SetDungeonData();
//Begin looking through every single tile
for(int i = 0; i < tiles.Length; i++)
{
//If our tile is something useful, aka not a void area in the dungeon
if(tiles[i] != 0){
//Bogus location
int x = 0;
int z = 0;
//Real World Location
convert.ConvertIndexToXY(i,ref x,ref z);
//Wouldn't need if I understood the math, but since I don't being extra careful
int leftTile = tiles[convert.ConvertXYToIndex(x-1,z)];
int rightTile = tiles[convert.ConvertXYToIndex(x+1,z)];
int topTile = tiles[convert.ConvertXYToIndex(x,z-1)];
int bottomTile = tiles[convert.ConvertXYToIndex(x,z+1)];
//Create a base layer for compairing dungeon
CreateDebugDungeon(x,z);
//Determine what we are trying to spawn, and spawn it
if(tiles[i] == (short)Enums.TileType.Corner)
CheckCorners(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
if(tiles[i] == (short)Enums.TileType.OneWall)
CheckOneWalls(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
if(tiles[i] == (short)Enums.TileType.FloorAndRoof)
CreateTile((int)Enums.TileType.FloorAndRoof, x,z,0,dungeonWidth,dungeonHeight);
if(tiles[i] == (short)Enums.TileType.Corridor)
CheckCorridors(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
}//end if tiles != 0
}//end for
Debug.Log ("Done pushing tiles");
//networkView.RPC("SpawnCharacter",RPCMode.AllBuffered, team1Spawn);
networkView.RPC ("SpawnCharacter",RPCMode.All);
//networkView.RPC ("Merp",RPCMode.All);
//networkView.RPC ("PushTiles",RPCMode.All);
//Debug.Log ("Merr?");
}//end generate dungeon
[RPC]
void SpawnCharacter()
{
Debug.Log ("Spawning character at : " );
//Instantiate(character,position, Quaternion.identity);
}
目前,这应该只被称为服务器端。
以下是该脚本的完整代码:
using UnityEngine;
using System.Collections;
/// <summary>
/// BSP Spawning Script is responsible creating a dungeon from scratch to finished.
/// </summary>
public class BSPSpawningScript : MonoBehaviour{
public int dungeonWidth = 80;
public int dungeonHeight = 80;
public int numSplits = 4;
public GameObject character;
public float charYOffset;
short[] tiles;
BSPDungeon dungeon;
CoConvert convert;
bool team1 = false;
bool team2 = false;
GameObject lastTile;
Vector3 team1Spawn;
void Start()
{
if(Network.isClient)
{
GameObject.Destroy(this.gameObject);
Debug.Log ("Destroying");
}
convert = new CoConvert(dungeonWidth);
dungeon = new BSPDungeon(dungeonWidth, dungeonHeight);
dungeon.treeData.SplitNodes(numSplits);
dungeon.GenerateRooms ();
dungeon.GenerateCorridors();
GenerateDungeon();
}
public void Reset()
{
dungeon.Reset();
dungeon.treeData.SplitNodes(numSplits);
dungeon.GenerateRooms ();
dungeon.GenerateCorridors();
GenerateDungeon();
}
public void GenerateDungeon()
{
Debug.Log ("GENERATING DUNGEON");
tiles = dungeon.SetDungeonData();
//Begin looking through every single tile
for(int i = 0; i < tiles.Length; i++)
{
//If our tile is something useful, aka not a void area in the dungeon
if(tiles[i] != 0){
//Bogus location
int x = 0;
int z = 0;
//Real World Location
convert.ConvertIndexToXY(i,ref x,ref z);
//Wouldn't need if I understood the math, but since I don't being extra careful
int leftTile = tiles[convert.ConvertXYToIndex(x-1,z)];
int rightTile = tiles[convert.ConvertXYToIndex(x+1,z)];
int topTile = tiles[convert.ConvertXYToIndex(x,z-1)];
int bottomTile = tiles[convert.ConvertXYToIndex(x,z+1)];
//Create a base layer for compairing dungeon
CreateDebugDungeon(x,z);
//Determine what we are trying to spawn, and spawn it
if(tiles[i] == (short)Enums.TileType.Corner)
CheckCorners(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
if(tiles[i] == (short)Enums.TileType.OneWall)
CheckOneWalls(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
if(tiles[i] == (short)Enums.TileType.FloorAndRoof)
CreateTile((int)Enums.TileType.FloorAndRoof, x,z,0,dungeonWidth,dungeonHeight);
if(tiles[i] == (short)Enums.TileType.Corridor)
CheckCorridors(leftTile, rightTile, topTile, bottomTile, x, z, dungeonWidth, dungeonHeight);
}//end if tiles != 0
}//end for
Debug.Log ("Done pushing tiles");
//networkView.RPC("SpawnCharacter",RPCMode.AllBuffered, team1Spawn);
networkView.RPC ("SpawnCharacter",RPCMode.All);
//networkView.RPC ("Merp",RPCMode.All);
//networkView.RPC ("PushTiles",RPCMode.All);
//Debug.Log ("Merr?");
}//end generate dungeon
[RPC]
void SpawnCharacter()
{
Debug.Log ("Spawning character at : " );
//Instantiate(character,position, Quaternion.identity);
}
/// <summary>
/// Create Tile is responsible for instantiating tiles.
/// </summary>
/// <param name="tileType">What Tile type to spawn.</param>
/// <param name="x">The x coordinate to spawn tile at.</param>
/// <param name="z">The z coordinate to spawn tile at.</param>
/// <param name="rotation">What rotation to spawn the tile at.</param>
/// <param name="dungeonWidth">Dungeon width.</param>
/// <param name="dungeonHeight">Dungeon height.</param>
public void CreateTile(int tileType, int x, int z, float rotation, int dungeonWidth, int dungeonHeight)
{
//So it displays right-side up in the center of the scene
x -= dungeonWidth/2;
z -= dungeonHeight/2;
//Offsetting for the tile size
x *= 8;
z *= -8;
//Set up temporary object
GameObject tempObject;
//Get it's position
Vector3 tempPos = new Vector3(x,0,z);
bool sendSpawn = false;
switch(tileType)
{
case -1:
Debug.Log ("NONE FOUND " + tempPos);
tempObject = (GameObject)GameObject.Instantiate(Resources.Load("Error"));
break;
case (int)Enums.TileType.Corner:
tempObject = (GameObject)GameObject.Instantiate(Resources.Load("Corner"));
break;
case (int)Enums.TileType.OneWall:
tempObject = (GameObject)GameObject.Instantiate(Resources.Load("OneWall"));
break;
case (int)Enums.TileType.Doorway:
tempObject = (GameObject)GameObject.Instantiate(Resources.Load("Doorway"));
break;
case (int)Enums.TileType.FloorAndRoof:
tempObject =(GameObject)GameObject.Instantiate(Resources.Load("FloorAndRoof"));
if(team1 == false)
{
//character.transform.position = new Vector3(x, charYOffset,z);
//GameObject.Find"
team1Spawn = new Vector3(x, charYOffset, z);
team1 = true;
sendSpawn = true;
Debug.Log ("SETTING SPAWN");
}
break;
case (int)Enums.TileType.Corridor:
tempObject =(GameObject)GameObject.Instantiate(Resources.Load("Corridor"));
break;
default:
tempObject = (GameObject)GameObject.Instantiate(Resources.Load ("Error"));
Debug.Log ("DEFAULT " + tempPos);
break;
}
tempObject.transform.Rotate (new Vector3(0f, rotation, 0f));
tempObject.transform.position = tempPos;
//TESTING
networkView.RPC ("PushTile", RPCMode.AllBuffered, tempObject, tempPos, rotation);
//GameObject.Destroy (tempObject);
}
[RPC]
void PushTile(GameObject tileObject, Vector3 tilePosition, float rotation)
{
Debug.Log ("Rawr");
GameObject objectCopy = tileObject;
Quaternion newRotation = Quaternion.Euler(0f, rotation, 0f);
Network.Instantiate(objectCopy, tilePosition, newRotation, 0);
}
/// <summary>
/// Determins which direction a tile should face, as a corner.
/// </summary>
/// <param name="leftTile">The tile to the left of the target tile.</param>
/// <param name="rightTile">The tile to the right of the target tile.</param>
/// <param name="topTile">The tile ontop of the target tile</param>
/// <param name="bottomTile">The tile below the target tile</param>
/// <param name="x">The x coordinate of the target tile.</param>
/// <param name="z">The z coordinate of the target tile.</param>
/// <param name="dungeonWidth">Dungeon width.</param>
/// <param name="dungeonHeight">Dungeon height.</param>
public void CheckCorners (int leftTile, int rightTile, int topTile, int bottomTile, int x, int z, int dungeonWidth, int dungeonHeight)
{
//Left And Top Empty = NW
//Left and Bottom Empty = SW
//Right and Top Empty = NE
//Right and Bottom Empty = NW
if(leftTile == (int)Enums.TileType.Empty)
{
if(topTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.Corner,x,z,(float)Enums.CornerDirections.NorthWest, dungeonWidth, dungeonHeight);
else if(bottomTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.Corner,x,z,(float)Enums.CornerDirections.SouthWest, dungeonWidth, dungeonHeight);
else
CreateTile(-1,x,z,0, dungeonWidth, dungeonHeight);
}
else if(rightTile == (int)Enums.TileType.Empty)
{
if(topTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.Corner,x,z,(float)Enums.CornerDirections.NorthEast, dungeonWidth, dungeonHeight);
else if(bottomTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.Corner,x,z,(float)Enums.CornerDirections.SouthEast, dungeonWidth, dungeonHeight);
else
CreateTile(-1,x,z,0, dungeonWidth, dungeonHeight);
}
else
CreateTile(-1,x,z,0, dungeonWidth, dungeonHeight);
}
/// <summary>
/// Determins which direction a tile should face, as a single wall.
/// </summary>
/// <param name="leftTile">The tile to the left of the target tile.</param>
/// <param name="rightTile">The tile to the right of the target tile.</param>
/// <param name="topTile">The tile ontop of the target tile</param>
/// <param name="bottomTile">The tile below the target tile</param>
/// <param name="x">The x coordinate of the target tile.</param>
/// <param name="z">The z coordinate of the target tile.</param>
/// <param name="dungeonWidth">Dungeon width.</param>
/// <param name="dungeonHeight">Dungeon height.</param>
public void CheckOneWalls(int leftTile, int rightTile, int topTile, int bottomTile, int x, int z, int dungeonWidth, int dungeonHeight)
{
if(bottomTile == (int)Enums.TileType.FloorAndRoof && topTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.OneWall, x,z,(float)Enums.OneWallDirections.North, dungeonWidth, dungeonHeight);
else if(leftTile == (int)Enums.TileType.FloorAndRoof && rightTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.OneWall, x,z,(float)Enums.OneWallDirections.East, dungeonWidth, dungeonHeight);
else if(rightTile == (int)Enums.TileType.FloorAndRoof && leftTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.OneWall, x,z,(float)Enums.OneWallDirections.West, dungeonWidth, dungeonHeight);
else if(topTile == (int)Enums.TileType.FloorAndRoof && bottomTile == (int)Enums.TileType.Empty)
CreateTile((int)Enums.TileType.OneWall, x,z,(float)Enums.OneWallDirections.South, dungeonWidth, dungeonHeight);
else if(bottomTile == (int)Enums.TileType.Corridor)
CreateTile((int)Enums.TileType.Doorway, x,z,(float)Enums.DoorwayDirections.South, dungeonWidth, dungeonHeight);
else if(topTile == (int)Enums.TileType.Corridor)
CreateTile((int)Enums.TileType.Doorway, x,z,(float)Enums.DoorwayDirections.North, dungeonWidth, dungeonHeight);
else if(leftTile == (int)Enums.TileType.Corridor)
CreateTile((int)Enums.TileType.Doorway, x,z,(float)Enums.DoorwayDirections.West, dungeonWidth, dungeonHeight);
else if(rightTile == (int)Enums.TileType.Corridor)
CreateTile((int)Enums.TileType.Doorway, x,z,(float)Enums.DoorwayDirections.East, dungeonWidth, dungeonHeight);
else
CreateTile(-1, x,z,0, dungeonWidth, dungeonHeight);
}
/// <summary>
/// Determins which direction a tile should face, as a corridor.
/// </summary>
/// <param name="leftTile">The tile to the left of the target tile.</param>
/// <param name="rightTile">The tile to the right of the target tile.</param>
/// <param name="topTile">The tile ontop of the target tile</param>
/// <param name="bottomTile">The tile below the target tile</param>
/// <param name="x">The x coordinate of the target tile.</param>
/// <param name="z">The z coordinate of the target tile.</param>
/// <param name="dungeonWidth">Dungeon width.</param>
/// <param name="dungeonHeight">Dungeon height.</param>
public void CheckCorridors(int leftTile, int rightTile, int topTile, int bottomTile, int x, int z, int dungeonWidth, int dungeonHeight)
{
//We are a N/S corridor IF our bottom tile is a...
//Doorway, corridor, or a single wall (because sometimes we are checked before walls have become doorways)
if(bottomTile == (int)Enums.TileType.Doorway || bottomTile == (int)Enums.TileType.Corridor || bottomTile == (int)Enums.TileType.OneWall)
CreateTile((int)Enums.TileType.Corridor, x,z,(float)Enums.CorridorDirections.NorthSouth, dungeonWidth, dungeonHeight);
//We are a W/E corridor IF our bottom tile is a...
//Doorway, corridor, or a single wall (because sometimes we are checked before walls have become doorways)
else if(leftTile == (int)Enums.TileType.Doorway || leftTile == (int)Enums.TileType.Corridor || leftTile == (int)Enums.TileType.OneWall)
CreateTile((int)Enums.TileType.Corridor, x,z,(float)Enums.CorridorDirections.WestEast, dungeonWidth, dungeonHeight);
else
CreateTile(-1, x,z,0, dungeonWidth, dungeonHeight);
}
/// <summary>
/// Create Debug Dungeon is responible for creating a flat dungeon underneathe (-2 y) the real dungeon.
/// This is for testing only and should not be included in the final product.
/// </summary>
/// <param name="x">The x coordinate of the tile to create.</param>
/// <param name="z">The z coordinate of the tile to create.</param>
public void CreateDebugDungeon(int x, int z)
{
//So it displays right-side up in the center of the scene
x -= dungeonWidth/2;
z -= dungeonHeight/2;
//Offsetting for the tile size
x *= 8;
z *= -8;
GameObject tempObjectDebug = (GameObject)GameObject.Instantiate(Resources.Load("TestSubject"));
tempObjectDebug.transform.position = new Vector3(x, -2, z);
}
}
毕竟说完了,控制台将会打印: 生成地下城 设置地下数据 设置SPAWN 完成推瓦片
正确设置了字符引用,正确地实例化了tile,一切似乎都按预期工作,但忽略了RPC调用?没有错误,也没有警告。
我感谢任何人都能给予的帮助, 蒂芙尼