private void Capture(Topology.Face face) { var color = _faceBoardStates[face]; if (color == BoardState.Empty) { return; } int captureCount = 0; TopologyVisitor.VisitFaces(face, (FaceVisitor visitor) => { var visitColor = _faceBoardStates[visitor.face]; if (visitColor == color) { SetPiece(visitor.face, null); _faceBoardStates[visitor.face] = BoardState.Empty; ++captureCount; visitor.VisitInternalNeighbors(); } }); if (color == BoardState.Black) { _blackCount -= captureCount; blackCountText.text = _blackCount.ToString(); } else { _whiteCount -= captureCount; whiteCountText.text = _whiteCount.ToString(); } }
private bool HasLiberties(Topology.Face face) { var color = _faceBoardStates[face]; if (color == BoardState.Empty) { return(true); } bool hasLiberties = false; TopologyVisitor.VisitFaces(face, (FaceVisitor visitor) => { var visitColor = _faceBoardStates[visitor.face]; if (visitColor == BoardState.Empty) { hasLiberties = true; visitor.Break(); } else if (visitColor == color) { visitor.VisitInternalNeighbors(); } }); return(hasLiberties); }
private void ObscureUnitVicinity(Topology.Face face) { _faceSightCounts[face] -= 1; _dynamicMesh.RebuildFace(face, _faceTriangulation); TopologyVisitor.VisitFacesInBreadthFirstOrder(face, (FaceVisitor visitor) => { _faceSightCounts[visitor.face] -= 1; _dynamicMesh.RebuildFace(visitor.face, _faceTriangulation); if (visitor.depth < 3) { visitor.VisitAllNeighbors(); } }); }
private void RevealUnitVicinity(Topology.Face face) { _faceSeenStates[face] = true; _faceSightCounts[face] += 1; _dynamicMesh.RebuildFace(face, _faceTriangulation); TopologyVisitor.VisitFacesInBreadthFirstOrder(face, (FaceVisitor visitor) => { _faceSeenStates[visitor.face] = true; if (visitor.depth <= fullSightDistance) { _faceSightCounts[visitor.face] += 1; } _dynamicMesh.RebuildFace(visitor.face, _faceTriangulation); if (visitor.depth < limitedSightDistance) { visitor.VisitAllNeighbors(); } }); }
private void ClearBlockedFaces(Topology.Face face) { _faceBlockedStates[face] = false; _dynamicMesh.RebuildFace(face, _triangulationNormal); TopologyVisitor.VisitFacesInBreadthFirstOrder(face, (FaceVisitor visitor) => { if (_faceBlockedStates[visitor.face] == true) { _faceBlockedStates[visitor.face] = false; _dynamicMesh.RebuildFace(visitor.face, _triangulationNormal); } if (visitor.depth < clearRadius) { visitor.VisitInternalNeighbors(); } }); }
protected void Start() { orbitalCamera.enabled = !isInverted; pivotalCamera.enabled = isInverted; exteriorLight.enabled = !isInverted; interiorLight.enabled = isInverted; _lightVector = (isInverted ? interiorLight : exteriorLight).transform.position; _lightAxis = Vector3.Cross(Vector3.Cross(Vector3.up, _lightVector), _lightVector); RenderSettings.ambientLight = new Color(0.3f, 0.4f, 0.5f); RenderSettings.ambientIntensity = 0.25f; RenderSettings.customReflection = whiteCubeMap; RenderSettings.reflectionIntensity = 0.125f; RenderSettings.defaultReflectionMode = UnityEngine.Rendering.DefaultReflectionMode.Custom; _picker = GetComponent <FaceSpatialPartitioningPicker>(); _surface = SphericalSurface.Create(Vector3.up, Vector3.right, 10f, isInverted); Vector3[] baseVertexPositionsArray; Topology baseTopology; SphericalManifoldUtility.CreateIcosahedron(_surface, out baseTopology, out baseVertexPositionsArray); Vector3[] vertexPositionsArray; SphericalManifoldUtility.Subdivide(_surface, baseTopology, baseVertexPositionsArray.AsVertexAttribute(), topologySubdivision, out _topology, out vertexPositionsArray); _vertexPositions = PositionalVertexAttribute.Create(_surface, vertexPositionsArray); SphericalManifoldUtility.MakeDual(_surface, _topology, _vertexPositions, out vertexPositionsArray); _vertexPositions = PositionalVertexAttribute.Create(_surface, vertexPositionsArray); var regularityWeight = 0.5f; var equalAreaWeight = 1f - regularityWeight; var regularityRelaxedVertexPositions = new Vector3[_topology.vertices.Count].AsVertexAttribute(); var equalAreaRelaxedVertexPositions = new Vector3[_topology.vertices.Count].AsVertexAttribute(); var relaxedVertexPositions = regularityRelaxedVertexPositions; var faceCentroids = PositionalFaceAttribute.Create(_surface, _topology.internalFaces.Count); var faceCentroidAngles = new float[_topology.faceEdges.Count].AsEdgeAttribute(); var vertexAreas = new float[_topology.vertices.Count].AsVertexAttribute(); FaceAttributeUtility.CalculateFaceCentroidsFromVertexPositions(_topology.internalFaces, _vertexPositions, faceCentroids); VertexAttributeUtility.CalculateVertexAreasFromVertexPositionsAndFaceCentroids(_topology.vertices, _vertexPositions, faceCentroids, vertexAreas); Func <float> relaxIterationFunction = () => { SphericalManifoldUtility.RelaxVertexPositionsForRegularity(_surface, _topology, _vertexPositions, true, regularityRelaxedVertexPositions); SphericalManifoldUtility.RelaxVertexPositionsForEqualArea(_surface, _topology, _vertexPositions, true, equalAreaRelaxedVertexPositions, faceCentroids, faceCentroidAngles, vertexAreas); for (int i = 0; i < relaxedVertexPositions.Count; ++i) { relaxedVertexPositions[i] = regularityRelaxedVertexPositions[i] * regularityWeight + equalAreaRelaxedVertexPositions[i] * equalAreaWeight; } var relaxationAmount = SphericalManifoldUtility.CalculateRelaxationAmount(_vertexPositions, relaxedVertexPositions); for (int i = 0; i < _vertexPositions.Count; ++i) { _vertexPositions[i] = relaxedVertexPositions[i]; } return(relaxationAmount); }; Func <bool> repairFunction = () => { return(SphericalManifoldUtility.ValidateAndRepair(_surface, _topology, _vertexPositions, 0.5f, true)); }; Action relaxationLoopFunction = TopologyRandomizer.CreateRelaxationLoopFunction(20, 20, 0.95f, relaxIterationFunction, repairFunction); TopologyRandomizer.Randomize( _topology, 1, 0.1f, 3, 3, 5, 7, true, _random, relaxationLoopFunction); _facePositions = PositionalFaceAttribute.Create(_surface, _topology.internalFaces.Count); FaceAttributeUtility.CalculateFaceCentroidsFromVertexPositions(_topology.internalFaces, _vertexPositions, _facePositions); _maximumFaceDistance = 0f; foreach (var edge in _topology.faceEdges) { var distance = Geometry.AngleBetweenVectors(_facePositions[edge.nearFace], _facePositions[edge.farFace]) * _surface.radius; _maximumFaceDistance = Mathf.Max(_maximumFaceDistance, distance); } _innerAngleBisectors = EdgeAttributeUtility.CalculateFaceEdgeBisectorsFromVertexPositions(_topology.internalFaces, _vertexPositions, _facePositions); _innerVertexPositions = new Vector3[_topology.faceEdges.Count].AsEdgeAttribute(); foreach (var edge in _topology.faceEdges) { _innerVertexPositions[edge] = _vertexPositions[edge] + _innerAngleBisectors[edge] * 0.03f; } _faceNormals = FaceAttributeUtility.CalculateFaceNormalsFromSurface(_topology.faces, _surface, _facePositions); _faceUVFrames = FaceAttributeUtility.CalculatePerFaceSphericalUVFramesFromFaceNormals(_topology.faces, _faceNormals, Quaternion.identity); _faceOuterEdgeUVs = EdgeAttributeUtility.CalculatePerFaceUnnormalizedUVsFromVertexPositions(_topology.faces, _vertexPositions, _faceUVFrames); _faceInnerEdgeUVs = EdgeAttributeUtility.CalculatePerFaceUnnormalizedUVsFromVertexPositions(_topology.faces, _innerVertexPositions, _faceUVFrames); _faceCenterUVs = FaceAttributeUtility.CalculateUnnormalizedUVsFromFacePositions(_topology.faces, _facePositions, _faceUVFrames); var faceMinUVs = new Vector2[_topology.faces.Count].AsFaceAttribute(); var faceRangeUVs = new Vector2[_topology.faces.Count].AsFaceAttribute(); FaceAttributeUtility.CalculateFaceEdgeMinAndRangeValues(_topology.faces, _faceOuterEdgeUVs, faceMinUVs, faceRangeUVs); foreach (var face in _topology.faces) { var uvMin = faceMinUVs[face]; var uvRange = faceRangeUVs[face]; var adjusted = AspectRatioUtility.Expand(new Rect(uvMin.x, uvMin.y, uvRange.x, uvRange.y), 1f); faceMinUVs[face] = adjusted.min; faceRangeUVs[face] = adjusted.size; } _faceOuterEdgeUVs = EdgeAttributeUtility.CalculatePerFaceUniformlyNormalizedUVsFromFaceUVMinAndRange(_topology.faces, faceMinUVs, faceRangeUVs, _faceOuterEdgeUVs); _faceInnerEdgeUVs = EdgeAttributeUtility.CalculatePerFaceUniformlyNormalizedUVsFromFaceUVMinAndRange(_topology.faces, faceMinUVs, faceRangeUVs, _faceInnerEdgeUVs); _faceCenterUVs = FaceAttributeUtility.CalculateUniformlyNormalizedUVsFromFaceUVMinAndRange(_topology.faces, faceMinUVs, faceRangeUVs, _faceCenterUVs); _partitioning = UniversalFaceSpatialPartitioning.Create(_surface, _topology, _vertexPositions); _picker.partitioning = _partitioning; _picker.enabled = true; _faceTerrainIndices = new int[_topology.faces.Count].AsFaceAttribute(); var terrainWeights = new int[] { grassWeight, waterWeight, desertWeight, mountainWeight }; int terrainWeightSum = 0; foreach (var weight in terrainWeights) { terrainWeightSum += weight; } var rootFaces = new List <Topology.Face>(); var rootFaceEdges = new List <Topology.FaceEdge>(); for (int regionIndex = 0; regionIndex < geographicalRegionCount; ++regionIndex) { Topology.Face face; do { face = _topology.internalFaces[_random.Index(_topology.internalFaces.Count)]; } while (rootFaces.Contains(face)); rootFaces.Add(face); foreach (var edge in face.edges) { rootFaceEdges.Add(edge); } _faceTerrainIndices[face] = _random.WeightedIndex(terrainWeights, terrainWeightSum); } TopologyVisitor.VisitFacesInRandomOrder(rootFaceEdges, (FaceEdgeVisitor visitor) => { _faceTerrainIndices[visitor.edge.farFace] = _faceTerrainIndices[visitor.edge.nearFace]; visitor.VisitInternalNeighborsExceptSource(); }, _random); _faceSeenStates = new bool[_topology.faces.Count].AsFaceAttribute(); _faceSightCounts = new int[_topology.faces.Count].AsFaceAttribute(); var triangulation = new SeparatedFacesUmbrellaTriangulation(2, (Topology.FaceEdge edge, DynamicMesh.IIndexedVertexAttributes vertexAttributes) => { var face = edge.nearFace; var faceNormal = _faceNormals[face]; var gridOverlayU = GetGridOverlayU(false, _faceSeenStates[face], _faceSightCounts[face]); vertexAttributes.position = _vertexPositions[edge]; vertexAttributes.normal = faceNormal; vertexAttributes.uv1 = AdjustSurfaceUV(_faceOuterEdgeUVs[edge], _faceTerrainIndices[face]); vertexAttributes.uv2 = new Vector2(gridOverlayU, 0f); vertexAttributes.Advance(); vertexAttributes.position = _innerVertexPositions[edge]; vertexAttributes.normal = faceNormal; vertexAttributes.uv1 = AdjustSurfaceUV(_faceInnerEdgeUVs[edge], _faceTerrainIndices[face]); vertexAttributes.uv2 = new Vector2(gridOverlayU, 0.5f); vertexAttributes.Advance(); }, (Topology.Face face, DynamicMesh.IIndexedVertexAttributes vertexAttributes) => { vertexAttributes.position = _facePositions[face]; vertexAttributes.normal = _faceNormals[face]; vertexAttributes.uv1 = AdjustSurfaceUV(_faceCenterUVs[face], _faceTerrainIndices[face]); vertexAttributes.uv2 = new Vector2(GetGridOverlayU(false, _faceSeenStates[face], _faceSightCounts[face]), 1f); vertexAttributes.Advance(); }); _dynamicMesh = DynamicMesh.Create( _topology.enumerableInternalFaces, DynamicMesh.VertexAttributes.Position | DynamicMesh.VertexAttributes.Normal | DynamicMesh.VertexAttributes.UV1 | DynamicMesh.VertexAttributes.UV2, triangulation); foreach (var mesh in _dynamicMesh.submeshes) { var meshObject = Instantiate(planetMeshPrefab); meshObject.mesh = mesh; meshObject.transform.SetParent(planetMeshes, false); } _faceUnits = new Transform[_topology.faces.Count].AsFaceAttribute(); for (int i = 0; i < unitCount; ++i) { Topology.Face face; do { face = _topology.internalFaces[_random.Index(_topology.internalFaces.Count)]; } while (_faceTerrainIndices[face] == 1 || _faceUnits[face] != null); var unit = Instantiate(unitPrefab); unit.SetParent(units, false); unit.transform.position = _facePositions[face] + _faceNormals[face] * 0.15f; _faceUnits[face] = unit; RevealUnitVicinity(face); } _dynamicMesh.RebuildMesh(DynamicMesh.VertexAttributes.UV2); }
public override IEnumerator BeginGeneration() { var topology = topologyInputSlot.GetAsset <Topology>(); var faceGroupIndices = new int[topology.internalFaces.Count].AsFaceAttribute(); List <int>[] faceGroupFaceIndices; var random = randomness.GetRandom(); var clampedRootCount = Mathf.Clamp(groupCount, 1, topology.internalFaces.Count); faceGroupFaceIndices = new List <int> [clampedRootCount]; var waitHandle = executive.GenerateConcurrently(() => { var rootFaces = new List <Topology.Face>(); var rootFaceEdges = new List <Topology.FaceEdge>(); for (int faceGroupIndex = 0; faceGroupIndex < clampedRootCount; ++faceGroupIndex) { faceGroupFaceIndices[faceGroupIndex] = new List <int>(); Topology.Face face; do { face = topology.internalFaces[random.Index(topology.internalFaces.Count)]; } while (rootFaces.Contains(face)); rootFaces.Add(face); foreach (var edge in face.edges) { if (edge.face.isInternal) { rootFaceEdges.Add(edge); } } faceGroupIndices[face] = faceGroupIndex; faceGroupFaceIndices[faceGroupIndex].Add(face.index); } TopologyVisitor.VisitFacesInRandomOrder( rootFaceEdges, (FaceEdgeVisitor visitor) => { var faceGroupIndex = faceGroupIndices[visitor.edge.nearFace]; faceGroupIndices[visitor.edge] = faceGroupIndex; faceGroupFaceIndices[faceGroupIndex].Add(visitor.edge.face.index); visitor.VisitInternalNeighborsExceptSource(); }, random); }); while (waitHandle.WaitOne(10) == false) { yield return(null); } faceGroupOutputSlots = GeneratorUtility.ResizeArray(faceGroupOutputSlots, faceGroupFaceIndices.Length, (int index) => { return(OutputSlot.CreateGrouped <FaceGroup>(this, string.Format("Face Group {0}", index), faceGroupCollectionOutputSlot.name, true, OutputSlot.Availability.DuringGeneration)); }, (OutputSlot output, int index) => { output.DisconnectAll(); output.path = faceGroupCollectionOutputSlot.name; return(output); }); var faceGroupCollection = FaceGroupCollection.Create(faceGroupFaceIndices.Length); for (int faceGroupIndex = 0; faceGroupIndex < faceGroupFaceIndices.Length; ++faceGroupIndex) { var faceGroup = ArrayFaceGroup.Create(topology, faceGroupFaceIndices[faceGroupIndex].ToArray()).SetName(faceGroupOutputSlots[faceGroupIndex].name); faceGroupCollection.faceGroups[faceGroupIndex] = faceGroupOutputSlots[faceGroupIndex].SetAsset(faceGroup); } faceGroupCollectionOutputSlot.SetAsset(faceGroupCollection); faceGroupIndicesOutputSlot.SetAsset(IntFaceAttribute.Create(faceGroupIndices.array)); yield break; }