void InitRandom() { var rand = new SimpleRNG(Seed); _randFirstAddX = (rand.value - 0.5f) * 1000f; _randFirstAddY = (rand.value - 0.5f) * 10000; _randSecondAddX = (rand.value - 0.5f) * 1000f; _randSecondAddY = (rand.value - 0.5f) * 1000f; }
private CollMapPoint GetCollMapPoint(int x, int y, BlockSetProfile.BlockType?colliding = null) { CollMapPoint cachedPoint; if (_collMapPoints.TryGetValue(new Point2(x, y), out cachedPoint) && (colliding == null || colliding.Value == cachedPoint.BlockType)) { return(cachedPoint); } var noise = GetNoise(x, y); var matchingBlockInfos = BlockSet.BlockInfos.FindAll(b => b.MinNoise <= noise && b.MaxNoise >= noise && (colliding == null || colliding.Value == b.BlockType)); if (matchingBlockInfos.Count == 0 && colliding != null) { matchingBlockInfos = BlockSet.BlockInfos .FindAll(b => colliding.Value == b.BlockType); } if (matchingBlockInfos.Count == 0) { Debug.LogError("No matching blocks found"); return(default(CollMapPoint)); } var rand = new SimpleRNG(Util.Hash(Seed, x, y)); var blockInfo = matchingBlockInfos .RandomElement(bi => bi.Weight, rand); var point = new CollMapPoint(noise) { BlockInfo = blockInfo, BlockType = blockInfo.BlockType }; _collMapPoints[new Point2(x, y)] = point; return(point); }
private void CreatePoint(int x, int y, BlockSetProfile.BlockInfo blockInfo, int compactInfo, bool noLightEffects, SimpleRNG rand, BlockSetProfile.BlockType?isColliding = null) { var sprite = blockInfo.SpriteInfo .RandomElement(ti => 1, rand); //if (tilingInfo == null) //{ // Debug.LogError("Tiling info not found"); // return; //} //var sprite = tilingInfo.Sprite; if (sprite == null) { Debug.LogError("Tiling info is broken"); return; } CreatePoint(x, y, sprite, blockInfo, isColliding == null ? blockInfo.BlockType : isColliding.Value, noLightEffects); }
private GameObject GenerateBlocksJoined(int xOffest, int yOffest) { var rand = new SimpleRNG(Util.Hash(Seed, xOffest, yOffest)); _vertices.Clear(); _uvs.Clear(); _triangles.Clear(); _lightAbsorptionColors.Clear(); _lightEmissionColors.Clear(); var meshObj = (GameObject)Instantiate(MeshObjectPrefab); meshObj.name = "Block Mesh { X = " + xOffest / ChunkSize + "; Y = " + yOffest / ChunkSize + " }"; var meshObjTransform = meshObj.transform; meshObjTransform.position = meshObjTransform.position.WithXY(xOffest, yOffest); meshObjTransform.parent = Container; var collMap = new CollMapPoint[ChunkSize, ChunkSize]; for (int x = 0; x < ChunkSize; x++) { for (int y = 0; y < ChunkSize; y++) { collMap[x, y] = GetCollMapPoint(x + xOffest, y + yOffest); } } for (int x = 0; x < ChunkSize; x++) { for (int y = 0; y < ChunkSize; y++) { var blockInfo = collMap[x, y].BlockInfo; if (blockInfo.AditionalObjectPrefab != null && blockInfo.AditionalObjectProbability >= rand.value) { var addObj = (GameObject)Instantiate(blockInfo.AditionalObjectPrefab); addObj.transform.parent = meshObjTransform; addObj.transform.localPosition = blockInfo.AditionalObjectPrefab .transform.position.WithXY(x + 0.5f, y + 0.5f); } if (blockInfo.SpriteInfo.Length == 0) { Debug.LogError("Sprite Info is broken"); continue; } var compactInfo = (SafeIndex(collMap, x, y + 1, ChunkSize, ChunkSize, () => GetCollMapPoint(x + xOffest, y + yOffest)) .BlockType == BlockSetProfile.BlockType.CollidingWall ? 1 : 0) + (SafeIndex(collMap, x + 1, y, ChunkSize, ChunkSize, () => GetCollMapPoint(x + xOffest, y + yOffest)) .BlockType == BlockSetProfile.BlockType.CollidingWall ? 2 : 0) + (SafeIndex(collMap, x, y - 1, ChunkSize, ChunkSize, () => GetCollMapPoint(x + xOffest, y + yOffest)) .BlockType == BlockSetProfile.BlockType.CollidingWall ? 4 : 0) + (SafeIndex(collMap, x - 1, y, ChunkSize, ChunkSize, () => GetCollMapPoint(x + xOffest, y + yOffest)) .BlockType == BlockSetProfile.BlockType.CollidingWall ? 8 : 0); CreatePoint(x, y, blockInfo, compactInfo, false, rand); } } var blockMesh = new Mesh(); blockMesh.vertices = _vertices.ToArray(); blockMesh.uv = _uvs.ToArray(); blockMesh.triangles = _triangles.ToArray(); blockMesh.RecalculateBounds(); ; var meshFilter = meshObj.GetComponent <MeshFilter>(); meshFilter.mesh = blockMesh; var meshRenderer = meshObj.GetComponent <MeshRenderer>(); var texture = BlockSet.BlockInfos .First(bi => bi.SpriteInfo.Any(si => si != null)) .SpriteInfo.First(ti => ti != null) .texture; var mpb = new MaterialPropertyBlock(); mpb.SetTexture("_MainTex", texture); meshRenderer.SetPropertyBlock(mpb); for (int x = 0; x < ChunkSize; x++) { var yStart = 0; for (int y = 0; y < ChunkSize; y++) { if (collMap[x, y].BlockInfo.BlockType != BlockSetProfile.BlockType.CollidingWall) { if (y - yStart > 0) { var obj = new GameObject(); obj.layer = meshObj.layer; obj.transform.parent = meshObjTransform; obj.transform.localPosition = new Vector3(x, 0); obj.name = "Collider x = " + x; var coll = obj.AddComponent <BoxCollider2D>(); coll.size = new Vector2(1, (y - yStart)); coll.offset = new Vector2(0.5f, yStart + coll.size.y / 2f); } yStart = y + 1; } } if (ChunkSize - yStart > 0) { var obj = new GameObject(); obj.layer = meshObj.layer; obj.transform.parent = meshObjTransform; obj.transform.localPosition = new Vector3(x, 0); obj.name = "Collider x = " + x; var coll = obj.AddComponent <BoxCollider2D>(); coll.size = new Vector2(1, (ChunkSize - yStart)); coll.offset = new Vector2(0.5f, yStart + coll.size.y / 2f); } } var lightObstaclesObject = (GameObject)Instantiate(LightObstaclesPrefab); lightObstaclesObject.transform.parent = meshObjTransform; lightObstaclesObject.transform.localPosition = Vector3.zero; //lightObstaclesObject.transform.localPosition += new Vector3(0, 0, -10); var lightObstaclesMeshFilter = lightObstaclesObject.GetComponent <MeshFilter>(); lightObstaclesMeshFilter.mesh = ChunkMeshFromColors(_lightAbsorptionColors); var ambientLightObject = (GameObject)Instantiate(AmbientLightPrefab); ambientLightObject.transform.parent = meshObjTransform; ambientLightObject.transform.localPosition = Vector3.zero; //ambientLightObject.transform.localPosition += new Vector3(0, 0, -5); var ambientLightMeshFilter = ambientLightObject.GetComponent <MeshFilter>(); ambientLightMeshFilter.mesh = ChunkMeshFromColors(_lightEmissionColors); return(meshObj); }
public static T RandomElement <T>(this IEnumerable <T> enumerable, Func <T, int> weightFunc, SimpleRNG rand) { int totalWeight = 0; // this stores sum of weights of all elements before current T selected = default(T); // currently selected element foreach (var data in enumerable) { int weight = weightFunc(data); // weight of current element int r = rand.Range(0, totalWeight + weight); // random value if (r >= totalWeight) // probability of this is weight/(totalWeight+weight) { selected = data; } // it is the probability of discarding last selected element and selecting current one instead totalWeight += weight; // increase weight sum } return(selected); // when iterations end, selected is some element of sequence. }