void RestoreMaterials(SelectedBrushSurface[] hoverBrushSurfaces) { if (hoverBrushSurfaces == null) { return; } var updateModels = new HashSet <CSGModel>(); var updateBrushes = new HashSet <CSGBrush>(); for (int i = 0; i < hoverBrushSurfaces.Length; i++) { var brush = hoverBrushSurfaces[i].brush; var brush_cache = InternalCSGModelManager.GetBrushCache(brush); if (brush_cache == null || brush_cache.childData == null || brush_cache.childData.Model == null) { continue; } try { var model = brush_cache.childData.Model; updateModels.Add(model); if (updateBrushes.Add(brush)) { InternalCSGModelManager.UnregisterMaterials(model, brush.Shape, false); System.Array.Copy(previousMaterials[i], brush.Shape.Materials, brush.Shape.Materials.Length); } } finally { } } UpdateBrushMeshes(updateBrushes, updateModels); }
public virtual void Cancel() { ResetVisuals(); CleanupGrid(); { if (generatedBrushes != null && generatedBrushes.Length > 0) { for (int i = 0; i < generatedBrushes.Length; i++) { InternalCSGModelManager.OnDestroyed(generatedBrushes[i]); GameObject.DestroyImmediate(generatedBrushes[i]); } } if (generatedGameObjects != null && generatedGameObjects.Length > 0) { for (int i = 0; i < generatedGameObjects.Length; i++) { GameObject.DestroyImmediate(generatedGameObjects[i]); } } if (parentGameObject != null) { GameObject.DestroyImmediate(parentGameObject); } } Cleanup(); Reset(); if (shapeCancelled != null) { shapeCancelled(); } }
void DisableVisualObjects() { //Debug.Log("DisableVisualObjects"); if (visualDragGameObject != null) { for (int i = visualDragGameObject.Count - 1; i >= 0; i--) { var obj = visualDragGameObject[i]; if (obj == null || !obj) { continue; } if (obj.activeSelf) { obj.SetActive(false); } } InternalCSGModelManager.CheckTransformChanged(); InternalCSGModelManager.OnHierarchyModified(); InternalCSGModelManager.UpdateRemoteMeshes(); } }
static void RunEditorUpdate() { if (!RealtimeCSG.CSGSettings.EnableRealtimeCSG) { return; } UpdateLoop.UpdateOnSceneChange(); if (EditorApplication.isPlayingOrWillChangePlaymode) { return; } try { ColorSettings.Update(); InternalCSGModelManager.Refresh(forceHierarchyUpdate: false); TooltipUtility.CleanCache(); } catch (Exception ex) { Debug.LogException(ex); } }
public static CSGBrush CreateBrushInstanceInScene(MenuCommand command) { #if EVALUATION if (NativeMethodBindings.BrushesAvailable() <= 0) { return(null); } #endif var parent = GetTransformForMenu(command); var lastUsedModelTransform = !SelectionUtility.LastUsedModel ? null : SelectionUtility.LastUsedModel.transform; if (lastUsedModelTransform == null && !parent) { lastUsedModelTransform = CreateModelInstanceInScene(parent).transform; parent = lastUsedModelTransform; } else if (!parent) { parent = lastUsedModelTransform; } var name = UnityEditor.GameObjectUtility.GetUniqueNameForSibling(parent, "Brush"); var gameObject = new GameObject(name); var brush = gameObject.AddComponent <CSGBrush>(); gameObject.transform.SetParent(parent, true); gameObject.transform.position = new Vector3(0.5f, 0.5f, 0.5f); // this aligns it's vertices to the grid BrushFactory.CreateCubeControlMesh(out brush.ControlMesh, out brush.Shape, Vector3.one); UnityEditor.Selection.activeGameObject = gameObject; Undo.RegisterCreatedObjectUndo(gameObject, "Created brush"); InternalCSGModelManager.CheckForChanges(); InternalCSGModelManager.UpdateMeshes(); return(brush); }
void UndoRedoPerformed() { InternalCSGModelManager.UndoRedoPerformed(); }
public static void HideUnselectedObjects() { Undo.IncrementCurrentGroup(); var undoGroupIndex = Undo.GetCurrentGroup(); var selected = Selection.gameObjects.ToList(); var selectedIDs = new HashSet <int>(); var models = InternalCSGModelManager.Models; for (var i = 0; i < models.Length; i++) { var model = models[i]; if (!model) { continue; } var modelCache = InternalCSGModelManager.GetModelCache(model); if (modelCache == null || !modelCache.GeneratedMeshes) { continue; } var meshContainerChildren = modelCache.GeneratedMeshes.GetComponentsInChildren <Transform>(); //for (int s = 0; s < MeshInstanceManager.SceneStates.Count; s++) //{ //var sceneState = MeshInstanceManager.SceneStates[s]; //if (!sceneState.ParentMeshContainer) // continue; //var meshContainerChildren = sceneState.ParentMeshContainer.GetComponentsInChildren<Transform>(); foreach (var child in meshContainerChildren) { selected.Add(child.gameObject); } } for (int i = 0; i < selected.Count; i++) // we keep adding parents, and their parents until we hit the root-objects { selectedIDs.Add(selected[i].GetInstanceID()); var transform = selected[i].transform; var parent = transform.parent; if (parent == null) { continue; } selected.Add(parent.gameObject); } for (var sceneIndex = 0; sceneIndex < SceneManager.sceneCount; sceneIndex++) { var activeScene = SceneManager.GetSceneAt(sceneIndex); var rootGameObjects = activeScene.GetRootGameObjects(); for (var i = 0; i < rootGameObjects.Length; i++) { var children = rootGameObjects[i].GetComponentsInChildren <Transform>(); for (var c = 0; c < children.Length; c++) { var transform = children[c]; var gameObject = transform.gameObject; if (!gameObject.activeInHierarchy || (gameObject.hideFlags != HideFlags.None)) { continue; } if (selectedIDs.Contains(gameObject.GetInstanceID())) { continue; } Undo.RecordObject(gameObject, "Hiding Object"); gameObject.SetActive(false); } } } Undo.CollapseUndoOperations(undoGroupIndex); }
public bool DragUpdated(SceneView sceneView) { var camera = sceneView.camera; LegacyBrushIntersection intersection; int highlight_surface = -1; CSGBrush highlight_brush = null; if (!SceneQueryUtility.FindWorldIntersection(camera, Event.current.mousePosition, out intersection)) { highlight_brush = null; highlight_surface = -1; } else { highlight_brush = intersection.brush; highlight_surface = intersection.surfaceIndex; } bool modified = true; if (hoverBrushSurfaces != null) { for (int i = 0; i < hoverBrushSurfaces.Length; i++) { if (hoverBrushSurfaces[i].brush == highlight_brush && hoverBrushSurfaces[i].surfaceIndex == highlight_surface) { modified = false; break; } } } bool needUpdate = false; if (modified) { hoverOnSelectedSurfaces = false; if (hoverBrushSurfaces != null) { needUpdate = true; RestoreMaterials(hoverBrushSurfaces); } hoverBrushSurfaces = HoverOnBrush(new CSGBrush[1] { highlight_brush }, highlight_surface); if (hoverBrushSurfaces != null) { hoverBrushSurfaces = GetCombinedBrushes(hoverBrushSurfaces); needUpdate = true; using (new UndoGroup(hoverBrushSurfaces, "Modified materials")) { RememberMaterials(hoverBrushSurfaces); ApplyMaterial(hoverBrushSurfaces); } } } else { bool prevSelectAllSurfaces = selectAllSurfaces; selectAllSurfaces = Event.current.shift; if (prevSelectAllSurfaces != selectAllSurfaces) { if (hoverBrushSurfaces != null) { needUpdate = true; using (new UndoGroup(hoverBrushSurfaces, "Modified materials")) { ApplyMaterial(hoverBrushSurfaces); } } } } if (needUpdate) { InternalCSGModelManager.UpdateMeshes(); MeshInstanceManager.UpdateHelperSurfaceVisibility(); } return(needUpdate); }
public static void EnsureBuildFinished() { InternalCSGModelManager.Refresh(true); }
protected override void HandleCreateShapeEvents(Rect sceneRect) { if (settings.vertices.Length < 2) { if (editMode == EditMode.ExtrudeShape || editMode == EditMode.EditShape) { editMode = EditMode.CreatePlane; } } bool pointOnEdge = false; bool havePlane = false; bool vertexOnGeometry = false; CSGBrush vertexOnBrush = null; CSGPlane hoverBuildPlane = buildPlane; var sceneView = SceneView.currentDrawingSceneView; //(SceneView.currentDrawingSceneView != null) ? SceneView.currentDrawingSceneView : SceneView.lastActiveSceneView; var camera = (sceneView == null) ? null : sceneView.camera; if (camera != null && camera.pixelRect.Contains(Event.current.mousePosition)) { if (!hoverDefaultPlane.HasValue || settings.vertices.Length == 0) { bool forceGrid = RealtimeCSG.CSGGrid.ForceGrid; RealtimeCSG.CSGGrid.ForceGrid = false; hoverDefaultPlane = RealtimeCSG.CSGGrid.CurrentGridPlane; RealtimeCSG.CSGGrid.ForceGrid = forceGrid; firstSnappedEdges = null; firstSnappedBrush = null; firstSnappedPlanes = null; base.geometryModel = null; } if (editMode == EditMode.CreatePlane) { BrushIntersection intersection; if (!IgnoreDepthForRayCasts(sceneView) && !havePlane && SceneQueryUtility.FindWorldIntersection(Event.current.mousePosition, out intersection)) { worldPosition = intersection.worldIntersection; if (intersection.surfaceInverted) { hoverBuildPlane = intersection.plane.Negated(); } else { hoverBuildPlane = intersection.plane; } vertexOnBrush = intersection.brush; vertexOnGeometry = true; } else { hoverBuildPlane = hoverDefaultPlane.Value; vertexOnBrush = null; var mouseRay = HandleUtility.GUIPointToWorldRay(Event.current.mousePosition); worldPosition = hoverBuildPlane.Intersection(mouseRay); vertexOnGeometry = false; } ResetVisuals(); if (snapFunction != null) { CSGBrush snappedOnBrush; worldPosition = snapFunction(worldPosition, hoverBuildPlane, ref visualSnappedEdges, out snappedOnBrush, generatedBrushes); if (snappedOnBrush != null) { pointOnEdge = (visualSnappedEdges != null && visualSnappedEdges.Count > 0); vertexOnBrush = snappedOnBrush; vertexOnGeometry = true; } } if (settings.vertices.Length == 1) { if (hoverBuildPlane.normal != MathConstants.zeroVector3) { editMode = EditMode.CreateShape; havePlane = true; } } else if (settings.vertices.Length == 2) { onLastPoint = true; } } else { var mouseRay = HandleUtility.GUIPointToWorldRay(Event.current.mousePosition); worldPosition = hoverBuildPlane.Intersection(mouseRay); ResetVisuals(); if (snapFunction != null) { CSGBrush snappedOnBrush; worldPosition = snapFunction(worldPosition, hoverBuildPlane, ref visualSnappedEdges, out snappedOnBrush, generatedBrushes); if (snappedOnBrush != null) { pointOnEdge = (visualSnappedEdges != null && visualSnappedEdges.Count > 0); vertexOnBrush = snappedOnBrush; } } } if (geometryModel == null && vertexOnBrush != null) { var brush_cache = InternalCSGModelManager.GetBrushCache(vertexOnBrush); if (brush_cache != null && brush_cache.childData != null && brush_cache.childData.Model) { geometryModel = brush_cache.childData.Model; } } if (worldPosition != prevWorldPosition) { prevWorldPosition = worldPosition; if (Event.current.type != EventType.Repaint) { SceneView.RepaintAll(); } } visualSnappedGrid = RealtimeCSG.CSGGrid.FindAllGridEdgesThatTouchPoint(worldPosition); visualSnappedBrush = vertexOnBrush; } RealtimeCSG.CSGGrid.SetForcedGrid(hoverBuildPlane); if (!SceneDragToolManager.IsDraggingObjectInScene && Event.current.type == EventType.Repaint) { PaintSnapVisualisation(); PaintShape(base.shapeId); } var type = Event.current.GetTypeForControl(base.shapeId); switch (type) { case EventType.Layout: { return; } case EventType.ValidateCommand: case EventType.KeyDown: { if (GUIUtility.hotControl == base.shapeId) { if (Keys.PerformActionKey.IsKeyPressed() || Keys.DeleteSelectionKey.IsKeyPressed() || Keys.CancelActionKey.IsKeyPressed()) { Event.current.Use(); } } return; } case EventType.KeyUp: { if (GUIUtility.hotControl == base.shapeId) { if (Keys.BoxBuilderMode.IsKeyPressed() || Keys.PerformActionKey.IsKeyPressed()) { HotKeyReleased(); Event.current.Use(); return; } if (Keys.DeleteSelectionKey.IsKeyPressed() || Keys.CancelActionKey.IsKeyPressed()) { Cancel(); Event.current.Use(); return; } } return; } case EventType.MouseDown: { if (!sceneRect.Contains(Event.current.mousePosition)) { break; } if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { return; } if ((GUIUtility.hotControl != 0 && GUIUtility.hotControl != shapeEditId && GUIUtility.hotControl != base.shapeId) || Event.current.button != 0) { return; } Event.current.Use(); if (settings.vertices.Length == 0) { if ((GUIUtility.hotControl == 0 || GUIUtility.hotControl == base.shapeEditId) && base.shapeId != -1) { base.CalculateWorldSpaceTangents(); GUIUtility.hotControl = base.shapeId; GUIUtility.keyboardControl = base.shapeId; EditorGUIUtility.editingTextField = false; } } if (GUIUtility.hotControl == base.shapeId && settings.vertices.Length < 2) { if (!float.IsNaN(worldPosition.x) && !float.IsInfinity(worldPosition.x) && !float.IsNaN(worldPosition.y) && !float.IsInfinity(worldPosition.y) && !float.IsNaN(worldPosition.z) && !float.IsInfinity(worldPosition.z)) { if (hoverBuildPlane.normal.sqrMagnitude != 0) { buildPlane = hoverBuildPlane; } CalculateWorldSpaceTangents(); if (settings.vertices.Length == 0) { if (pointOnEdge) { firstSnappedEdges = visualSnappedEdges.ToArray(); firstSnappedBrush = visualSnappedBrush; firstSnappedPlanes = null; } else { firstSnappedBrush = null; firstSnappedEdges = null; firstSnappedPlanes = null; } geometryPlane = buildPlane; planeOnGeometry = vertexOnGeometry; } else { if (firstSnappedEdges != null) { if (firstSnappedPlanes == null) { CreateSnappedPlanes(); } bool outside = true; for (int i = 0; i < firstSnappedPlanes.Length; i++) { if (firstSnappedPlanes[i].Distance(worldPosition) <= MathConstants.DistanceEpsilon) { outside = false; break; } } planeOnGeometry = !outside; } if (vertexOnGeometry) { var plane = hoverDefaultPlane.Value; var distance = plane.Distance(worldPosition); if (float.IsInfinity(distance) || float.IsNaN(distance)) { distance = 1.0f; } plane.d += distance; hoverDefaultPlane = plane; for (int i = 0; i < settings.vertices.Length; i++) { if (!settings.onGeometryVertices[i]) { settings.vertices[i] = GeometryUtility.ProjectPointOnPlane(plane, settings.vertices[i]); settings.onGeometryVertices[i] = true; } } } } ArrayUtility.Add(ref settings.onGeometryVertices, vertexOnGeometry); settings.AddPoint(worldPosition); SceneView.RepaintAll(); if (settings.vertices.Length == 2) { HotKeyReleased(); } } } return; } case EventType.MouseDrag: { if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { break; } if (GUIUtility.hotControl == base.shapeId && Event.current.button == 0) { Event.current.Use(); } return; } case EventType.MouseUp: { if (GUIUtility.hotControl != base.shapeId) { return; } if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { return; } if (Event.current.button == 0) { Event.current.Use(); ResetVisuals(); if (onLastPoint) { GUIUtility.hotControl = 0; GUIUtility.keyboardControl = 0; EditorGUIUtility.editingTextField = false; editMode = EditMode.CreateShape; HotKeyReleased(); } } return; } } return; }
// returns true on success internal static bool AddNode(HierarchyItem node, ParentNodeData top) { if (node.Parent != null) { //Debug.Log("node.parent != null"); return(false); } if (!top.Transform) { // var top_transform_name = (top.transform == null) ? "null" : top.transform.name; // var node_transform_name = (node.transform == null) ? "null" : node.transform.name; // Debug.Log("!top.transform (top.transform=" + top_transform_name + ", node.transform = " + node_transform_name + ")", node.transform); return(false); } var ancestors = new List <Transform>(); var leafTransform = node.Transform; if (leafTransform == null) { //Debug.Log("node.transform == null"); return(false); } var iterator = leafTransform.parent; while (iterator != null && iterator != top.Transform) { ancestors.Add(iterator); iterator = iterator.parent; } var defaultModel = InternalCSGModelManager.GetDefaultCSGModelForObject(iterator); if (!defaultModel) { return(false); } var defaultModelTransform = defaultModel.transform; if (iterator == null || top.Transform == null || top.Transform == defaultModelTransform) { iterator = defaultModelTransform; } if (iterator == null) { node.Reset(); top.Reset(); //Debug.Log("iterator == null"); return(false); } if (iterator != top.Transform) { //Debug.Log("iterator != top.transform"); return(false); } // var currentLoopCount = CurrentLoopCount; HierarchyItem lastParent = top; var ancestorDepth = ancestors.Count - 1; while (ancestorDepth >= 0) { var ancestor = ancestors[ancestorDepth]; int childIndex; if (!lastParent.FindSiblingIndex(ancestor, ancestor.GetSiblingIndex(), ancestor.GetInstanceID(), out childIndex)) { break; } lastParent = lastParent.ChildNodes[childIndex]; ancestorDepth--; } while (ancestorDepth >= 0) { var newAncestor = new HierarchyItem(); newAncestor.Transform = ancestors[ancestorDepth]; newAncestor.TransformID = newAncestor.Transform.GetInstanceID(); newAncestor.Parent = lastParent; if (!lastParent.AddChildItem(newAncestor)) { return(false); } lastParent = newAncestor; ancestorDepth--; } node.Parent = lastParent; top.ChildrenModified = true; return(lastParent.AddChildItem(node)); }
public static void OnInspectorGUI(UnityEngine.Object[] targets) { InitReflection(); if (!localStyles) { popupStyle = new GUIStyle(EditorStyles.popup); //popupStyle.padding.top += 2; popupStyle.margin.top += 2; localStyles = true; } bool updateMeshes = false; var models = new CSGModel[targets.Length]; for (int i = targets.Length - 1; i >= 0; i--) { models[i] = targets[i] as CSGModel; if (!models[i]) { ArrayUtility.RemoveAt(ref models, i); } } if (models.Length == 0) { return; } var settings = models[0].Settings; var vertexChannels = models[0].VertexChannels; ExportType? exportType = models[0].exportType; bool? VertexChannelColor = (vertexChannels & VertexChannelFlags.Color) == VertexChannelFlags.Color; bool? VertexChannelTangent = (vertexChannels & VertexChannelFlags.Tangent) == VertexChannelFlags.Tangent; bool? VertexChannelNormal = (vertexChannels & VertexChannelFlags.Normal) == VertexChannelFlags.Normal; bool? VertexChannelUV0 = (vertexChannels & VertexChannelFlags.UV0) == VertexChannelFlags.UV0; bool? InvertedWorld = (settings & ModelSettingsFlags.InvertedWorld) == ModelSettingsFlags.InvertedWorld; bool? NoCollider = (settings & ModelSettingsFlags.NoCollider) == ModelSettingsFlags.NoCollider; bool? IsTrigger = (settings & ModelSettingsFlags.IsTrigger) == ModelSettingsFlags.IsTrigger; bool? SetToConvex = (settings & ModelSettingsFlags.SetColliderConvex) == ModelSettingsFlags.SetColliderConvex; bool? AutoGenerateRigidBody = (settings & ModelSettingsFlags.AutoUpdateRigidBody) == ModelSettingsFlags.AutoUpdateRigidBody; bool? DoNotRender = (settings & ModelSettingsFlags.DoNotRender) == ModelSettingsFlags.DoNotRender; bool? ReceiveShadows = !((settings & ModelSettingsFlags.DoNotReceiveShadows) == ModelSettingsFlags.DoNotReceiveShadows); bool? AutoRebuildUVs = (settings & ModelSettingsFlags.AutoRebuildUVs) == ModelSettingsFlags.AutoRebuildUVs; bool? PreserveUVs = (settings & ModelSettingsFlags.PreserveUVs) == ModelSettingsFlags.PreserveUVs; bool? ShowGeneratedMeshes = models[0].ShowGeneratedMeshes; ShadowCastingMode?ShadowCastingMode = (ShadowCastingMode)(settings & ModelSettingsFlags.ShadowCastingModeFlags); var defaultPhysicsMaterial = models[0].DefaultPhysicsMaterial; var defaultPhysicsMaterialMixed = false; for (int i = 1; i < models.Length; i++) { settings = models[i].Settings; vertexChannels = models[i].VertexChannels; ExportType currExportType = models[i].exportType; bool currVertexChannelColor = (vertexChannels & VertexChannelFlags.Color) == VertexChannelFlags.Color; bool currVertexChannelTangent = (vertexChannels & VertexChannelFlags.Tangent) == VertexChannelFlags.Tangent; bool currVertexChannelNormal = (vertexChannels & VertexChannelFlags.Normal) == VertexChannelFlags.Normal; bool currVertexChannelUV0 = (vertexChannels & VertexChannelFlags.UV0) == VertexChannelFlags.UV0; bool currInvertedWorld = (settings & ModelSettingsFlags.InvertedWorld) == ModelSettingsFlags.InvertedWorld; bool currNoCollider = (settings & ModelSettingsFlags.NoCollider) == ModelSettingsFlags.NoCollider; bool currIsTrigger = (settings & ModelSettingsFlags.IsTrigger) == ModelSettingsFlags.IsTrigger; bool currSetToConvex = (settings & ModelSettingsFlags.SetColliderConvex) == ModelSettingsFlags.SetColliderConvex; bool currAutoGenerateRigidBody = (settings & ModelSettingsFlags.AutoUpdateRigidBody) == ModelSettingsFlags.AutoUpdateRigidBody; bool currDoNotRender = (settings & ModelSettingsFlags.DoNotRender) == ModelSettingsFlags.DoNotRender; bool currReceiveShadows = !((settings & ModelSettingsFlags.DoNotReceiveShadows) == ModelSettingsFlags.DoNotReceiveShadows); bool currAutoRebuildUVs = (settings & ModelSettingsFlags.AutoRebuildUVs) == ModelSettingsFlags.AutoRebuildUVs; bool currPreserveUVs = (settings & ModelSettingsFlags.PreserveUVs) == ModelSettingsFlags.PreserveUVs; bool currShowGeneratedMeshes = models[i].ShowGeneratedMeshes; var currdefaultPhysicsMaterial = models[i].DefaultPhysicsMaterial; ShadowCastingMode currShadowCastingMode = (ShadowCastingMode)(settings & ModelSettingsFlags.ShadowCastingModeFlags); if (VertexChannelColor.HasValue && VertexChannelColor.Value != currVertexChannelColor) { VertexChannelColor = null; } if (VertexChannelTangent.HasValue && VertexChannelTangent.Value != currVertexChannelTangent) { VertexChannelTangent = null; } if (VertexChannelNormal.HasValue && VertexChannelNormal.Value != currVertexChannelNormal) { VertexChannelNormal = null; } if (VertexChannelUV0.HasValue && VertexChannelUV0.Value != currVertexChannelUV0) { VertexChannelUV0 = null; } if (exportType.HasValue && exportType.Value != currExportType) { exportType = null; } if (InvertedWorld.HasValue && InvertedWorld.Value != currInvertedWorld) { InvertedWorld = null; } if (NoCollider.HasValue && NoCollider.Value != currNoCollider) { NoCollider = null; } if (IsTrigger.HasValue && IsTrigger.Value != currIsTrigger) { IsTrigger = null; } if (SetToConvex.HasValue && SetToConvex.Value != currSetToConvex) { SetToConvex = null; } if (AutoGenerateRigidBody.HasValue && AutoGenerateRigidBody.Value != currAutoGenerateRigidBody) { AutoGenerateRigidBody = null; } if (DoNotRender.HasValue && DoNotRender.Value != currDoNotRender) { DoNotRender = null; } if (ReceiveShadows.HasValue && ReceiveShadows.Value != currReceiveShadows) { ReceiveShadows = null; } if (ShadowCastingMode.HasValue && ShadowCastingMode.Value != currShadowCastingMode) { ShadowCastingMode = null; } if (AutoRebuildUVs.HasValue && AutoRebuildUVs.Value != currAutoRebuildUVs) { AutoRebuildUVs = null; } if (PreserveUVs.HasValue && PreserveUVs.Value != currPreserveUVs) { PreserveUVs = null; } if (ShowGeneratedMeshes.HasValue && ShowGeneratedMeshes.Value != currShowGeneratedMeshes) { ShowGeneratedMeshes = null; } if (defaultPhysicsMaterial != currdefaultPhysicsMaterial) { defaultPhysicsMaterialMixed = true; } } GUILayout.BeginVertical(GUI.skin.box); { EditorGUILayout.LabelField("Behaviour"); EditorGUI.indentLevel++; { bool inverted_world = InvertedWorld.HasValue ? InvertedWorld.Value : false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !InvertedWorld.HasValue; inverted_world = EditorGUILayout.Toggle(InvertedWorldContent, inverted_world); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (inverted_world) { models[i].Settings |= ModelSettingsFlags.InvertedWorld; } else { models[i].Settings &= ~ModelSettingsFlags.InvertedWorld; } } GUI.changed = true; InvertedWorld = inverted_world; } } EditorGUI.indentLevel--; } GUILayout.EndVertical(); if (models != null && models.Length == 1) { GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); { EditorGUILayout.LabelField("Export"); GUILayout.BeginHorizontal(); { EditorGUI.BeginDisabledGroup(!exportType.HasValue); { if (GUILayout.Button("Export to ...") && exportType.HasValue) { #if !DEMO MeshInstanceManager.Export(models[0], exportType.Value); #else Debug.LogWarning("Export is disabled in demo version"); #endif } } EditorGUI.EndDisabledGroup(); EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !exportType.HasValue; exportType = (ExportType)EditorGUILayout.EnumPopup(exportType ?? ExportType.FBX, popupStyle); EditorGUI.showMixedValue = false; } if (EditorGUI.EndChangeCheck() && exportType.HasValue) { for (int i = 0; i < models.Length; i++) { models[i].exportType = exportType.Value; } } } GUILayout.EndHorizontal(); } GUILayout.EndVertical(); } GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); { EditorGUILayout.LabelField("Physics"); EditorGUI.indentLevel++; { bool collider_value = NoCollider.HasValue ? NoCollider.Value : false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !NoCollider.HasValue; collider_value = !EditorGUILayout.Toggle(GenerateColliderContent, !collider_value); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (collider_value) { models[i].Settings |= ModelSettingsFlags.NoCollider; } else { models[i].Settings &= ~ModelSettingsFlags.NoCollider; } } GUI.changed = true; NoCollider = collider_value; updateMeshes = true; } } var have_no_collider = NoCollider.HasValue && NoCollider.Value; EditorGUI.BeginDisabledGroup(have_no_collider); { bool trigger_value_mixed = have_no_collider ? true : !IsTrigger.HasValue; bool trigger_value = IsTrigger.HasValue ? IsTrigger.Value : false; { EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = trigger_value_mixed; trigger_value = EditorGUILayout.Toggle(ModelIsTriggerContent, trigger_value); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (trigger_value) { models[i].Settings |= ModelSettingsFlags.IsTrigger; } else { models[i].Settings &= ~ModelSettingsFlags.IsTrigger; } } GUI.changed = true; IsTrigger = trigger_value; updateMeshes = true; } } bool set_convex_value_mixed = have_no_collider ? true : !SetToConvex.HasValue; bool set_convex_value = have_no_collider ? false : (SetToConvex.HasValue ? SetToConvex.Value : false); { EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = set_convex_value_mixed; var prevColor = GUI.color; if (!set_convex_value && trigger_value) { var color = new Color(1, 0.25f, 0.25f); GUI.color = color; } set_convex_value = EditorGUILayout.Toggle(ColliderSetToConvexContent, set_convex_value); GUI.color = prevColor; } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (set_convex_value) { models[i].Settings |= ModelSettingsFlags.SetColliderConvex; } else { models[i].Settings &= ~ModelSettingsFlags.SetColliderConvex; } } GUI.changed = true; SetToConvex = set_convex_value; updateMeshes = true; } } { EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = defaultPhysicsMaterialMixed; GUILayout.BeginHorizontal(); EditorGUILayout.PrefixLabel(DefaultPhysicsMaterialContent); defaultPhysicsMaterial = EditorGUILayout.ObjectField(defaultPhysicsMaterial, typeof(PhysicMaterial), true) as PhysicMaterial; GUILayout.EndHorizontal(); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { models[i].DefaultPhysicsMaterial = defaultPhysicsMaterial; } GUI.changed = true; //MeshInstanceManager.Clear(); updateMeshes = true; } } if (!have_no_collider && !set_convex_value && trigger_value) { var prevColor = GUI.color; var color = new Color(1, 0.25f, 0.25f); GUI.color = color; GUILayout.Label("Warning:\r\nFor performance reasons colliders need to\r\nbe convex!"); GUI.color = prevColor; } } EditorGUI.EndDisabledGroup(); { bool autoRigidbody = (AutoGenerateRigidBody.HasValue ? AutoGenerateRigidBody.Value : false); EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !AutoGenerateRigidBody.HasValue; autoRigidbody = !EditorGUILayout.Toggle(ColliderAutoRigidBodyContent, !autoRigidbody); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (autoRigidbody) { models[i].Settings |= ModelSettingsFlags.AutoUpdateRigidBody; } else { models[i].Settings &= ~ModelSettingsFlags.AutoUpdateRigidBody; } } GUI.changed = true; AutoGenerateRigidBody = autoRigidbody; } } EditorGUI.indentLevel--; } GUILayout.EndVertical(); GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); { ShadowCastingMode shadowcastingValue = ShadowCastingMode.HasValue ? ShadowCastingMode.Value : UnityEngine.Rendering.ShadowCastingMode.On; var castOnlyShadow = (shadowcastingValue == UnityEngine.Rendering.ShadowCastingMode.ShadowsOnly); EditorGUILayout.LabelField("Rendering"); EditorGUI.indentLevel++; EditorGUI.BeginDisabledGroup(castOnlyShadow); { bool donotrender_value = castOnlyShadow ? true : (DoNotRender.HasValue ? DoNotRender.Value : false); EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = castOnlyShadow ? true : !DoNotRender.HasValue; donotrender_value = EditorGUILayout.Toggle(DoNotRenderContent, donotrender_value); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (donotrender_value) { models[i].Settings |= ModelSettingsFlags.DoNotRender; } else { models[i].Settings &= ~ModelSettingsFlags.DoNotRender; } } GUI.changed = true; DoNotRender = donotrender_value; updateMeshes = true; } } EditorGUI.EndDisabledGroup(); GUILayout.Space(10); EditorGUI.BeginDisabledGroup(DoNotRender.HasValue && DoNotRender.Value); { EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !ShadowCastingMode.HasValue; shadowcastingValue = (ShadowCastingMode)EditorGUILayout.EnumPopup(CastShadows, shadowcastingValue); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { settings = models[i].Settings; settings &= ~ModelSettingsFlags.ShadowCastingModeFlags; settings |= (ModelSettingsFlags)(((int)shadowcastingValue) & (int)ModelSettingsFlags.ShadowCastingModeFlags); models[i].Settings = settings; } GUI.changed = true; ShadowCastingMode = shadowcastingValue; updateMeshes = true; } var isUsingDeferredRenderingPath = false; //IsUsingDeferredRenderingPath(); EditorGUI.BeginDisabledGroup(castOnlyShadow || isUsingDeferredRenderingPath); { var receiveshadowsValue = !castOnlyShadow && (isUsingDeferredRenderingPath || (ReceiveShadows ?? false)); EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = (castOnlyShadow || !ReceiveShadows.HasValue) && !isUsingDeferredRenderingPath; receiveshadowsValue = EditorGUILayout.Toggle(ModelInspectorGUI.ReceiveShadowsContent, receiveshadowsValue || isUsingDeferredRenderingPath); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (receiveshadowsValue) { models[i].Settings &= ~ModelSettingsFlags.DoNotReceiveShadows; } else { models[i].Settings |= ModelSettingsFlags.DoNotReceiveShadows; } } GUI.changed = true; ReceiveShadows = receiveshadowsValue; } } EditorGUI.EndDisabledGroup(); } EditorGUI.EndDisabledGroup(); EditorGUI.BeginDisabledGroup(castOnlyShadow); EditorGUI.showMixedValue = false; UpdateTargets(models); if (_probesInstance != null && _probesOnGUIMethod != null && _probesTargets != null && _probesInitialized) { GUILayout.Space(10); try { #if UNITY_5_6_OR_NEWER _probesSerializedObject.UpdateIfRequiredOrScript(); #else _probesSerializedObject.UpdateIfDirtyOrScript(); #endif _probesOnGUIMethod.Invoke(_probesInstance, new System.Object[] { _probesTargets, (Renderer)_probesTargets[0], false }); _probesSerializedObject.ApplyModifiedProperties(); } catch { } } EditorGUI.EndDisabledGroup(); EditorGUI.indentLevel--; } GUILayout.EndVertical(); GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); { EditorGUILayout.LabelField("Lighting"); EditorGUI.indentLevel++; { EditorGUI.indentLevel++; CommonGUI.GenerateLightmapUVButton(models); EditorGUI.indentLevel--; EditorGUILayout.LabelField("UV Settings"); EditorGUI.indentLevel++; { var autoRebuildUvs = AutoRebuildUVs ?? false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !AutoRebuildUVs.HasValue; autoRebuildUvs = EditorGUILayout.Toggle(AutoRebuildUVsContent, autoRebuildUvs); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (autoRebuildUvs) { models[i].Settings |= ModelSettingsFlags.AutoRebuildUVs; } else { models[i].Settings &= ~ModelSettingsFlags.AutoRebuildUVs; } } GUI.changed = true; AutoRebuildUVs = autoRebuildUvs; updateMeshes = true; } } { var preserveUVs = PreserveUVs ?? false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !PreserveUVs.HasValue; preserveUVs = EditorGUILayout.Toggle(PreserveUVsContent, preserveUVs); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { if (preserveUVs) { models[i].Settings |= ModelSettingsFlags.PreserveUVs; } else { models[i].Settings &= ~ModelSettingsFlags.PreserveUVs; } } GUI.changed = true; PreserveUVs = preserveUVs; updateMeshes = true; } } EditorGUI.indentLevel--; } EditorGUI.indentLevel--; } GUILayout.EndVertical(); GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); { EditorGUILayout.LabelField("Mesh (advanced)"); EditorGUI.indentLevel++; { var showGeneratedMeshes = ShowGeneratedMeshes ?? false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !ShowGeneratedMeshes.HasValue; showGeneratedMeshes = EditorGUILayout.Toggle(ShowGeneratedMeshesContent, showGeneratedMeshes); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { models[i].ShowGeneratedMeshes = showGeneratedMeshes; MeshInstanceManager.UpdateGeneratedMeshesVisibility(models[i]); } } GUILayout.Space(10); EditorGUILayout.LabelField("Used Vertex Channels"); EditorGUI.indentLevel++; { var vertex_channel_color = VertexChannelColor ?? false; var vertex_channel_tangent = VertexChannelTangent ?? false; var vertex_channel_normal = VertexChannelNormal ?? false; var vertex_channel_UV0 = VertexChannelUV0 ?? false; EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = !VertexChannelColor.HasValue; vertex_channel_color = EditorGUILayout.Toggle(VertexChannelColorContent, vertex_channel_color); EditorGUI.showMixedValue = !VertexChannelTangent.HasValue; vertex_channel_tangent = EditorGUILayout.Toggle(VertexChannelTangentContent, vertex_channel_tangent); EditorGUI.showMixedValue = !VertexChannelNormal.HasValue; vertex_channel_normal = EditorGUILayout.Toggle(VertexChannelNormalContent, vertex_channel_normal); EditorGUI.showMixedValue = !VertexChannelUV0.HasValue; vertex_channel_UV0 = EditorGUILayout.Toggle(VertexChannelUV1Content, vertex_channel_UV0); } if (EditorGUI.EndChangeCheck()) { for (int i = 0; i < models.Length; i++) { var vertexChannel = models[i].VertexChannels; vertexChannel &= ~(VertexChannelFlags.Color | VertexChannelFlags.Tangent | VertexChannelFlags.Normal | VertexChannelFlags.UV0); if (vertex_channel_color) { vertexChannel |= VertexChannelFlags.Color; } if (vertex_channel_tangent) { vertexChannel |= VertexChannelFlags.Tangent; } if (vertex_channel_normal) { vertexChannel |= VertexChannelFlags.Normal; } if (vertex_channel_UV0) { vertexChannel |= VertexChannelFlags.UV0; } models[i].VertexChannels = vertexChannel; } GUI.changed = true; } } EditorGUI.indentLevel--; } EditorGUI.indentLevel--; } GUILayout.EndVertical(); if (models != null && models.Length == 1) { GUILayout.Space(10); GUILayout.BeginVertical(GUI.skin.box); _showDetails = EditorGUILayout.BeginToggleGroup("Statistics", _showDetails); if (_showDetails) { var model_cache = InternalCSGModelManager.GetModelCache(models[0]); if (model_cache == null || model_cache.GeneratedMeshes == null || !model_cache.GeneratedMeshes) { GUILayout.Label("Could not find model cache for this model."); } else { var meshContainer = model_cache.GeneratedMeshes; var totalTriangles = 0; var totalVertices = 0; var totalMeshes = 0; var materialMeshes = new Dictionary <Material, List <MeshData> >(); foreach (var instance in meshContainer.meshInstances.Values) { var mesh = instance.SharedMesh; if (!MeshInstanceManager.HasVisibleMeshRenderer(instance)) { continue; } List <MeshData> meshes; if (!materialMeshes.TryGetValue(instance.RenderMaterial, out meshes)) { meshes = new List <MeshData>(); materialMeshes[instance.RenderMaterial] = meshes; } var meshData = new MeshData(); meshData.Mesh = mesh; meshData.VertexCount = mesh.vertexCount; meshData.TriangleCount = mesh.triangles.Length / 3; meshes.Add(meshData); totalVertices += meshData.VertexCount; totalTriangles = meshData.TriangleCount; totalMeshes++; } EditorGUI.indentLevel++; EditorGUILayout.Space(); EditorGUILayout.LabelField("total:"); EditorGUILayout.LabelField("vertices: " + totalVertices + " triangles: " + totalTriangles + " materials: " + materialMeshes.Count + " meshes: " + totalMeshes); GUILayout.Space(10); EditorGUILayout.LabelField("meshes:"); foreach (var item in materialMeshes) { var material = item.Key; var meshes = item.Value; GUILayout.BeginHorizontal(); { EditorGUI.BeginDisabledGroup(true); { EditorGUILayout.ObjectField(material, typeof(Material), true); } GUILayout.BeginVertical(); { if (meshes.Count == 1) { EditorGUILayout.ObjectField(meshes[0].Mesh, typeof(Mesh), true); EditorGUILayout.LabelField("vertices " + meshes[0].VertexCount + " triangles " + meshes[0].TriangleCount); } else { for (int i = 0; i < meshes.Count; i++) { EditorGUILayout.ObjectField(meshes[i].Mesh, typeof(Mesh), true); EditorGUILayout.LabelField("vertices " + meshes[i].VertexCount + " triangles " + meshes[i].TriangleCount); } } } GUILayout.EndVertical(); EditorGUI.EndDisabledGroup(); } GUILayout.EndHorizontal(); EditorGUILayout.Space(); } EditorGUI.indentLevel--; } } EditorGUILayout.EndToggleGroup(); GUILayout.EndVertical(); } EditorGUI.showMixedValue = false; if (updateMeshes) { InternalCSGModelManager.DoForcedMeshUpdate(); SceneViewEventHandler.ResetUpdateRoutine(); } }
internal override bool CreateControlMeshForBrushIndex(CSGModel parentModel, CSGBrush brush, ShapePolygon polygon, Matrix4x4 localToWorld, float height, out ControlMesh newControlMesh, out Shape newShape) { bool smooth = settings.circleSmoothShading; bool singleSurfaceEnds = settings.circleSingleSurfaceEnds; var direction = haveForcedDirection ? forcedDirection : buildPlane.normal; if (!ShapePolygonUtility.GenerateControlMeshFromVertices(polygon, localToWorld, GeometryUtility.RotatePointIntoPlaneSpace(buildPlane, direction), height, new TexGen(), smooth, singleSurfaceEnds, out newControlMesh, out newShape)) { return(false); } brush.Shape = newShape; brush.ControlMesh = newControlMesh; InternalCSGModelManager.ValidateBrush(brush, true); ControlMeshUtility.RebuildShape(brush); var vertices = polygon.Vertices; float circumference = 0.0f; for (int j = vertices.Length - 1, i = 0; i < vertices.Length; j = i, i++) { circumference += (vertices[j] - vertices[i]).magnitude; } var shape = brush.Shape; float desiredTextureLength = Mathf.Max(1.0f, Mathf.Round(circumference)); float scalar = desiredTextureLength / circumference; shape.TexGens[0].Scale.x = scalar; shape.TexGens[0].Scale.y = shape.TexGens[0].Scale.y; shape.TexGens[0].Translation.x = 0; var count = vertices.Length; if (!singleSurfaceEnds) { GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, 0, count); GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, 0, count + count); for (int j = 0, i = 1; i < count; j = i, i++) { GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, j, i); GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, i, i + count); GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, i, i + count + count); } } else { for (int j = 0, i = 1; i < count; j = i, i++) { GeometryUtility.ContinueTexGenFromSurfaceToSurface(brush, j, i); } } return(true); }
//void OnSceneGUI() <- paints -everything- again for every selected brush public static void OnSceneGUI(SceneView sceneView) { if (EditorApplication.isPlayingOrWillChangePlaymode) { return; } /* * int prevHotControl = GUIUtility.hotControl; * int prevKeyboardControl = GUIUtility.keyboardControl; * * // make it impossible for the tool to click in the bottom bar area * int bottomBarId = GUIUtility.GetControlID (BottomBarInputHash, FocusType.Passive); * bool forceRevert = false; * //if (GUIUtility.hotControl == 0) * { * var bottomBarRect = sceneView.position; * var min = bottomBarRect.min; * var max = bottomBarRect.max; * * min.y = max.y - (GUIStyleUtility.BottomToolBarHeight + 18); * * bottomBarRect.min = min; * bottomBarRect.max = max; * * if (bottomBarRect.Contains(Event.current.mousePosition)) * { * GUIUtility.hotControl = bottomBarId; * GUIUtility.keyboardControl = bottomBarId; * forceRevert = true; * } * } */ SelectionUtility.HandleEvents(); InitTools(); HandleBuilderEvents(); //HandleYMode(); { UpdateTool(); if (instance.activeTool != null) { if (RealtimeCSG.CSGSettings.EnableRealtimeCSG) { // handle the tool var sceneSize = sceneView.position.size; var sceneRect = new Rect(0, 0, sceneSize.x, sceneSize.y - ((GUIStyleUtility.BottomToolBarHeight + 4) + 17)); //var originalEventType = Event.current.type; //if (originalEventType == EventType.MouseMove || // originalEventType == EventType.MouseUp) // holdingDownMouse = false; //var mousePos = Event.current.mousePosition; //if (originalEventType == EventType.Layout || // originalEventType == EventType.Repaint || // sceneRect.Contains(mousePos) || // holdingDownMouse) instance.activeTool.HandleEvents(sceneRect); //if (originalEventType == EventType.MouseDown || // originalEventType == EventType.MouseDrag) // holdingDownMouse = true; } else { if (Event.current.type == EventType.Repaint) { var brushes = instance.filteredSelection.BrushTargets; var wireframes = new List <GeometryWireframe>(brushes.Length); var translations = new List <Vector3>(brushes.Length); for (int i = 0; i < brushes.Length; i++) { var brush = brushes[i]; if (!brush) { continue; } var brushCache = InternalCSGModelManager.GetBrushCache(brush); if (brushCache == null || brushCache.childData == null || !brushCache.childData.Model) { continue; } var brushTranslation = brushCache.compareTransformation.modelLocalPosition + brushCache.childData.ModelTransform.position; wireframes.Add(BrushOutlineManager.GetBrushOutline(brushes[i].brushID)); translations.Add(brushTranslation); } if (wireframes.Count > 0) { CSGRenderer.DrawSelectedBrushes(instance.zTestLineMeshManager, instance.noZTestLineMeshManager, wireframes.ToArray(), translations.ToArray(), ColorSettings.SelectedOutlines, ToolConstants.thickLineScale); } MaterialUtility.LineDashMultiplier = 1.0f; MaterialUtility.LineThicknessMultiplier = 1.0f; MaterialUtility.LineAlphaMultiplier = 1.0f; instance.zTestLineMeshManager.Render(MaterialUtility.ZTestGenericLine); instance.zTestLineMeshManager.Render(MaterialUtility.ZTestGenericLine); } } } } /* * // reset the control so the bottom bar can take over * if (forceRevert) * { * GUIUtility.hotControl = prevHotControl; * GUIUtility.keyboardControl = prevKeyboardControl; * } */ int sceneWindowId = GUIUtility.GetControlID(SceneWindowHash, FocusType.Passive); var sceneWindowType = Event.current.GetTypeForControl(sceneWindowId); if (sceneWindowType == EventType.Repaint) { if (currentEditorWindows.Count > 0) { for (int i = 0; i < currentEditorWindows.Count; i++) { currentEditorWindows[i].Repaint(); } return; } } if (sceneWindowType == EventType.MouseMove) { SceneTools.IsDraggingObjectInScene = false; } if (RealtimeCSG.CSGSettings.EnableRealtimeCSG) { if (sceneView != null && sceneWindowType != EventType.Used && !SceneTools.IsDraggingObjectInScene) { if (currentEditorWindows.Count == 0) { try { Handles.BeginGUI(); Rect windowRect = new Rect(Vector2.zero, sceneView.position.size); CSGBrushEditorGUI.HandleWindowGUI(windowRect); } finally { Handles.EndGUI(); } } } } }
public static void ForceRebuild() { InternalCSGModelManager.Rebuild(); }
protected bool GenerateBrushObjects(int brushObjectCount, bool inGridSpace = true) { Undo.IncrementCurrentGroup(); undoGroupIndex = Undo.GetCurrentGroup(); var lastUsedModel = SelectionUtility.LastUsedModel; if (!ModelTraits.IsModelEditable(lastUsedModel)) { lastUsedModel = null; } var lastUsedModelTransform = !lastUsedModel ? null : lastUsedModel.transform; if (!lastUsedModelTransform || !lastUsedModel.isActiveAndEnabled) { if (prevSelection != null && prevSelection.Length > 0) { for (int i = 0; i < prevSelection.Length; i++) { UnityEngine.Object obj = prevSelection[i]; CSGBrush brush = obj as CSGBrush; MonoBehaviour mono = obj as MonoBehaviour; GameObject go = obj as GameObject; if (!brush) { if (mono) { brush = mono.GetComponentInChildren <CSGBrush>(); } if (go) { brush = go.GetComponentInChildren <CSGBrush>(); } } if (!brush) { continue; } if ((brush.gameObject.hideFlags & (HideFlags.HideInHierarchy | HideFlags.NotEditable | HideFlags.DontSaveInBuild)) != 0) { continue; } if (brush.ChildData == null || brush.ChildData.ModelTransform == null) { continue; } var model = brush.ChildData.Model; if (!model || !model.isActiveAndEnabled) { continue; } lastUsedModelTransform = brush.ChildData.ModelTransform; break; } } } if (generatedBrushes != null && generatedBrushes.Length > 0) { for (int i = generatedBrushes.Length - 1; i >= 0; i--) { if (generatedBrushes[i]) { continue; } ArrayUtility.RemoveAt(ref generatedBrushes, i); } for (int i = generatedGameObjects.Length - 1; i >= 0; i--) { if (generatedGameObjects[i]) { var brush = generatedGameObjects[i].GetComponentInChildren <CSGBrush>(); if (brush && ArrayUtility.Contains(generatedBrushes, brush)) { continue; } } ArrayUtility.RemoveAt(ref generatedGameObjects, i); } } if (generatedGameObjects == null || generatedGameObjects.Length != brushObjectCount) { if (generatedBrushes != null && generatedBrushes.Length > 0) { for (int i = 0; i < generatedBrushes.Length; i++) { InternalCSGModelManager.OnDestroyed(generatedBrushes[i]); GameObject.DestroyImmediate(generatedBrushes[i]); } } if (generatedGameObjects != null && generatedGameObjects.Length > 0) { for (int i = 0; i < generatedGameObjects.Length; i++) { GameObject.DestroyImmediate(generatedGameObjects[i]); } } if (parentGameObject != null) { GameObject.DestroyImmediate(parentGameObject); } //DebugEditorWindow.PrintDebugInfo(); if (lastUsedModelTransform == null) { parentGameObject = OperationsUtility.CreateGameObject(lastUsedModelTransform, "Model", true); InternalCSGModelManager.CreateCSGModel(parentGameObject); parentModel = parentGameObject.GetComponent <CSGModel>(); Undo.RegisterCreatedObjectUndo(parentGameObject, "Created model"); if (brushObjectCount > 1) { operationGameObject = OperationsUtility.CreateGameObject(parentGameObject.transform, "Operation", true); var transform = operationGameObject.transform; SetBrushTransformation(transform); var operation = operationGameObject.AddComponent <CSGOperation>(); if (CurrentCSGOperationType != invalidCSGOperationType) { operation.OperationType = CurrentCSGOperationType; } operation.HandleAsOne = true; Undo.RegisterCreatedObjectUndo(operationGameObject, "Created operation"); parentTransform = operationGameObject.transform; } else { parentTransform = parentGameObject.transform; } } else if (brushObjectCount > 1) { parentModel = lastUsedModelTransform.GetComponent <CSGModel>(); parentGameObject = OperationsUtility.CreateGameObject(lastUsedModelTransform, "Brushes", true); var transform = parentGameObject.transform; SetBrushTransformation(transform); operationGameObject = parentGameObject; var operation = operationGameObject.AddComponent <CSGOperation>(); if (CurrentCSGOperationType != invalidCSGOperationType) { operation.OperationType = CurrentCSGOperationType; } operation.HandleAsOne = true; parentTransform = operationGameObject.transform; Undo.RegisterCreatedObjectUndo(parentGameObject, "Created brush"); } else { parentGameObject = null; operationGameObject = null; parentTransform = lastUsedModelTransform; parentModel = lastUsedModelTransform.GetComponent <CSGModel>(); } generatedGameObjects = new GameObject[brushObjectCount]; generatedBrushes = new CSGBrush[brushObjectCount]; for (int p = 0; p < brushObjectCount; p++) { string name; if (brushObjectCount == 1) { name = "Brush"; } else { name = "Brush (" + p + ")"; } var gameObject = OperationsUtility.CreateGameObject(parentTransform, name, false); gameObject.SetActive(false); var brushComponent = gameObject.AddComponent <CSGBrush>(); if (operationGameObject == null) { if (CurrentCSGOperationType != invalidCSGOperationType) { brushComponent.OperationType = CurrentCSGOperationType; } operationGameObject = gameObject; var transform = gameObject.transform; SetBrushTransformation(transform); } generatedBrushes[p] = brushComponent; generatedBrushes[p].ControlMesh = new ControlMesh(); generatedBrushes[p].Shape = new Shape(); Undo.RegisterCreatedObjectUndo(gameObject, "Created brush"); generatedGameObjects[p] = gameObject; } //InternalCSGModelManager.Refresh(forceHierarchyUpdate: true); // brushes not registered at this point!?? //DebugEditorWindow.PrintDebugInfo(); //Selection.objects = generatedGameObjects; } else { UpdateBrushPosition(); } return(generatedBrushes != null && generatedBrushes.Length > 0 && generatedBrushes.Length == brushObjectCount); }
protected bool UpdateExtrudedShape(bool registerUndo = true) { if (polygons == null || polygons.Length == 0) { return(false); } bool failures = false; bool modifiedHierarchy = false; if (HaveExtrusion) { UpdateBrushOperation(); if (generatedGameObjects != null && generatedGameObjects.Length > 0) { for (int i = generatedGameObjects.Length - 1; i >= 0; i--) { if (generatedGameObjects[i]) { continue; } ArrayUtility.RemoveAt(ref generatedGameObjects, i); } } if (generatedGameObjects == null || generatedGameObjects.Length == 0) { Cancel(); return(false); } if (generatedGameObjects != null && generatedGameObjects.Length > 0) { if (registerUndo) { Undo.RecordObjects(generatedGameObjects, "Extruded shape"); } int brushIndex = 0; for (int slice = 0; slice < extrusionPoints.Length - 1; slice++) { for (int p = 0; p < polygons.Length; p++) { var brush = generatedBrushes[brushIndex]; brushIndex++; if (!brush || !brush.gameObject) { continue; } var direction = haveForcedDirection ? forcedDirection : buildPlane.normal; var distance = new CSGPlane(direction, extrusionPoints[slice].Position).Distance(extrusionPoints[slice + 1].Position); if (float.IsInfinity(distance) || float.IsNaN(distance)) { distance = 1.0f; } var poly2dToWorldMatrix = brush.transform.worldToLocalMatrix * Matrix4x4.TRS(extrusionPoints[slice].Position, Quaternion.FromToRotation(MathConstants.upVector3, buildPlane.normal), Vector3.one); // * parentModel.transform.localToWorldMatrix; ControlMesh newControlMesh; Shape newShape; if (!CreateControlMeshForBrushIndex(parentModel, brush, polygons[p], poly2dToWorldMatrix, distance, out newControlMesh, out newShape)) { failures = true; if (brush.gameObject.activeSelf) { modifiedHierarchy = true; brush.gameObject.SetActive(false); } continue; } if (!brush.gameObject.activeSelf) { modifiedHierarchy = true; brush.gameObject.SetActive(true); } brush.ControlMesh.SetDirty(); if (registerUndo) { EditorUtility.SetDirty(brush); } } } } } else { if (generatedGameObjects != null) { if (registerUndo) { Undo.RecordObjects(generatedGameObjects, "Extruded brush"); } InternalCSGModelManager.skipCheckForChanges = false; int brushIndex = 0; for (int slice = 0; slice < extrusionPoints.Length - 1; slice++) { for (int p = 0; p < polygons.Length; p++) { if (p >= generatedBrushes.Length) { continue; } var brush = generatedBrushes[brushIndex]; brushIndex++; brush.ControlMesh.SetDirty(); if (registerUndo) { EditorUtility.SetDirty(brush); } } } HideGenerateBrushes(); } } try { InternalCSGModelManager.skipCheckForChanges = true; if (registerUndo) { EditorUtility.SetDirty(this); } //CSGModelManager.External.SetDirty(parentModel.modelNodeID); InternalCSGModelManager.CheckForChanges(forceHierarchyUpdate: modifiedHierarchy); } finally { InternalCSGModelManager.skipCheckForChanges = false; } if (shapeEdges != null && smearTextures) { CSGBrush lastBrush = null; int lastSurfaceIndex = -1; for (int slice = 0; slice < extrusionPoints.Length - 1; slice++) { for (int se = 0; se < shapeEdges.Length; se++) { var brushIndex = shapeEdges[se].PolygonIndex + (slice * shapeEdges.Length); var surfaceIndex = shapeEdges[se].EdgeIndex; if (brushIndex < 0 || brushIndex >= generatedBrushes.Length || surfaceIndex == -1) { continue; } var brush = generatedBrushes[brushIndex]; if (brush && brush.brushNodeID != CSGNode.InvalidNodeID) { if (lastBrush && lastBrush.brushNodeID != CSGNode.InvalidNodeID) { SurfaceUtility.CopyLastMaterial(brush, surfaceIndex, false, lastBrush, lastSurfaceIndex, false, registerUndo = false); } else { brush.Shape.TexGens[surfaceIndex].Translation = Vector3.zero; brush.Shape.TexGens[surfaceIndex].Scale = Vector2.one; brush.Shape.TexGens[surfaceIndex].RotationAngle = 0; } lastBrush = brush; lastSurfaceIndex = surfaceIndex; } } } } InternalCSGModelManager.RefreshMeshes(); return(!failures); }
static void OnBottomBarGUI(SceneView sceneView, Rect barSize) { //if (Event.current.type == EventType.Layout) // return; var snapMode = RealtimeCSG.CSGSettings.SnapMode; var uniformGrid = RealtimeCSG.CSGSettings.UniformGrid; var moveSnapVector = RealtimeCSG.CSGSettings.SnapVector; var rotationSnap = RealtimeCSG.CSGSettings.SnapRotation; var scaleSnap = RealtimeCSG.CSGSettings.SnapScale; var showGrid = RealtimeCSG.CSGSettings.GridVisible; var lockAxisX = RealtimeCSG.CSGSettings.LockAxisX; var lockAxisY = RealtimeCSG.CSGSettings.LockAxisY; var lockAxisZ = RealtimeCSG.CSGSettings.LockAxisZ; var distanceUnit = RealtimeCSG.CSGSettings.DistanceUnit; var helperSurfaces = RealtimeCSG.CSGSettings.VisibleHelperSurfaces; var showWireframe = RealtimeCSG.CSGSettings.IsWireframeShown(sceneView); var skin = CSG_GUIStyleUtility.Skin; var updateSurfaces = false; bool wireframeModified = false; var viewWidth = sceneView.position.width; float layoutHeight = barSize.height; float layoutX = 6.0f; bool modified = false; GUI.changed = false; { currentRect.width = 27; currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; #region "Grid" button if (showGrid) { showGrid = GUI.Toggle(currentRect, showGrid, skin.gridIconOn, EditorStyles.toolbarButton); } else { showGrid = GUI.Toggle(currentRect, showGrid, skin.gridIcon, EditorStyles.toolbarButton); } //(x:6.00, y:0.00, width:27.00, height:18.00) TooltipUtility.SetToolTip(showGridTooltip, currentRect); #endregion if (viewWidth >= 800) { layoutX += 6; //(x:33.00, y:0.00, width:6.00, height:6.00) } var prevBackgroundColor = GUI.backgroundColor; var lockedBackgroundColor = skin.lockedBackgroundColor; if (lockAxisX) { GUI.backgroundColor = lockedBackgroundColor; } #region "X" lock button currentRect.width = 17; currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; lockAxisX = !GUI.Toggle(currentRect, !lockAxisX, xLabel, skin.xToolbarButton); //(x:39.00, y:0.00, width:17.00, height:18.00) if (lockAxisX) { TooltipUtility.SetToolTip(xTooltipOn, currentRect); } else { TooltipUtility.SetToolTip(xTooltipOff, currentRect); } GUI.backgroundColor = prevBackgroundColor; #endregion #region "Y" lock button currentRect.x = layoutX; layoutX += currentRect.width; if (lockAxisY) { GUI.backgroundColor = lockedBackgroundColor; } lockAxisY = !GUI.Toggle(currentRect, !lockAxisY, yLabel, skin.yToolbarButton); //(x:56.00, y:0.00, width:17.00, height:18.00) if (lockAxisY) { TooltipUtility.SetToolTip(yTooltipOn, currentRect); } else { TooltipUtility.SetToolTip(yTooltipOff, currentRect); } GUI.backgroundColor = prevBackgroundColor; #endregion #region "Z" lock button currentRect.x = layoutX; layoutX += currentRect.width; if (lockAxisZ) { GUI.backgroundColor = lockedBackgroundColor; } lockAxisZ = !GUI.Toggle(currentRect, !lockAxisZ, zLabel, skin.zToolbarButton); //(x:56.00, y:0.00, width:17.00, height:18.00) if (lockAxisZ) { TooltipUtility.SetToolTip(zTooltipOn, currentRect); } else { TooltipUtility.SetToolTip(zTooltipOff, currentRect); } GUI.backgroundColor = prevBackgroundColor; #endregion } modified = GUI.changed || modified; if (viewWidth >= 800) { layoutX += 6; // (x:91.00, y:0.00, width:6.00, height:6.00) } #region "SnapMode" button GUI.changed = false; { currentRect.width = 27; currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; switch (snapMode) { case SnapMode.GridSnapping: { var newValue = GUI.Toggle(currentRect, snapMode == SnapMode.GridSnapping, CSG_GUIStyleUtility.Skin.gridSnapIconOn, EditorStyles.toolbarButton); if (GUI.changed) { snapMode = newValue ? SnapMode.GridSnapping : SnapMode.RelativeSnapping; } //(x:97.00, y:0.00, width:27.00, height:18.00) TooltipUtility.SetToolTip(gridSnapModeTooltip, currentRect); break; } case SnapMode.RelativeSnapping: { var newValue = GUI.Toggle(currentRect, snapMode == SnapMode.RelativeSnapping, CSG_GUIStyleUtility.Skin.relSnapIconOn, EditorStyles.toolbarButton); if (GUI.changed) { snapMode = newValue ? SnapMode.RelativeSnapping : SnapMode.None; } //(x:97.00, y:0.00, width:27.00, height:18.00) TooltipUtility.SetToolTip(relativeSnapModeTooltip, currentRect); break; } default: case SnapMode.None: { var newValue = GUI.Toggle(currentRect, snapMode != SnapMode.None, CSG_GUIStyleUtility.Skin.noSnapIconOn, EditorStyles.toolbarButton); if (GUI.changed) { snapMode = newValue ? SnapMode.GridSnapping : SnapMode.None; } //(x:97.00, y:0.00, width:27.00, height:18.00) TooltipUtility.SetToolTip(noSnappingModeTooltip, currentRect); break; } } } modified = GUI.changed || modified; #endregion if (viewWidth >= 460) { if (snapMode != SnapMode.None) { #region "Position" label if (viewWidth >= 500) { if (viewWidth >= 865) { currentRect.width = 44; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; uniformGrid = GUI.Toggle(currentRect, uniformGrid, positionLargeLabel, miniTextStyle); //(x:128.00, y:2.00, width:44.00, height:16.00) TooltipUtility.SetToolTip(positionTooltip, currentRect); } else { currentRect.width = 22; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; uniformGrid = GUI.Toggle(currentRect, uniformGrid, positionSmallLabel, miniTextStyle); //(x:127.00, y:2.00, width:22.00, height:16.00) TooltipUtility.SetToolTip(positionTooltip, currentRect); } } #endregion layoutX += 2; #region "Position" field if (uniformGrid || viewWidth < 515) { EditorGUI.showMixedValue = !(moveSnapVector.x == moveSnapVector.y && moveSnapVector.x == moveSnapVector.z); GUI.changed = false; { currentRect.width = 70; currentRect.y = 3; currentRect.height = layoutHeight - (currentRect.y - 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; moveSnapVector.x = Units.DistanceUnitToUnity(distanceUnit, EditorGUI.DoubleField(currentRect, Units.UnityToDistanceUnit(distanceUnit, moveSnapVector.x), textInputStyle)); //, MinSnapWidth, MaxSnapWidth)); //(x:176.00, y:3.00, width:70.00, height:16.00) } if (GUI.changed) { modified = true; moveSnapVector.y = moveSnapVector.x; moveSnapVector.z = moveSnapVector.x; } EditorGUI.showMixedValue = false; } else { GUI.changed = false; { currentRect.width = 70; currentRect.y = 3; currentRect.height = layoutHeight - (currentRect.y - 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; layoutX++; moveSnapVector.x = Units.DistanceUnitToUnity(distanceUnit, EditorGUI.DoubleField(currentRect, Units.UnityToDistanceUnit(distanceUnit, moveSnapVector.x), textInputStyle)); //, MinSnapWidth, MaxSnapWidth)); //(x:175.00, y:3.00, width:70.00, height:16.00) currentRect.x = layoutX; layoutX += currentRect.width; layoutX++; moveSnapVector.y = Units.DistanceUnitToUnity(distanceUnit, EditorGUI.DoubleField(currentRect, Units.UnityToDistanceUnit(distanceUnit, moveSnapVector.y), textInputStyle)); //, MinSnapWidth, MaxSnapWidth)); //(x:247.00, y:3.00, width:70.00, height:16.00) currentRect.x = layoutX; layoutX += currentRect.width; moveSnapVector.z = Units.DistanceUnitToUnity(distanceUnit, EditorGUI.DoubleField(currentRect, Units.UnityToDistanceUnit(distanceUnit, moveSnapVector.z), textInputStyle)); //, MinSnapWidth, MaxSnapWidth)); //(x:319.00, y:3.00, width:70.00, height:16.00) } modified = GUI.changed || modified; } #endregion layoutX++; #region "Position" Unit DistanceUnit nextUnit = Units.CycleToNextUnit(distanceUnit); GUIContent unitText = Units.GetUnitGUIContent(distanceUnit); currentRect.width = 22; currentRect.y = 2; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, unitText, miniTextStyle)) //(x:393.00, y:2.00, width:13.00, height:16.00) { distanceUnit = nextUnit; modified = true; } #endregion layoutX += 2; #region "Position" +/- if (viewWidth >= 700) { currentRect.width = 19; currentRect.y = 2; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, positionPlusLabel, EditorStyles.miniButtonLeft)) { GridUtility.DoubleGridSize(); moveSnapVector = RealtimeCSG.CSGSettings.SnapVector; } //(x:410.00, y:2.00, width:19.00, height:15.00) TooltipUtility.SetToolTip(positionPlusTooltip, currentRect); currentRect.width = 17; currentRect.y = 2; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, positionMinusLabel, EditorStyles.miniButtonRight)) { GridUtility.HalfGridSize(); moveSnapVector = RealtimeCSG.CSGSettings.SnapVector; } //(x:429.00, y:2.00, width:17.00, height:15.00) TooltipUtility.SetToolTip(positionMinnusTooltip, currentRect); } #endregion layoutX += 2; #region "Angle" label if (viewWidth >= 750) { if (viewWidth >= 865) { currentRect.width = 31; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, angleLargeLabel, miniTextStyle); //(x:450.00, y:2.00, width:31.00, height:16.00) } else { currentRect.width = 22; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, angleSmallLabel, miniTextStyle); //(x:355.00, y:2.00, width:22.00, height:16.00) } TooltipUtility.SetToolTip(angleTooltip, currentRect); } #endregion layoutX += 2; #region "Angle" field GUI.changed = false; { currentRect.width = 70; currentRect.y = 3; currentRect.height = layoutHeight - (currentRect.y - 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; rotationSnap = EditorGUI.FloatField(currentRect, rotationSnap, textInputStyle); //, MinSnapWidth, MaxSnapWidth); //(x:486.00, y:3.00, width:70.00, height:16.00) if (viewWidth <= 750) { TooltipUtility.SetToolTip(angleTooltip, currentRect); } } modified = GUI.changed || modified; #endregion layoutX++; #region "Angle" Unit if (viewWidth >= 370) { currentRect.width = 14; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, angleUnitLabel, miniTextStyle); } #endregion layoutX += 2; #region "Angle" +/- if (viewWidth >= 700) { currentRect.width = 19; currentRect.y = 1; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, anglePlusLabel, EditorStyles.miniButtonLeft)) { rotationSnap *= 2.0f; modified = true; } //(x:573.00, y:2.00, width:19.00, height:15.00) TooltipUtility.SetToolTip(anglePlusTooltip, currentRect); currentRect.width = 17; currentRect.y = 1; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, angleMinusLabel, EditorStyles.miniButtonRight)) { rotationSnap /= 2.0f; modified = true; } //(x:592.00, y:2.00, width:17.00, height:15.00) TooltipUtility.SetToolTip(angleMinnusTooltip, currentRect); } #endregion layoutX += 2; #region "Scale" label if (viewWidth >= 750) { if (viewWidth >= 865) { currentRect.width = 31; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, scaleLargeLabel, miniTextStyle); //(x:613.00, y:2.00, width:31.00, height:16.00) } else { currentRect.width = 19; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, scaleSmallLabel, miniTextStyle); //(x:495.00, y:2.00, width:19.00, height:16.00) } TooltipUtility.SetToolTip(scaleTooltip, currentRect); } #endregion layoutX += 2; #region "Scale" field GUI.changed = false; { currentRect.width = 70; currentRect.y = 3; currentRect.height = layoutHeight - (currentRect.y - 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; scaleSnap = EditorGUI.FloatField(currentRect, scaleSnap, textInputStyle); //, MinSnapWidth, MaxSnapWidth); //(x:648.00, y:3.00, width:70.00, height:16.00) if (viewWidth <= 750) { TooltipUtility.SetToolTip(scaleTooltip, currentRect); } } modified = GUI.changed || modified; #endregion layoutX++; #region "Scale" Unit if (viewWidth >= 370) { currentRect.width = 15; currentRect.y = 1; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; GUI.Label(currentRect, scaleUnitLabel, miniTextStyle); //(x:722.00, y:2.00, width:15.00, height:16.00) } #endregion layoutX += 2; #region "Scale" +/- if (viewWidth >= 700) { currentRect.width = 19; currentRect.y = 2; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, scalePlusLabel, EditorStyles.miniButtonLeft)) { scaleSnap *= 10.0f; modified = true; } //(x:741.00, y:2.00, width:19.00, height:15.00) TooltipUtility.SetToolTip(scalePlusTooltip, currentRect); currentRect.width = 17; currentRect.y = 2; currentRect.height = layoutHeight - (currentRect.y + 1); currentRect.y += barSize.y; currentRect.x = layoutX; layoutX += currentRect.width; if (GUI.Button(currentRect, scaleMinusLabel, EditorStyles.miniButtonRight)) { scaleSnap /= 10.0f; modified = true; } //(x:760.00, y:2.00, width:17.00, height:15.00) TooltipUtility.SetToolTip(scaleMinnusTooltip, currentRect); } #endregion } } var prevLayoutX = layoutX; layoutX = viewWidth; #region "Rebuild" currentRect.width = 27; currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; layoutX -= currentRect.width; currentRect.x = layoutX; if (GUI.Button(currentRect, CSG_GUIStyleUtility.Skin.rebuildIcon, EditorStyles.toolbarButton)) { Debug.Log("Starting complete rebuild"); var text = new System.Text.StringBuilder(); MaterialUtility.ResetMaterialTypeLookup(); InternalCSGModelManager.skipCheckForChanges = true; RealtimeCSG.CSGSettings.Reload(); UnityCompilerDefineManager.UpdateUnityDefines(); InternalCSGModelManager.registerTime = 0.0; InternalCSGModelManager.validateTime = 0.0; InternalCSGModelManager.hierarchyValidateTime = 0.0; InternalCSGModelManager.updateHierarchyTime = 0.0; var startTime = EditorApplication.timeSinceStartup; InternalCSGModelManager.ForceRebuildAll(); InternalCSGModelManager.OnHierarchyModified(); var hierarchy_update_endTime = EditorApplication.timeSinceStartup; text.AppendFormat(CultureInfo.InvariantCulture, "Full hierarchy rebuild in {0:F} ms. ", (hierarchy_update_endTime - startTime) * 1000); NativeMethodBindings.RebuildAll(); var csg_endTime = EditorApplication.timeSinceStartup; text.AppendFormat(CultureInfo.InvariantCulture, "Full CSG rebuild done in {0:F} ms. ", (csg_endTime - hierarchy_update_endTime) * 1000); InternalCSGModelManager.RemoveForcedUpdates(); // we already did this in rebuild all InternalCSGModelManager.UpdateMeshes(text, forceUpdate: true); updateSurfaces = true; UpdateLoop.ResetUpdateRoutine(); RealtimeCSG.CSGSettings.Save(); InternalCSGModelManager.skipCheckForChanges = false; var scenes = new HashSet <UnityEngine.SceneManagement.Scene>(); foreach (var model in InternalCSGModelManager.Models) { scenes.Add(model.gameObject.scene); } text.AppendFormat(CultureInfo.InvariantCulture, "{0} brushes. ", Foundation.CSGManager.TreeBrushCount); Debug.Log(text.ToString()); } //(x:1442.00, y:0.00, width:27.00, height:18.00) TooltipUtility.SetToolTip(rebuildTooltip, currentRect); #endregion if (viewWidth >= 800) { layoutX -= 6; //(x:1436.00, y:0.00, width:6.00, height:6.00) } #region "Helper Surface Flags" Mask if (viewWidth >= 250) { GUI.changed = false; { prevLayoutX += 8; // extra space prevLayoutX += 26; // width of "Show wireframe" button currentRect.width = Mathf.Max(20, Mathf.Min(165, (viewWidth - prevLayoutX - currentRect.width))); currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; layoutX -= currentRect.width; currentRect.x = layoutX; SurfaceVisibilityPopup.Button(sceneView, currentRect); //(x:1267.00, y:2.00, width:165.00, height:16.00) TooltipUtility.SetToolTip(helperSurfacesTooltip, currentRect); } if (GUI.changed) { updateSurfaces = true; modified = true; } } #endregion #region "Show wireframe" button GUI.changed = false; currentRect.width = 26; currentRect.y = 0; currentRect.height = layoutHeight - currentRect.y; currentRect.y += barSize.y; layoutX -= currentRect.width; currentRect.x = layoutX; if (showWireframe) { showWireframe = GUI.Toggle(currentRect, showWireframe, CSG_GUIStyleUtility.Skin.wireframe, EditorStyles.toolbarButton); //(x:1237.00, y:0.00, width:26.00, height:18.00) } else { showWireframe = GUI.Toggle(currentRect, showWireframe, CSG_GUIStyleUtility.Skin.wireframeOn, EditorStyles.toolbarButton); //(x:1237.00, y:0.00, width:26.00, height:18.00) } TooltipUtility.SetToolTip(showWireframeTooltip, currentRect); if (GUI.changed) { wireframeModified = true; modified = true; } #endregion #region Capture mouse clicks in empty space var mousePoint = Event.current.mousePosition; int controlID = GUIUtility.GetControlID(BottomBarEditorOverlayHash, FocusType.Passive, barSize); switch (Event.current.GetTypeForControl(controlID)) { case EventType.MouseDown: { if (barSize.Contains(mousePoint)) { GUIUtility.hotControl = controlID; GUIUtility.keyboardControl = controlID; Event.current.Use(); } break; } case EventType.MouseMove: { if (barSize.Contains(mousePoint)) { Event.current.Use(); } break; } case EventType.MouseUp: { if (GUIUtility.hotControl == controlID) { GUIUtility.hotControl = 0; GUIUtility.keyboardControl = 0; Event.current.Use(); } break; } case EventType.MouseDrag: { if (GUIUtility.hotControl == controlID) { Event.current.Use(); } break; } case EventType.ScrollWheel: { if (barSize.Contains(mousePoint)) { Event.current.Use(); } break; } } #endregion #region Store modified values rotationSnap = Mathf.Max(1.0f, Mathf.Abs((360 + (rotationSnap % 360))) % 360); moveSnapVector.x = Mathf.Max(1.0f / 1024.0f, moveSnapVector.x); moveSnapVector.y = Mathf.Max(1.0f / 1024.0f, moveSnapVector.y); moveSnapVector.z = Mathf.Max(1.0f / 1024.0f, moveSnapVector.z); scaleSnap = Mathf.Max(MathConstants.MinimumScale, scaleSnap); RealtimeCSG.CSGSettings.SnapMode = snapMode; RealtimeCSG.CSGSettings.SnapVector = moveSnapVector; RealtimeCSG.CSGSettings.SnapRotation = rotationSnap; RealtimeCSG.CSGSettings.SnapScale = scaleSnap; RealtimeCSG.CSGSettings.UniformGrid = uniformGrid; // RealtimeCSG.Settings.SnapVertex = vertexSnap; RealtimeCSG.CSGSettings.GridVisible = showGrid; RealtimeCSG.CSGSettings.LockAxisX = lockAxisX; RealtimeCSG.CSGSettings.LockAxisY = lockAxisY; RealtimeCSG.CSGSettings.LockAxisZ = lockAxisZ; RealtimeCSG.CSGSettings.DistanceUnit = distanceUnit; RealtimeCSG.CSGSettings.VisibleHelperSurfaces = helperSurfaces; if (wireframeModified) { RealtimeCSG.CSGSettings.SetWireframeShown(sceneView, showWireframe); } if (updateSurfaces) { MeshInstanceManager.UpdateHelperSurfaceVisibility(force: true); } if (modified) { GUI.changed = true; RealtimeCSG.CSGSettings.UpdateSnapSettings(); RealtimeCSG.CSGSettings.Save(); CSG_EditorGUIUtility.RepaintAll(); } #endregion }
// returns true when modified internal static bool UpdateNodePosition(HierarchyItem node, ParentNodeData top) { // on each level, compare sibling position to nodes before and after it. // if it's different, remove self and find new position in array. // continue to next parent. var iteratorParent = node.Parent; if (iteratorParent == null) { AddNode(node, top); top.ChildrenModified = true; return(true); } var currentLoopCount = CurrentLoopCount; var iterator = node; while (iteratorParent != null) { var iteratorTransformID = iterator.TransformID; if (iteratorTransformID == 0) { Debug.Log("iterator_transform == null"); } else if (iterator.LastLoopCount != currentLoopCount) { var iteratorTransform = iterator.Transform; var iteratorParentTransformID = iteratorTransform.parent == null ? 0 : iteratorTransform.parent.GetInstanceID(); // Compare the unity parent transform to the stored parent transform if (iteratorParent.TransformID != iteratorParentTransformID) { var defaultCSGInstanceID = 0; var defaultCSGModel = InternalCSGModelManager.GetDefaultCSGModelForObject(iteratorTransform); if (defaultCSGModel != null && defaultCSGModel.transform != null) { defaultCSGInstanceID = defaultCSGModel.transform.GetInstanceID(); } if (defaultCSGInstanceID == 0 || defaultCSGInstanceID != iteratorParent.TransformID) { RemoveNode(node, top); AddNode(node, top); top.ChildrenModified = true; return(true); } } if (iterator.LastLoopCount != currentLoopCount) { iterator.CachedTransformSiblingIndex = iteratorTransform.GetSiblingIndex(); iterator.LastLoopCount = currentLoopCount; } // Does the child even exist in the parent transform? int iteratorChildIndex; if (!iteratorParent.FindSiblingIndex(iteratorTransform, iterator.CachedTransformSiblingIndex, iteratorTransformID, out iteratorChildIndex)) { RemoveNode(node, top); AddNode(node, top); top.ChildrenModified = true; return(true); } // See if the position of the child has changed .. if (iteratorChildIndex != iterator.SiblingIndex) { iterator.SiblingIndex = iteratorChildIndex; RemoveNode(node, top); AddNode(node, top); top.ChildrenModified = true; return(true); } // Compare the child index to the one before and after it .. var iteratorParentChildNodes = iteratorParent.ChildNodes; var iteratorSiblingIndex = iteratorTransform.GetSiblingIndex(); if (iteratorChildIndex > 0) { var prevTransform = iteratorParentChildNodes[iteratorChildIndex - 1].Transform; if (!prevTransform) { return(false); } var iteratorPrevSiblingIndex = prevTransform.GetSiblingIndex(); if (iteratorPrevSiblingIndex >= iteratorSiblingIndex) { RemoveNode(node, top); AddNode(node, top); top.ChildrenModified = true; return(true); } } else if (iteratorChildIndex < iteratorParentChildNodes.Length - 1) { var nextTransform = iteratorParentChildNodes[iteratorChildIndex + 1].Transform; if (!nextTransform) { return(false); } var iteratorNextSiblingIndex = nextTransform.GetSiblingIndex(); if (iteratorNextSiblingIndex <= iteratorSiblingIndex) { RemoveNode(node, top); AddNode(node, top); top.ChildrenModified = true; return(true); } } } iterator = iteratorParent; iteratorParent = iterator.Parent; } return(false); }
public override void OnInspectorGUI() { GUILayout.BeginVertical(GUI.skin.box); { GUILayout.Label("A hidden CSG model, and all it's brushes and operations, is contained by this object. This will automatically be removed at build time.", GUIStyleUtility.wrapLabel); GUILayout.Space(10); if (GUILayout.Button("Revert back to CSG model")) { Undo.IncrementCurrentGroup(); var groupIndex = Undo.GetCurrentGroup(); Undo.SetCurrentGroupName("Reverted to former CSG model"); try { var selection = new List <UnityEngine.Object>(); var updateScenes = new HashSet <Scene>(); foreach (var target in targets) { var exportedModel = target as CSGModelExported; if (!exportedModel) { continue; } exportedModel.disarm = true; exportedModel.hideFlags = HideFlags.DontSaveInBuild; updateScenes.Add(exportedModel.gameObject.scene); if (exportedModel.containedModel) { Undo.RecordObject(exportedModel.containedModel, "Revert model"); selection.Add(exportedModel.containedModel.gameObject); exportedModel.containedModel.transform.SetParent(exportedModel.transform.parent, true); exportedModel.containedModel.transform.SetSiblingIndex(exportedModel.transform.GetSiblingIndex()); exportedModel.containedModel.gameObject.SetActive(true); exportedModel.containedModel.gameObject.hideFlags = HideFlags.None; EditorUtility.SetDirty(exportedModel.containedModel); Undo.DestroyObjectImmediate(exportedModel); } else { MeshInstanceManager.ReverseExport(exportedModel); selection.Add(exportedModel.gameObject); EditorUtility.SetDirty(exportedModel); Undo.DestroyObjectImmediate(exportedModel); } } Selection.objects = selection.ToArray(); InternalCSGModelManager.skipRefresh = true; BrushOutlineManager.ClearOutlines(); //CSGModelManager.Refresh(forceHierarchyUpdate: true); InternalCSGModelManager.Rebuild(); foreach (var scene in updateScenes) { UnityEditor.SceneManagement.EditorSceneManager.MarkSceneDirty(scene); } } finally { InternalCSGModelManager.skipRefresh = false; Undo.CollapseUndoOperations(groupIndex); } } } GUILayout.Space(30); if (GUILayout.Button("Remove hidden CSG model")) { Undo.IncrementCurrentGroup(); var groupIndex = Undo.GetCurrentGroup(); Undo.SetCurrentGroupName("Removed hidden CSG model"); Undo.RecordObject(this, "Removed hidden CSG model"); foreach (var target in targets) { var exportedModel = target as CSGModelExported; if (!exportedModel) { continue; } exportedModel.DestroyModel(undoable: true); Undo.DestroyObjectImmediate(exportedModel); } Undo.CollapseUndoOperations(groupIndex); } GUILayout.Space(10); GUILayout.EndVertical(); }
protected override void HandleEditShapeEvents(Rect sceneRect) { if (settings.vertices.Length < 2) { if (editMode == EditMode.ExtrudeShape || editMode == EditMode.EditShape) { editMode = EditMode.CreatePlane; } } if (!SceneDragToolManager.IsDraggingObjectInScene && Event.current.type == EventType.Repaint) { if (visualSnappedEdges != null) { PaintUtility.DrawLines(visualSnappedEdges.ToArray(), ToolConstants.oldThickLineScale, ColorSettings.SnappedEdges); } if (visualSnappedGrid != null) { var _origMatrix = Handles.matrix; Handles.matrix = MathConstants.identityMatrix; PaintUtility.DrawDottedLines(visualSnappedGrid.ToArray(), ColorSettings.SnappedEdges); Handles.matrix = _origMatrix; } if (visualSnappedBrush != null) { var brush_cache = InternalCSGModelManager.GetBrushCache(visualSnappedBrush); if (brush_cache != null && brush_cache.compareTransformation != null && brush_cache.childData != null && brush_cache.childData.ModelTransform != null && brush_cache.childData.ModelTransform) { var brush_translation = brush_cache.compareTransformation.modelLocalPosition + brush_cache.childData.ModelTransform.position; CSGRenderer.DrawOutlines(visualSnappedBrush.brushID, brush_translation, ColorSettings.SelectedOutlines, ColorSettings.SelectedOutlines, ColorSettings.SelectedOutlines, ColorSettings.SelectedOutlines); } } var origMatrix = Handles.matrix; Handles.matrix = MathConstants.identityMatrix; PaintBounds(); Handles.matrix = origMatrix; } HandleHeightHandles(sceneRect, false); for (int i = 0; i < settings.vertices.Length; i++) { var id = settings.vertexIDs[i]; var point_type = Event.current.GetTypeForControl(id); switch (point_type) { case EventType.Repaint: { if (SceneDragToolManager.IsDraggingObjectInScene) { break; } bool isSelected = id == GUIUtility.keyboardControl; var temp = Handles.color; var origMatrix = Handles.matrix; Handles.matrix = MathConstants.identityMatrix; var rotation = Camera.current.transform.rotation; if (isSelected) { Handles.color = ColorSettings.PointInnerStateColor[3]; } else if (HandleUtility.nearestControl == id) { Handles.color = ColorSettings.PointInnerStateColor[1]; } else { Handles.color = ColorSettings.PointInnerStateColor[0]; } float handleSize = CSG_HandleUtility.GetHandleSize(settings.vertices[i]); float scaledHandleSize = handleSize * ToolConstants.handleScale; PaintUtility.SquareDotCap(id, settings.vertices[i], rotation, scaledHandleSize); Handles.matrix = origMatrix; Handles.color = temp; break; } case EventType.Layout: { if ((Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan)) { break; } var origMatrix = Handles.matrix; Handles.matrix = MathConstants.identityMatrix; float handleSize = CSG_HandleUtility.GetHandleSize(settings.vertices[i]); float scaledHandleSize = handleSize * ToolConstants.handleScale; HandleUtility.AddControl(id, HandleUtility.DistanceToCircle(settings.vertices[i], scaledHandleSize)); Handles.matrix = origMatrix; break; } case EventType.ValidateCommand: case EventType.KeyDown: { if (GUIUtility.hotControl == id) { if (Keys.CancelActionKey.IsKeyPressed()) { Event.current.Use(); break; } } break; } case EventType.KeyUp: { if (GUIUtility.hotControl == id) { if (Keys.CancelActionKey.IsKeyPressed()) { GUIUtility.hotControl = 0; GUIUtility.keyboardControl = 0; EditorGUIUtility.editingTextField = false; Event.current.Use(); break; } } break; } case EventType.MouseDown: { if (!sceneRect.Contains(Event.current.mousePosition)) { break; } if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { break; } if (GUIUtility.hotControl == 0 && HandleUtility.nearestControl == id && Event.current.button == 0) { GUIUtility.hotControl = id; GUIUtility.keyboardControl = id; EditorGUIUtility.editingTextField = false; EditorGUIUtility.SetWantsMouseJumping(1); Event.current.Use(); break; } break; } case EventType.MouseDrag: { if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { break; } if (GUIUtility.hotControl == id && Event.current.button == 0) { Undo.RecordObject(this, "Modify shape"); var mouseRay = HandleUtility.GUIPointToWorldRay(Event.current.mousePosition); RealtimeCSG.CSGGrid.SetForcedGrid(buildPlane); var alignedPlane = new CSGPlane(RealtimeCSG.CSGGrid.CurrentWorkGridPlane.normal, settings.vertices[0]); var worldPosition = buildPlane.Project(alignedPlane.Intersection(mouseRay)); if (float.IsInfinity(worldPosition.x) || float.IsNaN(worldPosition.x) || float.IsInfinity(worldPosition.y) || float.IsNaN(worldPosition.y) || float.IsInfinity(worldPosition.z) || float.IsNaN(worldPosition.z)) { worldPosition = settings.vertices[i]; } ResetVisuals(); if (snapFunction != null) { CSGBrush snappedOnBrush; worldPosition = snapFunction(worldPosition, buildPlane, ref base.visualSnappedEdges, out snappedOnBrush, generatedBrushes); } base.visualSnappedGrid = RealtimeCSG.CSGGrid.FindAllGridEdgesThatTouchPoint(worldPosition); settings.vertices[i] = worldPosition; CenterExtrusionPoints(buildPlane); UpdateBaseShape(); if (editMode == EditMode.ExtrudeShape) { StartExtrudeMode(); UpdateBaseShape(); } UpdateExtrudedShape(); GUI.changed = true; Event.current.Use(); break; } break; } case EventType.MouseUp: { if (GUIUtility.hotControl != id) { break; } if (Tools.viewTool != ViewTool.None && Tools.viewTool != ViewTool.Pan) { break; } if (Event.current.button == 0) { GUIUtility.hotControl = 0; GUIUtility.keyboardControl = 0; EditorGUIUtility.editingTextField = false; EditorGUIUtility.SetWantsMouseJumping(0); Event.current.Use(); ResetVisuals(); //if (Length == 0 || Width == 0) //{ // Cancel(); //} break; } break; } } } }
static void UpdateChildrenModel(CSGModel model, Transform container) { if (External == null) { return; } if (model == null) { return; } for (int i = 0; i < container.childCount; i++) { var child = container.GetChild(i); var nodeObj = child.GetComponent(TypeConstants.CSGNodeType); if (nodeObj) { var op = nodeObj as CSGOperation; if (op && !op.PassThrough) { // make sure the node has already been initialized, otherwise // assume it'll still get initialized at some point, in which // case we shouldn't update it's hierarchy here if (!op.IsRegistered) { continue; } if (op.ChildData.Model != model) { if (model) // assume we're still initializing { SetCSGOperationHierarchy(op, op.ChildData.Parent, model); } } else { // assume that if this operation already has the // correct model, then it's children will have the same model break; } } var brush = nodeObj as CSGBrush; if (brush) { // make sure the node has already been initialized, otherwise // assume it'll still get initialized at some point, in which // case we shouldn't update it's hierarchy here if (!brush.IsRegistered) { continue; } if (brush.ChildData.Model != model) { if (model) // assume we're still initializing { SetCSGBrushHierarchy(brush, brush.ChildData.Parent, model); InternalCSGModelManager.CheckSurfaceModifications(brush); } } else { // assume that if this brush already has the // correct model, then it's children will have the same model break; } } } UpdateChildrenModel(model, child); } }
public bool DragUpdated(Transform transformInInspector, Rect selectionRect) { var highlight_brushes = transformInInspector.GetComponentsInChildren <CSGBrush>(); bool prevSelectAllSurfaces = selectAllSurfaces; selectAllSurfaces = true; bool modified = true; if (hoverBrushSurfaces != null) { if (hoverBrushSurfaces.Length != highlight_brushes.Length) { modified = false; } else { modified = false; for (int i = 0; i < highlight_brushes.Length; i++) { var find_brush = highlight_brushes[i]; bool found = false; for (int j = 0; j < hoverBrushSurfaces.Length; j++) { if (hoverBrushSurfaces[j].surfaceIndex == -1 && hoverBrushSurfaces[j].brush == find_brush) { found = true; break; } } if (!found) { modified = true; break; } } } } bool needUpdate = false; if (modified) { hoverOnSelectedSurfaces = false; if (hoverBrushSurfaces != null) { needUpdate = true; RestoreMaterials(hoverBrushSurfaces); } hoverBrushSurfaces = HoverOnBrush(highlight_brushes, -1); if (hoverBrushSurfaces != null) { hoverBrushSurfaces = GetCombinedBrushes(hoverBrushSurfaces); needUpdate = true; using (new UndoGroup(hoverBrushSurfaces, "Modified materials")) { RememberMaterials(hoverBrushSurfaces); ApplyMaterial(hoverBrushSurfaces); } } } else { if (prevSelectAllSurfaces != selectAllSurfaces) { if (hoverBrushSurfaces != null) { needUpdate = true; using (new UndoGroup(hoverBrushSurfaces, "Modified materials")) { ApplyMaterial(hoverBrushSurfaces); } } } } if (needUpdate) { InternalCSGModelManager.UpdateMeshes(); MeshInstanceManager.UpdateHelperSurfaceVisibility(); } return(needUpdate); }
internal override bool UpdateBaseShape(bool registerUndo = true) { if (editMode == EditMode.CreatePlane) { return(false); } var length = StairsDepth; if (length <= 0) { InternalCSGModelManager.skipRefresh = false; HideGenerateBrushes(); return(false); } var worldToLocalRotation = GetWorldToLocalRotation(); var localToWorldRotation = Quaternion.Inverse(worldToLocalRotation); brushPosition = localToWorldRotation * settings.bounds.Min; var totalSteps = TotalSteps; if (!GenerateBrushObjects(totalSteps)) { InternalCSGModelManager.skipRefresh = false; HideGenerateBrushes(); return(false); } if (registerUndo) { Undo.RecordObjects(generatedBrushes, "Created Linear Stairs"); } if (!GenerateStairs(generatedBrushes, totalSteps, StepDepth, StepHeight, StepDepth, StairsDepth, StairsWidth, StairsHeight, ExtraDepth, ExtraHeight, StairsBottom)) { InternalCSGModelManager.skipRefresh = false; HideGenerateBrushes(); return(false); } if (registerUndo) { MarkAllBrushesDirty(); } try { InternalCSGModelManager.skipRefresh = true; if (registerUndo) { EditorUtility.SetDirty(this); } InternalCSGModelManager.External.ForceModelUpdate(parentModel.modelID); InternalCSGModelManager.Refresh(forceHierarchyUpdate: true); //DebugEditorWindow.PrintDebugInfo(); } finally { InternalCSGModelManager.skipRefresh = false; } return(true); }
internal override bool UpdateBaseShape(bool registerUndo = true) { if (settings.vertices == null || settings.vertices.Length == 0) editMode = EditMode.CreatePlane; if (editMode == EditMode.CreatePlane) return false; float radius = SphereRadius; if (editMode == EditMode.CreateShape) { brushPosition = settings.vertices[0]; //extrusionPoints[0].Vertex = settings.vertices[0]; radius = (settings.vertices[0] - worldPosition).magnitude; } GenerateBrushObjects(1); if (radius == 0 || generatedBrushes == null || generatedBrushes.Length < 1) { InternalCSGModelManager.skipCheckForChanges = false; HideGenerateBrushes(); return false; } //UpdateBrushOperation(height); bool failures = false; bool modifiedHierarchy = false; if (generatedGameObjects != null && generatedGameObjects.Length > 0) { for (int i = generatedGameObjects.Length - 1; i >= 0; i--) { if (generatedGameObjects[i]) continue; ArrayUtility.RemoveAt(ref generatedGameObjects, i); } } if (generatedGameObjects == null || generatedGameObjects.Length == 0) { Cancel(); return false; } if (generatedGameObjects != null && generatedGameObjects.Length > 0) { if (registerUndo) Undo.RecordObjects(generatedGameObjects, "Created Sphere"); var brush = generatedBrushes[0]; if (brush && brush.gameObject) { ControlMesh newControlMesh; Shape newShape; if (GenerateSphere(radius, settings.sphereSplits, parentModel, brush, out newControlMesh, out newShape)) { if (!brush.gameObject.activeSelf) { modifiedHierarchy = true; brush.gameObject.SetActive(true); } brush.Shape = newShape; brush.ControlMesh = newControlMesh; if (registerUndo) EditorUtility.SetDirty(brush); ControlMeshUtility.UpdateBrushMesh(brush, brush.ControlMesh, brush.Shape); } else { failures = true; if (brush.gameObject.activeSelf) { modifiedHierarchy = true; brush.gameObject.SetActive(false); } } } } try { InternalCSGModelManager.skipCheckForChanges = true; if (registerUndo) EditorUtility.SetDirty(this); //CSGModelManager.External.SetDirty(parentModel.modelNodeID); InternalCSGModelManager.CheckForChanges(forceHierarchyUpdate: modifiedHierarchy); } finally { InternalCSGModelManager.skipCheckForChanges = false; } return !failures; }
static public void OnInspectorGUI(Editor editor, UnityEngine.Object[] targets) { TooltipUtility.InitToolTip(editor); try { var models = new CSGModel[targets.Length]; for (int i = targets.Length - 1; i >= 0; i--) { models[i] = targets[i] as CSGModel; if (!models[i]) { ArrayUtility.RemoveAt(ref models, i); } } CSG_GUIStyleUtility.InitStyles(); ShowRealtimeCSGDisabledMessage(); if (models.Length > 0 && models.Length == targets.Length) { CSGModelComponentInspectorGUI.OnInspectorGUI(targets); return; } var filteredSelection = EditModeManager.FilteredSelection; var targetNodes = filteredSelection.NodeTargets; var targetModels = filteredSelection.ModelTargets; var targetBrushes = filteredSelection.BrushTargets; var targetOperations = filteredSelection.OperationTargets; if (targetNodes == null) { return; } bool?isPrefab = false; PrefabInstantiateBehaviour?prefabBehaviour = PrefabInstantiateBehaviour.Reference; PrefabSourceAlignment? prefabSourceAlignment = PrefabSourceAlignment.AlignedTop; PrefabDestinationAlignment?prefabDestinationAlignment = PrefabDestinationAlignment.AlignToSurface; if (targetNodes.Length > 0) { var gameObject = targetNodes[0].gameObject; isPrefab = CSGPrefabUtility.IsPrefabAsset(gameObject); prefabBehaviour = targetNodes[0].PrefabBehaviour; prefabSourceAlignment = targetNodes[0].PrefabSourceAlignment; prefabDestinationAlignment = targetNodes[0].PrefabDestinationAlignment; for (int i = 1; i < targetNodes.Length; i++) { gameObject = targetNodes[i].gameObject; var currentIsPrefab = CSGPrefabUtility.IsPrefabAsset(gameObject); var currentPrefabBehaviour = targetNodes[i].PrefabBehaviour; var currentPrefabSourceAlignment = targetNodes[i].PrefabSourceAlignment; var currentPrefabDestinationAlignment = targetNodes[i].PrefabDestinationAlignment; if (isPrefab.HasValue && isPrefab.Value != currentIsPrefab) { isPrefab = null; } if (prefabBehaviour.HasValue && prefabBehaviour.Value != currentPrefabBehaviour) { prefabBehaviour = null; } if (prefabSourceAlignment.HasValue && prefabSourceAlignment.Value != currentPrefabSourceAlignment) { prefabSourceAlignment = null; } if (prefabDestinationAlignment.HasValue && prefabDestinationAlignment.Value != currentPrefabDestinationAlignment) { prefabDestinationAlignment = null; } } } GUILayout.BeginVertical(GUI.skin.box); { if (isPrefab.HasValue && isPrefab.Value) { EditorGUILayout.LabelField(PrefabLabelContent); } else { EditorGUILayout.LabelField(RaySnappingLabelContent); TooltipUtility.SetToolTip(RaySnappingBehaviourTooltip); } EditorGUI.indentLevel++; { if (isPrefab.HasValue && isPrefab.Value) { EditorGUI.showMixedValue = !prefabBehaviour.HasValue; var prefabBehavour = prefabBehaviour.HasValue ? prefabBehaviour.Value : PrefabInstantiateBehaviour.Reference; EditorGUI.BeginChangeCheck(); { prefabBehavour = (PrefabInstantiateBehaviour)EditorGUILayout.EnumPopup(PrefabInstantiateBehaviourContent, prefabBehavour); TooltipUtility.SetToolTip(PrefabInstantiateBehaviourTooltip); } if (EditorGUI.EndChangeCheck()) { Undo.RecordObjects(targetNodes, "Changed CSG operation of nodes"); for (int i = 0; i < targetNodes.Length; i++) { targetNodes[i].PrefabBehaviour = prefabBehavour; } } EditorGUI.showMixedValue = false; } EditorGUI.showMixedValue = !prefabDestinationAlignment.HasValue; var destinationAlignment = prefabDestinationAlignment.HasValue ? prefabDestinationAlignment.Value : PrefabDestinationAlignment.AlignToSurface; EditorGUI.BeginChangeCheck(); { destinationAlignment = (PrefabDestinationAlignment)EditorGUILayout.EnumPopup(DestinationAlignmentContent, destinationAlignment); TooltipUtility.SetToolTip(DestinationAlignmentTooltip); } if (EditorGUI.EndChangeCheck()) { Undo.RecordObjects(targetNodes, "Changed CSG operation of nodes"); for (int i = 0; i < targetNodes.Length; i++) { targetNodes[i].PrefabDestinationAlignment = destinationAlignment; } } EditorGUI.showMixedValue = false; EditorGUI.showMixedValue = !prefabSourceAlignment.HasValue; var sourceAlignment = prefabSourceAlignment.HasValue ? prefabSourceAlignment.Value : PrefabSourceAlignment.AlignedFront; EditorGUI.BeginChangeCheck(); { sourceAlignment = (PrefabSourceAlignment)EditorGUILayout.EnumPopup(SourceAlignmentContent, sourceAlignment); TooltipUtility.SetToolTip(SourceAlignmentTooltip); } if (EditorGUI.EndChangeCheck()) { Undo.RecordObjects(targetNodes, "Changed CSG operation of nodes"); for (int i = 0; i < targetNodes.Length; i++) { targetNodes[i].PrefabSourceAlignment = sourceAlignment; } } EditorGUI.showMixedValue = false; } EditorGUI.indentLevel--; } GUILayout.EndVertical(); GUILayout.Space(10); if (targetModels.Length == 0) { int invalidOperationType = 999; bool? handleAsOne = null; bool selMixedValues = false; CSGOperationType operationType = (CSGOperationType)invalidOperationType; bool opMixedValues = false; if (targetBrushes.Length > 0) { operationType = targetBrushes[0].OperationType; } for (int b = 1; b < targetBrushes.Length; b++) { var brush = targetBrushes[b]; if (operationType != brush.OperationType) { opMixedValues = true; } } foreach (var operation in targetOperations) { if (operationType == (CSGOperationType)invalidOperationType) { operationType = operation.OperationType; } else if (operationType != operation.OperationType) { opMixedValues = true; } if (!handleAsOne.HasValue) { handleAsOne = operation.HandleAsOne; } else if (handleAsOne.Value != operation.HandleAsOne) { selMixedValues = true; } } GUILayout.BeginVertical(GUI.skin.box); { bool passThroughValue = false; if (targetBrushes.Length == 0 && targetOperations.Length > 0) // only operations { bool?passThrough = targetOperations[0].PassThrough; for (int i = 1; i < targetOperations.Length; i++) { if (passThrough.HasValue && passThrough.Value != targetOperations[i].PassThrough) { passThrough = null; break; } } opMixedValues = !passThrough.HasValue || passThrough.Value; var ptMixedValues = !passThrough.HasValue; passThroughValue = passThrough.HasValue ? passThrough.Value : false; if (CSG_EditorGUIUtility.PassThroughButton(passThroughValue, ptMixedValues)) { Undo.RecordObjects(targetNodes, "Changed CSG operation of nodes"); foreach (var operation in targetOperations) { operation.PassThrough = true; } InternalCSGModelManager.CheckForChanges(); EditorApplication.RepaintHierarchyWindow(); } if (passThroughValue) { operationType = (CSGOperationType)255; } } EditorGUI.BeginChangeCheck(); { operationType = CSG_EditorGUIUtility.ChooseOperation(operationType, opMixedValues); } if (EditorGUI.EndChangeCheck()) { Undo.RecordObjects(targetNodes, "Changed CSG operation of nodes"); foreach (var brush in targetBrushes) { brush.OperationType = operationType; } foreach (var operation in targetOperations) { operation.PassThrough = false; operation.OperationType = operationType; } InternalCSGModelManager.CheckForChanges(); EditorApplication.RepaintHierarchyWindow(); } } GUILayout.EndVertical(); if (targetOperations.Length == 0 && targetModels.Length == 0) { GUILayout.Space(10); if (targetBrushes.Length == 1) { GUILayout.BeginVertical(GUI.skin.box); { EditorGUI.indentLevel++; OpenSurfaces = EditorGUILayout.Foldout(OpenSurfaces, SurfacesContent); EditorGUI.indentLevel--; if (OpenSurfaces) { var targetShape = targetBrushes[0].Shape; var texGens = targetShape.TexGens; var texGenFlagArray = targetShape.TexGenFlags; for (int t = 0; t < texGens.Length; t++) { GUILayout.Space(2); var texGenFlags = texGenFlagArray[t]; var material = targetShape.TexGens[t].RenderMaterial; var physicsMat = targetShape.TexGens[t].PhysicsMaterial; EditorGUI.BeginChangeCheck(); { GUILayout.BeginHorizontal(); { GUILayout.Space(4); material = CSG_EditorGUIUtility.MaterialImage(material); GUILayout.Space(2); GUILayout.BeginVertical(); { //EditorGUI.BeginDisabledGroup(texGenFlags != TexGenFlags.None); { material = EditorGUILayout.ObjectField(material, typeof(Material), true) as Material; } //EditorGUI.EndDisabledGroup(); physicsMat = EditorGUILayout.ObjectField(physicsMat, typeof(PhysicMaterial), true) as PhysicMaterial; texGenFlags = EditModeCommonGUI.OnSurfaceFlagButtons(texGenFlags); } GUILayout.EndVertical(); GUILayout.Space(4); } GUILayout.EndHorizontal(); } if (EditorGUI.EndChangeCheck()) { var selectedBrushSurfaces = new [] { new SelectedBrushSurface(targetBrushes[0], t) }; using (new UndoGroup(selectedBrushSurfaces, "discarding surface")) { texGenFlagArray[t] = texGenFlags; targetShape.TexGens[t].RenderMaterial = material; targetShape.TexGens[t].PhysicsMaterial = physicsMat; } } GUILayout.Space(4); } } } GUILayout.EndVertical(); } } if (handleAsOne.HasValue) { EditorGUI.BeginChangeCheck(); { EditorGUI.showMixedValue = selMixedValues; handleAsOne = EditorGUILayout.Toggle(HandleAsOneLabel, handleAsOne.Value); } if (EditorGUI.EndChangeCheck()) { Undo.RecordObjects(targetNodes, "Changed CSG operation 'Handle as one object'"); foreach (var operation in targetOperations) { operation.HandleAsOne = handleAsOne.Value; } EditorApplication.RepaintHierarchyWindow(); } } } #if false if (targetNodes.Length == 1) { var node = targetNodes[0]; var brush = node as CSGBrush; if (brush != null) { var brush_cache = CSGSceneManager.GetBrushCache(brush); if (brush_cache == null || brush_cache.childData == null || brush_cache.childData.modelTransform == null) { EditorGUILayout.LabelField("brush-cache: null"); } else { EditorGUILayout.LabelField("node-id: " + brush.brushNodeID); } } var operation = node as CSGOperation; if (operation != null) { var operation_cache = CSGSceneManager.GetOperationCache(operation); if (operation_cache == null || operation_cache.childData == null || operation_cache.childData.modelTransform == null) { EditorGUILayout.LabelField("operation-cache: null"); } else { EditorGUILayout.LabelField("operation-id: " + operation.operationNodeID); } } var model = node as CSGModel; if (model != null) { var model_cache = CSGSceneManager.GetModelCache(model); if (model_cache == null || model_cache.meshContainer == null) { EditorGUILayout.LabelField("model-cache: null"); } else { EditorGUILayout.LabelField("model-id: " + model.modelNodeID); } } } #endif } finally { TooltipUtility.DrawToolTip(getLastRect: true, goUp: true); } }
public static void DoSelectionClick() { GameObject gameobject; SceneQueryUtility.FindClickWorldIntersection(Event.current.mousePosition, out gameobject); gameobject = SceneQueryUtility.GetGroupGameObjectIfObjectIsPartOfGroup(gameobject); var selectedObjectsOnClick = new List <int>(Selection.instanceIDs); bool addedSelection = false; if (EditorGUI.actionKey) { if (gameobject != null) { var instanceID = gameobject.GetInstanceID(); if (selectedObjectsOnClick.Contains(instanceID)) { selectedObjectsOnClick.Remove(instanceID); } else { selectedObjectsOnClick.Add(instanceID); addedSelection = true; } if (selectedObjectsOnClick.Count == 0) { Selection.activeTransform = null; } else { Selection.instanceIDs = selectedObjectsOnClick.ToArray(); } } } else if (Event.current.shift) { if (gameobject != null) { var instanceID = gameobject.GetInstanceID(); selectedObjectsOnClick.Add(instanceID); Selection.instanceIDs = selectedObjectsOnClick.ToArray(); addedSelection = true; } } else if (Event.current.alt) { if (gameobject != null) { var instanceID = gameobject.GetInstanceID(); selectedObjectsOnClick.Remove(instanceID); Selection.instanceIDs = selectedObjectsOnClick.ToArray(); return; } } else { Selection.activeGameObject = gameobject; addedSelection = true; } if (!addedSelection) { foreach (var item in Selection.GetFiltered(typeof(CSGBrush), SelectionMode.Deep)) { var brush = item as CSGBrush; var brush_cache = InternalCSGModelManager.GetBrushCache(brush); if (brush_cache == null || brush_cache.childData == null || !brush_cache.childData.Model || !brush_cache.childData.Model.isActiveAndEnabled) { continue; } SelectionUtility.LastUsedModel = brush_cache.childData.Model; break; } } else if (gameobject != null) { var brush = gameobject.GetComponent <CSGBrush>(); if (brush != null) { var brush_cache = InternalCSGModelManager.GetBrushCache(brush); if (brush_cache == null || brush_cache.childData == null || !brush_cache.childData.Model || !brush_cache.childData.Model.isActiveAndEnabled) { return; } SelectionUtility.LastUsedModel = brush_cache.childData.Model; } } }
public void UpdateTransforms(CSGBrush brush) { BrushTransform = brush.GetComponent <Transform>(); ModelTransform = InternalCSGModelManager.FindModelTransform(BrushTransform); // ParentTransform = InternalCSGModelManager.FindParentTransform(BrushTransform); }
static void ShowCSGOperations(bool isSceneGUI, EditModePlace tool, FilteredSelection filteredSelection) { bool operations_enabled = (tool != null && filteredSelection.NodeTargets.Length > 0 && filteredSelection.NodeTargets.Length == (filteredSelection.BrushTargets.Length + filteredSelection.OperationTargets.Length)); EditorGUI.BeginDisabledGroup(!operations_enabled); { bool mixedValues = tool == null || ((filteredSelection.BrushTargets.Length == 0) && (filteredSelection.OperationTargets.Length == 0)); CSGOperationType operationType = CSGOperationType.Additive; if (tool != null) { if (filteredSelection.BrushTargets.Length > 0) { operationType = filteredSelection.BrushTargets[0].OperationType; for (int i = 1; i < filteredSelection.BrushTargets.Length; i++) { if (filteredSelection.BrushTargets[i].OperationType != operationType) { mixedValues = true; } } } else if (filteredSelection.OperationTargets.Length > 0) { operationType = filteredSelection.OperationTargets[0].OperationType; } if (filteredSelection.OperationTargets.Length > 0) { for (int i = 0; i < filteredSelection.OperationTargets.Length; i++) { if (filteredSelection.OperationTargets[i].OperationType != operationType) { mixedValues = true; } } } } GUILayout.BeginVertical(isSceneGUI ? GUI.skin.box : GUIStyle.none); { bool passThroughValue = false; if (tool != null && filteredSelection.BrushTargets.Length == 0 && filteredSelection.OperationTargets.Length > 0 && filteredSelection.OperationTargets.Length == filteredSelection.NodeTargets.Length) // only operations { bool?passThrough = filteredSelection.OperationTargets[0].PassThrough; for (int i = 1; i < filteredSelection.OperationTargets.Length; i++) { if (passThrough.HasValue && passThrough.Value != filteredSelection.OperationTargets[i].PassThrough) { passThrough = null; break; } } mixedValues = !passThrough.HasValue || passThrough.Value; var ptMixedValues = !passThrough.HasValue; passThroughValue = passThrough.HasValue ? passThrough.Value : false; if (CSG_EditorGUIUtility.PassThroughButton(passThroughValue, ptMixedValues)) { Undo.RecordObjects(filteredSelection.OperationTargets, "Changed CSG operation of nodes"); foreach (var operation in filteredSelection.OperationTargets) { operation.PassThrough = true; } InternalCSGModelManager.CheckForChanges(); EditorApplication.RepaintHierarchyWindow(); } if (passThroughValue) { operationType = (CSGOperationType)255; } } EditorGUI.BeginChangeCheck(); { operationType = CSG_EditorGUIUtility.ChooseOperation(operationType, mixedValues); } if (EditorGUI.EndChangeCheck() && tool != null) { Undo.RecordObjects(filteredSelection.NodeTargets, "Changed CSG operation of nodes"); for (int i = 0; i < filteredSelection.BrushTargets.Length; i++) { filteredSelection.BrushTargets[i].OperationType = operationType; } for (int i = 0; i < filteredSelection.OperationTargets.Length; i++) { filteredSelection.OperationTargets[i].PassThrough = false; filteredSelection.OperationTargets[i].OperationType = operationType; } InternalCSGModelManager.CheckForChanges(); EditorApplication.RepaintHierarchyWindow(); } } GUILayout.EndVertical(); } EditorGUI.EndDisabledGroup(); }
public bool UpdateSelection(HashSet <CSGNode> newTargetNodes, HashSet <Transform> newTargetOthers) { if (newTargetNodes == null) { newTargetNodes = new HashSet <CSGNode>(); } if (newTargetOthers == null) { newTargetOthers = new HashSet <Transform>(); } this.RemovedNodes = null; this.RemovedOthers = null; this.AddedNodes = null; this.AddedOthers = null; var foundRemovedNodes = new List <CSGNode>(); if (this.NodeTargets != null && this.NodeTargets.Length > 0) { if (newTargetNodes.Count == 0) { foundRemovedNodes.AddRange(this.NodeTargets); } else { for (int i = 0; i < this.NodeTargets.Length; i++) { if (!this.NodeTargets[i] || !newTargetNodes.Contains(this.NodeTargets[i])) { foundRemovedNodes.Add(this.NodeTargets[i]); } } } } var foundRemovedOthers = new List <Transform>(); if (this.OtherTargets != null && this.OtherTargets.Length > 0) { if (newTargetOthers.Count == 0) { foundRemovedOthers.AddRange(this.OtherTargets); } else { for (int i = 0; i < this.OtherTargets.Length; i++) { if (!this.OtherTargets[i] || !newTargetOthers.Contains(this.OtherTargets[i])) { foundRemovedOthers.Add(this.OtherTargets[i]); } } } } var originalTargetNodeCount = (this.NodeTargets == null) ? 0 : this.NodeTargets.Length; var originalTargetOtherCount = (this.OtherTargets == null) ? 0 : this.OtherTargets.Length; // If our counts are the same and nothing is removed (and nothing could've been added), nothing has changed. if (newTargetNodes.Count == originalTargetNodeCount && newTargetOthers.Count == originalTargetOtherCount && foundRemovedNodes.Count == 0 && foundRemovedOthers.Count == 0) { //Debug.Log(originalTargetNodeCount + " " + originalTargetOtherCount + " " + newTargetNodes .Count + " " + newTargetOthers .Count); return(false); } Validate(); foreach (var node in foundRemovedNodes) { ArrayUtility.Remove(ref this.NodeTargets, node); var brush = node as CSGBrush; if (brush != null) { ArrayUtility.Remove(ref this.BrushTargets, brush); continue; } var operation = node as CSGOperation; if (node is CSGOperation) { ArrayUtility.Remove(ref this.OperationTargets, operation); continue; } var model = node as CSGModel; if (node is CSGModel) { ArrayUtility.Remove(ref this.ModelTargets, model); continue; } } foreach (var other in foundRemovedOthers) { ArrayUtility.Remove(ref this.OtherTargets, other); } var foundAddedNodes = new List <CSGNode>(); foreach (var node in newTargetNodes) { if (this.NodeTargets != null && ArrayUtility.Contains(this.NodeTargets, node)) { continue; } if (this.NodeTargets == null) { this.NodeTargets = new CSGNode[] { node }; } else { ArrayUtility.Add(ref this.NodeTargets, node); } foundAddedNodes.Add(node); if (SelectionUtility.IsPrefab(node.gameObject)) { continue; } var brush = node as CSGBrush; if (brush != null) { if (this.BrushTargets == null) { this.BrushTargets = new CSGBrush[] { brush } } ; else { ArrayUtility.Add(ref this.BrushTargets, brush); } continue; } var operation = node as CSGOperation; if (node is CSGOperation) { if (this.OperationTargets == null) { this.OperationTargets = new CSGOperation[] { operation } } ; else { ArrayUtility.Add(ref this.OperationTargets, operation); } continue; } var model = node as CSGModel; if (node is CSGModel) { if (this.ModelTargets == null) { this.ModelTargets = new CSGModel[] { model } } ; else { ArrayUtility.Add(ref this.ModelTargets, model); } continue; } } var foundAddedOthers = new List <Transform>(); foreach (var other in newTargetOthers) { if (this.OtherTargets != null && ArrayUtility.Contains(this.OtherTargets, other)) { continue; } if (this.OtherTargets == null) { this.OtherTargets = new Transform[] { other } } ; else { ArrayUtility.Add(ref this.OtherTargets, other); } foundAddedOthers.Add(other); } for (int i = foundAddedNodes.Count - 1; i >= 0; i--) { var node = foundAddedNodes[i]; var brush = node as CSGBrush; if (brush != null) { var brush_cache = InternalCSGModelManager.GetBrushCache(brush); if (brush_cache == null || brush_cache.childData == null || brush_cache.childData.Model == null) { continue; } var childModel = brush_cache.childData.Model; if (childModel && childModel.isActiveAndEnabled) { SelectionUtility.LastUsedModel = childModel; } break; } var operation = node as CSGOperation; if (operation != null) { var operation_cache = InternalCSGModelManager.GetOperationCache(operation); if (operation_cache == null || operation_cache.ChildData == null || operation_cache.ChildData.Model == null) { continue; } SelectionUtility.LastUsedModel = operation_cache.ChildData.Model; break; } var model = node as CSGModel; if (model && model.isActiveAndEnabled) { SelectionUtility.LastUsedModel = model; break; } } this.RemovedNodes = foundRemovedNodes.ToArray(); this.RemovedOthers = foundRemovedOthers.ToArray(); this.AddedNodes = foundAddedNodes.ToArray(); this.AddedOthers = foundAddedOthers.ToArray(); return(foundAddedNodes.Count > 0 || foundRemovedNodes.Count > 0 || foundAddedOthers.Count > 0 || foundRemovedOthers.Count > 0); }