public IconMeshGenerator() { Scale = 0.1f; Translate = new Vector3f(0, 0, 0); Rotate = Quaternionf.AxisAngleD(Vector3f.AxisY, 120.0f); Color = Colorf.Grey; }
public virtual void Setup() { // do this here ?? behaviors = new InputBehaviorSet(); SpatialDeviceGrabBehavior behavior = new SpatialDeviceGrabBehavior(Scene.Context, (so) => { return(so == this.Target); }) { Priority = 1, RotationSpeed = 0.25f, TranslationSpeed = 0.25f }; behaviors.Add(behavior); indicators = new ToolIndicatorSet(this, Scene); float h = 300.0f; Frame3f f1 = Frame3f.Identity.Rotated(Quaternionf.AxisAngleD(Vector3f.AxisZ, 90.0f)).Translated(h * 0.5f * Vector3f.AxisY); var plane1 = new SectionPlaneIndicator() { Width = fDimension.Scene(h), // in mm SceneFrameF = () => { return(f1); } }; indicators.AddIndicator(plane1); Frame3f f2 = Frame3f.Identity.Rotated(Quaternionf.AxisAngleD(Vector3f.AxisX, 90.0f)).Translated(h * 0.5f * Vector3f.AxisY); var plane2 = new SectionPlaneIndicator() { Width = fDimension.Scene(h), // in mm SceneFrameF = () => { return(f2); } }; indicators.AddIndicator(plane2); }
// try to compute a stable ray/plane intersection. when origin is at < +/- an altitude threshold, // use ray/line distance with view-perp line, instead of actual intersection public static Vector3f SafeRayPlaneIntersection(Ray3f ray, Vector3f forwardDir, Vector3f planeOrigin, Vector3f planeNormal, float fAngleThresh = 10.0f) { // determine if we are in unstable condition float fOriginAngleDeg = (float)Math.Abs( planeNormal.AngleD((planeOrigin - ray.Origin).Normalized)); bool bOriginUnstable = Math.Abs(fOriginAngleDeg - 90.0f) < fAngleThresh; // we use ray/plane intersect if stable Frame3f planeF = new Frame3f(planeOrigin, planeNormal); Vector3f planeHit = planeF.RayPlaneIntersection(ray.Origin, ray.Direction, 2); if (bOriginUnstable == false) { return(planeHit); } // if unstable, find "right" direction in plane (ie perp to forward dir, which // may just be ray dir), then intersection is ray/axis closest point Vector3f fwDirInPlane = (forwardDir - planeNormal.Dot(forwardDir)).Normalized; Vector3f perpDirInPlane = Quaternionf.AxisAngleD(planeNormal, 90.0f) * fwDirInPlane; float fAxisDist = (float)DistLine3Ray3.MinDistanceLineParam(ray, new Line3d(planeOrigin, perpDirInPlane)); return(planeOrigin + fAxisDist * perpDirInPlane); }
public static void test_basic_generators() { TrivialDiscGenerator disc_gen = new TrivialDiscGenerator(); disc_gen.Generate(); WriteGeneratedMesh(disc_gen, "__g3Test_disc.obj"); TrivialRectGenerator rect_gen = new TrivialRectGenerator(); rect_gen.Generate(); WriteGeneratedMesh(rect_gen, "__g3Test_rect.obj"); PuncturedDiscGenerator punc_disc_gen = new PuncturedDiscGenerator(); punc_disc_gen.Generate(); WriteGeneratedMesh(punc_disc_gen, "__g3Test_punctured_disc.obj"); TrivialBox3Generator box_gen = new TrivialBox3Generator(); Frame3f f = Frame3f.Identity; f.Rotate(Quaternionf.AxisAngleD(Vector3f.AxisY, 45.0f)); f.Rotate(Quaternionf.AxisAngleD(Vector3f.AxisZ, 45.0f)); box_gen.Box = new Box3d(f.Origin, f.X, f.Y, f.Z, new Vector3d(3, 2, 1)); //box_gen.NoSharedVertices = true; box_gen.Generate(); WriteGeneratedMesh(box_gen, "__g3Test_trivial_box.obj"); RoundRectGenerator roundrect_gen = new RoundRectGenerator(); roundrect_gen.Width = 2; roundrect_gen.Generate(); WriteGeneratedMesh(roundrect_gen, "__g3Test_round_rect.obj"); }
// same as LocalFrame, but LocalFrame may be tilted up/down, which we want to undo public virtual Frame3f GetLevelViewFrame(CoordSpace eSpace) { // otherwise we can't just set y to 0... Debug.Assert(eSpace == CoordSpace.WorldCoords); Frame3f viewF = UnityUtil.GetGameObjectFrame(ActiveCamera.GameObject(), eSpace); float fAngle = VRUtil.PlaneAngleSigned(Vector3f.AxisZ, viewF.Z, 1); return(new Frame3f(viewF.Origin, Quaternionf.AxisAngleD(Vector3f.AxisY, fAngle))); }
public static fRectangleGameObject CreateRectangleGO(string sName, float fWidth, float fHeight, fMaterial useMaterial, bool bShareMaterial, bool bCollider) { GameObject go = new GameObject(sName); Mesh rectMesh = UnityUtil.GetPrimitiveMesh(PrimitiveType.Quad); UnityUtil.RotateMesh(rectMesh, Quaternionf.AxisAngleD(Vector3f.AxisX, 90), Vector3f.Zero); initialize_meshgo(go, new fMesh(rectMesh), bCollider, true); go.SetMaterial(useMaterial, bShareMaterial); return(new fRectangleGameObject(go, fWidth, fHeight)); }
// creates a button that is just the mesh, basically same as above but without the background disc public void Create(UnityEngine.PrimitiveType eType, fMaterial primMaterial, float fPrimScale = 1.0f) { button = GameObjectFactory.CreateParentGO(UniqueNames.GetNext("HUDButton")); buttonMesh = AppendUnityPrimitiveGO(UniqueNames.GetNext("HUDButton"), eType, primMaterial, button); float primSize = Shape.EffectiveRadius() * fPrimScale; buttonMesh.SetLocalScale(new Vector3f(primSize, primSize, primSize)); buttonMesh.Translate(new Vector3f(0.0f, 0.0f, -primSize), false); Quaternionf rot = buttonMesh.GetLocalRotation(); rot = rot * Quaternionf.AxisAngleD(Vector3f.AxisY, 45.0f); rot = rot * Quaternionf.AxisAngleD(Vector3f.AxisX, -15.0f); buttonMesh.SetLocalRotation(rot); //buttonMesh.transform.Rotate(-15.0f, 45.0f, 0.0f, Space.Self); MaterialUtil.DisableShadows(buttonMesh); standard_mat = new fMaterial(primMaterial); }
public static Mesh GetTwoSidedPlaneMesh() { Mesh m = GetPrimitiveMesh(PrimitiveType.Plane); Mesh m2 = GetPrimitiveMesh(PrimitiveType.Plane); UnityUtil.RotateMesh(m2, Quaternionf.AxisAngleD(Vector3f.AxisX, 180.0f), Vector3f.Zero); CombineInstance[] combine = new CombineInstance[2] { new CombineInstance() { mesh = m, transform = Matrix4x4.identity }, new CombineInstance() { mesh = m2, transform = Matrix4x4.identity }, }; Mesh twosided = new Mesh(); twosided.CombineMeshes(combine); return(twosided); }
void UpdateTracking(bool bSetInitial) { if (bSetInitial || PositionMode == MovementMode.Static) { // [TODO] should damp out jitter while allowing larger moves if (bStaticUpdated == false) { RootGameObject.SetPosition(ActiveCamera.GetPosition()); RootGameObject.SetRotation(Quaternionf.Identity); bStaticUpdated = true; } } else if (PositionMode == MovementMode.TrackOrientation) { RootGameObject.SetPosition(ActiveCamera.GetPosition()); RootGameObject.SetRotation(ActiveCamera.GetRotation()); } else if (PositionMode == MovementMode.CustomTracking && CustomTracker != null) { CustomTracker.UpdateTracking(this, ActiveCamera); } else { // MovemementMode.TrackPosition RootGameObject.SetPosition(ActiveCamera.GetPosition()); RootGameObject.SetRotation(Quaternionf.Identity); } // apply post-rotations Frame3f frame = RootGameObject.GetWorldFrame(); Quaternionf rotateLR = Quaternionf.AxisAngleD(frame.Y, ShiftAngle); Quaternionf rotateUp = Quaternionf.AxisAngleD(rotateLR * frame.X, TiltAngle); RootGameObject.SetRotation(rotateLR * rotateUp * RootGameObject.GetRotation()); // camera-tracking GO always tracks camera onCameraGO.SetPosition(ActiveCamera.GetPosition()); onCameraGO.SetRotation(ActiveCamera.GetRotation()); }
// Use this for initialization void Start() { Vector3f xz = new Vector3f(1, 0, 1); xz.Normalize(); Vector3f angleVec = Quaternionf.AxisAngleD(new Vector3f(xz.x, 0, -xz.z), -LightAltitudeAngle) * xz; //Vector3f angleVec = new Vector3f(1, 3, 1); angleVec.Normalize(); Vector3f vCornerPos = LightDistance * angleVec; // create a set of overheard spotlights float rotAngle = 360.0f / (float)LightCount; for (int k = 0; k < LightCount; k++) { GameObject lightObj = new GameObject(string.Format("spotlight{0}", k)); Light lightComp = lightObj.AddComponent <Light> (); lightComp.type = LightType.Directional; lightComp.transform.position = vCornerPos; lightComp.transform.LookAt(Vector3.zero); lightComp.transform.RotateAround(Vector3.zero, Vector3.up, (float)k * rotAngle); lightComp.intensity = 0.1f; lightComp.color = Color.white; // only add shadows on first two lights if (k < ShadowLightCount) { lightComp.shadows = LightShadows.Hard; } lightComp.transform.SetParent(this.gameObject.transform); lights.Add(lightObj); } // parent lights to Scene so they move with it Context.GetScene().LightingObjectsParent.AddChild(this.gameObject, false); }
override protected void BuildGizmo() { gizmo.SetName("SurfaceConstrainedGizmo"); make_materials(); centerGO = AppendMeshGO("object_origin", UnityUtil.GetPrimitiveMesh(PrimitiveType.Sphere), srcMaterial, gizmo); centerGO.SetLocalScale(WidgetScale); Widgets[centerGO] = new SurfaceConstrainedPointWidget(this, this.parentScene) { RootGameObject = centerGO, StandardMaterial = srcMaterial, HoverMaterial = srcHoverMaterial }; PuncturedDiscGenerator discgen = new PuncturedDiscGenerator() { StartAngleDeg = 180, EndAngleDeg = 270, OuterRadius = 1.5f, InnerRadius = 0.75f }; discgen.Generate(); SimpleMesh discmesh = discgen.MakeSimpleMesh(); MeshTransforms.Rotate(discmesh, Vector3d.Zero, Quaternionf.AxisAngleD(Vector3f.AxisX, 90)); rotateGO = AppendMeshGO("object_rotate", new fMesh(discmesh), srcMaterial, gizmo); rotateGO.SetLocalScale(WidgetScale); Widgets[rotateGO] = new AxisRotationWidget(2) { RootGameObject = rotateGO, StandardMaterial = srcMaterial, HoverMaterial = srcHoverMaterial }; gizmo.Hide(); }
public static void test_basic_generators() { TrivialDiscGenerator disc_gen = new TrivialDiscGenerator(); WriteGeneratedMesh(disc_gen, "meshgen_Disc.obj"); TrivialRectGenerator rect_gen = new TrivialRectGenerator(); WriteGeneratedMesh(rect_gen, "meshgen_Rect.obj"); GriddedRectGenerator gridrect_gen = new GriddedRectGenerator(); WriteGeneratedMesh(gridrect_gen, "meshgen_GriddedRect.obj"); PuncturedDiscGenerator punc_disc_gen = new PuncturedDiscGenerator(); WriteGeneratedMesh(punc_disc_gen, "meshgen_PuncturedDisc.obj"); TrivialBox3Generator box_gen = new TrivialBox3Generator(); Frame3f f = Frame3f.Identity; f.Rotate(Quaternionf.AxisAngleD(Vector3f.AxisY, 45.0f)); f.Rotate(Quaternionf.AxisAngleD(Vector3f.AxisZ, 45.0f)); box_gen.Box = new Box3d(f.Origin, f.X, f.Y, f.Z, new Vector3d(3, 2, 1)); WriteGeneratedMesh(box_gen, "meshgen_TrivialBox_shared.obj"); box_gen.NoSharedVertices = true; WriteGeneratedMesh(box_gen, "meshgen_TrivialBox_noshared.obj"); RoundRectGenerator roundrect_gen = new RoundRectGenerator(); roundrect_gen.Width = 2; WriteGeneratedMesh(roundrect_gen, "meshgen_RoundRect.obj"); GridBox3Generator gridbox_gen = new GridBox3Generator(); WriteGeneratedMesh(gridbox_gen, "meshgen_GridBox_shared.obj"); gridbox_gen.NoSharedVertices = true; WriteGeneratedMesh(gridbox_gen, "meshgen_GridBox_noshared.obj"); Sphere3Generator_NormalizedCube normcube_gen = new Sphere3Generator_NormalizedCube(); WriteGeneratedMesh(normcube_gen, "meshgen_Sphere_NormalizedCube_shared.obj"); normcube_gen.NoSharedVertices = true; normcube_gen.Box = new Box3d(new Frame3f(Vector3f.One, Vector3f.One), Vector3d.One * 1.3); WriteGeneratedMesh(normcube_gen, "meshgen_Sphere_NormalizedCube_noshared.obj"); TubeGenerator tube_gen = new TubeGenerator() { Vertices = new List <Vector3d>() { Vector3d.Zero, Vector3d.AxisX, 2 * Vector3d.AxisX, 3 * Vector3d.AxisX }, Polygon = Polygon2d.MakeCircle(1, 16) }; WriteGeneratedMesh(tube_gen, "meshgen_TubeGenerator.obj"); tube_gen.Polygon.Translate(Vector2d.One); tube_gen.CapCenter = Vector2d.One; WriteGeneratedMesh(tube_gen, "meshgen_TubeGenerator_shifted.obj"); }
public void UpdateTracking(Cockpit cockpit, fCamera camera) { fGameObject cockpitGO = cockpit.RootGameObject; if (!bInitialized) { currentFrame = cockpit.GetLevelViewFrame(CoordSpace.WorldCoords); currentFrame.ConstrainedAlignAxis(2, Vector3f.AxisZ, Vector3f.AxisY); bInitialized = true; } Vector3f vCamFW = camera.Forward(); vCamFW[1] = 0; vCamFW.Normalize(); // I don't think this is strictly necessary but // better to be safe for now... Vector3f vCamPos = camera.GetPosition(); //if (tracking_debug == null) // tracking_debug = UnityUtil.CreatePrimitiveGO("tracking_indicator", PrimitiveType.Sphere, MaterialUtil.CreateStandardMaterial(Color.green), false); //tracking_debug.transform.position = vCamPos + 15.0f * vCamFW; //if (tracking_avg == null) { // tracking_avg = UnityUtil.CreatePrimitiveGO("tracking_indicator", PrimitiveType.Sphere, MaterialUtil.CreateStandardMaterial(Color.blue), false); // tracking_avg.transform.localScale = new Vector3(0.5f, 0.5f, 0.5f); //} //tracking_avg.transform.position = vCamPos + 10.0f * vSlowViewDirTrack; //tracking_debug.SetVisible(false); //tracking_avg.SetVisible(false); if (vSlowViewDirTrack == Vector3f.Zero) { vSlowViewDirTrack = vCamFW; } float slowTrackSpeed = 0.05f; vSlowViewDirTrack = VRUtil.AngleLerp(vSlowViewDirTrack, vCamFW, slowTrackSpeed); // head position tracking if (IsLocked == false) { cockpitGO.SetPosition(vCamPos); } //Vector3 vDelta = (camera.transform.position - RootGameObject.transform.position); //if (vDelta.magnitude > 0.2f) // RootGameObject.transform.position = camera.transform.position; ////else if ( vDelta.magnitude > 0.05f) //else // RootGameObject.transform.position = // (1.0f - TrackingSpeed) * RootGameObject.transform.position + // (TrackingSpeed) * camera.transform.position; float RotationSpeed = 200.0f; float WarmupTrackingAngleThresh = 55.0f; float ImmediateTrackingAngleThresh = 65.0f; float StopTrackingAngleThresh = 5.0f; float TrackingWarmupDelay = 2.0f; float TrackingCooldownDelay = 0.75f; //Vector3 vCockpitFW = cockpitGO.transform.forward; Vector3f vCockpitFW = currentFrame.Z; float fSlowHDeviation = VRUtil.PlaneAngle(vCockpitFW, vSlowViewDirTrack); float fActualViewDeviation = VRUtil.PlaneAngle(vCockpitFW, vCamFW); bool bDoTrack = false; if (eState == TrackingState.NotTracking) { //tracking_debug.GetComponent<Renderer>().material = MaterialUtil.CreateStandardMaterial(Color.green); if (fSlowHDeviation > WarmupTrackingAngleThresh) { set_tracking_state(TrackingState.TrackingWarmup); stateChangeStartTime = FPlatform.RealTime(); } } else if (eState == TrackingState.TrackingWarmup) { //tracking_debug.GetComponent<Renderer>().material = MaterialUtil.CreateStandardMaterial(Color.yellow); if (fSlowHDeviation > ImmediateTrackingAngleThresh) { set_tracking_state(TrackingState.Tracking); } else if (fSlowHDeviation > WarmupTrackingAngleThresh) { if ((FPlatform.RealTime() - stateChangeStartTime) > TrackingWarmupDelay) { set_tracking_state(TrackingState.Tracking); } } else { set_tracking_state(TrackingState.NotTracking); } } else if (eState == TrackingState.Tracking) { bDoTrack = true; //tracking_debug.GetComponent<Renderer>().material = MaterialUtil.CreateStandardMaterial(Color.red); if (fActualViewDeviation < StopTrackingAngleThresh) { set_tracking_state(TrackingState.TrackingCooldown); stateChangeStartTime = FPlatform.RealTime(); } } else if (eState == TrackingState.TrackingCooldown) { bDoTrack = true; //tracking_debug.GetComponent<Renderer>().material = MaterialUtil.CreateStandardMaterial(Color.gray); if (fActualViewDeviation < StopTrackingAngleThresh) { if ((FPlatform.RealTime() - stateChangeStartTime) > TrackingCooldownDelay) { set_tracking_state(TrackingState.NotTracking); bDoTrack = false; } } else { set_tracking_state(TrackingState.Tracking); } } if (IsLocked) { bDoTrack = false; set_tracking_state(TrackingState.NotTracking); } if (bDoTrack) { float dt = (float)(FPlatform.RealTime() - animation_last_time); float fDelta = RotationSpeed * dt; Vector3f vCurrent = new Vector3f(vCockpitFW[0], 0, vCockpitFW[2]).Normalized; Vector3f vTarget = new Vector3f(vSlowViewDirTrack[0], 0, vSlowViewDirTrack[2]).Normalized; //Vector3 vTarget = new Vector3(vCamFW[0], 0, vCamFW[2]).normalized; Vector3f c = Vector3f.Cross(vCurrent, vTarget); float a = Vector3f.AngleD(vCurrent, vTarget); float fSign = (c[1] < 0) ? -1.0f : 1.0f; float fRotAngle = Math.Min(a, fDelta) * fSign; currentFrame.Rotate(Quaternionf.AxisAngleD(Vector3f.AxisY, fRotAngle)); } cockpitGO.SetRotation(currentFrame.Rotation); animation_last_time = FPlatform.RealTime(); if (indicator == null) { indicator = new CockpitTrackingWidget(); indicator.Create(this, cockpit); cockpit.AddUIElement(indicator, false); } indicator.EnableIndicator = show_indicator; }
public static void SwapUpDirection(FScene scene, List <PrintMeshSO> objects) { AxisAlignedBox3f sceneBounds = AxisAlignedBox3f.Empty; Vector3f sharedOrigin = Vector3f.Zero; foreach (var meshSO in objects) { sharedOrigin += meshSO.GetLocalFrame(CoordSpace.SceneCoords).Origin; sceneBounds.Contain(meshSO.GetBoundingBox(CoordSpace.SceneCoords).ToAABB()); } sharedOrigin /= objects.Count; foreach (var so in objects) { Frame3f curF = so.GetLocalFrame(CoordSpace.SceneCoords); UpDirection from = so.UpDirection; UpDirection to = (from == UpDirection.YUp) ? UpDirection.ZUp : UpDirection.YUp; Quaternionf rotate = Quaternionf.AxisAngleD(Vector3f.AxisX, (to == UpDirection.YUp) ? -90 : 90); Frame3f newF = curF; newF.RotateAround(sharedOrigin, rotate); TransformSOChange upChange = new TransformSOChange(so, newF, CoordSpace.SceneCoords) { OnApplyF = (x) => { so.UpDirection = to; }, OnRevertF = (x) => { so.UpDirection = from; } }; scene.History.PushChange(upChange, false); } AxisAlignedBox3f newSceneBounds = AxisAlignedBox3f.Empty; foreach (var meshSO in objects) { newSceneBounds.Contain(meshSO.GetBoundingBox(CoordSpace.SceneCoords).ToAABB()); } Vector3f startBase = sceneBounds.Center; startBase.y = 0; Vector3f newBase = newSceneBounds.Center; newBase.y = newSceneBounds.Min.y; Vector3f df = startBase - newBase; foreach (var so in objects) { Frame3f curF = so.GetLocalFrame(CoordSpace.SceneCoords); Frame3f newF = curF.Translated(df); TransformSOChange centerChange = new TransformSOChange(so, newF, CoordSpace.SceneCoords); scene.History.PushChange(centerChange, false); } // reposition pivots at base of List <Frame3f> setF = new List <Frame3f>(); foreach (var so in objects) { Frame3f objF = so.GetLocalFrame(CoordSpace.ObjectCoords); Vector3f center = so.GetBoundingBox(CoordSpace.SceneCoords).Center; center.y = 0; Frame3f sceneF = new Frame3f(center); setF.Add(sceneF); } for (int k = 0; k < objects.Count; ++k) { RepositionPivotChangeOp change = new RepositionPivotChangeOp(setF[k], objects[k], CoordSpace.SceneCoords); scene.History.PushChange(change, false); } }