// BRUSH METHODS // private BrushPrefabSettings ChooseRandomPrefab() { BrushPrefabSettings currentPick = SavedBrushes.brushes[BrushList.index].prefabs[0]; float currentWeight = Random.Range(0f, 1f) * currentPick.weight; for (int i = 0; i < SavedBrushes.brushes[BrushList.index].prefabs.Count; i++) { float weight = Random.Range(0f, 1f) * SavedBrushes.brushes[BrushList.index].prefabs[i].weight; if (weight > currentWeight) { currentWeight = weight; currentPick = SavedBrushes.brushes[BrushList.index].prefabs[i]; } } return(currentPick); }
private void PaintObjects(Event current) { // Checks if (current.type == EventType.Repaint) { return; } if (SavedBrushes.brushes[BrushList.index].prefabs.Count == 0) { return; } if (!mouseIsDown && current.type == EventType.MouseDown && current.modifiers == EventModifiers.None && current.button == 0) { lastCollider = brushHit.collider; mouseIsDown = true; } if (mouseIsDown && current.type == EventType.MouseUp) { lastCollider = null; mouseIsDown = false; } if (!mouseIsDown || brushHit.collider == null) { return; } // Exit if delay is not up yet. if (placeTimeStamp >= EditorApplication.timeSinceStartup) { return; } // Calculate direction from center to random angle. Vector3 dir = (Quaternion.AngleAxis(Random.Range(0f, 360f), brushHit.normal) * Vector3.Cross(brushHit.normal, Vector3.right)).normalized; // Calculate random range from center to radius. float range = Random.Range(0, SavedBrushes.brushes[BrushList.index].brushRadius); // Construct selected location from direction + range. Vector3 selectPos = brushHit.point + (dir * range); // Align this point to local surface or abort if nothing was hit. Ray upRay = new Ray(selectPos, Vector3.up); Ray downRay = new Ray(selectPos, Vector3.down); Ray safeRay = new Ray(selectPos + (Vector3.up * 0.01f), Vector3.down); Ray normalRay = new Ray(selectPos + (brushHit.normal * 0.01f), -brushHit.normal); RaycastHit hitToSurface; bool oldQuery = Physics.queriesHitBackfaces; Physics.queriesHitBackfaces = true; int layers = SavedBrushes.brushes[BrushList.index].layerMask; if (!Physics.Raycast(upRay, out hitToSurface, Mathf.Infinity, layers, QueryTriggerInteraction.Ignore) && !Physics.Raycast(downRay, out hitToSurface, Mathf.Infinity, layers, QueryTriggerInteraction.Ignore) && !Physics.Raycast(safeRay, out hitToSurface, Mathf.Infinity, layers, QueryTriggerInteraction.Ignore) && !Physics.Raycast(normalRay, out hitToSurface, Mathf.Infinity, layers, QueryTriggerInteraction.Ignore)) { return; } if (SavedBrushes.brushes[BrushList.index].colliderStrict && hitToSurface.collider != lastCollider) { return; } Physics.queriesHitBackfaces = oldQuery; if (SavedBrushes.brushes[BrushList.index].cullEnabled) { float angle = Vector3.Angle(SavedBrushes.brushes[BrushList.index].cullRef, hitToSurface.normal); if (!SavedBrushes.brushes[BrushList.index].cullInvert && angle > SavedBrushes.brushes[BrushList.index].cullAngle) { return; } if (SavedBrushes.brushes[BrushList.index].cullInvert && angle < SavedBrushes.brushes[BrushList.index].cullAngle) { return; } } BrushPrefabSettings pick = ChooseRandomPrefab(); if (pick.paintObject == null) { Debug.LogWarning("[ObjectPainter] The Prefab is null !"); return; } // Generate new object. float objScale = Random.Range(pick.objectRandomScale.x, pick.objectRandomScale.y); float objRot = Random.Range(pick.objectRandomRotation.x, pick.objectRandomRotation.y); GameObject newObj = PrefabUtility.InstantiatePrefab(pick.paintObject) as GameObject; // Set parent if (parent) { newObj.transform.parent = parent; } newObj.transform.position = hitToSurface.point; switch (pick.alignMode) { default: case BrushPrefabSettings.AlignMode.Up: newObj.transform.up = hitToSurface.normal; if (pick.alignToPath) { newObj.transform.forward = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.Down: newObj.transform.up = -hitToSurface.normal; if (pick.alignToPath) { newObj.transform.forward = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.Left: newObj.transform.right = -hitToSurface.normal; if (pick.alignToPath) { newObj.transform.forward = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.Right: newObj.transform.right = hitToSurface.normal; if (pick.alignToPath) { newObj.transform.forward = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.Forward: newObj.transform.forward = hitToSurface.normal; if (pick.alignToPath) { newObj.transform.up = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.Backward: newObj.transform.forward = -hitToSurface.normal; if (pick.alignToPath) { newObj.transform.up = brushHit.point - lastHitPoint; } break; case BrushPrefabSettings.AlignMode.None: if (pick.alignToPath) { newObj.transform.forward = brushHit.point - lastHitPoint; } break; } newObj.transform.localScale = new Vector3(objScale, objScale, objScale); newObj.transform.RotateAround(newObj.transform.position, hitToSurface.normal, objRot); lastHitPoint = brushHit.point; Undo.RegisterCreatedObjectUndo(newObj, "Object Painter"); float rate = SavedBrushes.brushes[BrushList.index].brushRate; placeTimeStamp = EditorApplication.timeSinceStartup + ((60d / rate) / 60d); }