public static List <ElementGroup> GetElementGroups(ProBuilderMesh mesh, bool collectCoincident) { var groups = new List <ElementGroup>(); var selectMode = ProBuilderEditor.selectMode; if (selectMode.ContainsFlag(SelectMode.Vertex | SelectMode.TextureVertex)) { foreach (var list in GetVertexSelectionGroups(mesh, collectCoincident)) { var pos = PHandleUtility.GetActiveElementPosition(mesh, list); var rot = PHandleUtility.GetVertexRotation(mesh, HandleOrientation.ActiveElement, list); groups.Add(new ElementGroup(list, pos, rot)); } } else if (selectMode.ContainsFlag(SelectMode.Edge | SelectMode.TextureEdge)) { foreach (var list in GetEdgeSelectionGroups(mesh)) { var pos = PHandleUtility.GetActiveElementPosition(mesh, list); var rot = PHandleUtility.GetEdgeRotation(mesh, HandleOrientation.ActiveElement, list); List <int> indices; if (collectCoincident) { indices = new List <int>(); mesh.GetCoincidentVertices(list, indices); } else { indices = list.SelectMany(x => new int[] { x.a, x.b }).ToList(); } groups.Add(new ElementGroup(indices, pos, rot)); } } else if (selectMode.ContainsFlag(SelectMode.Face | SelectMode.TextureFace)) { foreach (var list in GetFaceSelectionGroups(mesh)) { var pos = PHandleUtility.GetActiveElementPosition(mesh, list); var rot = PHandleUtility.GetFaceRotation(mesh, HandleOrientation.ActiveElement, list); List <int> indices; if (collectCoincident) { indices = new List <int>(); mesh.GetCoincidentVertices(list, indices); } else { indices = list.SelectMany(x => x.distinctIndexesInternal).ToList(); } groups.Add(new ElementGroup(indices, pos, rot)); } } return(groups); }
/// <summary> /// Called from ProGrids. /// </summary> /// <param name="snapVal"></param> void PushToGrid(float snapVal) { UndoUtility.RecordSelection(selection.ToArray(), "Push elements to Grid"); if (selectMode == SelectMode.Object || selectMode == SelectMode.None) { return; } for (int i = 0, c = MeshSelection.selectedObjectCount; i < c; i++) { ProBuilderMesh mesh = selection[i]; if (mesh.selectedVertexCount < 1) { continue; } var indexes = mesh.GetCoincidentVertices(mesh.selectedIndexesInternal); ProGridsSnapping.SnapVertices(mesh, indexes, Vector3.one * snapVal); mesh.ToMesh(); mesh.Refresh(); mesh.Optimize(); } UpdateSelection(); }
private void VerticesToEdges(bool invert, bool partial) { SelectedEdges.Clear(); UnselectedEdges.Clear(); foreach (KeyValuePair <GameObject, IList <int> > kvp in invert ? UnselectedIndices : SelectedIndices) { ProBuilderMesh mesh = kvp.Key.GetComponent <ProBuilderMesh>(); HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <Edge> edges = GetEdges(mesh, indicesHs, !partial); if (edges.Count > 0) { SelectedEdges.Add(mesh.gameObject, edges); } } foreach (KeyValuePair <GameObject, IList <int> > kvp in invert ? SelectedIndices : UnselectedIndices) { ProBuilderMesh mesh = kvp.Key.GetComponent <ProBuilderMesh>(); HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <Edge> edges = GetEdges(mesh, indicesHs, !partial); if (edges.Count > 0) { UnselectedEdges.Add(mesh.gameObject, edges); } } SelectedIndices.Clear(); UnselectedIndices.Clear(); SelectedFaces.Clear(); UnselectedFaces.Clear(); }
public void VerticesToFaces(bool invert, bool partial) { SelectedFaces.Clear(); UnselectedFaces.Clear(); foreach (KeyValuePair <ProBuilderMesh, IList <int> > kvp in invert ? UnselectedIndices : SelectedIndices) { ProBuilderMesh mesh = kvp.Key; HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <int> faces = GetFaces(mesh, indicesHs, !partial); if (faces.Count > 0) { SelectedFaces.Add(mesh, faces); } } foreach (KeyValuePair <ProBuilderMesh, IList <int> > kvp in invert ? SelectedIndices : UnselectedIndices) { ProBuilderMesh mesh = kvp.Key; HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <int> faces = GetFaces(mesh, indicesHs, !partial); if (faces.Count > 0) { UnselectedFaces.Add(mesh, faces); } } }
public void VerticesToEdges(bool invert) { SelectedEdges.Clear(); UnselectedEdges.Clear(); foreach (KeyValuePair <ProBuilderMesh, IList <int> > kvp in invert ? UnselectedIndices : SelectedIndices) { ProBuilderMesh mesh = kvp.Key; HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <Edge> edges = GetEdges(mesh, indicesHs); if (edges.Count > 0) { SelectedEdges.Add(mesh, edges); } } foreach (KeyValuePair <ProBuilderMesh, IList <int> > kvp in invert ? SelectedIndices : UnselectedIndices) { ProBuilderMesh mesh = kvp.Key; HashSet <int> indicesHs = new HashSet <int>(mesh.GetCoincidentVertices(kvp.Value)); List <Edge> edges = GetEdges(mesh, indicesHs); if (edges.Count > 0) { UnselectedEdges.Add(mesh, edges); } } }
public override MeshSelection Select(Camera camera, Rect rect, Rect uiRootRect, GameObject[] gameObjects, bool depthTest, MeshEditorSelectionMode mode) { Dictionary <ProBuilderMesh, HashSet <int> > pickResult = PBUtility.PickVertices(camera, rect, uiRootRect, gameObjects, depthTest); if (pickResult.Count == 0) { return(null); } MeshSelection selection = new MeshSelection(); foreach (KeyValuePair <ProBuilderMesh, HashSet <int> > kvp in pickResult) { ProBuilderMesh mesh = kvp.Key; HashSet <int> sharedIndexes = kvp.Value; IList <SharedVertex> sharedVertices = mesh.sharedVertices; HashSet <int> indices = new HashSet <int>(); foreach (int sharedIndex in sharedIndexes) { SharedVertex sharedVertex = sharedVertices[sharedIndex]; for (int j = 0; j < sharedVertex.Count; ++j) { if (!indices.Contains(sharedVertex[j])) { indices.Add(sharedVertex[j]); } } } if (mode == MeshEditorSelectionMode.Substract || mode == MeshEditorSelectionMode.Difference) { IList <int> selected = mesh.GetCoincidentVertices(indices).Where(index => m_vertexSelection.IsSelected(mesh, index)).ToArray(); selection.UnselectedIndices.Add(mesh.gameObject, selected); m_vertexSelection.Remove(mesh, selected); } if (mode == MeshEditorSelectionMode.Add || mode == MeshEditorSelectionMode.Difference) { IList <int> notSelected = mesh.GetCoincidentVertices(indices).Where(index => !m_vertexSelection.IsSelected(mesh, index)).ToArray(); selection.SelectedIndices.Add(mesh.gameObject, notSelected); m_vertexSelection.Add(mesh, notSelected); } } return(selection); }
private static void GetCoindicentIndices(KeyValuePair <GameObject, IList <Edge> > kvp, out ProBuilderMesh mesh, out List <int> indices) { mesh = kvp.Key.GetComponent <ProBuilderMesh>(); IList <Edge> edges = kvp.Value; indices = new List <int>(); mesh.GetCoincidentVertices(edges, indices); }
private static void GetCoindicentIndices(KeyValuePair <ProBuilderMesh, IList <Face> > kvp, out ProBuilderMesh mesh, out List <int> indices) { mesh = kvp.Key; IList <Face> faces = kvp.Value; indices = new List <int>(); mesh.GetCoincidentVertices(faces, indices); }
public MeshState(ProBuilderMesh mesh, IList <int> selectedIndices) { vertices = mesh.positions.ToArray(); indices = mesh.GetCoincidentVertices(selectedIndices); origins = new Vector3[indices.Count]; for (int i = 0, c = indices.Count; i < c; i++) { origins[i] = vertices[indices[i]]; } }
internal static List <int> GetSelectedIndicesForSelectMode(ProBuilderMesh mesh, SelectMode mode, bool collectCoincident) { if (mode.ContainsFlag(SelectMode.Face | SelectMode.TextureFace)) { List <int> indices = new List <int>(); if (collectCoincident) { mesh.GetCoincidentVertices(mesh.selectedFacesInternal, indices); } else { Face.GetDistinctIndices(mesh.selectedFacesInternal, indices); } return(indices); } else if (mode.ContainsFlag(SelectMode.Edge | SelectMode.TextureEdge)) { List <int> indices = new List <int>(); if (collectCoincident) { mesh.GetCoincidentVertices(mesh.selectedEdgesInternal, indices); } else { Edge.GetIndices(mesh.selectedEdgesInternal, indices); } return(indices); } return(collectCoincident ? mesh.GetCoincidentVertices(mesh.selectedIndexesInternal) : new List <int>(mesh.selectedIndexesInternal)); }
private void SetVerticesColor(ProBuilderMesh mesh, MeshFilter vertices, Color color, IEnumerable <int> indices) { if (IsGeometryShadersSupported) { List <int> coincident = new List <int>(); foreach (int index in indices) { mesh.GetCoincidentVertices(index, coincident); Color[] colors = vertices.sharedMesh.colors; for (int i = 0; i < coincident.Count; ++i) { colors[coincident[i]] = color; } vertices.sharedMesh.colors = colors; coincident.Clear(); } } else { List <int> coincident = new List <int>(); foreach (int index in indices) { mesh.GetCoincidentVertices(index, coincident); Color[] colors = vertices.sharedMesh.colors; for (int i = 0; i < coincident.Count; ++i) { colors[coincident[i] * 4] = color; colors[coincident[i] * 4 + 1] = color; colors[coincident[i] * 4 + 2] = color; colors[coincident[i] * 4 + 3] = color; } vertices.sharedMesh.colors = colors; coincident.Clear(); } } }
static IEnumerable <List <int> > GetVertexSelectionGroups(ProBuilderMesh mesh, bool collectCoincident) { if (!collectCoincident) { return(mesh.selectedIndexesInternal.Select(x => new List <int>() { x }).ToList()); } var shared = mesh.selectedSharedVertices; var groups = new List <List <int> >(); var groupIdx = -1; var i = -1; foreach (var index in shared) { var coincident = new List <int>(); mesh.GetCoincidentVertices(mesh.sharedVerticesInternal[index][0], coincident); groups.Add(coincident); i++; // Make sure the last selected vertic is the last in the group var idx = coincident.IndexOf(mesh.selectedIndexesInternal[mesh.selectedIndexesInternal.Length - 1]); if (idx != -1 && idx < coincident.Count) { var item = coincident[idx]; groupIdx = i; coincident[idx] = coincident[coincident.Count - 1]; coincident[coincident.Count - 1] = item; } } // Make sure the last selected vertic's group is the last in the groups if (groupIdx != -1 && groupIdx < groups.Count) { var item = groups[groupIdx]; groups[groupIdx] = groups[groups.Count - 1]; groups[groups.Count - 1] = item; } return(groups); }
static IEnumerable <List <int> > GetVertexSelectionGroups(ProBuilderMesh mesh, bool collectCoincident) { if (!collectCoincident) { return(mesh.selectedIndexesInternal.Select(x => new List <int>() { x }).ToList()); } var shared = mesh.selectedSharedVertices; var groups = new List <List <int> >(); foreach (var index in shared) { var coincident = new List <int>(); mesh.GetCoincidentVertices(mesh.sharedVerticesInternal[index][0], coincident); groups.Add(coincident); } return(groups); }
public static List <ElementGroup> GetElementGroups(ProBuilderMesh mesh, PivotPoint pivot, HandleOrientation orientation, bool collectCoincident) { var groups = new List <ElementGroup>(); var trs = mesh.transform.localToWorldMatrix; var selectMode = ProBuilderEditor.selectMode; switch (pivot) { case PivotPoint.IndividualOrigins: { if (selectMode.ContainsFlag(SelectMode.Vertex | SelectMode.TextureVertex)) { foreach (var list in GetVertexSelectionGroups(mesh, collectCoincident)) { var bounds = Math.GetBounds(mesh.positionsInternal, list); var rot = UnityEngine.ProBuilder.HandleUtility.GetVertexRotation(mesh, orientation, list); groups.Add(new ElementGroup(list, trs.MultiplyPoint3x4(bounds.center), rot)); } } else if (selectMode.ContainsFlag(SelectMode.Edge | SelectMode.TextureEdge)) { foreach (var list in GetEdgeSelectionGroups(mesh)) { var bounds = Math.GetBounds(mesh.positionsInternal, list); var rot = UnityEngine.ProBuilder.HandleUtility.GetEdgeRotation(mesh, orientation, list); List <int> indices; if (collectCoincident) { indices = new List <int>(); mesh.GetCoincidentVertices(list, indices); } else { indices = list.SelectMany(x => new int[] { x.a, x.b }).ToList(); } groups.Add(new ElementGroup(indices, trs.MultiplyPoint3x4(bounds.center), rot)); } } else if (selectMode.ContainsFlag(SelectMode.Face | SelectMode.TextureFace)) { foreach (var list in GetFaceSelectionGroups(mesh)) { var bounds = Math.GetBounds(mesh.positionsInternal, list); var rot = UnityEngine.ProBuilder.HandleUtility.GetFaceRotation(mesh, orientation, list); List <int> indices; if (collectCoincident) { indices = new List <int>(); mesh.GetCoincidentVertices(list, indices); } else { indices = list.SelectMany(x => x.distinctIndexesInternal).ToList(); } groups.Add(new ElementGroup(indices, trs.MultiplyPoint3x4(bounds.center), rot)); } } break; } case PivotPoint.ActiveElement: { var indices = GetSelectedIndicesForSelectMode(mesh, selectMode, collectCoincident); var position = mesh.transform.position; var rotation = mesh.transform.rotation; if (selectMode.ContainsFlag(SelectMode.Face | SelectMode.TextureFace)) { var face = mesh.GetActiveFace(); if (face != null) { position = trs.MultiplyPoint3x4(Math.GetBounds(mesh.positionsInternal, face.distinctIndexesInternal).center); rotation = UnityEngine.ProBuilder.HandleUtility.GetFaceRotation(mesh, orientation, new Face[] { face }); } } else if (selectMode.ContainsFlag(SelectMode.Edge | SelectMode.TextureEdge)) { var edge = mesh.GetActiveEdge(); if (edge != Edge.Empty) { position = trs.MultiplyPoint3x4(Math.GetBounds(mesh.positionsInternal, new int [] { edge.a, edge.b }).center); rotation = UnityEngine.ProBuilder.HandleUtility.GetEdgeRotation(mesh, orientation, new Edge[] { edge }); } } else if (selectMode.ContainsFlag(SelectMode.Vertex | SelectMode.TextureVertex)) { var vertex = mesh.GetActiveVertex(); if (vertex > -1) { position = trs.MultiplyPoint3x4(mesh.positionsInternal[vertex]); rotation = UnityEngine.ProBuilder.HandleUtility.GetVertexRotation(mesh, orientation, new int[] { vertex }); } } groups.Add(new ElementGroup(indices, position, rotation)); break; } default: { var indices = GetSelectedIndicesForSelectMode(mesh, selectMode, collectCoincident); var position = MeshSelection.bounds.center; var rotation = Quaternion.identity; if (selectMode.ContainsFlag(SelectMode.Face | SelectMode.TextureFace)) { var face = mesh.GetActiveFace(); if (face != null) { rotation = UnityEngine.ProBuilder.HandleUtility.GetFaceRotation(mesh, orientation, new Face[] { face }); } } else if (selectMode.ContainsFlag(SelectMode.Edge | SelectMode.TextureEdge)) { var edge = mesh.GetActiveEdge(); if (edge != Edge.Empty) { rotation = UnityEngine.ProBuilder.HandleUtility.GetEdgeRotation(mesh, orientation, new Edge[] { edge }); } } else if (selectMode.ContainsFlag(SelectMode.Vertex | SelectMode.TextureVertex)) { var vertex = mesh.GetActiveVertex(); if (vertex > -1) { rotation = UnityEngine.ProBuilder.HandleUtility.GetVertexRotation(mesh, orientation, new int[] { vertex }); } } groups.Add(new ElementGroup(indices, position, rotation)); break; } } return(groups); }
public ExtrudedSelection(ProBuilderMesh mesh, Face face) { indices = mesh.GetCoincidentVertices(face.distinctIndexes); normal = Math.Normal(mesh, face); }