void FillBoneWeight(BoneWeight2 boneWeight, List <float> weights) { boneWeight.weight0 = weights.Max(); boneWeight.boneIndex0 = weights.IndexOf(boneWeight.weight0); weights[boneWeight.boneIndex0] = 0f; boneWeight.weight1 = weights.Max(); boneWeight.boneIndex1 = weights.IndexOf(boneWeight.weight1); weights[boneWeight.boneIndex1] = 0f; boneWeight.weight2 = weights.Max(); boneWeight.boneIndex2 = weights.IndexOf(boneWeight.weight2); weights[boneWeight.boneIndex2] = 0f; boneWeight.weight3 = weights.Max(); boneWeight.boneIndex3 = weights.IndexOf(boneWeight.weight3); float sum = boneWeight.weight0 + boneWeight.weight1 + boneWeight.weight2 + boneWeight.weight3; if (sum > 0f) { boneWeight.weight0 /= sum; boneWeight.weight1 /= sum; boneWeight.weight2 /= sum; boneWeight.weight3 /= sum; } else { boneWeight.weight0 = 1f; } }
void DoWindow(int windowId) { Vertex selectedVertex = spriteMeshCache.selectedVertex; string[] names = GetBoneNames(); EditorGUIUtility.wideMode = true; float labelWidth = EditorGUIUtility.labelWidth; if (selectedVertex != null) { BoneWeight2 boneWeight = selectedVertex.boneWeight; int index0 = boneWeight.boneIndex0; int index1 = boneWeight.boneIndex1; int index2 = boneWeight.boneIndex2; int index3 = boneWeight.boneIndex3; float weight0 = boneWeight.weight0; float weight1 = boneWeight.weight1; float weight2 = boneWeight.weight2; float weight3 = boneWeight.weight3; EditorGUIUtility.labelWidth = 30f; EditorGUILayout.BeginHorizontal(); EditorGUI.BeginChangeCheck(); index0 = EditorGUILayout.Popup(index0, names, GUILayout.Width(100f)); weight0 = EditorGUILayout.Slider(weight0, 0f, 1f); if (boneWeight != null && EditorGUI.EndChangeCheck()) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Modify Weights"); boneWeight.SetWeight(0, index0, weight0); } EditorGUILayout.EndHorizontal(); EditorGUILayout.BeginHorizontal(); EditorGUI.BeginChangeCheck(); index1 = EditorGUILayout.Popup(index1, names, GUILayout.Width(100f)); weight1 = EditorGUILayout.Slider(weight1, 0f, 1f); if (boneWeight != null && EditorGUI.EndChangeCheck()) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Modify Weights"); boneWeight.SetWeight(1, index1, weight1); } EditorGUILayout.EndHorizontal(); EditorGUILayout.BeginHorizontal(); EditorGUI.BeginChangeCheck(); index2 = EditorGUILayout.Popup(index2, names, GUILayout.Width(100f)); weight2 = EditorGUILayout.Slider(weight2, 0f, 1f); if (boneWeight != null && EditorGUI.EndChangeCheck()) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Modify Weights"); boneWeight.SetWeight(2, index2, weight2); } EditorGUILayout.EndHorizontal(); EditorGUILayout.BeginHorizontal(); EditorGUI.BeginChangeCheck(); index3 = EditorGUILayout.Popup(index3, names, GUILayout.Width(100f)); weight3 = EditorGUILayout.Slider(weight3, 0f, 1f); if (boneWeight != null && EditorGUI.EndChangeCheck()) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Modify Weights"); boneWeight.SetWeight(3, index3, weight3); } EditorGUILayout.EndHorizontal(); } else { int index = spriteMeshCache.bindPoses.IndexOf(spriteMeshCache.selectedBone); EditorGUILayout.BeginHorizontal(); EditorGUI.BeginChangeCheck(); index = EditorGUILayout.Popup(index, names, GUILayout.Width(100f)); if (index >= 0 && index < spriteMeshCache.bindPoses.Count) { spriteMeshCache.selectedBone = spriteMeshCache.bindPoses[index]; } EditorGUI.BeginDisabledGroup(spriteMeshCache.selectedBone == null); if (Event.current.type == EventType.MouseUp || Event.current.type == EventType.MouseDown) { mLastWeight = 0f; mWeight = 0f; } mWeight = EditorGUILayout.Slider(mLastWeight, -1f, 1f); if (EditorGUI.EndChangeCheck()) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Modify Weights"); float delta = mWeight - mLastWeight; mLastWeight = mWeight; List <Vertex> vertices = spriteMeshCache.selectedVertices; if (vertices.Count == 0) { vertices = spriteMeshCache.texVertices; } foreach (Vertex vertex in vertices) { BoneWeight2 bw = vertex.boneWeight; bw.SetBoneIndexWeight(index, bw.GetBoneWeight(index) + delta); } } EditorGUILayout.EndHorizontal(); EditorGUI.EndDisabledGroup(); } EditorGUILayout.BeginHorizontal(); GUILayout.FlexibleSpace(); if (GUILayout.Button("Smooth")) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Smooth Weights"); List <Vertex> targetVertices = spriteMeshCache.texVertices; if (spriteMeshCache.selectedVertices.Count > 0) { targetVertices = spriteMeshCache.selectedVertices; } spriteMeshCache.SmoothVertices(targetVertices); } if (GUILayout.Button("Auto")) { Undo.RegisterCompleteObjectUndo(spriteMeshCache, "Calculate Weights"); List <Vertex> targetVertices = spriteMeshCache.texVertices; if (spriteMeshCache.selectedVertices.Count > 0) { targetVertices = spriteMeshCache.selectedVertices; } spriteMeshCache.CalculateAutomaticWeights(targetVertices); } GUILayout.FlexibleSpace(); EditorGUILayout.EndHorizontal(); EditorGUILayout.BeginHorizontal(); GUILayout.FlexibleSpace(); EditorGUIUtility.labelWidth = 50f; overlayColors = EditorGUILayout.Toggle("Overlay", overlayColors); EditorGUIUtility.labelWidth = 30f; showPie = EditorGUILayout.Toggle("Pies", showPie); GUILayout.FlexibleSpace(); EditorGUILayout.EndHorizontal(); EditorGUIUtility.labelWidth = labelWidth; /* * boneScrollListPosition = EditorGUILayout.BeginScrollView(boneScrollListPosition); * * boneList.DoLayoutList(); * * EditorGUILayout.EndScrollView(); */ EatMouseInput(new Rect(0, 0, windowRect.width, windowRect.height)); }
public void SmoothVertices(List <Vertex> targetVertices) { float[,] weights = new float[texVertices.Count, bindPoses.Count]; Array.Clear(weights, 0, weights.Length); List <int> usedIndices = new List <int>(); for (int i = 0; i < texVertices.Count; i++) { usedIndices.Clear(); Vertex vertex = texVertices [i]; BoneWeight2 weight = vertex.boneWeight; weights[i, weight.boneIndex0] = weight.weight0; usedIndices.Add(weight.boneIndex0); if (!usedIndices.Contains(weight.boneIndex1)) { weights[i, weight.boneIndex1] = weight.weight1; usedIndices.Add(weight.boneIndex1); } if (!usedIndices.Contains(weight.boneIndex2)) { weights[i, weight.boneIndex2] = weight.weight2; usedIndices.Add(weight.boneIndex2); } if (!usedIndices.Contains(weight.boneIndex3)) { weights[i, weight.boneIndex3] = weight.weight3; usedIndices.Add(weight.boneIndex3); } } float[] denominator = new float[texVertices.Count]; float[,] smoothedWeights = new float[texVertices.Count, bindPoses.Count]; Array.Clear(smoothedWeights, 0, smoothedWeights.Length); for (int i = 0; i < indices.Count / 3; ++i) { for (int j = 0; j < 3; ++j) { int j1 = (j + 1) % 3; int j2 = (j + 2) % 3; for (int k = 0; k < bindPoses.Count; ++k) { smoothedWeights[indices[i * 3 + j], k] += weights[indices[i * 3 + j1], k] + weights[indices[i * 3 + j2], k]; } denominator[indices[i * 3 + j]] += 2; } } for (int i = 0; i < texVertices.Count; ++i) { for (int j = 0; j < bindPoses.Count; ++j) { smoothedWeights[i, j] /= denominator[i]; } } float[,] smoothedWeightsTransposed = new float[bindPoses.Count, texVertices.Count]; for (int i = 0; i < texVertices.Count; ++i) { for (int j = 0; j < bindPoses.Count; ++j) { smoothedWeightsTransposed[j, i] = smoothedWeights[i, j]; } } FillBoneWeights(targetVertices, smoothedWeightsTransposed); isDirty = true; }