void OnBrushBeginApply(BrushTarget brushTarget, BrushSettings settings) { PolySceneUtility.PushGIWorkflowMode(); firstGameObject = brushTarget.gameObject; mode.RegisterUndo(brushTarget); m_UndoQueue.Add(brushTarget.gameObject); mode.OnBrushBeginApply(brushTarget, brushSettings); }
internal void OnFinishApplyingBrush() { PolySceneUtility.PopGIWorkflowMode(); firstGameObject = null; m_ApplyingBrush = false; mode.OnBrushFinishApply(brushTarget, brushSettings); FinalizeAndResetHovering(); m_IgnoreDrag.Clear(); }
void PlaceGameObject(PolyRaycastHit hit, PrefabAndSettings prefabAndSettings, BrushTarget target, BrushSettings settings) { if (prefabAndSettings == null) { return; } GameObject prefab = prefabAndSettings.gameObject; var worldPosition = target.transform.TransformPoint(hit.position); var worldNormal = target.transform.TransformDirection(hit.normal); Ray ray = RandomRay(worldPosition, worldNormal, settings.radius, settings.falloff, settings.falloffCurve); ray.origin = target.transform.InverseTransformPoint(ray.origin); ray.direction = target.transform.InverseTransformDirection(ray.direction); PolyRaycastHit rand_hit; Vector3[] vertices = target.editableObject.editMesh.vertices; int[] triangles = target.editableObject.editMesh.GetTriangles(); if (PolySceneUtility.MeshRaycast(ray, vertices, triangles, out rand_hit)) { PlacementSettings placementSettings = prefabAndSettings.settings; Vector3 scaleSetting = prefab.transform.localScale; if (placementSettings.uniformBool) { float uniformScale = Random.Range(placementSettings.uniformScale.x, placementSettings.uniformScale.y); scaleSetting *= uniformScale; } else { if (placementSettings.xScaleBool) { scaleSetting.x = Random.Range(placementSettings.scaleRangeMin.x, placementSettings.scaleRangeMax.x); } if (placementSettings.yScaleBool) { scaleSetting.y = Random.Range(placementSettings.scaleRangeMin.y, placementSettings.scaleRangeMax.y); } if (placementSettings.zScaleBool) { scaleSetting.z = Random.Range(placementSettings.scaleRangeMin.z, placementSettings.scaleRangeMax.z); } } Vector3 rotationSetting = Vector3.zero; if (placementSettings.xRotationBool) { rotationSetting.x = Random.Range(placementSettings.rotationRangeMin.x, placementSettings.rotationRangeMax.x); } if (placementSettings.yRotationBool) { rotationSetting.y = Random.Range(placementSettings.rotationRangeMin.y, placementSettings.rotationRangeMax.y); } if (placementSettings.xRotationBool) { rotationSetting.z = Random.Range(placementSettings.rotationRangeMin.z, placementSettings.rotationRangeMax.z); } Quaternion rotation = Quaternion.FromToRotation(Vector3.up, target.transform.TransformDirection(rand_hit.normal)); GameObject inst = (GameObject)PrefabUtility.InstantiatePrefab(prefab); inst.transform.position = target.transform.TransformPoint(rand_hit.position); inst.transform.rotation = rotation; inst.transform.localScale = scaleSetting; float pivotOffset = s_UsePivotForPlacement ? 0f : GetPivotOffset(inst); inst.name = FormatInstanceName(prefab); inst.transform.position = inst.transform.position - (inst.transform.up * pivotOffset); inst.transform.rotation = inst.transform.rotation * Quaternion.Euler(rotationSetting); if (s_AvoidOverlappingGameObjects && TestIntersection(inst)) { Object.DestroyImmediate(inst); return; } if (s_ParentObjectWithSurface) { inst.transform.SetParent(target.transform); } m_PrefabsInstances.Add(inst); Undo.RegisterCreatedObjectUndo(inst, UndoMessage); } }
internal override void OnBrushBeginApply(BrushTarget target, BrushSettings settings) { base.OnBrushBeginApply(target, settings); m_PrefabsInstances = PolySceneUtility.FindInstancesInScene(prefabPalette.prefabs.Select(x => x.gameObject), FormatInstanceName).ToList(); }
/// <summary> /// Calculate the weights for this ray. /// </summary> /// <param name="mouseRay">The ray used to calculate weights</param> /// <param name="target">The object on which to calculate the weights</param> /// <returns>true if mouseRay hits the target, false otherwise</returns> bool DoMeshRaycast(Ray mouseRay, BrushTarget target, MirrorSettings mirrorSettings) { if (!Util.IsValid(target)) { return(false); } target.ClearRaycasts(); EditableObject editable = target.editableObject; s_Rays.Clear(); s_Rays.Add(mouseRay); if (mirrorSettings.Axes != BrushMirror.None) { for (int i = 0; i < 3; i++) { if (((uint)mirrorSettings.Axes & (1u << i)) < 1) { continue; } int len = s_Rays.Count; for (int n = 0; n < len; n++) { Vector3 flipVec = ((BrushMirror)(1u << i)).ToVector3(); if (mirrorSettings.Space == MirrorCoordinateSpace.World) { Vector3 cen = editable.gameObjectAttached.GetComponent <Renderer>().bounds.center; s_Rays.Add(new Ray(Vector3.Scale(s_Rays[n].origin - cen, flipVec) + cen, Vector3.Scale(s_Rays[n].direction, flipVec))); } else { Transform t = SceneView.lastActiveSceneView.camera.transform; Vector3 o = t.InverseTransformPoint(s_Rays[n].origin); Vector3 d = t.InverseTransformDirection(s_Rays[n].direction); s_Rays.Add(new Ray(t.TransformPoint(Vector3.Scale(o, flipVec)), t.TransformDirection(Vector3.Scale(d, flipVec)))); } } } } bool hitMesh = false; int[] triangles = editable.editMesh.GetTriangles(); foreach (Ray ray in s_Rays) { PolyRaycastHit hit; if (PolySceneUtility.WorldRaycast(ray, editable.transform, editable.visualMesh.vertices, triangles, out hit)) { target.raycastHits.Add(hit); hitMesh = true; } } PolySceneUtility.CalculateWeightedVertices(target, brushSettings, tool, mode); return(hitMesh); }
void OnSceneGUI(SceneView sceneView) { if (mode == null) { return; } Event e = Event.current; CheckForEscapeKey(e); if (Tools.current != Tool.None) { SetTool(BrushTool.None); } if (brushSettings == null) { SetBrushSettings(PolyEditorUtility.GetFirstOrNew <BrushSettings>()); } if (PolySceneUtility.SceneViewInUse(e) || tool == BrushTool.None) { // Force exit the current brush if user's mouse left // the SceneView while a brush was still in use. if (m_ApplyingBrush) { OnFinishApplyingBrush(); } return; } int controlID = GUIUtility.GetControlID(FocusType.Passive); if (Util.IsValid(brushTarget)) { HandleUtility.AddDefaultControl(controlID); } switch (e.GetTypeForControl(controlID)) { case EventType.MouseMove: // Handles: // OnBrushEnter // OnBrushExit // OnBrushMove if (EditorApplication.timeSinceStartup - m_LastBrushUpdate > GetTargetFramerate(brushTarget)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.MouseDown: case EventType.MouseDrag: // Handles: // OnBrushBeginApply // OnBrushApply // OnBrushFinishApply if (EditorApplication.timeSinceStartup - m_LastBrushUpdate > GetTargetFramerate(brushTarget)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); ApplyBrush(Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.MouseUp: if (m_ApplyingBrush) { OnFinishApplyingBrush(); UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.ScrollWheel: ScrollBrushSettings(e); break; } if (Util.IsValid(brushTarget)) { mode.DrawGizmos(brushTarget, brushSettings); } }
void OnSceneGUI(SceneView sceneView) { if (mode == null) { return; } Event e = Event.current; CheckForEscapeKey(e); if (Tools.current != Tool.None) { SetTool(BrushTool.None); } if (brushSettings == null) { SetBrushSettings(PolyEditorUtility.GetFirstOrNew <BrushSettings>()); } if (PolySceneUtility.SceneViewInUse(e) || tool == BrushTool.None) { // Force exit the current brush if user's mouse left // the SceneView while a brush was still in use. if (m_ApplyingBrush) { OnFinishApplyingBrush(); } return; } int controlID = GUIUtility.GetControlID(FocusType.Passive); if (Util.IsValid(brushTarget)) { HandleUtility.AddDefaultControl(controlID); } switch (e.GetTypeForControl(controlID)) { case EventType.MouseMove: // Handles: // OnBrushEnter // OnBrushExit // OnBrushMove if (EditorApplication.timeSinceStartup - m_LastBrushUpdate > GetTargetFramerate(brushTarget)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.MouseDown: case EventType.MouseDrag: // Handles: // OnBrushBeginApply // OnBrushApply // OnBrushFinishApply if (EditorApplication.timeSinceStartup - m_LastBrushUpdate > GetTargetFramerate(brushTarget)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); ApplyBrush(Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.MouseUp: if (m_ApplyingBrush) { OnFinishApplyingBrush(); UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.ScrollWheel: ScrollBrushSettings(e); break; case EventType.KeyDown: // Key down event continues as long as the key is held down. However, we only need to update the brush once while the key is down. // Check if the key has already been marked as pressed in the brush settings, and don't update if it is. if (((e.keyCode == KeyCode.LeftControl || e.keyCode == KeyCode.RightControl) && !brushSettings.isUserHoldingControl) || ((e.keyCode == KeyCode.LeftShift || e.keyCode == KeyCode.RightShift) && !brushSettings.isUserHoldingShift)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; case EventType.KeyUp: // Key up only happens once, so don't need to check if we were already holding control/shift if ((e.keyCode == KeyCode.LeftControl || e.keyCode == KeyCode.RightControl) || (e.keyCode == KeyCode.LeftShift || e.keyCode == KeyCode.RightShift)) { m_LastBrushUpdate = EditorApplication.timeSinceStartup; UpdateBrush(e.mousePosition, Event.current.control, Event.current.shift && Event.current.type != EventType.ScrollWheel); } break; } if (Util.IsValid(brushTarget)) { mode.DrawGizmos(brushTarget, brushSettings); } }
/// <summary> /// Calculate the weights for this ray. /// </summary> /// <param name="mouseRay">The ray used to calculate weights</param> /// <param name="target">The object on which to calculate the weights</param> /// <returns>true if mouseRay hits the target, false otherwise</returns> bool DoMeshRaycast(Ray mouseRay, BrushTarget target, MirrorSettings mirrorSettings) { m_SecondaryBrushTargets.Clear(); if (!Util.IsValid(target)) { return(false); } target.ClearRaycasts(); EditableObject editable = target.editableObject; s_Rays.Clear(); s_Rays.Add(mouseRay); if (mirrorSettings.Axes != BrushMirror.None) { for (int i = 0; i < 3; i++) { if (((uint)mirrorSettings.Axes & (1u << i)) < 1) { continue; } int len = s_Rays.Count; for (int n = 0; n < len; n++) { Vector3 flipVec = ((BrushMirror)(1u << i)).ToVector3(); if (mirrorSettings.Space == MirrorCoordinateSpace.World) { Vector3 cen = editable.gameObjectAttached.GetComponent <Renderer>().bounds.center; s_Rays.Add(new Ray(Vector3.Scale(s_Rays[n].origin - cen, flipVec) + cen, Vector3.Scale(s_Rays[n].direction, flipVec))); } else { Transform t = SceneView.lastActiveSceneView.camera.transform; Vector3 o = t.InverseTransformPoint(s_Rays[n].origin); Vector3 d = t.InverseTransformDirection(s_Rays[n].direction); s_Rays.Add(new Ray(t.TransformPoint(Vector3.Scale(o, flipVec)), t.TransformDirection(Vector3.Scale(d, flipVec)))); } } } } bool hitMesh = false; int[] triangles = editable.editMesh.GetTriangles(); foreach (Ray ray in s_Rays) { PolyRaycastHit hit; if (PolySceneUtility.WorldRaycast(ray, editable.transform, editable.visualMesh.vertices, triangles, out hit)) { target.raycastHits.Add(hit); hitMesh = true; } } PolySceneUtility.CalculateWeightedVertices(target, brushSettings, tool, mode); if (hitMesh && !s_LockBrushToFirst) { Transform[] trs = Selection.GetTransforms(SelectionMode.Unfiltered); var hits = target.raycastHits; foreach (var selectedTransform in trs) { bool isValid = false; if (selectedTransform != editable.transform) { BrushTarget secondaryTarget = GetOrCreateBrushTarget(selectedTransform.gameObject); isValid = Util.IsValid(secondaryTarget); if (isValid) { m_SecondaryBrushTargets.Add(secondaryTarget); secondaryTarget.ClearRaycasts(); foreach (var hit in hits) { PolyRaycastHit secondaryHit = new PolyRaycastHit(hit.distance, secondaryTarget.transform.InverseTransformPoint(editable.transform.TransformPoint(hit.position)), hit.normal, -1); secondaryTarget.raycastHits.Add(secondaryHit); } } PolySceneUtility.CalculateWeightedVertices(secondaryTarget, brushSettings, tool, mode); } } } return(hitMesh); }